uart串口发送---那些年我们一起玩mini2440(arm9)裸机

Uart工作原理:

数据通信方式为:并行通信串行通信两种:

§并行通信:利用多条数据线将数据的各位同时传送

它的特点是:传输速度快,是用于短距离通信;

§串行通信:利用一条数据线将数据一位位地顺序传送。

特点是通信线路简单,利用简单的线缆就实现通信,低成本,是用于远距离通信。

 

异步通信:

ª异步通信:以一个字符为传输单位,通过两个字符间的时间间隔是不固定的,然而同一字符中的两个相邻位之间的时间间隔是固定的

ª通信协议:是指通信双方约定的一些规则。在异步通讯时,对数据格式有如下约定:规定有空闲位、起始位、资料位、奇偶校验位、停止位。

 

 

UART驱动程序设计

 

UART初始化:1.发送数据;2.接收数据;

UART初始化:1.设置波特率; 2.设置数据传输格式;3.选择通道工作模式;

 

 

一.设置波特率:UBRDIV

 

s3c2440中,通过UBRDIV(p352)寄存器可以设定UART的波特率。Uart0Uart1Uart2分别对应UBRDIV0UBRDIV1UBRDIV2

      到底UBRDIV寄存器中的值与波特率有何关系?

      UBRDIV=(int)UART clock / (buad  rate *16)-1

UART clockPCLK or FCLK/ n or UEXTCLK

如波特率为115200bpsUART时钟为40MHZ

UBRDIV =(int) (40MHZ /(115200*16))-1

 

二.设置数据传输格式ULCON

s3c2440中,通过ULCON(page341),可以设置传输格式(有多少个数据位是否使用校验位、是奇校验还是偶校验,有多少个停止位、是否使用流量控制

Uart0Uart1Uart2分别对应ULCON0ULCON1ULCON2.

 

三.设置通道工作模式UCON

s3c2440中,通过UCON(page342),可以设置UART通道的工作模式,(中断模式、查询模式、或DMA模式)

Uart0Uart1Uart2分别对应UCON0UCON1UCON2.

这三步都属于初始化:初始化完成之后à发送或/接收数据

 

发送数据:

将要发送的数据写UTXHn, UART会将保存到缓冲区中,并自动发出去

UTXH0UTXH1UTXH2

 

接收数据:

UART收到数据时UTRSTATn寄存器bit[0]被置1CPU读取URXHn寄存器,即可获得数据。

URXH0URXH1URXH2寄存器中读取数据

 

 pasting

  1. Main.c  
  2.   
  3. <span style="color:#000000;">#define   GLOBAL_CLK           1  
  4.   
  5. #include <stdlib.h>  
  6.   
  7. #include <string.h>  
  8.   
  9. #include "def.h"  
  10.   
  11. #include "option.h"  
  12.   
  13. #include "2440addr.h"  
  14.   
  15. #include "2440lib.h"  
  16.   
  17. #include "2440slib.h"  
  18.   
  19. #include "mmu.h"  
  20.   
  21. #include "profile.h"  
  22.   
  23. #include "memtest.h"  
  24.   
  25.    
  26.   
  27. static void cal_cpu_bus_clk(void);  
  28.   
  29. void Set_Clk(void);  
  30.   
  31. /*************************************************  
  32.   
  33. Function name: delay  
  34.   
  35. Parameter    : times  
  36.   
  37. Description    :延时函数  
  38.   
  39. Return          : void  
  40.   
  41. Argument     : void  
  42.   
  43. Autor & date : Daniel  
  44.   
  45. **************************************************/  
  46.   
  47. void delay(int times)  
  48.   
  49. {  
  50.   
  51.     int i,j;  
  52.   
  53.     for(i=0;i<times;i++)  
  54.   
  55.        for(j=0;j<400;j++);  
  56.   
  57. }  
  58.   
  59. /*************************************************  
  60.   
  61. Function name: Main  
  62.   
  63. Parameter    : void  
  64.   
  65. Description     : 主功能函数,实现了串口的收发功能  
  66.   
  67.                首先想串口发送十次“hello world”,  
  68.   
  69. Return            : void  
  70.   
  71. Argument     : void  
  72.   
  73. Autor & date : Daniel  
  74.   
  75. **************************************************/  
  76.   
  77. void Main(void)  
  78.   
  79. {       
  80.   
  81.     int i;  
  82.   
  83.     int Scom=0;  
  84.   
  85.     Set_Clk();  
  86.   
  87.     beep_init();  
  88.   
  89.       
  90.   
  91.     /*设置波特率、数据位、停止位、校验位*/  
  92.   
  93.     Uart_Init(0,115200);  
  94.   
  95.     Uart_Select(Scom);  
  96.   
  97.     for(i=0;i<10;i++)  
  98.   
  99.     Uart_Printf("\nHello World!\n");  
  100.   
  101.       
  102.   
  103.     while(1)  
  104.   
  105.     {  
  106.   
  107.       while(Uart_GetKey()=='r')  
  108.   
  109.       {  
  110.   
  111.           for(i=0;i<10;i++)  
  112.   
  113.           beep_run();  
  114.   
  115.           Uart_Printf("\nBeep Quit!\n");  
  116.   
  117.       }  
  118.   
  119.        }  
  120.   
  121.    
  122.   
  123. }       
  124.   
  125.        
  126.   
  127. /*************************************************  
  128.   
  129. Function name: Set_Clk()  
  130.   
  131. Parameter    : void  
  132.   
  133. Description     : 设置CPU的时钟频率  
  134.   
  135. Return            : void  
  136.   
  137. Argument     : void  
  138.   
  139. Autor & date : Daniel  
  140.   
  141. **************************************************/  
  142.   
  143. void Set_Clk(void)  
  144.   
  145. {  
  146.   
  147.        int i;  
  148.   
  149.        U8 key;  
  150.   
  151.        U32 mpll_val = 0 ;  
  152.   
  153.        i = 2 ;                  //don't use 100M!  
  154.   
  155.                                //boot_params.cpu_clk.val = 3;  
  156.   
  157.        switch ( i ) {  
  158.   
  159.        case 0:     //200  
  160.   
  161.               key = 12;  
  162.   
  163.               mpll_val = (92<<12)|(4<<4)|(1);  
  164.   
  165.               break;  
  166.   
  167.        case 1:     //300  
  168.   
  169.               key = 13;  
  170.   
  171.               mpll_val = (67<<12)|(1<<4)|(1);  
  172.   
  173.               break;  
  174.   
  175.        case 2:     //400  
  176.   
  177.               key = 14;  
  178.   
  179.               mpll_val = (92<<12)|(1<<4)|(1);  
  180.   
  181.               break;  
  182.   
  183.        case 3:     //440!!!  
  184.   
  185.               key = 14;  
  186.   
  187.               mpll_val = (102<<12)|(1<<4)|(1);  
  188.   
  189.               break;  
  190.   
  191.        default:  
  192.   
  193.               key = 14;  
  194.   
  195.               mpll_val = (92<<12)|(1<<4)|(1);  
  196.   
  197.               break;  
  198.   
  199.        }  
  200.   
  201.          
  202.   
  203.        //init FCLK=400M, so change MPLL first  
  204.   
  205.        ChangeMPllValue((mpll_val>>12)&0xff, (mpll_val>>4)&0x3f, mpll_val&3);   //set the register--rMPLLCON  
  206.   
  207.        ChangeClockDivider(key, 12);    //the result of rCLKDIVN [0:1:0:1] 3-0 bit  
  208.   
  209.        cal_cpu_bus_clk();    //HCLK=100M   PCLK=50M  
  210.   
  211. }  
  212.   
  213. /*************************************************  
  214.   
  215. Function name: cal_cpu_bus_clk  
  216.   
  217. Parameter    : void  
  218.   
  219. Description     : 设置PCLK\HCLK\FCLK的频率  
  220.   
  221. Return            : void  
  222.   
  223. Argument     : void  
  224.   
  225. Autor & date : Daniel  
  226.   
  227. **************************************************/  
  228.   
  229. static void cal_cpu_bus_clk(void)  
  230.   
  231. {  
  232.   
  233.        static U32 cpu_freq;  
  234.   
  235.     static U32 UPLL;  
  236.   
  237.          
  238.   
  239.        U32 val;  
  240.   
  241.        U8 m, p, s;  
  242.   
  243.          
  244.   
  245.        val = rMPLLCON;  
  246.   
  247.        m = (val>>12)&0xff;  
  248.   
  249.        p = (val>>4)&0x3f;  
  250.   
  251.        s = val&3;  
  252.   
  253.    
  254.   
  255.        //(m+8)*FIN*2不要超出32位数!  
  256.   
  257.        FCLK = ((m+8)*(FIN/100)*2)/((p+2)*(1<<s))*100;     //FCLK=400M  FIN=12000000  
  258.   
  259.          
  260.   
  261.        val = rCLKDIVN;  
  262.   
  263.        m = (val>>1)&3;  
  264.   
  265.        p = val&1;       
  266.   
  267.        val = rCAMDIVN;  
  268.   
  269.        s = val>>8;  
  270.   
  271.          
  272.   
  273.        switch (m) {  
  274.   
  275.        case 0:  
  276.   
  277.               HCLK = FCLK;  
  278.   
  279.               break;  
  280.   
  281.        case 1:  
  282.   
  283.               HCLK = FCLK>>1;  
  284.   
  285.               break;  
  286.   
  287.        case 2:  
  288.   
  289.               if(s&2)  
  290.   
  291.                      HCLK = FCLK>>3;  
  292.   
  293.               else  
  294.   
  295.                      HCLK = FCLK>>2;  
  296.   
  297.               break;  
  298.   
  299.        case 3:  
  300.   
  301.               if(s&1)  
  302.   
  303.                      HCLK = FCLK/6;  
  304.   
  305.               else  
  306.   
  307.                      HCLK = FCLK/3;  
  308.   
  309.               break;  
  310.   
  311.        }  
  312.   
  313.          
  314.   
  315.        if(p)  
  316.   
  317.               PCLK = HCLK>>1;  
  318.   
  319.        else  
  320.   
  321.               PCLK = HCLK;  
  322.   
  323.          
  324.   
  325.        if(s&0x10)  
  326.   
  327.               cpu_freq = HCLK;  
  328.   
  329.        else  
  330.   
  331.               cpu_freq = FCLK;  
  332.   
  333.                 
  334.   
  335.        val = rUPLLCON;  
  336.   
  337.        m = (val>>12)&0xff;  
  338.   
  339.        p = (val>>4)&0x3f;  
  340.   
  341.        s = val&3;  
  342.   
  343.        UPLL = ((m+8)*FIN)/((p+2)*(1<<s));  
  344.   
  345.        UCLK = (rCLKDIVN&8)?(UPLL>>1):UPLL;  
  346.   
  347. }  
  348.   
  349. </span>   

 2440lib.c

 pasting

  1. #include "def.h"  
  2.   
  3. #include "option.h"  
  4.   
  5. #include "2440addr.h"  
  6.   
  7. #include "2440lib.h"  
  8.   
  9. #include "2440slib.h"  
  10.   
  11.    
  12.   
  13. #include <stdarg.h>  
  14.   
  15. #include <string.h>  
  16.   
  17. #include <stdlib.h>  
  18.   
  19. #include <stdio.h>  
  20.   
  21. #include <ctype.h>  
  22.   
  23. static int whichUart=0;  
  24.   
  25.    
  26.   
  27. void Port_Init0(void)  //IO端口初始化  
  28.   
  29. {  
  30.   
  31.        //*** PORT H GROUP  
  32.   
  33.   //Ports  :  GPH10 GPH9 GPH8 GPH7 GPH6 GPH5 GPH4 GPH3 GPH2 GPH1  GPH0 //Signal : CLKOUT1 CLKOUT0 UCLK nCTS1 nRTS1 RXD1 TXD1 RXD0 TXD0 nRTS0 nCTS0  
  34.   
  35.     //Binary :   10   ,  10     10 , 11    11  , 10   10 , 10   10 , 10    10  
  36.   
  37.      rGPHCON = 0x00faaa;  
  38.   
  39.      rGPHUP  = 0x7ff;    // The pull up function is disabled GPH[10:0]  
  40.   
  41. }  
  42.   
  43.    
  44.   
  45. void Uart_Init(int pclk,int baud)  
  46.   
  47. {  
  48.   
  49.     int i;  
  50.   
  51.     if(pclk == 0)  
  52.   
  53.     pclk    = PCLK;  
  54.   
  55.     rUFCON0 = 0x0;   //UART channel 0 FIFO control register, FIFO disable  
  56.   
  57.     rUMCON0 = 0x0;   //UART chaneel 0 MODEM control register, AFC disable(AFC:流量控制)  
  58.   
  59.    //UART0  
  60.   
  61.     rULCON0 = 0x3;   //Line control register : Normal,No parity,1 stop,8 bits  
  62.   
  63.      //    [10]       [9]     [8]        [7]        [6]      [5]         [4]           [3:2]        [1:0]  
  64.   
  65.      // Clock Sel,  Tx Int,  Rx Int, Rx Time Out, Rx err, Loop-back, Send break,  Transmit Mode, Receive Mode  
  66.   
  67.      //     0          1       0    ,     0          1        0           0     ,       01          01  
  68.   
  69.      //   PCLK       Level    Pulse    Disable    Generate  Normal      Normal        Interrupt or Polling  
  70.   
  71.     rUCON0  = 0x245;   // Control register  
  72.   
  73.     rUBRDIV0=( (int)(pclk/16./baud+0.5) -1 );   //Baud rate divisior register 0  
  74.   
  75.     for(i=0;i<100;i++);  
  76.   
  77. }  
  78.   
  79.    
  80.   
  81. //===================================================================  
  82.   
  83. void Uart_Select(int ch)  
  84.   
  85. {  
  86.   
  87.     whichUart = ch;  
  88.   
  89. }  
  90.   
  91. //=====================================================================  
  92.   
  93. void Uart_SendByte(int data)  
  94.   
  95. {  
  96.   
  97.     if(whichUart==0)  
  98.   
  99.     {  
  100.   
  101.         if(data=='\n')  
  102.   
  103.         {  
  104.   
  105.             while(!(rUTRSTAT0 & 0x2));  
  106.   
  107.            // Delay(1);                 //because the slow response of hyper_terminal  
  108.   
  109.             WrUTXH0('\r');  
  110.   
  111.         }  
  112.   
  113.         while(!(rUTRSTAT0 & 0x2));   //不为换行符时,Wait until THR is empty.  
  114.   
  115.       //  Delay(1);  
  116.   
  117.         WrUTXH0(data);//往寄存器写数据  
  118.   
  119.     }  
  120.   
  121.     else if(whichUart==1)  
  122.   
  123.     {  
  124.   
  125.         if(data=='\n')  
  126.   
  127.         {  
  128.   
  129.             while(!(rUTRSTAT1 & 0x2));  
  130.   
  131.             //Delay(1);                 //because the slow response of hyper_terminal  
  132.   
  133.             rUTXH1 = '\r';  
  134.   
  135.         }  
  136.   
  137.         while(!(rUTRSTAT1 & 0x2));   //Wait until THR is empty.  
  138.   
  139.         //Delay(1);  
  140.   
  141.         rUTXH1 = data;  
  142.   
  143.     }     
  144.   
  145.     else if(whichUart==2)  
  146.   
  147.     {  
  148.   
  149.         if(data=='\n')  
  150.   
  151.         {  
  152.   
  153.             while(!(rUTRSTAT2 & 0x2));  
  154.   
  155.             //Delay(1);                 //because the slow response of hyper_terminal  
  156.   
  157.             rUTXH2 = '\r';  
  158.   
  159.         }  
  160.   
  161.         while(!(rUTRSTAT2 & 0x2));   //Wait until THR is empty.  
  162.   
  163.         //Delay(1);  
  164.   
  165.         rUTXH2 = data;  
  166.   
  167.     }         
  168.   
  169. }                 
  170.   
  171.    
  172.   
  173. //====================================================================  
  174.   
  175. void Uart_SendString(char *pt)  
  176.   
  177. {  
  178.   
  179.     while(*pt)  
  180.   
  181.         Uart_SendByte(*pt++);  
  182.   
  183. }  
  184.   
  185. //=====================================================================  
  186.   
  187. //If you don't use vsprintf(), the code size is reduced very much.  
  188.   
  189. void Uart_Printf(char *fmt,...)  
  190.   
  191. {  
  192.   
  193.     va_list ap;  
  194.   
  195.     char string[256];  
  196.   
  197.    
  198.   
  199.     va_start(ap,fmt);//va_start、 va_end成对出现,ap指向fmt之后的参数  
  200.   
  201.     vsprintf(string,fmt,ap);//把ap之后的参数拷贝进string  
  202.   
  203.     Uart_SendString(string);  
  204.   
  205.     va_end(ap);  
  206.   
  207. }  

 

 中断方式,串口发送:

 

 pasting

  1. #define    GLOBAL_CLK             1  
  2.   
  3. #include <stdlib.h>  
  4.   
  5. #include <string.h>  
  6.   
  7. #include "def.h"  
  8.   
  9. #include "option.h"  
  10.   
  11. #include "2440addr.h"  
  12.   
  13. #include "2440lib.h"  
  14.   
  15. #include "2440slib.h"  
  16.   
  17. #include "mmu.h"  
  18.   
  19. #include "profile.h"  
  20.   
  21. #include "memtest.h"  
  22.   
  23.    
  24.   
  25.    
  26.   
  27. void Uart0INT_init(void);  
  28.   
  29. static void __irq IRQ_ISR_UART0(void);  
  30.   
  31. void Set_Clk(void);  
  32.   
  33. static void cal_cpu_bus_clk(void);  
  34.   
  35. /*************************************************  
  36.   
  37. Function name: delay  
  38.   
  39. Parameter    : times  
  40.   
  41. Description     : 延时函数  
  42.   
  43. Return            : void  
  44.   
  45. Argument     : void  
  46.   
  47. Autor & date : Daniel  
  48.   
  49. **************************************************/  
  50.   
  51. void delay(int times)  
  52.   
  53. {  
  54.   
  55.     int i,j;  
  56.   
  57.     for(i=0;i<times;i++)  
  58.   
  59.        for(j=0;j<400;j++);  
  60.   
  61. }  
  62.   
  63. /*************************************************  
  64.   
  65. Function name: Main  
  66.   
  67. Parameter    : void  
  68.   
  69. Description     : 主功能函数  
  70.   
  71. Return            : void  
  72.   
  73. Argument     : void  
  74.   
  75. Autor & date : Daniel  
  76.   
  77. **************************************************/  
  78.   
  79. int Main(void)  
  80.   
  81. {       
  82.   
  83.     Set_Clk();  
  84.   
  85.     MMU_Init();  
  86.   
  87.     Uart0INT_init();  
  88.   
  89.        return 0 ;  
  90.   
  91. }       
  92.   
  93. /*************************************************  
  94.   
  95. Function name: Uart0INT_init()  
  96.   
  97. Parameter    : void  
  98.   
  99. Description     : 中断初始化函数,用于配置中断所需要的  
  100.   
  101.                几个寄存器  
  102.   
  103. Return            : void  
  104.   
  105. Argument     : void  
  106.   
  107. Autor & date : Daniel  
  108.   
  109. **************************************************/     
  110.   
  111. void Uart0INT_init(void)  
  112.   
  113. {  
  114.   
  115.     
  116.   
  117.   Uart_Init( 0,115200);  
  118.   
  119.   Uart_Select(0);  
  120.   
  121.     
  122.   
  123.   rPRIORITY = 0x00000000;     /*默认优先级*/  
  124.   
  125.   rINTMOD = 0x00000000;       /*默认IRQ中断*/  
  126.   
  127.     
  128.   
  129.   /*清中断*/  
  130.   
  131.   ClearSubPending(BIT_SUB_RXD0);  
  132.   
  133.   ClearPending(BIT_UART0);  
  134.   
  135.     
  136.   
  137.   /*设置UART的ISR*/  
  138.   
  139.   pISR_UART0 = (U32)IRQ_ISR_UART0;  
  140.   
  141.   EnableIrq(BIT_UART0);  
  142.   
  143.   EnableSubIrq(BIT_SUB_RXD0);  
  144.   
  145.    
  146.   
  147. }  
  148.   
  149. /*************************************************  
  150.   
  151. Function name: IRQ_ISR_UART0()  
  152.   
  153. Parameter    : void  
  154.   
  155. Description     : 中断服务子程序,该子程序的作用就是把  
  156.   
  157.                串口收到的数据发送到超级终端。  
  158.   
  159. Return            : void  
  160.   
  161. Argument     : void  
  162.   
  163. Autor & date : Daniel  
  164.   
  165. **************************************************/  
  166.   
  167. static void __irq IRQ_ISR_UART0(void)  
  168.   
  169. {  
  170.   
  171.         if(rSUBSRCPND & 0x1)  
  172.   
  173.            {  
  174.   
  175.                      rUTXH0 = rURXH0;  /*这里没考虑回车*/  
  176.   
  177.                      ClearSubPending(BIT_SUB_RXD0);  
  178.   
  179.               }  
  180.   
  181.            ClearPending(BIT_UART0);  
  182.   
  183. }  
  184.   
  185.    
  186.   
  187. /*************************************************  
  188.   
  189. Function name: Set_Clk()  
  190.   
  191. Parameter    : void  
  192.   
  193. Description     : 设置CPU的时钟频率  
  194.   
  195. Return            : void  
  196.   
  197. Argument     : void  
  198.   
  199. Autor & date : Daniel  
  200.   
  201. **************************************************/  
  202.   
  203. void Set_Clk(void)  
  204.   
  205. {  
  206.   
  207.        int i;  
  208.   
  209.        U8 key;  
  210.   
  211.        U32 mpll_val = 0 ;  
  212.   
  213.        i = 2 ;                  //don't use 100M!  
  214.   
  215.                                //boot_params.cpu_clk.val = 3;  
  216.   
  217.        switch ( i ) {  
  218.   
  219.        case 0:     //200  
  220.   
  221.               key = 12;  
  222.   
  223.               mpll_val = (92<<12)|(4<<4)|(1);  
  224.   
  225.               break;  
  226.   
  227.        case 1:     //300  
  228.   
  229.               key = 13;  
  230.   
  231.               mpll_val = (67<<12)|(1<<4)|(1);  
  232.   
  233.               break;  
  234.   
  235.        case 2:     //400  
  236.   
  237.               key = 14;  
  238.   
  239.               mpll_val = (92<<12)|(1<<4)|(1);  
  240.   
  241.               break;  
  242.   
  243.        case 3:     //440!!!  
  244.   
  245.               key = 14;  
  246.   
  247.               mpll_val = (102<<12)|(1<<4)|(1);  
  248.   
  249.               break;  
  250.   
  251.        default:  
  252.   
  253.               key = 14;  
  254.   
  255.               mpll_val = (92<<12)|(1<<4)|(1);  
  256.   
  257.               break;  
  258.   
  259.        }  
  260.   
  261.          
  262.   
  263.        //init FCLK=400M, so change MPLL first  
  264.   
  265.        ChangeMPllValue((mpll_val>>12)&0xff, (mpll_val>>4)&0x3f, mpll_val&3);   //set the register--rMPLLCON  
  266.   
  267.        ChangeClockDivider(key, 12);    //the result of rCLKDIVN [0:1:0:1] 3-0 bit  
  268.   
  269.        cal_cpu_bus_clk();    //HCLK=100M   PCLK=50M  
  270.   
  271. }  
  272.   
  273. /*************************************************  
  274.   
  275. Function name: cal_cpu_bus_clk  
  276.   
  277. Parameter    : void  
  278.   
  279. Description     : 设置PCLK\HCLK\FCLK的频率  
  280.   
  281. Return            : void  
  282.   
  283. Argument     : void  
  284.   
  285. Autor & date : Daniel  
  286.   
  287. **************************************************/  
  288.   
  289. static void cal_cpu_bus_clk(void)  
  290.   
  291. {  
  292.   
  293.        static U32 cpu_freq;  
  294.   
  295.     static U32 UPLL;  
  296.   
  297.          
  298.   
  299.        U32 val;  
  300.   
  301.        U8 m, p, s;  
  302.   
  303.          
  304.   
  305.        val = rMPLLCON;  
  306.   
  307.        m = (val>>12)&0xff;  
  308.   
  309.        p = (val>>4)&0x3f;  
  310.   
  311.        s = val&3;  
  312.   
  313.    
  314.   
  315.        //(m+8)*FIN*2不要超出32位数!  
  316.   
  317.        FCLK = ((m+8)*(FIN/100)*2)/((p+2)*(1<<s))*100;     //FCLK=400M  FIN=12000000  
  318.   
  319.          
  320.   
  321.        val = rCLKDIVN;  
  322.   
  323.        m = (val>>1)&3;  
  324.   
  325.        p = val&1;       
  326.   
  327.        val = rCAMDIVN;  
  328.   
  329.        s = val>>8;  
  330.   
  331.          
  332.   
  333.        switch (m) {  
  334.   
  335.        case 0:  
  336.   
  337.               HCLK = FCLK;  
  338.   
  339.               break;  
  340.   
  341.        case 1:  
  342.   
  343.               HCLK = FCLK>>1;  
  344.   
  345.               break;  
  346.   
  347.        case 2:  
  348.   
  349.               if(s&2)  
  350.   
  351.                      HCLK = FCLK>>3;  
  352.   
  353.               else  
  354.   
  355.                      HCLK = FCLK>>2;  
  356.   
  357.               break;  
  358.   
  359.        case 3:  
  360.   
  361.               if(s&1)  
  362.   
  363.                      HCLK = FCLK/6;  
  364.   
  365.               else  
  366.   
  367.                      HCLK = FCLK/3;  
  368.   
  369.               break;  
  370.   
  371.        }  
  372.   
  373.          
  374.   
  375.        if(p)  
  376.   
  377.               PCLK = HCLK>>1;  
  378.   
  379.        else  
  380.   
  381.               PCLK = HCLK;  
  382.   
  383.          
  384.   
  385.        if(s&0x10)  
  386.   
  387.               cpu_freq = HCLK;  
  388.   
  389.        else  
  390.   
  391.               cpu_freq = FCLK;  
  392.   
  393.                 
  394.   
  395.        val = rUPLLCON;  
  396.   
  397.        m = (val>>12)&0xff;  
  398.   
  399.        p = (val>>4)&0x3f;  
  400.   
  401.        s = val&3;  
  402.   
  403.        UPLL = ((m+8)*FIN)/((p+2)*(1<<s));  
  404.   
  405.        UCLK = (rCLKDIVN&8)?(UPLL>>1):UPLL;  
  406.   
  407. }  

 

 

 

 

 

 

 

 

 

 

 

起始位:先发一个逻辑“0”信号,表示传输字符的开始;

数据位:紧接在起始位之后。数据位的个数可以是45678等,从最低位开始传送,靠时钟定位。

奇偶校验位:数据位加上这一位后,使得“1”的位数应为偶数(偶校验)或(奇校验),以此校验数据传送的正确性。

停止位:它是一个字符数据的结束标志。

空闲位:处于逻辑“1”状态,表示当前线路没有数据传送。

 

波特率:

是衡量数据传送率的指标:记录每秒中传送的二进制位数。例如:数据传送速率为120字符、每秒。而每一个字符为10位,则其传送的波特率为10*120=1200/=1200波特率

 

UART基本原理

通用异步收发器,简称UART,即“Universal Asynchronous Receiver Transmitter”,它用来传输串行数据;

 

发送数据时:

CPU将并行数据写入UARTUART按照一定的格式在一根电线上串行发出;

接收数据时:

UART检测另一根电线上的信号,将串行数据放在缓冲区中,CPU可读取UART获得的这些数据。

 

posted @ 2014-12-08 11:02  来杯绿茶  阅读(676)  评论(0编辑  收藏  举报