Uplink scheduler with multiple bearers (LCs) allocates in a Round Robin fashion the active ones
authormmiozzo
Mon, 28 Nov 2011 12:32:08 +0100
changeset 8415 e9a27a8c6331
parent 8414 cd0669085267
child 8416 52f94032838a
Uplink scheduler with multiple bearers (LCs) allocates in a Round Robin fashion the active ones
src/lte/model/lte-enb-phy.cc
src/lte/model/lte-ue-mac.cc
src/lte/model/lte-ue-mac.h
src/lte/model/lte-ue-phy.cc
--- a/src/lte/model/lte-enb-phy.cc	Mon Nov 28 12:30:41 2011 +0100
+++ b/src/lte/model/lte-enb-phy.cc	Mon Nov 28 12:32:08 2011 +0100
@@ -397,8 +397,6 @@
     }
 
   // trigger the MAC
-  Ptr<LteEnbMac> macEntity = GetDevice ()->GetObject<LteEnbNetDevice> ()->GetMac ();
-
   m_enbPhySapUser->SubframeIndication (m_nrFrames, m_nrSubFrames);
 
 
--- a/src/lte/model/lte-ue-mac.cc	Mon Nov 28 12:30:41 2011 +0100
+++ b/src/lte/model/lte-ue-mac.cc	Mon Nov 28 12:32:08 2011 +0100
@@ -31,6 +31,7 @@
 #include "lte-mac-tag.h"
 #include <ns3/ff-mac-common.h>
 #include <ns3/ideal-control-messages.h>
+#include <ns3/simulator.h>
 
 
 NS_LOG_COMPONENT_DEFINE ("LteUeMac");
@@ -161,7 +162,7 @@
 void
 UeMemberLteUePhySapUser::SubframeIndication (uint32_t frameNo, uint32_t subframeNo)
 {
-  NS_LOG_LOGIC (this << " UE-MAC does not yet support this primitive");
+  m_mac->DoSubframeIndication (frameNo, subframeNo);
 }
 
 void
@@ -189,6 +190,9 @@
 
 
 LteUeMac::LteUeMac ()
+  :  m_bsrPeriodicity (MilliSeconds (1)), // ideal behavior
+  m_bsrLast (MilliSeconds (0))
+  
 {
   NS_LOG_FUNCTION (this);
   m_macSapProvider = new UeMemberLteMacSapProvider (this);
@@ -263,24 +267,51 @@
 LteUeMac::DoReportBufferStatus (LteMacSapProvider::ReportBufferStatusParameters params)
 {
   NS_LOG_FUNCTION (this);
+  
+  std::map <uint8_t, long uint>::iterator it;
+  
+  
+  it = m_ulBsrReceived.find (params.lcid);
+  if (it!=m_ulBsrReceived.end ())
+    {
+      // update entry
+      (*it).second = params.txQueueSize + params.retxQueueSize + params.statusPduSize;
+    }
+  else
+    {
+      m_ulBsrReceived.insert (std::pair<uint8_t, long uint> (params.lcid, params.txQueueSize + params.retxQueueSize + params.statusPduSize));
+    }
+}
+
+
+void
+LteUeMac::SendReportBufferStatus (void)
+{
+  NS_LOG_FUNCTION (this);
   MacCeListElement_s bsr;
   bsr.m_rnti = m_rnti;
   bsr.m_macCeType = MacCeListElement_s::BSR;
-  // short BSR
-  int queue = params.txQueueSize;
-  int index = 0;
-  if (BufferSizeLevelBsr[63] < queue)
+  // BSR
+  std::map <uint8_t, long uint>::iterator it;
+  NS_ASSERT_MSG (m_ulBsrReceived.size () <=4, " Too many LCs (max is 4)");
+  
+  for (it = m_ulBsrReceived.begin (); it != m_ulBsrReceived.end (); it++)
     {
-      index = 63;
+      int queue = (*it).second;
+      int index = 0;
+      if (BufferSizeLevelBsr[63] < queue)
+        {
+          index = 63;
+        }
+      else
+        {
+          while (BufferSizeLevelBsr[index] < queue)
+            {
+              index++;
+            }
+        }
+      bsr.m_macCeValue.m_bufferStatus.push_back (index);
     }
-  else
-    {
-      while (BufferSizeLevelBsr[index] < queue)
-        {
-          index++;
-        }
-    }
-  bsr.m_macCeValue.m_bufferStatus.push_back (index);
 
   // create the feedback to eNB
   Ptr<BsrIdealControlMessage> msg = Create<BsrIdealControlMessage> ();
@@ -336,9 +367,33 @@
     {
       Ptr<UlDciIdealControlMessage> msg2 = DynamicCast<UlDciIdealControlMessage> (msg);
       UlDciListElement_s dci = msg2->GetDci ();
-      std::map <uint8_t, LteMacSapUser*>::iterator it; 
-      it = m_macSapUserMap.begin ();  // use only the first LC --> UE-SCHEDULER??
-      (*it).second->NotifyTxOpportunity (dci.m_tbSize);
+      std::map <uint8_t, long uint>::iterator itBsr;
+      NS_ASSERT_MSG (m_ulBsrReceived.size () <=4, " Too many LCs (max is 4)");
+      int activeLcs = 0;
+      for (itBsr = m_ulBsrReceived.begin (); itBsr != m_ulBsrReceived.end (); itBsr++)
+        {
+          if ((*itBsr).second > 0)
+            {
+              activeLcs++;
+            }
+        }
+      if (activeLcs <= 0)
+        {
+          NS_LOG_ERROR (this << " No active flows for this UL-DCI");
+          return;
+        }
+      std::map <uint8_t, LteMacSapUser*>::iterator it;
+      NS_LOG_FUNCTION (this << " UE: UL-CQI notified TxOpportunity of " << dci.m_tbSize);
+      for (it = m_macSapUserMap.begin (); it!=m_macSapUserMap.end (); it++)
+        {
+          itBsr = m_ulBsrReceived.find ((*it).first);
+          if (itBsr!=m_ulBsrReceived.end ())
+            {
+              NS_LOG_FUNCTION (this << "\t" << dci.m_tbSize / m_macSapUserMap.size () << " bytes to LC " << (uint16_t)(*it).first << " queue " << (*itBsr).second);
+              (*it).second->NotifyTxOpportunity (dci.m_tbSize / activeLcs);
+              (*itBsr).second -= dci.m_tbSize / activeLcs;
+            }
+        }
 
     }
   else
@@ -348,4 +403,16 @@
 }
 
 
+void
+LteUeMac::DoSubframeIndication (uint32_t frameNo, uint32_t subframeNo)
+{
+  NS_LOG_FUNCTION (this);
+  if (Simulator::Now () > m_bsrLast + m_bsrPeriodicity)
+    {
+      SendReportBufferStatus ();
+      m_bsrLast = Simulator::Now ();
+    }
+}
+
+
 } // namespace ns3
--- a/src/lte/model/lte-ue-mac.h	Mon Nov 28 12:30:41 2011 +0100
+++ b/src/lte/model/lte-ue-mac.h	Mon Nov 28 12:32:08 2011 +0100
@@ -29,6 +29,7 @@
 #include <ns3/lte-mac-sap.h>
 #include <ns3/lte-ue-cmac-sap.h>
 #include <ns3/lte-ue-phy-sap.h>
+#include <ns3/nstime.h>
 
 
 namespace ns3 {
@@ -62,6 +63,14 @@
   * \param s a pointer to the PHY SAP Provider
   */
   void SetLteUePhySapProvider (LteUePhySapProvider* s);
+  
+  /**
+  * \brief Forwarded from LteUePhySapUser: trigger the start from a new frame
+  *
+  * \param frameNo frame number
+  * \param subframeNo subframe number
+  */
+  void DoSubframeIndication (uint32_t frameNo, uint32_t subframeNo);
 
 private:
   // forwarded from MAC SAP
@@ -76,6 +85,8 @@
   // forwarded from PHY SAP
   void DoReceivePhyPdu (Ptr<Packet> p);
   void DoReceiveIdealControlMessage (Ptr<IdealControlMessage> msg);
+  
+  void SendReportBufferStatus (void);
 
 private:
   // end of temporary hack
@@ -87,6 +98,11 @@
 
   LteUePhySapProvider* m_uePhySapProvider;
   LteUePhySapUser* m_uePhySapUser;
+  
+  std::map <uint8_t, long uint> m_ulBsrReceived; // BSR received from RLC (BSR up to now)
+  
+  Time m_bsrPeriodicity;
+  Time m_bsrLast;
 
 
   uint16_t m_rnti;
--- a/src/lte/model/lte-ue-phy.cc	Mon Nov 28 12:30:41 2011 +0100
+++ b/src/lte/model/lte-ue-phy.cc	Mon Nov 28 12:32:08 2011 +0100
@@ -491,6 +491,9 @@
     {
       m_uplinkSpectrumPhy->StartTx (pb);
     }
+    
+  // trigger the MAC
+  m_uePhySapUser->SubframeIndication (frameNo, subframeNo);
 
 }