diff --git a/src/wifi/model/channel-access-manager.cc b/src/wifi/model/channel-access-manager.cc index 3393f2232..6f515bc35 100644 --- a/src/wifi/model/channel-access-manager.cc +++ b/src/wifi/model/channel-access-manager.cc @@ -246,19 +246,24 @@ ChannelAccessManager::SetupPhyListener(Ptr phy) { NS_LOG_FUNCTION(this << phy); - if (auto phyListener = GetPhyListener(phy)) + auto phyListener = GetPhyListener(phy); + + if (phyListener) { // a PHY listener for the given PHY already exists, it must be inactive NS_ASSERT_MSG(!phyListener->IsActive(), "There is already an active listener registered for given PHY"); NS_ASSERT_MSG(!m_phy, "Cannot reactivate a listener if another PHY is active"); phyListener->SetActive(true); + // if a PHY listener already exists, the PHY was disconnected and now reconnected to the + // channel access manager; unregister the listener and register again (below) to get + // updated CCA busy information + phy->UnregisterListener(phyListener); } else { phyListener = std::make_shared(this); m_phyListeners.emplace(phy, phyListener); - phy->RegisterListener(phyListener); } if (m_phy) { @@ -266,6 +271,7 @@ ChannelAccessManager::SetupPhyListener(Ptr phy) } m_phy = phy; // this is the new active PHY InitLastBusyStructs(); + phy->RegisterListener(phyListener); if (phy->IsStateSwitching()) { auto duration = phy->GetDelayUntilIdle(); diff --git a/src/wifi/model/wifi-phy.cc b/src/wifi/model/wifi-phy.cc index c3c35dda6..7013bebc9 100644 --- a/src/wifi/model/wifi-phy.cc +++ b/src/wifi/model/wifi-phy.cc @@ -484,6 +484,11 @@ void WifiPhy::RegisterListener(const std::shared_ptr& listener) { m_state->RegisterListener(listener); + if (IsInitialized()) + { + // provide CCA busy information upon registering a PHY listener + SwitchMaybeToCcaBusy(nullptr); + } } void diff --git a/src/wifi/model/wifi-phy.h b/src/wifi/model/wifi-phy.h index a11fea0f8..8057f78f7 100644 --- a/src/wifi/model/wifi-phy.h +++ b/src/wifi/model/wifi-phy.h @@ -86,7 +86,7 @@ class WifiPhy : public Object * \param listener the new listener * * Add the input listener to the list of objects to be notified of - * PHY-level events. + * PHY-level events. The input listener is notified of CCA busy information. */ void RegisterListener(const std::shared_ptr& listener); /**