串口通信及中断
异步通信:发送和接收数据的双方用各自的时钟控制数据的发送和接收,为降低数据传输的错误率要求双方时钟尽可能一致。异步通信以帧为单位传送数据,由于每帧数据都具有起始位和停止位所以两帧数据之间的间隔时间不影响数据传送和接收的准确率,但是每帧数据内的各个二进制位间是以固定时间间隔传输的,即每个二进制位都有固定的传输速率,这个速率即为比特率,当一个码元仅表示0和1两种状态时(通信中常用时间间隔相同状态来表示一个二进制数字,这样的信号称为码元,而波特率表示每秒钟传输了多少个码元),一个码元等于一个二进制比特位,此时波特率与比特率大小相同,若是发送和接收双方的波特率不同,则会导致数据出现偏差。
同步通信:发送方和接收方的时钟完全同步,此时传输的数据帧间不留间隙
全双工通信:收发双方设备能同时实现数据的发送和接收(同时双向传输)
半双工通信:收发双方可实现双向数据传输,但同一时间段内只能实现单向传输,即收发不能同时进行
单工通信:收发双发只能实现数据单向传输
全双工 半双工 单工
通信速率:通常以比特率来表示通信速率,当一个码元仅表示两种状态,例如0和1时,可用波特率来表示比特率,此时也可用波特率直接表示通信速率。
串口内部结构
串口相关寄存器的配置
SCNO(串口控制寄存器)
SM0和SM1用于选择串口的工作方式
SM2用于多机位通信,主要用于方式2和3,而最常用的是方式1,此处不做过多解释。
REN:允许串行接收位,当REN=1时,启动串行口接收数据,当REN=0时,拒绝串行口接收数据
TB8和RB8均用于方式2和方式3中
TI:发送中断标志位,在数据传输过程中,当串行发送停止位开始时,由内部硬件置TI=1,并向CPU发出中断请求,进入中断程序并在数据发送完成后,需将TI软件置0,来结束中断请求,以便发送下一个数据
RI:接收中断标志位,在数据接收过程中,串行接收停止位的中间时,由内部硬件置1,向CPU发送中断请求,进入中断程序后,需将RI用软件置0,结束中断请求,以便接收下一个数据
PCNO(电源控制寄存器,可位寻址)
SMOD:波特率倍增位,当SMOD=1时,波特率提高一倍
定时器1的配置(8位自动重装)
在选定波特率后,根据晶振频率和是否倍增波特率用相关计算器算出TH1和TL1的初值
例如:设置串口工作方式1,波特率位9600,波特率不倍增,使用中断的配置程序
#include <regx52.h>
void UART_Init() 9600bps@11.0592MHz
{
TMOD &= 0x0F; //高四位清零,低四位不变,其目的为在不改变定时器0的状态下配置定时器1
TMOD |= 0x20; //高四位置为0010,低四位不变,其目的为选择定时器1位工作方式2(8位自动重装计时器)
SCON = 0x50; //选择串口工作方式为10位异步收发器(8位数据),波特率可变
PCON &=0x7F; //波特率不倍速
TH1 = 0xFD;
TL1 = 0xFD;
ET1 = 0; //关闭定时器1的中断允许
EA = 1; //打开总中断
ES = 1; //打开串口中断允许
TR1 = 1; //打开计时器1;
}
//void UART() interrupt 4 //串口中断
//{
// unsigned char Byte;
// RI=0; //清除接收中断标志位
// Byte=SBUF; //接收SBUF中的数据
// //用接收到的数据执行相应操作
//}
Kabooooom: 成功了但是这是为啥啊?
Maple_nue: 牛比啊啊啊啊!你是我爹
jhy8421: 没有INIT指令吗?AT+INIT\r\n,我返回错误码E
[B a]: 还是上传不上去
m0_74386055: 神医啊