串口
串口的发送与接收
简单理解一下,51单片机的串口,是个全双工的串口,发送数据的同时,还可以接收数据。
串口有以下几个寄存器
- 串行端口缓冲寄存器(SBUF): 地址是99H。有两个缓冲器,一个是只写发送寄存器,一个是只读接收寄存器。
- 串行端口控制寄存器(SCON):地址是98H,可以位寻址。如表1-1所示:
表1-1SCON简表
位 | 符号 | 地址 | 模式 |
---|---|---|---|
SCON.7 | SM0 | 9FH | 串行端口模式位0 |
SCON.6 | SM1 | 9EH | 串行端口模式位1 |
SCON.5 | SM2 | 9DH | 串行端口模式位2 |
SCON.4 | REN | 9CH | 置1为允许接收 |
SCON.3 | TB8 | 9BH | 发送数据的位8 |
SCON.2 | RB0 | 9AH | 接收数据的位8 |
SCON.1 | TI | 99H | 发送中断标志,字符数据发送完毕时硬件置位,由软件清零 |
SCON.0 | RI | 98H | 接收中断标志,字符数据发送完毕时硬件置位,由软件清零 |
表1-2串行端口工作模式
SM0 | SM1 | 模式 | 描述 | 波特率 |
---|---|---|---|---|
0 | 0 | 0 | 移位寄存器 | 固定 |
0 | 1 | 1 | 8位UART | 可变(由定时器T1控制) |
1 | 0 | 2 | 9位UART | 固定 |
1 | 1 | 3 | 9位UART | 可变 |
这里我用的是模式1实现串口通信。
keilC51 工程
- 这里,我以接收字符’A’,’B’控制发送字符,使用串口中断试下字符接收与发送。代码如下:
#include <reg51.h>
unsigned char receiveDate;
void UART_Init()
{
SCON = 0x50;
TMOD = 0x20;
PCON=PCON&0x7f;
TH1 = -3;
TL1 = -3;
TR1 = 1;
ES = 1; //串口中断允许位
}
void put1(char c)
{
SBUF = c;
while(!TI);
TI = 0;
}
void ISR_Init()
{
EA = 1;
}
void putall(char *s) //指针所指向的地址的值
{
while(*s)
{
put1(*s); //字符发送函数
s++; //地址指向下一个
}
}
void uart_0() interrupt 4
{
if(RI)
{
receiveDate = SBUF; //接收字符
RI = 0;
}
}
void main()
{
UART_Init(); //串口初始化
ISR_Init(); //总中断初始化
while(1)
{
if(receiveDate == 'A') //接收字符为'A',发送字符串“abcdef \n”
putall("abcdef \n");
else if(receiveDate == 'B')//接收字符为'B',发送字符串“psw\n”
putall("psw\n");
}
}
我们使用虚拟串口驱动,实现端口的映射,如图2-1所示,点击添加端口,实现COM3->COM4映射(图左侧已实现)
如图2-2,所示:在kileC51中右击Target-> Options for Target ‘Target 1’->Debug,将 Use Simulator,Limit Speed to Real-Time 选中(作用是选择Options for Target ‘Target 1’中Target里Xtal的晶振)。
图2-2如图2-3所示,点击 Start/Stop Debug Session,在keilC51左下角输入MODE COM3 9600,0,8,1 以及ASSIGN COM3
SOUT 指令,成功后虚拟串口驱动左侧COM3会出现[9600-N-8-1] 在串口助手这里选择COM4端口。这样就实现了串口软件虚拟仿真。