STC单片机虚拟串口发送程序(超简单)

合集下载

STC单片机虚拟串口发送程序(超简单)

STC单片机虚拟串口发送程序(超简单)

STC单片机虚拟串口发送程序(超简单)STC单片机(STC12C5A32S)虚拟串口发送程序//虚拟串口发送子函数void Uart(uint8 a){ACC=a; //TXD3是已经定义的任意的发送端口TR1=1;TXD3=0; //发送起始位while(TF1==0);TF1=0; //TF1必须清零,因为只有启用T1中断才会自动清零TXD3=ACC0; //发送8个位也可以用移位来发送,ACC0-ACC7也必须先定义while(TF1==0); //表示ACC的8个位,如果用移位发送,就不用这样定义。

TF1=0;TXD3=ACC1;while(TF1==0);TF1=0;TXD3=ACC2;while(TF1==0);TF1=0;TXD3=ACC3;while(TF1==0);TF1=0;TXD3=ACC4;while(TF1==0);TF1=0;TXD3=ACC5;while(TF1==0);TF1=0;TXD3=ACC6;while(TF1==0);TF1=0;TXD3=ACC7;while(TF1==0);TF1=0;TXD3=1; //发送停止位while(TF1==0);TF1=0;TR1=0;}该子函数使用T1定时器,T0也可以。

采用8位自动重装,重装值为A0Main(){TMOD = 0x21; //T0:模式1,16位定时器。

T1:模式2,8位定时器,自动重装AUXR &= 0x3f; //定时器0和定时器1与普通8051定时器一样(不同的单片机设置可能不同)TL1 = 0xa0; //虚拟串口波特率:9600TH1 = 0xa0;ET0 = 1;ET1 = 0; //T1中断一定不要使用,要不接收会错误TR0 = 1;TR1 = 0;Uart(0xaa); //0xaa是发送的数据,如果接收有误,在发送一个字节后可加点延时//延时While(1); //具体程序此处省略}注:因本人实验的硬件不需要模拟串口来接收数据,故没给出虚拟串口接收程序。

简单好用的stc12c5a串口2发送程序!

简单好用的stc12c5a串口2发送程序!

//功能:stc12c5a串口2发送程序,发送0--9,晶振频率11.0592MHz,串行口工作于方式1,波特率为9600#ifndef __STC12C5A60S2_H__#define __STC12C5A60S2_H__//--------------------------------------------------------------------------------//新一代 1T 8051系列单片机内核特殊功能寄存器 C51 Core SFRs// 7 6 5 4 3 21 0 Reset Valuesfr ACC = 0xE0; //Accumulator 0000,0000sfr B = 0xF0; //B Register 0000,0000sfr PSW = 0xD0; //Program Status Word CY AC F0 RS1 RS0 OVF1 P 0000,0000//-----------------------------------sbit CY = PSW^7;sbit AC = PSW^6;sbit F0 = PSW^5;sbit RS1 = PSW^4;sbit RS0 = PSW^3;sbit OV = PSW^2;sbit P = PSW^0;//-----------------------------------sfr SP = 0x81; //Stack Pointer 0000,0111sfr DPL = 0x82; //Data Pointer Low Byte 0000,0000sfr DPH = 0x83; //Data Pointer High Byte 0000,0000//--------------------------------------------------------------------------------//新一代 1T 8051系列单片机系统管理特殊功能寄存器// 7 6 5 4 3 21 0 Reset Valuesfr PCON = 0x87; //Power Control SMOD SMOD0 LVDF POF GF1 GF0 PDIDL 0001,0000// 7 6 5 4 3 21 0 Reset Valuesfr AUXR = 0x8E; //Auxiliary Register T0x12 T1x12 UART_M0x6 BRTR S2SMOD BRTx12 EXTRAM S1BRS 0000,0000//-----------------------------------sfr AUXR1 = 0xA2; //Auxiliary Register 1 - PCA_P4 SPI_P4 S2_P4 GF2 ADRJ -DPS 0000,0000/*PCA_P4:0, 缺省PCA 在P1 口1,PCA/PWM 从P1 口切换到P4 口: ECI 从P1.2 切换到P4.1 口,PCA0/PWM0 从P1.3 切换到P4.2 口PCA1/PWM1 从P1.4 切换到P4.3 口SPI_P4:0, 缺省SPI 在P1 口1,SPI 从P1 口切换到P4 口: SPICLK 从P1.7 切换到P4.3 口MISO 从P1.6 切换到P4.2 口MOSI 从P1.5 切换到P4.1 口SS 从P1.4 切换到P4.0 口S2_P4:0, 缺省UART2 在P1 口1,UART2 从P1 口切换到P4 口: TxD2 从P1.3 切换到P4.3 口RxD2 从P1.2 切换到P4.2 口GF2: 通用标志位ADRJ:0, 10 位A/D 转换结果的高8 位放在ADC_RES 寄存器, 低2 位放在ADC_RESL 寄存器1,10 位A/D 转换结果的最高2 位放在ADC_RES 寄存器的低2 位, 低8 位放在ADC_RESL 寄存器DPS: 0, 使用缺省数据指针DPTR01,使用另一个数据指针DPTR1*///-----------------------------------sfr WAKE_CLKO = 0x8F; //附加的 SFR WAK1_CLKO/*7 6 5 4 3 2 1 0 Reset ValuePCAWAKEUP RXD_PIN_IE T1_PIN_IE T0_PIN_IE LVD_WAKE _ T1CLKO T0CLKO 0000,0000Bb7 - PCAWAKEUP : PCA 中断可唤醒 powerdown。

stc单片机编程实例

stc单片机编程实例

stc单片机编程实例STC单片机编程是嵌入式系统开发中常用的一种技术手段,具有广泛的应用领域。

本文将通过几个实例介绍STC单片机编程的基本原理和实践操作,帮助读者更好地理解和掌握这一技术。

一、LED灯控制实例STC单片机通常具有多个IO口,可以通过控制这些IO口的电平来实现对外部设备的控制。

我们先来介绍一个简单的实例,通过STC 单片机控制LED灯的亮灭。

我们需要连接STC单片机的IO口和LED灯。

假设我们将LED灯连接到P1口,通过给P1口设置高电平或低电平来控制LED灯的亮灭。

接下来,我们需要编写程序来控制LED灯。

STC单片机的编程语言通常是汇编语言或C语言,这里我们以C语言为例。

首先,在程序中引入STC单片机的头文件,然后定义P1口为输出口。

```c#include <reg51.h> // 引入STC单片机头文件void main(){P1 = 0x00; // 将P1口初始值设为0,灯灭while (1){P1 = 0xff; // 将P1口设为全高电平,灯亮}}```编写好程序后,我们需要使用STC单片机的开发工具将程序烧录到单片机中。

烧录完成后,将单片机连接到电源,LED灯就会开始亮起。

通过这个实例,我们可以看到STC单片机编程的基本流程:连接硬件设备、编写程序、烧录程序、运行程序。

掌握了这些基本步骤,我们就可以实现更复杂的功能。

二、温度检测与显示实例除了控制外部设备,STC单片机还可以用来感知外部环境,并将感知到的信息进行处理和显示。

接下来,我们将介绍一个温度检测与显示的实例。

我们需要连接一个温度传感器到STC单片机的一个IO口。

温度传感器会将检测到的温度值转换为电压信号,并通过IO口输出。

接下来,我们需要编写程序来读取温度传感器的检测值,并将其显示在液晶屏上。

STC单片机通常需要通过一些额外的芯片来驱动液晶屏,这里我们假设我们已经连接好了液晶屏的驱动芯片。

```c#include <reg51.h> // 引入STC单片机头文件void delay(unsigned int t){while (t--);}void main(){unsigned int temp;while (1){temp = read_temperature(); // 读取温度传感器的检测值 display_temperature(temp); // 在液晶屏上显示温度值 delay(1000); // 延时1秒}}unsigned int read_temperature(){// 读取温度传感器的检测值的具体实现}void display_temperature(unsigned int temp){// 在液晶屏上显示温度值的具体实现}```在这个实例中,我们新增了两个函数:read_temperature()用于读取温度传感器的检测值,display_temperature()用于在液晶屏上显示温度值。

STC单片机模拟串口程序

STC单片机模拟串口程序

STC单片机模拟串口程序/*************stc12模拟串口程序*************//*功能:用单片机的任意I/O引脚模拟串口的TXB/RXB*//*适于STC1T系列单片机,波特率默认为9600晶振11.0592工作于1T模式,请根据实际需要直接使用或修改*//*未使用任何软件延时,仅占用了T0及其中断,和纯硬件串口效果完全相同,对其他程序执行无影响*//*示例功能为根据变量nSel的值选择1个字符串数组,并在条件满足时逐字节逐位由模拟串口引脚TXB发送,全部字符发完后置位TSEND 标志*//*发送同时以全双工方式接收数据,收到的字节按顺序循环存入Rbuf[16]中*//*以语音合成芯片SYN6658的命令格式为例,从3段合成文本中任选1段播放*//*数组选择变量nSel的值为1播放第1段,2播放第2段...,0不播放(nSel值的获取方法请根据具体需要添加相应程序段)*/ /*该程序已通过实际调试,误码率为0*//*该程序参考了STC单片机用户手册中的模拟串口程序*//***********作者:ltiaobao,2013.08***********/#include "reg51.h"#include/*define baudrate const*//*BAUD=65536-SYSclk/3/baudrate/M(1T:M=1,12T:M=12)*/ //#defineBAUDOxF400//******************(1T)#defineBAUD0xFE90//******************(1T)//#defineBAUDOxFF00//******************(12T)//#defineBAUDOxFFC0//******************(12T)//#defineBAUDOxFFE0//******************(12T)sfr AUXR=0x8E;sbit RXB=P3^0; //define UART TXD/RXD pinsbit TXB=P3^1;typedef bit BOOL;typedef unsigned char BYTE;typedef unsigned int WORD;BOOL TING,RING;BOOL TBEND,RBEND;BOOL TSEND;BYTE TDAT,RDAT;BYTE TCNT,RCNT; //baudrate counterBYTE nTBIT,nRBIT;BYTE nTbyte,nRbyte;BYTE nSel=1; //number to select string(0-don't send)BYTE Slength; //length of sending stringBYTE xdata *PTS; //pointer of string to sendBYTE xdata Rbuf[16];BYTE xdata headOfFrame[5]={0xFD,0x00,0x00,0x01,0x01};//command head of syn6658BYTE xdata string1[24]={"head,语音合成文本第一段"};BYTE xdata string2[24]={"head,语音合成文本第二段"};BYTE xdata stringn[26]={"head,选择溢出,请重新选择!"};void UART_INIT();void main(){BYTE i;TMOD=0x01; //set T0 to timer working at 16bit(mode1)AUXR=0x80; //T0x12=1,working at 1T modeTL0=BAUD;TH0=BAUD>>8;TR0=1;ET0=1;PT0=1;EA=1;UART_INIT();while(nSel){if(TSEND){if(Rbuf[(nRbyte-1)&0x0f]==0x4A||Rbuf[(nRbyte-1)&0x0f]==0x4F) //JUDGE SYN6658 READY OR NOT{Rbuf[(nRbyte-1)&0x0f]=0x55; //clear 0x4A 0r 0x4F inorder not to play many timesif(nSel==1){PTS=string1;Slength=strlen(string1+5)+5;}else if(nSel==2){PTS=string2;Slength=strlen(string2+5)+5;}else{PTS=stringn;Slength=strlen(stringn+5)+5;}headOfFrame[2]=Slength-3;for(i = 0; i<5; i++){PTS[i]=headOfFrame[i];}TING=1;TSEND=0;nTbyte=0;TCNT=0;nTBIT=0;}}}}/******Timer interrupt routline for UART******/ void tm0() interrupt 1 using 1{TL0=BAUD;TH0=BAUD>>8;if(RING){if(--RCNT==0){RCNT=3; //reset send baudrate counterif(--nRBIT==0) //received 9 bit{nRbyte &=0x0f;Rbuf[nRbyte++]=RDAT; //save the received byte to RBUF RING=0; //stop receiveRBEND=1; //set receive completed flag}else{RDAT>>=1; //receive 1 bitif(RXB) RDAT|=0x80;}}}else if(!RXB) //differentiate staring bit{RING=1;RCNT=4;nRBIT=9;}/*L_RBEND and L_TING*/if(--TCNT==0){TCNT=3; //reset send baudrate counterif(TING) //judge whether sending{if(nTBIT==0){TXB=0; //send start bitTDAT=PTS[nTbyte++]; //load data from string[] to TDAT nTBIT=9; //initial send bit number}else{TDAT>>=1; //shift data to CYif(--nTBIT==0){TXB=1;//TING=0; //stop sendTBEND=1; //set send completed flagif(nTbyte>=Slength){TING=0;TSEND=1;}}else{TXB=CY; //write CY to TXD pin}}}}}/******initial UART module variable******/void UART_INIT(){TING=0;RING=0; TSEND=1; RBEND=0; TCNT=0; RCNT=0; nTbyte=0; }。

STC单片机串口程序

STC单片机串口程序

//注意,如您使用的MCU没有那个功能,就不要操作相应的寄存器//注意,如您使用的MCU没有那那么大的扩展SRAM,就不要操作超过范围的SRAM#include<reg51.h>#include<intrins.h>sfr S2CON = 0x9A;//S2SM0,S2SM1,S2SM2,S2REN,S2TB8,SRB8,S2TI,S2RIsfr IE2 = 0xAF;//X,X,X,X,X,X,ESPI,ES2sfr S2BUF = 0x9B;sfr AUXR = 0x8e;sfr BRT = 0x9c;sfr IAP_CONTR = 0xC7;sfr CCON = 0xD8;sfr CMOD = 0xD9;sfr CL = 0xE9;sfr CH = 0xF9;sfr CCAP0L = 0xEA;sfr CCAP0H = 0xFA;sfr CCAPM0 = 0xDA;sfr CCAPM1 = 0xDB;sbit CR = 0xDE;sbit MCU_Start_Led = P1^7;sbit S2_Interrupt_Receive_Led = P1^4;//unsigned char self_command_array[4] = {0x22,0x33,0x44,0x55};#define Self_Define_ISP_Download_Command 0x22#define RELOAD_COUNT 0xfb //18.432MHz,12T,SMOD=0,9600bpsvoid serial_port_one_initial();void send_UART_one(unsigned char);void UART_one_Interrupt_Receive(void);void serial_port_two_initial();void send_UART_two(unsigned char);void UART_two_Interrupt_Receive(void);void soft_reset_to_ISP_Monitor(void);void delay(void);void display_MCU_Start_Led(void);void send_PWM(void);void main(void){unsigned int array_point = 0;unsigned char xdata Test_array_one[512] ={0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07,0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f,0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17,0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f,0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27,0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f,0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37,0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f,0x40, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47,0x48, 0x49, 0x4a, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f,0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57,0x58, 0x59, 0x5a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f,0x60, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67,0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f,0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77,0x78, 0x79, 0x7a, 0x7b, 0x7c, 0x7d, 0x7e, 0x7f,0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87,0x88, 0x89, 0x8a, 0x8b, 0x8c, 0x8d,0x8e, 0x8f,0x90, 0x91, 0x92, 0x93, 0x94, 0x95,0x96, 0x97,0x98, 0x99, 0x9a, 0x9b, 0x9c, 0x9d,0x9e, 0x9f,0xa0, 0xa1, 0xa2, 0xa3, 0xa4, 0xa5,0xa6, 0xa7,0xa8, 0xa9, 0xaa, 0xab, 0xac, 0xad,0xae, 0xaf,0xb0, 0xb1, 0xb2, 0xb3, 0xb4, 0xb5,0xb6, 0xb7,0xb8, 0xb9, 0xba, 0xbb, 0xbc, 0xbd,0xbe, 0xbf,0xc0, 0xc1, 0xc2, 0xc3, 0xc4, 0xc5,0xc6, 0xc7,0xc8, 0xc9, 0xca, 0xcb, 0xcc, 0xcd,0xce, 0xcf,0xd0, 0xd1, 0xd2, 0xd3, 0xd4, 0xd5,0xd6, 0xd7,0xd8, 0xd9, 0xda, 0xdb, 0xdc, 0xdd,0xde, 0xdf,0xe0, 0xe1, 0xe2, 0xe3, 0xe4, 0xe5,0xe6, 0xe7,0xe8, 0xe9, 0xea, 0xeb, 0xec, 0xed,0xee, 0xef,0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xf7,0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd, 0xfe, 0xff,0xff, 0xfe, 0xfd, 0xfc, 0xfb, 0xfa, 0xf9, 0xf8,0xf7, 0xf6, 0xf5, 0xf4, 0xf3, 0xf2, 0xf1, 0xf0,0xef, 0xee, 0xed, 0xec, 0xeb, 0xea,0xe9, 0xe8,0xe7, 0xe6, 0xe5, 0xe4, 0xe3, 0xe2,0xe1, 0xe0,0xdf, 0xde, 0xdd, 0xdc, 0xdb, 0xda,0xd9, 0xd8,0xd7, 0xd6, 0xd5, 0xd4, 0xd3, 0xd2,0xd1, 0xd0,0xc9, 0xc8,0xc7, 0xc6, 0xc5, 0xc4, 0xc3, 0xc2, 0xc1, 0xc0,0xbf, 0xbe, 0xbd, 0xbc, 0xbb, 0xba, 0xb9, 0xb8,0xb7, 0xb6, 0xb5, 0xb4, 0xb3, 0xb2, 0xb1, 0xb0,0xaf, 0xae, 0xad, 0xac, 0xab, 0xaa, 0xa9, 0xa8,0xa7, 0xa6, 0xa5, 0xa4, 0xa3, 0xa2, 0xa1, 0xa0,0x9f, 0x9e, 0x9d, 0x9c, 0x9b, 0x9a, 0x99, 0x98,0x97, 0x96, 0x95, 0x94, 0x93, 0x92, 0x91, 0x90,0x8f, 0x8e, 0x8d, 0x8c, 0x8b, 0x8a, 0x89, 0x88,0x87, 0x86, 0x85, 0x84, 0x83, 0x82, 0x81, 0x80,0x7f, 0x7e, 0x7d, 0x7c, 0x7b, 0x7a, 0x79, 0x78,0x77, 0x76, 0x75, 0x74, 0x73, 0x72, 0x71, 0x70,0x6f, 0x6e, 0x6d, 0x6c, 0x6b, 0x6a, 0x69, 0x68,0x67, 0x66, 0x65, 0x64, 0x63, 0x62, 0x61, 0x60,0x5f, 0x5e, 0x5d, 0x5c, 0x5b, 0x5a, 0x59, 0x58,0x57, 0x56, 0x55, 0x54, 0x53, 0x52, 0x51, 0x50,0x4f, 0x4e, 0x4d, 0x4c, 0x4b, 0x4a, 0x49, 0x48,0x47, 0x46, 0x45, 0x44, 0x43, 0x42, 0x41, 0x40,0x3f, 0x3e, 0x3d, 0x3c, 0x3b, 0x3a, 0x39, 0x38,0x37, 0x36, 0x35, 0x34, 0x33, 0x32, 0x31, 0x30,0x2f, 0x2e, 0x2d, 0x2c, 0x2b, 0x2a, 0x29, 0x28,0x21, 0x20,0x1f, 0x1e, 0x1d, 0x1c, 0x1b, 0x1a,0x19, 0x18,0x17, 0x16, 0x15, 0x14, 0x13, 0x12,0x11, 0x10,0x0f, 0x0e, 0x0d, 0x0c, 0x0b, 0x0a,0x09, 0x08,0x07, 0x06, 0x05, 0x04, 0x03, 0x02,0x01, 0x00};unsigned char i = 0;serial_port_one_initial(); //串口1初始化// serial_port_two_initial(); //串口2初始化display_MCU_Start_Led(); //点亮发光二极管表示单片机开始工作// send_UART_two(0x55); //串口2发送数据表示单片机串口正常工作// send_UART_two(0xaa); //串口2发送数据表示单片机串口正常工作/*for(array_point=0; array_point<512; array_point++){send_UART_two(Test_array_one[array_point]);}*/send_UART_one(0x34); //串口1发送数据表示单片机串口正常工作send_UART_one(0xa7); //串口1发送数据表示单片机串口正常工作for(array_point=0; array_point<512; array_point++){send_UART_one(Test_array_one[array_point]);}// send_PWM(); //6kHz PWM, 50% duty while(1);}void serial_port_one_initial(){SCON = 0x50; //0101,0000 8位可变波特率,无奇偶校验位// TMOD = 0x21; //0011,0001 设置顶时器1为8位自动重装计数器// TH1 = RELOAD_COUNT; //设置定时器1自动重装数// TL1 = RELOAD_COUNT;// TR1 = 1; //开定时器1BRT = RELOAD_COUNT;// BRTR = 1, S1BRS = 1, EXTRAM = 1 ENABLE EXTRAMAUXR = 0x11; //T0x12,T1x12,UART_M0x6,BRTR,S2SMOD,BRTx12,EXTRAM,S1BRS ES = 1; //允许串口中断EA = 1; //开总中断}void serial_port_two_initial(){//sfr SCON = 0x98;//SM0,SM1,SM2,REN,TB8,RB8,TI,RI//sfr S2CON = 0x9A;//S2SM0,S2SM1,S2SM2,S2REN,S2TB8,S2RB8,S2TI,S2RI//sfr S2BUF = 0x9B;//sfr IE2 = 0xAF;//X,X,X,X,X,X,ESPI,ES2S2CON = 0x50; //0101,0000 8位可变波特率,无奇偶校验位,允许接收BRT = RELOAD_COUNT;// BRTR = 1, S1BRS = 1, EXTRAM = 0 ENABLE EXTRAMAUXR = 0x11; //T0x12,T1x12,UART_M0x6,BRTR,S2SMOD,BRTx12,EXTRAM,S1BRS// ES = 1; //允许串口1中断// ES2 = 1IE2 = 0x01; //允许串口2中断,ES2=1EA = 1; //开总中断}void send_UART_one(unsigned char i){ES = 0; //关串口中断TI = 0; //清零串口发送完成中断请求标志SBUF = i;while(TI ==0); //等待发送完成TI = 0; //清零串口发送完成中断请求标志ES = 1; //允许串口中断}void send_UART_two(unsigned char i){//sfr SCON = 0x98;//SM0,SM1,SM2,REN,TB8,RB8,TI,RI//sfr S2CON = 0x9A;//S2SM0,S2SM1,S2SM2,S2REN,S2TB8,S2RB8,S2TI,S2RI//sfr S2BUF = 0x9B;//sfr IE2 = 0xAF;//X,X,X,X,X,X,ESPI,ES2unsigned char temp = 0;// ES = 0; //关串口1中断IE2 = 0x00; //关串口2中断,es2=0// TI = 0; //清零串口1发送完成中断请求标志S2CON = S2CON & 0xFD; //B'11111101,清零串口2发送完成中断请求标志// SBUF = i;S2BUF = i;// while(TI ==0); //等待发送完成do{temp = S2CON;temp = temp & 0x02;}while(temp==0);// TI = 0; //清零串口发送完成中断请求标志S2CON = S2CON & 0xFD; //B'11111101,清零串口2发送完成中断请求标志// ES = 1; //允许串口1中断// ES2 = 1IE2 = 0x01; //允许串口2中断,ES2=1}void UART_one_Interrupt_Receive(void) interrupt 4{unsigned char k = 0;if(RI==1){RI = 0;k = SBUF;if(k==Self_Define_ISP_Download_Command) //是自定义下载命令{delay(); //延时1秒就足够了delay(); //延时1秒就足够了soft_reset_to_ISP_Monitor(); //软复位到系统ISP监控区}send_UART_one(k+1);}else{TI = 0;}}void UART_two_Interrupt_Receive(void) interrupt 8{//sfr SCON = 0x98;//SM0,SM1,SM2,REN,TB8,RB8,TI,RI//sfr S2CON = 0x9A;//S2SM0,S2SM1,S2SM2,S2REN,S2TB8,S2RB8,S2TI,S2RI//sfr S2BUF = 0x9B;//sfr IE2 = 0xAF;//X,X,X,X,X,X,ESPI,ES2unsigned char k = 0;k = S2CON ;k = k & 0x01;//if(S2RI==1)if(k==1){//RI = 0;S2CON = S2CON & 0xFE; //1111,1110S2_Interrupt_Receive_Led = 0;k = S2BUF;if(k==Self_Define_ISP_Download_Command) //是自定义下载命令{delay(); //延时1秒就足够了delay(); //延时1秒就足够了soft_reset_to_ISP_Monitor(); //软复位到系统ISP监控区}send_UART_two(k+1);}else{//TI = 0;S2CON = S2CON & 0xFD; //1111,1101}}void soft_reset_to_ISP_Monitor(void){IAP_CONTR = 0x60; //0110,0000 软复位到系统ISP监控区}void delay(void){unsigned int j = 0;unsigned int g = 0;for(j=0;j<5;j++){for(g=0;g<60000;g++){_nop_();_nop_();_nop_();_nop_();_nop_();}}}void display_MCU_Start_Led(void){//sbit MCU_Start_Led = P1^7;unsigned char i = 0;for(i=0;i<1;i++){MCU_Start_Led = 0; //顶亮MCU开始工作指示灯delay();MCU_Start_Led = 1; //熄灭MCU开始工作指示灯delay();MCU_Start_Led = 0; //顶亮MCU开始工作指示灯}}void send_PWM(void){CMOD = 0x00; // CIDL - - - - CPS1 CPS0 ECF Setup PCA Timer// CPS1 CPS0 = 00, Fosc/12 is PCA/PWM clock// 18432000/12/256 = 6000CL = 0x00;CH = 0x00;CCAP0L = 0x80; //Set the initial value same as CCAP0HCCAP0H = 0x80; //50% Duty CycleCCAPM0 = 0x42; //0100,0010 Setup PCA module 0 in 8BIT PWM, P3.7CR = 1; //启动PCA/PWM 定时器}。

单片机IO口模拟串口程序(发送+接收)

单片机IO口模拟串口程序(发送+接收)

单片机IO口模拟串口程序(发送+接收)前一阵一直在做单片机的程序,由于串口不够,需要用IO口来模拟出一个串口。

经过若干曲折并参考了一些现有的资料,基本上完成了。

现在将完整的测试程序,以及其中一些需要总结的部分贴出来。

程序硬件平台:11.0592M晶振,STC单片机(兼容51)/************************************** ************************** 在单片机上模拟了一个串口,使用P2.1作为发送端* 把单片机中存放的数据通过P2.1作为串口TXD发送出去*************************************** ************************/#include <reg51.h>#include <stdio.h>#include <string.h>typedef unsigned char uchar;int i;uchar code info[] ={0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x5 5,0x55,0x55,0x55,0x55,0x55,0x55,0x55 };sbit newTXD = P2^1;//模拟串口的发送端设为P2.1void UartInit(){SCON = 0x50; // SCON: serail mode 1, 8-bit UARTTMOD |= 0x21; // T0工作在方式1,十六位定时PCON |= 0x80; // SMOD=1;TH0 = 0xFE; // 定时器0初始值,延时417us,目的是令模拟串口的波特率为2400bps fosc=11.0592MHzTL0 = 0x7F; // 定时器0初始值,延时417us,目的是令模拟串口的波特率为2400bps fosc=11.0592MHz// TH0 = 0xFD; // 定时器0初始值,延时417us,目的是令模拟串口的波特率为2400bps fosc=18.432MHz// TL0 = 0x7F; // 定时器0初始值,延时417us,目的是令模拟串口的波特率为2400bps fosc=18.432MHz}void WaitTF0(void){while(!TF0);TF0=0;TH0=0xFE; // 定时器重装初值fosc=11.0592MHzTL0=0x7F; // 定时器重装初值fosc=11.0592MHz// TH0 = 0xFD; // 定时器重装初值 fosc=18.432MHz// TL0 = 0x7F; // 定时器重装初值 fosc=18.432MHz}void WByte(uchar input){//发送启始位uchar j=8;TR0=1;newTXD=(bit)0;WaitTF0();//发送8位数据位while(j--){newTXD=(bit)(input&0x01); //先传低位WaitTF0();input=input>>1;}//发送校验位(无)//发送结束位newTXD=(bit)1;WaitTF0();TR0=0;}void Sendata(){for(i=0;i<sizeof(info);i++)//外层循环,遍历数组{WByte(info[i]);}}void main(){UartInit();while(1){Sendata();}}########################################## ####################################/************************************** ************************** 模拟接收程序,这个程序的作用从模拟串口接收数据,然后将这些数据发送到实际串口* 在单片机上模拟了一个串口,使用P3.2作为发送和接收端* 以P3.2模拟串口接收端,从模拟串口接收数据发至串口*************************************** ************************/#include<reg51.h>#include<stdio.h>#include<string.h>typedef unsigned char uchar ;//这里用来切换晶振频率,支持11.0592MHz 和18.432MHz//#define F18_432#define F11_0592uchar tmpbuf2[64]={0};//用来作为模拟串口接收数据的缓存struct{uchar recv :6 ;//tmpbuf2数组下标,用来将模拟串口接收到的数据存放到tmpbuf2中uchar send :6 ;//tmpbuf2数组下标,用来将tmpbuf2中的数据发送到串口}tmpbuf2_point={0,0};sbit newRXD=P3^2 ;//模拟串口的接收端设为P3.2void UartInit(){SCON=0x50 ;// SCON: serail mode 1, 8-bit UARTTMOD|=0x21 ;// TMOD: timer 1, mode 2, 8-bit reload,自动装载预置数(自动将TH1送到TL1);T0工作在方式1,十六位定时PCON|=0x80 ;// SMOD=1;#ifdef F11_0592TH1=0xE8 ;// Baud:2400 fosc=11.0592MHz 2400bps为从串口接收数据的速率TL1=0xE8 ;// 计数器初始值,fosc=11.0592MHz 因为TH1一直往TL1送,所以这个初值的意义不大TH0=0xFF ;// 定时器0初始值,延时208us,目的是令模拟串口的波特率为9600bps fosc=11.0592MHzTL0=0xA0 ;// 定时器0初始值,延时208us,目的是令模拟串口的波特率为9600bps fosc=11.0592MHz#endif#ifdef F18_432TH1=0xD8 ;// Baud:2400fosc=18.432MHz 2400bps为从串口接收数据的速率TL1=0xD8 ;// 计数器初始值,fosc=18.432MHz 因为TH1一直往TL1送,所以这个初值的意义不大TH0=0xFF ;// 定时器0初始值,延时104us,目的是令模拟串口的波特率为9600bps fosc=18.432MHzTL0=0x60 ;// 定时器0初始值,延时104us,目的是令模拟串口的波特率为9600bps fosc=18.432MHz#endifIE|=0x81 ;// 中断允许总控制位EA=1;使能外部中断0TF0=0 ;IT0=1 ;// 设置外部中断0为边沿触发方式TR1=1 ;// 启动TIMER1,用于产生波特率}void WaitTF0(void){while(!TF0);TF0=0 ;#ifdef F11_0592TH0=0xFF ;// 定时器重装初值模拟串口的波特率为9600bps fosc=11.0592MHz TL0=0xA0 ;// 定时器重装初值模拟串口的波特率为9600bps fosc=11.0592MHz #endif#ifdef F18_432TH0=0xFF ;// 定时器重装初值 fosc=18.432MHzTL0=0x60 ;// 定时器重装初值 fosc=18.432MHz#endif}//接收一个字符uchar RByte(){uchar Output=0 ;uchar i=8 ;TR0=1 ;//启动Timer0#ifdef F11_0592TH0=0xFF ;// 定时器重装初值模拟串口的波特率为9600bps fosc=11.0592MHz TL0=0xA0 ;// 定时器重装初值模拟串口的波特率为9600bps fosc=11.0592MHz #endif#ifdef F18_432TH0=0xFF ;// 定时器重装初值fosc=18.432MHzTL0=0x60 ;// 定时器重装初值fosc=18.432MHz#endifTF0=0 ;WaitTF0();//等过起始位//接收8位数据位while(i--){Output>>=1 ;if(newRXD)Output|=0x80 ;//先收低位WaitTF0();//位间延时}TR0=0 ;//停止Timer0return Output ;}//向COM1发送一个字符void SendChar(uchar byteToSend){SBUF=byteToSend ;while(!TI);TI=0 ;}void main(){UartInit();while(1){if(tmpbuf2_point.recv!=tmpbuf2_point.send)//差值表示模拟串口接收数据缓存中还有多少个字节的数据未被处理(发送至串口){SendChar(tmpbuf2[tmpbuf2_point.send++]);}}}//外部中断0,说明模拟串口的起始位到来了void Simulated_Serial_Start()interrupt 0{EX0=0 ;//屏蔽外部中断0tmpbuf2[tmpbuf2_point.recv++]=RByte(); //从模拟串口读取数据,存放到tmpbuf2数组中IE0=0 ;//防止外部中断响应2次,防止外部中断函数执行2次EX0=1 ;//打开外部中断0}~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~以上是两个独立的测试程序,分别是模拟串口发送的测试程序和接收的测试程序上面两个程序在编写过程中参考了这篇文章《51单片机模拟串口的三种方法》(在后文中简称《51》),但在它的基础上做了一些补充,下面是若干总结的内容:1、《51》在接收数据的程序中,采用的是循环等待的方法来检测起始位(见《51》的“附:51 IO 口模拟串口通讯C源程序(定时器计数法)”部分),这种方法在较大程序中,可能会错过起始位(比如起始位到来的时候程序正好在干别的,而没有处于判断起始位到来的状态),或者一直在检测起始位,而没有办法完成其他工作。

STC单片机程序下载、串口调试方法

STC单片机程序下载、串口调试方法

STC单片机程序下载、串口调试方法
一、STC单片机程序下载方法
STC单片机和A T89S系列单片机程序下载方式是不一样的,A T89S系列单片机采用USB_ISP下载线或是并口ISP下载线进行下载,STC单片机是采用串口ISP进行下载的.
STC单片机程序下载流程(以STC89C52RC为例):
1、在开发板断电的情况下将开发板用串口线和电脑连接起来,串口线的一端和开发板串口相接,另一
端和电脑的串口相接.
2、打开STC程序下载软件,界面如下:
3、选择单片机类型
4、打开要下载的程序文件
点“打开程序文件”,选择要下载的程序(.hex文件)5、下载设置,这项可以不管,使用默认的就可以.
6、点“”
点完后会出现如下界面:
7、给开发板供电,供完电后会出现如下界面
到此,整个程序就下载完成了!
注:STC单片机下载时,每次都要先点下载,再上电!
二、STC单片机串口调试方法
1、按上述上法把串口程序下载到单片机中(以串口接收和发送程序+数码管为例)
2、下载完程序后点串口助手进入到串口助手界面.
3、对串口助手进行设置.
5、点打开串口
打开后指示灯会变绿
6、在单字符发送区输入一个16进制数,如:55
7、点发送字符/数据
7、点完后在接收区会看到刚发的数据
以上是以串口接收和发送程序+数码管程序为例对串口调试进行了简单的介绍。

stc单片机串口使用

stc单片机串口使用

stc单片机串口使用串口一、中断图二、相关寄存器1、SCON 串行控制寄存器(可位寻址)0x98 B7 B6 B5 B4 B3 B2 B1 B0 SM0/FESM1 SM2 REN TB8 RB8 TI RISM0/FE :当PCON 寄存器中的SMOD0/PCON.6位为1时,该位用于帧错误检测。

当检测到一个无效停止位时,通过UART 接收器设置该位。

它必须由软件清零。

当PCON 寄存器中的SMOD0/PCON.6位为0时,该位和SM1一起指定串行通信的工作方式,如下表所示。

其中SM0、SM1按下列组合确定串行口1的工作方式:SM0 SM1 工作方式功能说明波特率0 0 方式0 同步移位串行方式:移位寄存器当UART_M0x6 = 0时,波特率是SYSclk/12, 当UART_M0x6 = 1时,波特率是SYSclk / 2 0 1 方式1 8位UART ,波特率可变( 2SMOD /32 )×(定时器1的溢出率或BRT 独立波特率发生器的溢出率)1 0 方式2 9位UART( 2SMOD / 64) x SYSclk 系统工作时钟频率 11方式39位UART ,波特率可变(2SMOD /32 )x(定时器1的溢出率或BRT 独立波特率发生器的溢出率)当T1x12 = 0时,定时器1的溢出率 = SYSclk/12/( 256 - T H1);当T1x12 = 1时,定时器1的溢出率 = SYSclk / ( 256 - T H1) 当BRTx12 = 0时,BRT 独立波特率发生器的溢出率= SYSclk/12/( 256 - BRT );当BRTx12 = 1时,BRT 独立波特率发生器的溢出率 = SYSclk / ( 256 - BRT )SM2:允许方式2或方式3多机通信控制位。

EX0EA PX001ET0PT001EX1PX101ET1PT101ES PS 01≥1RI TI SCON TCON IE0TF0IE1TF110101IT0IT1INT0INT1T0T1RX TXIE IP111111110硬件查询自然优先级自然优先级中断入口中断入口高级低级中断源中断源在方式2或方式3时,如果SM2位为1且REN位为1,则接收机处于地址帧筛选状态。

STC12C5A系列单片机串口编程

STC12C5A系列单片机串口编程

STC12C5A系列单片机串口编程串口头文件uart.h如下:=================================================================== /** File : uart.h* Description : This file is UART driver header of STC12C5A serial signal chip.* Author : Chao* Copyright : Chao** History* ----------------------* Rev : 0.0* Date : 20/08/2011** create.* ----------------------*/#ifndef UART_H_#define UART_H_//---------------Config-------------------------//#define UART1_EN //使能串口1#define UART1_RECEIVE_EN //允许串口1中断接收函数#define UART2_EN //使能串口2#define UART2_RECEIVE_EN //允许串口2中断接收函数//#define ECHO //使能回显//---------------Defines-------------------------//#define SystemFosc 22118400 //系统时钟:22.1184MHz#define UartBaud 9600 //串口波特率#define UART_BUFFER_SIZE 16 //串口数据缓冲区大小#define UartEndChar '>' //串口数据结束字符//---------------Type define-------------------------//typedef struct {unsigned int receive_flag; //数据接收标志unsigned char data_length; //数据缓冲区中有效数据个数unsigned char receive_buffer[UART_BUFFER_SIZE]; //数据接收缓冲区void (* init)(void); //串口初始化函数void (* send_byte)(unsigned char ddata); //发送单个字符void (* send_string)(unsigned char *ddata, unsigned char length); //发送字符串}UART_T;//---------------Extern-------------------------//#ifdef UART1_ENextern UART_T uart1;#endif#ifdef UART2_ENextern UART_T uart2;#endif#endif /*UART_H_*/======================================================================== 串口编程C程序文件uart.c如下:======================================================================== /** File : uart.c* Description : This file is UART driver of STC12C5A serial signal chip.* Author : Chao* Copyright : Chao** History* ----------------------* Rev : 0.0* Date : 20/08/2011** create.* ----------------------*///---------------Include files-------------------------//#include<stc12c5a.h>#include"uart.h"//---------------Function Prototype-------------------------//#ifdef UART1_ENstatic void uart1_init(void); //串口1初始化函数static void uart1_send_byte(unsigned char ddata); //串口1发送单个字符static void uart1_send_string(unsigned char *ddata, unsigned char length); //串口1发送字符串#endif#ifdef UART2_ENstatic void uart2_init(void); //串口2初始化函数static void uart2_send_byte(unsigned char ddata); //串口2发送单个字符static void uart2_send_string(unsigned char *ddata, unsigned char length); //串口2发送字符串#endif//---------------Variable-------------------------//unsigned long Fosc; //波特率设定时中间变量#ifdef UART1_ENUART_T uart1 = {0, // receive_flag0, // data_length"Hello\n", // receive_bufferuart1_init, // inituart1_send_byte, // send_byteuart1_send_string // send_string};unsigned char uart1_receive_temp;unsigned char *uart1_receive_point=uart1.receive_buffer;#endif#ifdef UART2_ENunsigned char uart1_receive_temp;UART_T uart2 = {0, // receive_flag0, // data_length"Hello\n", // receive_bufferuart2_init, // inituart2_send_byte, // send_byteuart2_send_string, // send_string};unsigned char uart2_receive_temp;unsigned char *uart2_receive_point=uart2.receive_buffer;#endif#ifdef UART1_EN/** ---- FUNCTION ----------------------------------------------------------------------- * Name : uart1_init* Description : 串口1初始化程序* -------------------------------------------------------------------------------------------- */static void uart1_init(void){unsigned long baud;//选择波特率产生方式:采用独立波特率发生器AUXR |= S1BRS;//设定波特率发生器重新计数初值Fosc = SystemFosc/32;baud = UartBaud;if(baud > 9600)AUXR |= BRTx12; //时钟频率不分频elseFosc /= 12;BRT = 256-Fosc/baud;//启动波特率发生器AUXR |= BRTR;SCON = 0x50; //设定串口1工作方式:方式1(8n1),允许接收ES = 1; //开串口1中断}/** === FUNCTION ---------------------------------------------------------------------* Name : uart1_send_byte* Description : 串口1发送单个字节数据* --------------------------------------------------------------------------------------------*/static void uart1_send_byte(unsigned char ddata){SBUF = ddata; //写入要发送的字符while(!TI); //等待发送完毕TI = 0; //清发送标志}/** === FUNCTION ---------------------------------------------------------------------* Name : uart1_send_string* Description : 串口1发送以'\0'结尾的字符串* --------------------------------------------------------------------------------------------*/static void uart1_send_string(unsigned char *ddata, unsigned char length){while(length--)uart1_send_byte(*ddata++);}#ifdef UART1_RECEIVE_EN/** === FUNCTION ---------------------------------------------------------------------* Name : ISR_uart1* Description : 串口1中断数据接收程序* --------------------------------------------------------------------------------------------*/void ISR_uart1(void) interrupt 4{if(RI) //确认接收到字符{uart1_receive_temp = SBUF;#ifdef ECHOuart1.send_byte(uart1_receive_temp);#endifif(uart1_receive_temp != UartEndChar) //如果没有接收到(假设接收缓冲区足够大){*uart1_receive_point++ = uart1_receive_temp;uart1.data_length++;}else{uart1_receive_point = uart1.receive_buffer; //重新将接收字符指针指向接收缓冲区头uart1.receive_flag = 1; //置位接收命令完成标志}RI = 0; //清接收标志}}#endif#endif#ifdef UART2_EN/** === FUNCTION ---------------------------------------------------------------------* Name : uart2_init* Description : 串口1初始化程序* --------------------------------------------------------------------------------------------*/static void uart2_init(void){#ifndef UART1_ENunsigned long baud;//选择波特率产生方式:采用独立波特率发生器AUXR |= S1BRS;//设定波特率发生器重新计数初值Fosc = SystemFosc/32;baud = UartBaud;if(baud > 9600)AUXR |= BRTx12; //时钟频率不分频elseFosc /= 12;BRT = 256-Fosc/UartBaud;//启动波特率发生器AUXR |= BRTR;#endifS2CON=0x50; //设定串口工作方式:方式1(8n1),允许接收IE2=0x01; //允许串口2中断}/** --- FUNCTION ---------------------------------------------------------------------* Name : uart2_send_byte* Description : 串口2发送单个字节数据* --------------------------------------------------------------------------------------------*/static void uart2_send_byte(unsigned char ddata){S2CON &= 0xFD; //清发送标志S2BUF = ddata; //发送数据while(!(S2CON&0x02)); //等待发送完成}/** === FUNCTION ---------------------------------------------------------------------* Name : uart2_send_string* Description : 串口2发送以'\0'结尾的字符串* --------------------------------------------------------------------------------------------*/static void uart2_send_string(unsigned char *ddata, unsigned char length){while(length--)uart2_send_byte(*ddata++);}#ifdef UART2_RECEIVE_EN/** ----- FUNCTION ---------------------------------------------------------------------* Name : ISR_uart2* Description : 串口2中断数据接收程序* --------------------------------------------------------------------------------------------*/void ISR_uart2(void) interrupt 8 //单片机接收从机发来的数据{if(S2CON&0x01) //如果接收到数据{uart2_receive_temp = S2BUF; //读取数据#ifdef ECHOuart2.send_byte(uart2_receive_temp);#endifif(uart2_receive_temp != UartEndChar) //如果没有接收到(假设接收缓冲区足够大){*uart2_receive_point++ = uart2_receive_temp;uart2.data_length++;}else{uart2_receive_point = uart2.receive_buffer; //重新将接收字符指针指向接收缓冲区头uart2.receive_flag = 1; //置位接收命令完成标志}S2CON &= 0xFE; //清接收标志}}#endif#endif======================================================================= 通过上面两个文件,就能很方便的实现STC12C5A系列单片机中串口操作,并且能够通过配置uart.h文件来实现串口1、串口2的条件编译,测试主函数main.c如下:======================================================================= #include<stc12c5a.h>#include"uart.h"void Sys_init(void); //系统初始化void main(){Sys_init();while(1){if(uart1.receive_flag){uart1.send_string(uart1.receive_buffer, uart1.data_length);uart1.receive_flag = 0;uart1.data_length = 0;}if(uart2.receive_flag){uart2.send_string(uart2.receive_buffer, uart2.data_length);uart2.receive_flag = 0;uart2.data_length = 0;}}}void Sys_init(void) //系统初始化{uart1.init();uart1.send_string("uart1\r\n",7);uart2.init();uart2.send_string("uart2\r\n",7);EA = 1;}该测试主函数实现的功能是:上电后,从串口1、串口2分别输出字符串"uart1\r\n"、“uart2\r\n”,然后两路串口分别等待接收数据,接收的字符串以字符“>”作为结束标志(可以在uart.h文件中进行修改),串口每接收完一个以“>”作为结尾的字符串,会通过相应串口将接收的字符串发送出去。

单片机虚拟串口的使用方法

单片机虚拟串口的使用方法

单片机虚拟串口的使用方法单片机的虚拟串口是一种非常常见的通信方式,它利用串口模拟的方式来进行数据的传输。

虚拟串口能够让单片机和计算机之间实现数据的传输和通讯,从而方便了开发者的开发工作,更好地实现了单片机与计算机的互联互通。

虚拟串口的使用方法如下:1. 确定虚拟串口的通信参数在使用虚拟串口前,首先要确认好虚拟串口的通信参数。

一般来说,包括波特率、数据位、停止位、奇偶校验等参数。

这些参数需要与单片机的串口通信参数相对应,否则通信将会失败。

2. 安装虚拟串口驱动程序在计算机上进行单片机项目的开发时,需要先安装对应的虚拟串口驱动程序。

常用的虚拟串口驱动程序有VirtualSerialDriver、FTDI等。

在安装驱动程序时,需要根据计算机的操作系统版本,选择对应的驱动程序版本。

3. 编写单片机程序在单片机中涉及到虚拟串口的程序中,需要先初始化串口通信参数,并打开串口,然后循环等待从串口接收到的数据。

在循环中,可以使用串口发送数据给计算机,或者从计算机接收数据。

4. 在计算机上打开虚拟串口设备在单片机程序中设置好虚拟串口的通信参数后,需要在计算机上打开虚拟串口设备。

在计算机的设备管理器中,能够看到已经成功安装的虚拟串口设备。

打开对应的串口,设置对应的通信参数即可。

5. 测试通信在单片机和计算机之间建立虚拟串口连接后,需要进行测试,确保串口通信正常。

可以先从单片机发送数据给计算机,观察是否能够在计算机上接收到数据;然后,可以在计算机上发送数据给单片机,观察单片机是否能够接收到数据。

如果测试结果正确,就可以通过这个虚拟串口通讯了。

总的来说,单片机虚拟串口的使用是比较简单的,只需设置好通信参数,安装对应的驱动程序,然后编写好单片机程序,最后进行测试即可。

虚拟串口通信的优点是方便快捷,能够更好地连接单片机与计算机,方便数据传输和控制。

因此,在实际应用中,虚拟串口通信被广泛应用于各种单片机项目开发中。

STC12单片机硬件SPI的nrf20l01从机发送程序

STC12单片机硬件SPI的nrf20l01从机发送程序

#include <reg52.h>#include <intrins.h>typedef unsigned char uchar;#define uint unsigned int//****************************************IO端口定义***************************************sfr SPCTL = 0xCE; //SPI Control Register SSIG SPEN DORD MSTR CPOL CPHA SPR1 SPR0 0000,0100sfr SPSTAT = 0xCD; //SPI Status Register SPIF WCOL - - - - - - 00xx,xxxxsfr SPDAT = 0xCF;sbit CE =P1^0;sbit CSN =P1^1;sbit IRQ =P1^2;sbit led=P1^3;//****************************************************************************************** uchar bdata sta; //状态标志sbit RX_DR =sta^6;sbit TX_DS =sta^5;sbit MAX_RT =sta^4;//*********************************************NRF24L01*************************************#define TX_ADR_WIDTH 5 // 5 uints TX address width#define RX_ADR_WIDTH 5 // 5 uints RX address width#define TX_PLOAD_WIDTH 32 // 32 uints TX payload#define RX_PLOAD_WIDTH 32 // 32 uints TX payloaduchar const TX_ADDRESS[TX_ADR_WIDTH]= {0x34,0x43,0x10,0x10,0x01}; //本地地址uchar const RX_ADDRESS[RX_ADR_WIDTH]= {0x34,0x43,0x10,0x10,0x01}; //接收地址uchar codeTx_Buf[TX_PLOAD_WIDTH]={0xff,0xee,0x11,0x22,0x33,0xaa,0xbb,0x11,0x22,0x33,0xaa,0xbb,0x11,0x22,0x33,0xaa,0xbb,0x11,0x22,0x33,0xaa,0xbb,0x11,0x22,0x33,0xaa,0xbb,0x11,0x22,0x33,0xee,0xff};//发送数据uchar Rx_Buf[RX_PLOAD_WIDTH];//接收数据//***************************************NRF24L01寄存器指令*******************************************************#define READ_REG 0x00 // 读寄存器指令#define WRITE_REG 0x20 // 写寄存器指令#define RD_RX_PLOAD 0x61 // 读取接收数据指令#define WR_TX_PLOAD 0xA0 // 写待发数据指令#define FLUSH_TX 0xE1 // 冲洗发送 FIFO指令#define FLUSH_RX 0xE2 // 冲洗接收 FIFO指令#define REUSE_TX_PL 0xE3 // 定义重复装载数据指令#define NOP 0xFF // 保留//*************************************SPI(nRF24L01)寄存器地址****************************************************#define CONFIG 0x00 // 配置收发状态,CRC校验模式以及收发状态响应方式#define EN_AA 0x01 // 自动应答功能设置#define EN_RXADDR 0x02 // 可用信道设置#define SETUP_AW 0x03 // 收发地址宽度设置#define SETUP_RETR 0x04 // 自动重发功能设置#define RF_CH 0x05 // 工作频率设置#define RF_SETUP 0x06 // 发射速率、功耗功能设置#define STATUS 0x07 // 状态寄存器#define OBSERVE_TX 0x08 // 发送监测功能#define CD 0x09 // 地址检测#define RX_ADDR_P0 0x0A // 频道0接收数据地址#define RX_ADDR_P1 0x0B // 频道1接收数据地址#define RX_ADDR_P2 0x0C // 频道2接收数据地址#define RX_ADDR_P3 0x0D // 频道3接收数据地址#define RX_ADDR_P4 0x0E // 频道4接收数据地址#define RX_ADDR_P5 0x0F // 频道5接收数据地址#define TX_ADDR 0x10 // 发送地址寄存器#define RX_PW_P0 0x11 // 接收频道0接收数据长度#define RX_PW_P1 0x12 // 接收频道1接收数据长度#define RX_PW_P2 0x13 // 接收频道2接收数据长度#define RX_PW_P3 0x14 // 接收频道3接收数据长度#define RX_PW_P4 0x15 // 接收频道4接收数据长度#define RX_PW_P5 0x16 // 接收频道5接收数据长度#define FIFO_STATUS 0x17 // FIFO栈入栈出状态寄存器设置/******************************************延时函数********************************************************///长延时void Delay(unsigned int s){unsigned int i,j;for(i=0;i<1000;i++)for(j=0;j<s;j++);}//短延时void delay_ms(unsigned int x){unsigned int i,j;i=0;for(i=0;i<x;i++){j=108;while(j--);}}/************初始化5A spi***************/void Init_SPI(){SPDAT=0; //初始化数据寄存器SPSTAT=0XC0; //清除状态寄存器SPCTL=0XD2;//设置为主机模式主频不能超过2M//忽略SS 使能spi MSB SCLK空闲为0 第一个时钟边沿开始采集 spi通信的频率为CUP_CLK/16 }//SPDAT 读写一个字节//TxData:要写入的字节//返回值:读取到的字节uchar SPI_ReadWriteByte(uchar TxData){SPDAT=TxData; //发送一个bytewhile((SPSTAT&0x80)==0);SPSTAT=0XC0; //清除状态寄存器return SPDAT; //返回收到的数据}//读取SPI寄存器值//reg:要读的寄存器uchar SPI_Read_Reg(uchar reg){uchar reg_val;CSN = 0; //使能SPI传输SPI_ReadWriteByte(reg); //发送寄存器号reg_val=SPI_ReadWriteByte(0xFF);//读取寄存器内容CSN = 1; //禁止SPI传输return(reg_val); //返回状态值}// 向寄存器REG写一个字节,同时返回状态字节 reg寄存器地址 value写入的数据uchar SPI_RW_Reg (uchar reg,uchar value){uchar status;CSN=0;status=SPI_ReadWriteByte(reg);//发送寄存器号SPI_ReadWriteByte(value); //写入寄存器的值CSN=1;return(status);}//写一个数据包uchar SPI_Write_Buf(uchar reg, uchar *pBuf, uchar bytes){uchar status,byte_ctr;CSN = 0;status=SPI_ReadWriteByte(reg);for(byte_ctr=0; byte_ctr<bytes; byte_ctr++)SPI_ReadWriteByte(*pBuf++);CSN = 1;return(status);}//读一个数据包uchar SPI_Read_Buf(uchar reg, uchar *pBuf, uchar uchars){uchar status,uchar_ctr;CSN = 0;status = SPI_ReadWriteByte(reg);for(uchar_ctr=0;uchar_ctr<uchars;uchar_ctr++)pBuf[uchar_ctr]=SPI_ReadWriteByte(0xFF);CSN = 1;return(status);}//*******************************发*****送*****模*****式*****代*****码*************************************/void TX_Mode(void){CE=0;SPI_RW_Reg(FLUSH_TX,0x00);SPI_Write_Buf(WRITE_REG + TX_ADDR, TX_ADDRESS, TX_ADR_WIDTH); // 写发送的地址 Writes TX_Address to nRF24L01SPI_Write_Buf(WRITE_REG + RX_ADDR_P0, TX_ADDRESS, TX_ADR_WIDTH); // 写接受的地址 RX_Addr0 same as TX_Adr for Auto.AckSPI_RW_Reg(WRITE_REG + EN_AA, 0x01); //**使能自动应答 Enable Auto.Ack:Pipe0SPI_RW_Reg(WRITE_REG + EN_RXADDR, 0x01); //使能通道0 Enable Pipe0SPI_RW_Reg(WRITE_REG + SETUP_RETR, 0x1a); // **自动重发功能设置 500us + 86us, 10 retrans...1a SPI_RW_Reg(WRITE_REG + RF_CH, 40); //收发频率SPI_RW_Reg(WRITE_REG + RF_SETUP, 0x07); // 发射速率、功耗功能设置TX_PWR:0dBm, Datarate:1Mbps, LNA:HCURRSPI_RW_Reg(WRITE_REG + RX_PW_P0, (unsigned char)RX_PLOAD_WIDTH); //设置接收数据长度,本次设置为2字节SPI_RW_Reg(WRITE_REG + CONFIG, 0x0e);CE=1;delay_ms(100);}void Transmit(unsigned char * tx_buf){CE=0; //StandBy I模式SPI_Write_Buf(WRITE_REG + RX_ADDR_P0, TX_ADDRESS, TX_ADR_WIDTH); //装载接收端地址SPI_RW_Reg(FLUSH_TX,0x00); //清除FIFOSPI_Write_Buf(WR_TX_PLOAD, tx_buf, TX_PLOAD_WIDTH); // 装载数据SPI_RW_Reg(WRITE_REG + CONFIG, 0x0e); // IRQ收发完成中断响应,16位CRC,主发送 CE=1; //置高CE,激发数据发送delay_ms(150);}/************************************主函数************************************************************/uchar NRF24L01_Check(void){uchar buf[5]={0XA5,0XA5,0XA5,0XA5,0XA5};uchar i;SPI_Write_Buf(WRITE_REG+TX_ADDR,buf,5);//写入5个字节的地址.SPI_Read_Buf(TX_ADDR,buf,5); //读出写入的地址for(i=0;i<5;i++) if(buf[i]!=0XA5) break;if(i!=5) return 1;//检测24L01错误return 0; //检测到24L01}void main(){uint i=0;CE=0;CSN=1;Init_SPI();while(NRF24L01_Check())//检测不到24L01{delay_ms(500);delay_ms(500);led=!led;}TX_Mode();while(1){Transmit(Tx_Buf); //清除FIFODelay(10);sta=SPI_Read_Reg(READ_REG + STATUS);if(TX_DS){led=0; //8位LED显示当前STATUS状态发送中断应使bit5 = 1 灯灭Delay(100);SPI_RW_Reg(WRITE_REG + STATUS,sta);}if(MAX_RT) //如果是发送超时{//发送超时时 8位LED灯 bit4 = 1 灯灭Delay(150);SPI_RW_Reg(WRITE_REG + STATUS,sta);}Delay(10);}}。

stc15串口范例程序

stc15串口范例程序

stc15串口范例程序STC15是一种常见的单片机型号,它具有丰富的外设和功能,其中包括串口通信功能。

下面是一个简单的STC15串口通信的范例程序,供你参考:c.#include <STC15F2K60S2.H>。

#define FOSC 11059200L.#define BAUD 9600。

void InitUART() {。

SCON = 0x50; // 8位数据,可变波特率。

TMOD = 0x20; // 设置定时器1为模式2。

TH1 = 256 FOSC/12/32/BAUD; // 波特率9600。

TL1 = TH1; // 初始化TL1。

TR1 = 1; // 启动定时器1。

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

EA = 1; // 打开总中断。

}。

void UARTInterrupt() interrupt 4 {。

if (RI) {。

P0 = SBUF; // 串口接收到的数据通过P0口输出。

RI = 0; // 清零接收中断标志位。

}。

if (TI) {。

TI = 0; // 清零发送中断标志位。

}。

}。

void main() {。

InitUART(); // 初始化串口。

while (1) {。

// 主循环。

}。

}。

以上是一个简单的STC15串口通信的范例程序。

在这个程序中,我们首先定义了晶振频率和波特率,然后编写了初始化串口的函数InitUART。

在主函数main中,我们调用InitUART进行串口的初始化,然后进入一个无限循环。

当有数据通过串口接收到时,会触发串口中断UARTInterrupt,并将接收到的数据通过P0口输出。

这个程序可以作为一个基础的串口通信范例,你可以根据自己的实际需求进行修改和扩展。

希望这个范例对你有所帮助。

单片机串口发送字符串程序

单片机串口发送字符串程序
4#include <stdio.h>
5
6/*******************************************************
7*宏定义数据类型
8******************************************R unsignedchar
63*函数定义
64*********************************************************/
65
66//初始化串口
67voidInitUART(UINT bits);
68
69//用串口发送一个字符串
70voidUartSend(UCHAR *Data,intLen);
函数功能:主函数
***************************************************/
void main(void)
{
unsigned int i;
TMOD=0x20; //TMOD=0010 0000B,定时器T1工作于方式2
SCON=0x40; //SCON=0100 0000B,串口工作方式1 1起始位8数据位1停止位
138OperateDistanceLed(ledPre);
139Bt_A_State=ENABLE;
140Bt_C_State=ENABLE;
141SpecialDelay(10000);
142Bt_A_State=DISABLE;
143Bt_C_State=DISABLE;
144if(Have_Agree){
38
39UINT Bt_R_State=ENABLE;
  1. 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
  2. 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
  3. 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。

STC单片机(STC12C5A32S)虚拟串口发送程序
//虚拟串口发送子函数
void Uart(uint8 a)
{
ACC=a; //TXD3是已经定义的任意的发送端口
TR1=1;
TXD3=0; //发送起始位
while(TF1==0);
TF1=0; //TF1必须清零,因为只有启用T1中断才会自动清零
TXD3=ACC0; //发送8个位也可以用移位来发送,ACC0-ACC7也必须先定义
while(TF1==0); //表示ACC的8个位,如果用移位发送,就不用这样定义。

TF1=0;
TXD3=ACC1;
while(TF1==0);
TF1=0;
TXD3=ACC2;
while(TF1==0);
TF1=0;
TXD3=ACC3;
while(TF1==0);
TF1=0;
TXD3=ACC4;
while(TF1==0);
TF1=0;
TXD3=ACC5;
while(TF1==0);
TF1=0;
TXD3=ACC6;
while(TF1==0);
TF1=0;
TXD3=ACC7;
while(TF1==0);
TF1=0;
TXD3=1; //发送停止位
while(TF1==0);
TF1=0;
TR1=0;
}
该子函数使用T1定时器,T0也可以。

采用8位自动重装,重装值为A0
Main()
{
TMOD = 0x21; //T0:模式1,16位定时器。

T1:模式2,8位定时器,自动重装AUXR &= 0x3f; //定时器0和定时器1与普通8051定时器一样(不同的单片机设置可能
不同)
TL1 = 0xa0; //虚拟串口波特率:9600
TH1 = 0xa0;
ET0 = 1;
ET1 = 0; //T1中断一定不要使用,要不接收会错误
TR0 = 1;
TR1 = 0;
Uart(0xaa); //0xaa是发送的数据,如果接收有误,在发送一个字节后可加点延时//延时
While(1); //具体程序此处省略
}
注:因本人实验的硬件不需要模拟串口来接收数据,故没给出虚拟串口接收程序。

以上程序已验证成功。

相关文档
最新文档