The slaves of an interface are determined during creation time and
stored in two objects:
* Interface on the controller
* NetConfigDeviceGeneric on the slave machine
When slaves are dynamically added / deleted during a Python task the
'slaves' data structures in these objects are not updated, which can
cause several problems:
If a slave is removed from its master, then during cleanup the slave
machine will try to remove it again and thereby generate an error. This
requires us to update the data struct on the slave machine.
If a slave is added to a master and that master is later reset(), then
the newly added slave won't be configured correctly after the reset().
This requires us to update the data struct on the controller.
Cc: Andrew Lunn <andrew(a)lunn.ch>
Fixes: af025186a329 ("InterfaceAPI: Introduce slave_{add, del}")
Signed-off-by: Ido Schimmel <idosch(a)mellanox.com>
---
lnst/Controller/Machine.py | 12 ++++++++++++
lnst/Slave/NetConfigDevice.py | 4 ++++
2 files changed, 16 insertions(+)
diff --git a/lnst/Controller/Machine.py b/lnst/Controller/Machine.py
index 884b315..9897580 100644
--- a/lnst/Controller/Machine.py
+++ b/lnst/Controller/Machine.py
@@ -591,6 +591,12 @@ class Interface(object):
else:
self._master["other"].append(master)
+ def del_master(self, master):
+ if self._master["primary"] is master:
+ self._master["primary"] = None
+ else:
+ self._master["other"].remove(master)
+
def get_primary_master(self):
return self._master["primary"]
@@ -601,6 +607,10 @@ class Interface(object):
else:
iface.add_master(self)
+ def del_slave(self, iface):
+ iface.del_master(self)
+ del self._slaves[iface.get_id()]
+
def set_slave_option(self, slave_id, name, value):
if slave_id not in self._slave_options:
self._slave_options[slave_id] = []
@@ -812,8 +822,10 @@ class Interface(object):
def slave_add(self, if_id):
self._machine._rpc_call_x(self._netns, "slave_add", self._id, if_id)
+ self.add_slave(self._machine.get_interface(if_id))
def slave_del(self, if_id):
+ self.del_slave(self._machine.get_interface(if_id))
self._machine._rpc_call_x(self._netns, "slave_del", self._id, if_id)
class StaticInterface(Interface):
diff --git a/lnst/Slave/NetConfigDevice.py b/lnst/Slave/NetConfigDevice.py
index 60be2ec..8adcf2b 100644
--- a/lnst/Slave/NetConfigDevice.py
+++ b/lnst/Slave/NetConfigDevice.py
@@ -212,8 +212,10 @@ class NetConfigDeviceBridge(NetConfigDeviceGeneric):
def slave_add(self, slave_id):
self._add_rm_port("add", slave_id)
+ self._dev_config["slaves"].append(slave_id)
def slave_del(self, slave_id):
+ self._dev_config["slaves"].remove(slave_id)
self._add_rm_port("del", slave_id)
class NetConfigDeviceMacvlan(NetConfigDeviceGeneric):
@@ -399,8 +401,10 @@ class NetConfigDeviceTeam(NetConfigDeviceGeneric):
exec_cmd("teamdctl %s %s port config update %s \"%s\"" %
(dbus_option, dev_name, port_name, teamd_port_config))
port_dev.down()
exec_cmd("teamdctl %s %s port add %s" % (dbus_option, dev_name,
port_name))
+ self._dev_config["slaves"].append(slave_id)
def slave_del(self, slave_id):
+ self._dev_config["slaves"].remove(slave_id)
dev_name = self._dev_config["name"]
port_dev = self._if_manager.get_mapped_device(slave_id)
port_name = port_dev.get_name()
--
2.4.10
Show replies by date