概要
学习51单片机中的串口中断
技术名词解释
- 串行通信:在不同的时间发送不同的高低电平,形成一串数字。一位一位传输。优点是节省串口资源,缺点发送时间长。
- 并行通信:一次传输多位。优点发送时间短,缺点占用串口资源。
- 异步通信:主机和从机不使用同一个时钟。每一帧可以在中间加一个校验位(比如记录该帧存放了几个1,当接收设备接收到该帧时,发现校验位有问题,可以退回重发)。形成帧的每个数字可以称为码元
- 同步通信:主机和从机使用同一个时钟。
- 单工通信: 只能单向传输数据。类似于上课铃声。
- 半双工通信:可以双向通信,但不可以同时通信。类似于对讲机。
- 全双工通信:可以双向同时通信。类似于手机电话。
- 常见的串行通信应用
配置寄存器
串行口结构
简单理解:A代表CPU,移位寄存器中存放接收到的数据,最高八位。这里给串口配置了特殊功能寄存器SBUF(数据缓冲),它也是一个八位的特殊功能计算器。当移位寄存器存了8位数据后,就由SBUF接收到该八位数据,CPU再从SBUF中读取。同理发送数据,由SBUF从CPU中读取发送。(防止数据丢失的一种方法。当SBUF读取到一个字节的数据后,把允许串口中断ES关掉,就接收不到数据,等将数据读走后,再打开串口中断,这样就保证数据不会丢失)
配置串行口寄存器
例如:SCON = 0x50;TCON = 0x80;配置方式1,波特率加倍
波特率计算方式
串行口通信初始化
基础练习
通过串口助手向单片机发送1,2,3,4字符,来实现不同灯光的亮灭
#include "reg52.h"
sbit led1 = P0^0;
sbit led2 = P0^1;
sbit led3 = P0^2;
sbit led4 = P0^3;
typedef unsigned int u16;
typedef unsigned char u8;
u8 receivedata;
u8 flag;
void Uart_init()
{
SCON = 0x50; //设置串口寄存器模式
TMOD = 0x20; //设置定时器工作模式为方式2 T1的TMOD = 0x20自动重装模式
PCON = 0x80; //设置波特率加倍
TH1 = 0xF3; //设置初值 根据波特率计算公式 (2^MODE/32)*晶振频率/[12*(256-TH1)] 需要赋初值
TL1 = 0xF3;
ES = 1; //打开串口中断
EA = 1; //打开总中断
TR1 = 1; //打开计数器
}
void main()
{
Uart_init();
led1 = 0;
led2 = 0;
led3 = 0;
led4 = 0;
while(1)
{
switch(receivedata)
{
case '1':led1 = ~led1;break;
case '2':led2 = ~led2;break;
case '3':led3 = ~led3;break;
case '4':led4 = ~led4;break;
default:break;
}
}
}
void Usart() interrupt 4
{
RI = 0; //接收到了数据,RI置1,要手动清零
receivedata = SBUF; //接收发送的数据
flag = receivedata; //将接受到的数据重新发送过去
SBUF = flag;
while(!TI); //等待数据发送完成
TI = 0;
}
注意事项
在串口中断发生时,如果接收到了数据,RI会被自动置1,这时候我们读取数据的同时要自己手动置0;同理在发送数据的时候,TI会被自动置1,我们发送数据的同时也要手动置0;