split interference calculation from YansWifiPhy. Move them to InterferenceHelper
--- a/src/devices/wifi/dcf-manager.cc Thu Jun 12 12:31:02 2008 -0700
+++ b/src/devices/wifi/dcf-manager.cc Sat Jun 14 10:52:10 2008 -0700
@@ -180,8 +180,8 @@
virtual void NotifyTxStart (Time duration) {
m_dcf->NotifyTxStartNow (duration);
}
- virtual void NotifyCcaBusyStart (Time duration) {
- m_dcf->NotifyCcaBusyStartNow (duration);
+ virtual void NotifyMaybeCcaBusyStart (Time duration) {
+ m_dcf->NotifyMaybeCcaBusyStartNow (duration);
}
private:
ns3::DcfManager *m_dcf;
@@ -528,7 +528,7 @@
m_lastTxDuration = duration;
}
void
-DcfManager::NotifyCcaBusyStartNow (Time duration)
+DcfManager::NotifyMaybeCcaBusyStartNow (Time duration)
{
MY_DEBUG ("busy start for "<<duration);
UpdateBackoff ();
--- a/src/devices/wifi/dcf-manager.h Thu Jun 12 12:31:02 2008 -0700
+++ b/src/devices/wifi/dcf-manager.h Sat Jun 14 10:52:10 2008 -0700
@@ -220,7 +220,7 @@
*
* Notify the DCF that a CCA busy period has just started.
*/
- void NotifyCcaBusyStartNow (Time duration);
+ void NotifyMaybeCcaBusyStartNow (Time duration);
/**
* \param duration the value of the received NAV.
*
--- a/src/devices/wifi/error-rate-model.cc Thu Jun 12 12:31:02 2008 -0700
+++ b/src/devices/wifi/error-rate-model.cc Sat Jun 14 10:52:10 2008 -0700
@@ -25,6 +25,8 @@
namespace ns3 {
+NS_OBJECT_ENSURE_REGISTERED (ErrorRateModel);
+
TypeId
ErrorRateModel::GetTypeId (void)
{
@@ -38,6 +40,30 @@
ErrorRateModel::ErrorRateModel ()
{}
+double
+ErrorRateModel::CalculateSnr (WifiMode txMode, double ber) const
+{
+ // This is a very simple binary search.
+ double low, high, precision;
+ low = 1e-25;
+ high = 1e25;
+ precision = 1e-12;
+ while (high - low > precision)
+ {
+ NS_ASSERT (high >= low);
+ double middle = low + (high - low) / 2;
+ if ((1 - GetChunkSuccessRate (txMode, middle, 1)) > ber)
+ {
+ low = middle;
+ }
+ else
+ {
+ high = middle;
+ }
+ }
+ return low;
+}
+
double
ErrorRateModel::Log2 (double val) const
--- a/src/devices/wifi/error-rate-model.h Thu Jun 12 12:31:02 2008 -0700
+++ b/src/devices/wifi/error-rate-model.h Sat Jun 14 10:52:10 2008 -0700
@@ -33,6 +33,14 @@
ErrorRateModel ();
+ /**
+ * \param txMode a specific transmission mode
+ * \param ber a target ber
+ * \returns the snr which corresponds to the requested
+ * ber.
+ */
+ double CalculateSnr (WifiMode txMode, double ber) const;
+
double GetChunkSuccessRate (WifiMode mode, double snr, uint32_t nbits) const;
private:
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/src/devices/wifi/interference-helper.cc Sat Jun 14 10:52:10 2008 -0700
@@ -0,0 +1,441 @@
+#include "interference-helper.h"
+#include "wifi-phy.h"
+#include "error-rate-model.h"
+#include "ns3/simulator.h"
+#include "ns3/log.h"
+
+NS_LOG_COMPONENT_DEFINE ("InterferenceHelper");
+
+namespace ns3 {
+
+/****************************************************************
+ * Phy event class
+ ****************************************************************/
+
+InterferenceHelper::Event::Event (uint32_t size, WifiMode payloadMode,
+ enum WifiPreamble preamble,
+ Time duration, double rxPower)
+ : m_size (size),
+ m_payloadMode (payloadMode),
+ m_preamble (preamble),
+ m_startTime (Simulator::Now ()),
+ m_endTime (m_startTime + duration),
+ m_rxPowerW (rxPower)
+{}
+InterferenceHelper::Event::~Event ()
+{}
+
+Time
+InterferenceHelper::Event::GetDuration (void) const
+{
+ return m_endTime - m_startTime;
+}
+Time
+InterferenceHelper::Event::GetStartTime (void) const
+{
+ return m_startTime;
+}
+Time
+InterferenceHelper::Event::GetEndTime (void) const
+{
+ return m_endTime;
+}
+bool
+InterferenceHelper::Event::Overlaps (Time time) const
+{
+ if (m_startTime <= time &&
+ m_endTime >= time)
+ {
+ return true;
+ }
+ else
+ {
+ return false;
+ }
+}
+double
+InterferenceHelper::Event::GetRxPowerW (void) const
+{
+ return m_rxPowerW;
+}
+uint32_t
+InterferenceHelper::Event::GetSize (void) const
+{
+ return m_size;
+}
+WifiMode
+InterferenceHelper::Event::GetPayloadMode (void) const
+{
+ return m_payloadMode;
+}
+enum WifiPreamble
+InterferenceHelper::Event::GetPreambleType (void) const
+{
+ return m_preamble;
+}
+
+/****************************************************************
+ * Class which records SNIR change events for a
+ * short period of time.
+ ****************************************************************/
+
+InterferenceHelper::NiChange::NiChange (Time time, double delta)
+ : m_time (time), m_delta (delta)
+{}
+Time
+InterferenceHelper::NiChange::GetTime (void) const
+{
+ return m_time;
+}
+double
+InterferenceHelper::NiChange::GetDelta (void) const
+{
+ return m_delta;
+}
+bool
+InterferenceHelper::NiChange::operator < (InterferenceHelper::NiChange const &o) const
+{
+ return (m_time < o.m_time)?true:false;
+}
+
+/****************************************************************
+ * The actual InterferenceHelper
+ ****************************************************************/
+
+InterferenceHelper::InterferenceHelper ()
+ : m_80211a (false)
+{
+ m_errorRateModel = Create<ErrorRateModel> ();
+}
+
+Ptr<InterferenceHelper::Event>
+InterferenceHelper::Add (uint32_t size, WifiMode payloadMode,
+ enum WifiPreamble preamble,
+ Time duration, double rxPowerW)
+{
+ Ptr<InterferenceHelper::Event> event;
+
+ event = Create<InterferenceHelper::Event>
+ (size,
+ payloadMode,
+ preamble,
+ duration,
+ rxPowerW);
+
+ AppendEvent (event);
+ return event;
+}
+
+Time
+InterferenceHelper::GetMaxPacketDuration (void) const
+{
+ return m_maxPacketDuration;
+}
+
+void
+InterferenceHelper::SetNoiseFloorW (double noiseFloor)
+{
+ m_noiseFloorW = noiseFloor;
+}
+
+double
+InterferenceHelper::GetNoiseFloorW (void) const
+{
+ return m_noiseFloorW;
+}
+
+void
+InterferenceHelper::SetErrorRateModel (Ptr<ErrorRateModel> rate)
+{
+ m_errorRateModel = rate;
+}
+
+Ptr<ErrorRateModel>
+InterferenceHelper::GetErrorRateModel (void) const
+{
+ return m_errorRateModel;
+}
+
+Time
+InterferenceHelper::GetEnergyDuration (double energyW)
+{
+ Time now = Simulator::Now ();
+
+ // first, we iterate over all events and, each event
+ // which contributes energy to the channel now is
+ // appended to the noise interference array.
+ Events::const_iterator i = m_events.begin ();
+ double noiseInterferenceW = 0.0;
+ NiChanges ni;
+ while (i != m_events.end ())
+ {
+ Ptr<Event> ev = *i;
+ NS_ASSERT (ev->GetStartTime () <= now);
+ if (ev->GetEndTime () > now)
+ {
+ ni.push_back (NiChange (ev->GetEndTime (), -ev->GetRxPowerW ()));
+ noiseInterferenceW += ev->GetRxPowerW ();
+ }
+ i++;
+ }
+ if (noiseInterferenceW < energyW)
+ {
+ return MicroSeconds (0);
+ }
+
+ /* quicksort vector of NI changes by time.
+ */
+ std::sort (ni.begin (), ni.end (), std::less<NiChange> ());
+
+ // Now, we iterate the piecewise linear noise function
+ Time end = now;
+ for (NiChanges::const_iterator i = ni.begin (); i != ni.end (); i++)
+ {
+ noiseInterferenceW += i->GetDelta ();
+ end = i->GetTime ();
+ if (noiseInterferenceW < energyW)
+ {
+ break;
+ }
+ }
+ return end - now;
+}
+
+Time
+InterferenceHelper::CalculateTxDuration (uint32_t size, WifiMode payloadMode, WifiPreamble preamble) const
+{
+ NS_ASSERT (m_80211a);
+ uint64_t delay = 0;
+ delay += m_plcpLongPreambleDelayUs;
+ // symbol duration is 4us
+ delay += 4;
+ delay += lrint (ceil ((size * 8.0 + 16.0 + 6.0) / payloadMode.GetDataRate () / 4e-6) * 4);
+ return MicroSeconds (delay);
+}
+
+void
+InterferenceHelper::Configure80211aParameters (void)
+{
+ NS_LOG_FUNCTION (this);
+ m_80211a = true;
+ m_plcpLongPreambleDelayUs = 16;
+ m_plcpShortPreambleDelayUs = 16;
+ m_longPlcpHeaderMode = WifiPhy::g_6mba;
+ m_shortPlcpHeaderMode = WifiPhy::g_6mba;
+ m_plcpHeaderLength = 4 + 1 + 12 + 1 + 6;
+ /* 4095 bytes at a 6Mb/s rate with a 1/2 coding rate. */
+ m_maxPacketDuration = CalculateTxDuration (4095, WifiPhy::g_6mba, WIFI_PREAMBLE_LONG);
+}
+
+void
+InterferenceHelper::AppendEvent (Ptr<InterferenceHelper::Event> event)
+{
+ /* attempt to remove the events which are
+ * not useful anymore.
+ * i.e.: all events which end _before_
+ * now - m_maxPacketDuration
+ */
+
+ if (Simulator::Now () > GetMaxPacketDuration ())
+ {
+ Time end = Simulator::Now () - GetMaxPacketDuration ();
+ Events::iterator i = m_events.begin ();
+ while (i != m_events.end () &&
+ (*i)->GetEndTime () <= end)
+ {
+ i++;
+ }
+ m_events.erase (m_events.begin (), i);
+ }
+ m_events.push_back (event);
+}
+
+
+double
+InterferenceHelper::CalculateSnr (double signal, double noiseInterference, WifiMode mode) const
+{
+ // thermal noise at 290K in J/s = W
+ static const double BOLTZMANN = 1.3803e-23;
+ double Nt = BOLTZMANN * 290.0 * mode.GetBandwidth ();
+ // receiver noise Floor (W)
+ double noiseFloor = m_noiseFloorW * Nt;
+ double noise = noiseFloor + noiseInterference;
+ double snr = signal / noise;
+ return snr;
+}
+
+double
+InterferenceHelper::CalculateNoiseInterferenceW (Ptr<InterferenceHelper::Event> event, NiChanges *ni) const
+{
+ Events::const_iterator i = m_events.begin ();
+ double noiseInterference = 0.0;
+ while (i != m_events.end ())
+ {
+ if (event == (*i))
+ {
+ i++;
+ continue;
+ }
+ if (event->Overlaps ((*i)->GetStartTime ()))
+ {
+ ni->push_back (NiChange ((*i)->GetStartTime (), (*i)->GetRxPowerW ()));
+ }
+ if (event->Overlaps ((*i)->GetEndTime ()))
+ {
+ ni->push_back (NiChange ((*i)->GetEndTime (), -(*i)->GetRxPowerW ()));
+ }
+ if ((*i)->Overlaps (event->GetStartTime ()))
+ {
+ noiseInterference += (*i)->GetRxPowerW ();
+ }
+ i++;
+ }
+ ni->push_back (NiChange (event->GetStartTime (), noiseInterference));
+ ni->push_back (NiChange (event->GetEndTime (), 0));
+
+ /* quicksort vector of NI changes by time. */
+ std::sort (ni->begin (), ni->end (), std::less<NiChange> ());
+
+ return noiseInterference;
+}
+
+double
+InterferenceHelper::CalculateChunkSuccessRate (double snir, Time duration, WifiMode mode) const
+{
+ if (duration == NanoSeconds (0)) {
+ return 1.0;
+ }
+ uint32_t rate = mode.GetPhyRate ();
+ uint64_t nbits = (uint64_t)(rate * duration.GetSeconds ());
+ double csr = m_errorRateModel->GetChunkSuccessRate (mode, snir, (uint32_t)nbits);
+ return csr;
+}
+
+double
+InterferenceHelper::CalculatePer (Ptr<const InterferenceHelper::Event> event, NiChanges *ni) const
+{
+ double psr = 1.0; /* Packet Success Rate */
+ NiChanges::iterator j = ni->begin ();
+ Time previous = (*j).GetTime ();
+ uint64_t plcpPreambleDelayUs;
+ WifiMode payloadMode = event->GetPayloadMode ();
+ WifiMode headerMode;
+ switch (event->GetPreambleType ()) {
+ case WIFI_PREAMBLE_LONG:
+ plcpPreambleDelayUs = m_plcpLongPreambleDelayUs;
+ headerMode = m_longPlcpHeaderMode;
+ break;
+ case WIFI_PREAMBLE_SHORT:
+ plcpPreambleDelayUs = m_plcpShortPreambleDelayUs;
+ headerMode = m_shortPlcpHeaderMode;
+ break;
+ default:
+ NS_ASSERT (false);
+ // only to quiet compiler. Really stupid.
+ plcpPreambleDelayUs = 0;
+ headerMode = m_shortPlcpHeaderMode;
+ break;
+ }
+ Time plcpHeaderStart = (*j).GetTime () + MicroSeconds (plcpPreambleDelayUs);
+ Time plcpPayloadStart = plcpHeaderStart +
+ Seconds ((m_plcpHeaderLength + 0.0) / headerMode.GetDataRate ());
+ double noiseInterferenceW = (*j).GetDelta ();
+ double powerW = event->GetRxPowerW ();
+
+ j++;
+ while (ni->end () != j)
+ {
+ Time current = (*j).GetTime ();
+ NS_ASSERT (current >= previous);
+
+ if (previous >= plcpPayloadStart)
+ {
+ psr *= CalculateChunkSuccessRate (CalculateSnr (powerW,
+ noiseInterferenceW,
+ payloadMode),
+ current - previous,
+ payloadMode);
+ }
+ else if (previous >= plcpHeaderStart)
+ {
+ if (current >= plcpPayloadStart)
+ {
+ psr *= CalculateChunkSuccessRate (CalculateSnr (powerW,
+ noiseInterferenceW,
+ headerMode),
+ plcpPayloadStart - previous,
+ headerMode);
+ psr *= CalculateChunkSuccessRate (CalculateSnr (powerW,
+ noiseInterferenceW,
+ payloadMode),
+ current - plcpPayloadStart,
+ payloadMode);
+ }
+ else
+ {
+ NS_ASSERT (current >= plcpHeaderStart);
+ psr *= CalculateChunkSuccessRate (CalculateSnr (powerW,
+ noiseInterferenceW,
+ headerMode),
+ current - previous,
+ headerMode);
+ }
+ }
+ else
+ {
+ if (current >= plcpPayloadStart)
+ {
+ psr *= CalculateChunkSuccessRate (CalculateSnr (powerW,
+ noiseInterferenceW,
+ headerMode),
+ plcpPayloadStart - plcpHeaderStart,
+ headerMode);
+ psr *= CalculateChunkSuccessRate (CalculateSnr (powerW,
+ noiseInterferenceW,
+ payloadMode),
+ current - plcpPayloadStart,
+ payloadMode);
+ }
+ else if (current >= plcpHeaderStart)
+ {
+ psr *= CalculateChunkSuccessRate (CalculateSnr (powerW,
+ noiseInterferenceW,
+ headerMode),
+ current - plcpHeaderStart,
+ headerMode);
+ }
+ }
+
+ noiseInterferenceW += (*j).GetDelta ();
+ previous = (*j).GetTime ();
+ j++;
+ }
+
+ double per = 1 - psr;
+ return per;
+}
+
+
+struct InterferenceHelper::SnrPer
+InterferenceHelper::CalculateSnrPer (Ptr<InterferenceHelper::Event> event)
+{
+ NiChanges ni;
+ double noiseInterferenceW = CalculateNoiseInterferenceW (event, &ni);
+ double snr = CalculateSnr (event->GetRxPowerW (),
+ noiseInterferenceW,
+ event->GetPayloadMode ());
+
+ /* calculate the SNIR at the start of the packet and accumulate
+ * all SNIR changes in the snir vector.
+ */
+ double per = CalculatePer (event, &ni);
+
+ struct SnrPer snrPer;
+ snrPer.snr = snr;
+ snrPer.per = per;
+ return snrPer;
+}
+
+
+
+} // namespace ns3
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/src/devices/wifi/interference-helper.h Sat Jun 14 10:52:10 2008 -0700
@@ -0,0 +1,107 @@
+#ifndef INTERFERENCE_HELPER_H
+#define INTERFERENCE_HELPER_H
+
+#include <stdint.h>
+#include <vector>
+#include <list>
+#include "wifi-mode.h"
+#include "wifi-preamble.h"
+#include "ns3/nstime.h"
+#include "ns3/ref-count-base.h"
+
+namespace ns3 {
+
+class ErrorRateModel;
+
+class InterferenceHelper
+{
+public:
+ class Event : public RefCountBase
+ {
+ public:
+ Event (uint32_t size, WifiMode payloadMode,
+ enum WifiPreamble preamble,
+ Time duration, double rxPower);
+ virtual ~Event ();
+
+ Time GetDuration (void) const;
+ Time GetStartTime (void) const;
+ Time GetEndTime (void) const;
+ bool Overlaps (Time time) const;
+ double GetRxPowerW (void) const;
+ uint32_t GetSize (void) const;
+ WifiMode GetPayloadMode (void) const;
+ enum WifiPreamble GetPreambleType (void) const;
+ private:
+ uint32_t m_size;
+ WifiMode m_payloadMode;
+ enum WifiPreamble m_preamble;
+ Time m_startTime;
+ Time m_endTime;
+ double m_rxPowerW;
+ };
+ struct SnrPer
+ {
+ double snr;
+ double per;
+ };
+
+ InterferenceHelper ();
+
+ void Configure80211aParameters (void);
+ void SetNoiseFloorW (double noiseFloor);
+ void SetErrorRateModel (Ptr<ErrorRateModel> rate);
+
+ double GetNoiseFloorW (void) const;
+ Ptr<ErrorRateModel> GetErrorRateModel (void) const;
+
+
+ /**
+ * \param energyW the minimum energy (W) requested
+ * \returns the expected amount of time the observed
+ * energy on the medium will be higher than
+ * the requested threshold.
+ */
+ Time GetEnergyDuration (double energyW);
+ Time CalculateTxDuration (uint32_t size, WifiMode payloadMode, WifiPreamble preamble) const;
+ Ptr<InterferenceHelper::Event> Add (uint32_t size, WifiMode payloadMode,
+ enum WifiPreamble preamble,
+ Time duration, double rxPower);
+
+ struct InterferenceHelper::SnrPer CalculateSnrPer (Ptr<InterferenceHelper::Event> event);
+private:
+ class NiChange {
+ public:
+ NiChange (Time time, double delta);
+ Time GetTime (void) const;
+ double GetDelta (void) const;
+ bool operator < (NiChange const &o) const;
+ private:
+ Time m_time;
+ double m_delta;
+ };
+ typedef std::vector <NiChange> NiChanges;
+ typedef std::list<Ptr<Event> > Events;
+
+ void AppendEvent (Ptr<Event> event);
+ double CalculateNoiseInterferenceW (Ptr<Event> event, NiChanges *ni) const;
+ double CalculateSnr (double signal, double noiseInterference, WifiMode mode) const;
+ double CalculateChunkSuccessRate (double snir, Time delay, WifiMode mode) const;
+ double CalculatePer (Ptr<const Event> event, NiChanges *ni) const;
+ Time GetMaxPacketDuration (void) const;
+
+ uint64_t m_plcpLongPreambleDelayUs;
+ uint64_t m_plcpShortPreambleDelayUs;
+ WifiMode m_longPlcpHeaderMode;
+ WifiMode m_shortPlcpHeaderMode;
+ uint32_t m_plcpHeaderLength;
+ Time m_maxPacketDuration;
+ double m_noiseFloorW;
+ Events m_events;
+ bool m_80211a;
+ Ptr<ErrorRateModel> m_errorRateModel;
+};
+
+} // namespace ns3
+
+#endif /* INTERFERENCE_HELPER_H */
--- a/src/devices/wifi/wifi-phy-state-helper.cc Thu Jun 12 12:31:02 2008 -0700
+++ b/src/devices/wifi/wifi-phy-state-helper.cc Sat Jun 14 10:52:10 2008 -0700
@@ -26,6 +26,8 @@
namespace ns3 {
+NS_OBJECT_ENSURE_REGISTERED (WifiPhyStateHelper);
+
TypeId
WifiPhyStateHelper::GetTypeId (void)
{
@@ -220,10 +222,10 @@
}
}
void
-WifiPhyStateHelper::NotifyCcaBusyStart (Time duration)
+WifiPhyStateHelper::NotifyMaybeCcaBusyStart (Time duration)
{
for (Listeners::const_iterator i = m_listeners.begin (); i != m_listeners.end (); i++) {
- (*i)->NotifyCcaBusyStart (duration);
+ (*i)->NotifyMaybeCcaBusyStart (duration);
}
}
@@ -343,7 +345,7 @@
void
WifiPhyStateHelper::SwitchMaybeToCcaBusy (Time duration)
{
- NotifyCcaBusyStart (duration);
+ NotifyMaybeCcaBusyStart (duration);
Time now = Simulator::Now ();
switch (GetState ()) {
case WifiPhy::IDLE:
@@ -357,7 +359,7 @@
break;
}
m_startCcaBusy = now;
- m_endCcaBusy = Max (m_endCcaBusy, now + duration);
+ m_endCcaBusy = std::max (m_endCcaBusy, now + duration);
}
} // namespace ns3
--- a/src/devices/wifi/wifi-phy-state-helper.h Thu Jun 12 12:31:02 2008 -0700
+++ b/src/devices/wifi/wifi-phy-state-helper.h Sat Jun 14 10:52:10 2008 -0700
@@ -65,7 +65,7 @@
void NotifySyncStart (Time duration);
void NotifySyncEndOk (void);
void NotifySyncEndError (void);
- void NotifyCcaBusyStart (Time duration);
+ void NotifyMaybeCcaBusyStart (Time duration);
void DoSwitchFromSync (void);
bool m_syncing;
--- a/src/devices/wifi/wifi-phy.h Thu Jun 12 12:31:02 2008 -0700
+++ b/src/devices/wifi/wifi-phy.h Sat Jun 14 10:52:10 2008 -0700
@@ -46,22 +46,24 @@
/**
* \param duration the expected duration of the packet reception.
*
- * we have received the first bit of a packet. We decided
+ * We have received the first bit of a packet. We decided
* that we could synchronize on this packet. It does not mean
* we will be able to successfully receive completely the
- * whole packet. It means we will report a BUSY status.
- * NotifyRxEndOk or NotifyRxEndError will be invoked later
- * to report whether or not the packet was successfully received.
+ * whole packet. It means that we will report a BUSY status until
+ * one of the following happens:
+ * - NotifyRxEndOk
+ * - NotifyExEndError
+ * - NotifyTxStart
*/
virtual void NotifyRxStart (Time duration) = 0;
/**
- * we have received the last bit of a packet for which
+ * We have received the last bit of a packet for which
* NotifyRxStart was invoked first and, the packet has
* been successfully received.
*/
virtual void NotifyRxEndOk (void) = 0;
/**
- * we have received the last bit of a packet for which
+ * We have received the last bit of a packet for which
* NotifyRxStart was invoked first and, the packet has
* _not_ been successfully received.
*/
@@ -70,14 +72,28 @@
* \param duration the expected transmission duration.
*
* We are about to send the first bit of the packet.
+ * We do not send any event to notify the end of
+ * transmission. Listeners should assume that the
+ * channel implicitely reverts to the idle state
+ * unless they have received a cca busy report.
*/
virtual void NotifyTxStart (Time duration) = 0;
/**
* \param duration the expected busy duration.
*
- * We are going to be cca-busy for a while.
+ * This method does not really report a real state
+ * change as opposed to the other methods in this class.
+ * It merely reports that, unless the medium is reported
+ * busy through NotifyTxStart or NotifyRxStart/End,
+ * it will be busy as defined by the currently selected
+ * CCA mode.
+ *
+ * Typical client code which wants to have a clear picture
+ * of the CCA state will need to keep track of the time at
+ * which the last NotifyCcaBusyStart method is called and
+ * what duration it reported.
*/
- virtual void NotifyCcaBusyStart (Time duration) = 0;
+ virtual void NotifyMaybeCcaBusyStart (Time duration) = 0;
};
--- a/src/devices/wifi/wscript Thu Jun 12 12:31:02 2008 -0700
+++ b/src/devices/wifi/wscript Sat Jun 14 10:52:10 2008 -0700
@@ -13,6 +13,7 @@
'wifi-phy.cc',
'wifi-phy-state-helper.cc',
'error-rate-model.cc',
+ 'interference-helper.cc',
'yans-wifi-phy.cc',
'yans-wifi-channel.cc',
'wifi-mac-header.cc',
@@ -60,6 +61,7 @@
'yans-wifi-phy.h',
'yans-wifi-channel.h',
'wifi-phy.h',
+ 'interference-helper.h',
'wifi-remote-station-manager.h',
'arf-wifi-manager.h',
'aarf-wifi-manager.h',
--- a/src/devices/wifi/yans-wifi-phy.cc Thu Jun 12 12:31:02 2008 -0700
+++ b/src/devices/wifi/yans-wifi-phy.cc Sat Jun 14 10:52:10 2008 -0700
@@ -39,109 +39,6 @@
namespace ns3 {
-/****************************************************************
- * Phy event class
- ****************************************************************/
-
-class RxEvent
-{
-public:
- RxEvent (uint32_t size, WifiMode payloadMode,
- enum WifiPreamble preamble,
- Time duration, double rxPower)
- : m_size (size),
- m_payloadMode (payloadMode),
- m_preamble (preamble),
- m_startTime (Simulator::Now ()),
- m_endTime (m_startTime + duration),
- m_rxPowerW (rxPower),
- m_refCount (1)
- {}
- ~RxEvent ()
- {
- NS_ASSERT (m_refCount == 0);
- }
-
- void Ref (void) const {
- m_refCount++;
- }
- void Unref (void) const {
- m_refCount--;
- if (m_refCount == 0) {
- delete this;
- }
- }
- Time GetDuration (void) const {
- return m_endTime - m_startTime;
- }
- Time GetStartTime (void) const {
- return m_startTime;
- }
- Time GetEndTime (void) const {
- return m_endTime;
- }
- bool Overlaps (Time time) const {
- if (m_startTime <= time &&
- m_endTime >= time) {
- return true;
- } else {
- return false;
- }
- }
- double GetRxPowerW (void) const {
- return m_rxPowerW;
- }
- uint32_t GetSize (void) const {
- return m_size;
- }
- WifiMode GetPayloadMode (void) const {
- return m_payloadMode;
- }
- enum WifiPreamble GetPreambleType (void) const {
- return m_preamble;
- }
-
-private:
- uint32_t m_size;
- WifiMode m_payloadMode;
- enum WifiPreamble m_preamble;
- Time m_startTime;
- Time m_endTime;
- double m_rxPowerW;
- mutable int m_refCount;
-};
-
-
-/****************************************************************
- * Class which records SNIR change events for a
- * short period of time.
- ****************************************************************/
-
-YansWifiPhy::NiChange::NiChange (Time time, double delta)
- : m_time (time), m_delta (delta)
-{}
-Time
-YansWifiPhy::NiChange::GetTime (void) const
-{
- return m_time;
-}
-double
-YansWifiPhy::NiChange::GetDelta (void) const
-{
- return m_delta;
-}
-bool
-YansWifiPhy::NiChange::operator < (YansWifiPhy::NiChange const &o) const
-{
- return (m_time < o.m_time)?true:false;
-}
-
-
-
-/****************************************************************
- * The actual YansWifiPhy class
- ****************************************************************/
-
NS_OBJECT_ENSURE_REGISTERED (YansWifiPhy);
TypeId
@@ -157,6 +54,13 @@
MakeDoubleAccessor (&YansWifiPhy::SetEdThreshold,
&YansWifiPhy::GetEdThreshold),
MakeDoubleChecker<double> ())
+ .AddAttribute ("CcaMode1Threshold",
+ "The energy of a received signal should be higher than "
+ "this threshold (dbm) to allow the PHY layer to declare CCA BUSY state",
+ DoubleValue (-140.0),
+ MakeDoubleAccessor (&YansWifiPhy::SetCcaMode1Threshold,
+ &YansWifiPhy::GetCcaMode1Threshold),
+ MakeDoubleChecker<double> ())
.AddAttribute ("TxGain",
"Transmission gain (dB).",
DoubleValue (1.0),
@@ -213,7 +117,6 @@
{
NS_LOG_FUNCTION (this);
m_state = CreateObject<WifiPhyStateHelper> ();
- m_errorRateModel = Create<ErrorRateModel> ();
}
YansWifiPhy::~YansWifiPhy ()
@@ -226,7 +129,6 @@
{
NS_LOG_FUNCTION (this);
m_channel = 0;
- m_events.clear ();
m_modes.clear ();
}
@@ -253,7 +155,7 @@
YansWifiPhy::SetRxNoise (double db)
{
NS_LOG_FUNCTION (this << db);
- m_rxNoiseRatio = DbToRatio (db);
+ m_interference.SetNoiseFloorW (DbToRatio (db));
}
void
YansWifiPhy::SetTxPowerStart (double start)
@@ -291,10 +193,21 @@
NS_LOG_FUNCTION (this << threshold);
m_edThresholdW = DbmToW (threshold);
}
+void
+YansWifiPhy::SetCcaMode1Threshold (double threshold)
+{
+ NS_LOG_FUNCTION (this << threshold);
+ m_ccaMode1ThresholdW = DbmToW (threshold);
+}
+void
+YansWifiPhy::SetErrorRateModel (Ptr<ErrorRateModel> rate)
+{
+ m_interference.SetErrorRateModel (rate);
+}
double
YansWifiPhy::GetRxNoise (void) const
{
- return RatioToDb (m_rxNoiseRatio);
+ return RatioToDb (m_interference.GetNoiseFloorW ());
}
double
YansWifiPhy::GetTxPowerStart (void) const
@@ -323,6 +236,24 @@
return WToDbm (m_edThresholdW);
}
+double
+YansWifiPhy::GetCcaMode1Threshold (void) const
+{
+ return WToDbm (m_ccaMode1ThresholdW);
+}
+
+Ptr<ErrorRateModel>
+YansWifiPhy::GetErrorRateModel (void) const
+{
+ return m_interference.GetErrorRateModel ();
+}
+
+double
+YansWifiPhy::CalculateSnr (WifiMode txMode, double ber) const
+{
+ return m_interference.GetErrorRateModel ()->CalculateSnr (txMode, ber);
+}
+
Ptr<WifiChannel>
YansWifiPhy::GetChannel (void) const
{
@@ -347,9 +278,9 @@
}
void
YansWifiPhy::StartReceivePacket (Ptr<Packet> packet,
- double rxPowerDbm,
- WifiMode txMode,
- enum WifiPreamble preamble)
+ double rxPowerDbm,
+ WifiMode txMode,
+ enum WifiPreamble preamble)
{
NS_LOG_FUNCTION (this << packet << rxPowerDbm << txMode << preamble);
rxPowerDbm += m_rxGainDb;
@@ -357,12 +288,12 @@
Time rxDuration = CalculateTxDuration (packet->GetSize (), txMode, preamble);
Time endRx = Simulator::Now () + rxDuration;
- Ptr<RxEvent> event = Create<RxEvent> (packet->GetSize (),
- txMode,
- preamble,
- rxDuration,
- rxPowerW);
- AppendEvent (event);
+ Ptr<InterferenceHelper::Event> event;
+ event = m_interference.Add (packet->GetSize (),
+ txMode,
+ preamble,
+ rxDuration,
+ rxPowerW);
switch (m_state->GetState ()) {
case YansWifiPhy::SYNC:
@@ -409,34 +340,16 @@
return;
maybeCcaBusy:
+ // We are here because we have received the first bit of a packet and we are
+ // not going to be able to synchronize on it
+ // In this model, CCA becomes busy when the aggregation of all signals as
+ // tracked by the InterferenceHelper class is higher than the CcaBusyThreshold
- if (rxPowerW > m_edThresholdW)
- {
- m_state->SwitchMaybeToCcaBusy (rxDuration);
- }
- else
+ Time delayUntilCcaEnd = m_interference.GetEnergyDuration (m_ccaMode1ThresholdW);
+ if (!delayUntilCcaEnd.IsZero ())
{
- double threshold = m_edThresholdW - rxPowerW;
- NiChanges ni;
- CalculateNoiseInterferenceW (event, &ni);
- double noiseInterferenceW = 0.0;
- Time end = Simulator::Now ();
- for (NiChanges::const_iterator i = ni.begin (); i != ni.end (); i++)
- {
- noiseInterferenceW += i->GetDelta ();
- if (noiseInterferenceW < threshold)
- {
- break;
- }
- end = i->GetTime ();
- }
- if (end > Simulator::Now ())
- {
- Time delta = end - Simulator::Now ();
- m_state->SwitchMaybeToCcaBusy (delta);
- }
+ m_state->SwitchMaybeToCcaBusy (delayUntilCcaEnd);
}
-
}
void
YansWifiPhy::SendPacket (Ptr<const Packet> packet, WifiMode txMode, WifiPreamble preamble, uint8_t txPower)
@@ -475,64 +388,11 @@
return m_nTxPower;
}
-double
-YansWifiPhy::CalculateSnr (WifiMode txMode, double ber) const
-{
- double low, high, precision;
- low = 1e-25;
- high = 1e25;
- precision = 1e-12;
- while (high - low > precision)
- {
- NS_ASSERT (high >= low);
- double middle = low + (high - low) / 2;
- if ((1 - m_errorRateModel->GetChunkSuccessRate (txMode, middle, 1)) > ber)
- {
- low = middle;
- }
- else
- {
- high = middle;
- }
- }
- return low;
-}
-
-void
-YansWifiPhy::Configure80211aParameters (void)
-{
- NS_LOG_FUNCTION (this);
- m_plcpLongPreambleDelayUs = 16;
- m_plcpShortPreambleDelayUs = 16;
- m_longPlcpHeaderMode = g_6mba;
- m_shortPlcpHeaderMode = g_6mba;
- m_plcpHeaderLength = 4 + 1 + 12 + 1 + 6;
- /* 4095 bytes at a 6Mb/s rate with a 1/2 coding rate. */
- m_maxPacketDuration = CalculateTxDuration (4095, g_6mba, WIFI_PREAMBLE_LONG);
-}
-
-void
-YansWifiPhy::PrintModes (void) const
-{
-#if 0
- for (double db = -10; db < 30; db+= 0.5) {
- double snr = DbToRatio (db);
- std::cout <<snr<<" ";
- for (uint8_t i = 0; i < GetNModes (); i++) {
- WifiMode mode = GetMode (i);
- double ber = 1-m_errorRateModel->GetChunkSuccessRate (mode,snr, 2000*8);
- std::cout <<ber<< " ";
- }
- std::cout << std::endl;
- }
-#endif
-}
-
void
YansWifiPhy::Configure80211a (void)
{
NS_LOG_FUNCTION (this);
- Configure80211aParameters ();
+ m_interference.Configure80211aParameters ();
m_modes.push_back (g_6mba);
m_modes.push_back (g_9mba);
m_modes.push_back (g_12mba);
@@ -541,22 +401,18 @@
m_modes.push_back (g_36mba);
m_modes.push_back (g_48mba);
m_modes.push_back (g_54mba);
-
- PrintModes ();
}
void
YansWifiPhy::ConfigureHolland (void)
{
NS_LOG_FUNCTION (this);
- Configure80211aParameters ();
+ m_interference.Configure80211aParameters ();
m_modes.push_back (g_6mba);
m_modes.push_back (g_12mba);
m_modes.push_back (g_18mba);
m_modes.push_back (g_36mba);
m_modes.push_back (g_54mba);
-
- PrintModes ();
}
void
@@ -609,28 +465,12 @@
return m_state->GetLastRxStartTime ();
}
-
-Time
-YansWifiPhy::CalculateTxDuration (uint32_t size, WifiMode payloadMode, WifiPreamble preamble) const
+Time
+YansWifiPhy::CalculateTxDuration (uint32_t size, WifiMode payloadMode, enum WifiPreamble preamble) const
{
- uint64_t delay = 0;
- switch (m_standard) {
- case WIFI_PHY_STANDARD_80211a:
- case WIFI_PHY_STANDARD_holland: {
- delay += m_plcpLongPreambleDelayUs;
- // symbol duration is 4us
- delay += 4;
- delay += lrint (ceil ((size * 8.0 + 16.0 + 6.0) / payloadMode.GetDataRate () / 4e-6) * 4);
- } break;
- default:
- // quiet compiler.
- NS_ASSERT (false);
- break;
- }
- return MicroSeconds (delay);
+ return m_interference.CalculateTxDuration (size, payloadMode, preamble);
}
-
double
YansWifiPhy::DbToRatio (double dB) const
{
@@ -663,12 +503,6 @@
return m_edThresholdW;
}
-Time
-YansWifiPhy::GetMaxPacketDuration (void) const
-{
- return m_maxPacketDuration;
-}
-
double
YansWifiPhy::GetPowerDbm (uint8_t power) const
{
@@ -678,225 +512,27 @@
return dbm;
}
-
-void
-YansWifiPhy::AppendEvent (Ptr<RxEvent> event)
-{
- /* attempt to remove the events which are
- * not useful anymore.
- * i.e.: all events which end _before_
- * now - m_maxPacketDuration
- */
-
- if (Simulator::Now () > GetMaxPacketDuration ())
- {
- Time end = Simulator::Now () - GetMaxPacketDuration ();
- Events::iterator i = m_events.begin ();
- while (i != m_events.end () &&
- (*i)->GetEndTime () <= end)
- {
- i++;
- }
- m_events.erase (m_events.begin (), i);
- }
- m_events.push_back (event);
-}
-
-
-double
-YansWifiPhy::CalculateSnr (double signal, double noiseInterference, WifiMode mode) const
-{
- // thermal noise at 290K in J/s = W
- static const double BOLTZMANN = 1.3803e-23;
- double Nt = BOLTZMANN * 290.0 * mode.GetBandwidth ();
- // receiver noise Floor (W)
- double noiseFloor = m_rxNoiseRatio * Nt;
- double noise = noiseFloor + noiseInterference;
- double snr = signal / noise;
- return snr;
-}
-
-double
-YansWifiPhy::CalculateNoiseInterferenceW (Ptr<RxEvent> event, NiChanges *ni) const
-{
- Events::const_iterator i = m_events.begin ();
- double noiseInterference = 0.0;
- while (i != m_events.end ())
- {
- if (event == (*i))
- {
- i++;
- continue;
- }
- if (event->Overlaps ((*i)->GetStartTime ()))
- {
- ni->push_back (NiChange ((*i)->GetStartTime (), (*i)->GetRxPowerW ()));
- }
- if (event->Overlaps ((*i)->GetEndTime ()))
- {
- ni->push_back (NiChange ((*i)->GetEndTime (), -(*i)->GetRxPowerW ()));
- }
- if ((*i)->Overlaps (event->GetStartTime ()))
- {
- noiseInterference += (*i)->GetRxPowerW ();
- }
- i++;
- }
- ni->push_back (NiChange (event->GetStartTime (), noiseInterference));
- ni->push_back (NiChange (event->GetEndTime (), 0));
-
- /* quicksort vector of NI changes by time. */
- std::sort (ni->begin (), ni->end (), std::less<NiChange> ());
-
- return noiseInterference;
-}
-
-double
-YansWifiPhy::CalculateChunkSuccessRate (double snir, Time duration, WifiMode mode) const
-{
- if (duration == NanoSeconds (0)) {
- return 1.0;
- }
- uint32_t rate = mode.GetPhyRate ();
- uint64_t nbits = (uint64_t)(rate * duration.GetSeconds ());
- double csr = m_errorRateModel->GetChunkSuccessRate (mode, snir, (uint32_t)nbits);
- return csr;
-}
-
-double
-YansWifiPhy::CalculatePer (Ptr<const RxEvent> event, NiChanges *ni) const
-{
- double psr = 1.0; /* Packet Success Rate */
- NiChanges::iterator j = ni->begin ();
- Time previous = (*j).GetTime ();
- uint64_t plcpPreambleDelayUs;
- WifiMode payloadMode = event->GetPayloadMode ();
- WifiMode headerMode;
- switch (event->GetPreambleType ()) {
- case WIFI_PREAMBLE_LONG:
- plcpPreambleDelayUs = m_plcpLongPreambleDelayUs;
- headerMode = m_longPlcpHeaderMode;
- break;
- case WIFI_PREAMBLE_SHORT:
- plcpPreambleDelayUs = m_plcpShortPreambleDelayUs;
- headerMode = m_shortPlcpHeaderMode;
- break;
- default:
- NS_ASSERT (false);
- // only to quiet compiler. Really stupid.
- plcpPreambleDelayUs = 0;
- headerMode = m_shortPlcpHeaderMode;
- break;
- }
- Time plcpHeaderStart = (*j).GetTime () + MicroSeconds (plcpPreambleDelayUs);
- Time plcpPayloadStart = plcpHeaderStart +
- Seconds ((m_plcpHeaderLength + 0.0) / headerMode.GetDataRate ());
- double noiseInterferenceW = (*j).GetDelta ();
- double powerW = event->GetRxPowerW ();
-
- j++;
- while (ni->end () != j)
- {
- Time current = (*j).GetTime ();
- NS_ASSERT (current >= previous);
-
- if (previous >= plcpPayloadStart)
- {
- psr *= CalculateChunkSuccessRate (CalculateSnr (powerW,
- noiseInterferenceW,
- payloadMode),
- current - previous,
- payloadMode);
- }
- else if (previous >= plcpHeaderStart)
- {
- if (current >= plcpPayloadStart)
- {
- psr *= CalculateChunkSuccessRate (CalculateSnr (powerW,
- noiseInterferenceW,
- headerMode),
- plcpPayloadStart - previous,
- headerMode);
- psr *= CalculateChunkSuccessRate (CalculateSnr (powerW,
- noiseInterferenceW,
- payloadMode),
- current - plcpPayloadStart,
- payloadMode);
- }
- else
- {
- NS_ASSERT (current >= plcpHeaderStart);
- psr *= CalculateChunkSuccessRate (CalculateSnr (powerW,
- noiseInterferenceW,
- headerMode),
- current - previous,
- headerMode);
- }
- }
- else
- {
- if (current >= plcpPayloadStart)
- {
- psr *= CalculateChunkSuccessRate (CalculateSnr (powerW,
- noiseInterferenceW,
- headerMode),
- plcpPayloadStart - plcpHeaderStart,
- headerMode);
- psr *= CalculateChunkSuccessRate (CalculateSnr (powerW,
- noiseInterferenceW,
- payloadMode),
- current - plcpPayloadStart,
- payloadMode);
- }
- else if (current >= plcpHeaderStart)
- {
- psr *= CalculateChunkSuccessRate (CalculateSnr (powerW,
- noiseInterferenceW,
- headerMode),
- current - plcpHeaderStart,
- headerMode);
- }
- }
-
- noiseInterferenceW += (*j).GetDelta ();
- previous = (*j).GetTime ();
- j++;
- }
-
- double per = 1 - psr;
- return per;
-}
-
-
void
-YansWifiPhy::EndSync (Ptr<Packet> packet, Ptr<RxEvent> event)
+YansWifiPhy::EndSync (Ptr<Packet> packet, Ptr<InterferenceHelper::Event> event)
{
NS_LOG_FUNCTION (this << packet << event);
NS_ASSERT (IsStateSync ());
NS_ASSERT (event->GetEndTime () == Simulator::Now ());
- NiChanges ni;
- double noiseInterferenceW = CalculateNoiseInterferenceW (event, &ni);
- double snr = CalculateSnr (event->GetRxPowerW (),
- noiseInterferenceW,
- event->GetPayloadMode ());
+ struct InterferenceHelper::SnrPer snrPer;
+ snrPer = m_interference.CalculateSnrPer (event);
+
+ NS_LOG_DEBUG ("mode="<<(event->GetPayloadMode ().GetDataRate ())<<
+ ", snr="<<snrPer.snr<<", per="<<snrPer.per<<", size="<<packet->GetSize ());
- /* calculate the SNIR at the start of the packet and accumulate
- * all SNIR changes in the snir vector.
- */
- double per = CalculatePer (event, &ni);
- NS_LOG_DEBUG ("mode="<<(event->GetPayloadMode ().GetDataRate ())<<
- ", ber="<<(1-m_errorRateModel->GetChunkSuccessRate (event->GetPayloadMode (), snr, 1))<<
- ", snr="<<snr<<", per="<<per<<", size="<<packet->GetSize ());
-
- if (m_random.GetValue () > per)
+ if (m_random.GetValue () > snrPer.per)
{
- m_state->SwitchFromSyncEndOk (packet, snr, event->GetPayloadMode (), event->GetPreambleType ());
+ m_state->SwitchFromSyncEndOk (packet, snrPer.snr, event->GetPayloadMode (), event->GetPreambleType ());
}
else
{
/* failure. */
- m_state->SwitchFromSyncEndError (packet, snr);
+ m_state->SwitchFromSyncEndError (packet, snrPer.snr);
}
}
--- a/src/devices/wifi/yans-wifi-phy.h Thu Jun 12 12:31:02 2008 -0700
+++ b/src/devices/wifi/yans-wifi-phy.h Sat Jun 14 10:52:10 2008 -0700
@@ -21,8 +21,6 @@
#ifndef YANS_WIFI_PHY_H
#define YANS_WIFI_PHY_H
-#include <vector>
-#include <list>
#include <stdint.h>
#include "ns3/callback.h"
#include "ns3/event-id.h"
@@ -36,6 +34,7 @@
#include "wifi-mode.h"
#include "wifi-preamble.h"
#include "wifi-phy-standard.h"
+#include "interference-helper.h"
namespace ns3 {
@@ -44,7 +43,6 @@
class RxEvent;
class YansWifiChannel;
class WifiPhyStateHelper;
-class ErrorRateModel;
/**
@@ -84,10 +82,14 @@
void SetTxGain (double gain);
void SetRxGain (double gain);
void SetEdThreshold (double threshold);
+ void SetCcaMode1Threshold (double threshold);
+ void SetErrorRateModel (Ptr<ErrorRateModel> rate);
double GetRxNoise (void) const;
double GetTxGain (void) const;
double GetRxGain (void) const;
double GetEdThreshold (void) const;
+ double GetCcaMode1Threshold (void) const;
+ Ptr<ErrorRateModel> GetErrorRateModel (void) const;
virtual double GetTxPowerStart (void) const;
@@ -112,24 +114,10 @@
virtual Ptr<WifiChannel> GetChannel (void) const;
private:
- class NiChange {
- public:
- NiChange (Time time, double delta);
- Time GetTime (void) const;
- double GetDelta (void) const;
- bool operator < (NiChange const &o) const;
- private:
- Time m_time;
- double m_delta;
- };
typedef std::vector<WifiMode> Modes;
- typedef std::list<Ptr<RxEvent> > Events;
- typedef std::vector <NiChange> NiChanges;
private:
virtual void DoDispose (void);
- void Configure80211aParameters (void);
- void PrintModes (void) const;
void Configure80211a (void);
void ConfigureHolland (void);
double GetEdThresholdW (void) const;
@@ -137,28 +125,14 @@
double DbToRatio (double db) const;
double WToDbm (double w) const;
double RatioToDb (double ratio) const;
- Time GetMaxPacketDuration (void) const;
double GetPowerDbm (uint8_t power) const;
+ void EndSync (Ptr<Packet> packet, Ptr<InterferenceHelper::Event> event);
- void AppendEvent (Ptr<RxEvent> event);
- double CalculateNoiseInterferenceW (Ptr<RxEvent> event, NiChanges *ni) const;
- double CalculateSnr (double signal, double noiseInterference, WifiMode mode) const;
- double CalculateChunkSuccessRate (double snir, Time delay, WifiMode mode) const;
- double CalculatePer (Ptr<const RxEvent> event, NiChanges *ni) const;
- void EndSync (Ptr<Packet> packet, Ptr<RxEvent> event);
private:
- uint64_t m_txPrepareDelayUs;
- uint64_t m_plcpLongPreambleDelayUs;
- uint64_t m_plcpShortPreambleDelayUs;
- WifiMode m_longPlcpHeaderMode;
- WifiMode m_shortPlcpHeaderMode;
- uint32_t m_plcpHeaderLength;
- Time m_maxPacketDuration;
-
- double m_edThresholdW; /* unit: W */
+ double m_edThresholdW;
+ double m_ccaMode1ThresholdW;
double m_txGainDb;
double m_rxGainDb;
- double m_rxNoiseRatio;
double m_txPowerBaseDbm;
double m_txPowerEndDbm;
uint32_t m_nTxPower;
@@ -166,11 +140,10 @@
Ptr<YansWifiChannel> m_channel;
Modes m_modes;
EventId m_endSyncEvent;
- Events m_events;
UniformVariable m_random;
WifiPhyStandard m_standard;
Ptr<WifiPhyStateHelper> m_state;
- Ptr<ErrorRateModel> m_errorRateModel;
+ InterferenceHelper m_interference;
};
} // namespace ns3