diff --git a/src/lte/model/pf-ff-mac-scheduler.cc b/src/lte/model/pf-ff-mac-scheduler.cc index 9f143536e..7c3a2515b 100644 --- a/src/lte/model/pf-ff-mac-scheduler.cc +++ b/src/lte/model/pf-ff-mac-scheduler.cc @@ -235,6 +235,7 @@ PfFfMacScheduler::DoDispose () { NS_LOG_FUNCTION (this); m_dlHarqProcessesDciBuffer.clear (); + m_dlHarqProcessesTimer.clear (); m_dlHarqProcessesRlcPduListBuffer.clear (); m_dlInfoListBuffered.clear (); m_ulHarqCurrentProcessId.clear (); @@ -315,6 +316,9 @@ PfFfMacScheduler::DoCschedUeConfigReq (const struct FfMacCschedSapProvider::Csch DlHarqProcessesStatus_t dlHarqPrcStatus; dlHarqPrcStatus.resize (8,0); m_dlHarqProcessesStatus.insert (std::pair (params.m_rnti, dlHarqPrcStatus)); + DlHarqProcessesTimer_t dlHarqProcessesTimer; + dlHarqProcessesTimer.resize (8,0); + m_dlHarqProcessesTimer.insert (std::pair (params.m_rnti, dlHarqProcessesTimer)); DlHarqProcessesDciBuffer_t dlHarqdci; dlHarqdci.resize (8); m_dlHarqProcessesDciBuffer.insert (std::pair (params.m_rnti, dlHarqdci)); @@ -541,6 +545,38 @@ PfFfMacScheduler::UpdateHarqProcessId (uint16_t rnti) } +void +PfFfMacScheduler::RefreshHarqProcesses () +{ + NS_LOG_FUNCTION (this); + + std::map ::iterator itTimers; + for (itTimers = m_dlHarqProcessesTimer.begin (); itTimers != m_dlHarqProcessesTimer.end (); itTimers ++) + { + for (uint16_t i = 0; i < HARQ_PROC_NUM; i++) + { + if ((*itTimers).second.at (i) == HARQ_DL_TIMEOUT) + { + // reset HARQ process + + NS_LOG_DEBUG (this << " Reset HARQ proc " << i << " for RNTI " << (*itTimers).first); + std::map ::iterator itStat = m_dlHarqProcessesStatus.find ((*itTimers).first); + if (itStat == m_dlHarqProcessesStatus.end ()) + { + NS_FATAL_ERROR ("No Process Id Status found for this RNTI " << (*itTimers).first); + } + (*itStat).second.at (i) = 0; + } + else + { + (*itTimers).second.at (i)++; + } + } + } + +} + + void PfFfMacScheduler::DoSchedDlTriggerReq (const struct FfMacSchedSapProvider::SchedDlTriggerReqParameters& params) { @@ -565,6 +601,7 @@ PfFfMacScheduler::DoSchedDlTriggerReq (const struct FfMacSchedSapProvider::Sched // Process DL HARQ feedback + RefreshHarqProcesses (); // retrieve past HARQ retx buffered if (m_dlInfoListBuffered.size () > 0) { @@ -785,6 +822,13 @@ PfFfMacScheduler::DoSchedDlTriggerReq (const struct FfMacSchedSapProvider::Sched newEl.m_rnti = rnti; newEl.m_dci = dci; (*itHarq).second.at (harqId).m_rv = dci.m_rv; + // refresh timer + std::map ::iterator itHarqTimer = m_dlHarqProcessesTimer.find (rnti); + if (itHarqTimer== m_dlHarqProcessesTimer.end ()) + { + NS_FATAL_ERROR ("Unable to find HARQ timer for RNTI " << (uint16_t)rnti); + } + (*itHarqTimer).second.at (harqId) = 0; ret.m_buildDataList.push_back (newEl); rntiAllocated.insert (rnti); } @@ -828,6 +872,14 @@ PfFfMacScheduler::DoSchedDlTriggerReq (const struct FfMacSchedSapProvider::Sched if ((itRnti != rntiAllocated.end ())||(!HarqProcessAvailability ((*it).first))) { // UE already allocated for HARQ or without HARQ process available -> drop it + if (itRnti != rntiAllocated.end ()) + { + NS_LOG_DEBUG (this << " RNTI discared for HARQ tx" << (uint16_t)(*it).first); + } + if (!HarqProcessAvailability ((*it).first)) + { + NS_LOG_DEBUG (this << " RNTI discared for HARQ id" << (uint16_t)(*it).first); + } continue; } std::map ::iterator itCqi; @@ -1066,6 +1118,13 @@ PfFfMacScheduler::DoSchedDlTriggerReq (const struct FfMacSchedSapProvider::Sched NS_FATAL_ERROR ("Unable to find RNTI entry in DCI HARQ buffer for RNTI " << newEl.m_rnti); } (*itDci).second.at (newDci.m_harqProcess) = newDci; + // refresh timer + std::map ::iterator itHarqTimer = m_dlHarqProcessesTimer.find (newEl.m_rnti); + if (itHarqTimer== m_dlHarqProcessesTimer.end ()) + { + NS_FATAL_ERROR ("Unable to find HARQ timer for RNTI " << (uint16_t)newEl.m_rnti); + } + (*itHarqTimer).second.at (newDci.m_harqProcess) = 0; } // ...more parameters -> ingored in this version diff --git a/src/lte/model/pf-ff-mac-scheduler.h b/src/lte/model/pf-ff-mac-scheduler.h index c85e67ae3..53796bcfa 100644 --- a/src/lte/model/pf-ff-mac-scheduler.h +++ b/src/lte/model/pf-ff-mac-scheduler.h @@ -37,11 +37,13 @@ #define HARQ_PROC_NUM 8 +#define HARQ_DL_TIMEOUT 8 namespace ns3 { typedef std::vector < uint8_t > DlHarqProcessesStatus_t; +typedef std::vector < uint8_t > DlHarqProcessesTimer_t; typedef std::vector < DlDciListElement_s > DlHarqProcessesDciBuffer_t; typedef std::vector < std::vector > RlcPduList_t; // vector of the LCs and layers per UE typedef std::vector < RlcPduList_t > DlHarqRlcPduListBuffer_t; // vector of the 8 HARQ processes per UE @@ -172,6 +174,12 @@ private: */ uint8_t HarqProcessAvailability (uint16_t rnti); + /** + * \brief Refresh HARQ processes according to the timers + * + */ + void RefreshHarqProcesses (); + Ptr m_amc; /* @@ -258,6 +266,7 @@ private: // 0: process Id available // x>0: process Id equal to `x` trasmission count std::map m_dlHarqProcessesStatus; + std::map m_dlHarqProcessesTimer; std::map m_dlHarqProcessesDciBuffer; std::map m_dlHarqProcessesRlcPduListBuffer; std::vector m_dlInfoListBuffered; // HARQ retx buffered diff --git a/src/lte/model/rr-ff-mac-scheduler.cc b/src/lte/model/rr-ff-mac-scheduler.cc index e2d6aac50..6aa71ebb4 100644 --- a/src/lte/model/rr-ff-mac-scheduler.cc +++ b/src/lte/model/rr-ff-mac-scheduler.cc @@ -237,6 +237,7 @@ RrFfMacScheduler::DoDispose () { NS_LOG_FUNCTION (this); m_dlHarqProcessesDciBuffer.clear (); + m_dlHarqProcessesTimer.clear (); m_dlHarqProcessesRlcPduListBuffer.clear (); m_dlInfoListBuffered.clear (); m_ulHarqCurrentProcessId.clear (); @@ -317,6 +318,9 @@ RrFfMacScheduler::DoCschedUeConfigReq (const struct FfMacCschedSapProvider::Csch DlHarqProcessesStatus_t dlHarqPrcStatus; dlHarqPrcStatus.resize (8,0); m_dlHarqProcessesStatus.insert (std::pair (params.m_rnti, dlHarqPrcStatus)); + DlHarqProcessesTimer_t dlHarqProcessesTimer; + dlHarqProcessesTimer.resize (8,0); + m_dlHarqProcessesTimer.insert (std::pair (params.m_rnti, dlHarqProcessesTimer)); DlHarqProcessesDciBuffer_t dlHarqdci; dlHarqdci.resize (8); m_dlHarqProcessesDciBuffer.insert (std::pair (params.m_rnti, dlHarqdci)); @@ -509,6 +513,39 @@ RrFfMacScheduler::UpdateHarqProcessId (uint16_t rnti) } +void +RrFfMacScheduler::RefreshHarqProcesses () +{ + NS_LOG_FUNCTION (this); + + std::map ::iterator itTimers; + for (itTimers = m_dlHarqProcessesTimer.begin (); itTimers != m_dlHarqProcessesTimer.end (); itTimers ++) + { + for (uint16_t i = 0; i < HARQ_PROC_NUM; i++) + { + if ((*itTimers).second.at (i) == HARQ_DL_TIMEOUT) + { + // reset HARQ process + + NS_LOG_DEBUG (this << " Reset HARQ proc " << i << " for RNTI " << (*itTimers).first); + std::map ::iterator itStat = m_dlHarqProcessesStatus.find ((*itTimers).first); + if (itStat == m_dlHarqProcessesStatus.end ()) + { + NS_FATAL_ERROR ("No Process Id Status found for this RNTI " << (*itTimers).first); + } + (*itStat).second.at (i) = 0; + } + else + { + (*itTimers).second.at (i)++; + } + } + } + +} + + + void RrFfMacScheduler::DoSchedDlTriggerReq (const struct FfMacSchedSapProvider::SchedDlTriggerReqParameters& params) { @@ -527,6 +564,7 @@ RrFfMacScheduler::DoSchedDlTriggerReq (const struct FfMacSchedSapProvider::Sched rbgMap.resize (m_cschedCellConfig.m_dlBandwidth / rbgSize, false); // Process DL HARQ feedback + RefreshHarqProcesses (); // retrieve past HARQ retx buffered if (m_dlInfoListBuffered.size () > 0) { @@ -749,6 +787,13 @@ RrFfMacScheduler::DoSchedDlTriggerReq (const struct FfMacSchedSapProvider::Sched newEl.m_rnti = rnti; newEl.m_dci = dci; (*itHarq).second.at (harqId).m_rv = dci.m_rv; + // refresh timer + std::map ::iterator itHarqTimer = m_dlHarqProcessesTimer.find (rnti); + if (itHarqTimer== m_dlHarqProcessesTimer.end ()) + { + NS_FATAL_ERROR ("Unable to find HARQ timer for RNTI " << (uint16_t)rnti); + } + (*itHarqTimer).second.at (harqId) = 0; ret.m_buildDataList.push_back (newEl); rntiAllocated.insert (rnti); } @@ -981,6 +1026,13 @@ RrFfMacScheduler::DoSchedDlTriggerReq (const struct FfMacSchedSapProvider::Sched NS_FATAL_ERROR ("Unable to find RNTI entry in DCI HARQ buffer for RNTI " << (*it).m_rnti); } (*itDci).second.at (newDci.m_harqProcess) = newDci; + // refresh timer + std::map ::iterator itHarqTimer = m_dlHarqProcessesTimer.find (newEl.m_rnti); + if (itHarqTimer== m_dlHarqProcessesTimer.end ()) + { + NS_FATAL_ERROR ("Unable to find HARQ timer for RNTI " << (uint16_t)newEl.m_rnti); + } + (*itHarqTimer).second.at (newDci.m_harqProcess) = 0; } // ...more parameters -> ignored in this version diff --git a/src/lte/model/rr-ff-mac-scheduler.h b/src/lte/model/rr-ff-mac-scheduler.h index 11f636eb0..62e7479ed 100644 --- a/src/lte/model/rr-ff-mac-scheduler.h +++ b/src/lte/model/rr-ff-mac-scheduler.h @@ -31,11 +31,13 @@ #include #define HARQ_PROC_NUM 8 +#define HARQ_DL_TIMEOUT 8 namespace ns3 { typedef std::vector < uint8_t > DlHarqProcessesStatus_t; +typedef std::vector < uint8_t > DlHarqProcessesTimer_t; typedef std::vector < DlDciListElement_s > DlHarqProcessesDciBuffer_t; typedef std::vector < std::vector > RlcPduList_t; // vector of the LCs and layers per UE typedef std::vector < RlcPduList_t > DlHarqRlcPduListBuffer_t; // vector of the 8 HARQ processes per UE @@ -142,21 +144,27 @@ private: void UpdateUlRlcBufferInfo (uint16_t rnti, uint16_t size); /** - * \brief Update and return a new process Id for the RNTI specified - * - * \param rnti the RNTI of the UE to be updated - * \return the process id value - */ + * \brief Update and return a new process Id for the RNTI specified + * + * \param rnti the RNTI of the UE to be updated + * \return the process id value + */ uint8_t UpdateHarqProcessId (uint16_t rnti); /** -* \brief Return the availability of free process for the RNTI specified -* -* \param rnti the RNTI of the UE to be updated -* \return the process id value -*/ + * \brief Return the availability of free process for the RNTI specified + * + * \param rnti the RNTI of the UE to be updated + * \return the process id value + */ uint8_t HarqProcessAvailability (uint16_t rnti); + /** + * \brief Refresh HARQ processes according to the timers + * + */ + void RefreshHarqProcesses (); + Ptr m_amc; /* @@ -223,6 +231,7 @@ private: // 0: process Id available // x>0: process Id equal to `x` trasmission count std::map m_dlHarqProcessesStatus; + std::map m_dlHarqProcessesTimer; std::map m_dlHarqProcessesDciBuffer; std::map m_dlHarqProcessesRlcPduListBuffer; std::vector m_dlInfoListBuffered; // HARQ retx buffered