diff --git a/src/sonic-config-engine/minigraph.py b/src/sonic-config-engine/minigraph.py
index cd8cff3eec1..57f3ea9269c 100644
--- a/src/sonic-config-engine/minigraph.py
+++ b/src/sonic-config-engine/minigraph.py
@@ -1569,6 +1569,7 @@ def parse_linkmeta(meta, hname):
upper_tor_hostname = ''
lower_tor_hostname = ''
auto_negotiation = None
+ link_training = None
macsec_enabled = False
tx_power = None
laser_freq = None
@@ -1586,6 +1587,8 @@ def parse_linkmeta(meta, hname):
lower_tor_hostname = value
elif name == "AutoNegotiation":
auto_negotiation = value
+ elif name == "LinkTraining":
+ link_training = value
elif name == "MacSecEnabled":
macsec_enabled = value
elif name == "TxPower":
@@ -1603,6 +1606,8 @@ def parse_linkmeta(meta, hname):
linkmetas[port]["PeerSwitch"] = upper_tor_hostname
if auto_negotiation:
linkmetas[port]["AutoNegotiation"] = auto_negotiation
+ if link_training:
+ linkmetas[port]["LinkTraining"] = link_training
if macsec_enabled:
linkmetas[port]["MacSecEnabled"] = macsec_enabled
if tx_power:
@@ -2437,6 +2442,11 @@ def parse_xml(filename, platform=None, port_config_file=None, asic_name=None, hw
if autoneg:
port['autoneg'] = 'on' if autoneg.lower() == 'true' else 'off'
+ # If LinkTraining is available in the minigraph, we override any value we may have received from port_config.ini
+ link_training = linkmetas.get(alias, {}).get('LinkTraining')
+ if link_training:
+ port['link_training'] = 'on' if link_training.lower() == 'true' else 'off'
+
# If macsec is enabled on interface, and profile is valid, add the profile to port
macsec_enabled = linkmetas.get(alias, {}).get('MacSecEnabled')
if macsec_enabled and 'PrimaryKey' in macsec_profile:
diff --git a/src/sonic-config-engine/tests/t0-sample-graph.xml b/src/sonic-config-engine/tests/t0-sample-graph.xml
index b343a8b5e39..32c91e00088 100644
--- a/src/sonic-config-engine/tests/t0-sample-graph.xml
+++ b/src/sonic-config-engine/tests/t0-sample-graph.xml
@@ -468,6 +468,13 @@
switch-t0
fortyGigE0/4
+
+ DeviceInterfaceLink
+ Servers1
+ eth0
+ switch-t0
+ fortyGigE0/16
+
DeviceInterfaceLink
Servers100
@@ -916,6 +923,22 @@
ARISTA06T1:Ethernet1/34;switch-t0:fortyGigE0/8
+
+
+
+
+ AutoNegotiation
+
+ False
+
+
+ LinkTraining
+
+ True
+
+
+ Servers1:eth0;switch-t0:fortyGigE0/16
+
diff --git a/src/sonic-config-engine/tests/test_cfggen.py b/src/sonic-config-engine/tests/test_cfggen.py
index 6991df40f09..3cdc77e9564 100644
--- a/src/sonic-config-engine/tests/test_cfggen.py
+++ b/src/sonic-config-engine/tests/test_cfggen.py
@@ -224,14 +224,14 @@ def test_minigraph_acl(self):
utils.to_dict(output.strip().replace("Warning: Ignoring Control Plane ACL NTP_ACL without type\n", '')),
utils.to_dict(
"{'NTP_ACL': {'services': ['NTP'], 'type': 'CTRLPLANE', 'policy_desc': 'NTP_ACL', 'stage': 'ingress'}, "
- "'EVERFLOW': {'stage': 'ingress', 'type': 'MIRROR', 'ports': ['PortChannel01', 'PortChannel02', 'PortChannel03', 'PortChannel04', 'Ethernet4', 'Ethernet100'], 'policy_desc': 'EVERFLOW'}, "
- "'EVERFLOW_EGRESS': {'stage': 'egress', 'type': 'MIRROR', 'ports': ['PortChannel01', 'PortChannel02', 'PortChannel03', 'PortChannel04', 'Ethernet4', 'Ethernet100'], 'policy_desc': 'EVERFLOW_EGRESS'}, "
+ "'EVERFLOW': {'stage': 'ingress', 'type': 'MIRROR', 'ports': ['PortChannel01', 'PortChannel02', 'PortChannel03', 'PortChannel04', 'Ethernet4', 'Ethernet16', 'Ethernet100'], 'policy_desc': 'EVERFLOW'}, "
+ "'EVERFLOW_EGRESS': {'stage': 'egress', 'type': 'MIRROR', 'ports': ['PortChannel01', 'PortChannel02', 'PortChannel03', 'PortChannel04', 'Ethernet4', 'Ethernet16', 'Ethernet100'], 'policy_desc': 'EVERFLOW_EGRESS'}, "
"'ROUTER_PROTECT': {'services': ['SSH', 'SNMP'], 'type': 'CTRLPLANE', 'policy_desc': 'ROUTER_PROTECT', 'stage': 'ingress'}, "
"'DATAACLINGRESS': {'stage': 'ingress', 'type': 'L3', 'ports': ['PortChannel01', 'PortChannel02', 'PortChannel03', 'PortChannel04'], 'policy_desc': 'DATAACLINGRESS'}, "
"'SNMP_ACL': {'services': ['SNMP'], 'type': 'CTRLPLANE', 'policy_desc': 'SNMP_ACL', 'stage': 'ingress'}, "
"'SSH_ACL': {'services': ['SSH'], 'type': 'CTRLPLANE', 'policy_desc': 'SSH_ACL', 'stage': 'ingress'}, "
"'DATAACLEGRESS': {'stage': 'egress', 'type': 'L3', 'ports': ['PortChannel01', 'PortChannel02', 'Ethernet100', 'PortChannel03'], 'policy_desc': 'DATAACLEGRESS'}, "
- "'EVERFLOWV6': {'stage': 'ingress', 'type': 'MIRRORV6', 'ports': ['PortChannel01', 'PortChannel02', 'PortChannel03', 'PortChannel04', 'Ethernet4', 'Ethernet100'], 'policy_desc': 'EVERFLOWV6'}}"
+ "'EVERFLOWV6': {'stage': 'ingress', 'type': 'MIRRORV6', 'ports': ['PortChannel01', 'PortChannel02', 'PortChannel03', 'PortChannel04', 'Ethernet4', 'Ethernet16', 'Ethernet100'], 'policy_desc': 'EVERFLOWV6'}}"
)
)
@@ -384,6 +384,7 @@ def test_minigraph_extra_neighbors(self):
"'Ethernet4': {'name': 'Servers0', 'port': 'eth0'}, "
"'Ethernet116': {'name': 'ARISTA02T1', 'port': 'Ethernet1/1'}, "
"'Ethernet100': {'name': 'Servers100', 'port': 'eth0'}, "
+ "'Ethernet16': {'name': 'Servers1', 'port': 'eth0'}, "
"'Ethernet112': {'name': 'ARISTA01T1', 'port': 'Ethernet1/1'}}")
)
@@ -415,7 +416,7 @@ def test_minigraph_port_autonegotiation(self):
"'Ethernet4': {'lanes': '25,26,27,28', 'description': 'Servers0:eth0', 'pfc_asym': 'off', 'mtu': '9100', 'tpid': '0x8100', 'alias': 'fortyGigE0/4', 'admin_status': 'up', 'autoneg': 'on', 'speed': '100000', 'fec': 'none'}, "
"'Ethernet8': {'lanes': '37,38,39,40', 'description': 'fortyGigE0/8', 'pfc_asym': 'off', 'mtu': '9100', 'tpid': '0x8100', 'alias': 'fortyGigE0/8', 'admin_status': 'up', 'autoneg': 'off', 'fec': 'none', 'speed': '40000'}, "
"'Ethernet12': {'lanes': '33,34,35,36', 'description': 'fortyGigE0/12', 'pfc_asym': 'off', 'mtu': '9100', 'tpid': '0x8100', 'alias': 'fortyGigE0/12', 'admin_status': 'up', 'speed': '40000'}, "
- "'Ethernet16': {'lanes': '41,42,43,44', 'description': 'fortyGigE0/16', 'pfc_asym': 'off', 'mtu': '9100', 'tpid': '0x8100', 'alias': 'fortyGigE0/16', 'admin_status': 'up', 'speed': '40000'}, "
+ "'Ethernet16': {'lanes': '41,42,43,44', 'description': 'Servers1:eth0', 'pfc_asym': 'off', 'mtu': '9100', 'tpid': '0x8100', 'alias': 'fortyGigE0/16', 'admin_status': 'up', 'autoneg': 'off', 'link_training': 'on', 'speed': '40000'}, "
"'Ethernet20': {'lanes': '45,46,47,48', 'description': 'fortyGigE0/20', 'pfc_asym': 'off', 'mtu': '9100', 'tpid': '0x8100', 'alias': 'fortyGigE0/20', 'admin_status': 'up', 'speed': '40000'}, "
"'Ethernet24': {'lanes': '5,6,7,8', 'description': 'fortyGigE0/24', 'pfc_asym': 'off', 'mtu': '9100', 'tpid': '0x8100', 'alias': 'fortyGigE0/24', 'admin_status': 'up', 'speed': '40000'}, "
"'Ethernet28': {'lanes': '1,2,3,4', 'description': 'fortyGigE0/28', 'pfc_asym': 'off', 'mtu': '9100', 'tpid': '0x8100', 'alias': 'fortyGigE0/28', 'admin_status': 'up', 'speed': '40000'}, "
@@ -456,7 +457,7 @@ def test_minigraph_port_autonegotiation(self):
"'Ethernet4': {'lanes': '25,26,27,28', 'description': 'Servers0:eth0', 'pfc_asym': 'off', 'mtu': '9100', 'tpid': '0x8100', 'alias': 'fortyGigE0/4', 'admin_status': 'up', 'autoneg': 'on', 'speed': '100000', 'fec': 'none'}, "
"'Ethernet8': {'lanes': '37,38,39,40', 'description': 'fortyGigE0/8', 'pfc_asym': 'off', 'mtu': '9100', 'tpid': '0x8100', 'alias': 'fortyGigE0/8', 'admin_status': 'up', 'autoneg': 'off', 'fec': 'none', 'speed': '40000'}, "
"'Ethernet12': {'lanes': '33,34,35,36', 'description': 'fortyGigE0/12', 'pfc_asym': 'off', 'mtu': '9100', 'tpid': '0x8100', 'alias': 'fortyGigE0/12', 'admin_status': 'up', 'autoneg': 'off', 'speed': '40000'}, "
- "'Ethernet16': {'lanes': '41,42,43,44', 'description': 'fortyGigE0/16', 'pfc_asym': 'off', 'mtu': '9100', 'tpid': '0x8100', 'alias': 'fortyGigE0/16', 'admin_status': 'up', 'autoneg': 'off', 'speed': '40000'}, "
+ "'Ethernet16': {'lanes': '41,42,43,44', 'description': 'Servers1:eth0', 'pfc_asym': 'off', 'mtu': '9100', 'tpid': '0x8100', 'alias': 'fortyGigE0/16', 'admin_status': 'up', 'autoneg': 'off', 'link_training': 'on', 'speed': '40000'}, "
"'Ethernet20': {'lanes': '45,46,47,48', 'description': 'fortyGigE0/20', 'pfc_asym': 'off', 'mtu': '9100', 'tpid': '0x8100', 'alias': 'fortyGigE0/20', 'admin_status': 'up', 'autoneg': 'off', 'speed': '40000'}, "
"'Ethernet24': {'lanes': '5,6,7,8', 'description': 'fortyGigE0/24', 'pfc_asym': 'off', 'mtu': '9100', 'tpid': '0x8100', 'alias': 'fortyGigE0/24', 'admin_status': 'up', 'autoneg': 'off', 'speed': '40000'}, "
"'Ethernet28': {'lanes': '1,2,3,4', 'description': 'fortyGigE0/28', 'pfc_asym': 'off', 'mtu': '9100', 'tpid': '0x8100', 'alias': 'fortyGigE0/28', 'admin_status': 'up', 'autoneg': 'off', 'speed': '40000'}, "
@@ -487,6 +488,14 @@ def test_minigraph_port_autonegotiation(self):
)
)
+ def test_minigraph_link_training(self):
+ argument = ['-m', self.sample_graph_t0, '-p', self.port_config, '-v', "PORT[\'Ethernet16\']"]
+ output = self.run_script(argument)
+ self.assertEqual(
+ utils.to_dict(output.strip()),
+ utils.to_dict("{'lanes': '41,42,43,44', 'description': 'Servers1:eth0', 'pfc_asym': 'off', 'mtu': '9100', 'tpid': '0x8100', 'alias': 'fortyGigE0/16', 'admin_status': 'up', 'autoneg': 'off', 'link_training': 'on', 'speed': '40000'}")
+ )
+
def test_minigraph_port_rs(self):
argument = ['-m', self.sample_graph_t0, '-p', self.port_config, '-v', "PORT[\'Ethernet124\']"]
output = self.run_script(argument)