UART

调试程序时,我们可以使用查看变量的方法,但是还是不能离开调试信息的打印。。。。。在开始其他实验时,首先把uart功能实验,方便调试。      

1.UART 支持中断模式和DMA模式

2.如果是使用系统时钟,UART最高能支持115.2k/s的数据传输,如果是使用外部的时钟,速度将更高,每道uart有FIFO模式和非FIFO模式,在FIFO模式中有两个64字节的FIFO分别用于接收和发送数据,在非FIFO模式中只有1字节的缓存区

3.下面是uart的结果图

 

4..从上面的结构图可以看出,UART由:波特率发生器,发送缓存和接收缓存,控制单元四个部分组成,波特率发生器可以是系统时钟(PCLK,FCLK/N)或者外部时钟(UEXTCLK),发送器和接收器各包含一个64字节的FIFO和数据移位器。要发送数据时,先将数据写入到FIFO接着在发送前复制到发送移位器中,随后将数据从发送数据引脚(TXDn)移出;接收数据时,从接收数据引脚(RXDn)移入收到的数据,接着从移位器复制到FIFO。

 

5.

在串行通讯处理中,常常看到硬件流控制(RTS/CTS)和软件流控制(XON/XOFF)这两个选项,这就是两个流控制的选项,目前流控制主要应用于调制解调器的数据通讯中

硬件流控制常用的有RTS/CTS流控制和DTR/DSR(数据终端就绪/数据设置就绪)流控制。
由于电缆线的限制,我们在普通的控制通讯中一般不用硬件流控制,而用软件流控制。一般通过XON/XOFF来实现软件流控制。常用方法是:当接收端的输入缓冲区内数据量超过设定的高位时,就向数据发送端发出XOFF字符(十进制的19或Control-S,设备编程说明书应该有详细阐述),发送端收到XOFF字符后就立即停止发送数据;当接收端的输入缓冲区内数据量低于设定的低位时,就向数据发送端发出XON字符(十进制的17或Control-Q),发送端收到XON字符后就立即开始发送数据。一般可以从设备配套源程序中找到发送的是什么字符。

应该注意,若传输的是二进制数据,标志字符也有可能在数据流中出现而引起误操作,这是软件流控制的缺陷,而硬件流控制不会有这个问题。

 在2440中,只有当CTS信号有效才可以发送数据,CTS有效表明其他的UARTFIFO准备好接收数据,在接收数据之前,RTS应该是有效的,并且FIFO应该是大于32字节,否则为非有效状态 

注意:2440的UART 2不支持自动流控制(AFC)

6.LoopBack操作模式:
S3C2410 CPU
UART提供了一种测试模式,也就是这里所说的LoopBack模式。在设计系统的具体应用时,为了判断通讯故障是由于外部的数据链路上的问题,还是CPU内驱动程序或CPU本身的问题,这就需要采用LoopBack模式来进行测试LoopBack模式中,资料发送端TXDUART内部就从逻辑上与接收端RXD连在一起,并可以来验证资料的收发是否正常

7.uart波特率计算公式:

 UBRDIVn  = (int)( UART clock / ( buad rate x 16) ) –1

 

For example, if the baud-rate is 115200 bps and UART clock is 40 MHz, UBRDIVn is:

UBRDIVn  = (int)(40000000 / (115200 x 16) ) -1

= (int)(21.7) -1    [round to the nearest whole number]

= 22 -1 = 21

 

 

8.核心代码:

  1. #include "uart.h"  
  2. #include "2440addr.h"  
  3. #include <stdlib.h>  
  4. #include <stdarg.h>  
  5. #include <string.h>  
  6. #include <stdlib.h>  
  7. #include <stdio.h>  
  8. #include <ctype.h>   
  9.   
  10. //端口和波特率初始化   
  11. void uart_init(int baud)   
  12. {   
  13.   
  14.    int i;   
  15.     //*** PORT H GROUP   
  16.     //Ports  :  GPH10    GPH9  GPH8 GPH7  GPH6  GPH5 GPH4 GPH3 GPH2 GPH1  GPH0    
  17.     //Signal : CLKOUT1 CLKOUT0 UCLK nCTS1 nRTS1 RXD1 TXD1 RXD0 TXD0 nRTS0 nCTS0   
  18.     //Binary :   00   ,  00     00 , 00    00  , 00  00 , 10   10 , 10    10   
  19.     rGPHCON = 0xaa ;   
  20.     //rGPHCON = 0x2a0aaa ;   
  21.     rGPHUP  = 0x7ff;    // The pull up function is disabled GPH[10:0]   
  22.    // 0  0  000  0 11   
  23.     rULCON0 = 0x3;//Line control register : Normal,No parity,1 stop,8 bits   
  24.      // [15:12] [11:10]    [9]   [8]  [7]  [6]    [5]  [4]  [3:2]  [1:0]   
  25.      //            00      1       0   0     1     0     0    01     01   
  26.         
  27.     rUCON0 =0x245;   
  28.     rUFCON0 = 0x0;   //不使用FIFO   
  29.     rUMCON0  = 0x00;     // 不使用流控   
  30.     rUBRDIV0=( (int)(PCLK/16./baud+0.5) -1 );   //Baud rate divisior register 0   
  31.     for(i=0;i<100;i++);   
  32.        
  33.   
  34.        
  35. }   
  36.   
  37. //字节发送   
  38. void uart_send_byte(int data)   
  39. {   
  40.     if(data == '\n') {    //结束符   
  41.         while(!(rUTRSTAT0 &0x2)) ;   //等待发送缓冲区为空   
  42.         WrUTXH0('\r');  //直接写数据到UTXH0寄存器中   
  43.     }   
  44.     //特别需要注意下面的语句不是用else和if并列   
  45.     while(!(rUTRSTAT0 &0x2)) ;  //等待发送缓冲区为空   
  46.     WrUTXH0(data);   
  47.   
  48. }   
  49.   
  50. //发送字符串   
  51. void uart_send_string(char *string)   
  52. {   
  53.     while(*string)   
  54.         uart_send_byte(*string++);   
  55. }   
  56.   
  57.   
  58. //实现类似printf函数变量输出   
  59. void uart_printf(char *fmt,...)   
  60. {   
  61.     va_list ap;   
  62.     char string[256];   
  63.        
  64.     va_start(ap,fmt);   
  65.     vsprintf(string,fmt,ap);   
  66.     uart_send_string(string);   
  67.     va_end(ap);   
  68. }   
  69.   
  70. //从终端读取单个字符   
  71. char uart_getch(void)   
  72. {   
  73.     while(!(rUTRSTAT0 &0x1)) ; //等待接收缓冲区中不为空   
  74.     return  RdURXH0();    //直接返回接收数据寄存器URXH0中的值   
  75. }   
  76.   
  77. //获取数据   
  78. char uart_get_key(void)   
  79. {   
  80.    if(rUTRSTAT0 &0x1)  //检查buffer中是否有数据   
  81.     return  RdURXH0();    
  82.     else    
  83.     return 0;   
  84. }   
  85.   
  86.   
  87. //从终端得到一个字符串,保存到string中   
  88. void uart_get_string(char *string)   
  89. {   
  90.     char *string2 = string;   
  91.     char c;   
  92.     while((c = uart_get_key())!='\r')   //回车   
  93.     {   
  94.         if(c == '\b') {   //backspace   
  95.             if((int)string2 < (int)string) {   
  96.                 uart_printf("\b \b");  //删除最后一个字符   
  97.                 string --;   
  98.             }   
  99.         }  else {   
  100.         *string++ = c;   
  101.         uart_send_byte(c);   //将输入的字符回显到终端,如果没有该语句在终端上看不到输入的内容   
  102.         }   
  103.     }   
  104.     *string = '\0';   
  105.     uart_send_byte('\n');   
  106. }  
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值