wifi: Extend protection mechanisms to support 802.11n
This commit is contained in:
@@ -101,39 +101,39 @@ Experiment::Run (bool enableProtection, bool enableShortSlotTime, bool enableSho
|
||||
mac.SetType ("ns3::StaWifiMac",
|
||||
"Ssid", SsidValue (ssid),
|
||||
"ShortSlotTimeSupported", BooleanValue (enableShortSlotTime));
|
||||
|
||||
|
||||
// Configure the PLCP preamble type: long or short
|
||||
phy.Set ("ShortPlcpPreambleSupported", BooleanValue (enableShortPlcpPreamble));
|
||||
|
||||
NetDeviceContainer bStaDevice;
|
||||
bStaDevice = wifi.Install (phy, mac, wifiBStaNodes);
|
||||
|
||||
|
||||
// 802.11b/g STA
|
||||
wifi.SetStandard (WIFI_PHY_STANDARD_80211g);
|
||||
NetDeviceContainer gStaDevice;
|
||||
gStaDevice = wifi.Install (phy, mac, wifiGStaNodes);
|
||||
|
||||
|
||||
// 802.11b/g AP
|
||||
mac.SetType ("ns3::ApWifiMac",
|
||||
"Ssid", SsidValue (ssid),
|
||||
"BeaconGeneration", BooleanValue (true),
|
||||
"EnableNonErpProtection", BooleanValue (enableProtection),
|
||||
"ShortSlotTimeSupported", BooleanValue (enableShortSlotTime));
|
||||
|
||||
|
||||
NetDeviceContainer apDevice;
|
||||
apDevice = wifi.Install (phy, mac, wifiApNode);
|
||||
|
||||
// Setting mobility model
|
||||
MobilityHelper mobility;
|
||||
Ptr<ListPositionAllocator> positionAlloc = CreateObject<ListPositionAllocator> ();
|
||||
|
||||
|
||||
positionAlloc->Add (Vector (0.0, 0.0, 0.0));
|
||||
if (isMixed)
|
||||
{
|
||||
positionAlloc->Add (Vector (5.0, 0.0, 0.0));
|
||||
}
|
||||
{
|
||||
positionAlloc->Add (Vector (5.0, 0.0, 0.0));
|
||||
}
|
||||
positionAlloc->Add (Vector (0.0, 5.0, 0.0));
|
||||
|
||||
|
||||
mobility.SetPositionAllocator (positionAlloc);
|
||||
mobility.SetMobilityModel ("ns3::ConstantPositionMobilityModel");
|
||||
mobility.Install (wifiApNode);
|
||||
@@ -172,11 +172,11 @@ Experiment::Run (bool enableProtection, bool enableShortSlotTime, bool enableSho
|
||||
ApplicationContainer clientApp = myClient.Install (wifiGStaNodes);
|
||||
clientApp.Start (Seconds (1.0));
|
||||
clientApp.Stop (Seconds (simulationTime + 1));
|
||||
|
||||
|
||||
Simulator::Stop (Seconds (simulationTime + 1));
|
||||
Simulator::Run ();
|
||||
Simulator::Destroy ();
|
||||
|
||||
|
||||
totalPacketsThrough = DynamicCast<UdpServer> (serverApp.Get (0))->GetReceived ();
|
||||
throughput = totalPacketsThrough * payloadSize * 8 / (simulationTime * 1000000.0);
|
||||
}
|
||||
@@ -185,7 +185,7 @@ Experiment::Run (bool enableProtection, bool enableShortSlotTime, bool enableSho
|
||||
uint16_t port = 50000;
|
||||
Address apLocalAddress (InetSocketAddress (Ipv4Address::GetAny (), port));
|
||||
PacketSinkHelper packetSinkHelper ("ns3::TcpSocketFactory", apLocalAddress);
|
||||
|
||||
|
||||
ApplicationContainer sinkApp = packetSinkHelper.Install (wifiApNode.Get (0));
|
||||
sinkApp.Start (Seconds (0.0));
|
||||
sinkApp.Stop (Seconds (simulationTime + 1));
|
||||
@@ -195,10 +195,10 @@ Experiment::Run (bool enableProtection, bool enableShortSlotTime, bool enableSho
|
||||
onoff.SetAttribute ("OffTime", StringValue ("ns3::ConstantRandomVariable[Constant=0]"));
|
||||
onoff.SetAttribute ("PacketSize", UintegerValue (payloadSize));
|
||||
onoff.SetAttribute ("DataRate", DataRateValue (54000000)); //bit/s
|
||||
|
||||
|
||||
AddressValue remoteAddress (InetSocketAddress (ApInterface.GetAddress (0), port));
|
||||
onoff.SetAttribute ("Remote", remoteAddress);
|
||||
|
||||
|
||||
ApplicationContainer apps;
|
||||
apps.Add (onoff.Install (wifiGStaNodes));
|
||||
apps.Start (Seconds (1.0));
|
||||
@@ -207,11 +207,11 @@ Experiment::Run (bool enableProtection, bool enableShortSlotTime, bool enableSho
|
||||
Simulator::Stop (Seconds (simulationTime + 1));
|
||||
Simulator::Run ();
|
||||
Simulator::Destroy ();
|
||||
|
||||
|
||||
totalPacketsThrough = DynamicCast<PacketSink> (sinkApp.Get (0))->GetTotalRx ();
|
||||
throughput += totalPacketsThrough * 8 / (simulationTime * 1000000.0);
|
||||
}
|
||||
|
||||
|
||||
return throughput;
|
||||
}
|
||||
|
||||
@@ -220,7 +220,7 @@ int main (int argc, char *argv[])
|
||||
uint32_t payloadSize = 1472; //bytes
|
||||
uint32_t simulationTime = 10; //seconds
|
||||
bool isUdp = true;
|
||||
|
||||
|
||||
CommandLine cmd;
|
||||
cmd.AddValue ("payloadSize", "Payload size in bytes", payloadSize);
|
||||
cmd.AddValue ("simulationTime", "Simulation time in seconds", simulationTime);
|
||||
@@ -237,67 +237,67 @@ int main (int argc, char *argv[])
|
||||
NS_LOG_ERROR ("Obtained throughput " << throughput << " is not in the expected boundaries!");
|
||||
exit (1);
|
||||
}
|
||||
std::cout << "Disabled" << "\t\t" << "Long" << "\t\t\t\t" << "Long" << "\t\t\t\t" << "G-only" << "\t\t" << throughput <<" Mbit/s" << std::endl;
|
||||
|
||||
std::cout << "Disabled" << "\t\t" << "Long" << "\t\t\t\t" << "Long" << "\t\t\t\t" << "G-only" << "\t\t" << throughput << " Mbit/s" << std::endl;
|
||||
|
||||
throughput = experiment.Run (false, true, false, false, isUdp, payloadSize, simulationTime);
|
||||
if (throughput < 29 || throughput > 30)
|
||||
{
|
||||
NS_LOG_ERROR ("Obtained throughput " << throughput << " is not in the expected boundaries!");
|
||||
exit (1);
|
||||
}
|
||||
std::cout << "Disabled" << "\t\t" << "Short" << "\t\t\t\t" << "Long" << "\t\t\t\t" << "G-only" << "\t\t" << throughput <<" Mbit/s" << std::endl;
|
||||
|
||||
std::cout << "Disabled" << "\t\t" << "Short" << "\t\t\t\t" << "Long" << "\t\t\t\t" << "G-only" << "\t\t" << throughput << " Mbit/s" << std::endl;
|
||||
|
||||
throughput = experiment.Run (false, false, false, true, isUdp, payloadSize, simulationTime);
|
||||
if (throughput < 22.5 || throughput > 23.5)
|
||||
{
|
||||
NS_LOG_ERROR ("Obtained throughput " << throughput << " is not in the expected boundaries!");
|
||||
exit (1);
|
||||
}
|
||||
std::cout << "Disabled" << "\t\t" << "Long" << "\t\t\t\t" << "Long" << "\t\t\t\t" << "Mixed" << "\t\t" << throughput <<" Mbit/s" << std::endl;
|
||||
|
||||
std::cout << "Disabled" << "\t\t" << "Long" << "\t\t\t\t" << "Long" << "\t\t\t\t" << "Mixed" << "\t\t" << throughput << " Mbit/s" << std::endl;
|
||||
|
||||
throughput = experiment.Run (false, false, true, true, isUdp, payloadSize, simulationTime);
|
||||
if (throughput < 22.5 || throughput > 23.5)
|
||||
{
|
||||
NS_LOG_ERROR ("Obtained throughput " << throughput << " is not in the expected boundaries!");
|
||||
exit (1);
|
||||
}
|
||||
std::cout << "Disabled" << "\t\t" << "Long" << "\t\t\t\t" << "Short" << "\t\t\t\t" << "Mixed" << "\t\t" << throughput <<" Mbit/s" << std::endl;
|
||||
|
||||
Config::SetDefault ("ns3::WifiRemoteStationManager::ProtectionMode", StringValue ("Rts-Cts"));
|
||||
|
||||
std::cout << "Disabled" << "\t\t" << "Long" << "\t\t\t\t" << "Short" << "\t\t\t\t" << "Mixed" << "\t\t" << throughput << " Mbit/s" << std::endl;
|
||||
|
||||
Config::SetDefault ("ns3::WifiRemoteStationManager::ErpProtectionMode", StringValue ("Rts-Cts"));
|
||||
|
||||
throughput = experiment.Run (true, false, false, true, isUdp, payloadSize, simulationTime);
|
||||
if (throughput < 19 || throughput > 20)
|
||||
{
|
||||
NS_LOG_ERROR ("Obtained throughput " << throughput << " is not in the expected boundaries!");
|
||||
exit (1);
|
||||
}
|
||||
std::cout << "RTS/CTS" << "\t\t\t" << "Long" << "\t\t\t\t" << "Long" << "\t\t\t\t" << "Mixed" << "\t\t" << throughput <<" Mbit/s" << std::endl;
|
||||
|
||||
std::cout << "RTS/CTS" << "\t\t\t" << "Long" << "\t\t\t\t" << "Long" << "\t\t\t\t" << "Mixed" << "\t\t" << throughput << " Mbit/s" << std::endl;
|
||||
|
||||
throughput = experiment.Run (true, false, true, true, isUdp, payloadSize, simulationTime);
|
||||
if (throughput < 19 || throughput > 20)
|
||||
{
|
||||
NS_LOG_ERROR ("Obtained throughput " << throughput << " is not in the expected boundaries!");
|
||||
exit (1);
|
||||
}
|
||||
std::cout << "RTS/CTS" << "\t\t\t" << "Long" << "\t\t\t\t" << "Short" << "\t\t\t\t" << "Mixed" << "\t\t" << throughput <<" Mbit/s" << std::endl;
|
||||
|
||||
Config::SetDefault ("ns3::WifiRemoteStationManager::ProtectionMode", StringValue ("Cts-To-Self"));
|
||||
|
||||
std::cout << "RTS/CTS" << "\t\t\t" << "Long" << "\t\t\t\t" << "Short" << "\t\t\t\t" << "Mixed" << "\t\t" << throughput << " Mbit/s" << std::endl;
|
||||
|
||||
Config::SetDefault ("ns3::WifiRemoteStationManager::ErpProtectionMode", StringValue ("Cts-To-Self"));
|
||||
|
||||
throughput = experiment.Run (true, false, false, true, isUdp, payloadSize, simulationTime);
|
||||
if (throughput < 20.5 || throughput > 21.5)
|
||||
{
|
||||
NS_LOG_ERROR ("Obtained throughput " << throughput << " is not in the expected boundaries!");
|
||||
exit (1);
|
||||
}
|
||||
std::cout << "CTS-TO-SELF" << "\t\t" << "Long" << "\t\t\t\t" << "Long" << "\t\t\t\t" << "Mixed" << "\t\t" << throughput <<" Mbit/s" << std::endl;
|
||||
|
||||
std::cout << "CTS-TO-SELF" << "\t\t" << "Long" << "\t\t\t\t" << "Long" << "\t\t\t\t" << "Mixed" << "\t\t" << throughput << " Mbit/s" << std::endl;
|
||||
|
||||
throughput = experiment.Run (true, false, true, true, isUdp, payloadSize, simulationTime);
|
||||
if (throughput < 20.5 || throughput > 21.5)
|
||||
{
|
||||
NS_LOG_ERROR ("Obtained throughput " << throughput << " is not in the expected boundaries!");
|
||||
exit (1);
|
||||
}
|
||||
std::cout << "CTS-TO-SELF" << "\t\t" << "Long" << "\t\t\t\t" << "Short" << "\t\t\t\t" << "Mixed" << "\t\t" << throughput <<" Mbit/s" << std::endl;
|
||||
|
||||
std::cout << "CTS-TO-SELF" << "\t\t" << "Long" << "\t\t\t\t" << "Short" << "\t\t\t\t" << "Mixed" << "\t\t" << throughput << " Mbit/s" << std::endl;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -325,11 +325,18 @@ WifiRemoteStationManager::GetTypeId (void)
|
||||
UintegerValue (0),
|
||||
MakeUintegerAccessor (&WifiRemoteStationManager::m_defaultTxPowerLevel),
|
||||
MakeUintegerChecker<uint8_t> ())
|
||||
.AddAttribute ("ProtectionMode",
|
||||
.AddAttribute ("ErpProtectionMode",
|
||||
"Protection mode used when non-ERP STAs are connected to an ERP AP: Rts-Cts or Cts-To-Self",
|
||||
EnumValue (WifiRemoteStationManager::CTS_TO_SELF),
|
||||
MakeEnumAccessor (&WifiRemoteStationManager::SetProtectionMode,
|
||||
&WifiRemoteStationManager::GetProtectionMode),
|
||||
MakeEnumAccessor (&WifiRemoteStationManager::SetErpProtectionMode,
|
||||
&WifiRemoteStationManager::GetErpProtectionMode),
|
||||
MakeEnumChecker (WifiRemoteStationManager::RTS_CTS, "Rts-Cts",
|
||||
WifiRemoteStationManager::CTS_TO_SELF, "Cts-To-Self"))
|
||||
.AddAttribute ("HtProtectionMode",
|
||||
"Protection mode used when non-HT STAs are connected to a HT AP: Rts-Cts or Cts-To-Self",
|
||||
EnumValue (WifiRemoteStationManager::CTS_TO_SELF),
|
||||
MakeEnumAccessor (&WifiRemoteStationManager::SetHtProtectionMode,
|
||||
&WifiRemoteStationManager::GetHtProtectionMode),
|
||||
MakeEnumChecker (WifiRemoteStationManager::RTS_CTS, "Rts-Cts",
|
||||
WifiRemoteStationManager::CTS_TO_SELF, "Cts-To-Self"))
|
||||
.AddTraceSource ("MacTxRtsFailed",
|
||||
@@ -358,6 +365,7 @@ WifiRemoteStationManager::WifiRemoteStationManager ()
|
||||
m_vhtSupported (false),
|
||||
m_heSupported (false),
|
||||
m_useNonErpProtection (false),
|
||||
m_useNonHtProtection (false),
|
||||
m_useGreenfieldProtection (false),
|
||||
m_shortPreambleEnabled (false),
|
||||
m_shortSlotTimeEnabled (false),
|
||||
@@ -447,9 +455,15 @@ WifiRemoteStationManager::SetFragmentationThreshold (uint32_t threshold)
|
||||
}
|
||||
|
||||
void
|
||||
WifiRemoteStationManager::SetProtectionMode (WifiRemoteStationManager::ProtectionMode mode)
|
||||
WifiRemoteStationManager::SetErpProtectionMode (WifiRemoteStationManager::ProtectionMode mode)
|
||||
{
|
||||
m_protectionMode = mode;
|
||||
m_erpProtectionMode = mode;
|
||||
}
|
||||
|
||||
void
|
||||
WifiRemoteStationManager::SetHtProtectionMode (WifiRemoteStationManager::ProtectionMode mode)
|
||||
{
|
||||
m_htProtectionMode = mode;
|
||||
}
|
||||
|
||||
void
|
||||
@@ -489,9 +503,15 @@ WifiRemoteStationManager::GetRifsPermitted (void) const
|
||||
}
|
||||
|
||||
WifiRemoteStationManager::ProtectionMode
|
||||
WifiRemoteStationManager::GetProtectionMode (void) const
|
||||
WifiRemoteStationManager::GetErpProtectionMode (void) const
|
||||
{
|
||||
return m_protectionMode;
|
||||
return m_erpProtectionMode;
|
||||
}
|
||||
|
||||
WifiRemoteStationManager::ProtectionMode
|
||||
WifiRemoteStationManager::GetHtProtectionMode (void) const
|
||||
{
|
||||
return m_htProtectionMode;
|
||||
}
|
||||
|
||||
bool
|
||||
@@ -975,7 +995,7 @@ WifiRemoteStationManager::NeedRts (Mac48Address address, const WifiMacHeader *he
|
||||
{
|
||||
return false;
|
||||
}
|
||||
if (m_protectionMode == RTS_CTS
|
||||
if (m_erpProtectionMode == RTS_CTS
|
||||
&& ((mode.GetModulationClass () == WIFI_MOD_CLASS_ERP_OFDM)
|
||||
|| (mode.GetModulationClass () == WIFI_MOD_CLASS_HT)
|
||||
|| (mode.GetModulationClass () == WIFI_MOD_CLASS_VHT)
|
||||
@@ -985,6 +1005,15 @@ WifiRemoteStationManager::NeedRts (Mac48Address address, const WifiMacHeader *he
|
||||
NS_LOG_DEBUG ("WifiRemoteStationManager::NeedRTS returning true to protect non-ERP stations");
|
||||
return true;
|
||||
}
|
||||
else if (m_htProtectionMode == RTS_CTS
|
||||
&& ((mode.GetModulationClass () == WIFI_MOD_CLASS_HT)
|
||||
|| (mode.GetModulationClass () == WIFI_MOD_CLASS_VHT))
|
||||
&& m_useNonHtProtection
|
||||
&& !(m_erpProtectionMode != RTS_CTS && m_useNonErpProtection))
|
||||
{
|
||||
NS_LOG_DEBUG ("WifiRemoteStationManager::NeedRTS returning true to protect non-HT stations");
|
||||
return true;
|
||||
}
|
||||
bool normally = (packet->GetSize () + header->GetSize () + WIFI_MAC_FCS_LENGTH) > GetRtsCtsThreshold ();
|
||||
return DoNeedRts (Lookup (address, header), packet, normally);
|
||||
}
|
||||
@@ -994,7 +1023,7 @@ WifiRemoteStationManager::NeedCtsToSelf (WifiTxVector txVector)
|
||||
{
|
||||
WifiMode mode = txVector.GetMode ();
|
||||
NS_LOG_FUNCTION (this << mode);
|
||||
if (m_protectionMode == CTS_TO_SELF
|
||||
if (m_erpProtectionMode == CTS_TO_SELF
|
||||
&& ((mode.GetModulationClass () == WIFI_MOD_CLASS_ERP_OFDM)
|
||||
|| (mode.GetModulationClass () == WIFI_MOD_CLASS_HT)
|
||||
|| (mode.GetModulationClass () == WIFI_MOD_CLASS_VHT)
|
||||
@@ -1004,6 +1033,15 @@ WifiRemoteStationManager::NeedCtsToSelf (WifiTxVector txVector)
|
||||
NS_LOG_DEBUG ("WifiRemoteStationManager::NeedCtsToSelf returning true to protect non-ERP stations");
|
||||
return true;
|
||||
}
|
||||
else if (m_htProtectionMode == CTS_TO_SELF
|
||||
&& ((mode.GetModulationClass () == WIFI_MOD_CLASS_HT)
|
||||
|| (mode.GetModulationClass () == WIFI_MOD_CLASS_VHT))
|
||||
&& m_useNonHtProtection
|
||||
&& !(m_erpProtectionMode != CTS_TO_SELF && m_useNonErpProtection))
|
||||
{
|
||||
NS_LOG_DEBUG ("WifiRemoteStationManager::NeedCtsToSelf returning true to protect non-HT stations");
|
||||
return true;
|
||||
}
|
||||
else if (!m_useNonErpProtection)
|
||||
{
|
||||
//search for the BSS Basic Rate set, if the used mode is in the basic set then there is no need for Cts To Self
|
||||
@@ -1045,6 +1083,18 @@ WifiRemoteStationManager::GetUseNonErpProtection (void) const
|
||||
return m_useNonErpProtection;
|
||||
}
|
||||
|
||||
void
|
||||
WifiRemoteStationManager::SetUseNonHtProtection (bool enable)
|
||||
{
|
||||
m_useNonHtProtection = enable;
|
||||
}
|
||||
|
||||
bool
|
||||
WifiRemoteStationManager::GetUseNonHtProtection (void) const
|
||||
{
|
||||
return m_useNonHtProtection;
|
||||
}
|
||||
|
||||
void
|
||||
WifiRemoteStationManager::SetUseGreenfieldProtection (bool enable)
|
||||
{
|
||||
|
||||
@@ -242,17 +242,29 @@ public:
|
||||
*/
|
||||
bool HasHeSupported (void) const;
|
||||
/**
|
||||
* Sets the protection mode.
|
||||
* Sets the ERP protection mode.
|
||||
*
|
||||
* \param mode the protection mode
|
||||
* \param mode the ERP protection mode
|
||||
*/
|
||||
void SetProtectionMode (ProtectionMode mode);
|
||||
void SetErpProtectionMode (ProtectionMode mode);
|
||||
/**
|
||||
* Return the protection mode.
|
||||
* Return the ERP protection mode.
|
||||
*
|
||||
* \return the protection mode
|
||||
* \return the ERP protection mode
|
||||
*/
|
||||
ProtectionMode GetProtectionMode (void) const;
|
||||
ProtectionMode GetErpProtectionMode (void) const;
|
||||
/**
|
||||
* Sets the HT protection mode.
|
||||
*
|
||||
* \param mode the HT protection mode
|
||||
*/
|
||||
void SetHtProtectionMode (ProtectionMode mode);
|
||||
/**
|
||||
* Return the HT protection mode.
|
||||
*
|
||||
* \return the HT protection mode
|
||||
*/
|
||||
ProtectionMode GetHtProtectionMode (void) const;
|
||||
/**
|
||||
* Enable or disable protection for non-ERP stations.
|
||||
*
|
||||
@@ -266,6 +278,19 @@ public:
|
||||
* false otherwise
|
||||
*/
|
||||
bool GetUseNonErpProtection (void) const;
|
||||
/**
|
||||
* Enable or disable protection for non-HT stations.
|
||||
*
|
||||
* \param enable enable or disable protection for non-HT stations
|
||||
*/
|
||||
void SetUseNonHtProtection (bool enable);
|
||||
/**
|
||||
* Return whether the device supports protection of non-HT stations.
|
||||
*
|
||||
* \return true if protection for non-HT stations is enabled,
|
||||
* false otherwise
|
||||
*/
|
||||
bool GetUseNonHtProtection (void) const;
|
||||
/**
|
||||
* Enable or disable protection for stations that do not support HT greenfield format.
|
||||
*
|
||||
@@ -1372,11 +1397,13 @@ private:
|
||||
uint8_t m_defaultTxPowerLevel; //!< Default tranmission power level
|
||||
WifiMode m_nonUnicastMode; //!< Transmission mode for non-unicast DATA frames
|
||||
bool m_useNonErpProtection; //!< flag if protection for non-ERP stations against ERP transmissions is enabled
|
||||
bool m_useNonHtProtection; //!< flag if protection for non-HT stations against HT transmissions is enabled
|
||||
bool m_useGreenfieldProtection; //!< flag if protection for stations that do not support HT greenfield format is enabled
|
||||
bool m_shortPreambleEnabled; //!< flag if short PLCP preamble is enabled
|
||||
bool m_shortSlotTimeEnabled; //!< flag if short slot time is enabled
|
||||
bool m_rifsPermitted; //!< flag if RIFS is enabled
|
||||
ProtectionMode m_protectionMode; //!< Protection mode for ERP stations when non-ERP stations are detected
|
||||
ProtectionMode m_erpProtectionMode; //!< Protection mode for ERP stations when non-ERP stations are detected
|
||||
ProtectionMode m_htProtectionMode; //!< Protection mode for HT stations when non-HT stations are detected
|
||||
|
||||
/**
|
||||
* The trace source fired when the transmission of a single RTS has failed
|
||||
|
||||
Reference in New Issue
Block a user