OpenEdv-开源电子网

 找回密码
 立即注册
正点原子全套STM32/Linux/FPGA开发资料,上千讲STM32视频教程免费下载...
查看: 4714|回复: 6

关于USART通信的USART_REC_LEN

[复制链接]

13

主题

47

帖子

0

精华

初级会员

Rank: 2

积分
158
金钱
158
注册时间
2019-3-14
在线时间
25 小时
发表于 2019-4-8 19:45:27 | 显示全部楼层 |阅读模式
1金钱
在usart.h里定义了 USART_REC_LEN 为最大接收字节数,我想问一下比如这个值是 10 的话,那作为判断标志的 0x0D 和 0x0A ,即\r\n,是否包含在这10个字节数里?

我用标准例程里的代码进行了研究,比如 #define USART_REC_LEN  10 时,在XCOM中进行发送——

情况1:发送 12345678 时,接收窗口显示的是“12345678”,XCOM状态栏显示的 S为10

情况2:发送 123456789 时,接收窗口显示的是“123456789”,XCOM状态栏显示的 S为11;

情况3:发送 1234567890 时(即10个字节数),接收窗口却不显示内容,XCOM状态栏显示的 S为12。

如果 \r\n 包含在其中,那情况1就是正确的,情况3就是因为最后的 if语句 判断STA的值大于LEN-1了
如果 \r\n 不包含在其中,那情况3为什么发送10个数却不显示?

所以最尴尬的就是情况2了,该怎么解释?

最佳答案

正点原子逻辑分析仪DL16劲爆上市
回复

使用道具 举报

31

主题

2183

帖子

0

精华

资深版主

Rank: 8Rank: 8

积分
14424
金钱
14424
注册时间
2018-8-3
在线时间
1157 小时
发表于 2019-4-8 19:45:28 | 显示全部楼层
回复

使用道具 举报

13

主题

47

帖子

0

精华

初级会员

Rank: 2

积分
158
金钱
158
注册时间
2019-3-14
在线时间
25 小时
 楼主| 发表于 2019-4-8 19:47:57 | 显示全部楼层
void USART1_IRQHandler(void)                                     //USART1的中断响应函数
{
       
        u8 Rec;                                                          //接收数据临时变量
        if(USART_GetITStatus(USART1 , USART_IT_RXNE) != RESET)           //判断是否允许USART1接收中断,如果允许,则开始读取数据
        {
                Rec = USART_ReceiveData(USART1);                                 //将接收的数据先放入临时变量中

                if((USART_RX_STA&0x8000)==0)                                     //检查USART_RX_STA的[15]是否为1。数据没接收完,则
                {
                        if(USART_RX_STA&0x4000)                                          //检查USART_RX_STA的[14]是否为1。接收到0x0D,则
                        {
                                if(Rec!=0x0A)                                                    //判断下一个数据是不是0x0A。若不是,则
                                        USART_RX_STA=0;                                                  //接收错误,重新开始
                               
                                else                                                             //若是,则
                                        USART_RX_STA|=0x8000;                                            //将[15]置为1,标记完成
                        }
                       
                        else                                                             //还没收到0x0D
                        {       
                                if(Rec==0x0d)                                                    //判断下一个数据是不是0x0D。若是,则
                                        USART_RX_STA|=0x4000;                                            //将[14]置为1
                               
                                else                                                             //若不是,则
                                {
                                        USART_RX_BUF[USART_RX_STA&0X3FFF]=Rec;                           //将临时变量里存放的数据放入接收缓冲数组,
                                        USART_RX_STA++;                                                  //放入的位数由USART_RX_STA决定,之后自加1
                                       
                                        if(USART_RX_STA > (USART_REC_LEN-1))                             //如果因长时间没有收到0x0D,导致接收的数据个数大于最大接收个数
                                                USART_RX_STA=0;                                                  //则接收错误,重新开始
                                }                 
                        }
                }                    
        }
}
回复

使用道具 举报

13

主题

47

帖子

0

精华

初级会员

Rank: 2

积分
158
金钱
158
注册时间
2019-3-14
在线时间
25 小时
 楼主| 发表于 2019-4-8 19:48:40 | 显示全部楼层
例程里的代码如上,有没有朋友可以解释一下啊
回复

使用道具 举报

13

主题

47

帖子

0

精华

初级会员

Rank: 2

积分
158
金钱
158
注册时间
2019-3-14
在线时间
25 小时
 楼主| 发表于 2019-4-8 19:54:39 | 显示全部楼层
翼行园子 发表于 2019-4-8 19:53
0D0A  也要算进去的

所以我说的那个情况2,应该就是代码的某个if语句有缺陷,是吗
回复

使用道具 举报

13

主题

47

帖子

0

精华

初级会员

Rank: 2

积分
158
金钱
158
注册时间
2019-3-14
在线时间
25 小时
 楼主| 发表于 2019-4-8 19:56:06 | 显示全部楼层
翼行园子 发表于 2019-4-8 19:53
0D0A  也要算进去的

if(USART_RX_STA > (USART_REC_LEN-1))

是不是把这个改成>= 会比较好,我试试看
回复

使用道具 举报

0

主题

1

帖子

0

精华

新手入门

积分
9
金钱
9
注册时间
2019-9-4
在线时间
2 小时
发表于 2020-8-31 16:33:41 | 显示全部楼层
if(USART_RX_STA>(USART_REC_LEN-1))
把“-1”去掉,改为
if(USART_RX_STA>(USART_REC_LEN))

说明:USART_REC_LEN 表示可缓冲的数据个数,判断语句是判断是否超过设置的缓冲数据个数。所以没必要减1。
我猜可能是原子哥,当时有点累,疏忽了。


PS:您的情况三的结果,其过程有一个细节,就是在有 -1 的情况下,发送最后的0时 程序识别为错误。开始第二次接收,恰好第二次接收的是 0后面的转义字符 回车和换行。
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则



关闭

原子哥极力推荐上一条 /2 下一条

正点原子公众号

QQ|手机版|OpenEdv-开源电子网 ( 粤ICP备12000418号-1 )

GMT+8, 2025-6-12 18:05

Powered by OpenEdv-开源电子网

© 2001-2030 OpenEdv-开源电子网

快速回复 返回顶部 返回列表