From 393f6364e8d0c303ac1b438bd4f40362d520ce78 Mon Sep 17 00:00:00 2001 From: Arun Saravanan Balachandran Date: Mon, 16 Nov 2020 13:36:41 +0530 Subject: [PATCH 1/2] [sonic_pcie] Add common get_pcie_aer_stats implementation --- sonic_platform_base/sonic_pcie/pcie_base.py | 106 +++++++++++------- sonic_platform_base/sonic_pcie/pcie_common.py | 36 ++++++ 2 files changed, 101 insertions(+), 41 deletions(-) diff --git a/sonic_platform_base/sonic_pcie/pcie_base.py b/sonic_platform_base/sonic_pcie/pcie_base.py index 17055aa32..3155401ff 100755 --- a/sonic_platform_base/sonic_pcie/pcie_base.py +++ b/sonic_platform_base/sonic_pcie/pcie_base.py @@ -1,41 +1,65 @@ -# -# pcie_base.py -# -# Abstract base class for implementing platform-specific -# PCIE functionality for SONiC -# - -try: - import abc -except ImportError as e: - raise ImportError (str(e) + " - required module not found") - -class PcieBase(object): - def __init__(self, path): - """ - Constructor - - Args: - pcieutil file and config file path - """ - - @abc.abstractmethod - def get_pcie_device(self): - """ - get current device pcie info - - Returns: - A list including pcie device info - """ - return [] - - - @abc.abstractmethod - def get_pcie_check(self): - """ - Check Pcie device with config file - - Returns: - A list including pcie device and test result info - """ - return [] +# +# pcie_base.py +# +# Abstract base class for implementing platform-specific +# PCIE functionality for SONiC +# + +try: + import abc +except ImportError as e: + raise ImportError(str(e) + " - required module not found") + + +class PcieBase(object): + def __init__(self, path): + """ + Constructor + + Args: + pcieutil file and config file path + """ + + @abc.abstractmethod + def get_pcie_device(self): + """ + get current device pcie info + + Returns: + A list including pcie device info + """ + return [] + + @abc.abstractmethod + def get_pcie_check(self): + """ + Check Pcie device with config file + + Returns: + A list including pcie device and test result info + """ + return [] + + @abc.abstractmethod + def get_pcie_aer_stats(self, domain, bus, dev, fn): + """ + Returns a nested dictionary containing the AER stats belonging to a + PCIe device + + Args: + domain, bus, dev, fn: Domain, bus, device, function of the PCIe + device respectively + + Returns: + A nested dictionary where key is severity 'correctable', 'fatal' or + 'non_fatal', value is a dictionary of key, value pairs in the format: + {'AER Error type': Error count} + + Ex. {'correctable': {'BadDLLP': 0, 'BadTLP': 0}, + 'fatal': {'RxOF': 0, 'MalfTLP': 0}, + 'non_fatal': {'RxOF': 0, 'MalfTLP': 0}} + + For PCIe devices that do not support AER, the value for each + severity key is an empty dictionary. + """ + return {} diff --git a/sonic_platform_base/sonic_pcie/pcie_common.py b/sonic_platform_base/sonic_pcie/pcie_common.py index 01ace2056..09821c6c5 100755 --- a/sonic_platform_base/sonic_pcie/pcie_common.py +++ b/sonic_platform_base/sonic_pcie/pcie_common.py @@ -98,6 +98,42 @@ def get_pcie_check(self): item_conf["result"] = "Failed" return self.confInfo + # return AER stats of PCIe device + def get_pcie_aer_stats(self, domain=0, bus=0, device=0, func=0): + aer_stats = dict.fromkeys(['correctable', 'fatal', 'non_fatal'], {}) + dev_path = os.path.join('/sys/bus/pci/devices', '%04x:%02x:%02x.%d' % (domain, bus, device, func)) + + # construct AER sysfs filepath + correctable_path = os.path.join(dev_path, "aer_dev_correctable") + fatal_path = os.path.join(dev_path, "aer_dev_fatal") + non_fatal_path = os.path.join(dev_path, "aer_dev_nonfatal") + + # update AER-correctable fields + if os.path.isfile(correctable_path): + with open(correctable_path, 'r') as fh: + lines = fh.readlines() + for line in lines: + correctable_field, value = line.split() + aer_stats['correctable'][correctable_field] = value + + # update AER-Fatal fields + if os.path.isfile(fatal_path): + with open(fatal_path, 'r') as fh: + lines = fh.readlines() + for line in lines: + fatal_field, value = line.split() + aer_stats['fatal'][fatal_field] = value + + # update AER-Non Fatal fields + if os.path.isfile(non_fatal_path): + with open(non_fatal_path, 'r') as fh: + lines = fh.readlines() + for line in lines: + non_fatal_field, value = line.split() + aer_stats['non_fatal'][non_fatal_field] = value + + return aer_stats + # generate the config file with current pci device def dump_conf_yaml(self): curInfo = self.get_pcie_device() From 3c89124b1e61cdd1b2ce132d7a14b5ffbd77b396 Mon Sep 17 00:00:00 2001 From: Arun Saravanan Balachandran Date: Mon, 16 Nov 2020 14:12:02 +0530 Subject: [PATCH 2/2] Update dict initialization --- sonic_platform_base/sonic_pcie/pcie_common.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/sonic_platform_base/sonic_pcie/pcie_common.py b/sonic_platform_base/sonic_pcie/pcie_common.py index 09821c6c5..c3d032ebc 100755 --- a/sonic_platform_base/sonic_pcie/pcie_common.py +++ b/sonic_platform_base/sonic_pcie/pcie_common.py @@ -100,7 +100,7 @@ def get_pcie_check(self): # return AER stats of PCIe device def get_pcie_aer_stats(self, domain=0, bus=0, device=0, func=0): - aer_stats = dict.fromkeys(['correctable', 'fatal', 'non_fatal'], {}) + aer_stats = {'correctable': {}, 'fatal': {}, 'non_fatal': {}} dev_path = os.path.join('/sys/bus/pci/devices', '%04x:%02x:%02x.%d' % (domain, bus, device, func)) # construct AER sysfs filepath