aboutsummaryrefslogtreecommitdiffstats
path: root/os_net_config/impl_ifcfg.py
diff options
context:
space:
mode:
Diffstat (limited to 'os_net_config/impl_ifcfg.py')
-rw-r--r--os_net_config/impl_ifcfg.py230
1 files changed, 204 insertions, 26 deletions
diff --git a/os_net_config/impl_ifcfg.py b/os_net_config/impl_ifcfg.py
index 2e99f98..6459bcc 100644
--- a/os_net_config/impl_ifcfg.py
+++ b/os_net_config/impl_ifcfg.py
@@ -30,15 +30,23 @@ def ifcfg_config_path(name):
return "/etc/sysconfig/network-scripts/ifcfg-%s" % name
-#NOTE(dprince): added here for testability
+# NOTE(dprince): added here for testability
def bridge_config_path(name):
return ifcfg_config_path(name)
+def ivs_config_path():
+ return "/etc/sysconfig/ivs"
+
+
def route_config_path(name):
return "/etc/sysconfig/network-scripts/route-%s" % name
+def route6_config_path(name):
+ return "/etc/sysconfig/network-scripts/route6-%s" % name
+
+
def cleanup_pattern():
return "/etc/sysconfig/network-scripts/ifcfg-*"
@@ -49,12 +57,14 @@ class IfcfgNetConfig(os_net_config.NetConfig):
def __init__(self, noop=False, root_dir=''):
super(IfcfgNetConfig, self).__init__(noop, root_dir)
self.interface_data = {}
+ self.ivsinterface_data = {}
+ self.vlan_data = {}
self.route_data = {}
+ self.route6_data = {}
self.bridge_data = {}
self.linuxbridge_data = {}
self.linuxbond_data = {}
self.member_names = {}
- self.bond_slaves = {}
self.renamed_interfaces = {}
self.bond_primary_ifaces = {}
logger.info('Ifcfg net config provider created.')
@@ -78,14 +88,27 @@ class IfcfgNetConfig(os_net_config.NetConfig):
data += "ONBOOT=yes\n"
data += "HOTPLUG=no\n"
data += "NM_CONTROLLED=no\n"
+ if not base_opt.dns_servers and not base_opt.use_dhcp:
+ data += "PEERDNS=no\n"
if isinstance(base_opt, objects.Vlan):
if not base_opt.ovs_port:
# vlans on OVS bridges are internal ports (no device, etc)
data += "VLAN=yes\n"
if base_opt.device:
data += "PHYSDEV=%s\n" % base_opt.device
+ else:
+ if base_opt.linux_bond_name:
+ data += "PHYSDEV=%s\n" % base_opt.linux_bond_name
+ elif isinstance(base_opt, objects.IvsInterface):
+ data += "TYPE=IVSIntPort\n"
elif re.match('\w+\.\d+$', base_opt.name):
data += "VLAN=yes\n"
+ if base_opt.linux_bond_name:
+ data += "MASTER=%s\n" % base_opt.linux_bond_name
+ data += "SLAVE=yes\n"
+ if base_opt.ivs_bridge_name:
+ data += "DEVICETYPE=ivs\n"
+ data += "IVS_BRIDGE=%s\n" % base_opt.ivs_bridge_name
if base_opt.ovs_port:
data += "DEVICETYPE=ovs\n"
if base_opt.bridge_name:
@@ -152,14 +175,9 @@ class IfcfgNetConfig(os_net_config.NetConfig):
if base_opt.members:
members = [member.name for member in base_opt.members]
self.member_names[base_opt.name] = members
- for member in members:
- self.bond_slaves[member] = base_opt.name
if base_opt.bonding_options:
data += "BONDING_OPTS=\"%s\"\n" % base_opt.bonding_options
else:
- if base_opt.name in self.bond_slaves:
- data += "MASTER=%s\n" % self.bond_slaves[base_opt.name]
- data += "SLAVE=yes\n"
if base_opt.use_dhcp:
data += "BOOTPROTO=dhcp\n"
elif not base_opt.addresses:
@@ -211,16 +229,31 @@ class IfcfgNetConfig(os_net_config.NetConfig):
logger.info('adding custom route for interface: %s' % interface_name)
data = ""
first_line = ""
+ data6 = ""
+ first_line6 = ""
for route in routes:
- if route.default:
- first_line = "default via %s dev %s\n" % (route.next_hop,
- interface_name)
+ if ":" not in route.next_hop:
+ # Route is an IPv4 route
+ if route.default:
+ first_line = "default via %s dev %s\n" % (route.next_hop,
+ interface_name)
+ else:
+ data += "%s via %s dev %s\n" % (route.ip_netmask,
+ route.next_hop,
+ interface_name)
else:
- data += "%s via %s dev %s\n" % (route.ip_netmask,
- route.next_hop,
- interface_name)
+ # Route is an IPv6 route
+ if route.default:
+ first_line6 = "default via %s dev %s\n" % (route.next_hop,
+ interface_name)
+ else:
+ data6 += "%s via %s dev %s\n" % (route.ip_netmask,
+ route.next_hop,
+ interface_name)
self.route_data[interface_name] = first_line + data
+ self.route6_data[interface_name] = first_line6 + data6
logger.debug('route data: %s' % self.route_data[interface_name])
+ logger.debug('ipv6 route data: %s' % self.route6_data[interface_name])
def add_interface(self, interface):
"""Add an Interface object to the net config object.
@@ -247,10 +280,22 @@ class IfcfgNetConfig(os_net_config.NetConfig):
logger.info('adding vlan: %s' % vlan.name)
data = self._add_common(vlan)
logger.debug('vlan data: %s' % data)
- self.interface_data[vlan.name] = data
+ self.vlan_data[vlan.name] = data
if vlan.routes:
self._add_routes(vlan.name, vlan.routes)
+ def add_ivs_interface(self, ivs_interface):
+ """Add a ivs_interface object to the net config object.
+
+ :param ivs_interface: The ivs_interface object to add.
+ """
+ logger.info('adding ivs_interface: %s' % ivs_interface.name)
+ data = self._add_common(ivs_interface)
+ logger.debug('ivs_interface data: %s' % data)
+ self.ivsinterface_data[ivs_interface.name] = data
+ if ivs_interface.routes:
+ self._add_routes(ivs_interface.name, ivs_interface.routes)
+
def add_bridge(self, bridge):
"""Add an OvsBridge object to the net config object.
@@ -275,6 +320,18 @@ class IfcfgNetConfig(os_net_config.NetConfig):
if bridge.routes:
self._add_routes(bridge.name, bridge.routes)
+ def add_ivs_bridge(self, bridge):
+ """Add a IvsBridge object to the net config object.
+
+ IVS can only support one virtual switch per node,
+ using "ivs" as its name. As long as the ivs service
+ is running, the ivs virtual switch will be there.
+ It is impossible to add multiple ivs virtual switches
+ per node.
+ :param bridge: The IvsBridge object to add.
+ """
+ pass
+
def add_bond(self, bond):
"""Add an OvsBond object to the net config object.
@@ -295,11 +352,30 @@ class IfcfgNetConfig(os_net_config.NetConfig):
logger.info('adding linux bond: %s' % bond.name)
data = self._add_common(bond)
logger.debug('bond data: %s' % data)
- self.interface_data[bond.name] = data
self.linuxbond_data[bond.name] = data
if bond.routes:
self._add_routes(bond.name, bond.routes)
+ def generate_ivs_config(self, ivs_uplinks, ivs_interfaces):
+ """Generate configuration content for ivs."""
+
+ intfs = []
+ for intf in ivs_uplinks:
+ intfs.append(' -u ')
+ intfs.append(intf)
+ uplink_str = ''.join(intfs)
+
+ intfs = []
+ for intf in ivs_interfaces:
+ intfs.append(' --internal-port=')
+ intfs.append(intf)
+ intf_str = ''.join(intfs)
+
+ data = ("DAEMON_ARGS=\"--hitless --certificate /etc/ivs "
+ "--inband-vlan 4092%s%s\""
+ % (uplink_str, intf_str))
+ return data
+
def apply(self, cleanup=False, activate=True):
"""Apply the network configuration.
@@ -317,65 +393,137 @@ class IfcfgNetConfig(os_net_config.NetConfig):
"""
logger.info('applying network configs...')
restart_interfaces = []
+ restart_vlans = []
restart_bridges = []
+ restart_linux_bonds = []
update_files = {}
all_file_names = []
+ ivs_uplinks = [] # ivs physical uplinks
+ ivs_interfaces = [] # ivs internal ports
for interface_name, iface_data in self.interface_data.iteritems():
route_data = self.route_data.get(interface_name, '')
+ route6_data = self.route6_data.get(interface_name, '')
interface_path = self.root_dir + ifcfg_config_path(interface_name)
route_path = self.root_dir + route_config_path(interface_name)
+ route6_path = self.root_dir + route6_config_path(interface_name)
all_file_names.append(interface_path)
all_file_names.append(route_path)
+ all_file_names.append(route6_path)
+ if "IVS_BRIDGE" in iface_data:
+ ivs_uplinks.append(interface_name)
+ all_file_names.append(route6_path)
if (utils.diff(interface_path, iface_data) or
- utils.diff(route_path, route_data)):
+ utils.diff(route_path, route_data) or
+ utils.diff(route6_path, route6_data)):
restart_interfaces.append(interface_name)
restart_interfaces.extend(self.child_members(interface_name))
update_files[interface_path] = iface_data
update_files[route_path] = route_data
+ update_files[route6_path] = route6_data
+ else:
logger.info('No changes required for interface: %s' %
interface_name)
+ for interface_name, iface_data in self.ivsinterface_data.iteritems():
+ route_data = self.route_data.get(interface_name, '')
+ route6_data = self.route6_data.get(interface_name, '')
+ interface_path = self.root_dir + ifcfg_config_path(interface_name)
+ route_path = self.root_dir + route_config_path(interface_name)
+ route6_path = self.root_dir + route6_config_path(interface_name)
+ all_file_names.append(interface_path)
+ all_file_names.append(route_path)
+ all_file_names.append(route6_path)
+ ivs_interfaces.append(interface_name)
+ if (utils.diff(interface_path, iface_data) or
+ utils.diff(route_path, route_data)):
+ restart_interfaces.append(interface_name)
+ restart_interfaces.extend(self.child_members(interface_name))
+ update_files[interface_path] = iface_data
+ update_files[route_path] = route_data
+ update_files[route6_path] = route6_data
+ else:
+ logger.info('No changes required for ivs interface: %s' %
+ interface_name)
+
+ for vlan_name, vlan_data in self.vlan_data.iteritems():
+ route_data = self.route_data.get(vlan_name, '')
+ route6_data = self.route6_data.get(vlan_name, '')
+ vlan_path = self.root_dir + ifcfg_config_path(vlan_name)
+ vlan_route_path = self.root_dir + route_config_path(vlan_name)
+ vlan_route6_path = self.root_dir + route6_config_path(vlan_name)
+ all_file_names.append(vlan_path)
+ all_file_names.append(vlan_route_path)
+ all_file_names.append(vlan_route6_path)
+ if (utils.diff(vlan_path, vlan_data) or
+ utils.diff(vlan_route_path, route_data)):
+ restart_vlans.append(vlan_name)
+ restart_vlans.extend(self.child_members(vlan_name))
+ update_files[vlan_path] = vlan_data
+ update_files[vlan_route_path] = route_data
+ update_files[vlan_route6_path] = route6_data
+ else:
+ logger.info('No changes required for vlan interface: %s' %
+ vlan_name)
+
for bridge_name, bridge_data in self.bridge_data.iteritems():
route_data = self.route_data.get(bridge_name, '')
+ route6_data = self.route6_data.get(bridge_name, '')
bridge_path = self.root_dir + bridge_config_path(bridge_name)
- bridge_route_path = self.root_dir + route_config_path(bridge_name)
+ br_route_path = self.root_dir + route_config_path(bridge_name)
+ br_route6_path = self.root_dir + route6_config_path(bridge_name)
all_file_names.append(bridge_path)
- all_file_names.append(bridge_route_path)
+ all_file_names.append(br_route_path)
+ all_file_names.append(br_route6_path)
if (utils.diff(bridge_path, bridge_data) or
- utils.diff(bridge_route_path, route_data)):
+ utils.diff(br_route_path, route_data) or
+ utils.diff(br_route6_path, route6_data)):
restart_bridges.append(bridge_name)
restart_interfaces.extend(self.child_members(bridge_name))
update_files[bridge_path] = bridge_data
- update_files[bridge_route_path] = route_data
+ update_files[br_route_path] = route_data
+ update_files[br_route6_path] = route6_data
+ else:
logger.info('No changes required for bridge: %s' % bridge_name)
for bridge_name, bridge_data in self.linuxbridge_data.iteritems():
route_data = self.route_data.get(bridge_name, '')
+ route6_data = self.route6_data.get(bridge_name, '')
bridge_path = self.root_dir + bridge_config_path(bridge_name)
- bridge_route_path = self.root_dir + route_config_path(bridge_name)
+ br_route_path = self.root_dir + route_config_path(bridge_name)
+ br_route6_path = self.root_dir + route6_config_path(bridge_name)
all_file_names.append(bridge_path)
- all_file_names.append(bridge_route_path)
+ all_file_names.append(br_route_path)
+ all_file_names.append(br_route6_path)
if (utils.diff(bridge_path, bridge_data) or
- utils.diff(bridge_route_path, route_data)):
+ utils.diff(br_route_path, route_data) or
+ utils.diff(br_route6_path, route6_data)):
restart_bridges.append(bridge_name)
restart_interfaces.extend(self.child_members(bridge_name))
update_files[bridge_path] = bridge_data
- update_files[bridge_route_path] = route_data
+ update_files[br_route_path] = route_data
+ update_files[br_route6_path] = route6_data
+ else:
logger.info('No changes required for bridge: %s' % bridge_name)
for bond_name, bond_data in self.linuxbond_data.iteritems():
route_data = self.route_data.get(bond_name, '')
+ route6_data = self.route6_data.get(bond_name, '')
bond_path = self.root_dir + bridge_config_path(bond_name)
bond_route_path = self.root_dir + route_config_path(bond_name)
+ bond_route6_path = self.root_dir + route6_config_path(bond_name)
all_file_names.append(bond_path)
all_file_names.append(bond_route_path)
+ all_file_names.append(bond_route6_path)
if (utils.diff(bond_path, bond_data) or
- utils.diff(bond_route_path, route_data)):
- restart_interfaces.append(bond_name)
+ utils.diff(bond_route_path, route_data) or
+ utils.diff(bond_route6_path, route6_data)):
+ restart_linux_bonds.append(bond_name)
restart_interfaces.extend(self.child_members(bond_name))
update_files[bond_path] = bond_data
update_files[bond_route_path] = route_data
+ update_files[bond_route6_path] = route6_data
+ else:
logger.info('No changes required for linux bond: %s' %
bond_name)
@@ -390,9 +538,15 @@ class IfcfgNetConfig(os_net_config.NetConfig):
self.remove_config(ifcfg_file)
if activate:
+ for vlan in restart_vlans:
+ self.ifdown(vlan)
+
for interface in restart_interfaces:
self.ifdown(interface)
+ for linux_bond in restart_linux_bonds:
+ self.ifdown(linux_bond)
+
for bridge in restart_bridges:
self.ifdown(bridge, iftype='bridge')
@@ -402,7 +556,15 @@ class IfcfgNetConfig(os_net_config.NetConfig):
for location, data in update_files.iteritems():
self.write_config(location, data)
+ if ivs_uplinks or ivs_interfaces:
+ location = ivs_config_path()
+ data = self.generate_ivs_config(ivs_uplinks, ivs_interfaces)
+ self.write_config(location, data)
+
if activate:
+ for linux_bond in restart_linux_bonds:
+ self.ifup(linux_bond)
+
for bridge in restart_bridges:
self.ifup(bridge, iftype='bridge')
@@ -413,4 +575,20 @@ class IfcfgNetConfig(os_net_config.NetConfig):
self.ovs_appctl('bond/set-active-slave', bond,
self.bond_primary_ifaces[bond])
+ if ivs_uplinks or ivs_interfaces:
+ logger.info("Attach to ivs with "
+ "uplinks: %s, "
+ "interfaces: %s" %
+ (ivs_uplinks, ivs_interfaces))
+ for ivs_uplink in ivs_uplinks:
+ self.ifup(ivs_uplink)
+ for ivs_interface in ivs_interfaces:
+ self.ifup(ivs_interface)
+ msg = "Restart ivs"
+ self.execute(msg, '/usr/bin/systemctl',
+ 'restart', 'ivs')
+
+ for vlan in restart_vlans:
+ self.ifup(vlan)
+
return update_files