因为想使两个51单片机通讯,又不能使用串口,因为STC89C52单片机只有一个串口,己被占用了,没有串口可以用。所以编写了这个程序。
使用仿真软件进行测试,工作正常。
在电路上实际测试,运行正常。
对控制线,进行短接干扰,测试,都按照预想的结果运行。
测试代码:
发送端不停的发送自定义数据帧,每发送一次,将第数据帧中的2个字节数加 1,再发送。
接收端使用LCD1602 将接收的据据帧中的第2个字节,显示出来。
对两根控制线进行断线,和对地短路干扰测试,也按照预想,干扰消除后,恢复正常工作。
下面是说明文档,附件源代码,和仿真电路图下载。
双单片机通信协议说明文档 一、通信协议的作用 功能:实现两片51单片机互相通信,4根线单向通信,8根线双向通信。 工作方式:使用普通IO口,不断轮询方式通讯。 (不使用单片机的中断,不使用串口) 适用场景:电路上两片51单片机,需要互相通讯。 传输速度:使用Porfessional和keil联调,在单片机的晶振频率为11.0592MHZ,单片机型号AT89C 51。两片单片机的时间全部用在轮询,测试约27MS接受完成16个字节数据。 (注:测试时发现的问题,Porfessional和keil联调,调试那个CPU就需要把正在调试的CPU改为U1,不然另一个CPU里面的代码没有运行,没有反应不能调试)。
定义数据帧的格式
传输1个字节的流程
分析运行时的步骤 协议在运行时,发送端控制C1,D1,D2三根线的电平状态,接收端控制C2一根线的电平状态。发送端不断在轮询C2的状态,接收端也同时在不断轮询C1的状态。这两根线我们把他称为控制线,也称为握手线。D1和D2我们把他称为数据线,两根线的电平可以表示4种状态,状态的表示如下:
为什么需要有(一个字节传输开始和一个字节传输结束)这两种状态,直接传送0和1不就可以了吗?我举一个例子:现在我们要把4个字节的数据发送给对方。如:01100110 01100110 01100110 01100110,按照正常的接收,接收端依次读取8个比特然后存入1字节,依次读完36比特存入4字节。但是通讯协议的设计应该要考虑到异常情况,如果由于某种原因受到干扰,这36比特中间少传或者多传了1比特。接收端接下来再以每8比特为1字节的取,接下来的数据就会全部错位。使用开始位和结束位来标识,就解决了这个问题。 发送和接收1比特数据的步骤如下: 初始状态:四根线的电平都为高电平1, 51单片机的IO口默认也是高电平。接收端在不断轮询C1的状态。 步骤一:发送端,发送1比特数据,在代码里,首先将D1和D2置为需要表达的电平,然后将C1置为底电平,等待接收端C2的底电平响应。(因为CPU执行指令是需要时间的,如果发送端先将C1置为底电平,然后再置D1和D2的电平,接收端恰好在C1刚为底电平时,检测到并且读取了D1和D2的状态。发送端还没来的及对D1和D2置需要的电平,这时就读到了错误的数据。虽然概率很小,但是这样可以避免。) 步骤二:接收端,检测到C1的状态是0时,表示发送端在发送1比特数据,接收端读取D1,D2的电平状态接收后,将C2置为底电平,表示己接收。然后等待接收端将C1恢复为高电平。 步骤三:发送端,检测到C2被置为底电平,表示接收端收到了数据,于是将C1恢复为高电平。等待C2恢复为高电平。 步骤四:接收端,检测到C1恢复为高电平,将C2恢复为高电平。 步骤五:发送端,检测到C2恢复为高电平,继续发送下一个比特。跳到步骤一(循环)。
分析协议在传输数据过程中受到干扰会发生的状态 在正常工作的情况下,数据会由发送端发送,接收端完成接收,一直运行。但是设计协议需要考虑到抗干扰性,受到干扰之后,协议能够恢复正常工作,继续传输数据,而不是停在某个状态。(例如:发送端在等待接收端响应,接收端同时也在等在发送端响应,一直停在这样的状态)。 现在我们来分类别分析发送端和接收端的等待情况,检查看能否发生同时等待的现象,造成死锁,数据传输停在这个状态。 发送端发生等待的2种情况: (1) 发送端C1置底电平,等待接收端C2底电平响应 (在第一步) (2) 发送端C1置高电平,等待接收端C2高电平响应 (在第五步) 接收端发生等待的2种情况: (1) 接收端C2是高电平,等待发送端C1的底电平 (在第一步) (2) 接收端C2置底电平,等待发送端C1高电平响应 (在第二步) 分析控制线的状态:如果有一个条件符合,其中的一端控制线的电平就会发生改变,不会发生死锁。如果没有条件符合,就会发生死锁。 分析1:发送端(1)和接收端(1)相结合,总有一个条件符合,不会发生死锁。 分析2:发送端(1)和接收端(2)相结合,总有一个条件符合,不会发生死锁。 分析3:发送端(2)和接收端(1)相结合,总有一个条件符合,不会发生死锁。 分析4:发送端(2)和接收端(2)相结合,总有一个条件符合,不会发生死锁。 结论:不会发生死锁 现在我们再来分类别分析发送端和接收端的异常情况,数据在传输时,会发生的情况。 1、接收端和发送端两片单片机不是同时启动分两种情况 (1)发送端先启动,接收端后启动,结果:接收端启动后开始检测C1的电平,接收比特数据,不影响。 (2)接收端先启动,发送端后启动,结果:发送端启动后,如果有数据,置C1为底电平,开始发送比特数据,不影响。 2、接收端在接收比特数据的时候死机重启分2种情况 (1)在步骤一,接收端死机重启后,接收端检测到C1为0,开始接收数据。如果不是开始位,丢弃接收到的比特,直到收到开始位。结果:会丢弃不完整数据,继续接收,恢复通讯。 (2)在步骤三,接收端死机重启后,接收端默认置C2为高电平,发送端检测到C2为高电平,认为接收端响应,继续发送下1比特数据。接收端开始接收比特数据。结果:会丢弃不完整数据,继续接收,恢复通讯。 (3)在步骤五,接收端死机重启后,结果和(步骤三)一样。 3、发送端在发送比特数据的时候死机重启分 3种情况 (1)在步骤二,发送端死机重启后,发送端恢复到初始状态,开始发送1比特,置C1为0。接收端在等待C1为1,等不到。但是接收端检测到C2被接收端己置为0,发送端认为接收端己收到数据,发送端响应,置C1 为1,接着正常执行后面的步骤。结果:发送端发送的这1比特丢失,会丢弃不完整的数据,继续接收,恢复通讯。 (2)在步骤二,发送端死机重启后,发送端恢复到初始状态,开始发送1比特,置C1为0的过程中。在发送端重启过程中,C1有一段时间为高电平,接收端正好收到,并响应。接收端进入步骤四。 (3)在步骤四,发送端死机重启后,发送端恢复到初始状态,开始发送1比特,置C1为0。接收端己完成1比特接收,没有等待,继续接收数据。结果:会丢弃不完整的数据,继续接收,恢复通讯。 4、在发送数据的1个初始状态和5个步骤过程中,控制线电平受到干扰分类别分析 (1)在初始状态,发送端没有数据需要发送:C1,C2全部为高电平,这时,接收端在等待C1的底电平到来然后接收比特数据。C1,C2受到干扰,由高电平变为底电平。 接收端的代码如果正好执行到检测C1位置,接收端响应,进入步骤二,等待C1恢得为高电平。干扰消除后,C1恢复为高电平,接收端进入步骤四完成1比特数据接收,继续接收下1比特数据。结果:接收1比特错误数据,续续接收,恢复通讯。 接收端的代码如果没有执行到检测C1位置,干扰消除。结果:无影响。 初始状态,发送端没有检测C2状态,受到干扰,无影响。 (2)在步骤1,发送端发送1比特数据,置C1为底电平,发送端等待C2的底电平来到来。C2受到干扰,由高电平变为底电平。 发送端的代码如果正好执行到检测C2位置,发送端认为接收端己接收到1比特数据并响应,发送端进入步骤三,置C1为高电平,等待C2恢复为高电平。干扰消除后,C2恢复为高电平。发送端进入到步骤五。结果:接收端少收到1比特数据,恢复通讯。 发送端的代码如果正好执行到检测C2位置,同时,接收端检测到C1为底电平,接收1比特数据并响应C2为底电平。结果:接收端正确收到1比特数据,无影响。 发送端的代码如果没有执行到检测到C2的位置,干扰消除。结果:无影响。 (3)在步骤2,接收端收到1比特数据,置C2为底电平,接收端等待C1的高电平到来。C1受到干扰,由底电平变为高电平。 接收端代码正好执行到检测C1位置,接收端认为发送端响应,接收端完成1比特数据接收,进入步骤四,恢复C2为高电平。干扰消除后,继续接收发送端的数据。结果:收到错误的1 比特数据,恢复通讯。 接收端代码没有执行到检测C1的位置,干扰消除。结果:无影响。 (4)在步骤3,发送端等待C2为高电平。受到干扰,C2变为高电平。 发送代码正好执行到检测C2位置,发送端认为接收端响应,跳到步骤五。如果此时接收端正好响应,则完成1比特数据发送。结果:无影响。 发送端等待C2为高电平。受到干扰,C2变为高电平。发送代码正好执行到检测C2位置,发送端认为接收端响应,跳到步骤五,然后又跳到步骤一,发送到下1比特数据。此时接收端在等待C1的高电平,然而C1是底电平,接收端继续等待。但是C2被接收端置为底电平,发送端认为接收端己接收1比特数据响应。进入步骤三,置C1为1,接收端响应,完成1比特数据接收。结果:接收端少收到1比特数据。 (5)在步骤4,接收端己完成接收,接收端在检测C1的底电平到来,接收数据。 C1受到干扰,由高电平变为底电平,然后干扰消除恢复为高电平。接收端会多收到1比特数据。当然这比特数据是错误的数据。结果:收到错误的1比特数据,恢复通讯。 C2受到干扰,由高电平变为底电平,干扰消除后恢复为高电平。因为发送端在这一步骤在等待接收端C2的高电平,然后发送数据,结果:干扰消除后发送端开始发送数据,无影响。 (6)在步骤5,实际就是初始状态。受到干扰发生的情况,也一样,就不再重复。
结论:受到干扰有三种结果:1,多收到1比特数据(数据是错误的)。2,少收到1比特数据。3,收到1比特错误数据。所以通信协议在受到干扰的情况下,不能保证数据的完整性,但是干扰消除,能够恢复通讯。这个通信方式,设计的时候,是尽可能的让数据传输,需要上层的通信协议来识别数据是否正确。
|