diff --git a/src/dmr/Slot.cpp b/src/dmr/Slot.cpp index a6601920..69f36c6e 100644 --- a/src/dmr/Slot.cpp +++ b/src/dmr/Slot.cpp @@ -133,6 +133,7 @@ Slot::Slot(uint32_t slotNo, uint32_t timeout, uint32_t tgHang, uint32_t queueSiz m_networkWatchdog(1000U, 0U, 1500U), m_rfTimeoutTimer(1000U, timeout), m_rfTGHang(1000U, tgHang), + m_rfLossWatchdog(1000U, 0U, 1500U), m_netTimeoutTimer(1000U, timeout), m_netTGHang(1000U, 2U), m_packetTimer(1000U, 0U, 50U), @@ -212,6 +213,7 @@ bool Slot::processFrame(uint8_t *data, uint32_t len) // increment the frame loss count by one for audio or data; otherwise drop // packets if (m_rfState == RS_RF_AUDIO || m_rfState == RS_RF_DATA) { + m_rfLossWatchdog.start(); ++m_frameLossCnt; } else { @@ -228,6 +230,12 @@ bool Slot::processFrame(uint8_t *data, uint32_t len) } } + if (m_rfState == RS_RF_AUDIO || m_rfState == RS_RF_DATA) { + if (m_rfLossWatchdog.isRunning()) { + m_rfLossWatchdog.start(); + } + } + // Have we got RSSI bytes on the end? if (len == (DMR_FRAME_LENGTH_BYTES + 4U)) { uint16_t raw = 0U; @@ -495,7 +503,10 @@ void Slot::clock() } } + // handle timeouts and hang timers m_rfTimeoutTimer.clock(ms); + m_netTimeoutTimer.clock(ms); + if (m_rfTimeoutTimer.isRunning() && m_rfTimeoutTimer.hasExpired()) { if (!m_rfTimeout) { LogMessage(LOG_RF, "DMR Slot %u, user has timed out", m_slotNo); @@ -503,11 +514,15 @@ void Slot::clock() } } - m_netTimeoutTimer.clock(ms); - if (m_netTimeoutTimer.isRunning() && m_netTimeoutTimer.hasExpired()) { - if (!m_netTimeout) { - LogMessage(LOG_NET, "DMR Slot %u, user has timed out", m_slotNo); - m_netTimeout = true; + if (m_rfState == RS_RF_AUDIO || m_rfState == RS_RF_DATA) { + if (m_rfLossWatchdog.isRunning()) { + m_rfLossWatchdog.clock(ms); + + if (m_rfLossWatchdog.hasExpired()) { + m_rfLossWatchdog.stop(); + + processFrameLoss(); + } } } @@ -529,6 +544,13 @@ void Slot::clock() } } + if (m_netTimeoutTimer.isRunning() && m_netTimeoutTimer.hasExpired()) { + if (!m_netTimeout) { + LogMessage(LOG_NET, "DMR Slot %u, user has timed out", m_slotNo); + m_netTimeout = true; + } + } + if (m_authoritative) { if (m_netTGHang.isRunning()) { m_netTGHang.clock(ms); @@ -1008,6 +1030,8 @@ void Slot::processFrameLoss() } } + clearTSCCActivated(); + if (!m_tscc->m_enableTSCC) { notifyCC_ReleaseGrant(m_rfLC->getDstId()); } diff --git a/src/dmr/Slot.h b/src/dmr/Slot.h index aaffb3f5..05f2603a 100644 --- a/src/dmr/Slot.h +++ b/src/dmr/Slot.h @@ -175,6 +175,7 @@ namespace dmr Timer m_networkWatchdog; Timer m_rfTimeoutTimer; Timer m_rfTGHang; + Timer m_rfLossWatchdog; Timer m_netTimeoutTimer; Timer m_netTGHang; Timer m_packetTimer; diff --git a/src/nxdn/Control.cpp b/src/nxdn/Control.cpp index 596eed98..d88c2329 100644 --- a/src/nxdn/Control.cpp +++ b/src/nxdn/Control.cpp @@ -130,6 +130,7 @@ Control::Control(bool authoritative, uint32_t ran, uint32_t callHang, uint32_t q m_ccHalted(false), m_rfTimeout(1000U, timeout), m_rfTGHang(1000U, tgHang), + m_rfLossWatchdog(1000U, 0U, 1500U), m_netTimeout(1000U, timeout), m_netTGHang(1000U, 2U), m_networkWatchdog(1000U, 0U, 1500U), @@ -394,6 +395,7 @@ bool Control::processFrame(uint8_t* data, uint32_t len) // increment the frame loss count by one for audio or data; otherwise drop // packets if (m_rfState == RS_RF_AUDIO || m_rfState == RS_RF_DATA) { + m_rfLossWatchdog.start(); ++m_frameLossCnt; } else { @@ -408,6 +410,12 @@ bool Control::processFrame(uint8_t* data, uint32_t len) } } + if (m_rfState == RS_RF_AUDIO || m_rfState == RS_RF_DATA) { + if (m_rfLossWatchdog.isRunning()) { + m_rfLossWatchdog.start(); + } + } + // have we got RSSI bytes on the end? if (len == (NXDN_FRAME_LENGTH_BYTES + 4U)) { uint16_t raw = 0U; @@ -621,6 +629,18 @@ void Control::clock(uint32_t ms) } } } + + if (m_rfState == RS_RF_AUDIO || m_rfState == RS_RF_DATA) { + if (m_rfLossWatchdog.isRunning()) { + m_rfLossWatchdog.clock(ms); + + if (m_rfLossWatchdog.hasExpired()) { + m_rfLossWatchdog.stop(); + + processFrameLoss(); + } + } + } if (m_authoritative) { if (m_netTGHang.isRunning()) { diff --git a/src/nxdn/Control.h b/src/nxdn/Control.h index 8b4e13d9..c2bbb027 100644 --- a/src/nxdn/Control.h +++ b/src/nxdn/Control.h @@ -191,6 +191,7 @@ namespace nxdn Timer m_rfTimeout; Timer m_rfTGHang; + Timer m_rfLossWatchdog; Timer m_netTimeout; Timer m_netTGHang; Timer m_networkWatchdog;