Skip to content

Commit

Permalink
[teammgrd]:Create unique LACP key for port-channel
Browse files Browse the repository at this point in the history
  • Loading branch information
DavidZagury committed Feb 18, 2021
1 parent f6c7422 commit fafca38
Show file tree
Hide file tree
Showing 2 changed files with 77 additions and 0 deletions.
75 changes: 75 additions & 0 deletions cfgmgr/teammgr.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -144,6 +144,7 @@ void TeamMgr::doLagTask(Consumer &consumer)
bool fallback = false;
string admin_status = DEFAULT_ADMIN_STATUS_STR;
string mtu = DEFAULT_MTU_STR;
string lacp_key;
string learn_mode;

for (auto i : kfvFieldsValues(t))
Expand Down Expand Up @@ -178,6 +179,12 @@ void TeamMgr::doLagTask(Consumer &consumer)
SWSS_LOG_INFO("Get learn_mode %s",
learn_mode.c_str());
}
else if (fvField(i) == "lacp_key")
{
lacp_key = fvValue(i);
SWSS_LOG_INFO("Get lacp_key %s",
lacp_key.c_str());
}
}

if (m_lagList.find(alias) == m_lagList.end())
Expand All @@ -193,6 +200,7 @@ void TeamMgr::doLagTask(Consumer &consumer)

setLagAdminStatus(alias, admin_status);
setLagMtu(alias, mtu);
setLacpKey(alias, lacp_key);
if (!learn_mode.empty())
{
setLagLearnMode(alias, learn_mode);
Expand Down Expand Up @@ -395,6 +403,21 @@ bool TeamMgr::setLagMtu(const string &alias, const string &mtu)
return true;
}

bool TeamMgr::setLacpKey(const string& alias, const string& lacp_key)
{
// Set the port-channel LACP key in config database
// Will *not* change LACP keys of ports that were already set if there are any.
SWSS_LOG_ENTER();
vector <FieldValueTuple> fvs;
FieldValueTuple fv("lacp_key", lacp_key);
fvs.push_back(fv);
m_cfgLagTable.set(alias, fvs);

SWSS_LOG_NOTICE("Set port channel %s LACP key to %s",
alias.c_str(), lacp_key.c_str());
return true;
}

bool TeamMgr::setLagLearnMode(const string &alias, const string &learn_mode)
{
// Set the port MAC learn mode in application database
Expand Down Expand Up @@ -504,6 +527,52 @@ bool TeamMgr::removeLag(const string &alias)
return true;
}

// Port-channel names are in the pattern of "PortChannel####"
//
// The LACP key could be generated in 3 ways based on the value in config DB:
// 1. "auto" - LACP key is extracted from the port-channel name and is set to be the number at the end of the port-channel name
// We are adding 1 at the beginning to avoid LACP key collisions between similar LACP keys e.g. PortChannel10 and PortChannel010.
// 2. n - LACP key will be n.
// 3. "" - LACP key will be 0 - exists for backward compatibility.
uint16_t TeamMgr::generateLacpKey(const string& lag)
{
vector <FieldValueTuple> fvs;
m_cfgLagTable.get(lag, fvs);

auto it = find_if(fvs.begin(), fvs.end(), [](const FieldValueTuple& fv)
{
return fv.first == "lacp_key";
});
string lacp_key;
if (it != fvs.end())
{
lacp_key = it->second;
if (!lacp_key.empty())
{
try
{
if (lacp_key == "auto")
{
return static_cast<uint16_t>(std::stoul("1" + lag.substr(lag.find_first_of("0123456789"))));
}
else
{
return static_cast<uint16_t>(std::stoul(lacp_key));
}
}
catch (const std::exception& e)
{
SWSS_LOG_THROW("Failed to parse LACP key %s for port channel %s", lacp_key.c_str(), lag.c_str());
}
}
else
{
return 0;
}
}
return 0;
}

// Once a port is enslaved into a port channel, the port's MTU will
// be inherited from the master's MTU while the port's admin status
// will still be controlled separately.
Expand All @@ -520,11 +589,17 @@ task_process_status TeamMgr::addLagMember(const string &lag, const string &membe

stringstream cmd;
string res;
uint16_t keyId = generateLacpKey(lag);

// Set admin down LAG member (required by teamd) and enslave it
// ip link set dev <member> down;
// teamdctl <port_channel_name> port config update <member> { lacp_key: <lacp_key>, link_watch: { name: ethtool } };
// teamdctl <port_channel_name> port add <member>;
cmd << IP_CMD << " link set dev " << shellquote(member) << " down; ";
cmd << TEAMDCTL_CMD << " " << shellquote(lag) << " port config update " << shellquote(member)
<< " '{\"lacp_key\":"
<< keyId
<< ",\"link_watch\": {\"name\": \"ethtool\"} }'; ";
cmd << TEAMDCTL_CMD << " " << shellquote(lag) << " port add " << shellquote(member);

if (exec(cmd.str(), res) != 0)
Expand Down
2 changes: 2 additions & 0 deletions cfgmgr/teammgr.h
Original file line number Diff line number Diff line change
Expand Up @@ -48,6 +48,7 @@ class TeamMgr : public Orch

bool setLagAdminStatus(const std::string &alias, const std::string &admin_status);
bool setLagMtu(const std::string &alias, const std::string &mtu);
bool setLacpKey(const std::string& alias, const std::string& lacp_key);
bool setLagLearnMode(const std::string &alias, const std::string &learn_mode);


Expand All @@ -56,6 +57,7 @@ class TeamMgr : public Orch
bool checkPortIffUp(const std::string &);
bool isPortStateOk(const std::string&);
bool isLagStateOk(const std::string&);
uint16_t generateLacpKey(const std::string&);
};

}

0 comments on commit fafca38

Please sign in to comment.