A Discrete-Event Network Simulator
API
Loading...
Searching...
No Matches
three-gpp-propagation-loss-model-test-suite.cc
Go to the documentation of this file.
1/*
2 * Copyright (c) 2019 SIGNET Lab, Department of Information Engineering,
3 * University of Padova
4 *
5 * SPDX-License-Identifier: GPL-2.0-only
6 */
7
8#include "ns3/abort.h"
9#include "ns3/boolean.h"
10#include "ns3/channel-condition-model.h"
11#include "ns3/config.h"
12#include "ns3/constant-position-mobility-model.h"
13#include "ns3/constant-velocity-mobility-model.h"
14#include "ns3/double.h"
15#include "ns3/log.h"
16#include "ns3/mobility-helper.h"
17#include "ns3/simulator.h"
18#include "ns3/test.h"
19#include "ns3/three-gpp-propagation-loss-model.h"
20#include "ns3/three-gpp-v2v-propagation-loss-model.h"
21
22using namespace ns3;
23
24NS_LOG_COMPONENT_DEFINE("ThreeGppPropagationLossModelsTest");
25
26/**
27 * @ingroup propagation-tests
28 *
29 * Test case for the class ThreeGppRmaPropagationLossModel.
30 * It computes the pathloss between two nodes and compares it with the value
31 * obtained using the formula in 3GPP TR 38.901, Table 7.4.1-1.
32 */
34{
35 public:
36 /**
37 * Constructor
38 */
40
41 /**
42 * Destructor
43 */
45
46 private:
47 /**
48 * Build the simulation scenario and run the tests
49 */
50 void DoRun() override;
51
52 /**
53 * Struct containing the parameters for each test
54 */
56 {
57 double m_distance; //!< 2D distance between UT and BS in meters
58 bool m_isLos; //!< if true LOS, if false NLOS
59 double m_frequency; //!< carrier frequency in Hz
60 double m_pt; //!< transmitted power in dBm
61 double m_pr; //!< received power in dBm
62 };
63
64 TestVectors<TestVector> m_testVectors; //!< array containing all the test vectors
65 double m_tolerance; //!< tolerance
66};
67
69 : TestCase("Test for the ThreeGppRmaPropagationLossModel class"),
70 m_testVectors(),
71 m_tolerance(5e-2)
72{
73}
74
78
79void
81{
82 TestVector testVector;
83
84 testVector.m_distance = 10.0;
85 testVector.m_isLos = true;
86 testVector.m_frequency = 5.0e9;
87 testVector.m_pt = 0.0;
88 testVector.m_pr = -77.3784;
89 m_testVectors.Add(testVector);
90
91 testVector.m_distance = 100.0;
92 testVector.m_isLos = true;
93 testVector.m_frequency = 5.0e9;
94 testVector.m_pt = 0.0;
95 testVector.m_pr = -87.2965;
96 m_testVectors.Add(testVector);
97
98 testVector.m_distance = 1000.0;
99 testVector.m_isLos = true;
100 testVector.m_frequency = 5.0e9;
101 testVector.m_pt = 0.0;
102 testVector.m_pr = -108.5577;
103 m_testVectors.Add(testVector);
104
105 testVector.m_distance = 10000.0;
106 testVector.m_isLos = true;
107 testVector.m_frequency = 5.0e9;
108 testVector.m_pt = 0.0;
109 testVector.m_pr = -140.3896;
110 m_testVectors.Add(testVector);
111
112 testVector.m_distance = 10.0;
113 testVector.m_isLos = false;
114 testVector.m_frequency = 5.0e9;
115 testVector.m_pt = 0.0;
116 testVector.m_pr = -77.3784;
117 m_testVectors.Add(testVector);
118
119 testVector.m_distance = 100.0;
120 testVector.m_isLos = false;
121 testVector.m_frequency = 5.0e9;
122 testVector.m_pt = 0.0;
123 testVector.m_pr = -95.7718;
124 m_testVectors.Add(testVector);
125
126 testVector.m_distance = 1000.0;
127 testVector.m_isLos = false;
128 testVector.m_frequency = 5.0e9;
129 testVector.m_pt = 0.0;
130 testVector.m_pr = -133.5223;
131 m_testVectors.Add(testVector);
132
133 testVector.m_distance = 5000.0;
134 testVector.m_isLos = false;
135 testVector.m_frequency = 5.0e9;
136 testVector.m_pt = 0.0;
137 testVector.m_pr = -160.5169;
138 m_testVectors.Add(testVector);
139
140 // Create the nodes for BS and UT
142 nodes.Create(2);
143
144 // Create the mobility models
149
150 // Use a deterministic channel condition model
153
154 // Create the propagation loss model
157 lossModel->SetAttribute("ShadowingEnabled", BooleanValue(false)); // disable the shadow fading
158
159 for (const auto& testVector : m_testVectors)
160 {
161 Vector posBs = Vector(0.0, 0.0, 35.0);
162 Vector posUt = Vector(testVector.m_distance, 0.0, 1.5);
163
164 // set the LOS or NLOS condition
165 if (testVector.m_isLos)
166 {
167 lossModel->SetChannelConditionModel(losCondModel);
168 }
169 else
170 {
171 lossModel->SetChannelConditionModel(nlosCondModel);
172 }
173
174 a->SetPosition(posBs);
175 b->SetPosition(posUt);
176
177 lossModel->SetAttribute("Frequency", DoubleValue(testVector.m_frequency));
178 NS_TEST_EXPECT_MSG_EQ_TOL(lossModel->CalcRxPower(testVector.m_pt, a, b),
179 testVector.m_pr,
181 "Got unexpected rcv power");
182 }
183
185}
186
187/**
188 * @ingroup propagation-tests
189 *
190 * Test case for the class ThreeGppUmaPropagationLossModel.
191 * It computes the pathloss between two nodes and compares it with the value
192 * obtained using the formula in 3GPP TR 38.901, Table 7.4.1-1.
193 */
195{
196 public:
197 /**
198 * Constructor
199 */
201
202 /**
203 * Destructor
204 */
206
207 private:
208 /**
209 * Build the simulation scenario and run the tests
210 */
211 void DoRun() override;
212
213 /**
214 * Struct containing the parameters for each test
215 */
217 {
218 double m_distance; //!< 2D distance between UT and BS in meters
219 bool m_isLos; //!< if true LOS, if false NLOS
220 double m_frequency; //!< carrier frequency in Hz
221 double m_pt; //!< transmitted power in dBm
222 double m_pr; //!< received power in dBm
223 };
224
225 TestVectors<TestVector> m_testVectors; //!< array containing all the test vectors
226 double m_tolerance; //!< tolerance
227};
228
230 : TestCase("Test for the ThreeGppUmaPropagationLossModel class"),
231 m_testVectors(),
232 m_tolerance(5e-2)
233{
234}
235
239
240void
242{
243 TestVector testVector;
244
245 testVector.m_distance = 10.0;
246 testVector.m_isLos = true;
247 testVector.m_frequency = 5.0e9;
248 testVector.m_pt = 0.0;
249 testVector.m_pr = -72.9380;
250 m_testVectors.Add(testVector);
251
252 testVector.m_distance = 100.0;
253 testVector.m_isLos = true;
254 testVector.m_frequency = 5.0e9;
255 testVector.m_pt = 0.0;
256 testVector.m_pr = -86.2362;
257 m_testVectors.Add(testVector);
258
259 testVector.m_distance = 1000.0;
260 testVector.m_isLos = true;
261 testVector.m_frequency = 5.0e9;
262 testVector.m_pt = 0.0;
263 testVector.m_pr = -109.7252;
264 m_testVectors.Add(testVector);
265
266 testVector.m_distance = 5000.0;
267 testVector.m_isLos = true;
268 testVector.m_frequency = 5.0e9;
269 testVector.m_pt = 0.0;
270 testVector.m_pr = -137.6794;
271 m_testVectors.Add(testVector);
272
273 testVector.m_distance = 10.0;
274 testVector.m_isLos = false;
275 testVector.m_frequency = 5.0e9;
276 testVector.m_pt = 0.0;
277 testVector.m_pr = -82.5131;
278 m_testVectors.Add(testVector);
279
280 testVector.m_distance = 100.0;
281 testVector.m_isLos = false;
282 testVector.m_frequency = 5.0e9;
283 testVector.m_pt = 0.0;
284 testVector.m_pr = -106.1356;
285 m_testVectors.Add(testVector);
286
287 testVector.m_distance = 1000.0;
288 testVector.m_isLos = false;
289 testVector.m_frequency = 5.0e9;
290 testVector.m_pt = 0.0;
291 testVector.m_pr = -144.7641;
292 m_testVectors.Add(testVector);
293
294 testVector.m_distance = 5000.0;
295 testVector.m_isLos = false;
296 testVector.m_frequency = 5.0e9;
297 testVector.m_pt = 0.0;
298 testVector.m_pr = -172.0753;
299 m_testVectors.Add(testVector);
300
301 // Create the nodes for BS and UT
303 nodes.Create(2);
304
305 // Create the mobility models
310
311 // Use a deterministic channel condition model
314
315 // Create the propagation loss model
318 lossModel->SetAttribute("ShadowingEnabled", BooleanValue(false)); // disable the shadow fading
319
320 for (std::size_t i = 0; i < m_testVectors.GetN(); i++)
321 {
322 TestVector testVector = m_testVectors.Get(i);
323
324 Vector posBs = Vector(0.0, 0.0, 25.0);
325 Vector posUt = Vector(testVector.m_distance, 0.0, 1.5);
326
327 // set the LOS or NLOS condition
328 if (testVector.m_isLos)
329 {
330 lossModel->SetChannelConditionModel(losCondModel);
331 }
332 else
333 {
334 lossModel->SetChannelConditionModel(nlosCondModel);
335 }
336
337 a->SetPosition(posBs);
338 b->SetPosition(posUt);
339
340 lossModel->SetAttribute("Frequency", DoubleValue(testVector.m_frequency));
341 NS_TEST_EXPECT_MSG_EQ_TOL(lossModel->CalcRxPower(testVector.m_pt, a, b),
342 testVector.m_pr,
344 "Got unexpected rcv power");
345 }
346
348}
349
350/**
351 * @ingroup propagation-tests
352 *
353 * Test case for the class ThreeGppUmiStreetCanyonPropagationLossModel.
354 * It computes the pathloss between two nodes and compares it with the value
355 * obtained using the formula in 3GPP TR 38.901, Table 7.4.1-1.
356 */
358{
359 public:
360 /**
361 * Constructor
362 */
364
365 /**
366 * Destructor
367 */
369
370 private:
371 /**
372 * Build the simulation scenario and run the tests
373 */
374 void DoRun() override;
375
376 /**
377 * Struct containing the parameters for each test
378 */
380 {
381 double m_distance; //!< 2D distance between UT and BS in meters
382 bool m_isLos; //!< if true LOS, if false NLOS
383 double m_frequency; //!< carrier frequency in Hz
384 double m_pt; //!< transmitted power in dBm
385 double m_pr; //!< received power in dBm
386 };
387
388 TestVectors<TestVector> m_testVectors; //!< array containing all the test vectors
389 double m_tolerance; //!< tolerance
390};
391
393 : TestCase("Test for the ThreeGppUmiPropagationLossModel class"),
394 m_testVectors(),
395 m_tolerance(5e-2)
396{
397}
398
402
403void
405{
406 TestVector testVector;
407
408 testVector.m_distance = 10.0;
409 testVector.m_isLos = true;
410 testVector.m_frequency = 5.0e9;
411 testVector.m_pt = 0.0;
412 testVector.m_pr = -69.8591;
413 m_testVectors.Add(testVector);
414
415 testVector.m_distance = 100.0;
416 testVector.m_isLos = true;
417 testVector.m_frequency = 5.0e9;
418 testVector.m_pt = 0.0;
419 testVector.m_pr = -88.4122;
420 m_testVectors.Add(testVector);
421
422 testVector.m_distance = 1000.0;
423 testVector.m_isLos = true;
424 testVector.m_frequency = 5.0e9;
425 testVector.m_pt = 0.0;
426 testVector.m_pr = -119.3114;
427
428 testVector.m_distance = 5000.0;
429 testVector.m_isLos = true;
430 testVector.m_frequency = 5.0e9;
431 testVector.m_pt = 0.0;
432 testVector.m_pr = -147.2696;
433
434 testVector.m_distance = 10.0;
435 testVector.m_isLos = false;
436 testVector.m_frequency = 5.0e9;
437 testVector.m_pt = 0.0;
438 testVector.m_pr = -76.7563;
439
440 testVector.m_distance = 100.0;
441 testVector.m_isLos = false;
442 testVector.m_frequency = 5.0e9;
443 testVector.m_pt = 0.0;
444 testVector.m_pr = -107.9432;
445
446 testVector.m_distance = 1000.0;
447 testVector.m_isLos = false;
448 testVector.m_frequency = 5.0e9;
449 testVector.m_pt = 0.0;
450 testVector.m_pr = -143.1886;
451
452 testVector.m_distance = 5000.0;
453 testVector.m_isLos = false;
454 testVector.m_frequency = 5.0e9;
455 testVector.m_pt = 0.0;
456 testVector.m_pr = -167.8617;
457
458 // Create the nodes for BS and UT
460 nodes.Create(2);
461
462 // Create the mobility models
467
468 // Use a deterministic channel condition model
471
472 // Create the propagation loss model
475 lossModel->SetAttribute("ShadowingEnabled", BooleanValue(false)); // disable the shadow fading
476
477 for (std::size_t i = 0; i < m_testVectors.GetN(); i++)
478 {
479 TestVector testVector = m_testVectors.Get(i);
480
481 Vector posBs = Vector(0.0, 0.0, 10.0);
482 Vector posUt = Vector(testVector.m_distance, 0.0, 1.5);
483
484 // set the LOS or NLOS condition
485 if (testVector.m_isLos)
486 {
487 lossModel->SetChannelConditionModel(losCondModel);
488 }
489 else
490 {
491 lossModel->SetChannelConditionModel(nlosCondModel);
492 }
493
494 a->SetPosition(posBs);
495 b->SetPosition(posUt);
496
497 lossModel->SetAttribute("Frequency", DoubleValue(testVector.m_frequency));
498 NS_TEST_EXPECT_MSG_EQ_TOL(lossModel->CalcRxPower(testVector.m_pt, a, b),
499 testVector.m_pr,
501 "Got unexpected rcv power");
502 }
503
505}
506
507/**
508 * @ingroup propagation-tests
509 *
510 * Test case for the class ThreeGppIndoorOfficePropagationLossModel.
511 * It computes the pathloss between two nodes and compares it with the value
512 * obtained using the formula in 3GPP TR 38.901, Table 7.4.1-1.
513 */
515{
516 public:
517 /**
518 * Constructor
519 */
521
522 /**
523 * Destructor
524 */
526
527 private:
528 /**
529 * Build the simulation scenario and run the tests
530 */
531 void DoRun() override;
532
533 /**
534 * Struct containing the parameters for each test
535 */
537 {
538 double m_distance; //!< 2D distance between UT and BS in meters
539 bool m_isLos; //!< if true LOS, if false NLOS
540 double m_frequency; //!< carrier frequency in Hz
541 double m_pt; //!< transmitted power in dBm
542 double m_pr; //!< received power in dBm
543 };
544
545 TestVectors<TestVector> m_testVectors; //!< array containing all the test vectors
546 double m_tolerance; //!< tolerance
547};
548
550 : TestCase("Test for the ThreeGppIndoorOfficePropagationLossModel class"),
551 m_testVectors(),
552 m_tolerance(5e-2)
553{
554}
555
560
561void
563{
564 TestVector testVector;
565
566 testVector.m_distance = 1.0;
567 testVector.m_isLos = true;
568 testVector.m_frequency = 5.0e9;
569 testVector.m_pt = 0.0;
570 testVector.m_pr = -50.8072;
571 m_testVectors.Add(testVector);
572
573 testVector.m_distance = 10.0;
574 testVector.m_isLos = true;
575 testVector.m_frequency = 5.0e9;
576 testVector.m_pt = 0.0;
577 testVector.m_pr = -63.7630;
578 m_testVectors.Add(testVector);
579
580 testVector.m_distance = 50.0;
581 testVector.m_isLos = true;
582 testVector.m_frequency = 5.0e9;
583 testVector.m_pt = 0.0;
584 testVector.m_pr = -75.7750;
585 m_testVectors.Add(testVector);
586
587 testVector.m_distance = 100.0;
588 testVector.m_isLos = true;
589 testVector.m_frequency = 5.0e9;
590 testVector.m_pt = 0.0;
591 testVector.m_pr = -80.9802;
592 m_testVectors.Add(testVector);
593
594 testVector.m_distance = 1.0;
595 testVector.m_isLos = false;
596 testVector.m_frequency = 5.0e9;
597 testVector.m_pt = 0.0;
598 testVector.m_pr = -50.8072;
599 m_testVectors.Add(testVector);
600
601 testVector.m_distance = 10.0;
602 testVector.m_isLos = false;
603 testVector.m_frequency = 5.0e9;
604 testVector.m_pt = 0.0;
605 testVector.m_pr = -73.1894;
606 m_testVectors.Add(testVector);
607
608 testVector.m_distance = 50.0;
609 testVector.m_isLos = false;
610 testVector.m_frequency = 5.0e9;
611 testVector.m_pt = 0.0;
612 testVector.m_pr = -99.7824;
613 m_testVectors.Add(testVector);
614
615 testVector.m_distance = 100.0;
616 testVector.m_isLos = false;
617 testVector.m_frequency = 5.0e9;
618 testVector.m_pt = 0.0;
619 testVector.m_pr = -111.3062;
620 m_testVectors.Add(testVector);
621
622 // Create the nodes for BS and UT
624 nodes.Create(2);
625
626 // Create the mobility models
631
632 // Use a deterministic channel condition model
635
636 // Create the propagation loss model
639 lossModel->SetAttribute("ShadowingEnabled", BooleanValue(false)); // disable the shadow fading
640
641 for (std::size_t i = 0; i < m_testVectors.GetN(); i++)
642 {
643 TestVector testVector = m_testVectors.Get(i);
644
645 Vector posBs = Vector(0.0, 0.0, 3.0);
646 Vector posUt = Vector(testVector.m_distance, 0.0, 1.5);
647
648 // set the LOS or NLOS condition
649 if (testVector.m_isLos)
650 {
651 lossModel->SetChannelConditionModel(losCondModel);
652 }
653 else
654 {
655 lossModel->SetChannelConditionModel(nlosCondModel);
656 }
657
658 a->SetPosition(posBs);
659 b->SetPosition(posUt);
660
661 lossModel->SetAttribute("Frequency", DoubleValue(testVector.m_frequency));
662 NS_TEST_EXPECT_MSG_EQ_TOL(lossModel->CalcRxPower(testVector.m_pt, a, b),
663 testVector.m_pr,
665 "Got unexpected rcv power");
666 }
667
669}
670
671/**
672 * @ingroup propagation-tests
673 *
674 * Test case for the class ThreeGppV2vUrbanPropagationLossModel.
675 * It computes the pathloss between two nodes and compares it with the value
676 * obtained using the formula in 3GPP TR 37.885 Table 6.2.1-1 for v2v
677 * communications (sidelink).
678 *
679 * Note that 3GPP TR 37.885 defines 3 different channel states for vehicular
680 * environments: LOS, NLOS, and NLOSv, the latter representing the case in which
681 * the LOS path is blocked by other vehicles in the scenario. However, for
682 * computing the pathloss, only the two states are considered: LOS/NLOSv or NLOS
683 * (see TR 37.885 Section 6.2.1). In case of NLOSv, an additional vehicle
684 * blockage loss may be added, according to a log-normal random variable.
685 * Here, we test both conditions: LOS/NLOSv (without vehicle blockage
686 * loss) and NLOS.
687 */
689{
690 public:
691 /**
692 * Constructor
693 */
695
696 /**
697 * Destructor
698 */
700
701 private:
702 /**
703 * Build the simulation scenario and run the tests
704 */
705 void DoRun() override;
706
707 /**
708 * Struct containing the parameters for each test
709 */
711 {
712 double m_distance; //!< 2D distance between UT and BS in meters
713 bool m_isLos; //!< if true LOS/NLOSv, if false NLOS
714 double m_frequency; //!< carrier frequency in Hz
715 double m_pt; //!< transmitted power in dBm
716 double m_pr; //!< received power in dBm
717 };
718
719 TestVectors<TestVector> m_testVectors; //!< array containing all the test vectors
720 double m_tolerance; //!< tolerance
721};
722
724 : TestCase("Test for the ThreeGppV2vUrbanPropagationLossModel class."),
725 m_testVectors(),
726 m_tolerance(5e-2)
727{
728}
729
733
734void
736{
737 TestVector testVector;
738
739 testVector.m_distance = 10.0;
740 testVector.m_isLos = true;
741 testVector.m_frequency = 5.0e9;
742 testVector.m_pt = 0.0;
743 testVector.m_pr = -68.1913;
744 m_testVectors.Add(testVector);
745
746 testVector.m_distance = 100.0;
747 testVector.m_isLos = true;
748 testVector.m_frequency = 5.0e9;
749 testVector.m_pt = 0.0;
750 testVector.m_pr = -84.8913;
751 m_testVectors.Add(testVector);
752
753 testVector.m_distance = 1000.0;
754 testVector.m_isLos = true;
755 testVector.m_frequency = 5.0e9;
756 testVector.m_pt = 0.0;
757 testVector.m_pr = -101.5913;
758 m_testVectors.Add(testVector);
759
760 testVector.m_distance = 10.0;
761 testVector.m_isLos = false;
762 testVector.m_frequency = 5.0e9;
763 testVector.m_pt = 0.0;
764 testVector.m_pr = -80.0605;
765 m_testVectors.Add(testVector);
766
767 testVector.m_distance = 100.0;
768 testVector.m_isLos = false;
769 testVector.m_frequency = 5.0e9;
770 testVector.m_pt = 0.0;
771 testVector.m_pr = -110.0605;
772 m_testVectors.Add(testVector);
773
774 testVector.m_distance = 1000.0;
775 testVector.m_isLos = false;
776 testVector.m_frequency = 5.0e9;
777 testVector.m_pt = 0.0;
778 testVector.m_pr = -140.0605;
779 m_testVectors.Add(testVector);
780
781 // Create the nodes for BS and UT
783 nodes.Create(2);
784
785 // Create the mobility models
790
791 // Use a deterministic channel condition model
794
795 // Create the propagation loss model
798 lossModel->SetAttribute("ShadowingEnabled", BooleanValue(false)); // disable the shadow fading
799
800 for (std::size_t i = 0; i < m_testVectors.GetN(); i++)
801 {
802 TestVector testVector = m_testVectors.Get(i);
803
804 Vector posUe1 = Vector(0.0, 0.0, 1.6);
805 Vector posUe2 = Vector(testVector.m_distance, 0.0, 1.6);
806
807 // set the LOS or NLOS condition
808 if (testVector.m_isLos)
809 {
810 lossModel->SetChannelConditionModel(losCondModel);
811 }
812 else
813 {
814 lossModel->SetChannelConditionModel(nlosCondModel);
815 }
816
817 a->SetPosition(posUe1);
818 b->SetPosition(posUe2);
819
820 lossModel->SetAttribute("Frequency", DoubleValue(testVector.m_frequency));
821 NS_TEST_EXPECT_MSG_EQ_TOL(lossModel->CalcRxPower(testVector.m_pt, a, b),
822 testVector.m_pr,
824 "Got unexpected rcv power");
825 }
826
828}
829
830/**
831 * @ingroup propagation-tests
832 *
833 * Test case for the class ThreeGppV2vHighwayPropagationLossModel.
834 * It computes the pathloss between two nodes and compares it with the value
835 * obtained using the formula in 3GPP TR 37.885 Table 6.2.1-1 for v2v
836 * communications (sidelink).
837 *
838 * Note that 3GPP TR 37.885 defines 3 different channel states for vehicular
839 * environments: LOS, NLOS and NLOSv, the latter representing the case in which
840 * the LOS path is blocked by other vehicles in the scenario. However, for
841 * computing the pathloss, only two states are considered: LOS/NLOSv or NLOS
842 * (see TR 37.885 Section 6.2.1). In case of NLOSv, an additional vehicle
843 * blockage loss may be added, according to a log-normal random variable.
844 * Here, we test both conditions: LOS/NLOSv (without vehicle blockage
845 * loss) and NLOS.
846 */
848{
849 public:
850 /**
851 * Constructor
852 */
854
855 /**
856 * Destructor
857 */
859
860 private:
861 /**
862 * Build the simulation scenario and run the tests
863 */
864 void DoRun() override;
865
866 /**
867 * Struct containing the parameters for each test
868 */
870 {
871 double m_distance; //!< 2D distance between UT and BS in meters
872 bool m_isLos; //!< if true LOS/NLOSv, if false NLOS
873 double m_frequency; //!< carrier frequency in Hz
874 double m_pt; //!< transmitted power in dBm
875 double m_pr; //!< received power in dBm
876 };
877
878 TestVectors<TestVector> m_testVectors; //!< array containing all the test vectors
879 double m_tolerance; //!< tolerance
880};
881
883 : TestCase("Test for the ThreeGppV2vHighwayPropagationLossModel"),
884 m_testVectors(),
885 m_tolerance(5e-2)
886{
887}
888
892
893void
895{
896 TestVector testVector;
897
898 testVector.m_distance = 10.0;
899 testVector.m_isLos = true;
900 testVector.m_frequency = 5.0e9;
901 testVector.m_pt = 0.0;
902 testVector.m_pr = -66.3794;
903 m_testVectors.Add(testVector);
904
905 testVector.m_distance = 100.0;
906 testVector.m_isLos = true;
907 testVector.m_frequency = 5.0e9;
908 testVector.m_pt = 0.0;
909 testVector.m_pr = -86.3794;
910 m_testVectors.Add(testVector);
911
912 testVector.m_distance = 1000.0;
913 testVector.m_isLos = true;
914 testVector.m_frequency = 5.0e9;
915 testVector.m_pt = 0.0;
916 testVector.m_pr = -106.3794;
917 m_testVectors.Add(testVector);
918
919 testVector.m_distance = 10.0;
920 testVector.m_isLos = false;
921 testVector.m_frequency = 5.0e9;
922 testVector.m_pt = 0.0;
923 testVector.m_pr = -80.0605;
924 m_testVectors.Add(testVector);
925
926 testVector.m_distance = 100.0;
927 testVector.m_isLos = false;
928 testVector.m_frequency = 5.0e9;
929 testVector.m_pt = 0.0;
930 testVector.m_pr = -110.0605;
931 m_testVectors.Add(testVector);
932
933 testVector.m_distance = 1000.0;
934 testVector.m_isLos = false;
935 testVector.m_frequency = 5.0e9;
936 testVector.m_pt = 0.0;
937 testVector.m_pr = -140.0605;
938 m_testVectors.Add(testVector);
939
940 // Create the nodes for BS and UT
942 nodes.Create(2);
943
944 // Create the mobility models
949
950 // Use a deterministic channel condition model
953
954 // Create the propagation loss model
957 lossModel->SetAttribute("ShadowingEnabled", BooleanValue(false)); // disable the shadow fading
958
959 for (std::size_t i = 0; i < m_testVectors.GetN(); i++)
960 {
961 TestVector testVector = m_testVectors.Get(i);
962
963 Vector posUe1 = Vector(0.0, 0.0, 1.6);
964 Vector posUe2 = Vector(testVector.m_distance, 0.0, 1.6);
965
966 // set the LOS or NLOS condition
967 if (testVector.m_isLos)
968 {
969 lossModel->SetChannelConditionModel(losCondModel);
970 }
971 else
972 {
973 lossModel->SetChannelConditionModel(nlosCondModel);
974 }
975
976 a->SetPosition(posUe1);
977 b->SetPosition(posUe2);
978
979 lossModel->SetAttribute("Frequency", DoubleValue(testVector.m_frequency));
980 NS_TEST_EXPECT_MSG_EQ_TOL(lossModel->CalcRxPower(testVector.m_pt, a, b),
981 testVector.m_pr,
983 "Got unexpected rcv power");
984 }
985
987}
988
989/**
990 * @ingroup propagation-tests
991 *
992 * Test to check if the shadowing fading is correctly computed
993 */
995{
996 public:
999
1000 private:
1001 void DoRun() override;
1002
1003 /**
1004 * Run the experiment
1005 * @param testNum the index of the experiment
1006 * @param propagationLossModelType the type id of the propagation loss model
1007 * to be used
1008 * @param hBs the BS height in meters
1009 * @param hUt the UT height in meters
1010 * @param distance the initial distance between the BS and the UT
1011 * @param shadowingEnabled true if shadowging must be enabled
1012 */
1013 void RunTest(uint16_t testNum,
1014 std::string propagationLossModelType,
1015 double hBs,
1016 double hUt,
1017 double distance,
1018 bool shadowingEnabled);
1019
1020 /**
1021 * Compute the propagation loss
1022 * @param a the first mobility model
1023 * @param b the second mobility model
1024 * @param testNum the index of the experiment
1025 */
1026 void EvaluateLoss(Ptr<MobilityModel> a, Ptr<MobilityModel> b, uint8_t testNum);
1027
1028 /**
1029 * Change the channel condition model
1030 * @param ccm the new ChannelConditionModel
1031 */
1033
1034 /**
1035 * Struct containing the parameters for each test
1036 */
1038 {
1039 std::string m_propagationLossModelType; //!< the propagation loss model type id
1040 double m_hBs; //!< the BS height in meters
1041 double m_hUt; //!< the UT height in meters
1042 double m_distance; //!< the initial 2D distance in meters between BS and UT in meters
1043 double m_shadowingStdLos; //!< the standard deviation of the shadowing component in the LOS
1044 //!< case in dB
1045 double m_shadowingStdNlos; //!< the standard deviation of the shadowing component in the
1046 //!< NLOS case in dB
1047 };
1048
1049 TestVectors<TestVector> m_testVectors; //!< array containing all the test vectors
1050 Ptr<ThreeGppPropagationLossModel> m_lossModel; //!< the propagation loss model
1051 std::map<uint16_t /* index of experiment */, std::vector<double> /* loss in dB for each run */>
1052 m_results; //!< used to store the test results
1053};
1054
1056 : TestCase("Test to check if the shadow fading is correctly computed")
1057{
1058}
1059
1063
1064void
1066{
1067 double loss = m_lossModel->CalcRxPower(0, a, b);
1068 m_results.at(testNum).push_back(loss);
1069}
1070
1071void
1076
1077void
1079 std::string propagationLossModelType,
1080 double hBs,
1081 double hUt,
1082 double distance,
1083 bool shadowingEnabled)
1084{
1085 // Add a new entry for this test in the results map
1086 m_results[testNum] = std::vector<double>();
1087
1088 // Create the nodes for BS and UT
1090 nodes.Create(2);
1091
1092 // Create the mobility models
1094 a->SetPosition(Vector(0.0, 0.0, hBs));
1095 nodes.Get(0)->AggregateObject(a);
1096
1098 nodes.Get(1)->AggregateObject(b);
1099 b->SetPosition(Vector(0.0, distance, hUt));
1100 b->SetVelocity(Vector(1.0, 0.0, 0.0));
1101
1102 // Create the propagation loss model
1103 ObjectFactory propagationLossModelFactory = ObjectFactory(propagationLossModelType);
1104 m_lossModel = propagationLossModelFactory.Create<ThreeGppPropagationLossModel>();
1105 m_lossModel->SetAttribute("Frequency", DoubleValue(3.5e9));
1106 m_lossModel->SetAttribute("ShadowingEnabled",
1107 BooleanValue(shadowingEnabled)); // enable the shadow fading
1108
1109 // Set the channel condition to LOS
1111 m_lossModel->SetChannelConditionModel(losCondModel);
1112 // Schedule a transition to NLOS
1116 this,
1117 nlosCondModel);
1118
1119 // Schedule multiple calls to EvaluateLoss. Use both EvaluateLoss (a,b) and
1120 // EvaluateLoss (b,a) to check if the reciprocity holds.
1121 for (int i = 0; i < 200; i++)
1122 {
1123 if (i % 2 == 0)
1124 {
1127 this,
1128 a,
1129 b,
1130 testNum);
1131 }
1132 else
1133 {
1136 this,
1137 b,
1138 a,
1139 testNum);
1140 }
1141 }
1142
1145}
1146
1147void
1149{
1150 // The test scenario is composed of two nodes, one fixed
1151 // at position (0,0) and the other moving with constant velocity from
1152 // position (0,50) to position (200,50).
1153 // The channel condition changes from LOS to NLOS when the second node
1154 // reaches position (100,50).
1155 // Each experiment computes the propagation loss between the two nodes
1156 // every second, until the final position is reached, and saves the
1157 // results in an entry of the map m_results.
1158 // We run numSamples experiments and estimate the mean propagation loss in
1159 // each position by averaging among the samples.
1160 // Then, we perform the null hypothesis test with a significance level of
1161 // 0.05.
1162 // This procedure is repeated for all the 3GPP propagation scenarios, i.e.,
1163 // RMa, UMa, UMi and Indoor-Office.
1164
1165 TestVector testVector;
1166 testVector.m_propagationLossModelType = "ns3::ThreeGppRmaPropagationLossModel";
1167 testVector.m_hBs = 25;
1168 testVector.m_hUt = 1.6;
1169 testVector.m_distance = 100;
1170 testVector.m_shadowingStdLos = 4;
1171 testVector.m_shadowingStdNlos = 8;
1172 m_testVectors.Add(testVector);
1173
1174 testVector.m_propagationLossModelType = "ns3::ThreeGppRmaPropagationLossModel";
1175 testVector.m_hBs = 25;
1176 testVector.m_hUt = 1.6;
1177 testVector.m_distance = 4000; // beyond the breakpoint distance
1178 testVector.m_shadowingStdLos = 6;
1179 testVector.m_shadowingStdNlos = 8;
1180 m_testVectors.Add(testVector);
1181
1182 testVector.m_propagationLossModelType = "ns3::ThreeGppUmaPropagationLossModel";
1183 testVector.m_hBs = 25;
1184 testVector.m_hUt = 1.6;
1185 testVector.m_distance = 100;
1186 testVector.m_shadowingStdLos = 4;
1187 testVector.m_shadowingStdNlos = 6;
1188 m_testVectors.Add(testVector);
1189
1190 testVector.m_propagationLossModelType = "ns3::ThreeGppUmiStreetCanyonPropagationLossModel";
1191 testVector.m_hBs = 10;
1192 testVector.m_hUt = 1.6;
1193 testVector.m_distance = 100;
1194 testVector.m_shadowingStdLos = 4;
1195 testVector.m_shadowingStdNlos = 7.82;
1196 m_testVectors.Add(testVector);
1197
1198 testVector.m_propagationLossModelType = "ns3::ThreeGppIndoorOfficePropagationLossModel";
1199 testVector.m_hBs = 3;
1200 testVector.m_hUt = 1;
1201 testVector.m_distance = 50;
1202 testVector.m_shadowingStdLos = 3;
1203 testVector.m_shadowingStdNlos = 8.03;
1204 m_testVectors.Add(testVector);
1205
1206 testVector.m_propagationLossModelType = "ns3::ThreeGppV2vUrbanPropagationLossModel";
1207 testVector.m_hBs = 1.6;
1208 testVector.m_hUt = 1.6;
1209 testVector.m_distance = 50;
1210 testVector.m_shadowingStdLos = 3;
1211 testVector.m_shadowingStdNlos = 4;
1212 m_testVectors.Add(testVector);
1213
1214 testVector.m_propagationLossModelType = "ns3::ThreeGppV2vHighwayPropagationLossModel";
1215 testVector.m_hBs = 1.6;
1216 testVector.m_hUt = 1.6;
1217 testVector.m_distance = 50;
1218 testVector.m_shadowingStdLos = 3;
1219 testVector.m_shadowingStdNlos = 4;
1220 m_testVectors.Add(testVector);
1221
1222 uint16_t numSamples = 250;
1223
1224 for (std::size_t tvIndex = 0; tvIndex < m_testVectors.GetN(); tvIndex++)
1225 {
1226 TestVector tv = m_testVectors.Get(tvIndex);
1227
1228 // run the experiments.
1229 for (uint16_t sampleIndex = 0; sampleIndex < numSamples; sampleIndex++)
1230 {
1231 RunTest(sampleIndex,
1233 tv.m_hBs,
1234 tv.m_hUt,
1235 tv.m_distance,
1236 true);
1237 }
1238
1239 // analyze the results
1240 std::vector<double> mean_vector; // the vector containing the mean propagation loss for each
1241 // position (sample mean)
1242
1243 uint16_t numPositions = m_results.at(0).size();
1244 for (uint16_t k = 0; k < numPositions; k++)
1245 {
1246 // compute the mean propagation loss in position k
1247 double mean = 0.0;
1248 for (auto resIt : m_results)
1249 {
1250 mean += resIt.second.at(k);
1251 }
1252 mean /= m_results.size();
1253 mean_vector.push_back(mean);
1254 }
1255
1256 // compute the true mean - just the pathloss, without the shadowing component
1257 RunTest(numSamples,
1259 tv.m_hBs,
1260 tv.m_hUt,
1261 tv.m_distance,
1262 false);
1263 std::vector<double> true_mean =
1264 m_results.at(numSamples); // the result of the last test is the true mean
1265
1266 // perform the null hypothesis test for the LOS case
1267 // positions from (0, 50) to (99, 50) are LOS
1268 for (std::size_t i = 0; i < mean_vector.size() / 2; i++)
1269 {
1270 double z = (mean_vector.at(i) - true_mean.at(i)) /
1271 (tv.m_shadowingStdLos / std::sqrt(mean_vector.size() / 2));
1273 z,
1274 0.0,
1275 1.96,
1276 "Null hypothesis test (LOS case) for the shadowing component rejected");
1277 }
1278
1279 // perform the null hypothesis test for the NLOS case
1280 // positions from (100, 50) to (199, 50) are NLOS
1281 for (std::size_t i = mean_vector.size() / 2; i < mean_vector.size(); i++)
1282 {
1283 double z = (mean_vector.at(i) - true_mean.at(i)) /
1284 (tv.m_shadowingStdNlos / std::sqrt(mean_vector.size() / 2));
1286 z,
1287 0.0,
1288 1.96,
1289 "Null hypothesis test (NLOS case) for the shadowing component rejected");
1290 }
1291 }
1292}
1293
1294/**
1295 * @ingroup propagation-tests
1296 *
1297 * @brief 3GPP Propagation models TestSuite
1298 *
1299 * This TestSuite tests the following models:
1300 * - ThreeGppRmaPropagationLossModel
1301 * - ThreeGppUmaPropagationLossModel
1302 * - ThreeGppUmiPropagationLossModel
1303 * - ThreeGppIndoorOfficePropagationLossModel
1304 * - ThreeGppV2vUrbanPropagationLossModel
1305 * - ThreeGppV2vHighwayPropagationLossModel
1306 * - ThreeGppShadowing
1307 */
1313
1315 : TestSuite("three-gpp-propagation-loss-model", Type::UNIT)
1316{
1317 AddTestCase(new ThreeGppRmaPropagationLossModelTestCase, TestCase::Duration::QUICK);
1318 AddTestCase(new ThreeGppUmaPropagationLossModelTestCase, TestCase::Duration::QUICK);
1319 AddTestCase(new ThreeGppUmiPropagationLossModelTestCase, TestCase::Duration::QUICK);
1320 AddTestCase(new ThreeGppIndoorOfficePropagationLossModelTestCase, TestCase::Duration::QUICK);
1321 AddTestCase(new ThreeGppV2vUrbanPropagationLossModelTestCase, TestCase::Duration::QUICK);
1322 AddTestCase(new ThreeGppV2vHighwayPropagationLossModelTestCase, TestCase::Duration::QUICK);
1323 AddTestCase(new ThreeGppShadowingTestCase, TestCase::Duration::QUICK);
1324}
1325
1326/// Static variable for test initialization
Test case for the class ThreeGppIndoorOfficePropagationLossModel.
void DoRun() override
Build the simulation scenario and run the tests.
TestVectors< TestVector > m_testVectors
array containing all the test vectors
Test case for the class ThreeGppRmaPropagationLossModel.
void DoRun() override
Build the simulation scenario and run the tests.
TestVectors< TestVector > m_testVectors
array containing all the test vectors
Test to check if the shadowing fading is correctly computed.
void EvaluateLoss(Ptr< MobilityModel > a, Ptr< MobilityModel > b, uint8_t testNum)
Compute the propagation loss.
void DoRun() override
Implementation to actually run this TestCase.
std::map< uint16_t, std::vector< double > > m_results
used to store the test results
void ChangeChannelCondition(Ptr< ChannelConditionModel > ccm)
Change the channel condition model.
Ptr< ThreeGppPropagationLossModel > m_lossModel
the propagation loss model
TestVectors< TestVector > m_testVectors
array containing all the test vectors
void RunTest(uint16_t testNum, std::string propagationLossModelType, double hBs, double hUt, double distance, bool shadowingEnabled)
Run the experiment.
Test case for the class ThreeGppUmaPropagationLossModel.
TestVectors< TestVector > m_testVectors
array containing all the test vectors
void DoRun() override
Build the simulation scenario and run the tests.
Test case for the class ThreeGppUmiStreetCanyonPropagationLossModel.
TestVectors< TestVector > m_testVectors
array containing all the test vectors
void DoRun() override
Build the simulation scenario and run the tests.
Test case for the class ThreeGppV2vHighwayPropagationLossModel.
TestVectors< TestVector > m_testVectors
array containing all the test vectors
void DoRun() override
Build the simulation scenario and run the tests.
Test case for the class ThreeGppV2vUrbanPropagationLossModel.
TestVectors< TestVector > m_testVectors
array containing all the test vectors
void DoRun() override
Build the simulation scenario and run the tests.
AttributeValue implementation for Boolean.
Definition boolean.h:26
This class can be used to hold variables of floating point type such as 'double' or 'float'.
Definition double.h:31
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.
void SetAttribute(std::string name, const AttributeValue &value)
Set a single attribute, raising fatal errors if unsuccessful.
Instantiate subclasses of ns3::Object.
Ptr< Object > Create() const
Create an Object instance of the configured TypeId.
void AggregateObject(Ptr< Object > other)
Aggregate two Objects together.
Definition object.cc:298
Smart pointer class similar to boost::intrusive_ptr.
static EventId Schedule(const Time &delay, FUNC f, Ts &&... args)
Schedule an event to expire after delay.
Definition simulator.h:560
static void Destroy()
Execute the events scheduled with ScheduleDestroy().
Definition simulator.cc:131
static void Run()
Run the simulation.
Definition simulator.cc:167
encapsulates test code
Definition test.h:1050
void AddTestCase(TestCase *testCase, Duration duration=Duration::QUICK)
Add an individual child TestCase to this test suite.
Definition test.cc:292
A suite of tests to run.
Definition test.h:1267
Type
Type of test.
Definition test.h:1274
A simple way to store test vectors (for stimulus or from responses)
Definition test.h:1348
Base class for the 3GPP propagation models.
#define NS_LOG_COMPONENT_DEFINE(name)
Define a Log component with a specific name.
Definition log.h:191
Ptr< T > CreateObject(Args &&... args)
Create an object by type, with varying number of constructor parameters.
Definition object.h:619
#define NS_TEST_EXPECT_MSG_EQ_TOL(actual, limit, tol, msg)
Test that actual and expected (limit) values are equal to plus or minus some tolerance and report if ...
Definition test.h:500
Time Seconds(double value)
Construct a Time in the indicated unit.
Definition nstime.h:1344
Time MilliSeconds(uint64_t value)
Construct a Time in the indicated unit.
Definition nstime.h:1356
NodeContainer nodes
Every class exported by the ns3 library is enclosed in the ns3 namespace.
double m_distance
the initial 2D distance in meters between BS and UT in meters
std::string m_propagationLossModelType
the propagation loss model type id
double m_shadowingStdLos
the standard deviation of the shadowing component in the LOS case in dB
double m_shadowingStdNlos
the standard deviation of the shadowing component in the NLOS case in dB
static ThreeGppPropagationLossModelsTestSuite g_propagationLossModelsTestSuite
Static variable for test initialization.