Skip to content

Commit

Permalink
Parse DHCP Table (sonic-net#8988)
Browse files Browse the repository at this point in the history
  • Loading branch information
kellyyeh committed Sep 6, 2022
1 parent 482f0d3 commit 35b5578
Show file tree
Hide file tree
Showing 4 changed files with 71 additions and 3 deletions.
30 changes: 27 additions & 3 deletions src/sonic-config-engine/minigraph.py
Original file line number Diff line number Diff line change
Expand Up @@ -396,6 +396,29 @@ def parse_dpg(dpg, hname):
vlan_attributes['alias'] = vintfname
vlans[sonic_vlan_name] = vlan_attributes

dhcp = child.find(str(QName(ns, "Dhcp")))
dhcp_table = {}

if dhcp is not None:
for vintf in dhcp.findall(str(QName(ns, "VlanInterface"))):
vintfname = vintf.find(str(QName(ns, "Name"))).text

dhcp_attributes = {}

dhcp_node = vintf.find(str(QName(ns, "Dhcpv6Relays")))
if dhcp_node is not None and dhcp_node.text is not None:
dhcpservers = dhcp_node.text
vdhcpserver_list = dhcpservers.split(';')
dhcp_attributes['dhcpv6_servers'] = vdhcpserver_list

option_linklayer_addr = vintf.find(str(QName(ns, "Dhcpv6OptionRfc6939")))
if option_linklayer_addr is not None and option_linklayer_addr.text == "true":
dhcp_attributes['dhcpv6_option|rfc6939_support'] = "true"
elif option_linklayer_addr is not None and option_linklayer_addr.text == "false":
dhcp_attributes['dhcpv6_option|rfc6939_support'] = "false"

dhcp_table[vintfname] = dhcp_attributes

acls = {}
for aclintf in aclintfs.findall(str(QName(ns, "AclInterface"))):
if aclintf.find(str(QName(ns, "InAcl"))) is not None:
Expand Down Expand Up @@ -496,7 +519,7 @@ def parse_dpg(dpg, hname):
except:
print >> sys.stderr, "Warning: Ignoring Control Plane ACL %s without type" % aclname

return intfs, lo_intfs, mvrf, mgmt_intf, vlans, vlan_members, pcs, pc_members, acls, vni
return intfs, lo_intfs, mvrf, mgmt_intf, vlans, vlan_members, dhcp_table, pcs, pc_members, acls, vni
return None, None, None, None, None, None, None, None, None, None

def parse_host_loopback(dpg, hname):
Expand Down Expand Up @@ -985,7 +1008,7 @@ def parse_xml(filename, platform=None, port_config_file=None, asic_name=None):
for child in root:
if asic_name is None:
if child.tag == str(QName(ns, "DpgDec")):
(intfs, lo_intfs, mvrf, mgmt_intf, vlans, vlan_members, pcs, pc_members, acls, vni) = parse_dpg(child, hostname)
(intfs, lo_intfs, mvrf, mgmt_intf, vlans, vlan_members, dhcp_table, pcs, pc_members, acls, vni) = parse_dpg(child, hostname)
elif child.tag == str(QName(ns, "CpgDec")):
(bgp_sessions, bgp_internal_sessions, bgp_asn, bgp_peers_with_range, bgp_monitors) = parse_cpg(child, hostname)
elif child.tag == str(QName(ns, "PngDec")):
Expand All @@ -1000,7 +1023,7 @@ def parse_xml(filename, platform=None, port_config_file=None, asic_name=None):
(port_speeds_default, port_descriptions) = parse_deviceinfo(child, hwsku)
else:
if child.tag == str(QName(ns, "DpgDec")):
(intfs, lo_intfs, mvrf, mgmt_intf, vlans, vlan_members, pcs, pc_members, acls, vni) = parse_dpg(child, asic_name)
(intfs, lo_intfs, mvrf, mgmt_intf, vlans, vlan_members, dhcp_table, pcs, pc_members, acls, vni) = parse_dpg(child, asic_name)
host_lo_intfs = parse_host_loopback(child, hostname)
elif child.tag == str(QName(ns, "CpgDec")):
(bgp_sessions, bgp_internal_sessions, bgp_asn, bgp_peers_with_range, bgp_monitors) = parse_cpg(child, asic_name, local_devices)
Expand Down Expand Up @@ -1254,6 +1277,7 @@ def parse_xml(filename, platform=None, port_config_file=None, asic_name=None):
results['SYSLOG_SERVER'] = dict((item, {}) for item in syslog_servers)
results['DHCP_SERVER'] = dict((item, {}) for item in dhcp_servers)
results['DHCPv6_SERVER'] = dict((item, {}) for item in dhcpv6_servers)
results['DHCP'] = dhcp_table
results['NTP_SERVER'] = dict((item, {}) for item in ntp_servers)
results['TACPLUS_SERVER'] = dict((item, {'priority': '1', 'tcp_port': '49'}) for item in tacacs_servers)
results['ACL_TABLE'] = filter_acl_table_bindings(acls, neighbors, pcs, sub_role)
Expand Down
12 changes: 12 additions & 0 deletions src/sonic-config-engine/tests/simple-sample-graph-case.xml
Original file line number Diff line number Diff line change
Expand Up @@ -136,6 +136,18 @@
<Subnets>192.168.0.0/27</Subnets>
</VlanInterface>
</VlanInterfaces>
<Dhcp>
<VlanInterface>
<Name>Vlan1000</Name>
<Dhcpv6Relays>fc02:2000::1;fc02:2000::2</Dhcpv6Relays>
<Dhcpv6OptionRfc6939>true</Dhcpv6OptionRfc6939>
</VlanInterface>
<VlanInterface>
<Name>Vlan2000</Name>
<Dhcpv6Relays>fc02:2000::3;fc02:2000::4</Dhcpv6Relays>
<Dhcpv6OptionRfc6939>false</Dhcpv6OptionRfc6939>
</VlanInterface>
</Dhcp>
<IPInterfaces>
<IPInterface>
<Name i:nil="true"/>
Expand Down
8 changes: 8 additions & 0 deletions src/sonic-config-engine/tests/test_cfggen.py
Original file line number Diff line number Diff line change
Expand Up @@ -617,3 +617,11 @@ def test_show_run_interfaces(self):
argument = '-a \'{"key1":"value"}\' --var-json INTERFACE'
output = self.run_script(argument)
self.assertEqual(output, '')

def test_minigraph_dhcp(self):
argument = '-m "' + self.sample_graph_simple_case + '" -p "' + self.port_config + '" -v DHCP'
output = self.run_script(argument)
self.assertEqual(
output.strip(),
"{'Vlan1000': {'dhcpv6_option|rfc6939_support': 'true', 'dhcpv6_servers': ['fc02:2000::1', 'fc02:2000::2']}, 'Vlan2000': {'dhcpv6_option|rfc6939_support': 'false', 'dhcpv6_servers': ['fc02:2000::3', 'fc02:2000::4']}}"
)
24 changes: 24 additions & 0 deletions src/sonic-config-engine/tests/test_minigraph_case.py
Original file line number Diff line number Diff line change
Expand Up @@ -190,3 +190,27 @@ def test_parse_device_desc_xml_mgmt_interface(self):
self.assertEqual(len(mgmt_intf.keys()), 1)
self.assertTrue(('eth0', 'FC00:1::32/64') in mgmt_intf.keys())
self.assertTrue(ipaddress.IPAddress('fc00:1::1') == mgmt_intf[('eth0', 'FC00:1::32/64')]['gwaddr'])

def test_dhcp_table(self):
argument = '-m "' + self.sample_graph + '" -p "' + self.port_config + '" -v "DHCP"'
expected = {
'Vlan1000': {
'dhcpv6_servers': [
"fc02:2000::1",
"fc02:2000::2"
],
'dhcpv6_option|rfc6939_support': 'true'
},
'Vlan2000': {
'dhcpv6_servers': [
"fc02:2000::3",
"fc02:2000::4"
],
'dhcpv6_option|rfc6939_support': 'false'
}
}
output = self.run_script(argument)
self.assertEqual(
output.strip(),
"{'Vlan1000': {'dhcpv6_option|rfc6939_support': 'true', 'dhcpv6_servers': ['fc02:2000::1', 'fc02:2000::2']}, 'Vlan2000': {'dhcpv6_option|rfc6939_support': 'false', 'dhcpv6_servers': ['fc02:2000::3', 'fc02:2000::4']}}"
)

0 comments on commit 35b5578

Please sign in to comment.