A Discrete-Event Network Simulator
API
ss-scheduler.cc
Go to the documentation of this file.
1 /*
2  * Copyright (c) 2007,2008 INRIA
3  *
4  * This program is free software; you can redistribute it and/or modify
5  * it under the terms of the GNU General Public License version 2 as
6  * published by the Free Software Foundation;
7  *
8  * This program is distributed in the hope that it will be useful,
9  * but WITHOUT ANY WARRANTY; without even the implied warranty of
10  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11  * GNU General Public License for more details.
12  *
13  * You should have received a copy of the GNU General Public License
14  * along with this program; if not, write to the Free Software
15  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
16  *
17  * Author: Jahanzeb Farooq <jahanzeb.farooq@sophia.inria.fr>
18  */
19 
20 #include "ss-scheduler.h"
21 
22 #include "connection-manager.h"
23 #include "service-flow-manager.h"
24 #include "service-flow-record.h"
25 #include "service-flow.h"
26 #include "ss-net-device.h"
27 #include "wimax-connection.h"
28 #include "wimax-mac-queue.h"
29 #include "wimax-phy.h"
30 
31 #include "ns3/log.h"
32 #include "ns3/node.h"
33 #include "ns3/simulator.h"
34 
35 namespace ns3
36 {
37 
38 NS_LOG_COMPONENT_DEFINE("SSScheduler");
39 
40 NS_OBJECT_ENSURE_REGISTERED(SSScheduler);
41 
42 TypeId
44 {
45  static TypeId tid = TypeId("ns3::SSScheduler").SetParent<Object>().SetGroupName("Wimax");
46  return tid;
47 }
48 
50  : m_ss(ss),
51  m_pollMe(false)
52 {
53 }
54 
56 {
57 }
58 
59 void
61 {
62  m_ss = nullptr;
63 }
64 
65 void
67 {
68  m_pollMe = pollMe;
69 }
70 
71 bool
73 {
74  return m_pollMe;
75 }
76 
78 SSScheduler::Schedule(uint16_t availableSymbols,
79  WimaxPhy::ModulationType modulationType,
80  MacHeaderType::HeaderType packetType,
81  Ptr<WimaxConnection>& connection)
82 {
83  Time timeStamp;
84  Ptr<PacketBurst> burst = Create<PacketBurst>();
85  uint16_t nrSymbolsRequired = 0;
86 
87  if (!connection)
88  {
89  connection = SelectConnection();
90  }
91  else
92  {
93  NS_ASSERT_MSG(connection->HasPackets(),
94  "SS: Error while scheduling packets: The selected connection has no packets");
95  }
96 
97  Ptr<Packet> packet;
98 
99  while (connection && connection->HasPackets(packetType))
100  {
101  NS_LOG_INFO("FRAG_DEBUG: SS Scheduler" << std::endl);
102 
103  uint32_t availableByte = m_ss->GetPhy()->GetNrBytes(availableSymbols, modulationType);
104 
105  uint32_t requiredByte = connection->GetQueue()->GetFirstPacketRequiredByte(packetType);
106 
107  NS_LOG_INFO("\t availableByte = " << availableByte << ", requiredByte = " << requiredByte);
108 
109  if (availableByte >= requiredByte)
110  {
111  // The SS could sent a packet without a other fragmentation
112  NS_LOG_INFO("\t availableByte >= requiredByte"
113  "\n\t Send packet without other fragmentation"
114  << std::endl);
115 
116  packet = connection->Dequeue(packetType);
117  burst->AddPacket(packet);
118 
119  nrSymbolsRequired = m_ss->GetPhy()->GetNrSymbols(packet->GetSize(), modulationType);
120  availableSymbols -= nrSymbolsRequired;
121  }
122  else
123  {
124  if (connection->GetType() == Cid::TRANSPORT)
125  {
126  NS_LOG_INFO("\t availableByte < requiredByte"
127  "\n\t Check if the fragmentation is possible");
128 
129  uint32_t headerSize = connection->GetQueue()->GetFirstPacketHdrSize(packetType);
130  if (!connection->GetQueue()->CheckForFragmentation(packetType))
131  {
132  NS_LOG_INFO("\t Add fragmentSubhdrSize = 2");
133  headerSize += 2;
134  }
135  NS_LOG_INFO("\t availableByte = " << availableByte
136  << " headerSize = " << headerSize);
137 
138  if (availableByte > headerSize)
139  {
140  NS_LOG_INFO("\t Fragmentation IS possible");
141  packet = connection->Dequeue(packetType, availableByte);
142  burst->AddPacket(packet);
143 
144  nrSymbolsRequired =
145  m_ss->GetPhy()->GetNrSymbols(packet->GetSize(), modulationType);
146  availableSymbols -= nrSymbolsRequired;
147  }
148  else
149  {
150  NS_LOG_INFO("\t Fragmentation IS NOT possible" << std::endl);
151  break;
152  }
153  }
154  else
155  {
156  NS_LOG_INFO("\t no Transport Connection "
157  "\n\t Fragmentation IS NOT possible, "
158  << std::endl);
159  break;
160  }
161  }
162  }
163  return burst;
164 }
165 
168 {
169  Time currentTime = Simulator::Now();
170  std::vector<ServiceFlow*>::const_iterator iter;
171  std::vector<ServiceFlow*> serviceFlows;
172 
173  NS_LOG_INFO("SS Scheduler: Selecting connection...");
174  if (m_ss->GetInitialRangingConnection()->HasPackets())
175  {
176  NS_LOG_INFO("Return GetInitialRangingConnection");
177  return m_ss->GetInitialRangingConnection();
178  }
179  if (m_ss->GetBasicConnection()->HasPackets())
180  {
181  NS_LOG_INFO("Return GetBasicConnection");
182  return m_ss->GetBasicConnection();
183  }
184  if (m_ss->GetPrimaryConnection()->HasPackets())
185  {
186  NS_LOG_INFO("Return GetPrimaryConnection");
187  return m_ss->GetPrimaryConnection();
188  }
189 
190  serviceFlows = m_ss->GetServiceFlowManager()->GetServiceFlows(ServiceFlow::SF_TYPE_UGS);
191  for (iter = serviceFlows.begin(); iter != serviceFlows.end(); ++iter)
192  {
193  // making sure that this grant was actually intended for this UGS
194 
195  if ((*iter)->HasPackets() && (currentTime + m_ss->GetPhy()->GetFrameDuration() >
196  MilliSeconds((*iter)->GetUnsolicitedGrantInterval())))
197  {
198  NS_LOG_INFO("Return UGS SF: CID = " << (*iter)->GetCid()
199  << "SFID = " << (*iter)->GetSfid());
200  return (*iter)->GetConnection();
201  }
202  }
203 
204  /* In the following cases (rtPS, nrtPS and BE flows) connection is seletected only for data
205  packets, for bandwidth request packets connection will itself be passed to Schedule () and
206  hence this function will never be called. */
207 
208  serviceFlows = m_ss->GetServiceFlowManager()->GetServiceFlows(ServiceFlow::SF_TYPE_RTPS);
209  for (iter = serviceFlows.begin(); iter != serviceFlows.end(); ++iter)
210  {
211  if ((*iter)->HasPackets(MacHeaderType::HEADER_TYPE_GENERIC) &&
212  (currentTime + m_ss->GetPhy()->GetFrameDuration() >
213  MilliSeconds((*iter)->GetUnsolicitedPollingInterval())))
214  {
215  NS_LOG_INFO("Return RTPS SF: CID = " << (*iter)->GetCid()
216  << "SFID = " << (*iter)->GetSfid());
217  return (*iter)->GetConnection();
218  }
219  }
220 
221  serviceFlows = m_ss->GetServiceFlowManager()->GetServiceFlows(ServiceFlow::SF_TYPE_NRTPS);
222  for (iter = serviceFlows.begin(); iter != serviceFlows.end(); ++iter)
223  {
224  if ((*iter)->HasPackets(MacHeaderType::HEADER_TYPE_GENERIC))
225  {
226  NS_LOG_INFO("Return NRTPS SF: CID = " << (*iter)->GetCid()
227  << "SFID = " << (*iter)->GetSfid());
228  return (*iter)->GetConnection();
229  }
230  }
231 
232  serviceFlows = m_ss->GetServiceFlowManager()->GetServiceFlows(ServiceFlow::SF_TYPE_BE);
233  for (iter = serviceFlows.begin(); iter != serviceFlows.end(); ++iter)
234  {
235  if ((*iter)->HasPackets(MacHeaderType::HEADER_TYPE_GENERIC))
236  {
237  NS_LOG_INFO("Return BE SF: CID = " << (*iter)->GetCid()
238  << "SFID = " << (*iter)->GetSfid());
239  return (*iter)->GetConnection();
240  }
241  }
242 
243  if (m_ss->GetBroadcastConnection()->HasPackets())
244  {
245  return m_ss->GetBroadcastConnection();
246  }
247  NS_LOG_INFO("NO connection is selected!");
248  return nullptr;
249 }
250 
251 } // namespace ns3
@ TRANSPORT
Definition: cid.h:46
HeaderType
Header type enumeration.
A base class which provides memory management and object aggregation.
Definition: object.h:89
uint32_t GetSize() const
Returns the the size in bytes of the packet (including the zero-filled initial payload).
Definition: packet.h:863
Smart pointer class similar to boost::intrusive_ptr.
Definition: ptr.h:78
SSScheduler(Ptr< SubscriberStationNetDevice > ss)
Constructor.
Definition: ss-scheduler.cc:49
bool m_pollMe
poll me flag
Definition: ss-scheduler.h:94
void DoDispose() override
Destructor implementation.
Definition: ss-scheduler.cc:60
Ptr< PacketBurst > Schedule(uint16_t availableSymbols, WimaxPhy::ModulationType modulationType, MacHeaderType::HeaderType packetType, Ptr< WimaxConnection > &connection)
Definition: ss-scheduler.cc:78
static TypeId GetTypeId()
Get the type ID.
Definition: ss-scheduler.cc:43
Ptr< SubscriberStationNetDevice > m_ss
the subscriber station
Definition: ss-scheduler.h:93
void SetPollMe(bool pollMe)
Set poll me value.
Definition: ss-scheduler.cc:66
Ptr< WimaxConnection > SelectConnection()
Select connection.
bool GetPollMe() const
Get the poll me value.
Definition: ss-scheduler.cc:72
~SSScheduler() override
Definition: ss-scheduler.cc:55
static Time Now()
Return the current simulation virtual time.
Definition: simulator.cc:199
Simulation virtual time values and global simulation resolution.
Definition: nstime.h:105
a unique identifier for an interface.
Definition: type-id.h:60
TypeId SetParent(TypeId tid)
Set the parent TypeId.
Definition: type-id.cc:935
ModulationType
ModulationType enumeration.
Definition: wimax-phy.h:54
#define NS_ASSERT_MSG(condition, message)
At runtime, in debugging builds, if this condition is not true, the program prints the message to out...
Definition: assert.h:86
#define NS_LOG_COMPONENT_DEFINE(name)
Define a Log component with a specific name.
Definition: log.h:202
#define NS_LOG_INFO(msg)
Use NS_LOG to output a message of level LOG_INFO.
Definition: log.h:275
#define NS_OBJECT_ENSURE_REGISTERED(type)
Register an Object subclass with the TypeId system.
Definition: object-base.h:46
Time MilliSeconds(uint64_t value)
Construct a Time in the indicated unit.
Definition: nstime.h:1348
Every class exported by the ns3 library is enclosed in the ns3 namespace.