怎么更新网站备案资料,营销网页设计公司,wordpress 插件外链,烟台网站title优化在做两个串口相互通信的实验中#xff0c;当发送频率快一点时偶尔会遇到以下情景#xff0c;即一次send中把原数据拆成两份发送#xff0c;就会导致CRC校验错误。下图中6字节数据拆成42是把SetRThreshold()阈值设为2#xff0c;当设为1的情况下则会拆成51。 一开始以为是缓…在做两个串口相互通信的实验中当发送频率快一点时偶尔会遇到以下情景即一次send中把原数据拆成两份发送就会导致CRC校验错误。下图中6字节数据拆成42是把SetRThreshold()阈值设为2当设为1的情况下则会拆成51。 一开始以为是缓冲区溢出问题然而并不是。真正的原因出在MFC的COMM组件的OnComm响应函数上即一次发送的报文会被响应两次检测阈值时先会响应阈值后面的数据再次响应。 对于此问题有两种方法 第一种是在报文前后加上固定的包头包尾当数据断开时响应函数分别会收到一个带包头的和一个带包尾的数据将它们拼在一起即可。但这种方法的问题是有可能被截断的数据刚好也同时带有包头包尾因此还需要加一步CRC校验比较麻烦。 第二种方法比较简便思路是延迟接收即OnComm一旦响应后不急着接收数据而是过一段时间再接收则可以保证延迟接收的数据是完整的。 使用第二种方法需要使用MFC的定时器功能步骤如下。
设置定时器
/* comm控件的响应函数 */
void CMODBUS_CRCDlg::OnOnCommMscomm1()
{SetTimer(1,50,NULL); //表示1号定时器、计时50毫秒
}使用50ms是因为基本上能保证收到完整的串口数据且大于发送频率。
编写定时逻辑 对选择的类右键ClassWizard找到WM_TIMER并引入响应函数OnTimer。 在OnTimer里编写定时器停止的逻辑。
void CMODBUS_CRCDlg::OnTimer(UINT nIDEvent)
{switch (nIDEvent){case 1:receiveData();KillTimer(1);break;default:break;}CDialog::OnTimer(nIDEvent);
}nIDEvent表示定时器的id每当满50ms时一号定时器就会触发OnTimer事件设置KillTimer(1)即为触发一次否则将反复触发。 receiveData()为接收数据后所做的处理包括拆包、CRC校验、进行展示等环节。
补Qt遇到类似问题的解决方法