UART 简介
UART(Universal Asynchronous Receiver/Transmitter)通用异步收发传输器,UART 作为异步串口通信协议的一种,工作原理是将传输数据的每个字符一位接一位地传输。是在应用程序开发过程中使用频率最高的数据总线。
UART 串口的特点是将数据一位一位地顺序传送,只要 **2 根传输线就可以实现双向通信,一根线发送数据的同时用另一根线接收数据。**UART 串口通信有几个重要的参数,分别是波特率、起始位、数据位、停止位和奇偶检验位,对于两个使用 UART 串口通信的端口,这些参数必须匹配,否则通信将无法正常完成。UART 串口传输的数据格式如下图所示:
起始位:表示数据传输的开始,电平逻辑为 “0” 。
数据位:可能值有 5、6、7、8、9,表示传输这几个 bit 位数据。一般取值为 8,因为一个 ASCII 字符值为 8 位。
奇偶校验位:用于接收方对接收到的数据进行校验,校验 “1” 的位数为偶数(偶校验)或奇数(奇校验),以此来校验数据传送的正确性,使用时不需要此位也可以。
停止位: 表示一帧数据的结束。电平逻辑为 “1”。
波特率:串口通信时的速率,它用单位时间内传输的二进制代码的有效位(bit)数来表示,其单位为每秒比特数 bit/s(bps)。常见的波特率值有 4800、9600、14400、38400、115200等,数值越大数据传输的越快,波特率为 115200 表示每秒钟传输 115200 位数据。
#define RT_DEVICE_FLAG_STREAM 0x040 /* 流模式 */
/* 接收模式参数 */
#define RT_DEVICE_FLAG_INT_RX 0x100 /* 中断接收模式 */
#define RT_DEVICE_FLAG_DMA_RX 0x200 /* DMA 接收模式 */
/* 发送模式参数 */
#define RT_DEVICE_FLAG_INT_TX 0x400 /* 中断发送模式 */
#define RT_DEVICE_FLAG_DMA_TX 0x800 /* DMA 发送模式 */
串口数据接收和发送数据的模式分为3种:中断模式、轮询模式、DMA模式。
在使用的时候,这3种模式只能选其1,若串口的打开参数oflags没有指定使用中断模式或者DMA模式,则默认使用轮询模式。
DMA(Direct Memory Access)即直接存储器访问。
DMA传输方式无需CPU直接控制传输,也没有中断处理方式那样保留现场和恢复现场的过程,通过DMA控制器为RAM与I/O设备开辟一条直接传输数据的通路,这就节省了CPU的资源来做其它操作。
使用 DMA 传输可以连续获取或发送一段信息而不占用中断或延时,在通信频繁或有大段信息要传输时非常有用。
控制串口设备
通过控制接口,应用程序可以对串口设备进行配置,如波特率、数据位、校验位、接收缓冲区大小、停止位等参数的修改。控制函数如下所示:
rt_err_t rt_device_control(rt_device_t dev, rt_uint8_t cmd, void* arg);
- dev:设备句柄
- cmd:命令控制字,可取值:RT_DEVICE_CTRL_CONFIG
- arg:控制的参数,可取类型:strcut serial_configure
struct serial_configure
{rt_uint32_t baud_rate; /* 波特率 */rt_uint32_t data_bits :4; /* 数据位 */rt_uint32_t stop_bits :2; /* 停止位 */rt_uint32_t parity :2; /* 奇偶校验位 */rt_uint32_t bit_order :1; /* 高位在前或者低位在前 */rt_uint32_t invert :1; /* 模式 */rt_uint32_t bufsz :16; /* 接收数据缓冲区大小 */rt_uint32_t reserved :4; /* 保留位 */
};/* 波特率可取值 */
#define BAUD_RATE_2400 2400
#define BAUD_RATE_4800 4800
#define BAUD_RATE_9600 9600
#define BAUD_RATE_19200 19200
#define BAUD_RATE_38400 38400
#define BAUD_RATE_57600 57600
#define BAUD_RATE_115200 115200
#define BAUD_RATE_230400 230400
#define BAUD_RATE_460800 460800
#define BAUD_RATE_921600 921600
#define BAUD_RATE_2000000 2000000
#define BAUD_RATE_3000000 3000000
/* 数据位可取值 */
#define DATA_BITS_5 5
#define DATA_BITS_6 6
#define DATA_BITS_7 7
#define DATA_BITS_8 8
#define DATA_BITS_9 9
/* 停止位可取值 */
#define STOP_BITS_1 0
#define STOP_BITS_2 1
#define STOP_BITS_3 2
#define STOP_BITS_4 3
/* 极性位可取值 */
#define PARITY_NONE 0
#define PARITY_ODD 1
#define PARITY_EVEN 2
/* 高低位顺序可取值 */
#define BIT_ORDER_LSB 0
#define BIT_ORDER_MSB 1
/* 模式可取值 */
#define NRZ_NORMAL 0 /* normal mode */
#define NRZ_INVERTED 1 /* inverted mode */
/* 接收数据缓冲区默认大小 */
#define RT_SERIAL_RB_BUFSZ 64
接收缓冲区:当串口使用中断接收模式打开时,串口驱动框架会根据RT_SERIAL_RB_BUFSIZE大小开辟一块缓冲区用于保存接收到的数据,底层驱动接收到一个数据,都会在中断服务程序里面将数据放入缓冲区。
#define RT_SERIAL_CONFIG_DEFAULT \
{ \BAUD_RATE_115200, /* 115200 bits/s */ \DATA_BITS_8, /* 8 databits */ \STOP_BITS_1, /* 1 stopbit */ \PARITY_NONE, /* No parity */ \BIT_ORDER_LSB, /* LSB first sent */ \NRZ_NORMAL, /* Normal mode */ \RT_SERIAL_RB_BUFSZ, /* Buffer size */ \0 \
}
默认串口配置接收数据缓冲区大小为RT_SERIAL_RB_BUFSZ,即64字节。
若一次性数据接收字节数很多,没有及时读取数据,那么缓冲区的数据将会被新接收到的数据覆盖,造成数据丢失,建议调大缓冲区,通过control接口修改。
open设备之后,缓冲区大小不可更改。
若实际使用串口的配置参数与默认配置参数不符,则用户可以通过应用代码进行修改。修改串口配置参数,如波特率、数据位、校验位、缓冲区接收 buffsize、停止位等.