7#include "ns3/boolean.h"
8#include "ns3/constant-position-mobility-model.h"
10#include "ns3/interference-helper.h"
12#include "ns3/mobility-helper.h"
13#include "ns3/multi-model-spectrum-channel.h"
14#include "ns3/nist-error-rate-model.h"
15#include "ns3/non-communicating-net-device.h"
16#include "ns3/ofdm-ppdu.h"
17#include "ns3/pointer.h"
18#include "ns3/spectrum-wifi-helper.h"
19#include "ns3/spectrum-wifi-phy.h"
20#include "ns3/string.h"
22#include "ns3/waveform-generator.h"
23#include "ns3/wifi-mac-header.h"
24#include "ns3/wifi-net-device.h"
25#include "ns3/wifi-phy-listener.h"
26#include "ns3/wifi-psdu.h"
27#include "ns3/wifi-spectrum-phy-interface.h"
28#include "ns3/wifi-spectrum-signal-parameters.h"
29#include "ns3/wifi-spectrum-value-helper.h"
30#include "ns3/wifi-utils.h"
80 return std::any_of(
m_rxing.cbegin(),
m_rxing.cend(), [](
const auto& rxing) {
92 bool IsBandTracked(
const std::vector<WifiSpectrumBandFrequencies>& startStopFreqs)
const
96 if (band.frequencies == startStopFreqs)
152 const std::vector<bool>& statusPerMpdu);
161 void DoRun()
override;
199 const auto txDuration =
200 m_phy->CalculateTxDuration(psdu->GetSize(), txVector,
m_phy->GetPhyBand());
210 txParams->psd = txPowerSpectrum;
211 txParams->txPhy =
nullptr;
212 txParams->duration = txDuration;
213 txParams->ppdu = ppdu;
229 const std::vector<bool>& statusPerMpdu)
256 m_phy->SetInterferenceHelper(interferenceHelper);
258 m_phy->SetErrorRateModel(error);
259 m_phy->SetDevice(dev);
260 m_phy->AddChannel(spectrumChannel);
263 m_phy->SetReceiveOkCallback(
265 m_phy->SetReceiveErrorCallback(
268 node->AddDevice(dev);
343 const std::vector<Time>& )
override
412 void DoRun()
override;
425 m_listener = std::make_shared<TestPhyListener>();
440 "Didn't receive NotifyCcaBusyStart (once preamble is detected + prolonged by L-SIG "
441 "reception, then switched to Rx by at the beginning of data)");
470 void DoRun()
override;
497 :
TestCase(
"SpectrumWifiPhy test RX filters"),
498 m_txChannelWidth(
MHz_u{20}),
499 m_rxChannelWidth(
MHz_u{20})
540 for (
const auto& [band, powerW] : rxPowersW)
543 "band: (" << band <<
") -> powerW=" << powerW
544 << (powerW > 0.0 ?
" (" + std::to_string(
WToDbm(powerW)) +
" dBm)" :
""));
547 size_t numBands = rxPowersW.size();
560 "Total number of bands handled by the receiver is incorrect");
564 auto it = rxPowersW.find(band);
565 NS_LOG_INFO(
"powerW total band: " << it->second <<
" (" <<
WToDbm(it->second) <<
" dBm)");
566 int totalRxPower =
static_cast<int>(
WToDbm(it->second) + 0.5);
567 int expectedTotalRxPower;
572 expectedTotalRxPower = 16;
577 expectedTotalRxPower =
581 expectedTotalRxPower,
582 "Total received power is not correct");
587 it = rxPowersW.find(band);
588 NS_LOG_INFO(
"powerW in primary 20 MHz channel: " << it->second <<
" (" <<
WToDbm(it->second)
590 const auto rxPowerPrimaryChannel20 =
static_cast<int>(
WToDbm(it->second) + 0.5);
591 const auto expectedRxPowerPrimaryChannel20 =
594 expectedRxPowerPrimaryChannel20,
595 "Received power in the primary 20 MHz band is not correct");
607 lossModel->SetFrequency(5.180e9);
608 spectrumChannel->AddPropagationLossModel(lossModel);
610 spectrumChannel->SetPropagationDelayModel(delayModel);
625 txNode->AggregateObject(apMobility);
626 txNode->AddDevice(txDev);
640 rxNode->AggregateObject(sta1Mobility);
641 rxNode->AddDevice(rxDev);
663 txFrequency =
MHz_u{5180};
666 txFrequency =
MHz_u{5190};
669 txFrequency =
MHz_u{5210};
672 txFrequency =
MHz_u{5250};
689 rxFrequency =
MHz_u{5180};
692 rxFrequency =
MHz_u{5190};
695 rxFrequency =
MHz_u{5210};
698 rxFrequency =
MHz_u{5250};
802 void DoRun()
override;
813 void RunOne(
const std::vector<uint8_t>& channelNumberPerSegment,
816 const std::vector<WifiSpectrumBandIndices>& expectedIndices,
817 const std::vector<WifiSpectrumBandFrequencies>& expectedFrequencies);
823 :
TestCase(
"SpectrumWifiPhy test bands calculations")
835 lossModel->SetFrequency(5.180e9);
836 spectrumChannel->AddPropagationLossModel(lossModel);
838 spectrumChannel->SetPropagationDelayModel(delayModel);
844 m_phy->SetInterferenceHelper(interferenceHelper);
846 m_phy->SetErrorRateModel(errorModel);
847 m_phy->SetDevice(dev);
848 m_phy->AddChannel(spectrumChannel);
851 node->AddDevice(dev);
863 const std::vector<uint8_t>& channelNumberPerSegment,
866 const std::vector<WifiSpectrumBandIndices>& expectedIndices,
867 const std::vector<WifiSpectrumBandFrequencies>& expectedFrequencies)
870 for (
auto channelNumber : channelNumberPerSegment)
877 channelSegments.emplace_back(channelInfo->number, channelInfo->width, channelInfo->band, 0);
879 m_phy->SetOperatingChannel(channelSegments);
881 const auto& bandInfo =
m_phy->GetBand(bandWidth, bandIndex);
882 NS_ASSERT(expectedIndices.size() == expectedFrequencies.size());
883 NS_ASSERT(expectedIndices.size() == bandInfo.indices.size());
884 NS_ASSERT(expectedFrequencies.size() == bandInfo.frequencies.size());
885 for (std::size_t i = 0; i < expectedIndices.size(); ++i)
887 NS_ASSERT(bandInfo.indices.at(i).first == expectedIndices.at(i).first);
889 expectedIndices.at(i).first,
890 "Incorrect start indice for segment " << i);
892 expectedIndices.at(i).second,
893 "Incorrect stop indice for segment " << i);
895 expectedFrequencies.at(i).first,
896 "Incorrect start frequency for segment " << i);
898 expectedFrequencies.at(i).second,
899 "Incorrect stop frequency for segment " << i);
906 const uint32_t indicesPer20MhzBand = 256;
907 const MHz_u channelWidth{160};
908 const uint8_t channelNumberContiguous160Mhz =
910 const std::vector<uint8_t> channelNumberPerSegment = {42,
913 const MHz_u separationWidth{240};
914 for (
bool contiguous160Mhz : {
true ,
false })
916 const auto guardWidth = contiguous160Mhz ? channelWidth : (channelWidth / 2);
918 std::vector<WifiSpectrumBandIndices> previousExpectedIndices{};
919 std::vector<WifiSpectrumBandFrequencies> previousExpectedFrequencies{};
922 const uint32_t expectedStartIndice = guardStopIndice + 1;
925 std::vector<WifiSpectrumBandIndices> expectedIndices{
926 {expectedStartIndice, expectedStopIndice}};
928 const Hz_u expectedStopFrequency =
MHzToHz(5170 + bandWidth);
929 std::vector<WifiSpectrumBandFrequencies> expectedFrequencies{
930 {expectedStartFrequency, expectedStopFrequency}};
931 const std::size_t numBands = (channelWidth / bandWidth);
932 for (std::size_t i = 0; i < numBands; ++i)
934 if ((bandWidth != channelWidth) && (i >= (numBands / 2)))
937 expectedIndices.at(0).first++;
939 if ((bandWidth == channelWidth) && !contiguous160Mhz)
943 expectedIndices = previousExpectedIndices;
944 expectedFrequencies = previousExpectedFrequencies;
946 else if ((i == (numBands / 2)) && !contiguous160Mhz)
948 expectedIndices.at(0).first +=
950 expectedIndices.at(0).second +=
952 expectedFrequencies.at(0).first +=
MHzToHz(separationWidth);
953 expectedFrequencies.at(0).second +=
MHzToHz(separationWidth);
955 RunOne(contiguous160Mhz ? std::vector<uint8_t>{channelNumberContiguous160Mhz}
956 : channelNumberPerSegment,
960 expectedFrequencies);
961 if (!contiguous160Mhz && (bandWidth == (channelWidth / 2)))
963 previousExpectedIndices.emplace_back(expectedIndices.front());
964 previousExpectedFrequencies.emplace_back(expectedFrequencies.front());
966 expectedIndices.at(0).first = expectedIndices.at(0).second + 1;
967 expectedIndices.at(0).second =
968 expectedIndices.at(0).first +
970 expectedFrequencies.at(0).first +=
MHzToHz(bandWidth);
971 expectedFrequencies.at(0).second +=
MHzToHz(bandWidth);
997 void DoRun()
override;
1005 void SwitchChannel(
const std::vector<uint8_t>& channelNumberPerSegment);
1016 const std::vector<std::vector<WifiSpectrumBandFrequencies>>& expectedTrackedBands,
1017 const std::vector<std::vector<WifiSpectrumBandFrequencies>>& expectedUntrackedBands);
1027 void RunOne(
const std::vector<uint8_t>& channelNumberPerSegmentBeforeSwitching,
1028 const std::vector<uint8_t>& channelNumberPerSegmentAfterSwitching,
1029 const std::vector<std::vector<WifiSpectrumBandFrequencies>>& expectedTrackedBands,
1030 const std::vector<std::vector<WifiSpectrumBandFrequencies>>& expectedUntrackedBand);
1036 :
TestCase(
"SpectrumWifiPhy test channel switching for non-contiguous operating channels")
1048 lossModel->SetFrequency(5.180e9);
1049 spectrumChannel->AddPropagationLossModel(lossModel);
1051 spectrumChannel->SetPropagationDelayModel(delayModel);
1064 node->AddDevice(dev);
1079 for (
auto channelNumber : channelNumberPerSegment)
1086 channelSegments.emplace_back(channelInfo->number, channelInfo->width, channelInfo->band, 0);
1093 const std::vector<std::vector<WifiSpectrumBandFrequencies>>& expectedTrackedBands,
1094 const std::vector<std::vector<WifiSpectrumBandFrequencies>>& expectedUntrackedBands)
1101 auto printBand = [](
const std::vector<WifiSpectrumBandFrequencies>& v) {
1102 std::stringstream ss;
1103 for (
const auto& [start, stop] : v)
1105 ss <<
"[" << start <<
"-" << stop <<
"] ";
1109 for (
const auto& expectedTrackedBand : expectedTrackedBands)
1111 auto bandTracked = interferenceHelper->IsBandTracked(expectedTrackedBand);
1114 "Band " << printBand(expectedTrackedBand) <<
" is not tracked");
1116 for (
const auto& expectedUntrackedBand : expectedUntrackedBands)
1118 auto bandTracked = interferenceHelper->IsBandTracked(expectedUntrackedBand);
1121 "Band " << printBand(expectedUntrackedBand)
1122 <<
" is unexpectedly tracked");
1128 const std::vector<uint8_t>& channelNumberPerSegmentBeforeSwitching,
1129 const std::vector<uint8_t>& channelNumberPerSegmentAfterSwitching,
1130 const std::vector<std::vector<WifiSpectrumBandFrequencies>>& expectedTrackedBands,
1131 const std::vector<std::vector<WifiSpectrumBandFrequencies>>& expectedUntrackedBands)
1138 channelNumberPerSegmentBeforeSwitching);
1143 channelNumberPerSegmentAfterSwitching);
1148 expectedTrackedBands,
1149 expectedUntrackedBands);
1248 void DoRun()
override;
1258 void RunOne(
const std::vector<uint8_t>& channelNumbers,
1259 MHz_u interferenceCenterFrequency,
1260 MHz_u interferenceBandWidth,
1261 bool expectSuccess);
1269 void SwitchChannel(
const std::vector<uint8_t>& channelNumbers);
1298 const std::vector<bool>& statusPerMpdu);
1322 :
TestCase(
"SpectrumWifiPhy test 80+80MHz transmission"),
1323 m_countRxSuccessSta(0),
1324 m_countRxFailureSta(0)
1333 for (
auto channelNumber : channelNumbers)
1340 channelSegments.emplace_back(channelInfo->number, channelInfo->width, channelInfo->band, 0);
1342 m_phyAp->SetOperatingChannel(channelSegments);
1343 m_phySta->SetOperatingChannel(channelSegments);
1368 m_phyAp->Send(psdu, txVector);
1390 const std::vector<bool>& )
1409 "Reception should be "
1410 << (expectSuccess ?
"successful" :
"unsuccessful"));
1421 spectrumChannel->AddPropagationLossModel(lossModel);
1423 spectrumChannel->SetPropagationDelayModel(delayModel);
1429 m_phyAp->SetInterferenceHelper(apInterferenceHelper);
1431 m_phyAp->SetErrorRateModel(apErrorModel);
1433 m_phyAp->AddChannel(spectrumChannel);
1436 m_phyAp->SetMobility(apMobility);
1438 apNode->AggregateObject(apMobility);
1439 apNode->AddDevice(apDev);
1445 m_phySta->SetInterferenceHelper(staInterferenceHelper);
1447 m_phySta->SetErrorRateModel(staErrorModel);
1449 m_phySta->AddChannel(spectrumChannel);
1455 m_phySta->SetMobility(staMobility);
1457 staNode->AggregateObject(staMobility);
1458 staNode->AddDevice(staDev);
1466 interfererNode->AddDevice(interfererDev);
1482 MHz_u interferenceCenterFrequency,
1483 MHz_u interferenceBandWidth,
1496 BandInfo bandInfo{.
fl =
MHzToHz(interferenceCenterFrequency - (interferenceBandWidth / 2)),
1497 .fc =
MHzToHz(interferenceCenterFrequency),
1498 .fh =
MHzToHz(interferenceCenterFrequency + (interferenceBandWidth / 2))};
1501 Watt_u interferencePower{0.1};
1502 *interferencePsd = interferencePower / (interferenceBandWidth * 20e6);
1629 ChannelSwitchScenario chanSwitchScenario);
1634 void DoRun()
override;
1647 uint8_t channelNumber,
1649 std::optional<std::size_t> listenerIndex);
1682 const std::vector<bool>& statusPerMpdu);
1701 bool interferencesExpected);
1711 bool interferencesExpected);
1730 const std::vector<std::size_t>& expectedConnectedPhysPerChannel);
1742 bool expectedCcaBusyIndication,
1743 Time switchingDelay,
1744 Time propagationDelay);
1771 std::vector<uint32_t>
1773 std::vector<uint32_t>
1782 bool trackSignalsInactiveInterfaces,
1784 :
TestCase{
"SpectrumWifiPhy test operation with multiple RF interfaces"},
1785 m_trackSignalsInactiveInterfaces{trackSignalsInactiveInterfaces},
1786 m_chanSwitchScenario{chanSwitchScenario}
1793 uint8_t channelNumber,
1795 std::optional<std::size_t> listenerIndex)
1797 NS_LOG_FUNCTION(
this << phy << band << +channelNumber << channelWidth);
1801 listener->m_notifyMaybeCcaBusyStart = 0;
1802 listener->m_ccaBusyStart =
Seconds(0);
1803 listener->m_ccaBusyEnd =
Seconds(0);
1818 NS_LOG_FUNCTION(
this << phy << txPower << payloadSize << phy->GetCurrentFrequencyRange()
1819 << phy->GetChannelWidth() << phy->GetChannelNumber());
1843 phy->SetTxPowerStart(txPower);
1844 phy->SetTxPowerEnd(txPower);
1854 const auto payloadBytes = packet->GetSize() - 30;
1855 NS_LOG_FUNCTION(
this << index << payloadBytes << phy->GetCurrentFrequencyRange()
1856 << phy->GetChannelWidth() << phy->GetChannelNumber());
1866 const std::vector<bool>& )
1883 bool interferencesExpected)
1896 interferencesExpected);
1902 bool interferencesExpected)
1906 phy->GetAttribute(
"InterferenceHelper", ptr);
1909 const auto energyDuration = interferenceHelper->GetEnergyDuration(
Watt_u{0}, band);
1911 interferencesExpected,
1912 "Incorrect interferences detection");
1922 const std::vector<std::size_t>& expectedConnectedPhysPerChannel)
1924 NS_LOG_FUNCTION(
this << index << expectedNumRx << expectedNumRxSuccess << expectedRxBytes
1925 << expectedFrequencyRangeActiveRfInterface);
1926 const auto phy =
m_rxPhys.at(index);
1927 std::size_t numActiveInterfaces = 0;
1928 for (
const auto& [freqRange, interface] : phy->GetSpectrumPhyInterfaces())
1930 const auto expectedActive = (freqRange == expectedFrequencyRangeActiveRfInterface);
1931 const auto isActive = (
interface == phy->GetCurrentInterface());
1935 numActiveInterfaces++;
1943 expectedConnectedPhysPerChannel.at(i),
1944 "Incorrect number of PHYs attached to the spectrum channel");
1948 expectedNumRxSuccess,
1949 "Unexpected amount of successfully received packets");
1952 "Unexpected amount of unsuccessfully received packets");
1954 expectedNumRxSuccess,
1955 "Unexpected amount of RX payload start indication");
1960 bool expectedCcaBusyIndication,
1961 Time switchingDelay,
1962 Time propagationDelay)
1964 const auto expectedCcaBusyStart =
1966 const auto expectedCcaBusyEnd =
1968 NS_LOG_FUNCTION(
this << index << expectedCcaBusyIndication << expectedCcaBusyStart
1969 << expectedCcaBusyEnd);
1971 const auto ccaBusyIndication = (listener->m_notifyMaybeCcaBusyStart > 0);
1972 const auto ccaBusyStart = listener->m_ccaBusyStart;
1973 const auto ccaBusyEnd = listener->m_ccaBusyEnd;
1975 expectedCcaBusyIndication,
1976 "CCA busy indication check failed");
1986 phy->GetAttribute(
"InterferenceHelper", ptr);
2005 for (std::size_t rxPhyIndex = 0; rxPhyIndex <
m_rxPhys.size(); ++rxPhyIndex)
2007 auto txPhy =
m_txPhys.at(rxPhyIndex);
2009 txPhy->GetPhyBand(),
2010 txPhy->GetChannelNumber(),
2011 txPhy->GetChannelWidth(),
2047 struct SpectrumPhyInterfaceInfo
2052 std::string bandName;
2064 const std::vector<SpectrumPhyInterfaceInfo> interfaces{
2070 for (std::size_t i = 0; i < interfaces.size(); ++i)
2074 spectrumChannel->SetPropagationDelayModel(delayModel);
2075 std::ostringstream oss;
2076 oss <<
"{" << +interfaces.at(i).number <<
", 0, " << interfaces.at(i).bandName <<
", 0}";
2078 phyHelper.
AddChannel(spectrumChannel, interfaces.at(i).range);
2083 mac.SetType(
"ns3::ApWifiMac",
"BeaconGeneration",
BooleanValue(
false));
2084 phyHelper.
Set(
"TrackSignalsFromInactiveInterfaces",
BooleanValue(
false));
2085 auto apDevice = wifi.Install(phyHelper, mac, wifiApNode.Get(0));
2087 mac.SetType(
"ns3::StaWifiMac",
"ActiveProbing",
BooleanValue(
false));
2088 phyHelper.
Set(
"TrackSignalsFromInactiveInterfaces",
2090 auto staDevice = wifi.Install(phyHelper, mac, wifiStaNode.
Get(0));
2095 positionAlloc->Add(Vector(0.0, 0.0, 0.0));
2096 positionAlloc->Add(Vector(10.0, 0.0, 0.0));
2097 mobility.SetPositionAllocator(positionAlloc);
2099 mobility.SetMobilityModel(
"ns3::ConstantPositionMobilityModel");
2100 mobility.Install(wifiApNode);
2101 mobility.Install(wifiStaNode);
2103 for (std::size_t i = 0; i < interfaces.size(); ++i)
2113 const auto index =
m_rxPhys.size();
2120 rxPhy->TraceConnectWithoutContext(
2124 rxPhy->SetReceiveOkCallback(
2126 rxPhy->SetReceiveErrorCallback(
2129 auto listener = std::make_shared<TestPhyListener>();
2130 rxPhy->RegisterListener(listener);
2163 const dBm_u ccaEdThreshold{-62.0};
2164 const auto txAfterChannelSwitchDelay =
2169 const auto checkResultsDelay =
2171 const auto flushResultsDelay =
2173 const auto txOngoingAfterTxStartedDelay =
2181 std::vector<std::size_t> expectedConnectedPhysPerChannel =
2185 std::vector<std::size_t>{2, 2, 2, 2};
2188 for (std::size_t i = 0; i < 4; ++i)
2198 for (std::size_t j = 0; j < 4; ++j)
2202 const auto& expectedFreqRange = txPhy->GetCurrentFrequencyRange();
2207 txPpduPhy->GetCurrentFrequencyRange(),
2208 txPpduPhy->GetBand(txPpduPhy->GetChannelWidth(), 0),
2216 (i == j) ? 1000 : 0,
2218 expectedConnectedPhysPerChannel);
2226 for (std::size_t i = 0; i < 4; ++i)
2236 const auto& expectedFreqRange = txPpduPhy->GetCurrentFrequencyRange();
2237 for (std::size_t j = 0; j < 4; ++j)
2241 for (std::size_t k = 0; k < expectedConnectedPhysPerChannel.size(); ++k)
2243 expectedConnectedPhysPerChannel.at(k) = (k == i) ? 5 : 1;
2251 txPpduPhy->GetPhyBand(),
2252 txPpduPhy->GetChannelNumber(),
2253 txPpduPhy->GetChannelWidth(),
2259 txPpduPhy->GetCurrentFrequencyRange(),
2260 txPpduPhy->GetBand(txPpduPhy->GetChannelWidth(), 0),
2270 expectedConnectedPhysPerChannel);
2279 const auto secondSpectrumChannelIndex = 1;
2280 auto channel36TxPhy =
m_txPhys.at(secondSpectrumChannelIndex);
2281 const auto& expectedFreqRange = channel36TxPhy->GetCurrentFrequencyRange();
2282 for (std::size_t i = 0; i < 4; ++i)
2292 for (std::size_t j = 0; j < 4; ++j)
2296 for (std::size_t k = 0; k < expectedConnectedPhysPerChannel.size(); ++k)
2298 expectedConnectedPhysPerChannel.at(k) =
2299 (k == secondSpectrumChannelIndex) ? 5 : 1;
2314 (i == secondSpectrumChannelIndex) ? 1 : 0,
2315 (i == secondSpectrumChannelIndex) ? 1 : 0,
2316 (i == secondSpectrumChannelIndex) ? 1000 : 0,
2318 expectedConnectedPhysPerChannel);
2326 for (
const auto txPower : {
dBm_u{-60} ,
dBm_u{-70} })
2328 for (std::size_t i = 0; i < 4; ++i)
2330 for (std::size_t j = 0; j < 4; ++j)
2334 txPpduPhy->GetPrimaryChannelNumber(
MHz_u{20}),
2338 txPpduPhy->GetPhyBand());
2339 for (
auto bw = txPpduPhy->GetChannelWidth(); bw >=
MHz_u{20}; bw /= 2)
2341 const auto& channelInfo =
2346 txPpduPhy->GetPhyBand(),
2363 for (std::size_t k = 0; k < 4; ++k)
2365 if ((i != j) && (k == i))
2369 const auto expectCcaBusyIndication =
2370 (k == i) ? (txPower >= ccaEdThreshold)
2372 ? ((txPower >= ccaEdThreshold) ? (j == k) :
false)
2375 delay + checkResultsDelay,
2379 expectCcaBusyIndication,
2380 txOngoingAfterTxStartedDelay,
2417 txPpduPhy->GetPhyBand(),
2418 txPpduPhy->GetChannelNumber(),
2419 txPpduPhy->GetChannelWidth(),
2438 txPpduPhy->GetPhyBand(),
2439 txPpduPhy->GetChannelNumber(),
2440 txPpduPhy->GetChannelWidth(),
2454 delay + checkResultsDelay,
2462 txPpduPhy->GetCurrentFrequencyRange(),
2463 expectedConnectedPhysPerChannel);
2484 txPpduPhy->GetPhyBand(),
2485 txPpduPhy->GetChannelNumber(),
2486 txPpduPhy->GetChannelWidth(),
2506 m_txPhys.at(0)->GetChannelNumber(),
2517 txPpduPhy->GetPhyBand(),
2518 txPpduPhy->GetChannelNumber(),
2519 txPpduPhy->GetChannelWidth(),
2548 m_rxPhys.at(2)->GetChannelNumber(),
2559 txPpduPhy->GetPhyBand(),
2560 txPpduPhy->GetChannelNumber(),
2561 txPpduPhy->GetChannelWidth(),
2581 txPpduPhy->GetCurrentFrequencyRange(),
2582 expectedConnectedPhysPerChannel);
2612 void DoRun()
override;
2616 :
TestCase(
"Check PHY interfaces added to PHY instances using helper")
2627 phyHelper.
Set(0,
"ChannelSettings",
StringValue(
"{2, 0, BAND_2_4GHZ, 0}"));
2628 phyHelper.
Set(1,
"ChannelSettings",
StringValue(
"{36, 0, BAND_5GHZ, 0}"));
2629 phyHelper.
Set(2,
"ChannelSettings",
StringValue(
"{1, 0, BAND_6GHZ, 0}"));
2647 "Incorrect number of PHY interfaces added to PHY link ID 0");
2654 "Incorrect number of PHY interfaces added to PHY link ID 1");
2661 "Incorrect number of PHY interfaces added to PHY link ID 2");
2674 "Incorrect number of PHY interfaces added to PHY link ID 0");
2677 "Incorrect PHY interfaces added to PHY link ID 0");
2683 "Incorrect number of PHY interfaces added to PHY link ID 1");
2686 "Incorrect PHY interfaces added to PHY link ID 1");
2692 "Incorrect number of PHY interfaces added to PHY link ID 2");
2695 "Incorrect PHY interfaces added to PHY link ID 2");
2706 "Incorrect number of PHY interfaces added to PHY link ID 0");
2709 "Incorrect PHY interfaces added to PHY link ID 0");
2712 "Incorrect PHY interfaces added to PHY link ID 0");
2718 "Incorrect number of PHY interfaces added to PHY link ID 1");
2721 "Incorrect PHY interfaces added to PHY link ID 1");
2727 "Incorrect number of PHY interfaces added to PHY link ID 2");
2730 "Incorrect PHY interfaces added to PHY link ID 2");
2741 "Incorrect number of PHY interfaces added to PHY link ID 0");
2744 "Incorrect PHY interfaces added to PHY link ID 0");
2747 "Incorrect PHY interfaces added to PHY link ID 0");
2750 "Incorrect PHY interfaces added to PHY link ID 0");
2756 "Incorrect number of PHY interfaces added to PHY link ID 1");
2759 "Incorrect PHY interfaces added to PHY link ID 0");
2762 "Incorrect PHY interfaces added to PHY link ID 0");
2765 "Incorrect PHY interfaces added to PHY link ID 0");
2771 "Incorrect number of PHY interfaces added to PHY link ID 2");
2774 "Incorrect PHY interfaces added to PHY link ID 0");
2777 "Incorrect PHY interfaces added to PHY link ID 0");
2780 "Incorrect PHY interfaces added to PHY link ID 0");
2809 TestCase::Duration::QUICK);
2813 TestCase::Duration::QUICK);
2817 TestCase::Duration::QUICK);
Extended InterferenceHelper class for the purpose of the tests.
static TypeId GetTypeId()
Get the type ID.
bool IsRxing() const
Indicate whether the interference helper is in receiving state.
bool IsBandTracked(const std::vector< WifiSpectrumBandFrequencies > &startStopFreqs) const
Indicate whether a given band is tracked by the interference helper.
Extended SpectrumWifiPhy class for the purpose of the tests.
virtual WifiSpectrumBandInfo GetBand(MHz_u bandWidth, uint8_t bandIndex=0)=0
Get the info of a given band.
Test 80+80MHz transmission.
SpectrumWifiPhy80Plus80Test()
void StopInterference()
Stop interference function.
void DoSetup() override
Implementation to do any local setup required for this TestCase.
Ptr< SpectrumWifiPhy > m_phyAp
PHY of AP.
void RunOne(const std::vector< uint8_t > &channelNumbers, MHz_u interferenceCenterFrequency, MHz_u interferenceBandWidth, bool expectSuccess)
Run one function.
uint32_t m_countRxSuccessSta
count RX success for STA
void DoRun() override
Implementation to actually run this TestCase.
Ptr< WaveformGenerator > m_phyInterferer
PHY of interferer.
void RxSuccessSta(Ptr< const WifiPsdu > psdu, RxSignalInfo rxSignalInfo, const WifiTxVector &txVector, const std::vector< bool > &statusPerMpdu)
Receive success function for STA.
void SwitchChannel(const std::vector< uint8_t > &channelNumbers)
Switch channel function.
Ptr< SpectrumWifiPhy > m_phySta
PHY of STA.
void RxFailureSta(Ptr< const WifiPsdu > psdu)
Receive failure function for STA.
uint32_t m_countRxFailureSta
count RX failure for STA
void DoTeardown() override
Implementation to do any local setup required for this TestCase.
void GenerateInterference(Ptr< SpectrumValue > interferencePsd, Time duration)
Generate interference function.
void CheckResults(bool expectSuccess)
Verify results.
void Send160MhzPpdu()
Send 160MHz PPDU function.
Spectrum Wifi Phy Basic Test.
void DoSetup() override
Implementation to do any local setup required for this TestCase.
void DoRun() override
Implementation to actually run this TestCase.
~SpectrumWifiPhyBasicTest() override
void SpectrumWifiPhyRxSuccess(Ptr< const WifiPsdu > psdu, RxSignalInfo rxSignalInfo, const WifiTxVector &txVector, const std::vector< bool > &statusPerMpdu)
Spectrum wifi receive success function.
SpectrumWifiPhyBasicTest()
void SpectrumWifiPhyRxFailure(Ptr< const WifiPsdu > psdu)
Spectrum wifi receive failure function.
Ptr< SpectrumSignalParameters > MakeSignal(Watt_u txPower, const WifiPhyOperatingChannel &channel)
Make signal function.
void SendSignal(Watt_u txPower)
Send signal function.
void DoTeardown() override
Implementation to do any local setup required for this TestCase.
uint64_t m_uid
the UID to use for the PPDU
Ptr< SpectrumWifiPhy > m_phy
Phy.
Spectrum Wifi Phy Filter Test.
void RxCallback(Ptr< const Packet > p, RxPowerWattPerChannelBand rxPowersW)
Callback triggered when a packet is received by the PHYs.
~SpectrumWifiPhyFilterTest() override
SpectrumWifiPhyFilterTest()
void DoRun() override
Implementation to actually run this TestCase.
void RunOne()
Run one function.
void SendPpdu()
Send PPDU function.
void DoSetup() override
Implementation to do any local setup required for this TestCase.
void DoTeardown() override
Implementation to do any local setup required for this TestCase.
Ptr< ExtSpectrumWifiPhy > m_rxPhy
RX PHY.
MHz_u m_rxChannelWidth
RX channel width.
Ptr< ExtSpectrumWifiPhy > m_txPhy
TX PHY.
MHz_u m_txChannelWidth
TX channel width.
Spectrum Wifi Phy Bands Calculations Test.
void RunOne(const std::vector< uint8_t > &channelNumberPerSegment, MHz_u bandWidth, uint8_t bandIndex, const std::vector< WifiSpectrumBandIndices > &expectedIndices, const std::vector< WifiSpectrumBandFrequencies > &expectedFrequencies)
Run one function.
void DoSetup() override
Implementation to do any local setup required for this TestCase.
Ptr< SpectrumWifiPhy > m_phy
PHY.
SpectrumWifiPhyGetBandTest()
void DoRun() override
Implementation to actually run this TestCase.
void DoTeardown() override
Implementation to do any local setup required for this TestCase.
Spectrum Wifi Phy Interfaces Helper Test.
~SpectrumWifiPhyInterfacesHelperTest() override=default
SpectrumWifiPhyInterfacesHelperTest()
void DoRun() override
Implementation to actually run this TestCase.
Spectrum Wifi Phy Listener Test.
void DoRun() override
Implementation to actually run this TestCase.
void DoSetup() override
Implementation to do any local setup required for this TestCase.
SpectrumWifiPhyListenerTest()
std::shared_ptr< TestPhyListener > m_listener
listener
Spectrum Wifi Phy Multiple Spectrum Test.
void SendPpdu(Ptr< SpectrumWifiPhy > phy, dBm_u txPower, uint32_t payloadSize)
Send PPDU function.
void DoSetup() override
Implementation to do any local setup required for this TestCase.
std::vector< uint32_t > m_rxBytes
count number of received bytes
std::vector< Ptr< SpectrumWifiPhy > > m_rxPhys
RX PHYs.
std::vector< uint32_t > m_countRxSuccess
count number of packets successfully received by PHYs
void DoTeardown() override
Implementation to do any local setup required for this TestCase.
ChannelSwitchScenario m_chanSwitchScenario
the channel switch scenario to consider for the test
void DoRun() override
Implementation to actually run this TestCase.
void DoCheckInterferences(Ptr< SpectrumWifiPhy > phy, const WifiSpectrumBandInfo &band, bool interferencesExpected)
Check the interferences.
void RxSuccess(std::size_t index, Ptr< const WifiPsdu > psdu, RxSignalInfo rxSignalInfo, const WifiTxVector &txVector, const std::vector< bool > &statusPerMpdu)
Receive success function.
bool m_trackSignalsInactiveInterfaces
flag to indicate whether signals coming from inactive spectrum PHY interfaces are tracked during the ...
void SwitchChannel(Ptr< SpectrumWifiPhy > phy, WifiPhyBand band, uint8_t channelNumber, MHz_u channelWidth, std::optional< std::size_t > listenerIndex)
Switch channel function.
std::vector< std::shared_ptr< TestPhyListener > > m_listeners
listeners
Time m_lastTxEnd
hold the time at which the last transmission ended
void RxFailure(std::size_t index, Ptr< const WifiPsdu > psdu)
Receive failure function.
Time m_lastTxStart
hold the time at which the last transmission started
std::vector< uint32_t > m_counts
count number of packets received by PHYs
void CheckResults(std::size_t index, uint32_t expectedNumRx, uint32_t expectedNumRxSuccess, uint32_t expectedRxBytes, FrequencyRange expectedFrequencyRangeActiveRfInterface, const std::vector< std::size_t > &expectedConnectedPhysPerChannel)
Verify results.
std::vector< Ptr< SpectrumWifiPhy > > m_txPhys
TX PHYs.
std::vector< Ptr< MultiModelSpectrumChannel > > m_spectrumChannels
Spectrum channels.
void CheckInterferences(Ptr< SpectrumWifiPhy > phy, const FrequencyRange &freqRange, const WifiSpectrumBandInfo &band, bool interferencesExpected)
Schedule now to check the interferences.
SpectrumWifiPhyMultipleInterfacesTest(bool trackSignalsInactiveInterfaces, ChannelSwitchScenario chanSwitchScenario)
Constructor.
void CheckCcaIndication(std::size_t index, bool expectedCcaBusyIndication, Time switchingDelay, Time propagationDelay)
Verify CCA indication reported by a given PHY.
void RxCallback(std::size_t index, Ptr< const Packet > packet, RxPowerWattPerChannelBand rxPowersW)
Callback triggered when a packet is received by a PHY.
void Reset()
Reset function.
void CheckRxingState(Ptr< SpectrumWifiPhy > phy, bool rxingExpected)
Verify rxing state of the interference helper.
ChannelSwitchScenario
Enumeration for channel switching scenarios.
@ BETWEEN_TX_RX
perform channel switch during propagation delay (after TX and before RX)
@ BEFORE_TX
start TX after channel switch is completed
std::vector< uint32_t > m_countRxFailure
count number of packets unsuccessfully received by PHYs
Spectrum Wifi Phy Test Suite.
SpectrumWifiPhyTestSuite()
Test tracked bands in interference helper upon channel switching.
void DoRun() override
Implementation to actually run this TestCase.
void RunOne(const std::vector< uint8_t > &channelNumberPerSegmentBeforeSwitching, const std::vector< uint8_t > &channelNumberPerSegmentAfterSwitching, const std::vector< std::vector< WifiSpectrumBandFrequencies > > &expectedTrackedBands, const std::vector< std::vector< WifiSpectrumBandFrequencies > > &expectedUntrackedBand)
Run one function.
void VerifyTrackedBands(const std::vector< std::vector< WifiSpectrumBandFrequencies > > &expectedTrackedBands, const std::vector< std::vector< WifiSpectrumBandFrequencies > > &expectedUntrackedBands)
Verify the bands tracked by the interference helper.
void DoSetup() override
Implementation to do any local setup required for this TestCase.
void SwitchChannel(const std::vector< uint8_t > &channelNumberPerSegment)
Switch channel function.
SpectrumWifiPhyTrackedBandsTest()
Ptr< ExtSpectrumWifiPhy > m_phy
PHY.
void DoTeardown() override
Implementation to do any local setup required for this TestCase.
Time m_ccaBusyEnd
CCA_BUSY end time.
void NotifyTxStart(Time duration, dBm_u txPower) override
void Reset()
Reset function.
void NotifyWakeup() override
Notify listeners that we woke up.
Time m_ccaBusyStart
CCA_BUSY start time.
void NotifyRxEndOk() override
We have received the last bit of a packet for which NotifyRxStart was invoked first and,...
void NotifyOff() override
Notify listeners that we went to switch off.
TestPhyListener()=default
Create a test PhyListener.
void NotifySleep() override
Notify listeners that we went to sleep.
void NotifySwitchingStart(Time duration) override
uint32_t m_notifyMaybeCcaBusyStart
notify maybe CCA busy start
uint32_t m_notifyRxStart
notify receive start
void NotifyCcaBusyStart(Time duration, WifiChannelListType channelType, const std::vector< Time > &) override
void NotifyRxStart(Time duration) override
void NotifyOn() override
Notify listeners that we went to switch on.
uint32_t m_notifyRxEndOk
notify receive end OK
void NotifyRxEndError() override
We have received the last bit of a packet for which NotifyRxStart was invoked first and,...
uint32_t m_notifyRxEndError
notify receive end error
~TestPhyListener() override=default
AttributeValue implementation for Boolean.
static WifiMode GetHeMcs11()
Return MCS 11 from HE MCS values.
static WifiMode GetHeMcs0()
Return MCS 0 from HE MCS values.
static WifiMode GetHeMcs7()
Return MCS 7 from HE MCS values.
handles interference calculations
std::map< FrequencyRange, bool > m_rxing
flag whether it is in receiving state for a given FrequencyRange
NiChangesPerBand m_niChanges
NI Changes for each band.
Helper class used to assign positions and mobility models to nodes.
keep track of a set of node pointers.
Ptr< Node > Get(uint32_t i) const
Get the Ptr<Node> stored in this container at a given index.
bool TraceConnectWithoutContext(std::string name, const CallbackBase &cb)
Connect a TraceSource to a Callback without a context.
void GetAttribute(std::string name, AttributeValue &value, bool permissive=false) const
Get the value of an attribute, raising fatal errors if unsuccessful.
void Dispose()
Dispose of this Object.
static WifiMode GetOfdmRate6Mbps()
Return a WifiMode for OFDM at 6 Mbps.
AttributeValue implementation for Pointer.
Smart pointer class similar to boost::intrusive_ptr.
static EventId Schedule(const Time &delay, FUNC f, Ts &&... args)
Schedule an event to expire after delay.
static void Destroy()
Execute the events scheduled with ScheduleDestroy().
static Time Now()
Return the current simulation virtual time.
static void Run()
Run the simulation.
static EventId ScheduleNow(FUNC f, Ts &&... args)
Schedule an event to expire Now.
static void Stop()
Tell the Simulator the calling event should be the last one executed.
Make it easy to create and manage PHY objects for the spectrum model.
void ResetPhyToFreqRangeMapping()
Reset mapping of the spectrum PHY interfaces added to the PHY instances.
void AddChannel(const Ptr< SpectrumChannel > channel, const FrequencyRange &freqRange=WHOLE_WIFI_SPECTRUM)
void AddPhyToFreqRangeMapping(uint8_t linkId, const FrequencyRange &freqRange)
Add a given spectrum PHY interface to the PHY instance corresponding of a given link.
void SetDevice(const Ptr< WifiNetDevice > device) override
Sets the device this PHY is associated with.
HeRuBands GetHeRuBands(Ptr< WifiSpectrumPhyInterface > spectrumPhyInterface, MHz_u guardBandwidth)
This function computes the RU bands that belong to a given spectrum PHY interface.
MHz_u GetGuardBandwidth(MHz_u currentChannelWidth) const override
void AddChannel(const Ptr< SpectrumChannel > channel, const FrequencyRange &freqRange=WHOLE_WIFI_SPECTRUM)
Attach a SpectrumChannel to use for a given frequency range.
Ptr< WifiSpectrumPhyInterface > GetCurrentInterface() const
Get the currently active spectrum PHY interface.
Hold variables of type string.
void AddTestCase(TestCase *testCase, Duration duration=Duration::QUICK)
Add an individual child TestCase to this test suite.
Simulation virtual time values and global simulation resolution.
bool IsStrictlyPositive() const
Exactly equivalent to t > 0.
AttributeValue implementation for Time.
a unique identifier for an interface.
TypeId SetParent(TypeId tid)
Set the parent TypeId.
helps to create WifiNetDevice objects
virtual void SetStandard(WifiStandard standard)
virtual NetDeviceContainer Install(const WifiPhyHelper &phy, const WifiMacHelper &mac, NodeContainer::Iterator first, NodeContainer::Iterator last) const
create MAC layers for a ns3::WifiNetDevice.
void SetPcapDataLinkType(SupportedPcapDataLinkTypes dlt)
Set the data link type of PCAP traces to be used.
void Set(std::string name, const AttributeValue &v)
void SetInterferenceHelper(std::string type, Args &&... args)
Helper function used to set the interference helper.
@ DLT_IEEE802_11_RADIO
Include Radiotap link layer information.
virtual void SetInterferenceHelper(const Ptr< InterferenceHelper > helper)
Sets the interference helper.
void Send(Ptr< const WifiPsdu > psdu, const WifiTxVector &txVector)
This function is a wrapper for the Send variant that accepts a WifiConstPsduMap as first argument.
void SetErrorRateModel(const Ptr< ErrorRateModel > model)
Sets the error rate model.
std::tuple< uint8_t, MHz_u, WifiPhyBand, uint8_t > ChannelTuple
Tuple identifying a segment of an operating channel.
virtual void ConfigureStandard(WifiStandard standard)
Configure the PHY-level parameters for different Wi-Fi standard.
static Time CalculateTxDuration(uint32_t size, const WifiTxVector &txVector, WifiPhyBand band, uint16_t staId=SU_STA_ID)
std::vector< ChannelTuple > ChannelSegments
segments identifying an operating channel
void SetOperatingChannel(const WifiPhyOperatingChannel &channel)
If the standard for this object has not been set yet, store the channel settings corresponding to the...
void SetMobility(const Ptr< MobilityModel > mobility)
assign a mobility model to this device
virtual WifiSpectrumBandInfo GetBand(MHz_u bandWidth, uint8_t bandIndex=0)=0
Get the info of a given band.
receive notifications about PHY events.
Class that keeps track of all information about the current PHY operating channel.
static ConstIterator FindFirst(uint8_t number, MHz_u frequency, MHz_u width, WifiStandard standard, WifiPhyBand band, ConstIterator start=m_frequencyChannels.begin())
Find the first frequency segment matching the specified parameters.
static Ptr< SpectrumValue > CreateOfdmTxPowerSpectralDensity(MHz_u centerFrequency, MHz_u channelWidth, Watt_u txPower, MHz_u guardBandwidth, dBr_u minInnerBand=dBr_u{-20}, dBr_u minOuterband=dBr_u{-28}, dBr_u lowestPoint=dBr_u{-40})
Create a transmit power spectral density corresponding to OFDM (802.11a/g).
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,...
#define NS_LOG_COMPONENT_DEFINE(name)
Define a Log component with a specific name.
#define NS_LOG_FUNCTION(parameters)
If log level LOG_FUNCTION is enabled, this macro will output all input parameters separated by ",...
#define NS_LOG_INFO(msg)
Use NS_LOG to output a message of level LOG_INFO.
Ptr< T > CreateObject(Args &&... args)
Create an object by type, with varying number of constructor parameters.
#define NS_OBJECT_ENSURE_REGISTERED(type)
Register an Object subclass with the TypeId system.
Ptr< T > Create(Ts &&... args)
Create class instances by constructors with varying numbers of arguments and return them by Ptr.
#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.
Time MicroSeconds(uint64_t value)
Construct a Time in the indicated unit.
Time NanoSeconds(uint64_t value)
Construct a Time in the indicated unit.
Time Seconds(double value)
Construct a Time in the indicated unit.
Time MilliSeconds(uint64_t value)
Construct a Time in the indicated unit.
WifiPhyBand
Identifies the PHY band.
WifiChannelListType
Enumeration of the possible channel-list parameter elements defined in Table 8-5 of IEEE 802....
@ WIFI_PHY_BAND_6GHZ
The 6 GHz band.
@ WIFI_PHY_BAND_2_4GHZ
The 2.4 GHz band.
@ WIFI_PHY_BAND_5GHZ
The 5 GHz band.
Every class exported by the ns3 library is enclosed in the ns3 namespace.
constexpr FrequencyRange WIFI_SPECTRUM_6_GHZ
Identifier for the frequency range covering the wifi spectrum in the 6 GHz band.
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...
dB_u RatioToDb(double ratio)
Convert from ratio to dB.
std::vector< BandInfo > Bands
Container of BandInfo.
dBm_u WToDbm(Watt_u val)
Convert from Watts to dBm.
Ptr< T1 > DynamicCast(const Ptr< T2 > &p)
Cast a Ptr.
std::map< WifiSpectrumBandInfo, Watt_u > RxPowerWattPerChannelBand
A map of the received power for each band.
std::size_t Count20MHzSubchannels(MHz_u channelWidth)
Return the number of 20 MHz subchannels covering the channel width.
constexpr FrequencyRange WIFI_SPECTRUM_5_GHZ
Identifier for the frequency range covering the wifi spectrum in the 5 GHz band.
Hz_u MHzToHz(MHz_u val)
Convert from MHz to Hz.
std::unordered_map< uint16_t, Ptr< const WifiPsdu > > WifiConstPsduMap
Map of const PSDUs indexed by STA-ID.
static constexpr uint16_t SU_STA_ID
STA_ID to identify a single user (SU)
constexpr FrequencyRange WIFI_SPECTRUM_2_4_GHZ
Identifier for the frequency range covering the wifi spectrum in the 2.4 GHz band.
static const uint8_t CHANNEL_NUMBER
static SpectrumWifiPhyTestSuite spectrumWifiPhyTestSuite
the test suite
static const MHz_u GUARD_WIDTH
static const MHz_u CHANNEL_WIDTH
The building block of a SpectrumModel.
double fl
lower limit of subband
Struct defining a frequency range between minFrequency and maxFrequency.
MHz_u minFrequency
the minimum frequency
MHz_u maxFrequency
the maximum frequency
RxSignalInfo structure containing info on the received signal.
WifiSpectrumBandInfo structure containing info about a spectrum band.