satellite-frame-allocator-test.cc
Go to the documentation of this file.
1 /* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
2 /*
3  * Copyright (c) 2014 Magister Solutions Ltd
4  * Copyright (c) 2018 CNES
5  *
6  * This program is free software; you can redistribute it and/or modify
7  * it under the terms of the GNU General Public License version 2 as
8  * published by the Free Software Foundation;
9  *
10  * This program is distributed in the hope that it will be useful,
11  * but WITHOUT ANY WARRANTY; without even the implied warranty of
12  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13  * GNU General Public License for more details.
14  *
15  * You should have received a copy of the GNU General Public License
16  * along with this program; if not, write to the Free Software
17  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
18  *
19  * Author: Sami Rantanen <sami.rantanen@magister.fi>
20  * Author: Mathias Ettinger <mettinger@toulouse.viveris.fr>
21  */
22 
29 #include "../model/satellite-superframe-allocator.h"
30 #include "../model/satellite-utils.h"
31 #include "../utils/satellite-env-variables.h"
32 
33 #include "ns3/boolean.h"
34 #include "ns3/config.h"
35 #include "ns3/log.h"
36 #include "ns3/simulator.h"
37 #include "ns3/singleton.h"
38 #include "ns3/test.h"
39 #include "ns3/uinteger.h"
40 
41 #include <algorithm>
42 
43 using namespace ns3;
44 
70 class SatFrameAllocatorTestCase : public TestCase
71 {
72  public:
74  virtual ~SatFrameAllocatorTestCase();
75 
76  private:
77  typedef std::map<Address, std::pair<SatFrameAllocator::SatFrameAllocReq, uint32_t>> ReqInfo_t;
78 
79  static const uint32_t m_ccLevelCount = 4;
80  static const uint32_t m_cnoValueCount = 10;
81 
82  SatFrameAllocator::CcLevel_t m_ccLevels[m_ccLevelCount];
83  double m_cnoValues[m_cnoValueCount];
84  uint32_t m_cnoIndex;
85  Ptr<SatWaveformConf> m_waveFormConf;
86  Ptr<SatFrameConf> m_frameConf;
87  Ptr<SatFrameAllocator> m_frameAllocator;
88 
89  virtual void DoRun(void);
90 
91  void InitFrame(SatSuperframeConf::ConfigType_t configType);
92  void RunSingleUtTest(SatSuperframeConf::ConfigType_t configType,
93  bool acmEnabled,
94  bool fcaEnabled);
95  void RunMultiUtTest();
96 
97  SatFrameAllocator::SatFrameAllocReq ContructRequestForUt(uint32_t& totalBytes,
98  uint32_t craBytes,
99  uint32_t minRbdcBytes,
100  uint32_t rbdcBytes,
101  uint32_t vbdcBytes,
102  uint32_t rcCount,
103  bool controlSlot);
104 
105  void CheckSingleUtTestResults(uint32_t bytesReq,
107  bool allocated,
111  bool rcBasedAllocation,
112  bool fcaEnabled,
113  bool acmEnabled);
114 
115  void CheckMultiUtTestResults(SatFrameAllocator::UtAllocInfoContainer_t& utAllocContainer,
116  ReqInfo_t& reqInfo);
117 };
118 
120  : TestCase("Test satellite frame allocator, configuration 0.")
121 {
122  m_ccLevels[0] = SatFrameAllocator::CC_LEVEL_CRA;
123  m_ccLevels[1] = SatFrameAllocator::CC_LEVEL_CRA_MIN_RBDC;
124  m_ccLevels[2] = SatFrameAllocator::CC_LEVEL_CRA_RBDC;
125  m_ccLevels[3] = SatFrameAllocator::CC_LEVEL_CRA_RBDC_VBDC;
126 
127  m_cnoIndex = 0;
128 
129  m_cnoValues[0] = SatUtils::DbToLinear(125.0);
130  m_cnoValues[1] = SatUtils::DbToLinear(35.0);
131  m_cnoValues[2] = SatUtils::DbToLinear(120.0);
132  m_cnoValues[3] = std::numeric_limits<double>::quiet_NaN();
133  m_cnoValues[4] = SatUtils::DbToLinear(77.0);
134  m_cnoValues[5] = SatUtils::DbToLinear(10.0);
135  m_cnoValues[6] = SatUtils::DbToLinear(66.0);
136  m_cnoValues[7] = SatUtils::DbToLinear(135.0);
137  m_cnoValues[8] = std::numeric_limits<double>::quiet_NaN();
138  m_cnoValues[9] = SatUtils::DbToLinear(60.0);
139 
140  std::string dataPath = Singleton<SatEnvVariables>::Get()->GetDataPath();
141  std::string fileNameWithPath = dataPath + "/dvbRcs2Waveforms.txt";
142  m_waveFormConf = CreateObject<SatWaveformConf>(fileNameWithPath);
143 }
144 
146 {
147 }
148 
149 void
151 {
152  // create first frame with two carriers and each carrier having three slots
153  Ptr<SatBtuConf> btu = Create<SatBtuConf>(10e4, 0.4, 0.1, 1);
154 
155  bool defaultWaveformInUse = false;
156  bool checkSlotLimit = true;
157 
158  if (configType == SatSuperframeConf::CONFIG_TYPE_0)
159  {
160  defaultWaveformInUse = true;
161  }
162 
163  if (configType == SatSuperframeConf::CONFIG_TYPE_2)
164  {
165  checkSlotLimit = false;
166  }
167 
168  SatFrameConf::SatFrameConfParams_t frameConfParameters;
169  frameConfParameters.m_bandwidthHz = 10e4 * 2;
170  frameConfParameters.m_targetDuration = MilliSeconds(125);
171  frameConfParameters.m_btuConf = btu;
172  frameConfParameters.m_waveformConf = m_waveFormConf;
173  frameConfParameters.m_allocationChannel = 0;
174  frameConfParameters.m_isRandomAccess = false;
175  frameConfParameters.m_defaultWaveformInUse = defaultWaveformInUse;
176  frameConfParameters.m_checkSlotLimit = checkSlotLimit;
177  frameConfParameters.m_guardTimeSymbols = 0;
178  m_frameConf = Create<SatFrameConf>(frameConfParameters);
179  m_frameAllocator = Create<SatFrameAllocator>(m_frameConf, 0, configType, nullptr);
180 }
181 
182 void
184  bool acmEnabled,
185  bool fcaEnabled)
186 {
187  m_waveFormConf->SetAttribute("AcmEnabled", BooleanValue(acmEnabled));
188 
189  InitFrame(configType);
190 
191  double cnoThreshold = std::numeric_limits<double>::quiet_NaN();
192 
193  // Test with one UT and one RC
194  for (uint32_t i = 0; i < 11; i += 2) // CRAs
195  {
196  for (uint32_t j = 0; j < 15; j += 2) // minimum RBDCs
197  {
198  for (uint32_t k = 0; k < 15; k += 2) // RBDCs
199  {
200  for (uint32_t l = 0; l < 15; l += 2) // VBDCs
201  {
202  uint32_t bytesReq = 0;
203 
205  ContructRequestForUt(bytesReq, i, j, k, l, 1, (bool)std::rand() % 2);
206 
207  // repeat with all CC levels
208  for (uint32_t o = 0; o < m_ccLevelCount; o++)
209  {
210  // reset first allocations
211  m_frameAllocator->Reset();
212 
213  uint32_t waveformId = m_waveFormConf->GetDefaultWaveformId();
214  m_frameAllocator->GetBestWaveform(req.m_cno, waveformId, cnoThreshold);
215 
216  // do allocation and check that result is what expected
217  bool allocationResult =
218  m_frameAllocator->Allocate(m_ccLevels[o], &req, waveformId);
219 
220  m_frameAllocator->PreAllocateSymbols(0.9, fcaEnabled);
221 
222  // generate time slots and check results against request, RC based
223  // allocation off
224 
225  Ptr<SatTbtpMessage> tptp = CreateObject<SatTbtpMessage>();
227  tbtpContainer.push_back(tptp);
229 
230  m_frameAllocator->GenerateTimeSlots(tbtpContainer,
231  1000,
232  utAllocContainer,
233  false,
234  TracedCallback<uint32_t>(),
235  TracedCallback<uint32_t, uint32_t>(),
236  TracedCallback<uint32_t, double>());
237 
238  CheckSingleUtTestResults(bytesReq,
239  req,
240  allocationResult,
241  configType,
242  tbtpContainer,
243  utAllocContainer,
244  false,
245  fcaEnabled,
246  acmEnabled);
247 
248  // generate time slots and check results against request, RC based
249  // allocation on
250 
251  tbtpContainer.clear();
252  tptp = CreateObject<SatTbtpMessage>();
253  tbtpContainer.push_back(tptp);
254  utAllocContainer.clear();
255 
256  m_frameAllocator->GenerateTimeSlots(tbtpContainer,
257  1000,
258  utAllocContainer,
259  true,
260  TracedCallback<uint32_t>(),
261  TracedCallback<uint32_t, uint32_t>(),
262  TracedCallback<uint32_t, double>());
263 
264  CheckSingleUtTestResults(bytesReq,
265  req,
266  allocationResult,
267  configType,
268  tbtpContainer,
269  utAllocContainer,
270  true,
271  fcaEnabled,
272  acmEnabled);
273  }
274  }
275  }
276  }
277  }
278 
279  // test several times with random values using RC indices 2, 3, 4
280  for (uint32_t i = 0; i < 1000; i++)
281  {
282  for (uint32_t m = 2; m < 4; m++) //
283  {
284  uint32_t bytesReq = 0;
285  uint32_t divider = m_frameConf->GetCarrierMinPayloadInBytes() * 2;
286 
288  std::rand() % divider,
289  std::rand() % divider,
290  std::rand() % divider,
291  std::rand() % divider,
292  2,
293  (bool)std::rand() % 2);
294 
295  // repeat with all CC levels
296  for (uint32_t o = 0; o < m_ccLevelCount; o++)
297  {
298  // reset first allocations
299  m_frameAllocator->Reset();
300 
301  uint32_t waveformId = m_waveFormConf->GetDefaultWaveformId();
302  m_frameAllocator->GetBestWaveform(req.m_cno, waveformId, cnoThreshold);
303 
304  // do allocation and check that result is what expected
305  bool allocationResult = m_frameAllocator->Allocate(m_ccLevels[o], &req, waveformId);
306 
307  m_frameAllocator->PreAllocateSymbols(0.9, false);
308 
309  // generate time slots and check results against request, RC based allocation off
310 
311  Ptr<SatTbtpMessage> tptp = CreateObject<SatTbtpMessage>();
313  tbtpContainer.push_back(tptp);
315 
316  m_frameAllocator->GenerateTimeSlots(tbtpContainer,
317  1000,
318  utAllocContainer,
319  false,
320  TracedCallback<uint32_t>(),
321  TracedCallback<uint32_t, uint32_t>(),
322  TracedCallback<uint32_t, double>());
323 
324  CheckSingleUtTestResults(bytesReq,
325  req,
326  allocationResult,
327  configType,
328  tbtpContainer,
329  utAllocContainer,
330  false,
331  fcaEnabled,
332  acmEnabled);
333 
334  // generate time slots and check results against request, RC based allocation on
335 
336  tbtpContainer.clear();
337  tptp = CreateObject<SatTbtpMessage>();
338  tbtpContainer.push_back(tptp);
339  utAllocContainer.clear();
340 
341  m_frameAllocator->GenerateTimeSlots(tbtpContainer,
342  1000,
343  utAllocContainer,
344  true,
345  TracedCallback<uint32_t>(),
346  TracedCallback<uint32_t, uint32_t>(),
347  TracedCallback<uint32_t, double>());
348 
349  CheckSingleUtTestResults(bytesReq,
350  req,
351  allocationResult,
352  configType,
353  tbtpContainer,
354  utAllocContainer,
355  true,
356  fcaEnabled,
357  acmEnabled);
358  }
359  }
360  }
361 
362  Simulator::Destroy();
363 }
364 
365 void
367  uint32_t bytesReq,
369  bool allocated,
373  bool rcBasedAllocation,
374  bool fcaEnabled,
375  bool acmEnabled)
376 {
377  uint16_t slotCount = m_frameConf->GetTimeSlotCount();
378  uint16_t carrierCount = m_frameConf->GetCarrierCount();
379  uint16_t slotsPerCarrier = slotCount / carrierCount;
380  uint32_t minCarrierBytes = m_frameConf->GetCarrierMinPayloadInBytes();
381 
382  uint32_t tbtpAllocatedBytes = 0;
383  uint32_t slotsAllocated = 0;
384 
385  for (SatFrameAllocator::TbtpMsgContainer_t::const_iterator it = tbtpContainer.begin();
386  it != tbtpContainer.end();
387  it++)
388  {
389  SatTbtpMessage::DaTimeSlotInfoItem_t info = (*it)->GetDaTimeslots(req.m_address);
390 
391  for (SatTbtpMessage::DaTimeSlotConfContainer_t::const_iterator it2 = info.second.begin();
392  it2 != info.second.end();
393  it2++)
394  {
395  tbtpAllocatedBytes += m_frameConf->GetWaveformConf()
396  ->GetWaveform((*it2)->GetWaveFormId())
397  ->GetPayloadInBytes();
398  }
399 
400  slotsAllocated += info.second.size();
401  }
402 
403  // check that information is identical in TBTP container and UT allocation container
404  if (slotsAllocated > 0)
405  {
406  NS_TEST_ASSERT_MSG_EQ(utAllocContainer.at(req.m_address).second,
407  req.m_generateCtrlSlot,
408  "Control slot generation what expected!");
409  NS_ASSERT(utAllocContainer.at(req.m_address).second == req.m_generateCtrlSlot);
410 
411  uint32_t utAllocContainerBytes = 0;
412 
413  for (uint32_t i = 0; i < utAllocContainer.at(req.m_address).first.size(); i++)
414  {
415  utAllocContainerBytes += utAllocContainer.at(req.m_address).first.at(i);
416  }
417 
418  // std::cout << i << " " << j << " " << k << " " << l << " " << m << " " << m_ccLevels[o] <<
419  // " " << tbtpAllocatedBytes << " " << utAllocContainerBytes << " " << std::endl;
420  NS_TEST_ASSERT_MSG_EQ(tbtpAllocatedBytes,
421  utAllocContainerBytes,
422  " TBTP bytes=" << tbtpAllocatedBytes
423  << ", UT bytes=" << utAllocContainerBytes);
424  NS_ASSERT(tbtpAllocatedBytes == utAllocContainerBytes);
425 
426  bool minBytesAllocated =
427  (utAllocContainerBytes >= std::min<uint32_t>(bytesReq, minCarrierBytes));
428 
429  NS_TEST_ASSERT_MSG_EQ(minBytesAllocated, true, "Minimum bytes not allocated!");
430  NS_ASSERT(minBytesAllocated == true);
431  }
432  else
433  {
434  NS_TEST_ASSERT_MSG_EQ(utAllocContainer.empty(), true, "No allocations expected!");
435  NS_ASSERT(utAllocContainer.empty() == true);
436  }
437 
438  uint32_t slotsExpected = 0;
439 
440  if (allocated)
441  {
442  slotsExpected =
443  std::ceil((double)bytesReq / (double)minCarrierBytes * (double)slotsPerCarrier);
444 
445  if (req.m_generateCtrlSlot)
446  {
447  slotsExpected++;
448  }
449 
450  slotsExpected = std::min<uint32_t>(slotsExpected, slotsPerCarrier);
451 
452  if (fcaEnabled)
453  {
454  bool onlyCraRequested = true;
455 
456  for (uint32_t i = 0; i < req.m_reqPerRc.size(); i++)
457  {
458  if ((req.m_reqPerRc.at(i).m_rbdcBytes > 0) ||
459  (req.m_reqPerRc.at(i).m_vbdcBytes > 0))
460  {
461  onlyCraRequested = false;
462  }
463  }
464 
465  if (((configType == SatSuperframeConf::CONFIG_TYPE_0) || (acmEnabled == false)) &&
466  (onlyCraRequested == false))
467  {
468  slotsExpected = slotsPerCarrier;
469  }
470  }
471  }
472  // std::cout << i << " " << j << " " << k << " " << l << " " << m << " "<< m_ccLevels[o] << " "
473  // << slotsExpected << "=" << slotsAllocated << " " << bytesReq << " " <<
474  // m_frameConf->GetCarrierMinPayloadInBytes () << std::endl;
475 
476  // check that slots are what expected
477  // in other configuration than 0 or when RC based allocation is enabled,
478  // it can be just checked that some slots are allocated (if request is not zero)
479 
480  if ((configType == SatSuperframeConf::CONFIG_TYPE_0) && (rcBasedAllocation == false))
481  {
482  NS_TEST_ASSERT_MSG_EQ(slotsAllocated,
483  slotsExpected,
484  " slots allocated= " << slotsAllocated
485  << ", slots expected= " << slotsExpected);
486  }
487  else
488  {
489  if (slotsExpected > 0)
490  {
491  NS_TEST_ASSERT_MSG_GT(slotsAllocated,
492  0,
493  " slots allocated= " << slotsAllocated
494  << ", at least one expected.");
495  }
496  else
497  {
498  NS_TEST_ASSERT_MSG_EQ(slotsAllocated,
499  slotsExpected,
500  " slots allocated= " << slotsAllocated
501  << ", slots expected= " << slotsExpected);
502  }
503  }
504 }
505 
506 void
508 {
509  m_waveFormConf->SetAttribute("AcmEnabled", BooleanValue(false));
510 
511  // test with configuration type 0
512  InitFrame(SatSuperframeConf::CONFIG_TYPE_0);
513 
514  uint32_t utBytesReq[6];
516 
517  req[0] = ContructRequestForUt(utBytesReq[0], 4, 1, 6, 0, 1, false);
518  req[1] = ContructRequestForUt(utBytesReq[1], 4, 0, 0, 6, 1, false);
519  req[2] = ContructRequestForUt(utBytesReq[2], 4, 1, 3, 3, 1, false);
520  req[3] = ContructRequestForUt(utBytesReq[3], 1, 0, 1, 0, 1, false);
521  req[4] = ContructRequestForUt(utBytesReq[4], 2, 0, 0, 1, 1, false);
522  req[5] = ContructRequestForUt(utBytesReq[5], 1, 1, 1, 1, 1, false);
523 
524  uint32_t waveformId[6];
525  double cnoThreshold = std::numeric_limits<double>::quiet_NaN();
526 
527  for (uint32_t i = 0; i < 6; i++)
528  {
529  waveformId[i] = m_waveFormConf->GetDefaultWaveformId();
530  m_frameAllocator->GetBestWaveform(req[i].m_cno, waveformId[i], cnoThreshold);
531  }
532 
533  bool allocationResult;
534 
535  // test with two UTs
536  for (uint32_t n = 0; n < 5; n++)
537  {
538  for (uint32_t m = n + 1; m < 6; m++)
539  {
540  // repeat case all CC levels
541  for (uint32_t o = 0; o < m_ccLevelCount; o++)
542  {
543  m_frameAllocator->Reset();
544 
545  allocationResult =
546  m_frameAllocator->Allocate(m_ccLevels[o], &req[n], waveformId[n]);
547  NS_TEST_ASSERT_MSG_EQ(true, allocationResult, "Allocation failed!");
548 
549  allocationResult =
550  m_frameAllocator->Allocate(m_ccLevels[o], &req[m], waveformId[m]);
551  NS_TEST_ASSERT_MSG_EQ(true, allocationResult, "Allocation failed!");
552 
553  m_frameAllocator->PreAllocateSymbols(1.0, false);
554 
555  Ptr<SatTbtpMessage> tptp = CreateObject<SatTbtpMessage>();
557  tbtpContainer.push_back(tptp);
559 
560  m_frameAllocator->GenerateTimeSlots(tbtpContainer,
561  1000,
562  utAllocContainer,
563  false,
564  TracedCallback<uint32_t>(),
565  TracedCallback<uint32_t, uint32_t>(),
566  TracedCallback<uint32_t, double>());
567 
568  ReqInfo_t reqInfo;
569  reqInfo.insert(
570  std::make_pair(req[n].m_address, std::make_pair(req[n], utBytesReq[n])));
571  reqInfo.insert(
572  std::make_pair(req[m].m_address, std::make_pair(req[m], utBytesReq[m])));
573 
574  CheckMultiUtTestResults(utAllocContainer, reqInfo);
575  }
576  }
577  }
578 
579  // test with three UTs
580  for (uint32_t n = 0; n < 4; n++)
581  {
582  for (uint32_t m = n + 1; m < 5; m++)
583  {
584  for (uint32_t o = m + 2; o < 6; o++)
585  {
586  m_frameAllocator->Reset();
587 
588  allocationResult = m_frameAllocator->Allocate(SatFrameAllocator::CC_LEVEL_CRA,
589  &req[n],
590  waveformId[n]);
591  NS_TEST_ASSERT_MSG_EQ(true, allocationResult, "Allocation failed!");
592 
593  allocationResult = m_frameAllocator->Allocate(SatFrameAllocator::CC_LEVEL_CRA,
594  &req[m],
595  waveformId[m]);
596  NS_TEST_ASSERT_MSG_EQ(true, allocationResult, "Allocation failed!");
597 
598  allocationResult = m_frameAllocator->Allocate(SatFrameAllocator::CC_LEVEL_CRA,
599  &req[o],
600  waveformId[o]);
601  NS_TEST_ASSERT_MSG_EQ(true, allocationResult, "Allocation failed!");
602 
603  m_frameAllocator->PreAllocateSymbols(1.0, false);
604 
605  Ptr<SatTbtpMessage> tptp = CreateObject<SatTbtpMessage>();
607  tbtpContainer.push_back(tptp);
609 
610  m_frameAllocator->GenerateTimeSlots(tbtpContainer,
611  1000,
612  utAllocContainer,
613  false,
614  TracedCallback<uint32_t>(),
615  TracedCallback<uint32_t, uint32_t>(),
616  TracedCallback<uint32_t, double>());
617 
618  ReqInfo_t reqInfo;
619  reqInfo.insert(
620  std::make_pair(req[n].m_address, std::make_pair(req[n], utBytesReq[n])));
621  reqInfo.insert(
622  std::make_pair(req[m].m_address, std::make_pair(req[m], utBytesReq[m])));
623  reqInfo.insert(
624  std::make_pair(req[m].m_address, std::make_pair(req[o], utBytesReq[o])));
625 
626  CheckMultiUtTestResults(utAllocContainer, reqInfo);
627  }
628  }
629  }
630 }
631 
632 void
635  ReqInfo_t& reqInfo)
636 {
637  uint16_t carrierCount = m_frameConf->GetCarrierCount();
638  uint32_t minCarrierBytes = m_frameConf->GetCarrierMinPayloadInBytes();
639 
640  for (SatFrameAllocator::UtAllocInfoContainer_t::const_iterator it = utAllocContainer.begin();
641  it != utAllocContainer.end();
642  it++)
643  {
644  uint32_t bytesAllocated = 0;
645 
646  for (std::vector<uint32_t>::const_iterator it2 = it->second.first.begin();
647  it2 != it->second.first.end();
648  it2++)
649  {
650  bytesAllocated += *it2;
651  }
652 
653  // check results can be easily checked by general way
654  if (utAllocContainer.size() > carrierCount)
655  {
656  NS_TEST_ASSERT_MSG_GT(bytesAllocated, 0, "Allocation not what expected!");
657  }
658  else if (reqInfo.at(it->first).second == minCarrierBytes)
659  {
660  NS_TEST_ASSERT_MSG_EQ(minCarrierBytes, bytesAllocated, "Allocation not what expected!");
661  }
662  else
663  {
664  NS_TEST_ASSERT_MSG_NE(minCarrierBytes, bytesAllocated, "Allocation not what expected!");
665  }
666  }
667 }
668 
671  uint32_t craBytes,
672  uint32_t minRbdcBytes,
673  uint32_t rbdcBytes,
674  uint32_t vbdcBytes,
675  uint32_t rcCount,
676  bool controlSlot)
677 {
680  rcCount,
682 
685  req.m_address = Mac48Address::Allocate();
686  req.m_generateCtrlSlot = controlSlot;
687 
688  m_cnoIndex++;
689 
691  {
692  m_cnoIndex = 0;
693  }
694 
696 
697  uint32_t craBytesReq = 0;
698  totalBytes = 0;
699 
700  uint32_t maxCraBytes = m_frameConf->GetCarrierMinPayloadInBytes();
701  uint32_t minCarrierBytes = maxCraBytes;
702 
703  if (req.m_generateCtrlSlot)
704  {
705  maxCraBytes -= m_frameAllocator->GetMostRobustWaveform()->GetPayloadInBytes();
706  }
707 
708  if (craBytesReq < maxCraBytes)
709  {
710  uint32_t craBytesLeft = maxCraBytes - craBytesReq;
711  req.m_reqPerRc[0].m_craBytes =
712  std::min<uint32_t>(minCarrierBytes * craBytes / 10, craBytesLeft);
713  }
714  else
715  {
716  req.m_reqPerRc[0].m_craBytes = 0;
717  }
718 
719  req.m_reqPerRc[0].m_minRbdcBytes = minCarrierBytes * minRbdcBytes / 10;
720  req.m_reqPerRc[0].m_rbdcBytes = minCarrierBytes * rbdcBytes / 10;
721  req.m_reqPerRc[0].m_vbdcBytes = minCarrierBytes * vbdcBytes / 10;
722 
723  if (req.m_reqPerRc[0].m_minRbdcBytes > req.m_reqPerRc[0].m_rbdcBytes)
724  {
725  req.m_reqPerRc[0].m_rbdcBytes = req.m_reqPerRc[0].m_minRbdcBytes;
726  }
727 
728  craBytesReq += req.m_reqPerRc[0].m_craBytes;
729 
730  totalBytes += req.m_reqPerRc[0].m_craBytes;
731  totalBytes += req.m_reqPerRc[0].m_rbdcBytes;
732  totalBytes += req.m_reqPerRc[0].m_vbdcBytes;
733 
734  uint32_t divider = minCarrierBytes + 1;
735 
736  // if more than one RC is given, then random request value is set for the RC 1 to RC n
737  for (uint32_t i = 1; i < rcCount; i++)
738  {
739  if (craBytesReq < maxCraBytes)
740  {
741  uint32_t craBytesLeft = maxCraBytes - craBytesReq;
742  req.m_reqPerRc[i].m_craBytes = std::min<uint32_t>(std::rand() % divider, craBytesLeft);
743  }
744  else
745  {
746  req.m_reqPerRc[i].m_craBytes = 0;
747  }
748 
749  req.m_reqPerRc[i].m_minRbdcBytes = std::rand() % divider;
750  req.m_reqPerRc[i].m_rbdcBytes = std::rand() % divider;
751  req.m_reqPerRc[i].m_vbdcBytes = std::rand() % divider;
752 
753  if (req.m_reqPerRc[i].m_minRbdcBytes > req.m_reqPerRc[i].m_rbdcBytes)
754  {
755  req.m_reqPerRc[i].m_rbdcBytes = req.m_reqPerRc[i].m_minRbdcBytes;
756  }
757 
758  craBytesReq += req.m_reqPerRc[i].m_craBytes;
759  totalBytes += req.m_reqPerRc[i].m_craBytes;
760  totalBytes += req.m_reqPerRc[i].m_rbdcBytes;
761  totalBytes += req.m_reqPerRc[i].m_vbdcBytes;
762  }
763 
764  return req;
765 }
766 
767 void
769 {
770  // Set simulation output details
771  Singleton<SatEnvVariables>::Get()->DoInitialize();
772  Singleton<SatEnvVariables>::Get()->SetOutputVariables("sat-frame-allocator", "", true);
773 
774  // test single UT with all configuration types, ACM and FCA disabled
775  RunSingleUtTest(SatSuperframeConf::CONFIG_TYPE_0, false, false);
776  RunSingleUtTest(SatSuperframeConf::CONFIG_TYPE_1, false, false);
777  RunSingleUtTest(SatSuperframeConf::CONFIG_TYPE_2, false, false);
778 
779  // test single UT with all configuration types, ACM disabled and FCA enabled
780  RunSingleUtTest(SatSuperframeConf::CONFIG_TYPE_0, false, true);
781  RunSingleUtTest(SatSuperframeConf::CONFIG_TYPE_1, false, true);
782  RunSingleUtTest(SatSuperframeConf::CONFIG_TYPE_2, false, true);
783 
784  // test single UT with all configuration types, ACM enabled and FCA disabled
785  RunSingleUtTest(SatSuperframeConf::CONFIG_TYPE_0, true, false);
786  RunSingleUtTest(SatSuperframeConf::CONFIG_TYPE_1, true, false);
787  RunSingleUtTest(SatSuperframeConf::CONFIG_TYPE_2, true, false);
788 
789  // test single UT with all configuration types, ACM enabled and FCA enabled
790  RunSingleUtTest(SatSuperframeConf::CONFIG_TYPE_0, true, true);
791  RunSingleUtTest(SatSuperframeConf::CONFIG_TYPE_1, true, true);
792  RunSingleUtTest(SatSuperframeConf::CONFIG_TYPE_2, true, true);
793 
794  // test with two and three UTs
795  RunMultiUtTest();
796 
797  Singleton<SatEnvVariables>::Get()->DoDispose();
798 }
799 
803 class SatFrameAllocatorTestSuite : public TestSuite
804 {
805  public:
807 };
808 
810  : TestSuite("sat-frame-allocator-test", UNIT)
811 {
812  AddTestCase(new SatFrameAllocatorTestCase, TestCase::QUICK);
813 }
814 
815 // Do allocate an instance of this TestSuite
Test case to unit test Satellite Frame Allocator.
SatFrameAllocator::SatFrameAllocReq ContructRequestForUt(uint32_t &totalBytes, uint32_t craBytes, uint32_t minRbdcBytes, uint32_t rbdcBytes, uint32_t vbdcBytes, uint32_t rcCount, bool controlSlot)
void CheckMultiUtTestResults(SatFrameAllocator::UtAllocInfoContainer_t &utAllocContainer, ReqInfo_t &reqInfo)
SatFrameAllocator::CcLevel_t m_ccLevels[m_ccLevelCount]
std::map< Address, std::pair< SatFrameAllocator::SatFrameAllocReq, uint32_t > > ReqInfo_t
Ptr< SatFrameAllocator > m_frameAllocator
void InitFrame(SatSuperframeConf::ConfigType_t configType)
void RunSingleUtTest(SatSuperframeConf::ConfigType_t configType, bool acmEnabled, bool fcaEnabled)
void CheckSingleUtTestResults(uint32_t bytesReq, SatFrameAllocator::SatFrameAllocReq req, bool allocated, SatSuperframeConf::ConfigType_t configType, SatFrameAllocator::TbtpMsgContainer_t &tbtpContainer, SatFrameAllocator::UtAllocInfoContainer_t &utAllocContainer, bool rcBasedAllocation, bool fcaEnabled, bool acmEnabled)
Test suite for Satellite Frame Allocator unit test cases.
SatFrameAllocReq is used to define frame allocation parameters when requesting allocation from SatFra...
Allocation information item for the UT/RC requests [bytes].
std::vector< Ptr< SatTbtpMessage > > TbtpMsgContainer_t
Container to store generated TBTP messages.
std::map< Address, UtAllocInfoItem_t > UtAllocInfoContainer_t
Map container to store UT allocation information.
std::vector< SatFrameAllocReqItem > SatFrameAllocReqItemContainer_t
Container to store SatFrameAllocReqItem items.
ConfigType_t
Enum for configuration types.
std::pair< uint8_t, DaTimeSlotConfContainer_t > DaTimeSlotInfoItem_t
Item for DA time slot information.
SatArqSequenceNumber is handling the sequence numbers for the ARQ process.
static SatFrameAllocatorTestSuite satFrameAllocatorTestSuite
Helper struct to reduce the number of parameters fed into the SatFrameConf constructor.