modbus是一項工業上經常用到的通訊協議,而freemodbus是一款開源的從機協議棧。關于它的移植網上已經有了很多的文章,但是大多都只是針對其中部分問題的表述。本文將會把自己在移植freemodbus過程中遇到的問題以及freemodbus的源碼分析盡量表述清楚。
(由于源碼分析部分在工作用的電腦上,這部分后續補上)
關于移植:
本次移植使用的片子是stm32f103的片子,編譯環境喂keil5.23
freemodbus源碼GitHub鏈接:
cwalter-at/freemodbus?github.com
首先移植需要有大致兩方面工作:1、相關硬件功能的編寫;2、freemodbus底層操作寄存器(線圈)的函數。
關于硬件功能主要包括usart的初始化,發送/接收狀態設置,串口中斷函數等;timer定時器的初始化,使能,失能以及定時器中斷等。其中需注意的是在串口中斷及定時器中斷中加入對應的處理函數,通知狀態機進行相應處理。
定時器方面基本沒有什么問題,確定還要使用的定時器以及編寫好對應的函數沒什么問題可以正常使用。但是在串口移植的時候需要注意,自己使用的串口發送中斷是txe還是tc。使用txe中斷需要預先發送一個字節觸發串口發送中斷,而是用tc中斷需要在中斷中添加延時否則會導致最后一個字節發送不出去的問題。關于這兩個問題的分析及解決方法:
txe中斷(本人測試過可以解決,八度大神還是屌啊):
FreeModbus在STM32上移植-OpenEdv-開源電子網?www.openedv.comtc中斷(該方法本人并沒有測試過是否可以解決問題):
STM32F407移植FreeModbus中遇到接收最后一個字節是0xff或0xfe的解決方法_劉恩明的博客-CSDN博客_485通信輸出0xff 0xfe?blog.csdn.net
硬件方面的問題大體如上
關于軟件部分:
1、狀態機在調用對應功能 的函數時,會在其中寄存器地址的處理后加入一句語句:usAddress++,不知道原作者加這一句是干嘛的。注釋掉即可,或者在底層的寄存器處理函數中加入一句對應的usAddress--;所謂負負得正嘛
2、在寄存器操作的部分中,有一個bug位于mbfuncholding.c文件eMBFuncReadHoldingRegister函數中文件第185行的位置,源代碼如下:
usRegCount = ( USHORT )( pucFrame[MB_PDU_FUNC_READ_REGCNT_OFF] << 8 ); usRegCount = ( USHORT )( pucFrame[MB_PDU_FUNC_READ_REGCNT_OFF + 1] );
應修正為:
usRegCount = ( USHORT )( pucFrame[MB_PDU_FUNC_READ_REGCNT_OFF] << 8 ); usRegCount |= ( USHORT )( pucFrame[MB_PDU_FUNC_READ_REGCNT_OFF + 1] );
3、關于需要實現的四個底層操作寄存器、線圈的函數需根據需求自行設計。后續在本人完成gd32f330的fremodbus移植后會貼出自己搞的移植后的freemodbus源碼。
附錄移植完畢的demo(基于GD32F330C8T6)
https://github.com/SlatedFish-QAQ/GD32_FreeModbus