一、背景
本文將以SSC從站協(xié)議棧代碼為例,分析EtherCAT從站運行過程中報錯(錯誤碼:0x1A\0x1B\0x2C),說明協(xié)議棧的檢測邏輯。
該類錯誤為運行時錯誤,是從站能成功進入OP狀態(tài)以后,在運行過程中檢測到錯誤,狀態(tài)從OP退回到更低級狀態(tài)時報出的錯誤碼。對于從站無法成功進入OP狀態(tài)的初始化錯誤不在此分析中。
當(dāng)從站發(fā)生錯誤時,會切換自身的狀態(tài)從OP到更低狀態(tài),并將錯誤代碼寫入從站的0x134寄存器報告AL狀態(tài)碼。

| 錯誤碼 | 說明 |
|---|---|
| 0x1A | Synchronization error(網(wǎng)絡(luò)的抖動導(dǎo)致從站的同步丟失) |
| 0x1B | Syncmanager watchdog(從站未接收到周期性數(shù)據(jù)的時間,持續(xù)超過了watchdog閾值) |
| 0x2C | Fatal SYNC error(ESC再未收到SYNC硬件中斷) |
完整的AL Status Code定義在ecatslv.h中。
二、 SSC協(xié)議棧代碼分析
不同參數(shù)配置下,SSC Tool生成的協(xié)議棧代碼會有一定不同,本例使用的參數(shù)選項包括如下設(shè)置:
| 參數(shù) | 說明 |
|---|---|
| ESC_SM_WD_SUPPORTED = 1 | 使用硬件同步管理器看門狗 |
| ECAT_TIMER_INT = 1 | 在軟件1ms中斷函數(shù)中執(zhí)行ECAT_CheckTimer() |
| AL_EVENT_ENABLED = 1 | 使用PDI中斷 |
| DC_SUPPORTED = 1 | 支持DC功能 |
分析協(xié)議棧代碼,可以發(fā)現(xiàn)在運行過程中錯誤碼0x1A\0x1B\0x2C是在CheckIfEcatError()函數(shù)中報出,
該函數(shù)在mainloop()中被調(diào)用,會周期性的執(zhí)行,負(fù)責(zé)檢查通信和同步變量,并設(shè)置AL status(Reg0x130)和AL status code(狀態(tài)錯誤碼 Reg0x134)。
/////////////////////////////////////////////////////////////////////////////////////////
/**
\brief Checks communication and synchronisation variables and update AL status / AL status code if an error has occurred
*////////////////////////////////////////////////////////////////////////////////////////
void CheckIfEcatError(void)
{
/*if the watchdog is enabled check the process data watchdog in the ESC
and set the AL status code 0x1B if the watchdog expired*/
if (EcatWdValue != 0) // 在從站初始化過程中賦值,默認(rèn)是100ms
{
/*watchdog time is set => watchdog is active*/
UINT32 WdStatusOK = 0;
HW_EscReadDWord(WdStatusOK, ESC_PD_WD_STATE); // 讀0x440寄存器獲取硬件WatchDog的狀態(tài)
WdStatusOK = SWAPDWORD(WdStatusOK);
if (!(WdStatusOK & ESC_PD_WD_TRIGGER_MASK) && (nPdOutputSize > 0)) // 當(dāng)WatchDog溢出時
{
/*The device is in OP state*/
if (bEcatOutputUpdateRunning
)
{
AL_ControlInd(STATE_SAFEOP, ALSTATUSCODE_SMWATCHDOG); //錯誤碼 0x1B
return;
}
else
{
bEcatFirstOutputsReceived = FALSE;
}
}
}
if(bDcSyncActive)
{
if(bEcatOutputUpdateRunning)
{
/*Slave is in OP state*/
if(!bDcRunning) //判斷條件
{
AL_ControlInd(STATE_SAFEOP, ALSTATUSCODE_FATALSYNCERROR); //錯誤碼 0x2C
return;
}
else if(!bSmSyncSequenceValid) // 判斷條件
{
AL_ControlInd(STATE_SAFEOP, ALSTATUSCODE_SYNCERROR); //錯誤碼 0x1A
return;
}
}
}
}
2.1 同步管理器看門狗錯誤碼 ALSTATUSCODE_SMWATCHDOG(0x1B)
該錯誤碼是利用ESC內(nèi)部的硬件看門狗監(jiān)控主站發(fā)給從站的過程數(shù)據(jù)是否按時被接收到。設(shè)定時間內(nèi)沒有接收到主站發(fā)來的PDO數(shù)據(jù)幀,看門狗就會溢出觸發(fā)報錯。
同步管理器看門狗(SM WatchDog)監(jiān)控同步管理器的狀態(tài),默認(rèn)配置SM2(主站發(fā)過程數(shù)據(jù)給從站)事件觸發(fā)看門狗。
當(dāng)從站接收到主站發(fā)來的過程數(shù)據(jù)時觸發(fā)硬件喂狗,看門狗不會超時。但當(dāng)從站長時間接收不到主站發(fā)來的過程數(shù)據(jù)幀時,看門狗(默認(rèn)閾值100ms)就會計數(shù)超時,讀0x440寄存器獲取當(dāng)前看門狗超時情況進行報錯,代碼分析見上文CheckIfEcatError()函數(shù)。
硬件同步管理器看門狗(SM WatchDog)的閾值和觸發(fā)設(shè)置如下:
出錯原因:同步管理器看門狗錯誤其默認(rèn)閾值是100ms,遠(yuǎn)大于常見的主站通信周期,在如此長時間沒有收到主站發(fā)來的過程數(shù)據(jù)幀,基本上是物理鏈路出了問題,比如鏈路中PHY出現(xiàn)斷聯(lián)導(dǎo)致主站和該從站之間斷開造成的。
2.2 致命同步錯誤碼 ALSTATUSCODE_FATALSYNCERROR(0x2C)
該錯誤碼是利用MCU提供的1ms軟件定時器監(jiān)控的SYNC0中斷服務(wù)函數(shù)的執(zhí)行情況。當(dāng)SYNC0中斷服務(wù)函數(shù)Sync0_Isr()在規(guī)定的時間內(nèi)得不到執(zhí)行時觸發(fā)報錯。
由上文CheckIfEcatError()函數(shù)可知,在函數(shù)中錯誤碼ALSTATUSCODE_FATALSYNCERROR(0x2C)根據(jù)bDcRunning變量狀態(tài)實現(xiàn)檢測。
查找bDcRunning變量的賦值情況,其在DC_CheckWatchdog()中賦值,該函數(shù)的調(diào)用路徑是:
MCU提供的1ms定時中斷服務(wù)函數(shù)(生成SSC代碼時設(shè)置ECAT_TIMER_INT = 1) -> ECAT_CheckTimer() -> DC_CheckWatchdog() -> bDcRunning變量賦值。
/////////////////////////////////////////////////////////////////////////////////////////
/**
\brief This function checks the current Sync state and set the local flags
The analyse of the local flags is handled in "CheckIfEcatError"
*////////////////////////////////////////////////////////////////////////////////////////
void DC_CheckWatchdog(void)
{
if(bDcSyncActive && bEcatInputUpdateRunning)
{
/*If Sync0 watchdog is enabled and expired*/
if((Sync0WdValue > 0) && (Sync0WdCounter >= Sync0WdValue)) //判斷計數(shù)器是否超出閾值
{
/*Sync0 watchdog expired*/
bDcRunning = FALSE; //超出閾值,設(shè)置bDcRunning為假
}
else
{
if(Sync0WdCounter < Sync0WdValue) // 計數(shù)器未超出閾值
{
Sync0WdCounter ++; // 計數(shù)器遞增
}
bDcRunning = TRUE;
}
//省略代碼
}
}
從DC_CheckWatchdog()代碼可知,該函數(shù)負(fù)責(zé)檢查DC同步狀態(tài)并設(shè)置flag,然后由CheckIfEcatError()根據(jù)相應(yīng)flag進行報錯。
為設(shè)置標(biāo)志bDcRunning,引入變量Sync0WdValue和Sync0WdCounter,可以將其機制理解為軟件實現(xiàn)的看門狗。
Sync0WdValue是閾值,Sync0WdCounter是計數(shù)器值。計數(shù)器Sync0WdCounter在DC_CheckWatchdog()中每1ms遞增1,當(dāng)Sync0_Isr()執(zhí)行時對Sync0WdCounter清零(相當(dāng)于喂狗),如果沒有執(zhí)行Sync0_Isr()(相當(dāng)于沒有喂狗),Sync0WdCounter會計數(shù)到超出閾值Sync0WdValue,觸發(fā)報錯邏輯。
PROTO UINT16 Sync0WdCounter; /**< \brief Sync0 watchdog counter*/
PROTO UINT16 Sync0WdValue; /**< \brief Sync0 watchdog value*/
閾值Sync0WdValue在從站初始化過程中由函數(shù)StartInputHandler()賦值,其賦值規(guī)則為閾值Sync0WdValue = 2 * Sync0周期且大于等于1ms(因為軟件定時器的時間精度是1ms),閾值為0時表示禁用。
UINT16 StartInputHandler(void)
{
//省略代碼
/* calculate the Sync0/Sync1 watchdog timeouts */
if ( (dcControl & ESC_DC_SYNC0_ACTIVE_MASK) != 0 )
{
/*calculate the Sync0 Watchdog counter value the minimum value is 1 ms
if the sync0 cycle is greater 500us the Sync0 Wd value is 2*Sycn0 cycle */
if(cycleTimeSync0 == 0)
{
Sync0WdValue = 0;
}
else
{
UINT32 Sync0Cycle = cycleTimeSync0/100000; //獲取Sync0周期,單位100us
if(Sync0Cycle < 5)
{
/*Sync0 cycle less than 500us*/
Sync0WdValue = 1; // 最小閾值1ms
}
else
{
Sync0WdValue = (UINT16)(Sync0Cycle*2)/10; // 閾值 = 2 * Sync0Cycle, 結(jié)果換算為ms
}
}
//省略代碼
}
//省略代碼
}
計數(shù)器Sync0WdCounter在Sync0_Isr()中清零。
void Sync0_Isr(void)
{
Sync0WdCounter = 0; // 計數(shù)器清零
//省略代碼
}
綜上,致命同步錯誤ALSTATUSCODE_FATALSYNCERROR(0x2C)的檢查邏輯為:根據(jù)Sync0的周期設(shè)置閾值Sync0WdValue,在MCU提供的1ms定時器中斷中對計數(shù)器值Sync0WdCounter+1,在Sync0中斷服務(wù)函數(shù)中對計數(shù)器值Sync0WdCounter清零。當(dāng)Sync0的中斷服務(wù)函數(shù)長時間不被執(zhí)行時,Sync0WdCounter就會累加超出閾值,DC_CheckWatchdog()將設(shè)置bDcRunning為假,最后CheckIfEcatError()依據(jù)bDcRunning報出錯誤。
該錯誤較少出現(xiàn)。因為SYNC0中斷請求是ESC自身的定時器(分布時鐘:Distributed Clocks)周期性產(chǎn)生的中斷請求。當(dāng)分布時鐘DC被激活之后,Sync0中斷請求的產(chǎn)生與通信情況無關(guān)(不考慮通信過程對DC時鐘進行的校準(zhǔn)),即使拔掉網(wǎng)線,SYNC0中斷請求依然周期性產(chǎn)生,MCU接收到Sync0中斷請求之后就會去執(zhí)行Sync0_Isr()中斷服務(wù)函數(shù)實現(xiàn)軟件定時器喂狗。
理論出錯原因:
- 主站在未更改從站同步模式的情況下,異常關(guān)閉從站的分布時鐘DC功能,導(dǎo)致其不再產(chǎn)生SYNC0中斷請求。
- 從站MCU錯誤關(guān)閉Sync0中斷響應(yīng),即雖然Sync0中斷請求產(chǎn)生了但中斷響應(yīng)被關(guān)閉了或其他原因?qū)е碌牟话磿r執(zhí)行SYNC中斷服務(wù)函數(shù)。
2.3 同步錯誤碼 ALSTATUSCODE_SYNCERROR(0x1A)
該錯誤碼檢測PDI_Isr()和Sync0_Isr()中斷服務(wù)函數(shù)的執(zhí)行順序。
由上文CheckIfEcatError()函數(shù)可知,錯誤碼ALSTATUSCODE_SYNCERROR(0x1A)是根據(jù)bSmSyncSequenceValid變量狀態(tài)實現(xiàn)的檢測。
PROTO BOOL bSmSyncSequenceValid; /**< \brief Set to true if SM/Sync0 sequence is valid*/
從bSmSyncSequenceValid標(biāo)志的名稱上可以看出,這是監(jiān)控SyncManager事件(PDI_Isr中斷函數(shù))和Sync0事件(Sync0_Isr中斷函數(shù))的執(zhí)行順序。
查看標(biāo)志bSmSyncSequenceValid的賦值過程,可知其同樣在函數(shù)DC_CheckWatchdog()中賦值:
/////////////////////////////////////////////////////////////////////////////////////////
/**
\brief This function checks the current Sync state and set the local flags
The analyse of the local flags is handled in "CheckIfEcatError"
*////////////////////////////////////////////////////////////////////////////////////////
void DC_CheckWatchdog(void)
{
if(bDcSyncActive && bEcatInputUpdateRunning)
{
// 省略代碼
if(bDcRunning)
{
/*ECATCHANGE_START(V5.13) ESM4*/
if((sErrorSettings.u16SyncErrorCounterLimit == 0) || (sSyncManOutPar.u16SmEventMissedCounter < sErrorSettings.u16SyncErrorCounterLimit))
/*ECATCHANGE_END(V5.13) ESM4*/
{
bSmSyncSequenceValid = TRUE;
/*Wait for PLL is active increment the Pll valid counter*/
if (i16WaitForPllRunningTimeout > 0)
{
i16WaitForPllRunningCnt++;
}
}
else if (bSmSyncSequenceValid) // 條件1: ((sErrorSettings.u16SyncErrorCounterLimit != 0) && (sSyncManOutPar.u16SmEventMissedCounter >= sErrorSettings.u16SyncErrorCounterLimit))
{
bSmSyncSequenceValid = FALSE; // 報錯
/*Wait for PLL is active reset the Pll valid counter*/
if (i16WaitForPllRunningTimeout > 0)
{
i16WaitForPllRunningCnt = 0;
}
}
}
else if(bSmSyncSequenceValid) // 條件2: (!bDcRunning), 該條件是在ALSTATUSCODE_FATALSYNCERROR(0x2C)時產(chǎn)生的
{
bSmSyncSequenceValid = FALSE; // 報錯
}
}
}
標(biāo)志bSmSyncSequenceValid的賦值過程使用到對象字典參數(shù)中的sSyncManOutPar.u16SmEventMissedCounter和sErrorSettings.u16SyncErrorCounterLimit。
閾值sErrorSettings.u16SyncErrorCounterLimit的值為4(賦值細(xì)節(jié)不展開):
#defineMAX_SM_EVENT_MISSED 4 /**< \brief threshold of max missed counter value (0x1C32.11 / 0x1C33.11)*/
計數(shù)值sSyncManOutPar.u16SmEventMissedCounter在Sync0_Isr(void)中增加:
sSyncManOutPar.u16SmEventMissedCounter = sSyncManOutPar.u16SmEventMissedCounter + 3;
計數(shù)值sSyncManOutPar.u16SmEventMissedCounter在PDI_Isr(void)中減?。?/p>
sSyncManOutPar.u16SmEventMissedCounter--;
為了管理sSyncManOutPar.u16SmEventMissedCounter的計數(shù),引入u16SmSync0Counter和u16SmSync0Value變量,實現(xiàn)對PDI_Isr()和Sync0_Isr()執(zhí)行順序的檢測。
PROTO UINT16 u16SmSync0Counter; /**< /brief Incremented by one on every Sync0 event and reset to 0 on every SM event. It is used to check the SM/Sync0 sequence */
PROTO UINT16 u16SmSync0Value; /**< /brief Allowed Sync0 events within one SM cycle. If 0 the Sequence check is disabled */
valid*/
閾值u16SmSync0Value同樣在初始過程中由StartInputHandler賦值,其根據(jù)同步類型進行賦值,在使用Sync0不使用Sync1的情況下,其被賦值為1。
UINT16 StartInputHandler(void)
{
//省略代碼
if(bSubordinatedCycles == TRUE)
{
// 省略代碼
}
else
{
if(SyncType0x1C32 == SYNCTYPE_DCSYNC0) // 判斷同步模式
{
/* if SyncType of 0x1C32 is 2 the Sync0 event is trigger once during a SM cycle */
u16SmSync0Value = 1; // 賦值為1
}
if(SyncType0x1C33 != SYNCTYPE_DCSYNC1)
{
LatchInputSync0Value = 1;
}
}
//省略代碼
}
查看計數(shù)器u16SmSync0Counter的賦值過程:
在Sync0_Isr()中u16SmSync0Counter遞增,當(dāng)u16SmSync0Counter遞增超出閾值時sSyncManOutPar.u16SmEventMissedCounter會+3。
void Sync0_Isr(void)
{
// 省略代碼
if(u16SmSync0Value > 0)
{
/* Check if Sm-Sync sequence is invalid */
if (u16SmSync0Counter > u16SmSync0Value) // 當(dāng)計數(shù)器值超出閾值
{
if ((nPdOutputSize > 0) && (sSyncManOutPar.u16SmEventMissedCounter <= sErrorSettings.u16SyncErrorCounterLimit))
{
sSyncManOutPar.u16SmEventMissedCounter = sSyncManOutPar.u16SmEventMissedCounter + 3; // 對象字典參數(shù)+3
}
if ((nPdInputSize > 0) && (nPdOutputSize == 0) && (sSyncManInPar.u16SmEventMissedCounter <= sErrorSettings.u16SyncErrorCounterLimit))
{
sSyncManInPar.u16SmEventMissedCounter = sSyncManInPar.u16SmEventMissedCounter + 3;
}
} // if (u16SmSync0Counter > u16SmSync0Value)
if ((nPdOutputSize == 0) && (nPdInputSize > 0))
{
// 省略代碼
}
else if (u16SmSync0Counter <= u16SmSync0Value) // 條件 (nPdOutputSize != 0)
{
u16SmSync0Counter++; // 計數(shù)器遞增
}
}//SM -Sync monitoring enabled
// 省略代碼
}
在PDI_Isr()中u16SmSync0Counter清零,并在sSyncManOutPar.u16SmEventMissedCounter > 0的情況下對其-1。
void PDI_Isr(void)
{
// 省略代碼
if(bEscIntEnabled)
{
if ( ALEvent & PROCESS_OUTPUT_EVENT )
{
if(bDcRunning && bDcSyncActive)
{
/* Reset SM/Sync0 counter. Will be incremented on every Sync0 event*/
u16SmSync0Counter = 0; // 計數(shù)器清零
}
if(sSyncManOutPar.u16SmEventMissedCounter > 0)
{
sSyncManOutPar.u16SmEventMissedCounter--; // 對象字典參數(shù)-1
}
sSyncManInPar.u16SmEventMissedCounter = sSyncManOutPar.u16SmEventMissedCounter;
}
}
// 省略代碼
}
綜上,u16SmSync0Counter在Sync0_Isr()中+1,在PDI_Isr()中清零。Sync0中斷由從站本地DC時鐘周期性觸發(fā),PDI(SM2事件)中斷由主站發(fā)PDO數(shù)據(jù)幀到從站,從站接收后觸發(fā)。
出錯原因:
正常情況下,每一個Sync0周期內(nèi),從站都能接收到主站發(fā)來的一次PDO數(shù)據(jù)幀。如果因為某種原因,在一個Sync0周期中,從站沒有接收到主站的PDO數(shù)據(jù)幀,那么就不會觸發(fā)PDI中斷,u16SmSync0Counter就不會清零,計數(shù)值就會超出閾值,造成sSyncManOutPar.u16SmEventMissedCounter+3。依此類推直到DC_CheckWatchdog()函數(shù)依據(jù)sSyncManOutPar.u16SmEventMissedCounter設(shè)置標(biāo)志bSmSyncSequenceValid為假,最后CheckIfEcatError()函數(shù)依據(jù)bSmSyncSequenceValid進行報錯。
主站發(fā)出PDO數(shù)據(jù)幀周期的抖動或物理鏈路斷開導(dǎo)致主站數(shù)據(jù)幀無法到達從站都能造成在一個Sync0周期中,從站接收不到主站的PDO數(shù)據(jù)幀。如果是物理鏈路問題導(dǎo)致的數(shù)據(jù)幀無法到達從站,由于物理鏈路的斷開和恢復(fù)時間,遠(yuǎn)超出100ms,從站會有超出100ms時間,無法接收到主站的PDO數(shù)據(jù)幀,這會最終導(dǎo)致報出同步管理器看門狗錯誤碼ALSTATUSCODE_SMWATCHDOG(0x1B)。如果最終產(chǎn)生的錯誤碼只有同步錯誤碼 ALSTATUSCODE_SYNCERROR(0x1A),這就說明是由主站發(fā)出PDO數(shù)據(jù)幀的周期抖動問題造成。
對于主站發(fā)出PDO數(shù)據(jù)幀的抖動,可以適當(dāng)在主站中配置Sync Shift Time,來增大對主站PDO數(shù)據(jù)幀周期抖動的容許,該辦法并不完全解決問題(細(xì)節(jié)此處不展開)。
更改閾值sErrorSettings.u16SyncErrorCounterLimit(值:MAX_SM_EVENT_MISSED)可以增大對該類錯誤的容許。
補充說明:
需要說明的是該過程中sSyncManOutPar.u16SmEventMissedCounter會在Sync_Isr()中滿足出錯條件時+3,在PDI_Isr()中滿足條件時-1,其數(shù)值增加和減少的幅度不同,
個人理解該機制可以用于適配不同的sync0周期設(shè)置。比如sync0周期是125us,DC_CheckWatchdog()執(zhí)行周期是固定1ms,使用這種機制可以有效監(jiān)控一段時間內(nèi)的出錯情況。如果一段時間內(nèi)連續(xù)出現(xiàn)Sync_Isr()和PDI_Isr()執(zhí)行順序問題,則會造成計數(shù)值累加到較大值(單次+3),即使后續(xù)被減小(單次-1);如果一段時間內(nèi)只是出現(xiàn)一兩次Sync_Isr()和PDI_Isr()執(zhí)行順序問題,計數(shù)值累加值不大,其后PDI_Isr()執(zhí)行時-1,等DC_CheckWatchdog()函數(shù)執(zhí)行時sSyncManOutPar.u16SmEventMissedCounter可能已經(jīng)被減小到閾值之下了不報錯了。
除了解決周期上不同的問題,該機制還可以解決sync0周期與DC_CheckWatchdog()執(zhí)行的1ms周期的異步問題。(sSyncManOutPar.u16SmEventMissedCounter的增減機制為個人理解,如有錯誤歡迎指正)。
總結(jié)
上文CheckIfEcatError()函數(shù)實現(xiàn)的理解可以看出其監(jiān)控了3種錯誤狀態(tài),3種錯誤監(jiān)控的時間閾值不同, 每個錯誤后都會有return語句提前返回,造成3種錯誤的報告優(yōu)先級/嚴(yán)重等級也不同。
致命同步錯誤碼ALSTATUSCODE_FATALSYNCERROR(0x2C)和同步錯誤碼ALSTATUSCODE_SYNCERROR(0x1A)是在啟用DC同步功能時才可能出現(xiàn)的錯誤碼。
假設(shè)在使用DC功能的情況下,某一時刻t拔掉主站和從站之間的網(wǎng)線,那么在t + 2 * Sync0 cycle后,同步錯誤ALSTATUSCODE_SYNCERROR(0x1A)能夠被報出,在t + 100ms后,同步管理器看門狗ALSTATUSCODE_SMWATCHDOG(0x1B) 錯誤發(fā)生,其優(yōu)先級最高,之后報出的錯誤碼就是ALSTATUSCODE_SMWATCHDOG(0x1B) 。
當(dāng)出現(xiàn)同步錯誤碼ALSTATUSCODE_SYNCERROR(0x1A)時,認(rèn)為與主站發(fā)出的PDO數(shù)據(jù)幀周期抖動相關(guān)??梢哉{(diào)大DC同步周期進行對比,或使用帶準(zhǔn)確時間戳的以太網(wǎng)數(shù)據(jù)抓包功能進行數(shù)據(jù)幀周期分析佐證,PC安裝TwinCAT軟件作為主站,其實時性一般較差,可以換成可靠的PLC設(shè)備進行小DC周期情況下的測試。
當(dāng)出現(xiàn)同步管理器看門狗錯誤ALSTATUSCODE_SMWATCHDOG(0x1B),其默認(rèn)閾值為100ms,一般會多倍于主站的數(shù)據(jù)幀周期,此時這種問題不會是主站的數(shù)據(jù)幀周期抖動造成,基本肯定是物理鏈路發(fā)生斷聯(lián)造成,可以肉眼觀察網(wǎng)線的Link指示燈(短時間可復(fù)現(xiàn)情況下)或使用wireshark抓包分析確認(rèn)物理鏈路斷聯(lián)問題。
-
代碼
+關(guān)注
關(guān)注
30文章
4971瀏覽量
74028 -
ethercat
+關(guān)注
關(guān)注
19文章
1520瀏覽量
45330 -
HPM
+關(guān)注
關(guān)注
2文章
53瀏覽量
8264
發(fā)布評論請先 登錄
BBB+dlpc2607 i2c 0x1b寄存器全是0x00,為什么?
SIM900A使用GPRS發(fā)送的數(shù)據(jù)中包含0x1A數(shù)據(jù)
NRF2401那里的0x01,和0x1a是什么意思?
“analogConfigTbl_NFC-6A1.c”中具有不同POLL_X_***_RX 的 0x0C (Rs-B) 要怎么設(shè)置?
s3c44b0x中文資料,s3c44b0x中文數(shù)據(jù)手冊
藍(lán)屏代碼0x000000d1的原因和解決方法
藍(lán)屏代碼0x0000007b的解決方法
基于A10PED-0U-A-066X3E2S-N-E2E2-1-066X3E2S-N-E2E2-0-0-ST2APS-ABField-Programmable Gate Array的參考設(shè)計
RM0091_STM32F0x1/STM32F0x2/STM32F0x8單片機參考手冊
HPM知識庫 | [EtherCAT] 從站運行過程中報錯(錯誤碼:0x1A\\0x1B\\0x2C)的代碼分析
評論