A Discrete-Event Network Simulator
API
wifi-phy-reception-test.cc
Go to the documentation of this file.
1/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
2/*
3 * Copyright (c) 2018 University of Washington
4 *
5 * This program is free software; you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License version 2 as
7 * published by the Free Software Foundation;
8 *
9 * This program is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 * GNU General Public License for more details.
13 *
14 * You should have received a copy of the GNU General Public License
15 * along with this program; if not, write to the Free Software
16 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
17 *
18 * Author: Sébastien Deronne <sebastien.deronne@gmail.com>
19 */
20
21#include "ns3/log.h"
22#include "ns3/mobility-helper.h"
23#include "ns3/multi-model-spectrum-channel.h"
24#include "ns3/config.h"
25#include "ns3/ap-wifi-mac.h"
26#include "ns3/packet-socket-address.h"
27#include "ns3/packet-socket-client.h"
28#include "ns3/packet-socket-helper.h"
29#include "ns3/packet-socket-server.h"
30#include "ns3/test.h"
31#include "ns3/double.h"
32#include "ns3/boolean.h"
33#include "ns3/pointer.h"
34#include "ns3/rng-seed-manager.h"
35#include "ns3/spectrum-wifi-helper.h"
36#include "ns3/wifi-net-device.h"
37#include "ns3/wifi-spectrum-value-helper.h"
38#include "ns3/spectrum-wifi-phy.h"
39#include "ns3/interference-helper.h"
40#include "ns3/nist-error-rate-model.h"
41#include "ns3/wifi-mac-header.h"
42#include "ns3/ampdu-tag.h"
43#include "ns3/wifi-spectrum-signal-parameters.h"
44#include "ns3/wifi-utils.h"
45#include "ns3/threshold-preamble-detection-model.h"
46#include "ns3/simple-frame-capture-model.h"
47#include "ns3/wifi-mpdu.h"
48#include "ns3/mpdu-aggregator.h"
49#include "ns3/wifi-psdu.h"
50#include "ns3/he-ppdu.h"
51#include "ns3/he-phy.h"
52
53using namespace ns3;
54
55NS_LOG_COMPONENT_DEFINE ("WifiPhyReceptionTest");
56
57static const uint8_t CHANNEL_NUMBER = 36;
58static const uint32_t FREQUENCY = 5180; // MHz
59static const uint16_t CHANNEL_WIDTH = 20; // MHz
60static const uint16_t GUARD_WIDTH = CHANNEL_WIDTH; // MHz (expanded to channel width to model spectrum mask)
61
69{
70public:
73
74protected:
75 void DoSetup (void) override;
76 void DoTeardown (void) override;
82 void SendPacket (double rxPowerDbm);
90 void RxSuccess (Ptr<const WifiPsdu> psdu, RxSignalInfo rxSignalInfo,
91 WifiTxVector txVector, std::vector<bool> statusPerMpdu);
99
100private:
101 void DoRun (void) override;
102
107 void CheckPhyState (WifiPhyState expectedState);
112 void DoCheckPhyState (WifiPhyState expectedState);
118 void CheckRxPacketCount (uint32_t expectedSuccessCount, uint32_t expectedFailureCount);
119
120 uint64_t m_uid;
121};
122
124 : TestCase ("Threshold preamble detection model test when no frame capture model is applied"),
125 m_countRxSuccess (0),
126 m_countRxFailure (0),
127 m_uid (0)
128{
129}
130
131void
133{
134 WifiTxVector txVector = WifiTxVector (HePhy::GetHeMcs7 (), 0, WIFI_PREAMBLE_HE_SU, 800, 1, 1, 0, 20, false);
135
136 Ptr<Packet> pkt = Create<Packet> (1000);
137 WifiMacHeader hdr;
138
140 hdr.SetQosTid (0);
141
142 Ptr<WifiPsdu> psdu = Create<WifiPsdu> (pkt, hdr);
143 Time txDuration = m_phy->CalculateTxDuration (psdu->GetSize (), txVector, m_phy->GetPhyBand ());
144
145 Ptr<WifiPpdu> ppdu = Create<HePpdu> (psdu, txVector, FREQUENCY, txDuration, WIFI_PHY_BAND_5GHZ, m_uid++);
146
147 Ptr<SpectrumValue> txPowerSpectrum = WifiSpectrumValueHelper::CreateHeOfdmTxPowerSpectralDensity (FREQUENCY, CHANNEL_WIDTH, DbmToW (rxPowerDbm), GUARD_WIDTH);
148
149 Ptr<WifiSpectrumSignalParameters> txParams = Create<WifiSpectrumSignalParameters> ();
150 txParams->psd = txPowerSpectrum;
151 txParams->txPhy = 0;
152 txParams->duration = txDuration;
153 txParams->ppdu = ppdu;
154
155 m_phy->StartRx (txParams);
156}
157
158void
160{
161 //This is needed to make sure PHY state will be checked as the last event if a state change occured at the exact same time as the check
162 Simulator::ScheduleNow (&TestThresholdPreambleDetectionWithoutFrameCapture::DoCheckPhyState, this, expectedState);
163}
164
165void
167{
168 WifiPhyState currentState;
169 PointerValue ptr;
170 m_phy->GetAttribute ("State", ptr);
171 Ptr <WifiPhyStateHelper> state = DynamicCast <WifiPhyStateHelper> (ptr.Get<WifiPhyStateHelper> ());
172 currentState = state->GetState ();
173 NS_LOG_FUNCTION (this << currentState);
174 NS_TEST_ASSERT_MSG_EQ (currentState, expectedState, "PHY State " << currentState << " does not match expected state " << expectedState << " at " << Simulator::Now ());
175}
176
177void
179{
180 NS_TEST_ASSERT_MSG_EQ (m_countRxSuccess, expectedSuccessCount, "Didn't receive right number of successful packets");
181 NS_TEST_ASSERT_MSG_EQ (m_countRxFailure, expectedFailureCount, "Didn't receive right number of unsuccessful packets");
182}
183
184void
186 WifiTxVector txVector, std::vector<bool> statusPerMpdu)
187{
188 NS_LOG_FUNCTION (this << *psdu << rxSignalInfo << txVector);
190}
191
192void
194{
195 NS_LOG_FUNCTION (this << *psdu);
197}
198
200{
201 m_phy = 0;
202}
203
204void
206{
207 m_phy = CreateObject<SpectrumWifiPhy> ();
209 Ptr<InterferenceHelper> interferenceHelper = CreateObject<InterferenceHelper> ();
210 m_phy->SetInterferenceHelper (interferenceHelper);
211 Ptr<ErrorRateModel> error = CreateObject<NistErrorRateModel> ();
212 m_phy->SetErrorRateModel (error);
216
217 Ptr<ThresholdPreambleDetectionModel> preambleDetectionModel = CreateObject<ThresholdPreambleDetectionModel> ();
218 preambleDetectionModel->SetAttribute ("Threshold", DoubleValue (4));
219 preambleDetectionModel->SetAttribute ("MinimumRssi", DoubleValue (-82));
220 m_phy->SetPreambleDetectionModel (preambleDetectionModel);
221}
222
223void
225{
226 m_phy->Dispose ();
227 m_phy = 0;
228}
229
230void
232{
233 RngSeedManager::SetSeed (1);
234 RngSeedManager::SetRun (1);
235 int64_t streamNumber = 0;
236 m_phy->AssignStreams (streamNumber);
237
238 //RX power > CCA-ED > CCA-PD
239 double rxPowerDbm = -50;
240
241 // CASE 1: send one packet and check PHY state:
242 // All reception stages should succeed and PHY state should be RX for the duration of the packet minus the time to detect the preamble,
243 // otherwise it should be IDLE.
244
245 Simulator::Schedule (Seconds (1.0), &TestThresholdPreambleDetectionWithoutFrameCapture::SendPacket, this, rxPowerDbm);
246 // At 4us, preamble should be successfully detected and STA PHY STATE should move from IDLE to CCA_BUSY
249 // At 44us, PHY header should be successfully received and STA PHY STATE should move from CCA_BUSY to RX
252 // Since it takes 152.8us to transmit the packet, PHY should be back to IDLE at time 152.8us
255 // Packet should have been successfully received
257
258 // CASE 2: send two packets with same power within the 4us window and check PHY state:
259 // PHY preamble detection should fail because SNR is too low (around 0 dB, which is lower than the threshold of 4 dB),
260 // and PHY state should be CCA_BUSY since the total energy is above CCA-ED (-62 dBm).
261 // CCA_BUSY state should last for the duration of the two packets minus the time to detect the preamble.
262
263 Simulator::Schedule (Seconds (2.0), &TestThresholdPreambleDetectionWithoutFrameCapture::SendPacket, this, rxPowerDbm);
264 Simulator::Schedule (Seconds (2.0) + MicroSeconds (2.0), &TestThresholdPreambleDetectionWithoutFrameCapture::SendPacket, this, rxPowerDbm);
265 // At 4us, no preamble is successfully detected and STA PHY STATE should move from IDLE to CCA_BUSY
268 // Since it takes 152.8us to transmit each packet, PHY should be back to IDLE at time 152.8 + 2 = 154.8us
271 // No more packet should have been successfully received, and since preamble detection did not pass, the packet should not have been counted as a failure
273
274 // CASE 3: send two packets with second one 3 dB weaker within the 4us window and check PHY state:
275 // PHY preamble detection should fail because SNR is too low (around 3 dB, which is lower than the threshold of 4 dB),
276 // and PHY state should be CCA_BUSY since the total energy is above CCA-ED (-62 dBm).
277 // CCA_BUSY state should last for the duration of the two packets minus the time to detect the preamble.
278
279 Simulator::Schedule (Seconds (3.0), &TestThresholdPreambleDetectionWithoutFrameCapture::SendPacket, this, rxPowerDbm);
280 Simulator::Schedule (Seconds (3.0) + MicroSeconds (2.0), &TestThresholdPreambleDetectionWithoutFrameCapture::SendPacket, this, rxPowerDbm - 3);
281 // At 4us, no preamble is successfully detected, hence STA PHY STATE should move from IDLE to CCA_BUSY
284 // Since it takes 152.8us to transmit each packet, PHY should be back to IDLE at time 152.8 + 2 = 154.8us
287 // No more packet should have been successfully received, and since preamble detection did not pass the packet should not have been counted as a failure
289
290 // CASE 4: send two packets with second one 6 dB weaker within the 4us window and check PHY state:
291 // PHY preamble detection should succeed because SNR is high enough (around 6 dB, which is higher than the threshold of 4 dB),
292 // but payload reception should fail (SNR too low to decode the modulation).
293
294 Simulator::Schedule (Seconds (4.0), &TestThresholdPreambleDetectionWithoutFrameCapture::SendPacket, this, rxPowerDbm);
295 Simulator::Schedule (Seconds (4.0) + MicroSeconds (2.0), &TestThresholdPreambleDetectionWithoutFrameCapture::SendPacket, this, rxPowerDbm - 6);
296 // At 4us, preamble should be successfully detected and STA PHY STATE should move from IDLE to CCA_BUSY
299 // At 44us, PHY header should be successfully received and STA PHY STATE should move from CCA_BUSY to RX
302 // Since it takes 152.8us to transmit the packet, PHY should be back to IDLE at time 152.8us.
303 // However, since there is a second packet transmitted with a power above CCA-ED (-62 dBm), PHY should first be seen as CCA_BUSY for 2us.
308 // In this case, the first packet should be marked as a failure
310
311 // CASE 5: send two packets with second one 3 dB higher within the 4us window and check PHY state:
312 // PHY preamble detection should fail because SNR is too low (around -3 dB, which is lower than the threshold of 4 dB),
313 // and PHY state should be CCA_BUSY since the total energy is above CCA-ED (-62 dBm).
314 // CCA_BUSY state should last for the duration of the two packets minus the time to detect the preamble.
315
316 Simulator::Schedule (Seconds (5.0), &TestThresholdPreambleDetectionWithoutFrameCapture::SendPacket, this, rxPowerDbm);
317 Simulator::Schedule (Seconds (5.0) + MicroSeconds (2.0), &TestThresholdPreambleDetectionWithoutFrameCapture::SendPacket, this, rxPowerDbm + 3);
318 // At 6us (hence 4us after the last signal is received), no preamble is successfully detected, hence STA PHY STATE should move from IDLE to CCA_BUSY
321 // Since it takes 152.8us to transmit each packet, PHY should be back to IDLE at time 152.8 + 2 = 154.8us
324 // No more packet should have been successfully received, and since preamble detection did not pass the packet should not have been counted as a failure
326
327 // CCA-PD < RX power < CCA-ED
328 rxPowerDbm = -70;
329
330 // CASE 6: send one packet and check PHY state:
331 // All reception stages should succeed and PHY state should be RX for the duration of the packet minus the time to detect the preamble,
332 // otherwise it should be IDLE.
333
334 Simulator::Schedule (Seconds (6.0), &TestThresholdPreambleDetectionWithoutFrameCapture::SendPacket, this, rxPowerDbm);
335 // At 4us, preamble should be successfully detected and STA PHY STATE should move from IDLE to CCA_BUSY
338 // At 44us, PHY header should be successfully received and STA PHY STATE should move from CCA_BUSY to RX
341 // Since it takes 152.8us to transmit the packet, PHY should be back to IDLE at time 152.8us
344 // Packet should have been successfully received
346
347 // CASE 7: send two packets with same power within the 4us window and check PHY state:
348 // PHY preamble detection should fail because SNR is too low (around 0 dB, which is lower than the threshold of 4 dB),
349 // and PHY state should be CCA_BUSY since it should detect the start of a valid OFDM transmission at a receive level greater
350 // than or equal to the minimum modulation and coding rate sensitivity (–82 dBm for 20 MHz channel spacing).
351
352 Simulator::Schedule (Seconds (7.0), &TestThresholdPreambleDetectionWithoutFrameCapture::SendPacket, this, rxPowerDbm);
353 Simulator::Schedule (Seconds (7.0) + MicroSeconds (2.0), &TestThresholdPreambleDetectionWithoutFrameCapture::SendPacket, this, rxPowerDbm);
354 // At 4us, STA PHY STATE should stay IDLE
356 // No more packet should have been successfully received, and since preamble detection did not pass the packet should not have been counted as a failure
358
359 // CASE 8: send two packets with second one 3 dB weaker within the 4us window and check PHY state: PHY preamble detection should fail
360 // PHY preamble detection should fail because SNR is too low (around 3 dB, which is lower than the threshold of 4 dB),
361 // and PHY state should be CCA_BUSY since it should detect the start of a valid OFDM transmission at a receive level greater
362 // than or equal to the minimum modulation and coding rate sensitivity (–82 dBm for 20 MHz channel spacing).
363
364 Simulator::Schedule (Seconds (8.0), &TestThresholdPreambleDetectionWithoutFrameCapture::SendPacket, this, rxPowerDbm);
365 Simulator::Schedule (Seconds (8.0) + MicroSeconds (2.0), &TestThresholdPreambleDetectionWithoutFrameCapture::SendPacket, this, rxPowerDbm - 3);
366 // At 4us, STA PHY STATE should stay IDLE
368 // No more packet should have been successfully received, and since preamble detection did not pass the packet should not have been counted as a failure
370
371 // CASE 9: send two packets with second one 6 dB weaker within the 4us window and check PHY state:
372 // PHY preamble detection should succeed because SNR is high enough (around 6 dB, which is higher than the threshold of 4 dB),
373 // but payload reception should fail (SNR too low to decode the modulation).
374
375 Simulator::Schedule (Seconds (9.0), &TestThresholdPreambleDetectionWithoutFrameCapture::SendPacket, this, rxPowerDbm);
376 Simulator::Schedule (Seconds (9.0) + MicroSeconds (2.0), &TestThresholdPreambleDetectionWithoutFrameCapture::SendPacket, this, rxPowerDbm - 6);
377 // At 4us, preamble should be successfully detected and STA PHY STATE should move from IDLE to CCA_BUSY
380 // At 44us, PHY header should be successfully received and STA PHY STATE should move from CCA_BUSY to RX
383 // Since it takes 152.8us to transmit the packet, PHY should be back to CCA_BUSY at time 152.8us.
386 // In this case, the first packet should be marked as a failure
388
389 // CASE 10: send two packets with second one 3 dB higher within the 4us window and check PHY state:
390 // PHY preamble detection should fail because SNR is too low (around -3 dB, which is lower than the threshold of 4 dB),
391 // and PHY state should stay IDLE since the total energy is below CCA-ED (-62 dBm).
392
393 Simulator::Schedule (Seconds (10.0), &TestThresholdPreambleDetectionWithoutFrameCapture::SendPacket, this, rxPowerDbm);
394 Simulator::Schedule (Seconds (10.0) + MicroSeconds (2.0), &TestThresholdPreambleDetectionWithoutFrameCapture::SendPacket, this, rxPowerDbm + 3);
395 // At 4us, STA PHY STATE should stay IDLE
397 // No more packet should have been successfully received, and since preamble detection did not pass the packet should not have been counted as a failure
399
400 // CASE 11: send one packet with a power slightly above the minimum RSSI needed for the preamble detection (-82 dBm) and check PHY state:
401 // preamble detection should succeed and PHY state should move to RX.
402
403 rxPowerDbm = -81;
404
405 Simulator::Schedule (Seconds (11.0), &TestThresholdPreambleDetectionWithoutFrameCapture::SendPacket, this, rxPowerDbm);
406 // At 4us, preamble should be successfully detected and STA PHY STATE should move from IDLE to CCA_BUSY
409 // At 44us, PHY header should be successfully received and STA PHY STATE should move from CCA_BUSY to RX
412 // Since it takes 152.8us to transmit the packet, PHY should be back to IDLE at time 152.8us.
415
416 // RX power < CCA-PD < CCA-ED
417 rxPowerDbm = -83;
418
419 //CASE 12: send one packet with a power slightly below the minimum RSSI needed for the preamble detection (-82 dBm) and check PHY state:
420 //preamble detection should fail and PHY should be kept in IDLE state.
421
422 Simulator::Schedule (Seconds (12.0), &TestThresholdPreambleDetectionWithoutFrameCapture::SendPacket, this, rxPowerDbm);
423 // At 4us, STA PHY state should be IDLE
425
427 Simulator::Destroy ();
428}
429
437{
438public:
441
442protected:
443 void DoSetup (void) override;
444 void DoTeardown (void) override;
450 void SendPacket (double rxPowerDbm);
458 void RxSuccess (Ptr<const WifiPsdu> psdu, RxSignalInfo rxSignalInfo,
459 WifiTxVector txVector, std::vector<bool> statusPerMpdu);
464 void RxFailure (Ptr<const WifiPsdu> psdu);
467
468private:
469 void DoRun (void) override;
470
475 void CheckPhyState (WifiPhyState expectedState);
480 void DoCheckPhyState (WifiPhyState expectedState);
486 void CheckRxPacketCount (uint32_t expectedSuccessCount, uint32_t expectedFailureCount);
487
488 uint64_t m_uid;
489};
490
492: TestCase ("Threshold preamble detection model test when simple frame capture model is applied"),
493 m_countRxSuccess (0),
494 m_countRxFailure (0),
495 m_uid (0)
496{
497}
498
499void
501{
502 WifiTxVector txVector = WifiTxVector (HePhy::GetHeMcs7 (), 0, WIFI_PREAMBLE_HE_SU, 800, 1, 1, 0, 20, false);
503
504 Ptr<Packet> pkt = Create<Packet> (1000);
505 WifiMacHeader hdr;
506
508 hdr.SetQosTid (0);
509
510 Ptr<WifiPsdu> psdu = Create<WifiPsdu> (pkt, hdr);
511 Time txDuration = m_phy->CalculateTxDuration (psdu->GetSize (), txVector, m_phy->GetPhyBand ());
512
513 Ptr<WifiPpdu> ppdu = Create<HePpdu> (psdu, txVector, FREQUENCY, txDuration, WIFI_PHY_BAND_5GHZ, m_uid++);
514
515 Ptr<SpectrumValue> txPowerSpectrum = WifiSpectrumValueHelper::CreateHeOfdmTxPowerSpectralDensity (FREQUENCY, CHANNEL_WIDTH, DbmToW (rxPowerDbm), GUARD_WIDTH);
516
517 Ptr<WifiSpectrumSignalParameters> txParams = Create<WifiSpectrumSignalParameters> ();
518 txParams->psd = txPowerSpectrum;
519 txParams->txPhy = 0;
520 txParams->duration = txDuration;
521 txParams->ppdu = ppdu;
522
523 m_phy->StartRx (txParams);
524}
525
526void
528{
529 //This is needed to make sure PHY state will be checked as the last event if a state change occured at the exact same time as the check
530 Simulator::ScheduleNow (&TestThresholdPreambleDetectionWithFrameCapture::DoCheckPhyState, this, expectedState);
531}
532
533void
535{
536 WifiPhyState currentState;
537 PointerValue ptr;
538 m_phy->GetAttribute ("State", ptr);
539 Ptr <WifiPhyStateHelper> state = DynamicCast <WifiPhyStateHelper> (ptr.Get<WifiPhyStateHelper> ());
540 currentState = state->GetState ();
541 NS_LOG_FUNCTION (this << currentState);
542 NS_TEST_ASSERT_MSG_EQ (currentState, expectedState, "PHY State " << currentState << " does not match expected state " << expectedState << " at " << Simulator::Now ());
543}
544
545void
547{
548 NS_TEST_ASSERT_MSG_EQ (m_countRxSuccess, expectedSuccessCount, "Didn't receive right number of successful packets");
549 NS_TEST_ASSERT_MSG_EQ (m_countRxFailure, expectedFailureCount, "Didn't receive right number of unsuccessful packets");
550}
551
552void
554 WifiTxVector txVector, std::vector<bool> statusPerMpdu)
555{
556 NS_LOG_FUNCTION (this << *psdu << txVector);
558}
559
560void
562{
563 NS_LOG_FUNCTION (this << *psdu);
565}
566
568{
569 m_phy = 0;
570}
571
572void
574{
575 m_phy = CreateObject<SpectrumWifiPhy> ();
577 Ptr<InterferenceHelper> interferenceHelper = CreateObject<InterferenceHelper> ();
578 m_phy->SetInterferenceHelper (interferenceHelper);
579 Ptr<ErrorRateModel> error = CreateObject<NistErrorRateModel> ();
580 m_phy->SetErrorRateModel (error);
584
585 Ptr<ThresholdPreambleDetectionModel> preambleDetectionModel = CreateObject<ThresholdPreambleDetectionModel> ();
586 preambleDetectionModel->SetAttribute ("Threshold", DoubleValue (4));
587 preambleDetectionModel->SetAttribute ("MinimumRssi", DoubleValue (-82));
588 m_phy->SetPreambleDetectionModel (preambleDetectionModel);
589
590 Ptr<SimpleFrameCaptureModel> frameCaptureModel = CreateObject<SimpleFrameCaptureModel> ();
591 frameCaptureModel->SetAttribute ("Margin", DoubleValue (5));
592 frameCaptureModel->SetAttribute ("CaptureWindow", TimeValue (MicroSeconds (16)));
593 m_phy->SetFrameCaptureModel (frameCaptureModel);
594}
595
596void
598{
599 m_phy->Dispose ();
600 m_phy = 0;
601}
602
603void
605{
606 RngSeedManager::SetSeed (1);
607 RngSeedManager::SetRun (1);
608 int64_t streamNumber = 1;
609 m_phy->AssignStreams (streamNumber);
610
611 //RX power > CCA-ED > CCA-PD
612 double rxPowerDbm = -50;
613
614 // CASE 1: send one packet and check PHY state:
615 // All reception stages should succeed and PHY state should be RX for the duration of the packet minus the time to detect the preamble,
616 // otherwise it should be IDLE.
617
618 Simulator::Schedule (Seconds (1.0), &TestThresholdPreambleDetectionWithFrameCapture::SendPacket, this, rxPowerDbm);
619 // At 4us, preamble should be successfully detected and STA PHY STATE should move from IDLE to CCA_BUSY
622 // At 44us, PHY header should be successfully received and STA PHY STATE should move from CCA_BUSY to RX
625 // Since it takes 152.8us to transmit the packet, PHY should be back to IDLE at time 152.8us
628 // Packet should have been successfully received
629 Simulator::Schedule (Seconds (1.1), &TestThresholdPreambleDetectionWithFrameCapture::CheckRxPacketCount, this, 1, 0);
630
631 // CASE 2: send two packets with same power within the 4us window and check PHY state:
632 // PHY preamble detection should fail because SNR is too low (around 0 dB, which is lower than the threshold of 4 dB),
633 // and PHY state should be CCA_BUSY since the total energy is above CCA-ED (-62 dBm).
634 // CCA_BUSY state should last for the duration of the two packets minus the time to detect the preamble.
635
636 Simulator::Schedule (Seconds (2.0), &TestThresholdPreambleDetectionWithFrameCapture::SendPacket, this, rxPowerDbm);
637 Simulator::Schedule (Seconds (2.0) + MicroSeconds (2.0), &TestThresholdPreambleDetectionWithFrameCapture::SendPacket, this, rxPowerDbm);
638 // At 4us, no preamble is successfully detected, hence STA PHY STATE should move from IDLE to CCA_BUSY
641 // Since it takes 152.8us to transmit each packet, PHY should be back to IDLE at time 152.8 + 2 = 154.8us
644 // No more packet should have been successfully received, and since preamble detection did not pass the packet should not have been counted as a failure
645 Simulator::Schedule (Seconds (2.1), &TestThresholdPreambleDetectionWithFrameCapture::CheckRxPacketCount, this, 1, 0);
646
647 // CASE 3: send two packets with second one 3 dB weaker within the 4us window and check PHY state:
648 // PHY preamble detection should fail because SNR is too low (around 3 dB, which is lower than the threshold of 4 dB),
649 // and PHY state should be CCA_BUSY since the total energy is above CCA-ED (-62 dBm).
650 // CCA_BUSY state should last for the duration of the two packets minus the time to detect the preamble.
651
652 Simulator::Schedule (Seconds (3.0), &TestThresholdPreambleDetectionWithFrameCapture::SendPacket, this, rxPowerDbm);
653 Simulator::Schedule (Seconds (3.0) + MicroSeconds (2.0), &TestThresholdPreambleDetectionWithFrameCapture::SendPacket, this, rxPowerDbm - 3);
654 // At 4us, no preamble is successfully detected, hence STA PHY STATE should move from IDLE to CCA_BUSY
657 // Since it takes 152.8us to transmit each packet, PHY should be back to IDLE at time 152.8 + 2 = 154.8us
660 // No more packet should have been successfully received, and since preamble detection did not pass the packet should not have been counted as a failure
661 Simulator::Schedule (Seconds (3.1), &TestThresholdPreambleDetectionWithFrameCapture::CheckRxPacketCount, this, 1, 0);
662
663 // CASE 4: send two packets with second one 6 dB weaker within the 4us window and check PHY state:
664 // PHY preamble detection should succeed because SNR is high enough (around 6 dB, which is higher than the threshold of 4 dB),
665 // but payload reception should fail (SNR too low to decode the modulation).
666
667 Simulator::Schedule (Seconds (4.0), &TestThresholdPreambleDetectionWithFrameCapture::SendPacket, this, rxPowerDbm);
668 Simulator::Schedule (Seconds (4.0) + MicroSeconds (2.0), &TestThresholdPreambleDetectionWithFrameCapture::SendPacket, this, rxPowerDbm - 6);
669 // At 4us, preamble should be successfully detected and STA PHY STATE should move from IDLE to CCA_BUSY
672 // At 44us, PHY header should be successfully received and STA PHY STATE should move from CCA_BUSY to RX
675 // Since it takes 152.8us to transmit the packet, PHY should be back to IDLE at time 152.8us.
676 // However, since there is a second packet transmitted with a power above CCA-ED (-62 dBm), PHY should first be seen as CCA_BUSY for 2us.
681 // In this case, the first packet should be marked as a failure
682 Simulator::Schedule (Seconds (4.1), &TestThresholdPreambleDetectionWithFrameCapture::CheckRxPacketCount, this, 1, 1);
683
684 // CASE 5: send two packets with second one 3 dB higher within the 4us window and check PHY state:
685 // PHY preamble detection should switch because a higher packet is received within the 4us window,
686 // but preamble detection should fail because SNR is too low (around 3 dB, which is lower than the threshold of 4 dB),
687 // PHY state should be CCA_BUSY since the total energy is above CCA-ED (-62 dBm).
688
689 Simulator::Schedule (Seconds (5.0), &TestThresholdPreambleDetectionWithFrameCapture::SendPacket, this, rxPowerDbm);
690 Simulator::Schedule (Seconds (5.0) + MicroSeconds (2.0), &TestThresholdPreambleDetectionWithFrameCapture::SendPacket, this, rxPowerDbm + 3);
691 // At 4us, STA PHY STATE should stay IDLE
693 // At 6us, STA PHY STATE should move from IDLE to CCA_BUSY
696 // Since it takes 152.8us to transmit each packet, PHY should be back to IDLE at time 152.8 + 2 = 154.8us
699 // No more packet should have been successfully received, and since preamble detection did not pass the packet should not have been counted as a failure
700 Simulator::Schedule (Seconds (5.1), &TestThresholdPreambleDetectionWithFrameCapture::CheckRxPacketCount, this, 1, 1);
701
702 // CASE 6: send two packets with second one 6 dB higher within the 4us window and check PHY state:
703 // PHY preamble detection should switch because a higher packet is received within the 4us window,
704 // and preamble detection should succeed because SNR is high enough (around 6 dB, which is higher than the threshold of 4 dB),
705 // Payload reception should fail (SNR too low to decode the modulation).
706
707 Simulator::Schedule (Seconds (6.0), &TestThresholdPreambleDetectionWithFrameCapture::SendPacket, this, rxPowerDbm);
708 Simulator::Schedule (Seconds (6.0) + MicroSeconds (2.0), &TestThresholdPreambleDetectionWithFrameCapture::SendPacket, this, rxPowerDbm + 6);
709 // At 4us, STA PHY STATE should stay IDLE
711 // At 6us, preamble should be successfully detected and STA PHY STATE should move from IDLE to CCA_BUSY
714 // At 46us, PHY header should be successfully received and STA PHY STATE should move from CCA_BUSY to RX
717 // Since it takes 152.8us to transmit each packet, PHY should be back to IDLE at time 152.8 + 2 = 154.8us
720 // In this case, the second packet should be marked as a failure
721 Simulator::Schedule (Seconds (6.1), &TestThresholdPreambleDetectionWithFrameCapture::CheckRxPacketCount, this, 1, 2);
722
723 // CASE 7: send two packets with same power at the exact same time and check PHY state:
724 // PHY preamble detection should fail because SNR is too low (around 0 dB, which is lower than the threshold of 4 dB),
725 // and PHY state should be CCA_BUSY since the total energy is above CCA-ED (-62 dBm).
726 // CCA_BUSY state should last for the duration of the two packets minus the time to detect the preamble.
727
728 Simulator::Schedule (Seconds (7.0), &TestThresholdPreambleDetectionWithFrameCapture::SendPacket, this, rxPowerDbm);
729 Simulator::Schedule (Seconds (7.0), &TestThresholdPreambleDetectionWithFrameCapture::SendPacket, this, rxPowerDbm);
730 // At 4us, no preamble is successfully detected, hence STA PHY STATE should move from IDLE to CCA_BUSY
733 // Since it takes 152.8us to transmit each packet, PHY should be back to IDLE at time 152.8 + 2 = 154.8us
736 // No more packet should have been successfully received, and since preamble detection did not pass the packet should not have been counted as a failure
737 Simulator::Schedule (Seconds (7.1), &TestThresholdPreambleDetectionWithFrameCapture::CheckRxPacketCount, this, 1, 2);
738
739 // CASE 8: send two packets with second one 3 dB weaker at the exact same time and check PHY state:
740 // PHY preamble detection should fail because SNR is too low (around 3 dB, which is lower than the threshold of 4 dB),
741 // and PHY state should be CCA_BUSY since the total energy is above CCA-ED (-62 dBm).
742 // CCA_BUSY state should last for the duration of the two packets minus the time to detect the preamble.
743
744 Simulator::Schedule (Seconds (8.0), &TestThresholdPreambleDetectionWithFrameCapture::SendPacket, this, rxPowerDbm);
745 Simulator::Schedule (Seconds (8.0), &TestThresholdPreambleDetectionWithFrameCapture::SendPacket, this, rxPowerDbm - 3);
746 // At 4us, no preamble is successfully detected, hence STA PHY STATE should move from IDLE to CCA_BUSY
749 // Since it takes 152.8us to transmit each packet, PHY should be back to IDLE at time 152.8 us
752 // No more packet should have been successfully received, and since preamble detection did not pass the packet should not have been counted as a failure
753 Simulator::Schedule (Seconds (8.1), &TestThresholdPreambleDetectionWithFrameCapture::CheckRxPacketCount, this, 1, 2);
754
755 // CASE 9: send two packets with second one 6 dB weaker at the exact same time and check PHY state:
756 // PHY preamble detection should succeed because SNR is high enough (around 6 dB, which is higher than the threshold of 4 dB),
757 // but payload reception should fail (SNR too low to decode the modulation).
758
759 Simulator::Schedule (Seconds (9.0), &TestThresholdPreambleDetectionWithFrameCapture::SendPacket, this, rxPowerDbm);
760 Simulator::Schedule (Seconds (9.0), &TestThresholdPreambleDetectionWithFrameCapture::SendPacket, this, rxPowerDbm - 6);
761 // At 4us, preamble should be successfully detected and STA PHY STATE should move from IDLE to CCA_BUSY
764 // At 44us, PHY header should be successfully received and STA PHY STATE should move from CCA_BUSY to RX
767 // Since it takes 152.8us to transmit the packets, PHY should be back to IDLE at time 152.8us.
770 // In this case, the first packet should be marked as a failure
771 Simulator::Schedule (Seconds (9.1), &TestThresholdPreambleDetectionWithFrameCapture::CheckRxPacketCount, this, 1, 3);
772
773 // CASE 10: send two packets with second one 3 dB higher at the exact same time and check PHY state:
774 // PHY preamble detection should switch because a higher packet is received within the 4us window,
775 // but preamble detection should fail because SNR is too low (around 3 dB, which is lower than the threshold of 4 dB),
776 // PHY state should be CCA_BUSY since the total energy is above CCA-ED (-62 dBm).
777
778 Simulator::Schedule (Seconds (10.0), &TestThresholdPreambleDetectionWithFrameCapture::SendPacket, this, rxPowerDbm);
779 Simulator::Schedule (Seconds (10.0), &TestThresholdPreambleDetectionWithFrameCapture::SendPacket, this, rxPowerDbm + 3);
780 // At 4us, no preamble is successfully detected, hence STA PHY STATE should move from IDLE to CCA_BUSY
783 // Since it takes 152.8us to transmit each packet, PHY should be back to IDLE at time 152.8 us
786 // No more packet should have been successfully received, and since preamble detection did not pass the packet should not have been counted as a failure
787 Simulator::Schedule (Seconds (10.1), &TestThresholdPreambleDetectionWithFrameCapture::CheckRxPacketCount, this, 1, 3);
788
789 // CASE 11: send two packets with second one 6 dB higher at the exact same time and check PHY state:
790 // PHY preamble detection should switch because a higher packet is received within the 4us window,
791 // and preamble detection should succeed because SNR is high enough (around 6 dB, which is higher than the threshold of 4 dB),
792 // Payload reception should fail (SNR too low to decode the modulation).
793
794 Simulator::Schedule (Seconds (11.0), &TestThresholdPreambleDetectionWithFrameCapture::SendPacket, this, rxPowerDbm);
795 Simulator::Schedule (Seconds (11.0), &TestThresholdPreambleDetectionWithFrameCapture::SendPacket, this, rxPowerDbm + 6);
796 // At 4us, preamble should be successfully detected and STA PHY STATE should move from IDLE to CCA_BUSY
799 // At 44us, PHY header should be successfully received and STA PHY STATE should move from CCA_BUSY to RX
802 // Since it takes 152.8us to transmit each packet, PHY should be back to IDLE at time 152.8 us
805 // In this case, the second packet should be marked as a failure
806 Simulator::Schedule (Seconds (11.1), &TestThresholdPreambleDetectionWithFrameCapture::CheckRxPacketCount, this, 1, 4);
807
808 // CCA-PD < RX power < CCA-ED
809 rxPowerDbm = -70;
810
811 // CASE 12: send one packet and check PHY state:
812 // All reception stages should succeed and PHY state should be RX for the duration of the packet minus the time to detect the preamble,
813 // otherwise it should be IDLE.
814
815 Simulator::Schedule (Seconds (12.0), &TestThresholdPreambleDetectionWithFrameCapture::SendPacket, this, rxPowerDbm);
816 // At 4us, preamble should be successfully detected and STA PHY STATE should move from IDLE to CCA_BUSY
819 // At 44us, PHY header should be successfully received and STA PHY STATE should move from CCA_BUSY to RX
822 // Since it takes 152.8us to transmit the packet, PHY should be back to IDLE at time 152.8us
825 // Packet should have been successfully received
826 Simulator::Schedule (Seconds (12.1), &TestThresholdPreambleDetectionWithFrameCapture::CheckRxPacketCount, this, 2, 4);
827
828 // CASE 13: send two packets with same power within the 4us window and check PHY state:
829 // PHY preamble detection should fail because SNR is too low (around 0 dB, which is lower than the threshold of 4 dB),
830 // and PHY state should be CCA_BUSY since it should detect the start of a valid OFDM transmission at a receive level greater
831 // than or equal to the minimum modulation and coding rate sensitivity (–82 dBm for 20 MHz channel spacing).
832
833 Simulator::Schedule (Seconds (13.0), &TestThresholdPreambleDetectionWithFrameCapture::SendPacket, this, rxPowerDbm);
834 Simulator::Schedule (Seconds (13.0) + MicroSeconds (2.0), &TestThresholdPreambleDetectionWithFrameCapture::SendPacket, this, rxPowerDbm);
835 // At 4us, STA PHY STATE should stay IDLE
837 // No more packet should have been successfully received, and since preamble detection did not pass the packet should not have been counted as a failure
838 Simulator::Schedule (Seconds (13.1), &TestThresholdPreambleDetectionWithFrameCapture::CheckRxPacketCount, this, 2, 4);
839
840 // CASE 14: send two packets with second one 3 dB weaker within the 4us window and check PHY state: PHY preamble detection should fail
841 // PHY preamble detection should fail because SNR is too low (around 3 dB, which is lower than the threshold of 4 dB),
842 // and PHY state should be CCA_BUSY since it should detect the start of a valid OFDM transmission at a receive level greater
843 // than or equal to the minimum modulation and coding rate sensitivity (–82 dBm for 20 MHz channel spacing).
844
845 Simulator::Schedule (Seconds (14.0), &TestThresholdPreambleDetectionWithFrameCapture::SendPacket, this, rxPowerDbm);
846 Simulator::Schedule (Seconds (14.0) + MicroSeconds (2.0), &TestThresholdPreambleDetectionWithFrameCapture::SendPacket, this, rxPowerDbm - 3);
847 // At 4us, STA PHY STATE should stay IDLE
849 // No more packet should have been successfully received, and since preamble detection did not pass the packet should not have been counted as a failure
850 Simulator::Schedule (Seconds (14.1), &TestThresholdPreambleDetectionWithFrameCapture::CheckRxPacketCount, this, 2, 4);
851
852 // CASE 15: send two packets with second one 6 dB weaker within the 4us window and check PHY state:
853 // PHY preamble detection should succeed because SNR is high enough (around 6 dB, which is higher than the threshold of 4 dB),
854 // but payload reception should fail (SNR too low to decode the modulation).
855
856 Simulator::Schedule (Seconds (15.0), &TestThresholdPreambleDetectionWithFrameCapture::SendPacket, this, rxPowerDbm);
857 Simulator::Schedule (Seconds (15.0) + MicroSeconds (2.0), &TestThresholdPreambleDetectionWithFrameCapture::SendPacket, this, rxPowerDbm - 6);
858 // At 4us, preamble should be successfully detected and STA PHY STATE should move from IDLE to CCA_BUSY
861 // At 44us, PHY header should be successfully received and STA PHY STATE should move from CCA_BUSY to RX
864 // Since it takes 152.8us to transmit the packet, PHY should be back to CCA_BUSY at time 152.8us.
867 // In this case, the first packet should be marked as a failure
868 Simulator::Schedule (Seconds (15.1), &TestThresholdPreambleDetectionWithFrameCapture::CheckRxPacketCount, this, 2, 5);
869
870 // CASE 16: send two packets with second one 3 dB higher within the 4us window and check PHY state:
871 // PHY preamble detection should switch because a higher packet is received within the 4us window,
872 // but preamble detection should fail because SNR is too low (around 3 dB, which is lower than the threshold of 4 dB).
873 // and PHY state should be CCA_BUSY since it should detect the start of a valid OFDM transmission at a receive level greater
874 // than or equal to the minimum modulation and coding rate sensitivity (–82 dBm for 20 MHz channel spacing).
875
876 Simulator::Schedule (Seconds (16.0), &TestThresholdPreambleDetectionWithFrameCapture::SendPacket, this, rxPowerDbm);
877 Simulator::Schedule (Seconds (16.0) + MicroSeconds (2.0), &TestThresholdPreambleDetectionWithFrameCapture::SendPacket, this, rxPowerDbm + 3);
878 // At 4us, STA PHY STATE should stay IDLE
880 // At 6us, STA PHY STATE should be CCA_BUSY
882 // No more packet should have been successfully received, and since preamble detection did not pass the packet should not have been counted as a failure
883 Simulator::Schedule (Seconds (16.1), &TestThresholdPreambleDetectionWithFrameCapture::CheckRxPacketCount, this, 2, 5);
884
885 // CASE 17: send two packets with second one 6 dB higher within the 4us window and check PHY state:
886 // PHY preamble detection should switch because a higher packet is received within the 4us window,
887 // and preamble detection should succeed because SNR is high enough (around 6 dB, which is higher than the threshold of 4 dB),
888 // Payload reception should fail (SNR too low to decode the modulation).
889
890 Simulator::Schedule (Seconds (17.0), &TestThresholdPreambleDetectionWithFrameCapture::SendPacket, this, rxPowerDbm);
891 Simulator::Schedule (Seconds (17.0) + MicroSeconds (2.0), &TestThresholdPreambleDetectionWithFrameCapture::SendPacket, this, rxPowerDbm + 6);
892 // At 4us, STA PHY STATE should stay IDLE
894 // At 6us, preamble should be successfully detected and STA PHY STATE should move from IDLE to CCA_BUSY
897 // At 46us, PHY header should be successfully received and STA PHY STATE should move from CCA_BUSY to RX
900 // Since it takes 152.8us to transmit each packet, PHY should be back to IDLE at time 152.8 + 2 = 154.8us
903 // In this case, the second packet should be marked as a failure
904 Simulator::Schedule (Seconds (17.1), &TestThresholdPreambleDetectionWithFrameCapture::CheckRxPacketCount, this, 2, 6);
905
906 rxPowerDbm = -50;
907 // CASE 18: send two packets with second one 50 dB higher within the 4us window
908
909 Simulator::Schedule (Seconds (18.0), &TestThresholdPreambleDetectionWithFrameCapture::SendPacket, this, rxPowerDbm);
910 Simulator::Schedule (Seconds (18.0) + MicroSeconds (2.0), &TestThresholdPreambleDetectionWithFrameCapture::SendPacket, this, rxPowerDbm+50);
911 // The second packet should be received successfully
912 Simulator::Schedule (Seconds (18.1), &TestThresholdPreambleDetectionWithFrameCapture::CheckRxPacketCount, this, 3, 6);
913
914 // CASE 19: send two packets with second one 10 dB higher within the 4us window
915
916 Simulator::Schedule (Seconds (19.0), &TestThresholdPreambleDetectionWithFrameCapture::SendPacket, this, rxPowerDbm);
917 Simulator::Schedule (Seconds (19.0) + MicroSeconds (2.0), &TestThresholdPreambleDetectionWithFrameCapture::SendPacket, this, rxPowerDbm+10);
918 // The second packet should be captured, but not decoded since SNR to low for used MCS
919 Simulator::Schedule (Seconds (19.1), &TestThresholdPreambleDetectionWithFrameCapture::CheckRxPacketCount, this, 3, 7);
920
921 // CASE 20: send two packets with second one 50 dB higher in the same time
922
923 Simulator::Schedule (Seconds (20.0), &TestThresholdPreambleDetectionWithFrameCapture::SendPacket, this, rxPowerDbm);
924 Simulator::Schedule (Seconds (20.0), &TestThresholdPreambleDetectionWithFrameCapture::SendPacket, this, rxPowerDbm+50);
925 // The second packet should be received successfully, same as in CASE 13
926 Simulator::Schedule (Seconds (20.1), &TestThresholdPreambleDetectionWithFrameCapture::CheckRxPacketCount, this, 4, 7);
927
928 // CASE 21: send two packets with second one 10 dB higher in the same time
929
930 Simulator::Schedule (Seconds (21.0), &TestThresholdPreambleDetectionWithFrameCapture::SendPacket, this, rxPowerDbm);
931 Simulator::Schedule (Seconds (21.0), &TestThresholdPreambleDetectionWithFrameCapture::SendPacket, this, rxPowerDbm+10);
932 // The second packet should be captured, but not decoded since SNR to low for used MCS, same as in CASE 19
933 Simulator::Schedule (Seconds (21.1), &TestThresholdPreambleDetectionWithFrameCapture::CheckRxPacketCount, this, 4, 8);
934
936 Simulator::Destroy ();
937}
938
946{
947public:
950
951protected:
952 void DoSetup (void) override;
953 void DoTeardown (void) override;
954
955private:
956 void DoRun (void) override;
957
961 void Reset (void);
967 void SendPacket (double rxPowerDbm, uint32_t packetSize);
975 void RxSuccess (Ptr<const WifiPsdu> psdu, RxSignalInfo rxSignalInfo,
976 WifiTxVector txVector, std::vector<bool> statusPerMpdu);
983
1000
1002
1007
1008 uint64_t m_uid;
1009};
1010
1012: TestCase ("Simple frame capture model test"),
1013 m_rxSuccess1000B (false),
1014 m_rxSuccess1500B (false),
1015 m_rxDropped1000B (false),
1016 m_rxDropped1500B (false),
1017 m_uid (0)
1018{
1019}
1020
1021void
1023{
1024 WifiTxVector txVector = WifiTxVector (HePhy::GetHeMcs0 (), 0, WIFI_PREAMBLE_HE_SU, 800, 1, 1, 0, 20, false);
1025
1026 Ptr<Packet> pkt = Create<Packet> (packetSize);
1027 WifiMacHeader hdr;
1028
1030 hdr.SetQosTid (0);
1031
1032 Ptr<WifiPsdu> psdu = Create<WifiPsdu> (pkt, hdr);
1033 Time txDuration = m_phy->CalculateTxDuration (psdu->GetSize (), txVector, m_phy->GetPhyBand ());
1034
1035 Ptr<WifiPpdu> ppdu = Create<HePpdu> (psdu, txVector, FREQUENCY, txDuration, WIFI_PHY_BAND_5GHZ, m_uid++);
1036
1037 Ptr<SpectrumValue> txPowerSpectrum = WifiSpectrumValueHelper::CreateHeOfdmTxPowerSpectralDensity (FREQUENCY, CHANNEL_WIDTH, DbmToW (rxPowerDbm), GUARD_WIDTH);
1038
1039 Ptr<WifiSpectrumSignalParameters> txParams = Create<WifiSpectrumSignalParameters> ();
1040 txParams->psd = txPowerSpectrum;
1041 txParams->txPhy = 0;
1042 txParams->duration = txDuration;
1043 txParams->ppdu = ppdu;
1044
1045 m_phy->StartRx (txParams);
1046}
1047
1048void
1050 WifiTxVector txVector, std::vector<bool> statusPerMpdu)
1051{
1052 NS_LOG_FUNCTION (this << *psdu << rxSignalInfo << txVector);
1053 NS_ASSERT (!psdu->IsAggregate () || psdu->IsSingle ());
1054 if (psdu->GetSize () == 1030)
1055 {
1056 m_rxSuccess1000B = true;
1057 }
1058 else if (psdu->GetSize () == 1530)
1059 {
1060 m_rxSuccess1500B = true;
1061 }
1062}
1063
1064void
1066{
1067 NS_LOG_FUNCTION (this << p << reason);
1068 if (p->GetSize () == 1030)
1069 {
1070 m_rxDropped1000B = true;
1071 }
1072 else if (p->GetSize () == 1530)
1073 {
1074 m_rxDropped1500B = true;
1075 }
1076}
1077
1078void
1080{
1081 m_rxSuccess1000B = false;
1082 m_rxSuccess1500B = false;
1083 m_rxDropped1000B = false;
1084 m_rxDropped1500B = false;
1085}
1086
1087void
1089{
1090 NS_TEST_ASSERT_MSG_EQ (m_rxSuccess1000B, true, "Didn't receive 1000B packet");
1091}
1092
1093void
1095{
1096 NS_TEST_ASSERT_MSG_EQ (m_rxSuccess1500B, true, "Didn't receive 1500B packet");
1097}
1098void
1100{
1101 NS_TEST_ASSERT_MSG_EQ (m_rxDropped1000B, true, "Didn't drop 1000B packet");
1102}
1103
1104void
1106{
1107 NS_TEST_ASSERT_MSG_EQ (m_rxDropped1500B, true, "Didn't drop 1500B packet");
1108}
1109
1111{
1112 m_phy = 0;
1113}
1114
1115void
1117{
1118 m_phy = CreateObject<SpectrumWifiPhy> ();
1120 Ptr<InterferenceHelper> interferenceHelper = CreateObject<InterferenceHelper> ();
1121 m_phy->SetInterferenceHelper (interferenceHelper);
1122 Ptr<ErrorRateModel> error = CreateObject<NistErrorRateModel> ();
1123 m_phy->SetErrorRateModel (error);
1125
1128
1129 Ptr<ThresholdPreambleDetectionModel> preambleDetectionModel = CreateObject<ThresholdPreambleDetectionModel> ();
1130 preambleDetectionModel->SetAttribute ("Threshold", DoubleValue (2));
1131 m_phy->SetPreambleDetectionModel (preambleDetectionModel);
1132
1133 Ptr<SimpleFrameCaptureModel> frameCaptureModel = CreateObject<SimpleFrameCaptureModel> ();
1134 frameCaptureModel->SetAttribute ("Margin", DoubleValue (5));
1135 frameCaptureModel->SetAttribute ("CaptureWindow", TimeValue (MicroSeconds (16)));
1136 m_phy->SetFrameCaptureModel (frameCaptureModel);
1137}
1138
1139void
1141{
1142 m_phy->Dispose ();
1143 m_phy = 0;
1144}
1145
1146void
1148{
1149 RngSeedManager::SetSeed (1);
1150 RngSeedManager::SetRun (1);
1151 int64_t streamNumber = 2;
1152 double rxPowerDbm = -30;
1153 m_phy->AssignStreams (streamNumber);
1154
1155 // CASE 1: send two packets with same power within the capture window:
1156 // PHY should not switch reception because they have same power.
1157
1158 Simulator::Schedule (Seconds (1.0), &TestSimpleFrameCaptureModel::SendPacket, this, rxPowerDbm, 1000);
1159 Simulator::Schedule (Seconds (1.0) + MicroSeconds (10.0), &TestSimpleFrameCaptureModel::SendPacket, this, rxPowerDbm, 1500);
1160 Simulator::Schedule (Seconds (1.1), &TestSimpleFrameCaptureModel::Expect1500BPacketDropped, this);
1161 Simulator::Schedule (Seconds (1.2), &TestSimpleFrameCaptureModel::Reset, this);
1162
1163 // CASE 2: send two packets with second one 6 dB weaker within the capture window:
1164 // PHY should not switch reception because first one has higher power.
1165
1166 Simulator::Schedule (Seconds (2.0), &TestSimpleFrameCaptureModel::SendPacket, this, rxPowerDbm, 1000);
1167 Simulator::Schedule (Seconds (2.0) + MicroSeconds (10.0), &TestSimpleFrameCaptureModel::SendPacket, this, rxPowerDbm - 6, 1500);
1168 Simulator::Schedule (Seconds (2.1), &TestSimpleFrameCaptureModel::Expect1000BPacketReceived, this);
1169 Simulator::Schedule (Seconds (2.1), &TestSimpleFrameCaptureModel::Expect1500BPacketDropped, this);
1170 Simulator::Schedule (Seconds (2.2), &TestSimpleFrameCaptureModel::Reset, this);
1171
1172 // CASE 3: send two packets with second one 6 dB higher within the capture window:
1173 // PHY should switch reception because the second one has a higher power.
1174
1175 Simulator::Schedule (Seconds (3.0), &TestSimpleFrameCaptureModel::SendPacket, this, rxPowerDbm, 1000);
1176 Simulator::Schedule (Seconds (3.0) + MicroSeconds (10.0), &TestSimpleFrameCaptureModel::SendPacket, this, rxPowerDbm + 6, 1500);
1177 Simulator::Schedule (Seconds (3.1), &TestSimpleFrameCaptureModel::Expect1000BPacketDropped, this);
1178 Simulator::Schedule (Seconds (3.1), &TestSimpleFrameCaptureModel::Expect1500BPacketReceived, this);
1179 Simulator::Schedule (Seconds (3.2), &TestSimpleFrameCaptureModel::Reset, this);
1180
1181 // CASE 4: send two packets with second one 6 dB higher after the capture window:
1182 // PHY should not switch reception because capture window duration has elapsed when the second packet arrives.
1183
1184 Simulator::Schedule (Seconds (4.0), &TestSimpleFrameCaptureModel::SendPacket, this, rxPowerDbm, 1000);
1185 Simulator::Schedule (Seconds (4.0) + MicroSeconds (25.0), &TestSimpleFrameCaptureModel::SendPacket, this, rxPowerDbm + 6, 1500);
1186 Simulator::Schedule (Seconds (4.1), &TestSimpleFrameCaptureModel::Expect1500BPacketDropped, this);
1187 Simulator::Schedule (Seconds (4.2), &TestSimpleFrameCaptureModel::Reset, this);
1188
1189 Simulator::Run ();
1190 Simulator::Destroy ();
1191}
1192
1200{
1201public:
1203 virtual ~TestPhyHeadersReception ();
1204
1205protected:
1206 void DoSetup (void) override;
1207 void DoTeardown (void) override;
1213 void SendPacket (double rxPowerDbm);
1214
1215private:
1216 void DoRun (void) override;
1217
1222 void CheckPhyState (WifiPhyState expectedState);
1227 void DoCheckPhyState (WifiPhyState expectedState);
1228
1229 uint64_t m_uid;
1230};
1231
1233: TestCase ("PHY headers reception test"),
1234 m_uid (0)
1235{
1236}
1237
1238void
1240{
1241 WifiTxVector txVector = WifiTxVector (HePhy::GetHeMcs7 (), 0, WIFI_PREAMBLE_HE_SU, 800, 1, 1, 0, 20, false);
1242
1243 Ptr<Packet> pkt = Create<Packet> (1000);
1244 WifiMacHeader hdr;
1245
1247 hdr.SetQosTid (0);
1248
1249 Ptr<WifiPsdu> psdu = Create<WifiPsdu> (pkt, hdr);
1250 Time txDuration = m_phy->CalculateTxDuration (psdu->GetSize (), txVector, m_phy->GetPhyBand ());
1251
1252 Ptr<WifiPpdu> ppdu = Create<HePpdu> (psdu, txVector, FREQUENCY, txDuration, WIFI_PHY_BAND_5GHZ, m_uid++);
1253
1254 Ptr<SpectrumValue> txPowerSpectrum = WifiSpectrumValueHelper::CreateHeOfdmTxPowerSpectralDensity (FREQUENCY, CHANNEL_WIDTH, DbmToW (rxPowerDbm), GUARD_WIDTH);
1255
1256 Ptr<WifiSpectrumSignalParameters> txParams = Create<WifiSpectrumSignalParameters> ();
1257 txParams->psd = txPowerSpectrum;
1258 txParams->txPhy = 0;
1259 txParams->duration = txDuration;
1260 txParams->ppdu = ppdu;
1261
1262 m_phy->StartRx (txParams);
1263}
1264
1265void
1267{
1268 //This is needed to make sure PHY state will be checked as the last event if a state change occured at the exact same time as the check
1269 Simulator::ScheduleNow (&TestPhyHeadersReception::DoCheckPhyState, this, expectedState);
1270}
1271
1272void
1274{
1275 WifiPhyState currentState;
1276 PointerValue ptr;
1277 m_phy->GetAttribute ("State", ptr);
1278 Ptr <WifiPhyStateHelper> state = DynamicCast <WifiPhyStateHelper> (ptr.Get<WifiPhyStateHelper> ());
1279 currentState = state->GetState ();
1280 NS_LOG_FUNCTION (this << currentState);
1281 NS_TEST_ASSERT_MSG_EQ (currentState, expectedState, "PHY State " << currentState << " does not match expected state " << expectedState << " at " << Simulator::Now ());
1282}
1283
1285{
1286 m_phy = 0;
1287}
1288
1289void
1291{
1292 m_phy = CreateObject<SpectrumWifiPhy> ();
1294 Ptr<InterferenceHelper> interferenceHelper = CreateObject<InterferenceHelper> ();
1295 m_phy->SetInterferenceHelper (interferenceHelper);
1296 Ptr<ErrorRateModel> error = CreateObject<NistErrorRateModel> ();
1297 m_phy->SetErrorRateModel (error);
1299}
1300
1301void
1303{
1304 m_phy->Dispose ();
1305 m_phy = 0;
1306}
1307
1308void
1310{
1311 RngSeedManager::SetSeed (1);
1312 RngSeedManager::SetRun (1);
1313 int64_t streamNumber = 0;
1314 m_phy->AssignStreams (streamNumber);
1315
1316 // RX power > CCA-ED
1317 double rxPowerDbm = -50;
1318
1319 // CASE 1: send one packet followed by a second one with same power between the end of the 4us preamble detection window
1320 // and the start of L-SIG of the first packet: reception should be aborted since L-SIG cannot be decoded (SNR too low).
1321
1322 Simulator::Schedule (Seconds (1.0), &TestPhyHeadersReception::SendPacket, this, rxPowerDbm);
1323 Simulator::Schedule (Seconds (1.0) + MicroSeconds (10), &TestPhyHeadersReception::SendPacket, this, rxPowerDbm);
1324 // At 10 us, STA PHY STATE should be CCA_BUSY.
1325 Simulator::Schedule (Seconds (1.0) + MicroSeconds (10.0), &TestPhyHeadersReception::CheckPhyState, this, WifiPhyState::CCA_BUSY);
1326 // At 44us (end of PHY header), STA PHY STATE should not have moved to RX and be kept to CCA_BUSY.
1327 Simulator::Schedule (Seconds (1.0) + NanoSeconds (44000), &TestPhyHeadersReception::CheckPhyState, this, WifiPhyState::CCA_BUSY);
1328 // Since it takes 152.8us to transmit the packet, PHY should be back to IDLE at time 152.8 + 10 = 162.8us.
1329 Simulator::Schedule (Seconds (1.0) + NanoSeconds (162799), &TestPhyHeadersReception::CheckPhyState, this, WifiPhyState::CCA_BUSY);
1330 Simulator::Schedule (Seconds (1.0) + NanoSeconds (162800), &TestPhyHeadersReception::CheckPhyState, this, WifiPhyState::IDLE);
1331
1332 // CASE 2: send one packet followed by a second one 3 dB weaker between the end of the 4us preamble detection window
1333 // and the start of L-SIG of the first packet: reception should not be aborted since L-SIG can be decoded (SNR high enough).
1334
1335 Simulator::Schedule (Seconds (2.0), &TestPhyHeadersReception::SendPacket, this, rxPowerDbm);
1336 Simulator::Schedule (Seconds (2.0) + MicroSeconds (10), &TestPhyHeadersReception::SendPacket, this, rxPowerDbm - 3);
1337 // At 10 us, STA PHY STATE should be CCA_BUSY.
1338 Simulator::Schedule (Seconds (2.0) + MicroSeconds (10.0), &TestPhyHeadersReception::CheckPhyState, this, WifiPhyState::CCA_BUSY);
1339 // At 44us (end of PHY header), STA PHY STATE should have moved to RX since PHY header reception should have succeeded.
1340 Simulator::Schedule (Seconds (2.0) + NanoSeconds (43999), &TestPhyHeadersReception::CheckPhyState, this, WifiPhyState::CCA_BUSY);
1341 Simulator::Schedule (Seconds (2.0) + NanoSeconds (44000), &TestPhyHeadersReception::CheckPhyState, this, WifiPhyState::RX);
1342 // Since it takes 152.8us to transmit the packet, PHY should be back to IDLE at time 152.8us.
1343 // However, since there is a second packet transmitted with a power above CCA-ED (-62 dBm), PHY should first be seen as CCA_BUSY for 10us.
1344 Simulator::Schedule (Seconds (2.0) + NanoSeconds (152799), &TestPhyHeadersReception::CheckPhyState, this, WifiPhyState::RX);
1345 Simulator::Schedule (Seconds (2.0) + NanoSeconds (152800), &TestPhyHeadersReception::CheckPhyState, this, WifiPhyState::CCA_BUSY);
1346 Simulator::Schedule (Seconds (2.0) + NanoSeconds (162799), &TestPhyHeadersReception::CheckPhyState, this, WifiPhyState::CCA_BUSY);
1347 Simulator::Schedule (Seconds (2.0) + NanoSeconds (162800), &TestPhyHeadersReception::CheckPhyState, this, WifiPhyState::IDLE);
1348
1349 // CASE 3: send one packet followed by a second one with same power between the end of L-SIG and the start of HE-SIG of the first packet:
1350 // PHY header reception should not succeed but PHY should stay in RX state for the duration estimated from L-SIG.
1351
1352 Simulator::Schedule (Seconds (3.0), &TestPhyHeadersReception::SendPacket, this, rxPowerDbm);
1353 Simulator::Schedule (Seconds (3.0) + MicroSeconds (25), &TestPhyHeadersReception::SendPacket, this, rxPowerDbm);
1354 // At 44us (end of PHY header), STA PHY STATE should not have moved to RX (HE-SIG failed) and be kept to CCA_BUSY.
1355 Simulator::Schedule (Seconds (3.0) + MicroSeconds (44.0), &TestPhyHeadersReception::CheckPhyState, this, WifiPhyState::CCA_BUSY);
1356 // STA PHY STATE should move back to IDLE once the duration estimated from L-SIG has elapsed, i.e. at 152.8us.
1357 // However, since there is a second packet transmitted with a power above CCA-ED (-62 dBm), PHY should first be seen as CCA_BUSY for 25us.
1358 Simulator::Schedule (Seconds (3.0) + NanoSeconds (152799), &TestPhyHeadersReception::CheckPhyState, this, WifiPhyState::CCA_BUSY);
1359 Simulator::Schedule (Seconds (3.0) + NanoSeconds (152800), &TestPhyHeadersReception::CheckPhyState, this, WifiPhyState::CCA_BUSY);
1360 Simulator::Schedule (Seconds (3.0) + NanoSeconds (177799), &TestPhyHeadersReception::CheckPhyState, this, WifiPhyState::CCA_BUSY);
1361 Simulator::Schedule (Seconds (3.0) + NanoSeconds (177800), &TestPhyHeadersReception::CheckPhyState, this, WifiPhyState::IDLE);
1362
1363 // CASE 4: send one packet followed by a second one 3 dB weaker between the end of L-SIG and the start of HE-SIG of the first packet:
1364 // PHY header reception should succeed.
1365
1366 Simulator::Schedule (Seconds (4.0), &TestPhyHeadersReception::SendPacket, this, rxPowerDbm);
1367 Simulator::Schedule (Seconds (4.0) + MicroSeconds (25), &TestPhyHeadersReception::SendPacket, this, rxPowerDbm - 3);
1368 // At 10 us, STA PHY STATE should be CCA_BUSY.
1369 Simulator::Schedule (Seconds (4.0) + MicroSeconds (10.0), &TestPhyHeadersReception::CheckPhyState, this, WifiPhyState::CCA_BUSY);
1370 // At 44 us (end of HE-SIG), STA PHY STATE should move to RX since the PHY header reception should have succeeded.
1371 Simulator::Schedule (Seconds (4.0) + NanoSeconds (43999), &TestPhyHeadersReception::CheckPhyState, this, WifiPhyState::CCA_BUSY);
1372 Simulator::Schedule (Seconds (4.0) + NanoSeconds (44000), &TestPhyHeadersReception::CheckPhyState, this, WifiPhyState::RX);
1373 // STA PHY STATE should move back to IDLE once the duration estimated from L-SIG has elapsed, i.e. at 152.8us.
1374 // However, since there is a second packet transmitted with a power above CCA-ED (-62 dBm), PHY should first be seen as CCA_BUSY for 25us.
1375 Simulator::Schedule (Seconds (4.0) + NanoSeconds (152799), &TestPhyHeadersReception::CheckPhyState, this, WifiPhyState::RX);
1376 Simulator::Schedule (Seconds (4.0) + NanoSeconds (152800), &TestPhyHeadersReception::CheckPhyState, this, WifiPhyState::CCA_BUSY);
1377 Simulator::Schedule (Seconds (4.0) + NanoSeconds (177799), &TestPhyHeadersReception::CheckPhyState, this, WifiPhyState::CCA_BUSY);
1378 Simulator::Schedule (Seconds (4.0) + NanoSeconds (177800), &TestPhyHeadersReception::CheckPhyState, this, WifiPhyState::IDLE);
1379
1380 // RX power < CCA-ED
1381 rxPowerDbm = -70;
1382
1383 // CASE 5: send one packet followed by a second one with same power between the end of the 4us preamble detection window
1384 // and the start of L-SIG of the first packet: reception should be aborted since L-SIG cannot be decoded (SNR too low).
1385
1386 Simulator::Schedule (Seconds (5.0), &TestPhyHeadersReception::SendPacket, this, rxPowerDbm);
1387 Simulator::Schedule (Seconds (5.0) + MicroSeconds (10), &TestPhyHeadersReception::SendPacket, this, rxPowerDbm);
1388 // At 10 us, STA PHY STATE should be CCA_BUSY.
1389 Simulator::Schedule (Seconds (5.0) + MicroSeconds (10.0), &TestPhyHeadersReception::CheckPhyState, this, WifiPhyState::CCA_BUSY);
1390 // At 24us (end of L-SIG), STA PHY STATE stay CCA_BUSY because L-SIG reception failed and the start of a valid OFDM transmission has been detected
1391 Simulator::Schedule (Seconds (5.0) + NanoSeconds (24000), &TestPhyHeadersReception::CheckPhyState, this, WifiPhyState::CCA_BUSY);
1392
1393 // CASE 6: send one packet followed by a second one 3 dB weaker between the end of the 4us preamble detection window
1394 // and the start of L-SIG of the first packet: reception should not be aborted since L-SIG can be decoded (SNR high enough).
1395
1396 Simulator::Schedule (Seconds (6.0), &TestPhyHeadersReception::SendPacket, this, rxPowerDbm);
1397 Simulator::Schedule (Seconds (6.0) + MicroSeconds (10), &TestPhyHeadersReception::SendPacket, this, rxPowerDbm - 3);
1398 // At 10 us, STA PHY STATE should be CCA_BUSY.
1399 Simulator::Schedule (Seconds (6.0) + MicroSeconds (10.0), &TestPhyHeadersReception::CheckPhyState, this, WifiPhyState::CCA_BUSY);
1400 // At 24us (end of L-SIG), STA PHY STATE should be unchanged because L-SIG reception should have succeeded.
1401 Simulator::Schedule (Seconds (6.0) + MicroSeconds (24.0), &TestPhyHeadersReception::CheckPhyState, this, WifiPhyState::CCA_BUSY);
1402 // At 44 us (end of HE-SIG), STA PHY STATE should move to RX since the PHY header reception should have succeeded.
1403 Simulator::Schedule (Seconds (6.0) + NanoSeconds (43999), &TestPhyHeadersReception::CheckPhyState, this, WifiPhyState::CCA_BUSY);
1404 Simulator::Schedule (Seconds (6.0) + NanoSeconds (44000), &TestPhyHeadersReception::CheckPhyState, this, WifiPhyState::RX);
1405 // Since it takes 152.8us to transmit the packet, PHY should be back to CCA_BUSY at time 152.8us.
1406 Simulator::Schedule (Seconds (6.0) + NanoSeconds (152799), &TestPhyHeadersReception::CheckPhyState, this, WifiPhyState::RX);
1407 Simulator::Schedule (Seconds (6.0) + NanoSeconds (152800), &TestPhyHeadersReception::CheckPhyState, this, WifiPhyState::CCA_BUSY);
1408
1409 // CASE 7: send one packet followed by a second one with same power between the end of L-SIG and the start of HE-SIG of the first packet:
1410 // PHY header reception should not succeed but PHY should stay in RX state for the duration estimated from L-SIG.
1411
1412 Simulator::Schedule (Seconds (7.0), &TestPhyHeadersReception::SendPacket, this, rxPowerDbm);
1413 Simulator::Schedule (Seconds (7.0) + MicroSeconds (25), &TestPhyHeadersReception::SendPacket, this, rxPowerDbm);
1414 // At 10 us, STA PHY STATE should be CCA_BUSY.
1415 Simulator::Schedule (Seconds (7.0) + MicroSeconds (10.0), &TestPhyHeadersReception::CheckPhyState, this, WifiPhyState::CCA_BUSY);
1416 // At 24us (end of L-SIG), STA PHY STATE should be unchanged because L-SIG reception should have succeeded.
1417 Simulator::Schedule (Seconds (7.0) + MicroSeconds (24.0), &TestPhyHeadersReception::CheckPhyState, this, WifiPhyState::CCA_BUSY);
1418 // At 44 us (end of HE-SIG), STA PHY STATE should be not have moved to RX since reception of HE-SIG should have failed.
1419 Simulator::Schedule (Seconds (7.0) + MicroSeconds (44.0), &TestPhyHeadersReception::CheckPhyState, this, WifiPhyState::CCA_BUSY);
1420 // STA PHY STATE should keep CCA_BUSY once the duration estimated from L-SIG has elapsed, i.e. at 152.8us.
1421 Simulator::Schedule (Seconds (7.0) + NanoSeconds (152800), &TestPhyHeadersReception::CheckPhyState, this, WifiPhyState::CCA_BUSY);
1422
1423 // CASE 8: send one packet followed by a second one 3 dB weaker between the end of L-SIG and the start of HE-SIG of the first packet:
1424 // PHY header reception should succeed.
1425
1426 Simulator::Schedule (Seconds (8.0), &TestPhyHeadersReception::SendPacket, this, rxPowerDbm);
1427 Simulator::Schedule (Seconds (8.0) + MicroSeconds (25), &TestPhyHeadersReception::SendPacket, this, rxPowerDbm - 3);
1428 // At 10 us, STA PHY STATE should be CCA_BUSY.
1429 Simulator::Schedule (Seconds (8.0) + MicroSeconds (10.0), &TestPhyHeadersReception::CheckPhyState, this, WifiPhyState::CCA_BUSY);
1430 // At 24us (end of L-SIG), STA PHY STATE should be unchanged because L-SIG reception should have succeeded.
1431 Simulator::Schedule (Seconds (8.0) + MicroSeconds (24.0), &TestPhyHeadersReception::CheckPhyState, this, WifiPhyState::CCA_BUSY);
1432 // At 44 us (end of HE-SIG), STA PHY STATE should move to RX since the PHY header reception should have succeeded.
1433 Simulator::Schedule (Seconds (8.0) + NanoSeconds (43999), &TestPhyHeadersReception::CheckPhyState, this, WifiPhyState::CCA_BUSY);
1434 Simulator::Schedule (Seconds (8.0) + NanoSeconds (44000), &TestPhyHeadersReception::CheckPhyState, this, WifiPhyState::RX);
1435 // STA PHY STATE should move back to CCA_BUSY once the duration estimated from L-SIG has elapsed, i.e. at 152.8us.
1436 Simulator::Schedule (Seconds (8.0) + NanoSeconds (152799), &TestPhyHeadersReception::CheckPhyState, this, WifiPhyState::RX);
1437 Simulator::Schedule (Seconds (8.0) + NanoSeconds (152800), &TestPhyHeadersReception::CheckPhyState, this, WifiPhyState::CCA_BUSY);
1438
1439 Simulator::Run ();
1440 Simulator::Destroy ();
1441}
1442
1450{
1451public:
1453 virtual ~TestAmpduReception ();
1454
1455protected:
1456 void DoSetup (void) override;
1457 void DoTeardown (void) override;
1458
1459private:
1460 void DoRun (void) override;
1461
1469 void RxSuccess (Ptr<const WifiPsdu> psdu, RxSignalInfo rxSignalInfo,
1470 WifiTxVector txVector, std::vector<bool> statusPerMpdu);
1475 void RxFailure (Ptr<const WifiPsdu> psdu);
1486 void IncrementSuccessBitmap (uint32_t size);
1491 void IncrementFailureBitmap (uint32_t size);
1492
1496 void ResetBitmaps();
1497
1503 void SendAmpduWithThreeMpdus (double rxPowerDbm, uint32_t referencePacketSize);
1504
1509 void CheckRxSuccessBitmapAmpdu1 (uint8_t expected);
1514 void CheckRxSuccessBitmapAmpdu2 (uint8_t expected);
1519 void CheckRxFailureBitmapAmpdu1 (uint8_t expected);
1524 void CheckRxFailureBitmapAmpdu2 (uint8_t expected);
1529 void CheckRxDroppedBitmapAmpdu1 (uint8_t expected);
1534 void CheckRxDroppedBitmapAmpdu2 (uint8_t expected);
1535
1540 void CheckPhyState (WifiPhyState expectedState);
1541
1543
1546
1549
1552
1553 uint64_t m_uid;
1554};
1555
1557: TestCase ("A-MPDU reception test"),
1558 m_rxSuccessBitmapAmpdu1 (0),
1559 m_rxSuccessBitmapAmpdu2 (0),
1560 m_rxFailureBitmapAmpdu1 (0),
1561 m_rxFailureBitmapAmpdu2 (0),
1562 m_rxDroppedBitmapAmpdu1 (0),
1563 m_rxDroppedBitmapAmpdu2 (0),
1564 m_uid (0)
1565{
1566}
1567
1569{
1570 m_phy = 0;
1571}
1572
1573void
1575{
1582}
1583
1584void
1586 WifiTxVector txVector, std::vector<bool> statusPerMpdu)
1587{
1588 NS_LOG_FUNCTION (this << *psdu << rxSignalInfo << txVector);
1589 if (statusPerMpdu.empty ()) //wait for the whole A-MPDU
1590 {
1591 return;
1592 }
1593 NS_ABORT_MSG_IF (psdu->GetNMpdus () != statusPerMpdu.size (), "Should have one receive status per MPDU");
1594 auto rxOkForMpdu = statusPerMpdu.begin ();
1595 for (auto mpdu = psdu->begin (); mpdu != psdu->end (); ++mpdu)
1596 {
1597 if (*rxOkForMpdu)
1598 {
1599 IncrementSuccessBitmap ((*mpdu)->GetSize ());
1600 }
1601 else
1602 {
1603 IncrementFailureBitmap ((*mpdu)->GetSize ());
1604 }
1605 ++rxOkForMpdu;
1606 }
1607}
1608
1609void
1611{
1612 if (size == 1030) //A-MPDU 1 - MPDU #1
1613 {
1615 }
1616 else if (size == 1130) //A-MPDU 1 - MPDU #2
1617 {
1618 m_rxSuccessBitmapAmpdu1 |= (1 << 1);
1619 }
1620 else if (size == 1230) //A-MPDU 1 - MPDU #3
1621 {
1622 m_rxSuccessBitmapAmpdu1 |= (1 << 2);
1623 }
1624 else if (size == 1330) //A-MPDU 2 - MPDU #1
1625 {
1627 }
1628 else if (size == 1430) //A-MPDU 2 - MPDU #2
1629 {
1630 m_rxSuccessBitmapAmpdu2 |= (1 << 1);
1631 }
1632 else if (size == 1530) //A-MPDU 2 - MPDU #3
1633 {
1634 m_rxSuccessBitmapAmpdu2 |= (1 << 2);
1635 }
1636}
1637
1638void
1640{
1641 NS_LOG_FUNCTION (this << *psdu);
1642 for (auto mpdu = psdu->begin (); mpdu != psdu->end (); ++mpdu)
1643 {
1644 IncrementFailureBitmap ((*mpdu)->GetSize ());
1645 }
1646}
1647
1648void
1650{
1651 if (size == 1030) //A-MPDU 1 - MPDU #1
1652 {
1654 }
1655 else if (size == 1130) //A-MPDU 1 - MPDU #2
1656 {
1657 m_rxFailureBitmapAmpdu1 |= (1 << 1);
1658 }
1659 else if (size == 1230) //A-MPDU 1 - MPDU #3
1660 {
1661 m_rxFailureBitmapAmpdu1 |= (1 << 2);
1662 }
1663 else if (size == 1330) //A-MPDU 2 - MPDU #1
1664 {
1666 }
1667 else if (size == 1430) //A-MPDU 2 - MPDU #2
1668 {
1669 m_rxFailureBitmapAmpdu2 |= (1 << 1);
1670 }
1671 else if (size == 1530) //A-MPDU 2 - MPDU #3
1672 {
1673 m_rxFailureBitmapAmpdu2 |= (1 << 2);
1674 }
1675}
1676
1677void
1679{
1680 NS_LOG_FUNCTION (this << p << reason);
1681 if (p->GetSize () == 1030) //A-MPDU 1 - MPDU #1
1682 {
1684 }
1685 else if (p->GetSize () == 1130) //A-MPDU 1 - MPDU #2
1686 {
1687 m_rxDroppedBitmapAmpdu1 |= (1 << 1);
1688 }
1689 else if (p->GetSize () == 1230) //A-MPDU 1 - MPDU #3
1690 {
1691 m_rxDroppedBitmapAmpdu1 |= (1 << 2);
1692 }
1693 else if (p->GetSize () == 1330) //A-MPDU 2 - MPDU #1
1694 {
1696 }
1697 else if (p->GetSize () == 1430) //A-MPDU 2 - MPDU #2
1698 {
1699 m_rxDroppedBitmapAmpdu2 |= (1 << 1);
1700 }
1701 else if (p->GetSize () == 1530) //A-MPDU 2 - MPDU #3
1702 {
1703 m_rxDroppedBitmapAmpdu2 |= (1 << 2);
1704 }
1705}
1706
1707void
1709{
1710 NS_TEST_ASSERT_MSG_EQ (m_rxSuccessBitmapAmpdu1, expected, "RX success bitmap for A-MPDU 1 is not as expected");
1711}
1712
1713void
1715{
1716 NS_TEST_ASSERT_MSG_EQ (m_rxSuccessBitmapAmpdu2, expected, "RX success bitmap for A-MPDU 2 is not as expected");
1717}
1718
1719void
1721{
1722 NS_TEST_ASSERT_MSG_EQ (m_rxFailureBitmapAmpdu1, expected, "RX failure bitmap for A-MPDU 1 is not as expected");
1723}
1724
1725void
1727{
1728 NS_TEST_ASSERT_MSG_EQ (m_rxFailureBitmapAmpdu2, expected, "RX failure bitmap for A-MPDU 2 is not as expected");
1729}
1730
1731void
1733{
1734 NS_TEST_ASSERT_MSG_EQ (m_rxDroppedBitmapAmpdu1, expected, "RX dropped bitmap for A-MPDU 1 is not as expected");
1735}
1736
1737void
1739{
1740 NS_TEST_ASSERT_MSG_EQ (m_rxDroppedBitmapAmpdu2, expected, "RX dropped bitmap for A-MPDU 2 is not as expected");
1741}
1742
1743void
1745{
1746 WifiPhyState currentState;
1747 PointerValue ptr;
1748 m_phy->GetAttribute ("State", ptr);
1749 Ptr <WifiPhyStateHelper> state = DynamicCast <WifiPhyStateHelper> (ptr.Get<WifiPhyStateHelper> ());
1750 currentState = state->GetState ();
1751 NS_TEST_ASSERT_MSG_EQ (currentState, expectedState, "PHY State " << currentState << " does not match expected state " << expectedState << " at " << Simulator::Now ());
1752}
1753
1754void
1755TestAmpduReception::SendAmpduWithThreeMpdus (double rxPowerDbm, uint32_t referencePacketSize)
1756{
1757 WifiTxVector txVector = WifiTxVector (HePhy::GetHeMcs0 (), 0, WIFI_PREAMBLE_HE_SU, 800, 1, 1, 0, 20, true);
1758
1759 WifiMacHeader hdr;
1761 hdr.SetQosTid (0);
1762
1763 std::vector<Ptr<WifiMpdu>> mpduList;
1764 for (size_t i = 0; i < 3; ++i)
1765 {
1766 Ptr<Packet> p = Create<Packet> (referencePacketSize + i * 100);
1767 mpduList.push_back (Create<WifiMpdu> (p, hdr));
1768 }
1769 Ptr<WifiPsdu> psdu = Create<WifiPsdu> (mpduList);
1770
1771 Time txDuration = m_phy->CalculateTxDuration (psdu->GetSize (), txVector, m_phy->GetPhyBand ());
1772
1773 Ptr<WifiPpdu> ppdu = Create<HePpdu> (psdu, txVector, FREQUENCY, txDuration, WIFI_PHY_BAND_5GHZ, m_uid++);
1774
1775 Ptr<SpectrumValue> txPowerSpectrum = WifiSpectrumValueHelper::CreateHeOfdmTxPowerSpectralDensity (FREQUENCY, CHANNEL_WIDTH, DbmToW (rxPowerDbm), GUARD_WIDTH);
1776
1777 Ptr<WifiSpectrumSignalParameters> txParams = Create<WifiSpectrumSignalParameters> ();
1778 txParams->psd = txPowerSpectrum;
1779 txParams->txPhy = 0;
1780 txParams->duration = txDuration;
1781 txParams->ppdu = ppdu;
1782
1783 m_phy->StartRx (txParams);
1784}
1785
1786void
1788{
1789 m_phy = CreateObject<SpectrumWifiPhy> ();
1791 Ptr<InterferenceHelper> interferenceHelper = CreateObject<InterferenceHelper> ();
1792 m_phy->SetInterferenceHelper (interferenceHelper);
1793 Ptr<ErrorRateModel> error = CreateObject<NistErrorRateModel> ();
1794 m_phy->SetErrorRateModel (error);
1796
1800
1801 Ptr<ThresholdPreambleDetectionModel> preambleDetectionModel = CreateObject<ThresholdPreambleDetectionModel> ();
1802 preambleDetectionModel->SetAttribute ("Threshold", DoubleValue (2));
1803 m_phy->SetPreambleDetectionModel (preambleDetectionModel);
1804
1805 Ptr<SimpleFrameCaptureModel> frameCaptureModel = CreateObject<SimpleFrameCaptureModel> ();
1806 frameCaptureModel->SetAttribute ("Margin", DoubleValue (5));
1807 frameCaptureModel->SetAttribute ("CaptureWindow", TimeValue (MicroSeconds (16)));
1808 m_phy->SetFrameCaptureModel (frameCaptureModel);
1809}
1810
1811void
1813{
1814 m_phy->Dispose ();
1815 m_phy = 0;
1816}
1817
1818void
1820{
1821 RngSeedManager::SetSeed (1);
1822 RngSeedManager::SetRun (2);
1823 int64_t streamNumber = 1;
1824 double rxPowerDbm = -30;
1825 m_phy->AssignStreams (streamNumber);
1826
1828 // CASE 1: receive two A-MPDUs (containing each 3 MPDUs) where the first A-MPDU is received with power under RX sensitivity.
1829 // The second A-MPDU is received 2 microseconds after the first A-MPDU (i.e. during preamble detection).
1831
1832 // A-MPDU 1
1833 Simulator::Schedule (Seconds (1.0), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm - 100, 1000);
1834
1835 // A-MPDU 2
1836 Simulator::Schedule (Seconds (1.0) + MicroSeconds (2), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm, 1300);
1837
1838 // All MPDUs of A-MPDU 1 should have been ignored.
1839 Simulator::Schedule (Seconds (1.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu1, this, 0b00000000);
1840 Simulator::Schedule (Seconds (1.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu1, this, 0b00000000);
1841 Simulator::Schedule (Seconds (1.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu1, this, 0b00000000);
1842
1843 // All MPDUs of A-MPDU 2 should have been successfully received.
1844 Simulator::Schedule (Seconds (1.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu2, this, 0b00000111);
1845 Simulator::Schedule (Seconds (1.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu2, this, 0b00000000);
1846 Simulator::Schedule (Seconds (1.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu2, this, 0b00000000);
1847
1848 Simulator::Schedule (Seconds (1.2), &TestAmpduReception::ResetBitmaps, this);
1849
1851 // CASE 2: receive two A-MPDUs (containing each 3 MPDUs) where the second A-MPDU is received with power under RX sensitivity.
1852 // The second A-MPDU is received 2 microseconds after the first A-MPDU (i.e. during preamble detection).
1854
1855 // A-MPDU 1
1856 Simulator::Schedule (Seconds (2.0), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm, 1000);
1857
1858 // A-MPDU 2
1859 Simulator::Schedule (Seconds (2.0) + MicroSeconds (2), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm - 100, 1300);
1860
1861 // All MPDUs of A-MPDU 1 should have been received.
1862 Simulator::Schedule (Seconds (2.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu1, this, 0b00000111);
1863 Simulator::Schedule (Seconds (2.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu1, this, 0b00000000);
1864 Simulator::Schedule (Seconds (2.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu1, this, 0b00000000);
1865
1866 // All MPDUs of A-MPDU 2 should have been ignored.
1867 Simulator::Schedule (Seconds (2.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu2, this, 0b00000000);
1868 Simulator::Schedule (Seconds (2.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu2, this, 0b00000000);
1869 Simulator::Schedule (Seconds (2.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu2, this, 0b00000000);
1870
1871 Simulator::Schedule (Seconds (2.2), &TestAmpduReception::ResetBitmaps, this);
1872
1874 // CASE 3: receive two A-MPDUs (containing each 3 MPDUs) where the first A-MPDU is received with power under RX sensitivity.
1875 // The second A-MPDU is received 10 microseconds after the first A-MPDU (i.e. during the frame capture window).
1877
1878 // A-MPDU 1
1879 Simulator::Schedule (Seconds (3.0), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm - 100, 1000);
1880
1881 // A-MPDU 2
1882 Simulator::Schedule (Seconds (3.0) + MicroSeconds (10), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm, 1300);
1883
1884 // All MPDUs of A-MPDU 1 should have been ignored.
1885 Simulator::Schedule (Seconds (3.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu1, this, 0b00000000);
1886 Simulator::Schedule (Seconds (3.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu1, this, 0b00000000);
1887 Simulator::Schedule (Seconds (3.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu1, this, 0b00000000);
1888
1889 // All MPDUs of A-MPDU 2 should have been successfully received.
1890 Simulator::Schedule (Seconds (3.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu2, this, 0b00000111);
1891 Simulator::Schedule (Seconds (3.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu2, this, 0b00000000);
1892 Simulator::Schedule (Seconds (3.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu2, this, 0b00000000);
1893
1894 Simulator::Schedule (Seconds (3.2), &TestAmpduReception::ResetBitmaps, this);
1895
1897 // CASE 4: receive two A-MPDUs (containing each 3 MPDUs) where the second A-MPDU is received with power under RX sensitivity.
1898 // The second A-MPDU is received 10 microseconds after the first A-MPDU (i.e. during the frame capture window).
1900
1901 // A-MPDU 1
1902 Simulator::Schedule (Seconds (4.0), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm, 1000);
1903
1904 // A-MPDU 2
1905 Simulator::Schedule (Seconds (4.0) + MicroSeconds (10), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm - 100, 1300);
1906
1907 // All MPDUs of A-MPDU 1 should have been received.
1908 Simulator::Schedule (Seconds (4.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu1, this, 0b00000111);
1909 Simulator::Schedule (Seconds (4.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu1, this, 0b00000000);
1910 Simulator::Schedule (Seconds (4.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu1, this, 0b00000000);
1911
1912 // All MPDUs of A-MPDU 2 should have been ignored.
1913 Simulator::Schedule (Seconds (4.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu2, this, 0b00000000);
1914 Simulator::Schedule (Seconds (4.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu2, this, 0b00000000);
1915 Simulator::Schedule (Seconds (4.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu2, this, 0b00000000);
1916
1917 Simulator::Schedule (Seconds (4.2), &TestAmpduReception::ResetBitmaps, this);
1918
1920 // CASE 5: receive two A-MPDUs (containing each 3 MPDUs) where the first A-MPDU is received with power under RX sensitivity.
1921 // The second A-MPDU is received 100 microseconds after the first A-MPDU (i.e. after the frame capture window, during the payload of MPDU #1).
1923
1924 // A-MPDU 1
1925 Simulator::Schedule (Seconds (5.0), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm - 100, 1000);
1926
1927 // A-MPDU 2
1928 Simulator::Schedule (Seconds (5.0) + MicroSeconds (100), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm, 1300);
1929
1930 // All MPDUs of A-MPDU 1 should have been ignored.
1931 Simulator::Schedule (Seconds (5.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu1, this, 0b00000000);
1932 Simulator::Schedule (Seconds (5.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu1, this, 0b00000000);
1933 Simulator::Schedule (Seconds (5.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu1, this, 0b00000000);
1934
1935 // All MPDUs of A-MPDU 2 should have been successfully received.
1936 Simulator::Schedule (Seconds (5.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu2, this, 0b00000111);
1937 Simulator::Schedule (Seconds (5.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu2, this, 0b00000000);
1938 Simulator::Schedule (Seconds (5.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu2, this, 0b00000000);
1939
1940 Simulator::Schedule (Seconds (5.2), &TestAmpduReception::ResetBitmaps, this);
1941
1943 // CASE 6: receive two A-MPDUs (containing each 3 MPDUs) where the second A-MPDU is received with power under RX sensitivity.
1944 // The second A-MPDU is received 100 microseconds after the first A-MPDU (i.e. after the frame capture window, during the payload of MPDU #1).
1946
1947 // A-MPDU 1
1948 Simulator::Schedule (Seconds (6.0), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm, 1000);
1949
1950 // A-MPDU 2
1951 Simulator::Schedule (Seconds (6.0) + MicroSeconds (100), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm - 100, 1300);
1952
1953 // All MPDUs of A-MPDU 1 should have been received.
1954 Simulator::Schedule (Seconds (6.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu1, this, 0b00000111);
1955 Simulator::Schedule (Seconds (6.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu1, this, 0b00000000);
1956 Simulator::Schedule (Seconds (6.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu1, this, 0b00000000);
1957
1958 // All MPDUs of A-MPDU 2 should have been ignored.
1959 Simulator::Schedule (Seconds (6.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu2, this, 0b00000000);
1960 Simulator::Schedule (Seconds (6.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu2, this, 0b00000000);
1961 Simulator::Schedule (Seconds (6.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu2, this, 0b00000000);
1962
1963 Simulator::Schedule (Seconds (6.2), &TestAmpduReception::ResetBitmaps, this);
1964
1966 // CASE 7: receive two A-MPDUs (containing each 3 MPDUs) where the first A-MPDU is received with power under RX sensitivity.
1967 // The second A-MPDU is received during the payload of MPDU #2.
1969
1970 // A-MPDU 1
1971 Simulator::Schedule (Seconds (7.0), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm - 100, 1000);
1972
1973 // A-MPDU 2
1974 Simulator::Schedule (Seconds (7.0) + NanoSeconds (1100000), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm, 1300);
1975
1976 // All MPDUs of A-MPDU 1 should have been ignored.
1977 Simulator::Schedule (Seconds (7.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu1, this, 0b00000000);
1978 Simulator::Schedule (Seconds (7.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu1, this, 0b00000000);
1979 Simulator::Schedule (Seconds (7.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu1, this, 0b00000000);
1980
1981 // All MPDUs of A-MPDU 2 should have been successfully received.
1982 Simulator::Schedule (Seconds (7.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu2, this, 0b00000111);
1983 Simulator::Schedule (Seconds (7.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu2, this, 0b00000000);
1984 Simulator::Schedule (Seconds (7.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu2, this, 0b00000000);
1985
1986 Simulator::Schedule (Seconds (7.2), &TestAmpduReception::ResetBitmaps, this);
1987
1989 // CASE 8: receive two A-MPDUs (containing each 3 MPDUs) where the second A-MPDU is received with power under RX sensitivity.
1990 // The second A-MPDU is received during the payload of MPDU #2.
1992
1993 // A-MPDU 1
1994 Simulator::Schedule (Seconds (8.0), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm, 1000);
1995
1996 // A-MPDU 2
1997 Simulator::Schedule (Seconds (8.0) + NanoSeconds (1100000), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm - 100, 1300);
1998
1999 // All MPDUs of A-MPDU 1 should have been received.
2000 Simulator::Schedule (Seconds (8.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu1, this, 0b00000111);
2001 Simulator::Schedule (Seconds (8.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu1, this, 0b00000000);
2002 Simulator::Schedule (Seconds (8.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu1, this, 0b00000000);
2003
2004 // All MPDUs of A-MPDU 2 should have been ignored.
2005 Simulator::Schedule (Seconds (8.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu2, this, 0b00000000);
2006 Simulator::Schedule (Seconds (8.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu2, this, 0b00000000);
2007 Simulator::Schedule (Seconds (8.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu2, this, 0b00000000);
2008
2009 Simulator::Schedule (Seconds (8.2), &TestAmpduReception::ResetBitmaps, this);
2010
2012 // CASE 9: receive two A-MPDUs (containing each 3 MPDUs) with the second A-MPDU having a power 3 dB higher.
2013 // The second A-MPDU is received 2 microseconds after the first A-MPDU (i.e. during preamble detection).
2015
2016 // A-MPDU 1
2017 Simulator::Schedule (Seconds (9.0), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm, 1000);
2018
2019 // A-MPDU 2
2020 Simulator::Schedule (Seconds (9.0) + MicroSeconds (2), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm + 3, 1300);
2021
2022 // All MPDUs of A-MPDU 1 should have been dropped.
2023 Simulator::Schedule (Seconds (9.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu1, this, 0b00000000);
2024 Simulator::Schedule (Seconds (9.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu1, this, 0b00000000);
2025 Simulator::Schedule (Seconds (9.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu1, this, 0b00000111);
2026
2027 // All MPDUs of A-MPDU 2 should have been received with errors.
2028 Simulator::Schedule (Seconds (9.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu2, this, 0b00000000);
2029 Simulator::Schedule (Seconds (9.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu2, this, 0b00000111);
2030 Simulator::Schedule (Seconds (9.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu2, this, 0b00000000);
2031
2032 Simulator::Schedule (Seconds (9.2), &TestAmpduReception::ResetBitmaps, this);
2033
2035 // CASE 10: receive two A-MPDUs (containing each 3 MPDUs) with the same power.
2036 // The second A-MPDU is received 2 microseconds after the first A-MPDU (i.e. during preamble detection).
2038
2039 // A-MPDU 1
2040 Simulator::Schedule (Seconds (10.0), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm, 1000);
2041
2042 // A-MPDU 2
2043 Simulator::Schedule (Seconds (10.0) + MicroSeconds (2), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm, 1300);
2044
2045 // All MPDUs of A-MPDU 1 should have been dropped (preamble detection failed).
2046 Simulator::Schedule (Seconds (10.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu1, this, 0b00000000);
2047 Simulator::Schedule (Seconds (10.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu1, this, 0b00000000);
2048 Simulator::Schedule (Seconds (10.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu1, this, 0b00000111);
2049
2050 // All MPDUs of A-MPDU 2 should have been dropped as well.
2051 Simulator::Schedule (Seconds (10.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu2, this, 0b00000000);
2052 Simulator::Schedule (Seconds (10.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu2, this, 0b00000000);
2053 Simulator::Schedule (Seconds (10.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu2, this, 0b00000111);
2054
2055 Simulator::Schedule (Seconds (10.2), &TestAmpduReception::ResetBitmaps, this);
2056
2058 // CASE 11: receive two A-MPDUs (containing each 3 MPDUs) with the first A-MPDU having a power 3 dB higher.
2059 // The second A-MPDU is received 2 microseconds after the first A-MPDU (i.e. during preamble detection).
2061
2062 // A-MPDU 1
2063 Simulator::Schedule (Seconds (11.0), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm + 3, 1000);
2064
2065 // A-MPDU 2
2066 Simulator::Schedule (Seconds (11.0) + MicroSeconds (2), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm, 1300);
2067
2068 // All MPDUs of A-MPDU 1 should have been received with errors.
2069 Simulator::Schedule (Seconds (11.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu1, this, 0b00000000);
2070 Simulator::Schedule (Seconds (11.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu1, this, 0b00000111);
2071 Simulator::Schedule (Seconds (11.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu1, this, 0b00000000);
2072
2073 // All MPDUs of A-MPDU 2 should have been dropped.
2074 Simulator::Schedule (Seconds (11.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu2, this, 0b00000000);
2075 Simulator::Schedule (Seconds (11.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu2, this, 0b00000000);
2076 Simulator::Schedule (Seconds (11.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu2, this, 0b00000111);
2077
2078 Simulator::Schedule (Seconds (11.2), &TestAmpduReception::ResetBitmaps, this);
2079
2081 // CASE 12: receive two A-MPDUs (containing each 3 MPDUs) with the second A-MPDU having a power 3 dB higher.
2082 // The second A-MPDU is received 10 microseconds after the first A-MPDU (i.e. during the frame capture window).
2084
2085 // A-MPDU 1
2086 Simulator::Schedule (Seconds (12.0), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm, 1000);
2087
2088 // A-MPDU 2
2089 Simulator::Schedule (Seconds (12.0) + MicroSeconds (10), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm + 3, 1300);
2090
2091 // All MPDUs of A-MPDU 1 should have been received with errors (PHY header reception failed and thus incorrect decoding of payload).
2092 Simulator::Schedule (Seconds (12.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu1, this, 0b00000000);
2093 Simulator::Schedule (Seconds (12.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu1, this, 0b00000000);
2094 Simulator::Schedule (Seconds (12.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu1, this, 0b00000111);
2095
2096 // All MPDUs of A-MPDU 2 should have been dropped (even though TX power is higher, it is not high enough to get the PHY reception switched)
2097 Simulator::Schedule (Seconds (12.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu2, this, 0b00000000);
2098 Simulator::Schedule (Seconds (12.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu2, this, 0b00000000);
2099 Simulator::Schedule (Seconds (12.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu2, this, 0b00000111);
2100
2101 Simulator::Schedule (Seconds (12.2), &TestAmpduReception::ResetBitmaps, this);
2102
2104 // CASE 13: receive two A-MPDUs (containing each 3 MPDUs) with the same power.
2105 // The second A-MPDU is received 10 microseconds after the first A-MPDU (i.e. during the frame capture window).
2107
2108 // A-MPDU 1
2109 Simulator::Schedule (Seconds (13.0), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm, 1000);
2110
2111 // A-MPDU 2
2112 Simulator::Schedule (Seconds (13.0) + MicroSeconds (10), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm, 1300);
2113
2114 // All MPDUs of A-MPDU 1 should have been received with errors (PHY header reception failed and thus incorrect decoding of payload).
2115 Simulator::Schedule (Seconds (13.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu1, this, 0b00000000);
2116 Simulator::Schedule (Seconds (13.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu1, this, 0b00000000);
2117 Simulator::Schedule (Seconds (13.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu1, this, 0b00000111);
2118
2119 // All MPDUs of A-MPDU 2 should have been dropped as well.
2120 Simulator::Schedule (Seconds (13.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu2, this, 0b00000000);
2121 Simulator::Schedule (Seconds (13.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu2, this, 0b00000000);
2122 Simulator::Schedule (Seconds (13.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu2, this, 0b00000111);
2123
2124 Simulator::Schedule (Seconds (13.2), &TestAmpduReception::ResetBitmaps, this);
2125
2127 // CASE 14: receive two A-MPDUs (containing each 3 MPDUs) with the first A-MPDU having a power 3 dB higher.
2128 // The second A-MPDU is received 10 microseconds after the first A-MPDU (i.e. during the frame capture window).
2130
2131 // A-MPDU 1
2132 Simulator::Schedule (Seconds (14.0), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm + 3, 1000);
2133
2134 // A-MPDU 2
2135 Simulator::Schedule (Seconds (14.0) + MicroSeconds (10), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm, 1300);
2136
2137 // All MPDUs of A-MPDU 1 should have been received with errors.
2138 Simulator::Schedule (Seconds (14.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu1, this, 0b00000000);
2139 Simulator::Schedule (Seconds (14.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu1, this, 0b00000111);
2140 Simulator::Schedule (Seconds (14.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu1, this, 0b00000000);
2141
2142 // All MPDUs of A-MPDU 2 should have been dropped.
2143 Simulator::Schedule (Seconds (14.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu2, this, 0b00000000);
2144 Simulator::Schedule (Seconds (14.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu2, this, 0b00000000);
2145 Simulator::Schedule (Seconds (14.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu2, this, 0b00000111);
2146
2147 Simulator::Schedule (Seconds (14.2), &TestAmpduReception::ResetBitmaps, this);
2148
2150 // CASE 15: receive two A-MPDUs (containing each 3 MPDUs) with the second A-MPDU having a power 6 dB higher.
2151 // The second A-MPDU is received 10 microseconds after the first A-MPDU (i.e. during the frame capture window).
2153
2154 // A-MPDU 1
2155 Simulator::Schedule (Seconds (15.0), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm, 1000);
2156
2157 // A-MPDU 2
2158 Simulator::Schedule (Seconds (15.0) + MicroSeconds (10), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm + 6, 1300);
2159
2160 // All MPDUs of A-MPDU 1 should have been dropped because PHY reception switched to A-MPDU 2.
2161 Simulator::Schedule (Seconds (15.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu1, this, 0b00000000);
2162 Simulator::Schedule (Seconds (15.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu1, this, 0b00000000);
2163 Simulator::Schedule (Seconds (15.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu1, this, 0b00000111);
2164
2165 // All MPDUs of A-MPDU 2 should have been successfully received
2166 Simulator::Schedule (Seconds (15.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu2, this, 0b00000111);
2167 Simulator::Schedule (Seconds (15.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu2, this, 0b00000000);
2168 Simulator::Schedule (Seconds (15.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu2, this, 0b00000000);
2169
2170 Simulator::Schedule (Seconds (15.2), &TestAmpduReception::ResetBitmaps, this);
2171
2173 // CASE 16: receive two A-MPDUs (containing each 3 MPDUs) with the first A-MPDU having a power 6 dB higher.
2174 // The second A-MPDU is received 10 microseconds after the first A-MPDU (i.e. during the frame capture window).
2176
2177 // A-MPDU 1
2178 Simulator::Schedule (Seconds (16.0), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm + 6, 1000);
2179
2180 // A-MPDU 2
2181 Simulator::Schedule (Seconds (16.0) + MicroSeconds (10), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm, 1300);
2182
2183 // All MPDUs of A-MPDU 1 should have been successfully received.
2184 Simulator::Schedule (Seconds (16.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu1, this, 0b00000111);
2185 Simulator::Schedule (Seconds (16.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu1, this, 0b00000000);
2186 Simulator::Schedule (Seconds (16.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu1, this, 0b00000000);
2187
2188 // All MPDUs of A-MPDU 2 should have been dropped.
2189 Simulator::Schedule (Seconds (16.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu2, this, 0b00000000);
2190 Simulator::Schedule (Seconds (16.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu2, this, 0b00000000);
2191 Simulator::Schedule (Seconds (16.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu2, this, 0b00000111);
2192
2193 Simulator::Schedule (Seconds (16.2), &TestAmpduReception::ResetBitmaps, this);
2194
2196 // CASE 17: receive two A-MPDUs (containing each 3 MPDUs) with the second A-MPDU having a power 6 dB higher.
2197 // The second A-MPDU is received 25 microseconds after the first A-MPDU (i.e. after the frame capture window, but still during PHY header).
2199
2200 // A-MPDU 1
2201 Simulator::Schedule (Seconds (17.0), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm, 1000);
2202
2203 // A-MPDU 2
2204 Simulator::Schedule (Seconds (17.0) + MicroSeconds (25), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm + 6, 1300);
2205
2206 // All MPDUs of A-MPDU 1 should have been received with errors.
2207 Simulator::Schedule (Seconds (17.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu1, this, 0b00000000);
2208 Simulator::Schedule (Seconds (17.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu1, this, 0b00000000);
2209 Simulator::Schedule (Seconds (17.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu1, this, 0b00000111);
2210
2211 // All MPDUs of A-MPDU 2 should have been dropped (no reception switch, MPDUs dropped because PHY is already in RX state).
2212 Simulator::Schedule (Seconds (17.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu2, this, 0b00000000);
2213 Simulator::Schedule (Seconds (17.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu2, this, 0b00000000);
2214 Simulator::Schedule (Seconds (17.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu2, this, 0b00000111);
2215
2216 Simulator::Schedule (Seconds (17.2), &TestAmpduReception::ResetBitmaps, this);
2217
2219 // CASE 18: receive two A-MPDUs (containing each 3 MPDUs) with the first A-MPDU having a power 6 dB higher.
2220 // The second A-MPDU is received 25 microseconds after the first A-MPDU (i.e. after the frame capture window, but still during PHY header).
2222
2223 // A-MPDU 1
2224 Simulator::Schedule (Seconds (18.0), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm + 6, 1000);
2225
2226 // A-MPDU 2
2227 Simulator::Schedule (Seconds (18.0) + MicroSeconds (25), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm, 1300);
2228
2229 // All MPDUs of A-MPDU 1 should have been successfully received.
2230 Simulator::Schedule (Seconds (18.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu1, this, 0b00000111);
2231 Simulator::Schedule (Seconds (18.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu1, this, 0b00000000);
2232 Simulator::Schedule (Seconds (18.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu1, this, 0b00000000);
2233
2234 // All MPDUs of A-MPDU 2 should have been dropped.
2235 Simulator::Schedule (Seconds (18.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu2, this, 0b00000000);
2236 Simulator::Schedule (Seconds (18.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu2, this, 0b00000000);
2237 Simulator::Schedule (Seconds (18.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu2, this, 0b00000111);
2238
2239 Simulator::Schedule (Seconds (18.2), &TestAmpduReception::ResetBitmaps, this);
2240
2242 // CASE 19: receive two A-MPDUs (containing each 3 MPDUs) with the same power.
2243 // The second A-MPDU is received 25 microseconds after the first A-MPDU (i.e. after the frame capture window, but still during PHY header).
2245
2246 // A-MPDU 1
2247 Simulator::Schedule (Seconds (19.0), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm, 1000);
2248
2249 // A-MPDU 2
2250 Simulator::Schedule (Seconds (19.0) + MicroSeconds (25), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm, 1300);
2251
2252 // All MPDUs of A-MPDU 1 should have been received with errors.
2253 Simulator::Schedule (Seconds (19.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu1, this, 0b00000000);
2254 Simulator::Schedule (Seconds (19.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu1, this, 0b00000000);
2255 Simulator::Schedule (Seconds (19.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu1, this, 0b00000111);
2256
2257 // All MPDUs of A-MPDU 2 should have been dropped.
2258 Simulator::Schedule (Seconds (19.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu2, this, 0b00000000);
2259 Simulator::Schedule (Seconds (19.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu2, this, 0b00000000);
2260 Simulator::Schedule (Seconds (19.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu2, this, 0b00000111);
2261
2262 Simulator::Schedule (Seconds (19.2), &TestAmpduReception::ResetBitmaps, this);
2263
2265 // CASE 20: receive two A-MPDUs (containing each 3 MPDUs) with the second A-MPDU having a power 6 dB higher.
2266 // The second A-MPDU is received 100 microseconds after the first A-MPDU (i.e. during the payload of MPDU #1).
2268
2269 // A-MPDU 1
2270 Simulator::Schedule (Seconds (20.0), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm, 1000);
2271
2272 // A-MPDU 2
2273 Simulator::Schedule (Seconds (20.0) + MicroSeconds (100), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm + 6, 1300);
2274
2275 // All MPDUs of A-MPDU 1 should have been received with errors.
2276 Simulator::Schedule (Seconds (20.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu1, this, 0b00000000);
2277 Simulator::Schedule (Seconds (20.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu1, this, 0b00000111);
2278 Simulator::Schedule (Seconds (20.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu1, this, 0b00000000);
2279
2280 // All MPDUs of A-MPDU 2 should have been dropped (no reception switch, MPDUs dropped because PHY is already in RX state).
2281 Simulator::Schedule (Seconds (20.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu2, this, 0b00000000);
2282 Simulator::Schedule (Seconds (20.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu2, this, 0b00000000);
2283 Simulator::Schedule (Seconds (20.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu2, this, 0b00000111);
2284
2285 Simulator::Schedule (Seconds (20.2), &TestAmpduReception::ResetBitmaps, this);
2286
2288 // CASE 21: receive two A-MPDUs (containing each 3 MPDUs) with the first A-MPDU having a power 6 dB higher.
2289 // The second A-MPDU is received 100 microseconds after the first A-MPDU (i.e. during the payload of MPDU #1).
2291
2292 // A-MPDU 1
2293 Simulator::Schedule (Seconds (21.0), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm + 6, 1000);
2294
2295 // A-MPDU 2
2296 Simulator::Schedule (Seconds (21.0) + MicroSeconds (100), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm, 1300);
2297
2298 // All MPDUs of A-MPDU 1 should have been successfully received.
2299 Simulator::Schedule (Seconds (21.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu1, this, 0b00000111);
2300 Simulator::Schedule (Seconds (21.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu1, this, 0b00000000);
2301 Simulator::Schedule (Seconds (21.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu1, this, 0b00000000);
2302
2303 // All MPDUs of A-MPDU 2 should have been dropped.
2304 Simulator::Schedule (Seconds (21.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu2, this, 0b00000000);
2305 Simulator::Schedule (Seconds (21.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu2, this, 0b00000000);
2306 Simulator::Schedule (Seconds (21.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu2, this, 0b00000111);
2307
2308 Simulator::Schedule (Seconds (21.2), &TestAmpduReception::ResetBitmaps, this);
2309
2311 // CASE 22: receive two A-MPDUs (containing each 3 MPDUs) with the same power.
2312 // The second A-MPDU is received 100 microseconds after the first A-MPDU (i.e. during the payload of MPDU #1).
2314
2315 // A-MPDU 1
2316 Simulator::Schedule (Seconds (22.0), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm, 1000);
2317
2318 // A-MPDU 2
2319 Simulator::Schedule (Seconds (22.0) + MicroSeconds (100), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm, 1300);
2320
2321 // All MPDUs of A-MPDU 1 should have been received with errors.
2322 Simulator::Schedule (Seconds (22.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu1, this, 0b00000000);
2323 Simulator::Schedule (Seconds (22.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu1, this, 0b00000111);
2324 Simulator::Schedule (Seconds (22.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu1, this, 0b00000000);
2325
2326 // All MPDUs of A-MPDU 2 should have been dropped.
2327 Simulator::Schedule (Seconds (22.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu2, this, 0b00000000);
2328 Simulator::Schedule (Seconds (22.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu2, this, 0b00000000);
2329 Simulator::Schedule (Seconds (22.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu2, this, 0b00000111);
2330
2331 Simulator::Schedule (Seconds (22.2), &TestAmpduReception::ResetBitmaps, this);
2332
2334 // CASE 23: receive two A-MPDUs (containing each 3 MPDUs) with the same power.
2335 // The second A-MPDU is received during the payload of MPDU #2.
2337
2338 // A-MPDU 1
2339 Simulator::Schedule (Seconds (23.0), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm, 1000);
2340
2341 // A-MPDU 2
2342 Simulator::Schedule (Seconds (23.0) + NanoSeconds (1100000), &TestAmpduReception::SendAmpduWithThreeMpdus, this, rxPowerDbm, 1300);
2343
2344 // The first MPDU of A-MPDU 1 should have been successfully received (no interference).
2345 // The two other MPDUs failed due to interference and are marked as failure (and dropped).
2346 Simulator::Schedule (Seconds (23.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu1, this, 0b00000001);
2347 Simulator::Schedule (Seconds (23.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu1, this, 0b00000110);
2348 Simulator::Schedule (Seconds (23.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu1, this, 0b00000000);
2349
2350 // The two first MPDUs of A-MPDU 2 are dropped because PHY is already in RX state (receiving A-MPDU 1).
2351 // The last MPDU of A-MPDU 2 is interference free (A-MPDU 1 transmission is finished) but is dropped because its PHY preamble and header were not received.
2352 Simulator::Schedule (Seconds (23.1), &TestAmpduReception::CheckRxSuccessBitmapAmpdu2, this, 0b00000000);
2353 Simulator::Schedule (Seconds (23.1), &TestAmpduReception::CheckRxFailureBitmapAmpdu2, this, 0b00000000);
2354 Simulator::Schedule (Seconds (23.1), &TestAmpduReception::CheckRxDroppedBitmapAmpdu2, this, 0b00000111);
2355
2356 Simulator::Schedule (Seconds (23.2), &TestAmpduReception::ResetBitmaps, this);
2357
2358 Simulator::Run ();
2359 Simulator::Destroy ();
2360}
2361
2383{
2384public:
2390
2397 void Dropped (std::string context, Ptr<const Packet> packet, WifiPhyRxfailureReason reason);
2401 void CheckResults (void);
2402
2403private:
2404 void DoRun (void) override;
2405 uint16_t m_dropped;
2406};
2407
2409 : TestCase ("Check correct behavior when a STA is receiving a transmission using an unsupported modulation"),
2410 m_dropped (0)
2411{
2412}
2413
2415{
2416}
2417
2418void
2421{
2422 // Print if the test is executed through test-runner
2423 if (reason == RXING)
2424 {
2425 std::cout << "Dropped a packet because already receiving" << std::endl;
2426 m_dropped++;
2427 }
2428}
2429
2430void
2432{
2433 uint16_t m_nStations = 2;
2434 NetDeviceContainer m_staDevices;
2435 NetDeviceContainer m_apDevices;
2436
2437 // RngSeedManager::SetSeed (1);
2438 // RngSeedManager::SetRun (40);
2439 int64_t streamNumber = 100;
2440
2442 wifiApNode.Create (1);
2443
2445 wifiStaNodes.Create (m_nStations);
2446
2447 Ptr<MultiModelSpectrumChannel> spectrumChannel = CreateObject<MultiModelSpectrumChannel> ();
2448 Ptr<FriisPropagationLossModel> lossModel = CreateObject<FriisPropagationLossModel> ();
2449 spectrumChannel->AddPropagationLossModel (lossModel);
2451 CreateObject<ConstantSpeedPropagationDelayModel> ();
2452 spectrumChannel->SetPropagationDelayModel (delayModel);
2453
2455 phy.SetChannel (spectrumChannel);
2456
2457 Config::SetDefault ("ns3::WifiRemoteStationManager::RtsCtsThreshold", UintegerValue (65535));
2458
2460 wifi.SetRemoteStationManager ("ns3::IdealWifiManager");
2461
2463 mac.SetType ("ns3::StaWifiMac", "QosSupported", BooleanValue (true), "Ssid",
2464 SsidValue (Ssid ("non-existent-ssid")));
2465
2466 wifi.SetStandard (WIFI_STANDARD_80211ax);
2467 m_staDevices.Add (wifi.Install (phy, mac, wifiStaNodes.Get (0)));
2468 wifi.SetStandard (WIFI_STANDARD_80211ac);
2469 m_staDevices.Add (wifi.Install (phy, mac, wifiStaNodes.Get (1)));
2470
2471 wifi.SetStandard (WIFI_STANDARD_80211ax);
2472 mac.SetType ("ns3::ApWifiMac", "QosSupported", BooleanValue (true), "Ssid",
2473 SsidValue (Ssid ("wifi-backoff-ssid")), "BeaconInterval",
2474 TimeValue (MicroSeconds (102400)), "EnableBeaconJitter", BooleanValue (false));
2475
2476 m_apDevices = wifi.Install (phy, mac, wifiApNode);
2477
2478 // schedule association requests at different times
2479 Time init = MilliSeconds (100);
2481
2482 for (uint16_t i = 0; i < m_nStations; i++)
2483 {
2484 dev = DynamicCast<WifiNetDevice> (m_staDevices.Get (i));
2485 Simulator::Schedule (init + i * MicroSeconds (102400), &WifiMac::SetSsid, dev->GetMac (),
2486 Ssid ("wifi-backoff-ssid"));
2487 }
2488
2489 // Assign fixed streams to random variables in use
2490 wifi.AssignStreams (m_apDevices, streamNumber);
2491
2493 Ptr<ListPositionAllocator> positionAlloc = CreateObject<ListPositionAllocator> ();
2494
2495 positionAlloc->Add (Vector (0.0, 0.0, 0.0));
2496 positionAlloc->Add (Vector (1.0, 0.0, 0.0));
2497 positionAlloc->Add (Vector (0.0, 1.0, 0.0));
2498 positionAlloc->Add (Vector (-1.0, 0.0, 0.0));
2499 mobility.SetPositionAllocator (positionAlloc);
2500
2501 mobility.SetMobilityModel ("ns3::ConstantPositionMobilityModel");
2502 mobility.Install (wifiApNode);
2503 mobility.Install (wifiStaNodes);
2504
2505 // set the TXOP limit on BE AC
2506 dev = DynamicCast<WifiNetDevice> (m_apDevices.Get (0));
2507 PointerValue ptr;
2508 dev->GetMac ()->GetAttribute ("BE_Txop", ptr);
2509
2510 PacketSocketHelper packetSocket;
2511 packetSocket.Install (wifiApNode);
2512 packetSocket.Install (wifiStaNodes);
2513
2514 // UL Traffic
2515 for (uint16_t i = 0; i < m_nStations; i++)
2516 {
2517 PacketSocketAddress socket;
2518 socket.SetSingleDevice (m_staDevices.Get (0)->GetIfIndex ());
2519 socket.SetPhysicalAddress (m_apDevices.Get (0)->GetAddress ());
2520 socket.SetProtocol (1);
2521 Ptr<PacketSocketClient> client = CreateObject<PacketSocketClient> ();
2522 client->SetAttribute ("PacketSize", UintegerValue (1500));
2523 client->SetAttribute ("MaxPackets", UintegerValue (200));
2524 client->SetAttribute ("Interval", TimeValue (MicroSeconds (0)));
2525 client->SetRemote (socket);
2526 wifiStaNodes.Get (i)->AddApplication (client);
2527 client->SetStartTime (MicroSeconds (400000));
2528 client->SetStopTime (Seconds (1.0));
2529 Ptr<PacketSocketClient> legacyStaClient = CreateObject<PacketSocketClient> ();
2530 legacyStaClient->SetAttribute ("PacketSize", UintegerValue (1500));
2531 legacyStaClient->SetAttribute ("MaxPackets", UintegerValue (200));
2532 legacyStaClient->SetAttribute ("Interval", TimeValue (MicroSeconds (0)));
2533 legacyStaClient->SetRemote (socket);
2534 wifiStaNodes.Get (i)->AddApplication (legacyStaClient);
2535 legacyStaClient->SetStartTime (MicroSeconds (400000));
2536 legacyStaClient->SetStopTime (Seconds (1.0));
2537 Ptr<PacketSocketServer> server = CreateObject<PacketSocketServer> ();
2538 server->SetLocal (socket);
2539 wifiApNode.Get (0)->AddApplication (server);
2540 server->SetStartTime (Seconds (0.0));
2541 server->SetStopTime (Seconds (1.0));
2542 }
2543
2544 // Trace dropped packets
2545 Config::Connect ("/NodeList/*/DeviceList/*/$ns3::WifiNetDevice/Phy/PhyRxDrop",
2547
2548 Simulator::Stop (Seconds (1));
2549 Simulator::Run ();
2550
2551 CheckResults ();
2552
2553 Simulator::Destroy ();
2554}
2555
2556void
2558{
2559 NS_TEST_EXPECT_MSG_EQ (m_dropped, 0, "Dropped some packets unexpectedly");
2560}
2561
2569{
2570public:
2572};
2573
2575 : TestSuite ("wifi-phy-reception", UNIT)
2576{
2579 AddTestCase (new TestSimpleFrameCaptureModel, TestCase::QUICK);
2580 AddTestCase (new TestPhyHeadersReception, TestCase::QUICK);
2581 AddTestCase (new TestAmpduReception, TestCase::QUICK);
2582 AddTestCase (new TestUnsupportedModulationReception (), TestCase::QUICK);
2583}
2584
void Run(ObjectFactory &factory, uint32_t pop, uint32_t total, uint32_t runs, Ptr< RandomVariableStream > eventStream, bool calRev)
Perform the runs for a single scheduler type.
A-MPDU reception test.
void RxSuccess(Ptr< const WifiPsdu > psdu, RxSignalInfo rxSignalInfo, WifiTxVector txVector, std::vector< bool > statusPerMpdu)
RX success function.
void IncrementSuccessBitmap(uint32_t size)
Increment reception success bitmap.
uint8_t m_rxDroppedBitmapAmpdu2
bitmap of dropped MPDUs in A-MPDU #2
void CheckRxSuccessBitmapAmpdu2(uint8_t expected)
Check the RX success bitmap for A-MPDU 2.
void DoTeardown(void) override
Implementation to do any local setup required for this TestCase.
void CheckRxDroppedBitmapAmpdu1(uint8_t expected)
Check the RX dropped bitmap for A-MPDU 1.
uint8_t m_rxSuccessBitmapAmpdu1
bitmap of successfully received MPDUs in A-MPDU #1
uint8_t m_rxFailureBitmapAmpdu1
bitmap of unsuccessfully received MPDUs in A-MPDU #1
uint8_t m_rxFailureBitmapAmpdu2
bitmap of unsuccessfully received MPDUs in A-MPDU #2
void DoRun(void) override
Implementation to actually run this TestCase.
void RxDropped(Ptr< const Packet > p, WifiPhyRxfailureReason reason)
RX dropped function.
void SendAmpduWithThreeMpdus(double rxPowerDbm, uint32_t referencePacketSize)
Send A-MPDU with 3 MPDUs of different size (i-th MSDU will have 100 bytes more than (i-1)-th).
void RxFailure(Ptr< const WifiPsdu > psdu)
RX failure function.
void CheckRxFailureBitmapAmpdu2(uint8_t expected)
Check the RX failure bitmap for A-MPDU 2.
uint8_t m_rxDroppedBitmapAmpdu1
bitmap of dropped MPDUs in A-MPDU #1
void IncrementFailureBitmap(uint32_t size)
Increment reception failure bitmap.
void ResetBitmaps()
Reset bitmaps function.
void CheckPhyState(WifiPhyState expectedState)
Check the PHY state.
void DoSetup(void) override
Implementation to do any local setup required for this TestCase.
void CheckRxSuccessBitmapAmpdu1(uint8_t expected)
Check the RX success bitmap for A-MPDU 1.
void CheckRxFailureBitmapAmpdu1(uint8_t expected)
Check the RX failure bitmap for A-MPDU 1.
uint8_t m_rxSuccessBitmapAmpdu2
bitmap of successfully received MPDUs in A-MPDU #2
Ptr< SpectrumWifiPhy > m_phy
Phy.
void CheckRxDroppedBitmapAmpdu2(uint8_t expected)
Check the RX dropped bitmap for A-MPDU 2.
Test PHY state upon success or failure of L-SIG and SIG-A.
void SendPacket(double rxPowerDbm)
Send packet function.
Ptr< SpectrumWifiPhy > m_phy
Phy.
void DoSetup(void) override
Implementation to do any local setup required for this TestCase.
void CheckPhyState(WifiPhyState expectedState)
Schedule now to check the PHY state.
void DoCheckPhyState(WifiPhyState expectedState)
Check the PHY state now.
uint64_t m_uid
the UID to use for the PPDU
void DoRun(void) override
Implementation to actually run this TestCase.
void DoTeardown(void) override
Implementation to do any local setup required for this TestCase.
Simple frame capture model test.
void Expect1000BPacketReceived()
Verify whether 1000 bytes packet has been received.
bool m_rxDropped1500B
count dropped packets with 1500B payload
void Expect1500BPacketDropped()
Verify whether 1500 bytes packet has been dropped.
void Expect1000BPacketDropped()
Verify whether 1000 bytes packet has been dropped.
void DoRun(void) override
Implementation to actually run this TestCase.
void SendPacket(double rxPowerDbm, uint32_t packetSize)
Send packet function.
Ptr< SpectrumWifiPhy > m_phy
Phy.
void RxSuccess(Ptr< const WifiPsdu > psdu, RxSignalInfo rxSignalInfo, WifiTxVector txVector, std::vector< bool > statusPerMpdu)
Spectrum wifi receive success function.
void RxDropped(Ptr< const Packet > p, WifiPhyRxfailureReason reason)
RX dropped function.
void DoSetup(void) override
Implementation to do any local setup required for this TestCase.
bool m_rxSuccess1000B
count received packets with 1000B payload
bool m_rxSuccess1500B
count received packets with 1500B payload
void Expect1500BPacketReceived()
Verify whether 1500 bytes packet has been received.
uint64_t m_uid
the UID to use for the PPDU
void DoTeardown(void) override
Implementation to do any local setup required for this TestCase.
bool m_rxDropped1000B
count dropped packets with 1000B payload
Preamble detection test w/o frame capture.
void CheckPhyState(WifiPhyState expectedState)
Schedule now to check the PHY state.
void SendPacket(double rxPowerDbm)
Send packet function.
void DoTeardown(void) override
Implementation to do any local setup required for this TestCase.
void RxFailure(Ptr< const WifiPsdu > psdu)
Spectrum wifi receive failure function.
void RxSuccess(Ptr< const WifiPsdu > psdu, RxSignalInfo rxSignalInfo, WifiTxVector txVector, std::vector< bool > statusPerMpdu)
Spectrum wifi receive success function.
void DoCheckPhyState(WifiPhyState expectedState)
Check the PHY state now.
void DoSetup(void) override
Implementation to do any local setup required for this TestCase.
void DoRun(void) override
Implementation to actually run this TestCase.
void CheckRxPacketCount(uint32_t expectedSuccessCount, uint32_t expectedFailureCount)
Check the number of received packets.
Preamble detection test w/o frame capture.
void DoTeardown(void) override
Implementation to do any local setup required for this TestCase.
void DoSetup(void) override
Implementation to do any local setup required for this TestCase.
void RxSuccess(Ptr< const WifiPsdu > psdu, RxSignalInfo rxSignalInfo, WifiTxVector txVector, std::vector< bool > statusPerMpdu)
Spectrum wifi receive success function.
void CheckRxPacketCount(uint32_t expectedSuccessCount, uint32_t expectedFailureCount)
Check the number of received packets.
void DoCheckPhyState(WifiPhyState expectedState)
Check the PHY state now.
void DoRun(void) override
Implementation to actually run this TestCase.
void SendPacket(double rxPowerDbm)
Send packet function.
void CheckPhyState(WifiPhyState expectedState)
Schedule now to check the PHY state.
void RxFailure(Ptr< const WifiPsdu > psdu)
Spectrum wifi receive failure function.
Unsupported Modulation Reception Test This test creates a mixed network, in which an HE STA and a VHT...
void DoRun(void) override
Implementation to actually run this TestCase.
void Dropped(std::string context, Ptr< const Packet > packet, WifiPhyRxfailureReason reason)
Callback invoked when PHY drops an incoming packet.
void CheckResults(void)
Check correctness of transmitted frames.
uint16_t m_dropped
number of packets dropped by the AP because it was already receiving
wifi PHY reception Test Suite
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:41
Helper class used to assign positions and mobility models to nodes.
holds a vector of ns3::NetDevice pointers
void Add(NetDeviceContainer other)
Append the contents of another NetDeviceContainer to the end of this container.
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.
bool TraceConnectWithoutContext(std::string name, const CallbackBase &cb)
Connect a TraceSource to a Callback without a context.
Definition: object-base.cc:364
void GetAttribute(std::string name, AttributeValue &value) const
Get the value of an attribute, raising fatal errors if unsuccessful.
Definition: object-base.cc:294
void Dispose(void)
Dispose of this Object.
Definition: object.cc:214
uint32_t GetSize(void) const
Returns the the size in bytes of the packet (including the zero-filled initial payload).
Definition: packet.h:856
an address for a packet socket
void SetProtocol(uint16_t protocol)
Set the protocol.
void SetPhysicalAddress(const Address address)
Set the destination address.
void SetSingleDevice(uint32_t device)
Set the address to match only a specified NetDevice.
Give ns3::PacketSocket powers to ns3::Node.
void Install(Ptr< Node > node) const
Aggregate an instance of a ns3::PacketSocketFactory onto the provided node.
Hold objects of type Ptr<T>.
Definition: pointer.h:37
Ptr< T > Get(void) const
Definition: pointer.h:201
Make it easy to create and manage PHY objects for the spectrum model.
void StartRx(Ptr< SpectrumSignalParameters > rxParams)
Input method for delivering a signal from the spectrum channel and low-level PHY interface to this Sp...
The IEEE 802.11 SSID Information Element.
Definition: ssid.h:36
AttributeValue implementation for Ssid.
encapsulates test code
Definition: test.h:994
void AddTestCase(TestCase *testCase, TestDuration duration=QUICK)
Add an individual child TestCase to this test suite.
Definition: test.cc:299
A suite of tests to run.
Definition: test.h:1188
Simulation virtual time values and global simulation resolution.
Definition: nstime.h:104
AttributeValue implementation for Time.
Definition: nstime.h:1309
Hold an unsigned integer type.
Definition: uinteger.h:44
helps to create WifiNetDevice objects
Definition: wifi-helper.h:322
Implements the IEEE 802.11 MAC header.
void SetType(WifiMacType type, bool resetToDsFromDs=true)
Set Type/Subtype values with the correct values depending on the given type.
void SetQosTid(uint8_t tid)
Set the TID for the QoS header.
create MAC layers for a ns3::WifiNetDevice.
Ptr< WifiMac > GetMac(void) const
virtual void SetInterferenceHelper(const Ptr< InterferenceHelper > helper)
Sets the interference helper.
Definition: wifi-phy.cc:600
void SetErrorRateModel(const Ptr< ErrorRateModel > model)
Sets the error rate model.
Definition: wifi-phy.cc:608
WifiPhyBand GetPhyBand(void) const
Get the configured Wi-Fi band.
Definition: wifi-phy.cc:938
void SetReceiveErrorCallback(RxErrorCallback callback)
Definition: wifi-phy.cc:417
virtual void ConfigureStandard(WifiStandard standard)
Configure the PHY-level parameters for different Wi-Fi standard.
Definition: wifi-phy.cc:883
static Time CalculateTxDuration(uint32_t size, const WifiTxVector &txVector, WifiPhyBand band, uint16_t staId=SU_STA_ID)
Definition: wifi-phy.cc:1389
void SetOperatingChannel(const ChannelTuple &channelTuple)
If the standard for this object has not been set yet, store the given channel settings.
Definition: wifi-phy.cc:993
void SetPreambleDetectionModel(const Ptr< PreambleDetectionModel > preambleDetectionModel)
Sets the preamble detection model.
Definition: wifi-phy.cc:628
void SetReceiveOkCallback(RxOkCallback callback)
Definition: wifi-phy.cc:411
void SetFrameCaptureModel(const Ptr< FrameCaptureModel > frameCaptureModel)
Sets the frame capture model.
Definition: wifi-phy.cc:622
std::tuple< uint8_t, uint16_t, int, uint8_t > ChannelTuple
Tuple identifying an operating channel.
Definition: wifi-phy.h:839
virtual int64_t AssignStreams(int64_t stream)
Assign a fixed random variable stream number to the random variables used by this model.
Definition: wifi-phy.cc:2038
This objects implements the PHY state machine of the Wifi device.
uint32_t GetSize(void) const
Return the size of the PSDU in bytes.
Definition: wifi-psdu.cc:260
std::size_t GetNMpdus(void) const
Return the number of MPDUs constituting the PSDU.
Definition: wifi-psdu.cc:313
std::vector< Ptr< WifiMpdu > >::const_iterator begin(void) const
Return a const iterator to the first MPDU.
Definition: wifi-psdu.cc:319
bool IsAggregate(void) const
Return true if the PSDU is an S-MPDU or A-MPDU.
Definition: wifi-psdu.cc:81
bool IsSingle(void) const
Return true if the PSDU is an S-MPDU.
Definition: wifi-psdu.cc:75
std::vector< Ptr< WifiMpdu > >::const_iterator end(void) const
Return a const iterator to past-the-last MPDU.
Definition: wifi-psdu.cc:331
This class mimics the TXVECTOR which is to be passed to the PHY in order to define the parameters whi...
#define NS_ASSERT(condition)
At runtime, in debugging builds, if this condition is not true, the program prints the source file,...
Definition: assert.h:67
void SetDefault(std::string name, const AttributeValue &value)
Definition: config.cc:849
void Connect(std::string path, const CallbackBase &cb)
Definition: config.cc:920
#define NS_ABORT_MSG_IF(cond, msg)
Abnormal program termination if a condition is true, with a message.
Definition: abort.h:108
#define NS_LOG_COMPONENT_DEFINE(name)
Define a Log component with a specific name.
Definition: log.h:206
#define NS_LOG_FUNCTION(parameters)
If log level LOG_FUNCTION is enabled, this macro will output all input parameters separated by ",...
Time Now(void)
create an ns3::Time instance which contains the current simulation time.
Definition: simulator.cc:287
#define NS_TEST_ASSERT_MSG_EQ(actual, limit, msg)
Test that an actual and expected (limit) value are equal and report and abort if not.
Definition: test.h:141
#define NS_TEST_EXPECT_MSG_EQ(actual, limit, msg)
Test that an actual and expected (limit) value are equal and report if not.
Definition: test.h:240
Time MicroSeconds(uint64_t value)
Construct a Time in the indicated unit.
Definition: nstime.h:1261
Time NanoSeconds(uint64_t value)
Construct a Time in the indicated unit.
Definition: nstime.h:1269
Time Seconds(double value)
Construct a Time in the indicated unit.
Definition: nstime.h:1245
Time MilliSeconds(uint64_t value)
Construct a Time in the indicated unit.
Definition: nstime.h:1253
WifiPhyRxfailureReason
Enumeration of the possible reception failure reasons.
@ WIFI_STANDARD_80211ax
@ WIFI_STANDARD_80211ac
@ WIFI_PREAMBLE_HE_SU
@ WIFI_PHY_BAND_5GHZ
The 5 GHz band.
Definition: wifi-phy-band.h:37
Every class exported by the ns3 library is enclosed in the ns3 namespace.
Callback< R, Args... > MakeCallback(R(T::*memPtr)(Args...), OBJ objPtr)
Build Callbacks for class method members which take varying numbers of arguments and potentially retu...
Definition: callback.h:661
double DbmToW(double dBm)
Convert from dBm to Watts.
Definition: wifi-utils.cc:37
@ WIFI_MAC_QOSDATA
mac
Definition: third.py:87
wifi
Definition: third.py:90
wifiApNode
Definition: third.py:81
mobility
Definition: third.py:98
wifiStaNodes
Definition: third.py:79
phy
Definition: third.py:84
RxSignalInfo structure containing info on the received signal.
Definition: phy-entity.h:69
static const uint8_t CHANNEL_NUMBER
static const uint16_t GUARD_WIDTH
static const uint16_t CHANNEL_WIDTH
static WifiPhyReceptionTestSuite wifiPhyReceptionTestSuite
the test suite
static const uint32_t FREQUENCY
WifiPhyState
The state of the PHY layer.
@ CCA_BUSY
The PHY layer has sense the medium busy through the CCA mechanism.
@ RX
The PHY layer is receiving a packet.
@ IDLE
The PHY layer is IDLE.
static const uint32_t packetSize
Packet size generated at the AP.