- 1、本文档共7页,可阅读全部内容。
- 2、原创力文档(book118)网站文档一经付费(服务费),不意味着购买了该文档的版权,仅供个人/单位学习、研究之用,不得用于商业用途,未经授权,严禁复制、发行、汇编、翻译或者网络传播等,侵权必究。
- 3、本站所有内容均由合作方或网友上传,本站不对文档的完整性、权威性及其观点立场正确性做任何保证或承诺!文档内容仅供研究参考,付费前请自行鉴别。如您付费,意味着您自己接受本站规则且自行承担风险,本站不退款、不进行额外附加服务;查看《如何避免下载的几个坑》。如果您已付费下载过本站文档,您可以点击 这里二次下载。
- 4、如文档侵犯商业秘密、侵犯著作权、侵犯人身权等,请点击“版权申诉”(推荐),也可以打举报电话:400-050-0827(电话支持时间:9:00-18:30)。
查看更多
1.??FreeModbus协议分析
协议必须首先调用初始化功能eMBinit()函数。后调用eMBEnable(),最后,在循环体或者单独一个任务中调用eMBPoll()函数。
2.??应用层协议
2.1.????系统的启动
2.1.1.??eMBInit()函数的源码分析
以RTU方式为例,首先,检查调用的地址是否合法。如不合法,返回错误。如果合法则继续执行,
首先,针对RTU方式还是ASCII方式,选择不同的编译模块。
对需要调用的函数指针进行复制。如果移植需要改变其他用途,则要修改相应的指针,包括如下赋值:
???????????pvMBFrameStartCur = eMBRTUStart;
???????????pvMBFrameStopCur = eMBRTUStop;
???????????peMBFrameSendCur = eMBRTUSend;
???????????peMBFrameReceiveCur = eMBRTUReceive;
???????????pvMBFrameCloseCur = MB_PORT_HAS_CLOSE ? vMBPortClose :NULL;
???????????pxMBFrameCBByteReceived= xMBRTUReceiveFSM;
???????????pxMBFrameCBTransmitterEmpty = xMBRTUTransmitFSM;
???????????pxMBPortCBTimerExpired = xMBRTUTimerT35Expired;
然后调用eStatus =eMBRTUInit( ucMBAddress, ucPort, ulBaudRate, eParity);具体初始化通讯端口。
2.1.2.??eMBRTUInit
eMBRTUInit这个函数主要干两件事:
第一,??初始化串口:???
if( xMBPortSerialInit(ucPort, ulBaudRate, 8, eParity ) != TRUE )
{
??eStatus = MB_EPORTERR;
}
这个函数在portserial.c中,需要用户在移植的时候根据自己的处理器编写。
第二,??初始化计时器:首先要根据波特率计算一下是3.5~5.0个字节周期的时间,然后再调用xMBPortTimersInit( ( USHORT ) usTimerT35_50us),初始化计时器。这个函数在porttimer.c中,需要用户在移植的时候根据自己的处理器编写。
2.1.3.??eMBEnable源码分析
首先,看看Modbus功能是否是被关闭的,如果不是被关闭(可能是没有被初始化或者已经打开),就返回错误。
如果是disable状态,就干下面两件事:
l?调用pvMBFrameStartCur()。由于这是个函数指针,在模块eMBInit中,指向了eMBRTUStart函数
n?在源代码中有这样一段注释:,意思是,首先设置成STATE_RX_INIT,然后打开计时器,等待t3.5以后,进入STATE_RX_IDLE状态。
n?看源代码中,首先有设置Receiver的状态,后调用vMBPortSerialEnable,设置接收状态,然后打开定时器。
n?当定时器中断后,自动调用中断服务程序,在中断服务程序中,只调用了pxMBPortCBTimerExpired,而这是一个函数指针,在RTU方式初始化时,被指向了xMBRTUTimerT35Expired()函数。
n?xMBRTUTimerT35Expired函数在mbrtu.c中,在这里,我们只看第一种方式,就是进入初始化状态,在t35时间以后,只调用了一个xNeedPoll = xMBPortEventPost( EV_READY );
n?xMBPortEventPost函数就是在事件队列里加了一个EV_RDY事件。
l?然后,将eMB状态改为使能状态,
l?初始化结束。
2.2.????总线侦听eMBPoll()
首先,判断系统是否被使能,如果没有,则返回错误值。
然后,检查是否有事件发生,如果有,则根据不同类型的事件响应:
l?如果是EV_RDY,表示系统刚刚进入侦听状态,则什么都不做;
l?如果状态为EV_FRAME_RECEIVED,也就是接收到完整的帧,做下面两件事情:
n?调用eStatus=peMBFrameReceiveCur( ucRcvAddress,ucMBFrame, usLength)。这是一个函数指针,在eMBInit中,被初始化指向eMBRTUReceive。
n?eMBRTUReceive这个函数首先校验帧的长度和CRC,然后从协议中解析出地址、数据和长度。
n
文档评论(0)