STM32F103、FreeModbus从站设计(7)-如何让RTU的定时器正常工作起来

关键词:Modbus FreeModbus STM32F103C8T6 CubeMX 移植

1.基本原理
在CubeMX工程配置中,已经将定时器2(TIM2)的时钟周期(可以理解为心跳一下)设为50us,Counter Period(产生中断)暂时设为了35,也就是说50us×35=1750us产生一次中断,这个时间就是判断RTU中帧间隔的标准。但在Freemodbus协议栈(遵循Modbus国标)中,这个时间不是固定的,在波特率小于19200bps时,需要具体计算这个时间,当波特率大于或等于19200bps时,这个时间固定为1750us,如图1所示。因此,孔丙火(微信公众号:孔丙火)认为,把它设为固定值是不方便的,当波特率修改的时候,还要单独修改此参数,可以用一个变量来设置此参数,变量的值随波特率而改变,这也有利于后期通信参数修改的程序。

图1
2.代码修改
在mbrtu.c中,有一个eMBRTUInit()函数,在协议栈初始化的时候被调用,在图2中可以看出,t3.5的计算方法。计算完了以后,调用xMBPortTimersInit()这个函数,这个函数在porttimer.c中,如果参数是写死的,CubeMX本身已经生成了定时器的初始化函数,这个函数是不用写的,直接返回True就行了。孔丙火(微信公众号:孔丙火)这里需要根据这个计算结果修改通信参数,因此要用一下这个函数。

图2
在modbus_app.c中定义一个全局变量uint16_t usUsrTimeOutCount;//modbus定时器计数周期(50us的个数),在xMBPortTimersInit()中,将usTimerT35_50us的值赋给usUsrTimeOutCount,然后在函数MX_TIM2_Init()中用这个值对TIM2进行初始化。xMBPortTimersInit()的代码如图3所示。MX_TIM2_Init()修改后的代码如图4所示。孔丙火(微信公众号:孔丙火)提醒,这样修改之后,在main.c中MX_TIM2_Init()这个函数的调用必须在eMBInit( MB_RTU, ucUsrSlaveAddress, 1, ulUsrBaudRate, eUsrParity );之后。在main.c中的初始化阶段的调用关系如图5所示。

图3

图4

图5

文章在公众号(孔丙火)同步推出,欢迎查看更多系列文章。
单片机、ARM、现场总线、PLC、嵌入式软硬件的设计经验分享,秉承“点点滴滴皆智慧”的理念,以实际项目为单元阐述知识点,一起分享,共同交流。


©著作权归作者所有:来自51CTO博客作者haoren1101的原创作品,如需转载,请注明出处,否则将追究法律责任

更多相关文章

  1. 300行Go代码玩转RPC
  2. 如何写出让大厂面试官满意的字符串复制函数(my_strcpy)?
  3. 3-19(c++基础)
  4. 【C语言】猜数字游戏
  5. ASM磁盘组配置
  6. 硬盘提示函数不正确怎么找回
  7. OEL7.9+Oracle12c+asm安装文档
  8. error C2059: 语法错误:“类型”
  9. SparkStreaming源码阅读思路

随机推荐

  1. PHP中的替代语法
  2. 仅在LARAVEL或AJAX中提交表单时,无需用户
  3. JAVA/PHP/C#版RSA验签--转
  4. 十大最流行PHP框架排名
  5. 无法在phpmyadmin中打开一些表
  6. PHP联系表格给用户发送随机确认号码
  7. 谈谈php里的DAO Model AR
  8. PHP:如何通过sprintf()添加前导零/零填充浮
  9. 如果不使用OAuth - PHP库,如何使用OAuth和
  10. 提交动态复选框表单并成对获取值