A Discrete-Event Network Simulator
API
Loading...
Searching...
No Matches
lte-test-uplink-power-control.cc
Go to the documentation of this file.
1/*
2 * Copyright (c) 2014 Piotr Gawlowicz
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: Piotr Gawlowicz <gawlowicz.p@gmail.com>
18 *
19 */
20
22
23#include "lte-ffr-simple.h"
24
25#include "ns3/lte-helper.h"
26#include "ns3/mobility-helper.h"
27#include <ns3/boolean.h>
28#include <ns3/callback.h>
29#include <ns3/config.h>
30#include <ns3/double.h>
31#include <ns3/enum.h>
32#include <ns3/ff-mac-scheduler.h>
33#include <ns3/integer.h>
34#include <ns3/log.h>
35#include <ns3/lte-common.h>
36#include <ns3/lte-enb-net-device.h>
37#include <ns3/lte-enb-phy.h>
38#include <ns3/lte-enb-rrc.h>
39#include <ns3/lte-rrc-sap.h>
40#include <ns3/lte-ue-net-device.h>
41#include <ns3/lte-ue-phy.h>
42#include <ns3/lte-ue-rrc.h>
43#include <ns3/pointer.h>
44#include <ns3/simulator.h>
45#include <ns3/string.h>
46
47using namespace ns3;
48
49NS_LOG_COMPONENT_DEFINE("LteUplinkPowerControlTest");
50
56 : TestSuite("lte-uplink-power-control", Type::SYSTEM)
57{
58 // LogLevel logLevel = (LogLevel)(LOG_PREFIX_FUNC | LOG_PREFIX_TIME | LOG_LEVEL_DEBUG);
59 // LogComponentEnable ("LteUplinkPowerControlTest", logLevel);
60 NS_LOG_INFO("Creating LteUplinkPowerControlTestSuite");
61
63 TestCase::Duration::QUICK);
65 new LteUplinkClosedLoopPowerControlAbsoluteModeTestCase("ClosedLoopAbsoluteModeTest1"),
66 TestCase::Duration::QUICK);
68 "ClosedLoopAccumulatedModeTest1"),
69 TestCase::Duration::QUICK);
70}
71
77
81void
83 uint16_t cellId,
84 uint16_t rnti,
85 double txPower)
86{
87 testcase->PuschTxPowerTrace(cellId, rnti, txPower);
88}
89
90void
92 uint16_t cellId,
93 uint16_t rnti,
94 double txPower)
95{
96 testcase->PucchTxPowerTrace(cellId, rnti, txPower);
97}
98
99void
101 uint16_t cellId,
102 uint16_t rnti,
103 double txPower)
104{
105 testcase->SrsTxPowerTrace(cellId, rnti, txPower);
106}
107
109 : TestCase(name)
110{
111 NS_LOG_INFO("Creating LteUplinkPowerControlTestCase");
112}
113
115{
116}
117
118void
120 uint32_t y,
121 double expectedPuschTxPower,
122 double expectedPucchTxPower,
123 double expectedSrsTxPower)
124{
125 NS_LOG_FUNCTION(this);
126 NS_LOG_DEBUG("Teleport UE to : (" << x << ", " << y << ", 0)");
127
128 m_ueMobility->SetPosition(Vector(x, y, 0.0));
130
131 m_expectedPuschTxPower = expectedPuschTxPower;
132 m_expectedPucchTxPower = expectedPucchTxPower;
133 m_expectedSrsTxPower = expectedSrsTxPower;
134}
135
136void
138 uint32_t tpcNum,
139 double expectedPuschTxPower,
140 double expectedPucchTxPower,
141 double expectedSrsTxPower)
142{
143 NS_LOG_FUNCTION(this);
144
146
147 m_expectedPuschTxPower = expectedPuschTxPower;
148 m_expectedPucchTxPower = expectedPucchTxPower;
149 m_expectedSrsTxPower = expectedSrsTxPower;
150
151 m_ffrSimple->SetTpc(tpc, tpcNum, m_accumulatedMode);
152}
153
154void
155LteUplinkPowerControlTestCase::PuschTxPowerTrace(uint16_t cellId, uint16_t rnti, double txPower)
156{
157 NS_LOG_FUNCTION(this);
158 NS_LOG_DEBUG("PuschTxPower : CellId: " << cellId << " RNTI: " << rnti
159 << " PuschTxPower: " << txPower);
160 // wait because of RSRP filtering
162 {
163 return;
164 }
165 NS_TEST_ASSERT_MSG_EQ_TOL(txPower, m_expectedPuschTxPower, 0.01, "Wrong Pusch Tx Power");
166}
167
168void
169LteUplinkPowerControlTestCase::PucchTxPowerTrace(uint16_t cellId, uint16_t rnti, double txPower)
170{
171 NS_LOG_FUNCTION(this);
172 NS_LOG_DEBUG("PucchTxPower : CellId: " << cellId << " RNTI: " << rnti
173 << " PuschTxPower: " << txPower);
174 // wait because of RSRP filtering
176 {
177 return;
178 }
179
180 NS_TEST_ASSERT_MSG_EQ_TOL(txPower, m_expectedPucchTxPower, 0.01, "Wrong Pucch Tx Power");
181}
182
183void
184LteUplinkPowerControlTestCase::SrsTxPowerTrace(uint16_t cellId, uint16_t rnti, double txPower)
185{
186 NS_LOG_FUNCTION(this);
187 NS_LOG_DEBUG("SrsTxPower : CellId: " << cellId << " RNTI: " << rnti
188 << " PuschTxPower: " << txPower);
189 // wait because of RSRP filtering
191 {
192 return;
193 }
194 NS_TEST_ASSERT_MSG_EQ_TOL(txPower, m_expectedSrsTxPower, 0.01, "Wrong Srs Tx Power");
195}
196
197void
199{
200}
201
203 : LteUplinkPowerControlTestCase("Uplink Open Loop Power Control: " + name)
204{
205 NS_LOG_INFO("Creating LteUplinkPowerControlTestCase");
206}
207
209{
210}
211
212void
214{
216 Config::SetDefault("ns3::LteHelper::UseIdealRrc", BooleanValue(false));
217
218 double eNbTxPower = 30;
219 Config::SetDefault("ns3::LteEnbPhy::TxPower", DoubleValue(eNbTxPower));
220 Config::SetDefault("ns3::LteUePhy::TxPower", DoubleValue(10.0));
221 Config::SetDefault("ns3::LteUePhy::EnableUplinkPowerControl", BooleanValue(true));
222
223 Config::SetDefault("ns3::LteUePowerControl::ClosedLoop", BooleanValue(false));
224 Config::SetDefault("ns3::LteUePowerControl::AccumulationEnabled", BooleanValue(false));
225 Config::SetDefault("ns3::LteUePowerControl::PoNominalPusch", IntegerValue(-90));
226 Config::SetDefault("ns3::LteUePowerControl::PsrsOffset", IntegerValue(9));
227
228 Ptr<LteHelper> lteHelper = CreateObject<LteHelper>();
229
230 uint16_t bandwidth = 25;
231 double d1 = 0;
232
233 // Create Nodes: eNodeB and UE
234 NodeContainer enbNodes;
235 NodeContainer ueNodes;
236 enbNodes.Create(1);
237 ueNodes.Create(1);
238 NodeContainer allNodes = NodeContainer(enbNodes, ueNodes);
239
240 /* the topology is the following:
241 *
242 * eNB1-------------------------UE
243 * d1
244 */
245
246 // Install Mobility Model
247 Ptr<ListPositionAllocator> positionAlloc = CreateObject<ListPositionAllocator>();
248 positionAlloc->Add(Vector(0.0, 0.0, 0.0)); // eNB1
249 positionAlloc->Add(Vector(d1, 0.0, 0.0)); // UE1
250
251 MobilityHelper mobility;
252 mobility.SetMobilityModel("ns3::ConstantPositionMobilityModel");
253 mobility.SetPositionAllocator(positionAlloc);
254 mobility.Install(allNodes);
255 m_ueMobility = ueNodes.Get(0)->GetObject<MobilityModel>();
256
257 // Create Devices and install them in the Nodes (eNB and UE)
258 NetDeviceContainer enbDevs;
259 NetDeviceContainer ueDevs;
260 lteHelper->SetSchedulerType("ns3::PfFfMacScheduler");
261
262 lteHelper->SetEnbDeviceAttribute("DlBandwidth", UintegerValue(bandwidth));
263 lteHelper->SetEnbDeviceAttribute("UlBandwidth", UintegerValue(bandwidth));
264
265 enbDevs = lteHelper->InstallEnbDevice(enbNodes);
266 ueDevs = lteHelper->InstallUeDevice(ueNodes);
267
268 Ptr<LteUePhy> uePhy =
269 DynamicCast<LteUePhy>(ueDevs.Get(0)->GetObject<LteUeNetDevice>()->GetPhy());
270 m_ueUpc = uePhy->GetUplinkPowerControl();
271
272 m_ueUpc->TraceConnectWithoutContext("ReportPuschTxPower",
274 m_ueUpc->TraceConnectWithoutContext("ReportPucchTxPower",
276 m_ueUpc->TraceConnectWithoutContext("ReportSrsTxPower",
278
279 // Attach a UE to a eNB
280 lteHelper->Attach(ueDevs, enbDevs.Get(0));
281
282 // Activate a data radio bearer
284 EpsBearer bearer(q);
285 lteHelper->ActivateDataRadioBearer(ueDevs, bearer);
286
287 // Changing UE position
290 this,
291 0,
292 0,
293 -40,
294 -40,
295 -40);
298 this,
299 200,
300 0,
301 8.9745,
302 8.9745,
303 11.9745);
306 this,
307 400,
308 0,
309 14.9951,
310 14.9951,
311 17.9951);
314 this,
315 600,
316 0,
317 18.5169,
318 18.5169,
319 21.5169);
322 this,
323 800,
324 0,
325 21.0157,
326 21.0157,
327 23);
330 this,
331 1000,
332 0,
333 22.9539,
334 22.9539,
335 23);
338 this,
339 1200,
340 0,
341 23,
342 10,
343 23);
346 this,
347 400,
348 0,
349 14.9951,
350 14.9951,
351 17.9951);
354 this,
355 800,
356 0,
357 21.0157,
358 21.0157,
359 23);
362 this,
363 0,
364 0,
365 -40,
366 -40,
367 -40);
370 this,
371 100,
372 0,
373 2.9539,
374 2.9539,
375 5.9539);
376 Simulator::Stop(Seconds(1.200));
378
380}
381
384 : LteUplinkPowerControlTestCase("Uplink Closed Loop Power Control: " + name)
385{
386 NS_LOG_INFO("Creating LteUplinkClosedLoopPowerControlAbsoluteModeTestCase");
387}
388
391{
392}
393
394void
396{
398 Config::SetDefault("ns3::LteHelper::UseIdealRrc", BooleanValue(false));
399
400 double eNbTxPower = 30;
401 Config::SetDefault("ns3::LteEnbPhy::TxPower", DoubleValue(eNbTxPower));
402 Config::SetDefault("ns3::LteUePhy::TxPower", DoubleValue(10.0));
403 Config::SetDefault("ns3::LteUePhy::EnableUplinkPowerControl", BooleanValue(true));
404
405 Config::SetDefault("ns3::LteUePowerControl::ClosedLoop", BooleanValue(true));
406 Config::SetDefault("ns3::LteUePowerControl::AccumulationEnabled", BooleanValue(false));
407 Config::SetDefault("ns3::LteUePowerControl::PoNominalPusch", IntegerValue(-90));
408 Config::SetDefault("ns3::LteUePowerControl::PsrsOffset", IntegerValue(9));
409
410 Ptr<LteHelper> lteHelper = CreateObject<LteHelper>();
411 lteHelper->SetFfrAlgorithmType("ns3::LteFfrSimple");
412
413 uint16_t bandwidth = 25;
414 double d1 = 100;
415
416 // Create Nodes: eNodeB and UE
417 NodeContainer enbNodes;
418 NodeContainer ueNodes;
419 enbNodes.Create(1);
420 ueNodes.Create(1);
421 NodeContainer allNodes = NodeContainer(enbNodes, ueNodes);
422
423 /* the topology is the following:
424 *
425 * eNB1-------------------------UE
426 * d1
427 */
428
429 // Install Mobility Model
430 Ptr<ListPositionAllocator> positionAlloc = CreateObject<ListPositionAllocator>();
431 positionAlloc->Add(Vector(0.0, 0.0, 0.0)); // eNB1
432 positionAlloc->Add(Vector(d1, 0.0, 0.0)); // UE1
433
434 MobilityHelper mobility;
435 mobility.SetMobilityModel("ns3::ConstantPositionMobilityModel");
436 mobility.SetPositionAllocator(positionAlloc);
437 mobility.Install(allNodes);
438 m_ueMobility = ueNodes.Get(0)->GetObject<MobilityModel>();
439
440 // Create Devices and install them in the Nodes (eNB and UE)
441 NetDeviceContainer enbDevs;
442 NetDeviceContainer ueDevs;
443 lteHelper->SetSchedulerType("ns3::PfFfMacScheduler");
444
445 lteHelper->SetEnbDeviceAttribute("DlBandwidth", UintegerValue(bandwidth));
446 lteHelper->SetEnbDeviceAttribute("UlBandwidth", UintegerValue(bandwidth));
447
448 enbDevs = lteHelper->InstallEnbDevice(enbNodes);
449 ueDevs = lteHelper->InstallUeDevice(ueNodes);
450
451 Ptr<LteUePhy> uePhy =
452 DynamicCast<LteUePhy>(ueDevs.Get(0)->GetObject<LteUeNetDevice>()->GetPhy());
453 m_ueUpc = uePhy->GetUplinkPowerControl();
454
455 m_ueUpc->TraceConnectWithoutContext("ReportPuschTxPower",
457 m_ueUpc->TraceConnectWithoutContext("ReportPucchTxPower",
459 m_ueUpc->TraceConnectWithoutContext("ReportSrsTxPower",
461
462 // Attach a UE to a eNB
463 lteHelper->Attach(ueDevs, enbDevs.Get(0));
464
465 // Activate a data radio bearer
467 EpsBearer bearer(q);
468 lteHelper->ActivateDataRadioBearer(ueDevs, bearer);
469
470 PointerValue tmp;
471 enbDevs.Get(0)->GetAttribute("LteFfrAlgorithm", tmp);
472 m_ffrSimple = DynamicCast<LteFfrSimple>(tmp.GetObject());
473 m_accumulatedMode = false;
474
475 // Changing TPC value
478 this,
479 1,
480 0,
481 1.9539,
482 1.9539,
483 4.9539);
486 this,
487 0,
488 0,
489 -1.0461,
490 -1.0461,
491 1.9539);
494 this,
495 2,
496 0,
497 3.9539,
498 3.9539,
499 6.9539);
502 this,
503 3,
504 0,
505 6.9539,
506 6.9539,
507 9.9539);
510 this,
511 0,
512 0,
513 -1.0461,
514 -1.0461,
515 1.9539);
518 this,
519 1,
520 0,
521 1.9539,
522 1.9539,
523 4.9539);
526 this,
527 3,
528 0,
529 6.9539,
530 6.9539,
531 9.9539);
534 this,
535 2,
536 0,
537 3.9539,
538 3.9539,
539 6.9539);
540 Simulator::Stop(Seconds(1.000));
542
544}
545
548 : LteUplinkPowerControlTestCase("Uplink Closed Loop Power Control: " + name)
549{
550 NS_LOG_INFO("Creating LteUplinkClosedLoopPowerControlAccumulatedModeTestCase");
551}
552
555{
556}
557
558void
560{
562 Config::SetDefault("ns3::LteHelper::UseIdealRrc", BooleanValue(false));
563
564 double eNbTxPower = 30;
565 Config::SetDefault("ns3::LteEnbPhy::TxPower", DoubleValue(eNbTxPower));
566 Config::SetDefault("ns3::LteUePhy::TxPower", DoubleValue(10.0));
567 Config::SetDefault("ns3::LteUePhy::EnableUplinkPowerControl", BooleanValue(true));
568
569 Config::SetDefault("ns3::LteUePowerControl::ClosedLoop", BooleanValue(true));
570 Config::SetDefault("ns3::LteUePowerControl::AccumulationEnabled", BooleanValue(true));
571 Config::SetDefault("ns3::LteUePowerControl::PoNominalPusch", IntegerValue(-90));
572 Config::SetDefault("ns3::LteUePowerControl::PsrsOffset", IntegerValue(9));
573
574 Ptr<LteHelper> lteHelper = CreateObject<LteHelper>();
575 lteHelper->SetFfrAlgorithmType("ns3::LteFfrSimple");
576
577 uint16_t bandwidth = 25;
578 double d1 = 10;
579
580 // Create Nodes: eNodeB and UE
581 NodeContainer enbNodes;
582 NodeContainer ueNodes;
583 enbNodes.Create(1);
584 ueNodes.Create(1);
585 NodeContainer allNodes = NodeContainer(enbNodes, ueNodes);
586
587 /* the topology is the following:
588 *
589 * eNB1-------------------------UE
590 * d1
591 */
592
593 // Install Mobility Model
594 Ptr<ListPositionAllocator> positionAlloc = CreateObject<ListPositionAllocator>();
595 positionAlloc->Add(Vector(0.0, 0.0, 0.0)); // eNB1
596 positionAlloc->Add(Vector(d1, 0.0, 0.0)); // UE1
597
598 MobilityHelper mobility;
599 mobility.SetMobilityModel("ns3::ConstantPositionMobilityModel");
600 mobility.SetPositionAllocator(positionAlloc);
601 mobility.Install(allNodes);
602 m_ueMobility = ueNodes.Get(0)->GetObject<MobilityModel>();
603
604 // Create Devices and install them in the Nodes (eNB and UE)
605 NetDeviceContainer enbDevs;
606 NetDeviceContainer ueDevs;
607 lteHelper->SetSchedulerType("ns3::PfFfMacScheduler");
608
609 lteHelper->SetEnbDeviceAttribute("DlBandwidth", UintegerValue(bandwidth));
610 lteHelper->SetEnbDeviceAttribute("UlBandwidth", UintegerValue(bandwidth));
611
612 enbDevs = lteHelper->InstallEnbDevice(enbNodes);
613 ueDevs = lteHelper->InstallUeDevice(ueNodes);
614
615 Ptr<LteUePhy> uePhy =
616 DynamicCast<LteUePhy>(ueDevs.Get(0)->GetObject<LteUeNetDevice>()->GetPhy());
617 m_ueUpc = uePhy->GetUplinkPowerControl();
618
619 m_ueUpc->TraceConnectWithoutContext("ReportPuschTxPower",
621 m_ueUpc->TraceConnectWithoutContext("ReportPucchTxPower",
623 m_ueUpc->TraceConnectWithoutContext("ReportSrsTxPower",
625
626 // Attach a UE to a eNB
627 lteHelper->Attach(ueDevs, enbDevs.Get(0));
628
629 // Activate a data radio bearer
631 EpsBearer bearer(q);
632 lteHelper->ActivateDataRadioBearer(ueDevs, bearer);
633
634 PointerValue tmp;
635 enbDevs.Get(0)->GetAttribute("LteFfrAlgorithm", tmp);
636 m_ffrSimple = DynamicCast<LteFfrSimple>(tmp.GetObject());
637 m_accumulatedMode = true;
638
639 // Changing TPC value
642 this,
643 1,
644 0,
645 -17.0461,
646 -17.0461,
647 -14.0461);
650 this,
651 0,
652 20,
653 -37.0461,
654 -37.0461,
655 -34.0461);
658 this,
659 0,
660 20,
661 -40,
662 10,
663 -37.0461);
666 this,
667 2,
668 1,
669 -39.0461,
670 -39.0461,
671 -36.0461);
674 this,
675 3,
676 10,
677 -9.0461,
678 -9.0461,
679 -6.0461);
682 this,
683 2,
684 15,
685 5.9539,
686 5.9539,
687 8.9539);
690 this,
691 3,
692 1,
693 8.9539,
694 8.9539,
695 11.9539);
698 this,
699 2,
700 10,
701 18.9539,
702 18.9539,
703 21.9539);
706 this,
707 2,
708 20,
709 23,
710 23,
711 23);
714 this,
715 0,
716 1,
717 22.9539,
718 22.9539,
719 23);
722 this,
723 0,
724 20,
725 2.9539,
726 2.9539,
727 5.9539);
730 this,
731 2,
732 5,
733 7.9539,
734 7.9539,
735 10.9539);
736 Simulator::Stop(Seconds(1.200));
738
740}
AttributeValue implementation for Boolean.
Definition: boolean.h:37
This class can be used to hold variables of floating point type such as 'double' or 'float'.
Definition: double.h:42
This class contains the specification of EPS Bearers.
Definition: eps-bearer.h:91
Qci
QoS Class Indicator.
Definition: eps-bearer.h:106
@ GBR_CONV_VOICE
GBR Conversational Voice.
Definition: eps-bearer.h:107
Hold a signed integer type.
Definition: integer.h:45
void SetTpc(uint32_t tpc, uint32_t num, bool accumulatedMode)
Set transmission power control.
The LteUeNetDevice class implements the UE net device.
Ptr< LteUePhy > GetPhy() const
Get the Phy.
Helper class used to assign positions and mobility models to nodes.
Keep track of the current position and velocity of an object.
void SetPosition(const Vector &position)
holds a vector of ns3::NetDevice pointers
Ptr< NetDevice > Get(uint32_t i) const
Get the Ptr<NetDevice> stored in this container at a given index.
keep track of a set of node pointers.
void Create(uint32_t n)
Create n nodes and append pointers to them to the end of this NodeContainer.
Ptr< Node > Get(uint32_t i) const
Get the Ptr<Node> stored in this container at a given index.
bool TraceConnectWithoutContext(std::string name, const CallbackBase &cb)
Connect a TraceSource to a Callback without a context.
Definition: object-base.cc:322
Ptr< T > GetObject() const
Get a pointer to the requested aggregated Object.
Definition: object.h:522
AttributeValue implementation for Pointer.
Definition: pointer.h:48
Ptr< Object > GetObject() const
Get the Object referenced by the PointerValue.
Definition: pointer.cc:57
Ptr< T > Get() const
Definition: pointer.h:234
Smart pointer class similar to boost::intrusive_ptr.
Definition: ptr.h:77
static EventId Schedule(const Time &delay, FUNC f, Ts &&... args)
Schedule an event to expire after delay.
Definition: simulator.h:571
static void Destroy()
Execute the events scheduled with ScheduleDestroy().
Definition: simulator.cc:142
static Time Now()
Return the current simulation virtual time.
Definition: simulator.cc:208
static void Run()
Run the simulation.
Definition: simulator.cc:178
static void Stop()
Tell the Simulator the calling event should be the last one executed.
Definition: simulator.cc:186
encapsulates test code
Definition: test.h:1061
void AddTestCase(TestCase *testCase, Duration duration=Duration::QUICK)
Add an individual child TestCase to this test suite.
Definition: test.cc:301
A suite of tests to run.
Definition: test.h:1268
Type
Type of test.
Definition: test.h:1275
Hold an unsigned integer type.
Definition: uinteger.h:45
void Reset()
Reset the initial value of every attribute as well as the value of every global to what they were bef...
Definition: config.cc:859
void SetDefault(std::string name, const AttributeValue &value)
Definition: config.cc:894
#define NS_LOG_COMPONENT_DEFINE(name)
Define a Log component with a specific name.
Definition: log.h:202
#define NS_LOG_DEBUG(msg)
Use NS_LOG to output a message of level LOG_DEBUG.
Definition: log.h:268
#define NS_LOG_FUNCTION(parameters)
If log level LOG_FUNCTION is enabled, this macro will output all input parameters separated by ",...
#define NS_LOG_INFO(msg)
Use NS_LOG to output a message of level LOG_INFO.
Definition: log.h:275
static LteUplinkPowerControlTestSuite lteUplinkPowerControlTestSuite
Static variable for test initialization.
auto MakeBoundCallback(R(*fnPtr)(Args...), BArgs &&... bargs)
Make Callbacks with varying number of bound arguments.
Definition: callback.h:765
#define NS_TEST_ASSERT_MSG_EQ_TOL(actual, limit, tol, msg)
Test that actual and expected (limit) values are equal to plus or minus some tolerance and report and...
Definition: test.h:338
Time Seconds(double value)
Construct a Time in the indicated unit.
Definition: nstime.h:1326
Time MilliSeconds(uint64_t value)
Construct a Time in the indicated unit.
Definition: nstime.h:1338
Every class exported by the ns3 library is enclosed in the ns3 namespace.