AUTOSAR網路管理節點內部有兩個狀態,一個是Requested - 被請求狀態,另一個是Released - 被釋放狀態,當節點的應用層需要使用匯流排進行通訊的時候,會呼叫介面使得節點進入請求狀態,當應用層沒有通訊需求的時候,呼叫介面使得節點進入釋放狀態。
需要注意的是,即使節點當前處於釋放狀態,節點的通訊依然有可能是處於開啟狀態,因為網路上的其它節點有可能正在請求匯流排。所以這個狀態代表的是節點應用層是否有通訊需求,並不代表匯流排開啟或關閉。有通訊需求的時候處於請求狀態,無通訊需求的時候處於釋放,但匯流排是否在通訊不僅僅取決於當前節點自己,而是取決於網路上的所有節點。
節點上電初始化後預設進入釋放狀態。
一個CAN網路通訊節點包含以下執行模式:
處於網路模式中的節點,網路通訊是處於開啟或工作模式(包含了開始工作時和結束工作時的準備階段)。網路模式又細分為以下三個階段:
當節點從其他模式進入Network Mode時,預設進入Repeat Message State,該階段是網路正式開始工作前的準備階段,用來等待網路中所有相關節點進行網路準備,開啟通訊。
節點由Repeat Message State進入Normal Operation State,該狀態為節點通訊正常工作狀態。
節點工作完成後,由Normal Operation State狀態進入Ready Sleep State,準備進入睡眠狀態。該階段用來等待網路中所有節點工作完成,之後統一進入睡眠狀態。
節點從網路模式的準備睡眠階段進入預睡眠模式,該模式與Ready Sleep State的作用類似,但它已經不再屬於網路模式了,是正式進入睡眠階段前更進一步的準備階段。
睡眠模式就是節點停止工作的模式,可以節省能量消耗,是整個網路管理的最終目的。網路管理工作就是管理各個節點如何有序進入睡眠模式和恢復工作狀態。節點上電或復位後應預設進入睡眠模式。
在AUTOSAR中,網路管理報文以NM PDU的形式存在,典型的結構如下圖所示:
其中有用的兩個位元組就是Byte0-Source Node Identifier(節點源地址)和Byte1-Control Bit Vector(控制位元組)。這兩個位元組在NM PDU中的位置是可以設定的。
節點源地址是節點的識別符號,網路中所有節點的源地址是唯一的,通常位於0x400-0x4FF範圍內。
Control Bit Vector的定義如下,在節點初始化的時候被置為0x00:
我們對著標準中的這幅狀態轉換圖,來詳細說一下各個狀態之間是如何轉換的,以及節點處於每個狀態時要做哪些工作。
節點上電或復位後,經初始化函數CanNm_Init()預設進入匯流排睡眠狀態,在匯流排睡眠狀態下應停發所有應用報文和網路管理報文,但要可以接收網路管理報文,以使得其它節點能夠喚醒當前節點。
當節點收到了網路管理報文時,不是直接進入網路模式,而是上報應用層,應用層判斷當前狀態,允許的話會呼叫CanNm_PassiveStartup()函數,使節點進入網路模式。當節點自身想要進行網路通訊時,呼叫CanNm_NetworkRequest()使節點進入網路模式。前者是被動,後者是主動。後者傳送的網路管理報文中CBV的Active Wakeup Bit位為1.
節點在網路模式中要一直傳送應用報文。
節點進入網路模式後,預設進入重複報文階段,啟動定時器NM-Timeout,NM-Timeout用來記錄網路管理報文是否超時,其超時時間為CanNmTimeoutTime,每收到或成功傳送一幀網路管理報文,都應重新啟動NM-Timeout。節點要開始週期傳送網路管理報文。常規情況下,節點要先等待一個時間偏移量(CanNmMsgCycleOffset)後再傳送第一幀網路管理報文,傳送週期為CanNmMsgCycleTime,傳送次數為CanNmRepeatMessageTime。
網路中所有節點的報文傳送週期CanNmMsgCycleTime和CanNmTimeoutTime都是相同的,且CanNmTimeoutTime必須大於CanNmMsgCycleTime;所有節點的CanNmMsgCycleOffset都是不同的,以防止網路中所有節點同時傳送網路管理報文造成網路擁塞。
當節點在重複報文階段傳送了CanNmRepeatMessageTime次網路管理報文後,需要退出重複報文階段,退出時判斷網路當前處於釋放狀態還是請求狀態,如果處於請求狀態,則進入常規執行階段,如果處於釋放狀態,則進入準備睡眠階段。
在常規執行階段中,節點要週期傳送網路管理報文,傳送週期為CanNmMsgCycleTime。節點網路此時處於正常工作狀態。
在常規執行階段中,定時器NM-Timeout如果超時了要被重新啟動。
當節點處於常規執行階段時,如果收到了Repeat Message Request置為1的網路管理報文,則會強制重新進入重複報文階段。進入重複報文階段後的邏輯同上。
當節點不再需要進行網路通訊時,應用層會呼叫**CanNm_NetworkRelease()**函數,釋放網路,節點進入準備睡眠階段,停髮網路管理報文,但要保持應用報文的傳送。
節點處於準備睡眠階段時,如果應用層重新需要使用網路,可以呼叫CanNm_NetworkRequest()函數使節點重新回到常規執行階段。
當節點處於準備睡眠階段時,如果收到了Repeat Message Request置為1的網路管理報文,也會強制重新進入重複報文階段。進入重複報文階段後的邏輯同上。
如上文所述,當重複報文階段退出時如果節點網路處於釋放狀態,則節點直接進入準備睡眠階段。
當節點在準備睡眠階段NM-Timeout超時,即網路中所有節點都已進入準備睡眠階段(或不處於網路模式),網路中沒有網路管理報文,節點將會進入預睡眠模式,同時啟動定時器Wait Bus-Sleep Timer,其超時時間為CanNmWaitBusSleepTime,所有節點的CanNmWaitBusSleepTime都應設定為相同的,以保證所有節點同時進入睡眠模式。
節點在預睡眠模式中同樣不傳送網路管理報文,同時還要停止應用報文的傳送。
步驟⑩和⑫我理解是一回事,就是當節點處於預睡眠模式的時候,應用層想要使用網路進行通訊,或收到了其他節點的網路管理報文,就會重新進入網路模式,也是預設進入重複報文階段。
當節點在預睡眠模式中定時器Wait Bus-Sleep Timer超時後,就會進入睡眠模式,睡眠模式中網路管理報文和應用報文同樣都不傳送,節點正式進入休眠狀態,應儘可能地關閉功能,降低能量消耗。
我們前文說過,當節點進入重複報文階段時,會重複傳送幾次網路管理報文。常規情況下,因為網路管理報文通常週期比較長,且第一幀報文還有偏移量,所以啟用網路的實時性不是很好,標準中為解決這個問題制定了一個能夠立即傳送網路管理報文的策略。
當CanNmImmediateNmTransmissions > 0時,要啟動網路管理報文立即傳送模式,此時CanNmMsgCycleOffset不再起作用,節點儘可能快地傳送第一幀網路管理報文,傳送週期不再為CanNmMsgCycleTime,而是用更短的CanNmImmediateNmCycleTime,共傳送CanNmImmediateNmTransmissions次,然後進入常規執行階段,之後網路管理報文的傳送週期恢復CanNmMsgCycleTime。
注意:網路管理報文立即傳送模式只有當節點主動喚醒網路的時候才啟用,被動喚醒時不啟用。是當前節點用來快速喚醒網路中其它節點的一個策略。
由上文可知,當節點處於重複報文階段和常規執行階段的時候,都會週期性傳送網路管理報文,這對匯流排負載是一種消耗,且網路中節點越多,匯流排負載佔用越大。標準中制定了一種策略來降低匯流排負載。
通常情況下,在常規執行階段,所有節點都要傳送網路管理報文,節點中有一個定時器CanNm Message Cycle Timer,每傳送一幀網路管理報文,該定時器就重新裝載CanNmMsgCycleTime的值,即網路管理報文的傳送週期為CanNmMsgCycleTime。但其實只要有一個節點在傳送報文,網路中所有節點就都可以保持在網路模式,多發的網路管理報文是對匯流排負載的浪費。
匯流排負載降低策略具體為:
當設定引數與CanNmBusLoadReductionEnabled為有效,且節點處於常規執行階段時,進入匯流排負載降低模式,此時:
這種策略的結果是:網路中只有CanNmMsgReducedTime 值最小的兩個節點交替傳送網路管理報文。
我們假設節點A的CanNmMsgReducedTime 最小,B次之,在某一時刻,網路上所有節點都進入了匯流排負載降低模式,此時某個節點傳送了一幀網路管理報文,之後該節點因為是傳送節點,所以定時器CanNm Message Cycle Timer重置為CanNmMsgCycleTime ,其餘節點是接收節點,CanNm Message Cycle Timer重置為各自的CanNmMsgReducedTime,節點A的CanNmMsgReducedTime值最小,所以一段時間後率先發了一條網路管理報文,之後將CanNm Message Cycle Timer重置為CanNmMsgCycleTime,其餘節點CanNm Message Cycle Timer再次重置為各自的CanNmMsgReducedTime,此時網路中節點B變成了CanNm Message Cycle Timer值最小的節點,一段時間後會發出一條網路管理報文,這又會使得節點A的CanNm Message Cycle Timer值變成最小,所以實現了網路中CanNmMsgReducedTime 值最小的兩個節點交替傳送網路管理報文,其餘節點不傳送網路管理報文。
當最小的兩個節點中某個節點進入準備睡眠階段,不再傳送網路管理報文了,那麼CanNmMsgReducedTime 值略大的下一個節點會開始傳送網路管理報文。
當網路中只有一個節點處於常規執行階段時,網路管理報文的週期為CanNmMsgCycleTime。
當設定引數CanNmRemoteSleepIndEnabled為有效的時候,如果節點在CanNmRemoteSleepIndTime時間後仍沒有收到其他節點傳送的網路管理報文,說明其它節點都已經進入休眠或準備休眠,此時應呼叫Nm_RemoteSleepIndication()函數通知應用層網路中所有節點都進入了休眠。如果此時節點又收到了其他節點傳送的網路管理報文,應該再呼叫Nm_RemoteSleepCancellation()函數通知應用層取消之前的指示。該策略稱為遠端睡眠指示。
下表展示了所有網路管理相關的時間引數,最左欄是設定引數,通常通過設定工具進行設定,中間欄是節點中網路管理程式需要用到的定時器:
下圖為所有網路管理相關內容的一個梳理,通常情況下控制器的狀態轉換如下圖藍色箭頭所示: