教程簡介 MODBUS是一種基于主從結(jié)構(gòu)的控制協(xié)議,由一個(gè)主機(jī)和多個(gè)從機(jī)組成。 MODBUS是施耐德電氣于1979年為可編程邏輯控制器(PLC)通信所開發(fā)并發(fā)布的協(xié)議,至今已有相當(dāng)長的歷史。 以前它主要基于串口,但由于物聯(lián)網(wǎng)的發(fā)展,基于TCP的MODBUS現(xiàn)在被越來越廣泛地使用。恩智浦的i.MX RT 系列控制器的SDK中沒有相關(guān)的demo,本文的目標(biāo)是向大家介紹如何在SDK中的lwip_ping_freertos例程基礎(chǔ)上添加MODBUS TCP。
MODBUS 協(xié)議棧的下載地址:
https://www.embedded-experts.at/en/freemodbus/
測試軟件QModMaster 的下載地址:
https://sourceforge.net/projects/qmodmaster/
我在本次教程使用了MIMXRT1024-EVK 作為硬件平臺,MIMXRT1024-EVK 和電腦都連接到一臺路由器組成一個(gè)測試網(wǎng)絡(luò)。使用 MCUXpresso IDE 作為開發(fā)環(huán)境,MIMXRT1024-EVK SDK 版本是 2.12.1。 一、文件復(fù)制
下載完協(xié)議棧后,先解壓,隨后將其中的 modbus 目錄完整復(fù)制到 lwip_ping_freertos 工程目錄下,添加 modbus 及其所有子文件夾到工程的 include paths 中。
在協(xié)議棧里有一個(gè)demo 目錄,里面是modbus 被移植到各個(gè)廠商的處理器上的demo, 可惜沒有i.MX RT。仔細(xì)對比各個(gè) demo 就可以發(fā)現(xiàn),原來這些 demo 有很多就是基于freertos 和 lwip 的。我們就從 MCF5235 TCP 下手,它既有freertos 又有l(wèi)wip,完美符合我們的項(xiàng)目??梢园阉?port 目錄復(fù)制到我們項(xiàng)目的modbus 目錄下。把其中的文件全部涵蓋進(jìn)來。
二、修改程序
接下來首先是在 lwip_ping_freertos.c 中include “mb.h”。這個(gè)文件包含了 freemodbus 協(xié)議棧提供的所有接口函數(shù)。
1.程序結(jié)構(gòu)
Lwip 協(xié)議棧為用戶應(yīng)用程序的編寫提供 3 種編程接口:
第一種是Raw Callback API,這種方式下協(xié)議棧與用戶程序間通過回調(diào)函數(shù)實(shí)現(xiàn)通信。而且協(xié)議棧同應(yīng)用程序處在同一個(gè)進(jìn)程中,彼此間的執(zhí)行都會互相制約。
第二種是 Sequential API 方式,用戶向內(nèi)核注冊回調(diào)函數(shù),并通過直接調(diào)用內(nèi)核 UDP 或TCP 相關(guān)操作函數(shù)來完成應(yīng)用程序的編寫。在這種方式下,協(xié)議棧內(nèi)核運(yùn)行于進(jìn)程 tcpip_thread, 而應(yīng)用程序進(jìn)程也是一個(gè)單獨(dú)的進(jìn)程。獨(dú)立的進(jìn)程結(jié)構(gòu)可以使協(xié)議棧和應(yīng)用程序的執(zhí)行互不影響。通過使用郵箱和信號量等機(jī)制,內(nèi)核進(jìn)程可以直接將數(shù)據(jù)遞交給應(yīng)用程序郵箱中然后繼續(xù)執(zhí)行,不必阻塞等待。
第三種是使用 BSD socket 函數(shù)進(jìn)行應(yīng)用程序開發(fā)。本來這是最簡單的方式,但是由于BSD socket 函數(shù)在實(shí)現(xiàn)上高度抽象,不適合小型嵌入式TCP/IP 應(yīng)用,所以 lwip 里的socket 函數(shù)并不是非常完整。
為實(shí)現(xiàn)與 lwip 協(xié)議棧之間的相互調(diào)用,freemodbus 協(xié)議棧采用的是sequential API 方式。具體的調(diào)用順序如下:在 mb.c 中提供了 eMBTCPInit() 函數(shù), 這個(gè)函數(shù)調(diào)用eMBTCPDoInit()函數(shù), 隨后層層調(diào)用下去,最后在 xMBTCPPortInit()函數(shù)中調(diào)用 tcp_bind()。這個(gè)函數(shù)是 lwip 的 tcp.c 提供的。下圖反映出了 modbus 協(xié)議棧的層次結(jié)構(gòu)。
最下層的tcp_bind()函數(shù)的作用是將一個(gè)連接結(jié)構(gòu)與本地 IP地址addr和端口號 port 進(jìn)行綁定。作為服務(wù)器端程序,執(zhí)行這一步操作是必要的,服務(wù)器必須與熟知端口進(jìn)行綁定才能接受客戶端的連接請求。這里可以看到,freemodbus協(xié)議棧并沒有以最標(biāo)準(zhǔn)的方式調(diào)用netconn_bind()進(jìn)行綁定,而是直接調(diào)用 tcp_bind()。原因應(yīng)該是這樣做可以免去IPC 通信過程,在無操作系統(tǒng)的環(huán)境下也能工作。
tcp_listen()的任務(wù)是讓 tcp 內(nèi)核監(jiān)聽這個(gè)端口;tcp_accept()是為新的連接注冊一個(gè)回調(diào)函數(shù)prvxMBTCPPortAccept()。在tcpip_thread()進(jìn)程監(jiān)聽到有效連接后會回調(diào)這個(gè)函數(shù)。而這個(gè)函數(shù)會把 modbus 的數(shù)據(jù)包從 tcp 數(shù)據(jù)包中復(fù)制出來,隨后發(fā)送 mailbox 信息給modbus 的進(jìn)程,用來處理消息。
2. 修改接口
隨后是修改porttcp.c。在這個(gè)文件中的 prvxMBTCPPortReceive()函數(shù)有一個(gè)致命問題必須被改正。這個(gè)函數(shù)是 tcpip_thread()核心進(jìn)程在收到 modbus 包后的回調(diào)函數(shù)。當(dāng)數(shù)據(jù)處理完成后它會調(diào)用pbuf_free()函數(shù)釋放pbuf包并返回 ERR_OK。tcpip_thread()核心進(jìn)程收到ERR_OK就知道數(shù)據(jù)已經(jīng)處理完了,就可以放心踏實(shí)的干別的事情了。然而不知為何,這里的 prvxMBTCPPortReceive() 函數(shù)在某些時(shí)候釋放了pbuf卻并不返回 ERR_OK。于是tcpip_thread()核心進(jìn)程在沒有收到正確的返回值時(shí)會認(rèn)為數(shù)據(jù)包沒有被處理,會把這個(gè)實(shí)際已經(jīng)廢棄的包暫存下來,下次再處理。等到下次處理時(shí)就會產(chǎn)生 pbuf錯(cuò)誤,使得整個(gè)程序被鎖死。
以下是修改的地方:
3. 上層代碼編寫
接下去是為上層應(yīng)用寫的示例代碼。以下 code 全部都是在 lwip_ping_freertos.c 中。 3.1 Tcpip協(xié)議棧初始化 我沒有指定 IP 地址,而是由路由器來分配。
3.2Modbus協(xié)議棧初始化
這個(gè)進(jìn)程首先是等 DHCP 拿到路由器給的 IP 地址,隨后就可以初始化 modbus 協(xié)議,并采用輪詢方式等待連接。
3.3編寫各種命令對應(yīng)的程序
三、驗(yàn)證 連接所有線路后編譯下載。我們的程序會在串口打印出路由器給它分配的 IP 地址。
打 開 QModMaster, Modbus 模式選 TCP;
選項(xiàng)->Modbus TCP->從機(jī) IP 填獲得的 IP 地址,端口是 502;功能碼選Read Holding Register (0x03),起始地址 100;
寄存器數(shù)量選 6,Data Format 選 16 進(jìn)制; 按連接按鈕,QModMaster 就能和我們的板子連上,按鈕變成連接起來的樣子;按旁邊讀寫按鈕,就能讀出register的值(見程序vTask_HoldingRegister())。 一切順利,移植成功!
QModMaster有一個(gè)總線監(jiān)視器窗口,可以看到收發(fā)的數(shù)據(jù)。
審核編輯 :李倩
-
控制器
+關(guān)注
關(guān)注
112文章
16367瀏覽量
178122 -
協(xié)議棧
+關(guān)注
關(guān)注
2文章
141瀏覽量
33633 -
SDK
+關(guān)注
關(guān)注
3文章
1036瀏覽量
45957
原文標(biāo)題:i.MX RT1024: 移植 MODBUS TCP協(xié)議棧教程
文章出處:【微信號:NXP_SMART_HARDWARE,微信公眾號:恩智浦MCU加油站】歡迎添加關(guān)注!文章轉(zhuǎn)載請注明出處。
發(fā)布評論請先 登錄
相關(guān)推薦
評論