Add IPv6 Support for Rhel.

This patch does the following:

1. Adds support to process network config with IPv6
2. Adds support to display 'ifconfig -a' information for IPv6
3. Adds support to display routing information for IPv6
This commit is contained in:
Shraddha Pandhe 2014-11-21 18:32:30 +00:00
parent bc8b165643
commit 88f8b150ec
3 changed files with 102 additions and 29 deletions

View File

@ -113,6 +113,10 @@ def translate_network(settings):
for info in ifaces: for info in ifaces:
if 'iface' not in info: if 'iface' not in info:
continue continue
use_ipv6 = False
# Check if current device has an ipv6 IP
if 'inet6' in info['iface']:
use_ipv6 = True
iface_details = info['iface'].split(None) iface_details = info['iface'].split(None)
dev_name = None dev_name = None
if len(iface_details) >= 1: if len(iface_details) >= 1:
@ -122,6 +126,7 @@ def translate_network(settings):
if not dev_name: if not dev_name:
continue continue
iface_info = {} iface_info = {}
iface_info['ipv6'] = {}
if len(iface_details) >= 3: if len(iface_details) >= 3:
proto_type = iface_details[2].strip().lower() proto_type = iface_details[2].strip().lower()
# Seems like this can be 'loopback' which we don't # Seems like this can be 'loopback' which we don't
@ -129,26 +134,39 @@ def translate_network(settings):
if proto_type in ['dhcp', 'static']: if proto_type in ['dhcp', 'static']:
iface_info['bootproto'] = proto_type iface_info['bootproto'] = proto_type
# These can just be copied over # These can just be copied over
for k in ['netmask', 'address', 'gateway', 'broadcast']: if use_ipv6:
if k in info: for k in ['address', 'gateway']:
val = info[k].strip().lower() if k in info:
if val: val = info[k].strip().lower()
iface_info[k] = val if val:
# Name server info provided?? iface_info['ipv6'][k] = val
if 'dns-nameservers' in info: else:
iface_info['dns-nameservers'] = info['dns-nameservers'].split() for k in ['netmask', 'address', 'gateway', 'broadcast']:
# Name server search info provided?? if k in info:
if 'dns-search' in info: val = info[k].strip().lower()
iface_info['dns-search'] = info['dns-search'].split() if val:
# Is any mac address spoofing going on?? iface_info[k] = val
if 'hwaddress' in info: # Name server info provided??
hw_info = info['hwaddress'].lower().strip() if 'dns-nameservers' in info:
hw_split = hw_info.split(None, 1) iface_info['dns-nameservers'] = info['dns-nameservers'].split()
if len(hw_split) == 2 and hw_split[0].startswith('ether'): # Name server search info provided??
hw_addr = hw_split[1] if 'dns-search' in info:
if hw_addr: iface_info['dns-search'] = info['dns-search'].split()
iface_info['hwaddress'] = hw_addr # Is any mac address spoofing going on??
real_ifaces[dev_name] = iface_info if 'hwaddress' in info:
hw_info = info['hwaddress'].lower().strip()
hw_split = hw_info.split(None, 1)
if len(hw_split) == 2 and hw_split[0].startswith('ether'):
hw_addr = hw_split[1]
if hw_addr:
iface_info['hwaddress'] = hw_addr
# If ipv6 is enabled, device will have multiple IPs.
# Update the dictionary instead of overwriting it
if dev_name in real_ifaces:
real_ifaces[dev_name].update(iface_info)
else:
real_ifaces[dev_name] = iface_info
# Check for those that should be started on boot via 'auto' # Check for those that should be started on boot via 'auto'
for (cmd, args) in entries: for (cmd, args) in entries:
if cmd == 'auto': if cmd == 'auto':
@ -160,4 +178,6 @@ def translate_network(settings):
dev_name = args[0].strip().lower() dev_name = args[0].strip().lower()
if dev_name in real_ifaces: if dev_name in real_ifaces:
real_ifaces[dev_name]['auto'] = True real_ifaces[dev_name]['auto'] = True
if cmd == 'iface' and 'inet6' in args:
real_ifaces[dev_name]['inet6'] = True
return real_ifaces return real_ifaces

View File

@ -71,6 +71,7 @@ class Distro(distros.Distro):
nameservers = [] nameservers = []
searchservers = [] searchservers = []
dev_names = entries.keys() dev_names = entries.keys()
use_ipv6 = False
for (dev, info) in entries.iteritems(): for (dev, info) in entries.iteritems():
net_fn = self.network_script_tpl % (dev) net_fn = self.network_script_tpl % (dev)
net_cfg = { net_cfg = {
@ -83,6 +84,13 @@ class Distro(distros.Distro):
'MACADDR': info.get('hwaddress'), 'MACADDR': info.get('hwaddress'),
'ONBOOT': _make_sysconfig_bool(info.get('auto')), 'ONBOOT': _make_sysconfig_bool(info.get('auto')),
} }
if info.get('inet6'):
use_ipv6 = True
net_cfg.update({
'IPV6INIT': _make_sysconfig_bool(True),
'IPV6ADDR': info.get('ipv6').get('address'),
'IPV6_DEFAULTGW': info.get('ipv6').get('gateway'),
})
rhel_util.update_sysconfig_file(net_fn, net_cfg) rhel_util.update_sysconfig_file(net_fn, net_cfg)
if 'dns-nameservers' in info: if 'dns-nameservers' in info:
nameservers.extend(info['dns-nameservers']) nameservers.extend(info['dns-nameservers'])
@ -95,6 +103,9 @@ class Distro(distros.Distro):
net_cfg = { net_cfg = {
'NETWORKING': _make_sysconfig_bool(True), 'NETWORKING': _make_sysconfig_bool(True),
} }
# If IPv6 interface present, enable ipv6 networking
if use_ipv6:
net_cfg['NETWORKING_IPV6'] = _make_sysconfig_bool(True)
rhel_util.update_sysconfig_file(self.network_conf_fn, net_cfg) rhel_util.update_sysconfig_file(self.network_conf_fn, net_cfg)
return dev_names return dev_names

View File

@ -72,6 +72,7 @@ def netdev_info(empty=""):
"bcast:": "bcast", "broadcast": "bcast", "bcast:": "bcast", "broadcast": "bcast",
"mask:": "mask", "netmask": "mask", "mask:": "mask", "netmask": "mask",
"hwaddr": "hwaddr", "ether": "hwaddr", "hwaddr": "hwaddr", "ether": "hwaddr",
"scope": "scope",
} }
for origfield, field in ifconfigfields.items(): for origfield, field in ifconfigfields.items():
target = "%s%s" % (field, fieldpost) target = "%s%s" % (field, fieldpost)
@ -96,7 +97,12 @@ def netdev_info(empty=""):
def route_info(): def route_info():
(route_out, _err) = util.subp(["netstat", "-rn"]) (route_out, _err) = util.subp(["netstat", "-rn"])
routes = [] (route_out6, _err6) = util.subp(["netstat", "-A inet6", "-n"])
routes = {}
routes['ipv4'] = []
routes['ipv6'] = []
entries = route_out.splitlines()[1:] entries = route_out.splitlines()[1:]
for line in entries: for line in entries:
if not line: if not line:
@ -132,7 +138,26 @@ def route_info():
'iface': toks[7], 'iface': toks[7],
} }
routes.append(entry) routes['ipv4'].append(entry)
entries6 = route_out6.splitlines()[1:]
for line in entries6:
if not line:
continue
toks = line.split()
if (len(toks) < 6 or toks[0] == "Kernel" or
toks[0] == "Proto" or toks[0] == "Active"):
continue
entry = {
'proto': toks[0],
'recv-q': toks[1],
'send-q': toks[2],
'local address': toks[3],
'foreign address': toks[4],
'state': toks[5],
}
routes['ipv6'].append(entry)
return routes return routes
@ -156,10 +181,12 @@ def netdev_pformat():
lines.append(util.center("Net device info failed", '!', 80)) lines.append(util.center("Net device info failed", '!', 80))
netdev = None netdev = None
if netdev is not None: if netdev is not None:
fields = ['Device', 'Up', 'Address', 'Mask', 'Hw-Address'] fields = ['Device', 'Up', 'Address', 'Mask', 'Scope', 'Hw-Address']
tbl = PrettyTable(fields) tbl = PrettyTable(fields)
for (dev, d) in netdev.iteritems(): for (dev, d) in netdev.iteritems():
tbl.add_row([dev, d["up"], d["addr"], d["mask"], d["hwaddr"]]) tbl.add_row([dev, d["up"], d["addr"], d["mask"], ".", d["hwaddr"]])
if d["addr6"]:
tbl.add_row([dev, d["up"], d["addr6"], ".", d["scope6"], d["hwaddr"]])
netdev_s = tbl.get_string() netdev_s = tbl.get_string()
max_len = len(max(netdev_s.splitlines(), key=len)) max_len = len(max(netdev_s.splitlines(), key=len))
header = util.center("Net device info", "+", max_len) header = util.center("Net device info", "+", max_len)
@ -176,15 +203,30 @@ def route_pformat():
util.logexc(LOG, "Route info failed: %s" % e) util.logexc(LOG, "Route info failed: %s" % e)
routes = None routes = None
if routes is not None: if routes is not None:
fields = ['Route', 'Destination', 'Gateway', fields_v4 = ['Route', 'Destination', 'Gateway',
'Genmask', 'Interface', 'Flags'] 'Genmask', 'Interface', 'Flags']
tbl = PrettyTable(fields)
for (n, r) in enumerate(routes): if routes.get('ipv6') is not None:
fields_v6 = ['Route', 'Proto', 'Recv-Q', 'Send-Q', 'Local Address',
'Foreign Address', 'State']
tbl_v4 = PrettyTable(fields_v4)
for (n, r) in enumerate(routes.get('ipv4')):
route_id = str(n) route_id = str(n)
tbl.add_row([route_id, r['destination'], tbl_v4.add_row([route_id, r['destination'],
r['gateway'], r['genmask'], r['gateway'], r['genmask'],
r['iface'], r['flags']]) r['iface'], r['flags']])
route_s = tbl.get_string() route_s = tbl_v4.get_string()
if fields_v6:
tbl_v6 = PrettyTable(fields_v6)
for (n, r) in enumerate(routes.get('ipv6')):
route_id = str(n)
tbl_v6.add_row([route_id, r['proto'],
r['recv-q'], r['send-q'],
r['local address'], r['foreign address'],
r['state']])
route_s = route_s + tbl_v6.get_string()
max_len = len(max(route_s.splitlines(), key=len)) max_len = len(max(route_s.splitlines(), key=len))
header = util.center("Route info", "+", max_len) header = util.center("Route info", "+", max_len)
lines.extend([header, route_s]) lines.extend([header, route_s])