From 33ce795b4812af24d7a82cee5747228658bade9f Mon Sep 17 00:00:00 2001 From: mkbalani Date: Thu, 6 Sep 2018 11:17:55 -0700 Subject: [PATCH 01/11] Add sfputil.py script for SONiC --- .../plugins/sfputil.py | 107 ++++++++++++++++++ 1 file changed, 107 insertions(+) create mode 100644 device/barefoot/x86_64-accton_wedge100bf_32x-r0/plugins/sfputil.py diff --git a/device/barefoot/x86_64-accton_wedge100bf_32x-r0/plugins/sfputil.py b/device/barefoot/x86_64-accton_wedge100bf_32x-r0/plugins/sfputil.py new file mode 100644 index 00000000000..7fb24405077 --- /dev/null +++ b/device/barefoot/x86_64-accton_wedge100bf_32x-r0/plugins/sfputil.py @@ -0,0 +1,107 @@ +# sfputil.py +# +# Platform-specific SFP transceiver interface for SONiC +# + +import subprocess +import re + +try: + import time + from sonic_sfp.sfputilbase import SfpUtilBase +except ImportError as e: + raise ImportError("%s - required module not found" % str(e)) + +class SfpUtil(SfpUtilBase): + """Platform-specific SfpUtil class""" + + PORT_START = 0 + PORT_END = 31 + PORTS_IN_BLOCK = 32 + + @property + def port_start(self): + return self.PORT_START + + @property + def port_end(self): + return self.PORT_END + + """ BFN Wedge based platform do not export eeprom info via sysfs path. Hence we skip this""" + @property + def port_to_eeprom_mapping(self): + pass + + def __init__(self): + SfpUtilBase.__init__(self) + + def get_presence(self, port_num): + # Check for invalid port_num + if port_num < self.port_start or port_num > self.port_end: + return False + qsfp_port = port_num + 1 + cmd = "docker exec -it syncd sfputil get_presence {0:s}".format(str(qsfp_port)) + presence=subprocess.Popen(cmd, shell=True,stdout=subprocess.PIPE).stdout.read() + if presence.strip() == "True": + return True + else: + return False + + @property + def get_low_power_mode(self, port_num): + # Check for invalid port_num + if port_num < self.port_start or port_num > self.port_end: + return False + qsfp_port = port_num + 1 + cmd = "docker exec -it syncd sfputil get_lp_mode {0:s}".format(str(qsfp_port)) + lpmode=subprocess.Popen(cmd, shell=True,stdout=subprocess.PIPE).stdout.read() + if lpmode.strip() == "True": + return True + else: + return False + + @property + def qsfp_ports(self): + return range(0, self.PORTS_IN_BLOCK + 1) + + @property + def reset(self, port_num): + pass + + @property + def set_low_power_mode(self, port_num, lpmode): + pass + + """ Overrides method get_eeprom_raw of baseclasee SpfUtilBase. This method return data from lower/upper page0""" + def get_eeprom_raw(self, port_num): + # Check for invalid port_num + if port_num < self.port_start or port_num > self.port_end: + return False + qsfp_port = port_num + 1 + cmd = "docker exec -i syncd sfputil get_eeprom_raw {0:s}".format(str(qsfp_port)) + #sfp_raw=subprocess.Popen(cmd, shell=True,stdout=subprocess.PIPE).stdout.read() + process = subprocess.Popen(cmd, shell=True, stdout=subprocess.PIPE, stderr=subprocess.PIPE) + sfp_raw, err = process.communicate() + if sfp_raw != "": + raw = re.findall('..?', sfp_raw) + print "raw {0:s}".format(sfp_raw) + return raw[:256] + else: + return None + + """ Overrides method get_eeprom_dom_raw of baseclasee SpfUtilBase. This method returns data from page3""" + def get_eeprom_dom_raw(self, port_num): + # Check for invalid port_num + if port_num < self.port_start or port_num > self.port_end: + return False + qsfp_port = port_num + 1 + cmd = "docker exec -i syncd sfputil get_eeprom_raw {0:s}".format(str(qsfp_port)) + #sfp_raw=subprocess.Popen(cmd, shell=True,stdout=subprocess.PIPE).stdout.read() + process = subprocess.Popen(cmd, shell=True, stdout=subprocess.PIPE, stderr=subprocess.PIPE) + sfp_raw, err = process.communicate() + if sfp_raw != "": + raw = re.findall('..?', sfp_raw) + print "raw {0:s}".format(sfp_raw) + return raw[256:] + else: + return None From 3d82c2e2579130c72d84cddf3b2b7aed33f1e567 Mon Sep 17 00:00:00 2001 From: mkbalani Date: Thu, 6 Sep 2018 11:49:57 -0700 Subject: [PATCH 02/11] Remove some stray prints --- .../x86_64-accton_wedge100bf_32x-r0/plugins/sfputil.py | 4 ---- 1 file changed, 4 deletions(-) diff --git a/device/barefoot/x86_64-accton_wedge100bf_32x-r0/plugins/sfputil.py b/device/barefoot/x86_64-accton_wedge100bf_32x-r0/plugins/sfputil.py index 7fb24405077..de548ae3f68 100644 --- a/device/barefoot/x86_64-accton_wedge100bf_32x-r0/plugins/sfputil.py +++ b/device/barefoot/x86_64-accton_wedge100bf_32x-r0/plugins/sfputil.py @@ -79,12 +79,10 @@ def get_eeprom_raw(self, port_num): return False qsfp_port = port_num + 1 cmd = "docker exec -i syncd sfputil get_eeprom_raw {0:s}".format(str(qsfp_port)) - #sfp_raw=subprocess.Popen(cmd, shell=True,stdout=subprocess.PIPE).stdout.read() process = subprocess.Popen(cmd, shell=True, stdout=subprocess.PIPE, stderr=subprocess.PIPE) sfp_raw, err = process.communicate() if sfp_raw != "": raw = re.findall('..?', sfp_raw) - print "raw {0:s}".format(sfp_raw) return raw[:256] else: return None @@ -96,12 +94,10 @@ def get_eeprom_dom_raw(self, port_num): return False qsfp_port = port_num + 1 cmd = "docker exec -i syncd sfputil get_eeprom_raw {0:s}".format(str(qsfp_port)) - #sfp_raw=subprocess.Popen(cmd, shell=True,stdout=subprocess.PIPE).stdout.read() process = subprocess.Popen(cmd, shell=True, stdout=subprocess.PIPE, stderr=subprocess.PIPE) sfp_raw, err = process.communicate() if sfp_raw != "": raw = re.findall('..?', sfp_raw) - print "raw {0:s}".format(sfp_raw) return raw[256:] else: return None From 24699ed063847d952f17979f7e24623d6f0c828b Mon Sep 17 00:00:00 2001 From: mkbalani Date: Thu, 6 Sep 2018 14:59:50 -0700 Subject: [PATCH 03/11] Implement remaining abstract methods of baseclass * + set low power mode, reset * also fetch #ports from platfroms instead of hardcoding in script --- .../plugins/sfputil.py | 40 +++++++++++++++---- 1 file changed, 33 insertions(+), 7 deletions(-) diff --git a/device/barefoot/x86_64-accton_wedge100bf_32x-r0/plugins/sfputil.py b/device/barefoot/x86_64-accton_wedge100bf_32x-r0/plugins/sfputil.py index de548ae3f68..814f5a9ac77 100644 --- a/device/barefoot/x86_64-accton_wedge100bf_32x-r0/plugins/sfputil.py +++ b/device/barefoot/x86_64-accton_wedge100bf_32x-r0/plugins/sfputil.py @@ -16,8 +16,6 @@ class SfpUtil(SfpUtilBase): """Platform-specific SfpUtil class""" PORT_START = 0 - PORT_END = 31 - PORTS_IN_BLOCK = 32 @property def port_start(self): @@ -25,7 +23,9 @@ def port_start(self): @property def port_end(self): - return self.PORT_END + cmd = "docker exec -it syncd sfputil get_number_qsfp_ports" + count=subprocess.Popen(cmd, shell=True,stdout=subprocess.PIPE).stdout.read() + return int(count.strip())-1 """ BFN Wedge based platform do not export eeprom info via sysfs path. Hence we skip this""" @property @@ -62,17 +62,43 @@ def get_low_power_mode(self, port_num): @property def qsfp_ports(self): - return range(0, self.PORTS_IN_BLOCK + 1) + return range(self.port_start, self.port_end + 1) @property def reset(self, port_num): - pass + # Check for invalid port_num + if port_num < self.port_start or port_num > self.port_end: + return False + qsfp_port = port_num + 1 + cmd = "docker exec -it syncd sfputil sfp_reset {0:s}".format(str(qsfp_port)) + out,err = subprocess.Popen(cmd, shell=True,stdout=subprocess.PIPE, stdout=subprocess.PIPE) + + if err != "": + print "Unable to reset port {0:d} {1:s}".format(port_num, err) + return False + else: + return True @property def set_low_power_mode(self, port_num, lpmode): - pass + # Check for invalid port_num + if port_num < self.port_start or port_num > self.port_end: + return False + + if lpmode is True: + mode = 1 + else: + mode = 0 + cmd = "docker exec -it syncd sfputil set_low_power_mode {0:s} {1:d}".format(str(qsfp_port),mode) + out,err = subprocess.Popen(cmd, shell=True,stdout=subprocess.PIPE, stderr=subprocess.PIPE) + + if err != "": + print "Unable to set low power mode {0:s}".format(err) + return False + + return True - """ Overrides method get_eeprom_raw of baseclasee SpfUtilBase. This method return data from lower/upper page0""" + """ Overrides method get_eeprom_raw of baseclasee SpfUtilBase. This method return data from lower & upper page0""" def get_eeprom_raw(self, port_num): # Check for invalid port_num if port_num < self.port_start or port_num > self.port_end: From fc84f834290bcdf8b690dac68c4e234514285cc7 Mon Sep 17 00:00:00 2001 From: mkbalani Date: Thu, 6 Sep 2018 16:24:44 -0700 Subject: [PATCH 04/11] Fix reset and set low power mode * tested with sfputil cli commands of SONiC --- .../plugins/sfputil.py | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/device/barefoot/x86_64-accton_wedge100bf_32x-r0/plugins/sfputil.py b/device/barefoot/x86_64-accton_wedge100bf_32x-r0/plugins/sfputil.py index 814f5a9ac77..b64aa061ff7 100644 --- a/device/barefoot/x86_64-accton_wedge100bf_32x-r0/plugins/sfputil.py +++ b/device/barefoot/x86_64-accton_wedge100bf_32x-r0/plugins/sfputil.py @@ -47,7 +47,6 @@ def get_presence(self, port_num): else: return False - @property def get_low_power_mode(self, port_num): # Check for invalid port_num if port_num < self.port_start or port_num > self.port_end: @@ -64,14 +63,14 @@ def get_low_power_mode(self, port_num): def qsfp_ports(self): return range(self.port_start, self.port_end + 1) - @property def reset(self, port_num): # Check for invalid port_num if port_num < self.port_start or port_num > self.port_end: return False qsfp_port = port_num + 1 - cmd = "docker exec -it syncd sfputil sfp_reset {0:s}".format(str(qsfp_port)) - out,err = subprocess.Popen(cmd, shell=True,stdout=subprocess.PIPE, stdout=subprocess.PIPE) + cmd = "docker exec -i syncd sfputil sfp_reset {0:s}".format(str(qsfp_port)) + output = subprocess.Popen(cmd, shell=True,stdout=subprocess.PIPE, stderr=subprocess.PIPE) + out, err = output.communicate() if err != "": print "Unable to reset port {0:d} {1:s}".format(port_num, err) @@ -79,7 +78,6 @@ def reset(self, port_num): else: return True - @property def set_low_power_mode(self, port_num, lpmode): # Check for invalid port_num if port_num < self.port_start or port_num > self.port_end: @@ -89,8 +87,10 @@ def set_low_power_mode(self, port_num, lpmode): mode = 1 else: mode = 0 - cmd = "docker exec -it syncd sfputil set_low_power_mode {0:s} {1:d}".format(str(qsfp_port),mode) - out,err = subprocess.Popen(cmd, shell=True,stdout=subprocess.PIPE, stderr=subprocess.PIPE) + qsfp_port = port_num + 1 + cmd = "docker exec -i syncd sfputil set_low_power_mode {0:s} {1:d}".format(str(qsfp_port),mode) + output = subprocess.Popen(cmd, shell=True, stdout=subprocess.PIPE, stderr=subprocess.PIPE) + out,err = output.communicate() if err != "": print "Unable to set low power mode {0:s}".format(err) @@ -113,7 +113,7 @@ def get_eeprom_raw(self, port_num): else: return None - """ Overrides method get_eeprom_dom_raw of baseclasee SpfUtilBase. This method returns data from page3""" + """ Overrides method get_eeprom_raw of baseclasee SpfUtilBase. This method return data from page3""" def get_eeprom_dom_raw(self, port_num): # Check for invalid port_num if port_num < self.port_start or port_num > self.port_end: From 6e60aee361ff4893db5afae86b5bc10ff436ca3c Mon Sep 17 00:00:00 2001 From: mkbalani Date: Fri, 7 Sep 2018 14:03:37 -0700 Subject: [PATCH 05/11] Add bfn eeprom.py pltfm plugin script --- .../plugins/eeprom.py | 145 ++++++++++++++++++ 1 file changed, 145 insertions(+) create mode 100644 device/barefoot/x86_64-accton_wedge100bf_32x-r0/plugins/eeprom.py diff --git a/device/barefoot/x86_64-accton_wedge100bf_32x-r0/plugins/eeprom.py b/device/barefoot/x86_64-accton_wedge100bf_32x-r0/plugins/eeprom.py new file mode 100644 index 00000000000..95b5ed92158 --- /dev/null +++ b/device/barefoot/x86_64-accton_wedge100bf_32x-r0/plugins/eeprom.py @@ -0,0 +1,145 @@ +#!/usr/bin/env python + +############################################################################# +#Barefoot Montara/Mavericks +# +# Platform and model specific eeprom subclass, inherits from the base class, +# and provides the followings: +# - the eeprom format definition +# - specific encoder/decoder if there is special need +############################################################################# + +try: + import exceptions + import binascii + import time + import optparse + import warnings + import os + import sys + import subprocess + import json + from sonic_eeprom import eeprom_base + from sonic_eeprom import eeprom_tlvinfo +except ImportError, e: + raise ImportError (str(e) + "- required module not found") + +eeprom_dict = { "version": ("Version", None, 0 ), + "pcb_mfger": ("PCB Manufacturer", "0x01", 8), + "prod_ser_num": ("Serial Number","0x23",12), + "bfn_pcba_part_num": ("Switch PCBA Part Number","0x02",12), + "odm_pcba_part_num": ("Part Number","0x22",13), + "bfn_pcbb_part_num": ("Switch PCBB Part Number","0x04",12), + "sys_asm_part_num": ("System Assembly Part Number", "0x05", 12), + "prod_state": ("Product Production State", "0x06", 1), + "location": ("EEPROM Location of Fabric", "0x07", 8), + "ext_mac_addr_size": ("Extende MAC Address Size", "0x08", 2), + "sys_mfg_date": ("System Manufacturing Date", "0x25", 4), + "prod_name": ("Product Name", "0x21",12), + "prod_ver": ("Product Version", "0x26", 1), + "prod_part_num": ("Product Part Number", "0x09", 8), + "sys_mfger": ("Manufacturer", "0x2B", 8), + "assembled_at": ("Assembled at","0x08" ,8), + "prod_ast_tag": ("Product Asset Tag", "0x09", 12), + "loc_mac_addr": ("Local MAC address", "0x0A",12), + "crc8": ("CRC8", "0xFE", 1), + "odm_pcba_ser_num": ("ODM PBCA Serial Number", "0x0B", 12), + "ext_mac_addr": ("Extended MAC Address Base", "0x0C",12), + "prod_sub_ver": ("Product Sub Version", "0x0D",1) + } + +product_dict = {"Montara":"Wedge100BF-32X-O-AC-F-BF", + "Lower MAV":"Wedge100BF-65X-O-AC-F-BF", + "Upper MAV":"Wedge100BF-65X-O-AC-F-BF" + } + +class board(eeprom_tlvinfo.TlvInfoDecoder, eeprom_base.EepromDecoder): + + """ On BFN platform onie system eeprom is not mapped to sysfs tree """ + def __init__(self, name, path, cpld_root, ro): + self.eeprom_path = "" + super(board, self).__init__(self.eeprom_path, 0, '', True) + + def set_cache_name(self,name): + pass + + def update_cache(self,e): + pass + + def write_cache(self,e): + pass + + + def read_eeprom(self): + cmd = "docker exec -it syncd eeprom read_eeprom" + output = subprocess.Popen(cmd, shell=True, stdout=subprocess.PIPE, stderr=subprocess.PIPE) + eeprom,err = output.communicate() + return eeprom + + + def base_mac_addr(self,e): + mac = e.get("loc_mac_addr",None) + if mac is None: + return "Bad Base Mac Address" + else: + return mac + + def base_mac_addr(self,e): + serial = e.get("prod_ser_num", None) + if serial is None: + return "Bad service tag" + else: + return serial + + def decode_eeprom(self,e): + + eeprom = json.loads(e) + value = "" + total_len = 0 + tlvHeader = "" + tlvBody = "" + + tlvHeader += "TlvInfo Header:\n" + tlvHeader += " Id String: TlvInfo\n" + tlvHeader += " Version: {0:d}\n".format(eeprom.get("version",1)) + + for attr, val in eeprom.iteritems(): + if val is not None: + if isinstance(val, basestring): + value = val + else: + value = str(val) + type, code, tlvlen = eeprom_dict.get(attr) + if type is not None and tlvlen > 0 and value: + product = product_dict.get(value) + if product is not None: + value = product + + tlvlen = len(value) + if tlvlen > 0: + total_len += tlvlen + tlvBody += "{0:s} {1:s} {2:d} {3:s}\n".format(type, code, tlvlen, value) + + tlvHeader += " Total Length: {0:d}\n".format(total_len) + tlvHeader += "TLV Name Len Value\n" + tlvHeader += "-------------------- --- -----" + + print tlvHeader + print tlvBody + + def is_checksum_valid(self,e): + # Assumption is checksum verification already done in BMC and correctly parsed and verified information is avail + return (True,0) + + +# def is_valid_block(self, e): +# pass +# +# def is_valid_block_checksum(self, e): +# pass +# +# def decoder(self, s, t): +# pass +# +# def get_tlv_index(self, e, code): +# pass From 463af30e62688cfd64252c3febd9f8d5b95749a8 Mon Sep 17 00:00:00 2001 From: mkbalani Date: Fri, 7 Sep 2018 14:11:05 -0700 Subject: [PATCH 06/11] Remove bfn sfputil script * sfputil show command to use sonic infra instead --- .../sonic-platform-modules-bfn/scripts/sfputil | 10 ---------- 1 file changed, 10 deletions(-) delete mode 100755 platform/barefoot/sonic-platform-modules-bfn/scripts/sfputil diff --git a/platform/barefoot/sonic-platform-modules-bfn/scripts/sfputil b/platform/barefoot/sonic-platform-modules-bfn/scripts/sfputil deleted file mode 100755 index 3df67614e49..00000000000 --- a/platform/barefoot/sonic-platform-modules-bfn/scripts/sfputil +++ /dev/null @@ -1,10 +0,0 @@ -#!/bin/bash - -DOCKER_EXEC_FLAGS="i" - -# Determine whether stdout is on a terminal -if [ -t 1 ] ; then - DOCKER_EXEC_FLAGS+="t" -fi - -docker exec -$DOCKER_EXEC_FLAGS syncd sfputil "$@" From e864f0bde667c5770cd7c11b2c2d971fabe3bda0 Mon Sep 17 00:00:00 2001 From: mkbalani Date: Fri, 7 Sep 2018 16:43:00 -0700 Subject: [PATCH 07/11] Add bfn psuutil.py script --- .../plugins/psuutil.py | 88 +++++++++++++++++++ 1 file changed, 88 insertions(+) create mode 100644 device/barefoot/x86_64-accton_wedge100bf_32x-r0/plugins/psuutil.py diff --git a/device/barefoot/x86_64-accton_wedge100bf_32x-r0/plugins/psuutil.py b/device/barefoot/x86_64-accton_wedge100bf_32x-r0/plugins/psuutil.py new file mode 100644 index 00000000000..ad6391e1698 --- /dev/null +++ b/device/barefoot/x86_64-accton_wedge100bf_32x-r0/plugins/psuutil.py @@ -0,0 +1,88 @@ +# +# psuutil.py +# Platform-specific PSU status interface for SONiC +# + + +import os.path +import subprocess + +try: + from sonic_psu.psu_base import PsuBase +except ImportError as e: + raise ImportError(str(e) + "- required module not found") + + +class PsuUtil(PsuBase): + """Platform-specific PSUutil class""" + + def __init__(self): + PsuBase.__init__(self) + + def get_num_psus(self): + """ + Retrieves the number of PSUs available on the device + :return: An integer, the number of PSUs available on the device + """ + cmd = "docker exec -it syncd ps_info get_num_psus" + output = subprocess.Popen(cmd, shell=True, stdout=subprocess.PIPE, stderr=subprocess.PIPE) + num,err = output.communicate() + if err != "": + raise RuntimeError("{0:s}".format(err)) + else: + return int(num.strip()) + + def get_psu_status(self, index): + """ + Retrieves the oprational status of power supply unit (PSU) defined + by index + :param index: An integer, index of the PSU of which to query status + :return: Boolean, True if PSU is operating properly, False if PSU is\ + faulty + """ + + cmd = "docker exec -it syncd ps_info get_psu_presence {0:d}".format(index) + output = subprocess.Popen(cmd, shell=True, stdout=subprocess.PIPE, stderr=subprocess.PIPE) + out,err = output.communicate() + if err != "": + raise RuntimeError("{0:s}".format(err)) + else: + if out.strip() == "True": + presence = True + else: + presence = False + + cmd = "docker exec -it syncd ps_info get_psu_status {0:d}".format(index) + status = subprocess.Popen(cmd, shell=True, stdout=subprocess.PIPE, stderr=subprocess.PIPE) + sout,serr = status.communicate() + + if serr != "": + raise RuntimeError("{0:s}".format(err)) + else: + if sout.strip() == "True": + psu_status = True + else: + psu_status = False + + return (presence & psu_status) + + def get_psu_presence(self, index): + """ + Retrieves the presence status of power supply unit (PSU) defined + by index + :param index: An integer, index of the PSU of which to query status + :return: Boolean, True if PSU is plugged, False if not + """ + + cmd = "docker exec -it syncd ps_info get_psu_presence {0:d}".format(index) + output = subprocess.Popen(cmd, shell=True, stdout=subprocess.PIPE, stderr=subprocess.PIPE) + out,err = output.communicate() + if err != "": + raise RuntimeError("{0:s}".format(err)) + else: + if out.strip() == "True": + presence = True + else: + presence = False + + return presence From 5fd04c8fa49860591c769657c4ddc8b6e262d9c6 Mon Sep 17 00:00:00 2001 From: mkbalani Date: Fri, 7 Sep 2018 17:03:21 -0700 Subject: [PATCH 08/11] Minor changes --- .../x86_64-accton_wedge100bf_32x-r0/plugins/eeprom.py | 11 +++++++---- 1 file changed, 7 insertions(+), 4 deletions(-) diff --git a/device/barefoot/x86_64-accton_wedge100bf_32x-r0/plugins/eeprom.py b/device/barefoot/x86_64-accton_wedge100bf_32x-r0/plugins/eeprom.py index 95b5ed92158..4c77a6e47ac 100644 --- a/device/barefoot/x86_64-accton_wedge100bf_32x-r0/plugins/eeprom.py +++ b/device/barefoot/x86_64-accton_wedge100bf_32x-r0/plugins/eeprom.py @@ -74,7 +74,10 @@ def read_eeprom(self): cmd = "docker exec -it syncd eeprom read_eeprom" output = subprocess.Popen(cmd, shell=True, stdout=subprocess.PIPE, stderr=subprocess.PIPE) eeprom,err = output.communicate() - return eeprom + if err != "": + raise RuntimeError("{0:s}".format(err)) + else: + return eeprom def base_mac_addr(self,e): @@ -122,10 +125,10 @@ def decode_eeprom(self,e): tlvHeader += " Total Length: {0:d}\n".format(total_len) tlvHeader += "TLV Name Len Value\n" - tlvHeader += "-------------------- --- -----" + tlvHeader += "-------------------- --- -----\n" - print tlvHeader - print tlvBody + sys.stdout.write(tlvHeader) + sys.stdout.write(tlvBody) def is_checksum_valid(self,e): # Assumption is checksum verification already done in BMC and correctly parsed and verified information is avail From c3ef8a91f32af9a50403c956ebc74b5f5c9ace14 Mon Sep 17 00:00:00 2001 From: mkbalani Date: Fri, 7 Sep 2018 17:16:30 -0700 Subject: [PATCH 09/11] Minor changes --- .../x86_64-accton_wedge100bf_32x-r0/plugins/eeprom.py | 11 ++++++----- 1 file changed, 6 insertions(+), 5 deletions(-) diff --git a/device/barefoot/x86_64-accton_wedge100bf_32x-r0/plugins/eeprom.py b/device/barefoot/x86_64-accton_wedge100bf_32x-r0/plugins/eeprom.py index 4c77a6e47ac..909a4a05d93 100644 --- a/device/barefoot/x86_64-accton_wedge100bf_32x-r0/plugins/eeprom.py +++ b/device/barefoot/x86_64-accton_wedge100bf_32x-r0/plugins/eeprom.py @@ -81,22 +81,23 @@ def read_eeprom(self): def base_mac_addr(self,e): - mac = e.get("loc_mac_addr",None) + eeprom = json.loads(e) + mac = eeprom.get("loc_mac_addr",None) if mac is None: return "Bad Base Mac Address" else: return mac - def base_mac_addr(self,e): - serial = e.get("prod_ser_num", None) + def serial_number_str(self,e): + eeprom = json.loads(e) + serial = eeprom.get("prod_ser_num", None) if serial is None: return "Bad service tag" else: return serial def decode_eeprom(self,e): - - eeprom = json.loads(e) + eeprom = json.loads(e) value = "" total_len = 0 tlvHeader = "" From 8b8ddee38c6ef6c3cb194c0f0be4bfb58e3e4a6d Mon Sep 17 00:00:00 2001 From: mkbalani Date: Fri, 7 Sep 2018 17:19:15 -0700 Subject: [PATCH 10/11] Add bfn pltfm sonic plugins scripts for mavericks --- .../plugins/eeprom.py | 149 ++++++++++++++++++ .../plugins/psuutil.py | 88 +++++++++++ .../plugins/sfputil.py | 129 +++++++++++++++ 3 files changed, 366 insertions(+) create mode 100644 device/barefoot/x86_64-accton_wedge100bf_65x-r0/plugins/eeprom.py create mode 100644 device/barefoot/x86_64-accton_wedge100bf_65x-r0/plugins/psuutil.py create mode 100644 device/barefoot/x86_64-accton_wedge100bf_65x-r0/plugins/sfputil.py diff --git a/device/barefoot/x86_64-accton_wedge100bf_65x-r0/plugins/eeprom.py b/device/barefoot/x86_64-accton_wedge100bf_65x-r0/plugins/eeprom.py new file mode 100644 index 00000000000..909a4a05d93 --- /dev/null +++ b/device/barefoot/x86_64-accton_wedge100bf_65x-r0/plugins/eeprom.py @@ -0,0 +1,149 @@ +#!/usr/bin/env python + +############################################################################# +#Barefoot Montara/Mavericks +# +# Platform and model specific eeprom subclass, inherits from the base class, +# and provides the followings: +# - the eeprom format definition +# - specific encoder/decoder if there is special need +############################################################################# + +try: + import exceptions + import binascii + import time + import optparse + import warnings + import os + import sys + import subprocess + import json + from sonic_eeprom import eeprom_base + from sonic_eeprom import eeprom_tlvinfo +except ImportError, e: + raise ImportError (str(e) + "- required module not found") + +eeprom_dict = { "version": ("Version", None, 0 ), + "pcb_mfger": ("PCB Manufacturer", "0x01", 8), + "prod_ser_num": ("Serial Number","0x23",12), + "bfn_pcba_part_num": ("Switch PCBA Part Number","0x02",12), + "odm_pcba_part_num": ("Part Number","0x22",13), + "bfn_pcbb_part_num": ("Switch PCBB Part Number","0x04",12), + "sys_asm_part_num": ("System Assembly Part Number", "0x05", 12), + "prod_state": ("Product Production State", "0x06", 1), + "location": ("EEPROM Location of Fabric", "0x07", 8), + "ext_mac_addr_size": ("Extende MAC Address Size", "0x08", 2), + "sys_mfg_date": ("System Manufacturing Date", "0x25", 4), + "prod_name": ("Product Name", "0x21",12), + "prod_ver": ("Product Version", "0x26", 1), + "prod_part_num": ("Product Part Number", "0x09", 8), + "sys_mfger": ("Manufacturer", "0x2B", 8), + "assembled_at": ("Assembled at","0x08" ,8), + "prod_ast_tag": ("Product Asset Tag", "0x09", 12), + "loc_mac_addr": ("Local MAC address", "0x0A",12), + "crc8": ("CRC8", "0xFE", 1), + "odm_pcba_ser_num": ("ODM PBCA Serial Number", "0x0B", 12), + "ext_mac_addr": ("Extended MAC Address Base", "0x0C",12), + "prod_sub_ver": ("Product Sub Version", "0x0D",1) + } + +product_dict = {"Montara":"Wedge100BF-32X-O-AC-F-BF", + "Lower MAV":"Wedge100BF-65X-O-AC-F-BF", + "Upper MAV":"Wedge100BF-65X-O-AC-F-BF" + } + +class board(eeprom_tlvinfo.TlvInfoDecoder, eeprom_base.EepromDecoder): + + """ On BFN platform onie system eeprom is not mapped to sysfs tree """ + def __init__(self, name, path, cpld_root, ro): + self.eeprom_path = "" + super(board, self).__init__(self.eeprom_path, 0, '', True) + + def set_cache_name(self,name): + pass + + def update_cache(self,e): + pass + + def write_cache(self,e): + pass + + + def read_eeprom(self): + cmd = "docker exec -it syncd eeprom read_eeprom" + output = subprocess.Popen(cmd, shell=True, stdout=subprocess.PIPE, stderr=subprocess.PIPE) + eeprom,err = output.communicate() + if err != "": + raise RuntimeError("{0:s}".format(err)) + else: + return eeprom + + + def base_mac_addr(self,e): + eeprom = json.loads(e) + mac = eeprom.get("loc_mac_addr",None) + if mac is None: + return "Bad Base Mac Address" + else: + return mac + + def serial_number_str(self,e): + eeprom = json.loads(e) + serial = eeprom.get("prod_ser_num", None) + if serial is None: + return "Bad service tag" + else: + return serial + + def decode_eeprom(self,e): + eeprom = json.loads(e) + value = "" + total_len = 0 + tlvHeader = "" + tlvBody = "" + + tlvHeader += "TlvInfo Header:\n" + tlvHeader += " Id String: TlvInfo\n" + tlvHeader += " Version: {0:d}\n".format(eeprom.get("version",1)) + + for attr, val in eeprom.iteritems(): + if val is not None: + if isinstance(val, basestring): + value = val + else: + value = str(val) + type, code, tlvlen = eeprom_dict.get(attr) + if type is not None and tlvlen > 0 and value: + product = product_dict.get(value) + if product is not None: + value = product + + tlvlen = len(value) + if tlvlen > 0: + total_len += tlvlen + tlvBody += "{0:s} {1:s} {2:d} {3:s}\n".format(type, code, tlvlen, value) + + tlvHeader += " Total Length: {0:d}\n".format(total_len) + tlvHeader += "TLV Name Len Value\n" + tlvHeader += "-------------------- --- -----\n" + + sys.stdout.write(tlvHeader) + sys.stdout.write(tlvBody) + + def is_checksum_valid(self,e): + # Assumption is checksum verification already done in BMC and correctly parsed and verified information is avail + return (True,0) + + +# def is_valid_block(self, e): +# pass +# +# def is_valid_block_checksum(self, e): +# pass +# +# def decoder(self, s, t): +# pass +# +# def get_tlv_index(self, e, code): +# pass diff --git a/device/barefoot/x86_64-accton_wedge100bf_65x-r0/plugins/psuutil.py b/device/barefoot/x86_64-accton_wedge100bf_65x-r0/plugins/psuutil.py new file mode 100644 index 00000000000..ad6391e1698 --- /dev/null +++ b/device/barefoot/x86_64-accton_wedge100bf_65x-r0/plugins/psuutil.py @@ -0,0 +1,88 @@ +# +# psuutil.py +# Platform-specific PSU status interface for SONiC +# + + +import os.path +import subprocess + +try: + from sonic_psu.psu_base import PsuBase +except ImportError as e: + raise ImportError(str(e) + "- required module not found") + + +class PsuUtil(PsuBase): + """Platform-specific PSUutil class""" + + def __init__(self): + PsuBase.__init__(self) + + def get_num_psus(self): + """ + Retrieves the number of PSUs available on the device + :return: An integer, the number of PSUs available on the device + """ + cmd = "docker exec -it syncd ps_info get_num_psus" + output = subprocess.Popen(cmd, shell=True, stdout=subprocess.PIPE, stderr=subprocess.PIPE) + num,err = output.communicate() + if err != "": + raise RuntimeError("{0:s}".format(err)) + else: + return int(num.strip()) + + def get_psu_status(self, index): + """ + Retrieves the oprational status of power supply unit (PSU) defined + by index + :param index: An integer, index of the PSU of which to query status + :return: Boolean, True if PSU is operating properly, False if PSU is\ + faulty + """ + + cmd = "docker exec -it syncd ps_info get_psu_presence {0:d}".format(index) + output = subprocess.Popen(cmd, shell=True, stdout=subprocess.PIPE, stderr=subprocess.PIPE) + out,err = output.communicate() + if err != "": + raise RuntimeError("{0:s}".format(err)) + else: + if out.strip() == "True": + presence = True + else: + presence = False + + cmd = "docker exec -it syncd ps_info get_psu_status {0:d}".format(index) + status = subprocess.Popen(cmd, shell=True, stdout=subprocess.PIPE, stderr=subprocess.PIPE) + sout,serr = status.communicate() + + if serr != "": + raise RuntimeError("{0:s}".format(err)) + else: + if sout.strip() == "True": + psu_status = True + else: + psu_status = False + + return (presence & psu_status) + + def get_psu_presence(self, index): + """ + Retrieves the presence status of power supply unit (PSU) defined + by index + :param index: An integer, index of the PSU of which to query status + :return: Boolean, True if PSU is plugged, False if not + """ + + cmd = "docker exec -it syncd ps_info get_psu_presence {0:d}".format(index) + output = subprocess.Popen(cmd, shell=True, stdout=subprocess.PIPE, stderr=subprocess.PIPE) + out,err = output.communicate() + if err != "": + raise RuntimeError("{0:s}".format(err)) + else: + if out.strip() == "True": + presence = True + else: + presence = False + + return presence diff --git a/device/barefoot/x86_64-accton_wedge100bf_65x-r0/plugins/sfputil.py b/device/barefoot/x86_64-accton_wedge100bf_65x-r0/plugins/sfputil.py new file mode 100644 index 00000000000..b64aa061ff7 --- /dev/null +++ b/device/barefoot/x86_64-accton_wedge100bf_65x-r0/plugins/sfputil.py @@ -0,0 +1,129 @@ +# sfputil.py +# +# Platform-specific SFP transceiver interface for SONiC +# + +import subprocess +import re + +try: + import time + from sonic_sfp.sfputilbase import SfpUtilBase +except ImportError as e: + raise ImportError("%s - required module not found" % str(e)) + +class SfpUtil(SfpUtilBase): + """Platform-specific SfpUtil class""" + + PORT_START = 0 + + @property + def port_start(self): + return self.PORT_START + + @property + def port_end(self): + cmd = "docker exec -it syncd sfputil get_number_qsfp_ports" + count=subprocess.Popen(cmd, shell=True,stdout=subprocess.PIPE).stdout.read() + return int(count.strip())-1 + + """ BFN Wedge based platform do not export eeprom info via sysfs path. Hence we skip this""" + @property + def port_to_eeprom_mapping(self): + pass + + def __init__(self): + SfpUtilBase.__init__(self) + + def get_presence(self, port_num): + # Check for invalid port_num + if port_num < self.port_start or port_num > self.port_end: + return False + qsfp_port = port_num + 1 + cmd = "docker exec -it syncd sfputil get_presence {0:s}".format(str(qsfp_port)) + presence=subprocess.Popen(cmd, shell=True,stdout=subprocess.PIPE).stdout.read() + if presence.strip() == "True": + return True + else: + return False + + def get_low_power_mode(self, port_num): + # Check for invalid port_num + if port_num < self.port_start or port_num > self.port_end: + return False + qsfp_port = port_num + 1 + cmd = "docker exec -it syncd sfputil get_lp_mode {0:s}".format(str(qsfp_port)) + lpmode=subprocess.Popen(cmd, shell=True,stdout=subprocess.PIPE).stdout.read() + if lpmode.strip() == "True": + return True + else: + return False + + @property + def qsfp_ports(self): + return range(self.port_start, self.port_end + 1) + + def reset(self, port_num): + # Check for invalid port_num + if port_num < self.port_start or port_num > self.port_end: + return False + qsfp_port = port_num + 1 + cmd = "docker exec -i syncd sfputil sfp_reset {0:s}".format(str(qsfp_port)) + output = subprocess.Popen(cmd, shell=True,stdout=subprocess.PIPE, stderr=subprocess.PIPE) + out, err = output.communicate() + + if err != "": + print "Unable to reset port {0:d} {1:s}".format(port_num, err) + return False + else: + return True + + def set_low_power_mode(self, port_num, lpmode): + # Check for invalid port_num + if port_num < self.port_start or port_num > self.port_end: + return False + + if lpmode is True: + mode = 1 + else: + mode = 0 + qsfp_port = port_num + 1 + cmd = "docker exec -i syncd sfputil set_low_power_mode {0:s} {1:d}".format(str(qsfp_port),mode) + output = subprocess.Popen(cmd, shell=True, stdout=subprocess.PIPE, stderr=subprocess.PIPE) + out,err = output.communicate() + + if err != "": + print "Unable to set low power mode {0:s}".format(err) + return False + + return True + + """ Overrides method get_eeprom_raw of baseclasee SpfUtilBase. This method return data from lower & upper page0""" + def get_eeprom_raw(self, port_num): + # Check for invalid port_num + if port_num < self.port_start or port_num > self.port_end: + return False + qsfp_port = port_num + 1 + cmd = "docker exec -i syncd sfputil get_eeprom_raw {0:s}".format(str(qsfp_port)) + process = subprocess.Popen(cmd, shell=True, stdout=subprocess.PIPE, stderr=subprocess.PIPE) + sfp_raw, err = process.communicate() + if sfp_raw != "": + raw = re.findall('..?', sfp_raw) + return raw[:256] + else: + return None + + """ Overrides method get_eeprom_raw of baseclasee SpfUtilBase. This method return data from page3""" + def get_eeprom_dom_raw(self, port_num): + # Check for invalid port_num + if port_num < self.port_start or port_num > self.port_end: + return False + qsfp_port = port_num + 1 + cmd = "docker exec -i syncd sfputil get_eeprom_raw {0:s}".format(str(qsfp_port)) + process = subprocess.Popen(cmd, shell=True, stdout=subprocess.PIPE, stderr=subprocess.PIPE) + sfp_raw, err = process.communicate() + if sfp_raw != "": + raw = re.findall('..?', sfp_raw) + return raw[256:] + else: + return None From e924d62a4a28cbe86add3f946318ad9cb41c04fe Mon Sep 17 00:00:00 2001 From: mkbalani Date: Fri, 7 Sep 2018 17:22:15 -0700 Subject: [PATCH 11/11] Remove bfn spfutil script for maverick --- .../sonic-platform-modules-bfn-montara/scripts/sfputil | 10 ---------- 1 file changed, 10 deletions(-) delete mode 100755 platform/barefoot/sonic-platform-modules-bfn-montara/scripts/sfputil diff --git a/platform/barefoot/sonic-platform-modules-bfn-montara/scripts/sfputil b/platform/barefoot/sonic-platform-modules-bfn-montara/scripts/sfputil deleted file mode 100755 index 3df67614e49..00000000000 --- a/platform/barefoot/sonic-platform-modules-bfn-montara/scripts/sfputil +++ /dev/null @@ -1,10 +0,0 @@ -#!/bin/bash - -DOCKER_EXEC_FLAGS="i" - -# Determine whether stdout is on a terminal -if [ -t 1 ] ; then - DOCKER_EXEC_FLAGS+="t" -fi - -docker exec -$DOCKER_EXEC_FLAGS syncd sfputil "$@"