"); //-->
需要做这么一个东西:三块单板通过Rs232,以38400的速度发送大量数据(帧的最后一个字节为0A)给STM32的USART2/3/4,STM32收到之后,以115200的速度通过USART1发送到上位机。同时,上位机以很低的频率发送单字节命令字到STM32,STM32需要将其转发到三块单板上。
看上去很简单的一个东西,于是在前两天熟悉了GPIO,NVIC,USART的基础上,就开工了。
一开始想得很简单,开辟Buffer[3][60],Buffer[0..2]分别为USART2/3/4的接收缓存区,定义FrameFlag[3],分别对应USART2/3/4的帧完成标志位,开辟TxBuffer[60],用作发送缓存区。
打开USART2/3/4的接收中断,不停的接收数据到对应的Buffer[x][BufCounter++]里面,一旦Buffer[x][BufCounter-1] == 0x0A则判断FrameFlag[x]为1。
而在主程序里面,则不停的检测三个标志位,只要为1,则清标志位,清计数器等,然后复制对应的Buffer里面得数据到TxBuffer里面,以查询的方式发送完TxBuffer,接着检测下个标志位。
基于这个思想,配置外设等,程序很快写完了,实测却发现有丢字节的现象,即有时候一帧不能够发完。
后来仔细考虑,发现程序有一个最大的Bug,发送一帧的数据是需要较长时间的,如果在检测到FrameFlag[0]为1,正在发送一帧数据的时候刚好出现FrameFlag[1]为1了,那么这个时候代码不能及时响应这一帧数据,该路上的数据便会出现问题。
改进方法如下:
1:采用乒乓操作
2:发送改为中断形式
2自不必说,下面详细说明一下1
开辟两个Buffer,分别为Buffer1[3][60],Buffer2[3][60],定义指针*Buffer[3]分别对应三个串口的接收缓冲区,定义指针*TxBuffer[3]及相应的指针p,q,用作发送数据队列。
具体实现的时候,一开始Buffer[x]等于Buffer1[x],在中断里面判断如果一帧接收完毕,则将Buffer[x]等于Buffer2[x]。实现接收缓存区的乒乓。
在主程序里面,当检测到FrameFlag[x]为1的时候,则将Buffer1[x]入*TxBuffer这个待发送数据队列,即TxBuffer[p] = Buffer1[x],p = p ==2 ? 0 : p++,最后如果检测到p != q,则发送TxBuffer[q]。
将代码按照上述思想修改之后,果然工作正常了。
搞这个代码花了整整两天,快20个小时。
代码在工作电脑上,表达能力着实有限,希望半年后再来看时,自己还能明白这个是什么意思,呵呵。
专栏文章内容及配图由作者撰写发布,仅供工程师学习之用,如有侵权或者其他违规问题,请联系本站处理。 联系我们
相关推荐
常用modemAT指令详解
Intersil Zilker Labs电源导航软件
第二十四届全国大学生机器人大赛 ROBOTAC在烟台芝罘落幕
二合一:OLED 屏幕还支持基于像素的声音
TDA1518Q功放电路
设计功率器件中的散热考虑
威胜控股集团成功于海外新兴市场夺得三项大型智能电表合约 总价值逾9.4亿港元
常用热电偶的补偿导线
Intersil ZL9101 数字电源模块 - 热设计
超星阅览器
全球晶圆厂扩张能否跟上美光 HBM 的激增?美国、日本和印度的最新时间表
常见EMC疑问及对策
据报道台积电有望从人形机器人中迎来十年繁荣,并由英伟达 Jetson 和特斯拉的芯片支持
程序的多任务和资源复用举例
英伟达 CEO 黄仁勋开始出售价值 9.25 亿美元的英伟达股票
TDA1516Q功放电路
TDA1519A功放电路
禾元电子推出三星2410开发板-------1500.00
新型单分子磁体技术或可解锁容量提升 100 倍的硬盘
ZL9101M数字电源模块简介
AI 颠覆者 DeepSeek 的下一代模型因 Nvidia GPU 对中国出口限制而延迟——AI GPU 短缺阻碍开发
有哪位能提供一下atmel代理商的联系方式么?
原创] 禾元电子ARM仿真器的优势——不买你会后悔的
据报道,瑞萨因 Wolfspeed 倒闭影响将 2030 年销售目标推迟 5 年,遭受 2500 亿日元损失
控制系统冗余的攻击网格电源可靠性问题
ZL9101M数字功率模块节省电路板空间、降低物料成本
有哪位能提供一下atmel代理商的联系方式么?
TDA1521功放电路
TDA1519功放电路
[原创] ARM仿真器全国最低价