STC89C52_51单片机_串口配置_UART串口通信

2020-06-27来源: eefocus关键字:STC89C52  51单片机  串口配置  UART

寄存器配置

PCON电源管理寄存器

位序号 D7 D6 D5 D4 D3 D2 D1 D0

位符号 SM0 SM1 SM2 REN TB8 RB8 TI RI

– 模式 模式 模式1直接清零 使能串口接收 模式1接收停止位 发送标志位,软件清零 接受标志位,软件清0

//不能位寻址


SCON串口控制寄存器

位序号 D7 D6 D5 D4 D3 D2 D1 D0

位符号 SM0 SM1 SM2 REN TB8 RB8 TI RI

– 模式 模式 模式1直接清零 使能串口接收 模式1接收停止位 发送标志位,软件清零 接受标志位,软件清0

/*  SCON  */

sbit SM0   = SCON^7;

sbit SM1   = SCON^6;

sbit SM2   = SCON^5;

sbit REN   = SCON^4;

sbit TB8   = SCON^3;

sbit RB8   = SCON^2;

sbit TI    = SCON^1;

sbit RI    = SCON^0;


模式&波特率(宋雪松P183)

SCON主要用模式1,的波特率

对应的,要用定时器T1&T2的模式2


TH1 = TL1 = 256 - 晶振值/12/2/16/波特率

(256是TL1的溢出值,12指12个时钟周期,16是硬件因素)


SBUF

两个SBUF寄存器,分别负责接收和发送缓冲


流程

配置串口为模式1

配置定时器T1为模式2

根据波特率计算TH0&TL0的值

配置PCON&SCON寄存器

打开定时器


IO口模拟UART串口通信

UART串口传送数据示意图

在这里插入图片描述

挖坑:波特率&TH0是怎么算的?



#include


sbit PIN_RXD = P3^0;

sbit PIN_TXD = P3^1;


bit RxdOrTxd = 0;

bit RxdEnd = 0;

bit TxdEnd = 0;

unsigned char RxdBuf = 0;

unsigned char TxdBuf = 0;


void configUART(unsigned long baud);

void startRXD(void);

void startTXD(unsigned char dat);


void main(void)

{

EA = 1;

configUART(9600);


while(1)

{

while(PIN_RXD);

startRXD();

while(!RxdEnd);

startTXD(RxdBuf+1);

while(!TxdEnd);

}

}


void configUART(unsigned long baud)

{

TMOD &= ~(0xF<<0);

TMOD |= 0x1<<1;

TH0 = 256 - (11059200 / 12) / baud;

}


void startRXD(void)

{

TL0 = 256 - ((256 - TH0) >> 1);


ET0 = 1;

TR0 = 1;


RxdEnd = 0;

RxdOrTxd = 0;

}


void startTXD(unsigned char dat)

{

TxdBuf = dat;


TL0 = TH0;


ET0 = 1;

TR0 = 1;


PIN_TXD = 0;

RxdEnd = 0;

RxdOrTxd = 1;

}


void timer0(void) interrupt 1

{

static unsigned char cnt = 0;


if(RxdOrTxd)

{

cnt++;

if(cnt<=8)

{

PIN_TXD = TxdBuf & 0x01;

TxdBuf >>= 1;

}

else if(cnt==9)

{

PIN_TXD = 1;

}

else 

{

cnt = 0;

TR0 = 0;

TxdEnd = 1;

}

}


else

{

if(cnt==0)

{

if(!PIN_RXD)

{

RxdBuf = 0;

cnt++;

}

else

{

TR0 = 0;

}

}

else if(cnt<=8)

{

RxdBuf >>= 1;

if(PIN_RXD)

{

RxdBuf |= 0x80;

}

cnt++;

}

else

{

cnt = 0;

TR0 = 0;

if(PIN_RXD)

{

RxdEnd = 1;

}

}

}

}


UART串口通信

教学版


#include


void configUART(unsigned long baud);


void main(void)

{

configUART(9600);

while(!RI);

RI = 0;

SBUF = SBUF + 1;

while(!TI);

TI = 0;

}


void configUART(unsigned long baud)

{

SCON = 0x50;


TH1 = 256 - (11059200 / 12 / 2 / 16) / baud;

TL1 = TH1;

TMOD &= ~(0xF<<4);

TMOD |= 0x2<<4;

ET1 = 0;

TR1 = 1;

}


工业版


#include


void configUART(unsigned long baud);


void main(void)

{

EA = 1;

configUART(9600);

while(1);

}


void configUART(unsigned long baud)

{

SCON = 0x50;


TH1 = 256 - (11059200 / 12 / 2 / 16) / baud;

TL1 = TH0;

TMOD &= ~(0xF<<4);

TMOD |= 0x2<<4;

ET1 = 0;

ES = 1;

TR1 = 1;

}


void UART(void) interrupt 4

{

if(RI)

{

RI = 0;

SBUF = SBUF + 1;

}

if(TI)

{

TI = 0;

}

}


计算机发送数据,在数码管中显示


#include


sbit wei = P2^7;

sbit duan = P2^6;


unsigned char code weitable[6] = 

{

~0x20,~0x10,~0x08,~0x04,~0x02,~0x01

};


unsigned char code duantable[16] = 

{

0x3F,0x06,0x5B,0x4F,0x66,0x6D,0x7D,0x07,

0x7F,0x6F,0x77,0x7C,0x39,0x5E,0x79,0x71

};


unsigned char ledbuff[6] = 

{

0x00,0x00,0x00,0x00,0x00,0x00

};


unsigned char T0RH = 0,T0RL = 0;

unsigned char RxdByte = 0;


void configtimer0(unsigned char ms);

void configUART(unsigned long baud);


void main(void)

{

EA = 1;

configtimer0(1);

configUART(9600);

while(1)

{

ledbuff[0] = duantable[RxdByte & 0x0F];

ledbuff[1] = duantable[RxdByte >> 4];

}

}


void configtimer0(unsigned char ms)

{

unsigned long tmp;


tmp = 11059200 / 12;

tmp = (tmp * ms) / 1000;

tmp = 65536 - tmp;

tmp = tmp + 12;


T0RH = (unsigned char)(tmp>>8);

T0RL = (unsigned char)tmp;


TH0 = T0RH;

TL0 = T0RL;

TMOD &= ~(0xF<<0);

TMOD |= 0x1<<0;

ET0 = 1;

TR0 = 1;

}


void configUART(unsigned long baud)

{

TH1 = 256 - (11059200 / 12 / 2 / 16) / baud;

TL1 = TH0;

SCON = 0x50;

TMOD &= ~(0xF<<4);

TMOD |= 0x2<<4;

ET1 = 0;

ES = 1;

TR1 = 1;

}


void ledscan(void)

{

static unsigned char i = 0;


P0 = 0x00;

duan = 1;

duan = 0;


P0 = weitable[i];

wei = 1;

wei = 0;

P0 = ledbuff[i];   

duan = 1;

duan = 0;


if(i<5)

i++;

else

i = 0;

}


void timer0(void) interrupt 1

{

TH0 = T0RH;

TL0 = T0RL;


ledscan();

}


void UART(void) interrupt 4

{

if(RI)

{

RI = 0;

RxdByte = SBUF;

SBUF = RxdByte;

}

if(TI)

{

TI = 0;

}

}

关键字:STC89C52  51单片机  串口配置  UART 编辑:什么鱼 引用地址:http://news.eeworld.com.cn/mcu/ic501214.html

上一篇:51单片机简单的串口通讯-1
下一篇:51单片机 | 串口通信实验(模拟串口通信/多机通信实例)

关注eeworld公众号 快捷获取更多信息
关注eeworld公众号
快捷获取更多信息
关注eeworld服务号 享受更多官方福利
关注eeworld服务号
享受更多官方福利

推荐阅读

按键可调时电子钟程序
简介:单片机开源项目之按键可调时电子钟(矩阵按键+红外遥控按键进行调时)此程序是基于51hei单片机开发板上面写的,如需要移植到自己的电路上,修改相应的端口即可。/*************************************************************************** @file : main.c* @author : xr* @date : 2014年4月21日 22:23:12 - 2014年4月26日21:22:29* @version : V1.2.3* @brief : 按键可调时电子钟(矩阵按键+红外遥控按键进行调时) 单片机STC89C52RC MCU 晶振
发表于 2021-05-25
STC89C52RC单片机的NRF24L01无线通信程序,收发一体
本设计由两块STC89C52RC单片机组成,通过NRF24L01实现最廉价的无线通信。每块单片机都是集收发于一体,先初始化会在OLED上显示是否初始化成功,然后通过按键可选择收发模式,并在OLED屏幕上显示出来最后选择串口调试助手,打开串口给单片机发送信息,单片机接收到后再通过NRF24L01向另一块单片机发送接收成功后会将接收到的信息显示在OLED上。OLED显示屏较1602液晶显示屏清楚,可现实的内容丰富,可以建立自己的字库并且占用的引脚较少单片机源程序如下:#include "reg52.h"#include "oled.h"#include "bmp.h"
发表于 2020-11-09
STC89c52+DS1302时钟,数码管显示时间日期,可调节
最近在做数字电子时钟,也总结出来一些资料,在这分享给大家,DS1302时钟芯片。电脑仿真所需要的芯片有AT89C52,74HC138 排阻(因为C52单片机P0的IO口没有上拉电阻),74HC245 ,如果需要做实物,还得根据数码管的型号选择合适的电阻,DS1302芯片,按钮1,工作原理我们先了解我们所用的东西,STC89C52是8051单片机,这里就不多介绍了,然后就是DS1302时钟芯片,这个是DS1302时钟芯片这个是工作原理,我们经常用的DS1302与单片机的连接使用2.实验思路理解DS1302时钟芯片与单片机之间的数据传送,用的单总线的方式,所以会有时序图,还有读写图表三是地址,如果读取某个分钟或者小时,我们读数
发表于 2020-09-18
<font color='red'>STC89c52</font>+DS1302时钟,数码管显示时间日期,可调节
分享一个STC89C52的头文件
.--------------------------------------------------------------------------*/#ifndef __STC89C52_H__#define __STC89C52_H__typedef unsigned char u8;typedef unsigned int u16;/*  BYTE Registers  */sfr P0    = 0x80;sfr P1    = 0x90;sfr P2    = 0xA0;sfr P3    = 0xB0;sfr PSW   = 0xD0;sfr ACC
发表于 2020-09-09
单片机数码管时钟电路图
用STC89c52单片机,12M晶振。计时用T2定时器,16位自动重装模式  基本功能如下: 可以显示年份、月、日、时间,有闹钟功能,有倒计时功能。 上电默认显示时间,可通过按键切换显示年份、日期、闹钟、倒计时,显示一定时间后自动返回到时间显示。 在相应的显示状态下按设置键进行相应的设置。如在时间显示时按设置键可调整时间。其余类推倒计时最多可以倒数99小时59分59秒,设置完倒计时时间后进入倒数状态,闪烁显示倒数时间,中途可按键退出,倒数结束后铃响1分钟返回时间显示。 闹钟可选择开或关,闹铃响1分钟停止。电路原理图如下:制作出来的实物图如下:单片机源程序如下:#include <reg52.h>
发表于 2020-08-26
单片机数码管时钟电路图
电阻、电容和电感测试仪设计
实物图总电路图:电源模块:测量模块:显示模块:摘要近几年来,电子行业的发展速度相当快,电子行业的公司企业数目也不断增多。这个现象带来的直接结果是电子行业方面的人才需求不断增多。所以,现在大多数高校都开设与电子类相关的专业及课程,为社会培养大量的电子行业的人才。做过电路设计的工作人员或者学生大多数使用万用表来测量一些元件参数或者电路中的电压电流。然而万用表有一定的局限性,它只能测量有限种类的元器件的参数,对于电容和电感等一些电抗元件就无能为力了。所以制作一种简便的电容电感测量仪显得尤为重要,方便电路设计人员或者高校电子类专业的学生测量电路中需要用到的电容及电感的具体值。本次设计的思想是基于以上原因提出来的。该系统以STC89C52
发表于 2020-08-24
电阻、电容和电感测试仪设计
小广播
何立民专栏 单片机及嵌入式宝典

北京航空航天大学教授,20余年来致力于单片机与嵌入式系统推广工作。

换一换 更多 相关热搜器件
电子工程世界版权所有 京B2-20211791 京ICP备10001474号-1 电信业务审批[2006]字第258号函 京公网安备 11010802033920号 Copyright © 2005-2021 EEWORLD.com.cn, Inc. All rights reserved