From a6b1afe70d7a330dd44beab2e56d0135c871b255 Mon Sep 17 00:00:00 2001 From: Ravi Vantipalli Date: Tue, 17 Dec 2024 09:28:10 -0800 Subject: [PATCH] DLB: SaiSwitch changes for ARS support Summary: SaiSwitch changes to process update for flowlet config Reviewed By: msomasundaran Differential Revision: D63679606 fbshipit-source-id: 59ba077026cf4316188f31ec8a8d0c9d9f31b718 --- fboss/agent/hw/sai/switch/SaiManagerTable.cpp | 1 + fboss/agent/hw/sai/switch/SaiSwitch.cpp | 75 +++++++++++++++++++ fboss/agent/hw/sai/switch/SaiSwitch.h | 8 ++ .../agent/hw/sai/switch/SaiSwitchManager.cpp | 3 +- 4 files changed, 85 insertions(+), 2 deletions(-) diff --git a/fboss/agent/hw/sai/switch/SaiManagerTable.cpp b/fboss/agent/hw/sai/switch/SaiManagerTable.cpp index 7dfec2e5fdbbf..5286e3d2ac1fe 100644 --- a/fboss/agent/hw/sai/switch/SaiManagerTable.cpp +++ b/fboss/agent/hw/sai/switch/SaiManagerTable.cpp @@ -175,6 +175,7 @@ void SaiManagerTable::reset(bool skipSwitchManager) { switchManager_->resetQosMaps(); samplePacketManager_.reset(); + switchManager_->resetArsProfile(); arsProfileManager_.reset(); arsManager_.reset(); diff --git a/fboss/agent/hw/sai/switch/SaiSwitch.cpp b/fboss/agent/hw/sai/switch/SaiSwitch.cpp index 735bfd51600d0..da9473de92f49 100644 --- a/fboss/agent/hw/sai/switch/SaiSwitch.cpp +++ b/fboss/agent/hw/sai/switch/SaiSwitch.cpp @@ -31,6 +31,8 @@ #include "fboss/agent/hw/sai/switch/ConcurrentIndices.h" #include "fboss/agent/hw/sai/switch/SaiAclTableGroupManager.h" #include "fboss/agent/hw/sai/switch/SaiAclTableManager.h" +#include "fboss/agent/hw/sai/switch/SaiArsManager.h" +#include "fboss/agent/hw/sai/switch/SaiArsProfileManager.h" #include "fboss/agent/hw/sai/switch/SaiBufferManager.h" #include "fboss/agent/hw/sai/switch/SaiCounterManager.h" #include "fboss/agent/hw/sai/switch/SaiDebugCounterManager.h" @@ -1139,6 +1141,12 @@ std::shared_ptr SaiSwitch::stateChangedImplLocked( &SaiUdfManager::removeUdfGroup); #endif + if (FLAGS_flowletSwitchingEnable) { + if (platform_->getAsic()->isSupported(HwAsic::Feature::FLOWLET)) { + processFlowletSwitchingConfigDelta(delta, lockPolicy); + } + } + processPfcWatchdogGlobalDelta(delta, lockPolicy); if (platform_->getAsic()->isSupported( @@ -4166,6 +4174,73 @@ void SaiSwitch::processPfcWatchdogGlobalDelta( processPfcWatchdogGlobalDeltaLocked(delta, lockPolicy.lock()); } +void SaiSwitch::processFlowletSwitchingConfigDeltaLocked( + const StateDelta& delta, + const std::lock_guard& /* lock */) { + const auto flowletSwitchingDelta = delta.getFlowletSwitchingConfigDelta(); + const auto& oldFlowletConfig = flowletSwitchingDelta.getOld(); + const auto& newFlowletConfig = flowletSwitchingDelta.getNew(); + + // process change in the flowlet switching config + if (!oldFlowletConfig && !newFlowletConfig) { + XLOG(DBG5) << "Flowlet switching config is null"; + return; + } + +#if SAI_API_VERSION >= SAI_VERSION(1, 14, 0) + auto& switchManager = managerTable_->switchManager(); + auto& arsManager = managerTable_->arsManager(); + auto& arsProfileManager = managerTable_->arsProfileManager(); + auto& nextHopGroupManager = managerTable_->nextHopGroupManager(); + + if (oldFlowletConfig && newFlowletConfig) { + if (*oldFlowletConfig == *newFlowletConfig) { + XLOG(DBG5) << "Flowlet switching config is same"; + // flowlet is enabled here. lets walk through all ecmp objects to ensure + // things look ok. For most purposes, this will be a no-op + // One case this becomes useful is when a nhg went away and there are + // other nhg's waiting to get flowlet resources, this will ensure they do + // during a config update + nextHopGroupManager.updateArsModeAll(newFlowletConfig); + return; + } else { + XLOG(DBG2) << "Flowlet switching config is changed"; + // FlowletSwitchingConfig has both ARS_PROFILE and ARS info + arsProfileManager.changeArsProfile(oldFlowletConfig, newFlowletConfig); + arsManager.changeArs(oldFlowletConfig, newFlowletConfig); + } + } + + if (newFlowletConfig && !oldFlowletConfig) { + XLOG(DBG2) << "Flowlet switching config is added"; + // create the ARS profile object and attach to switch + arsProfileManager.addArsProfile(newFlowletConfig); + auto arsProfileHandlePtr = arsProfileManager.getArsProfileHandle(); + CHECK(arsProfileHandlePtr); + switchManager.setArsProfile(arsProfileHandlePtr->arsProfile->adapterKey()); + + // create the ARS object and attach to all ECMP groups + arsManager.addArs(newFlowletConfig); + auto arsHandlePtr = arsManager.getArsHandle(); + CHECK(arsHandlePtr); + nextHopGroupManager.updateArsModeAll(newFlowletConfig); + } else if (oldFlowletConfig && !newFlowletConfig) { + XLOG(DBG2) << "Flowlet switching config is removed"; + nextHopGroupManager.updateArsModeAll(newFlowletConfig); + arsManager.removeArs(newFlowletConfig); + switchManager.resetArsProfile(); + arsProfileManager.removeArsProfile(oldFlowletConfig); + } +#endif +} + +template +void SaiSwitch::processFlowletSwitchingConfigDelta( + const StateDelta& delta, + const LockPolicyT& lockPolicy) { + processFlowletSwitchingConfigDeltaLocked(delta, lockPolicy.lock()); +} + void SaiSwitch::pfcDeadlockNotificationCallback( PortSaiId portSaiId, uint8_t queueId, diff --git a/fboss/agent/hw/sai/switch/SaiSwitch.h b/fboss/agent/hw/sai/switch/SaiSwitch.h index 347c50c38eed9..c38a66ce04c63 100644 --- a/fboss/agent/hw/sai/switch/SaiSwitch.h +++ b/fboss/agent/hw/sai/switch/SaiSwitch.h @@ -552,6 +552,14 @@ class SaiSwitch : public HwSwitch { void initialStateApplied() override; + template + void processFlowletSwitchingConfigDelta( + const StateDelta& delta, + const LockPolicyT& lockPolicy); + void processFlowletSwitchingConfigDeltaLocked( + const StateDelta& delta, + const std::lock_guard& lock); + template void processPfcWatchdogGlobalDelta( const StateDelta& delta, diff --git a/fboss/agent/hw/sai/switch/SaiSwitchManager.cpp b/fboss/agent/hw/sai/switch/SaiSwitchManager.cpp index 3a9a05a87ed51..7080f2a841f44 100644 --- a/fboss/agent/hw/sai/switch/SaiSwitchManager.cpp +++ b/fboss/agent/hw/sai/switch/SaiSwitchManager.cpp @@ -677,8 +677,7 @@ void SaiSwitchManager::setArsProfile( void SaiSwitchManager::resetArsProfile() { #if SAI_API_VERSION >= SAI_VERSION(1, 14, 0) - if (FLAGS_flowletSwitchingEnable && - platform_->getAsic()->isSupported(HwAsic::Feature::FLOWLET)) { + if (FLAGS_flowletSwitchingEnable) { switch_->setOptionalAttribute( SaiSwitchTraits::Attributes::ArsProfile{SAI_NULL_OBJECT_ID}); }