wifi: Handle main PHY channel switch when no CTS is received

...by the aux PHY that gained an UL TXOP and sent an RTS.
This commit is contained in:
Stefano Avallone
2023-10-04 17:13:46 +02:00
committed by Stefano Avallone
parent 38b4db155b
commit 37034f2fa8
2 changed files with 32 additions and 13 deletions

View File

@@ -130,14 +130,34 @@ DefaultEmlsrManager::DoNotifyTxopEnd(uint8_t linkId)
// switch main PHY to the previous link, if needed
if (m_linkIdForMainPhyAfterTxop && linkId != m_linkIdForMainPhyAfterTxop)
{
auto phy = m_auxPhyToReconnect;
SwitchMainPhy(*m_linkIdForMainPhyAfterTxop, false);
// Reconnect the aux PHY to its original link
Simulator::ScheduleNow([=, this]() {
auto auxPhy = m_auxPhyToReconnect;
// lambda to switch the main PHY back to its previous link and reconnect the aux PHY to
// its original link
auto restorePhys = [=, this]() {
SwitchMainPhy(*m_linkIdForMainPhyAfterTxop, false);
// the Aux PHY is not actually switching (hence no switching delay)
GetStaMac()->NotifySwitchingEmlsrLink(phy, linkId, Seconds(0));
});
SetCcaEdThresholdOnLinkSwitch(phy, linkId);
GetStaMac()->NotifySwitchingEmlsrLink(auxPhy, linkId, Seconds(0));
SetCcaEdThresholdOnLinkSwitch(auxPhy, linkId);
m_linkIdForMainPhyAfterTxop.reset();
};
auto mainPhy = GetStaMac()->GetDevice()->GetPhy(m_mainPhyId);
// the main PHY may be switching at the end of a TXOP when, e.g., the main PHY starts
// switching to a link on which an aux PHY gained a TXOP and sent an RTS, but the CTS
// is not received and the UL TXOP ends before the main PHY channel switch is completed.
// In such cases, wait until the main PHY channel switch is completed before requesting
// a new channel switch.
if (!mainPhy->IsStateSwitching())
{
restorePhys();
}
else
{
Simulator::Schedule(mainPhy->GetDelayUntilIdle(), restorePhys);
}
return;
}
m_linkIdForMainPhyAfterTxop.reset();
}

View File

@@ -584,13 +584,12 @@ EmlsrManager::StartMediumSyncDelayTimer(uint8_t linkId)
// reset the max number of TXOP attempts
it->second.msdNTxopsLeft = m_msdMaxNTxops;
if (!it->second.timer.IsRunning())
// there are cases in which no PHY is operating on a link; e.g., the main PHY starts
// switching to a link on which an aux PHY gained a TXOP and sent an RTS, but the CTS
// is not received and the UL TXOP ends before the main PHY channel switch is
// completed. The MSD timer is started on the link left "uncovered" by the main PHY
if (auto phy = m_staMac->GetWifiPhy(id); phy && !it->second.timer.IsRunning())
{
// set the MSD OFDM ED threshold
auto phy = m_staMac->GetWifiPhy(id);
NS_ASSERT_MSG(phy,
"Expected a PHY to be operating on link "
<< +id << " after terminating a TXOP");
NS_LOG_DEBUG("Setting CCA ED threshold on link "
<< +id << " to " << +m_msdOfdmEdThreshold << " PHY " << phy);
m_prevCcaEdThreshold[phy] = phy->GetCcaEdThreshold();