Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Common functions for Multi ASIC CLIs #4973

Merged
merged 24 commits into from
Aug 14, 2020
Merged
Show file tree
Hide file tree
Changes from 8 commits
Commits
Show all changes
24 commits
Select commit Hold shift + click to select a range
0c7d22f
Changes for identifing the cli object's role
arlakshm Jul 15, 2020
0620982
Fix lgtm warning
arlakshm Jul 15, 2020
00e34d0
address review comment
arlakshm Jul 16, 2020
b133dc1
Fixed review comments
arlakshm Jul 16, 2020
3c671c1
Add index to port_config and minor fixes
arlakshm Jul 20, 2020
51adf86
Merge remote-tracking branch 'arlakshm/master' into masic_port_role
arlakshm Jul 27, 2020
4985d2d
move common functions to sonic_py_common package
arlakshm Jul 28, 2020
525b6b4
fix compilation issue
arlakshm Jul 30, 2020
2af6005
Address review comments
arlakshm Aug 5, 2020
3028347
reorganize imports
arlakshm Aug 5, 2020
c249599
Merge remote-tracking branch 'arlakshm/master' into masic_port_role
arlakshm Aug 6, 2020
c69a6c3
Fix compilation
arlakshm Aug 6, 2020
ea16670
fix lgtm warnings
arlakshm Aug 6, 2020
2e5bc12
Merge remote-tracking branch 'arlakshm/master' into masic_port_role
arlakshm Aug 7, 2020
413b06d
use TCP instead of Unix socket
arlakshm Aug 7, 2020
6a3009c
address review commit
arlakshm Aug 7, 2020
7628bbd
change the port in port_config to Ext\Int
arlakshm Aug 7, 2020
b4837ff
Merge remote-tracking branch 'arlakshm/master' into masic_port_role
arlakshm Aug 10, 2020
cabc2f3
revert the changes in device_info.py
arlakshm Aug 10, 2020
789a548
address review comments
arlakshm Aug 12, 2020
b65012e
For cli get the namespace list from linux
arlakshm Aug 12, 2020
f1814c5
Merge remote-tracking branch 'arlakshm/master' into masic_port_role
arlakshm Aug 13, 2020
f1a4f07
fix import spacing
arlakshm Aug 13, 2020
0b0cfd5
address review comments
arlakshm Aug 13, 2020
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
14 changes: 12 additions & 2 deletions src/sonic-config-engine/sonic_device_util.py
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,8 @@
from natsort import natsorted
import glob
from swsssdk import ConfigDBConnector, SonicDBConfig
from portconfig import get_port_config
from portconfig import get_port_config_file_name

DOCUMENTATION = '''
---
Expand All @@ -26,6 +28,13 @@
ASIC_CONF_FILENAME = 'asic.conf'
FRONTEND_ASIC_SUB_ROLE = 'FrontEnd'
BACKEND_ASIC_SUB_ROLE = 'BackEnd'
EXTERNAL_PORT = 'E'
INTERNAL_PORT = 'I'
PORT_CHANNEL_CFG_DB_TABLE = 'PORTCHANNEL'
PORT_CFG_DB_TABLE = 'PORT'
BGP_NEIGH_CFG_DB_TABLE = 'BGP_NEIGHBOR'
NEIGH_DEVICE_METADATA_CFG_DB_TABLE = "DEVICE_NEIGHBOR_METADATA"

def get_machine_info():
if not os.path.isfile('/host/machine.conf'):
return None
Expand Down Expand Up @@ -100,9 +109,10 @@ def is_multi_npu():
num_npus = get_num_npus()
return (num_npus > 1)


def get_all_namespaces():
"""
In case of Multi-Asic platform, Each ASIC will have a linux network namespace created.
In case of MultiAsic platform, Each ASIC will have a linux network namespace created.
So we loop through the databases in different namespaces and depending on the sub_role
decide whether this is a front end ASIC/namespace or a back end one.
"""
Expand All @@ -124,7 +134,7 @@ def get_all_namespaces():
back_ns.append(namespace)

return {'front_ns':front_ns, 'back_ns':back_ns}

def get_platform_info(machine_info):
if machine_info != None:
if machine_info.has_key('onie_platform'):
Expand Down
Original file line number Diff line number Diff line change
@@ -1,9 +1,9 @@
# name lanes alias asic_port_name
Ethernet0 33,34,35,36 Ethernet1/1 Eth0-ASIC0
Ethernet4 29,30,31,32 Ethernet1/2 Eth1-ASIC0
Ethernet8 41,42,43,44 Ethernet1/3 Eth2-ASIC0
Ethernet12 37,38,39,40 Ethernet1/4 Eth3-ASIC0
Ethernet-BP0 13,14,15,16 Ethernet-BP0 Eth4-ASIC0
Ethernet-BP4 17,18,19,20 Ethernet-BP4 Eth5-ASIC0
Ethernet-BP8 21,22,23,24 Ethernet-BP8 Eth6-ASIC0
Ethernet-BP12 25,26,27,28 Ethernet-BP12 Eth7-ASIC0
# name lanes alias index asic_port_name role
Ethernet0 33,34,35,36 Ethernet1/1 0 Eth0-ASIC0 E
Ethernet4 29,30,31,32 Ethernet1/2 1 Eth1-ASIC0 E
Ethernet8 41,42,43,44 Ethernet1/3 2 Eth2-ASIC0 E
Ethernet12 37,38,39,40 Ethernet1/4 3 Eth3-ASIC0 E
Ethernet-BP0 13,14,15,16 Ethernet-BP0 0 Eth4-ASIC0 I
Ethernet-BP4 17,18,19,20 Ethernet-BP4 1 Eth5-ASIC0 I
Ethernet-BP8 21,22,23,24 Ethernet-BP8 2 Eth6-ASIC0 I
Ethernet-BP12 25,26,27,28 Ethernet-BP12 3 Eth7-ASIC0 I
Original file line number Diff line number Diff line change
@@ -1,9 +1,9 @@
# name lanes alias asic_port_name
Ethernet16 33,34,35,36 Ethernet1/5 Eth0-ASIC1
Ethernet20 29,30,31,32 Ethernet1/6 Eth1-ASIC1
Ethernet24 41,42,43,44 Ethernet1/7 Eth2-ASIC1
Ethernet28 37,38,39,40 Ethernet1/8 Eth3-ASIC1
Ethernet-BP16 13,14,15,16 Ethernet-BP16 Eth4-ASIC1
Ethernet-BP20 17,18,19,20 Ethernet-BP20 Eth5-ASIC1
Ethernet-BP24 21,22,23,24 Ethernet-BP24 Eth6-ASIC1
Ethernet-BP28 25,26,27,28 Ethernet-BP28 Eth7-ASIC1
# name lanes alias index asic_port_name role
Ethernet16 33,34,35,36 Ethernet1/5 4 Eth0-ASIC1 E
Ethernet20 29,30,31,32 Ethernet1/6 5 Eth1-ASIC1 E
Ethernet24 41,42,43,44 Ethernet1/7 6 Eth2-ASIC1 E
Ethernet28 37,38,39,40 Ethernet1/8 7 Eth3-ASIC1 E
Ethernet-BP16 13,14,15,16 Ethernet-BP16 4 Eth4-ASIC1 I
Ethernet-BP20 17,18,19,20 Ethernet-BP20 5 Eth5-ASIC1 I
Ethernet-BP24 21,22,23,24 Ethernet-BP24 6 Eth6-ASIC1 I
Ethernet-BP28 25,26,27,28 Ethernet-BP28 7 Eth7-ASIC1 I
Original file line number Diff line number Diff line change
@@ -1,9 +1,9 @@
# name lanes alias asic_port_name
Ethernet-BP256 61,62,63,64 Ethernet-BP256 Eth0-ASIC2
Ethernet-BP260 57,58,59,60 Ethernet-BP260 Eth1-ASIC2
Ethernet-BP264 53,54,55,56 Ethernet-BP264 Eth2-ASIC2
Ethernet-BP268 49,50,51,52 Ethernet-BP268 Eth3-ASIC2
Ethernet-BP272 45,46,47,48 Ethernet-BP272 Eth4-ASIC2
Ethernet-BP276 41,42,43,44 Ethernet-BP276 Eth5-ASIC2
Ethernet-BP280 37,38,39,40 Ethernet-BP280 Eth6-ASIC2
Ethernet-BP284 33,34,35,36 Ethernet-BP284 Eth7-ASIC2
# name lanes alias index asic_port_name role
Ethernet-BP256 61,62,63,64 Ethernet-BP256 8 Eth0-ASIC2 I
Ethernet-BP260 57,58,59,60 Ethernet-BP260 9 Eth1-ASIC2 I
Ethernet-BP264 53,54,55,56 Ethernet-BP264 10 Eth2-ASIC2 I
Ethernet-BP268 49,50,51,52 Ethernet-BP268 11 Eth3-ASIC2 I
Ethernet-BP272 45,46,47,48 Ethernet-BP272 12 Eth4-ASIC2 I
Ethernet-BP276 41,42,43,44 Ethernet-BP276 13 Eth5-ASIC2 I
Ethernet-BP280 37,38,39,40 Ethernet-BP280 14 Eth6-ASIC2 I
Ethernet-BP284 33,34,35,36 Ethernet-BP284 15 Eth7-ASIC2 I
Original file line number Diff line number Diff line change
@@ -1,9 +1,9 @@
# name lanes alias asic_port_name
Ethernet-BP384 29,30,31,32 Ethernet-BP384 Eth0-ASIC3
Ethernet-BP388 25,26,27,28 Ethernet-BP388 Eth1-ASIC3
Ethernet-BP392 21,22,23,24 Ethernet-BP392 Eth2-ASIC3
Ethernet-BP396 17,18,19,20 Ethernet-BP396 Eth3-ASIC3
Ethernet-BP400 13,14,15,16 Ethernet-BP400 Eth4-ASIC3
Ethernet-BP404 9,10,11,12 Ethernet-BP404 Eth5-ASIC3
Ethernet-BP408 5,6,7,8 Ethernet-BP408 Eth6-ASIC3
Ethernet-BP412 1,2,3,4 Ethernet-BP412 Eth7-ASIC3
# name lanes alias index asic_port_name role
Ethernet-BP384 29,30,31,32 Ethernet-BP384 16 Eth0-ASIC3 I
Ethernet-BP388 25,26,27,28 Ethernet-BP388 17 Eth1-ASIC3 I
Ethernet-BP392 21,22,23,24 Ethernet-BP392 18 Eth2-ASIC3 I
Ethernet-BP396 17,18,19,20 Ethernet-BP396 19 Eth3-ASIC3 I
Ethernet-BP400 13,14,15,16 Ethernet-BP400 20 Eth4-ASIC3 I
Ethernet-BP404 9,10,11,12 Ethernet-BP404 21 Eth5-ASIC3 I
Ethernet-BP408 5,6,7,8 Ethernet-BP408 22 Eth6-ASIC3 I
Ethernet-BP412 1,2,3,4 Ethernet-BP412 23 Eth7-ASIC3 I
14 changes: 14 additions & 0 deletions src/sonic-config-engine/tests/test_multinpu_cfggen.py
Original file line number Diff line number Diff line change
Expand Up @@ -158,6 +158,20 @@ def test_backend_asic_portchannel_intf(self):
self.assertListEqual(output.keys(), \
['PortChannel4013', 'PortChannel4013|10.1.0.2/31', 'PortChannel4014', 'PortChannel4014|10.1.0.6/31'])

def test_frontend_asic_ports(self):
argument = "-m {} -p {} -n asic0 --var-json \"PORT\"".format(self.sample_graph, self.port_config[0])
output = json.loads(self.run_script(argument))
self.assertDictEqual(output, \
{
"Ethernet0": { "admin_status": "up", "alias": "Ethernet1/1", "asic_port_name": "Eth0-ASIC0", "description": "01T2:Ethernet1", "index": "0", "lanes": "33,34,35,36", "mtu": "9100", "pfc_asym": "off", "role": "E", "speed": "40000" },
"Ethernet4": { "admin_status": "up", "alias": "Ethernet1/2", "asic_port_name": "Eth1-ASIC0", "description": "01T2:Ethernet2", "index": "1", "lanes": "29,30,31,32", "mtu": "9100", "pfc_asym": "off", "role": "E", "speed": "40000" },
"Ethernet8": { "alias": "Ethernet1/3", "asic_port_name": "Eth2-ASIC0", "description": "Ethernet1/3", "index": "2", "lanes": "41,42,43,44", "mtu": "9100", "pfc_asym": "off", "role": "E", "speed": "40000" },
"Ethernet12": { "alias": "Ethernet1/4", "asic_port_name": "Eth3-ASIC0", "description": "Ethernet1/4", "index": "3", "lanes": "37,38,39,40", "mtu": "9100", "pfc_asym": "off", "role": "E", "speed": "40000" },
"Ethernet-BP0": { "admin_status": "up", "alias": "Ethernet-BP0", "asic_port_name": "Eth4-ASIC0", "description": "ASIC2:Eth0-ASIC2", "index": "0", "lanes": "13,14,15,16", "mtu": "9100", "pfc_asym": "off", "role": "I", "speed": "40000" },
"Ethernet-BP4": { "admin_status": "up", "alias": "Ethernet-BP4", "asic_port_name": "Eth5-ASIC0", "description": "ASIC2:Eth1-ASIC2", "index": "1", "lanes": "17,18,19,20", "mtu": "9100", "pfc_asym": "off", "role": "I", "speed": "40000" },
"Ethernet-BP8": { "admin_status": "up", "alias": "Ethernet-BP8", "asic_port_name": "Eth6-ASIC0", "description": "ASIC3:Eth0-ASIC3", "index": "2", "lanes": "21,22,23,24", "mtu": "9100", "pfc_asym": "off", "role": "I", "speed": "40000" },
"Ethernet-BP12": { "admin_status": "up", "alias": "Ethernet-BP12", "asic_port_name": "Eth7-ASIC0", "description": "ASIC3:Eth1-ASIC3", "index": "3", "lanes": "25,26,27,28", "mtu": "9100", "pfc_asym": "off", "role": "I", "speed": "40000" }})

def test_frontend_asic_device_neigh(self):
argument = "-m {} -p {} -n asic0 --var-json \"DEVICE_NEIGHBOR\"".format(self.sample_graph, self.port_config[0])
output = json.loads(self.run_script(argument))
Expand Down
100 changes: 2 additions & 98 deletions src/sonic-py-common/sonic_py_common/device_info.py
Original file line number Diff line number Diff line change
@@ -1,9 +1,7 @@
import glob
import os
import subprocess

import yaml
from natsort import natsorted

# TODD: Replace with swsscommon
from swsssdk import ConfigDBConnector, SonicDBConfig
Expand All @@ -19,13 +17,6 @@
PORT_CONFIG_FILE = "port_config.ini"
PLATFORM_JSON_FILE = "platform.json"

# Multi-NPU constants
# TODO: Move Multi-ASIC-related functions and constants to a "multi_asic.py" module
NPU_NAME_PREFIX = "asic"
NAMESPACE_PATH_GLOB = "/run/netns/*"
ASIC_CONF_FILENAME = "asic.conf"
FRONTEND_ASIC_SUB_ROLE = "FrontEnd"
BACKEND_ASIC_SUB_ROLE = "BackEnd"


def get_machine_info():
Expand Down Expand Up @@ -111,30 +102,6 @@ def get_platform_and_hwsku():

return (platform, hwsku)


def get_asic_conf_file_path():
"""
Retrieves the path to the ASIC conguration file on the device

Returns:
A string containing the path to the ASIC conguration file on success,
None on failure
"""
asic_conf_path_candidates = []

asic_conf_path_candidates.append(os.path.join(CONTAINER_PLATFORM_PATH, ASIC_CONF_FILENAME))

platform = get_platform()
if platform:
asic_conf_path_candidates.append(os.path.join(HOST_DEVICE_PATH, platform, ASIC_CONF_FILENAME))

for asic_conf_file_path in asic_conf_path_candidates:
if os.path.isfile(asic_conf_file_path):
return asic_conf_file_path

return None


def get_paths_to_platform_and_hwsku_dirs():
"""
Retreives the paths to the device's platform and hardware SKU data
Expand Down Expand Up @@ -199,73 +166,9 @@ def get_sonic_version_info():


#
# Multi-NPU functionality
# Multi-ASIC functionality
#

def get_num_npus():
asic_conf_file_path = get_asic_conf_file_path()
if asic_conf_file_path is None:
return 1
with open(asic_conf_file_path) as asic_conf_file:
for line in asic_conf_file:
tokens = line.split('=')
if len(tokens) < 2:
continue
if tokens[0].lower() == 'num_asic':
num_npus = tokens[1].strip()
return int(num_npus)


def is_multi_npu():
num_npus = get_num_npus()
return (num_npus > 1)


def get_npu_id_from_name(npu_name):
if npu_name.startswith(NPU_NAME_PREFIX):
return npu_name[len(NPU_NAME_PREFIX):]
else:
return None


def get_namespaces():
"""
In a multi NPU platform, each NPU is in a Linux Namespace.
This method returns list of all the Namespace present on the device
"""
ns_list = []
for path in glob.glob(NAMESPACE_PATH_GLOB):
ns = os.path.basename(path)
ns_list.append(ns)
return natsorted(ns_list)


def get_all_namespaces():
"""
In case of Multi-Asic platform, Each ASIC will have a linux network namespace created.
So we loop through the databases in different namespaces and depending on the sub_role
decide whether this is a front end ASIC/namespace or a back end one.
"""
front_ns = []
back_ns = []
num_npus = get_num_npus()
SonicDBConfig.load_sonic_global_db_config()

if is_multi_npu():
for npu in range(num_npus):
namespace = "{}{}".format(NPU_NAME_PREFIX, npu)
config_db = ConfigDBConnector(use_unix_socket_path=True, namespace=namespace)
config_db.connect()

metadata = config_db.get_table('DEVICE_METADATA')
if metadata['localhost']['sub_role'] == FRONTEND_ASIC_SUB_ROLE:
front_ns.append(namespace)
elif metadata['localhost']['sub_role'] == BACKEND_ASIC_SUB_ROLE:
back_ns.append(namespace)

return {'front_ns':front_ns, 'back_ns':back_ns}


def _valid_mac_address(mac):
return bool(re.match("^([0-9A-Fa-f]{2}[:-]){5}([0-9A-Fa-f]{2})$", mac))

Expand Down Expand Up @@ -342,3 +245,4 @@ def get_system_routing_stack():
raise OSError("Cannot detect routing stack")

return result

Loading