STC89C52RC拓展串口(串口不够)的解决方法

发布者:TranquilSoul最新更新时间:2019-12-20 来源: 51hei关键字:STC89C52RC  拓展串口  串口 手机看文章 扫描二维码
随时随地手机看文章

现在很多人拿51单片机起步,其中用的最多的当属STC89C52RC,但随着学习的深入,越来越感觉到这款单片机功能的落后,再加上现在物联网技术的发展,通信成了重要的一环,而许多模块比如蓝牙模块,串口屏,无线模块,GSM模块,串口语言模块等等都用串口通信,而这款单片机的串口就只有一个,远远不能满足功能复杂的大型应用,所以有些人就转向12,15,AVR,STM32等等,但这些单片机的学习资源远不如STC89C52RC,编程复杂了很多,但实际作品并不一定需要这么高级的单片机怎么办,本文将介绍几种常见的方法帮你扩展51单片机的串口:

1:先发一个常用的传统串口程序,里面包含了各种收发程序。

#include

#define MAIN_Fosc     11059200UL                        /*使用11.0592M晶体,UL相当于无符号整型,也就是unsigned int*/

//函数声明

void ConfigUART(unsigned int baud);

void SendByte(unsigned char d);

void SendString(unsigned char * pd);

//定义一个全局变量a存储接受到的数据

unsigned int a;

void main()

{

    EA = 1;   //使能总中断

    ConfigUART(9600);  //配置波特率为9600

        SendByte(0x03);

        SendString("ok");

    while(1);

}

//串口初始化程序

void ConfigUART(unsigned int baud)

{

    SCON  = 0x50;  //配置串口为模式1

    TMOD &= 0x0F;  //清零T1的控制位

    TMOD |= 0x20;  //配置T1为模式2

    TH1 = 256 - (MAIN_Fosc/12/32)/baud;  //计算T1重载值

    TL1 = TH1;     //初值等于重载值

    ET1 = 0;       //禁止T1中断

    ES  = 1;       //使能串口中断

    TR1 = 1;       //启动T1

}

//发送一个字节的数据,形参d即为待发送数据。

void SendByte(unsigned char d)                  

{

        SBUF=d; //将数据写入到串口缓冲

        while(!TI); //等待发送完毕

        TI=0;

}

//发送一个字符串

void SendString(unsigned char * pd)

{

        while((*pd)!='') //发送字符串,直到遇到0才结束

        {

                SendByte(*pd); //发送一个字符

                pd++;  //移动到下一个字符

        }

}

//串口中断函数

void InterruptUART() interrupt 4

{

        if(RI)

        {

                RI = 0;

                a= SBUF;

        }

}

2:其实不用单片机自带的串口,用定时器可以让任意两个IO口模拟串口

#include

sbit PIN_RXD = P3^0;

sbit PIN_TXD = P3^1;

bit RxdEnd = 0;

bit RxdOrTxd = 0;

bit TxdEnd = 0;

unsigned char RxdBuf = 0;

unsigned char TxdBuf = 0;

void ConfigUART(unsigned int baud);

void StartRXD();

void StartTXD(unsigned char dat);

void main()

{

        EA = 1;

        ConfigUART(9600);

       

        while(1)

        {

                while(PIN_RXD);

                StartRXD();

                while(!RxdEnd);

                StartTXD(RxdBuf);

                while(!TxdEnd);

        }

       

}

void ConfigUART(unsigned int baud)

{

        TMOD &= 0xF0;

        TMOD |= 0x02;

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

}

void StartRXD()

{

        TL0 = 256 - ((256 - TH0)>>1)+4;//之所以加4是因为实地测试发送数据还行,但接收数据误差率太大,估计是51速度太慢,中断中语句太多,当波特率低于9600时可不加4,波特率等于9600则加3以上

        ET0 = 1;

        TR0 = 1;

        RxdEnd = 0;

        RxdOrTxd = 0;

}

void  StartTXD(unsigned char dat)

{

        TxdBuf = dat;

        TL0 = TH0;

        ET0 = 1;

        TR0 = 1;

        PIN_TXD = 0;

        TxdEnd = 0;

        RxdOrTxd = 1;

}

void InterruptTimer0() 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;

                        }

                }

        }

}

3:有些模块只需要接收单片机发送的数据,那就只接单片机的Txd,同理有些模块只需要给单片机发送数据只接Rxd;

4:多用几块单片机,我们的原则是能用低级的单品机解决的绝不用高级单片机解决。单片机与单片机之间可以用IIC通信或者原始的检测IO口电平。

5:把所有需要用到串口通信的模块都接到单片机的串口上,然后用三极管控制什么时间段什么模块供电工作。

6:通过SPI串口拓展芯片,比如VK3224芯片,CH432T芯片,GM8142芯片,8251芯片等等。

关键字:STC89C52RC  拓展串口  串口 引用地址:STC89C52RC拓展串口(串口不够)的解决方法

上一篇:基于51单片机的停车场车位管理系统
下一篇:单片机DES加解密源程序,参数带入密钥就能加密解密了

推荐阅读最新更新时间:2024-11-16 20:01

MSP430学习总结——UART串口
一、MSP430串口 我用的这个单片机是MSP430F5529,这个单片机有两个串口,分别是USCI_A0和USCI_A1,以下是关于MSP430串口的配置以及接收函数和发送函数。 二、串口配置 说到串口,那肯定离不开起始位、数据位、校验位、停止位以及波特率。 先来说一下常用的寄存器。 串口控制寄存器0 这个寄存器可以设置数据位,停止位和校验位等 串口控制寄存器1 这里可以设置时钟源和中断使能等 波特率设置寄存器 波特率设置涉及到三个寄存器UCA0BR,UCA0BR1,UCA0MCTL 具体的设置方法在芯片手册上有写,也可以参考一下这位大佬的博客https://blog.csdn.net/weixin_27070451
[单片机]
MSP430学习总结——UART<font color='red'>串口</font>
STM32串口收发数据为什么要使用DMA?有哪些常见问题?
直接存储器访问(Direct Memory Access),简称DMA。DMA是CPU一个用于数据从一个地址空间到另一地址空间“搬运”(拷贝)的组件,数据拷贝过程不需CPU干预,数据拷贝结束则通知CPU处理。因此,大量数据拷贝时,使用DMA可以释放CPU资源。 在STM32控制器中,芯片采用Cortex-M3架构,总线结构有了很大的优化,DMA占用另外的总线,并不会与CPU的系统总线发生冲突。也就是说,DMA的使用不会影响CPU的运行速度。 DMA数据拷贝过程,典型的有:(1)内存— 内存,内存间拷贝;(2)外设— 内存,如uart、spi、i2c等总线接收数据过程;(3)内存— 外设,如uart、spi、i2c等总线发送
[单片机]
STM32<font color='red'>串口</font>收发数据为什么要使用DMA?有哪些常见问题?
s3c2440串口详解
一、UART原理说明 通用异步收发器简称UART(Universal Asynchronous Receiver/Transmitter),它用来传输串行数据:发送数据时,CPU将并行数据写入UART,UART按照一定的格式在一根电线上串行发出;接收数据时,UART检测另一根电线上的信号,将串行数据收集放在缓冲区中,CPU就可以读取UART获得这些数据。串口之间以全双工方式传输数据,最精简的连线只有三根线:TxD用于发送数据,RxD用于接收数据,Gnd用于给双方提供参考电平,连线如下图: UART使用标准的TTL/CMOS逻辑电平(0-5V、0-3.3V、0-2.5V、0-1.8V)来表示数据,高电平表示1,低电平表示0。为了
[单片机]
s3c2440<font color='red'>串口</font>详解
ARM 开发板嵌入式linux系统与主机PC通过串口传输文件
嵌入式linux系统与主机通过串口传输文件 我想如果要从PC机下载东西到开发板的嵌入式linux系统里面,很多人首先会想到用tftp sftp等网络工具从网口下载。但如果网络用不了,只能通过串口下载怎么办呢?这个时候有两个工具能帮到你:一个是zmrx、zmtx,另外一个是lsz、lrz。个人觉得zmrx/zmtx没有lsz/lrz稳定,建议还是用后者。下面介绍一下lsz/lrz的使用方法。 一、编译lrzsz并下载到开发板上 从http://download.chinaunix.net/download/0007000/6293.shtml下一个lrzsz的tar包,解压缩后输入./configure,然后进入了sr
[单片机]
关于STM32F107VCT6串口DMA接收数字控制LED亮灭的功能实现
主函数中代码如下: #include stm32f10x.h void GPIO_Config(void); void USART_Config(void); void DMA_Config(void); void NVIC_Config(void); void LED1_ON(void); void LED2_ON(void); void LED3_ON(void); void LED4_ON(void); void LED_ALL_OFF(void); void delay(void); uint8_t DMA_BUFFER ; int main() { GPIO_Config(); USART_Co
[单片机]
关于STM32F107VCT6<font color='red'>串口</font>DMA接收数字控制LED亮灭的功能实现
stm32f103 串口通讯
串口通讯(SerialCommunication)是一种设备间非常常用的串行通讯方式,因为它简单 便捷,因此大部分电子设备都支持该通讯方式,电子工程师在调试设备时也经常使用该通讯方式输出调试信息。 stm32f103 串口通讯大致可以分为这五步 1.初始化gpio口,使能RX和TX引脚GPIO时钟 2.初始化USART,和USART时钟; 3.初始化nvic 总中断 4.编写字符串发送函数 5.编写USART 中断服务函数 1.初始化gpio口,使能RX和TX引脚GPIO时钟 void init_uart_gpio(void) { GPIO_InitTypeDef tx; GPIO_InitTypeDef
[单片机]
ARM9的系统时钟和串口(非流控 + 非FIFO + 查询方式)
实验的目的: 设置系统时钟,并在串口上输入一个字符,单板接收后将它的ASCII值加1后,从串口输出。 实验的源程序: /************************************************************************* s3c24xx.h *************************************************************************/ /* WOTCH DOG register */ #define WTCON (*(volatile unsigned long *)0x53000000) /* SDRAM regi
[单片机]
11.串口基本知识
大纲: 串口角色:1.数据传输。2.充当控制台。 数据传输:两个嵌入式设备,除了使用usb和网络来实现数据的传输外,就是可以使用串口来实现数据传输。 控制台:在pc机里,我们使用键盘来输入命令和信息等,通过显示器来显示查询的结果或者信息等。在嵌入式里,是通过终端控制台来输入命令来控制开发板和显示返回结果的。前面烧写的uboot和kernel等就是实例。 串口通讯参数: 首先了解一下波特率: 在这里我们使用115200. 各个位段的含义: 上面这些位参数的设置,对应发送方和接受方的参数必须一致,例如前面uboot的知识里,我们需要通过终端来操作开发板里的uboot。我们在终端软件里设置的波特率是1
[单片机]
11.<font color='red'>串口</font>基本知识
小广播
设计资源 培训 开发板 精华推荐

最新单片机文章
何立民专栏 单片机及嵌入式宝典

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

换一换 更多 相关热搜器件

 
EEWorld订阅号

 
EEWorld服务号

 
汽车开发圈

电子工程世界版权所有 京B2-20211791 京ICP备10001474号-1 电信业务审批[2006]字第258号函 京公网安备 11010802033920号 Copyright © 2005-2024 EEWORLD.com.cn, Inc. All rights reserved