[DellEMC]: EEPROM decoder for S6000, S6000-ON (#4718)
**- Why I did it** For decoding system EEPROM of S6000 based on Dell offset format and S6000-ON’s system EEPROM in ONIE TLV format. **- How I did it** - Differentiate between S6000 and S6000-ON using the product name available in ‘dmi’ ( “/sys/class/dmi/id/product_name” ) - For decoding S6000 system EEPROM in Dell offset format and updating the redis DB with the EEPROM contents, added a new class ‘EepromS6000’ in eeprom.py, - Renamed certain methods in both Eeprom, EepromS6000 classes to accommodate the plugin-specific methods. **- How to verify it** - Use 'decode-syseeprom' command to list the system EEPROM details. - Wrote a python script to load chassis class and call the appropriate methods. UT Logs: [S6000_eeprom_logs.txt](https://github.com/Azure/sonic-buildimage/files/4735515/S6000_eeprom_logs.txt), [S6000-ON_eeprom_logs.txt](https://github.com/Azure/sonic-buildimage/files/4735461/S6000-ON_eeprom_logs.txt) Test script: [eeprom_test_py.txt](https://github.com/Azure/sonic-buildimage/files/4735509/eeprom_test_py.txt)
This commit is contained in:
parent
9505bdb910
commit
54b284f4b0
@ -10,13 +10,21 @@
|
|||||||
#############################################################################
|
#############################################################################
|
||||||
|
|
||||||
try:
|
try:
|
||||||
from sonic_eeprom import eeprom_tlvinfo
|
from sonic_eeprom.eeprom_tlvinfo import TlvInfoDecoder
|
||||||
except ImportError, e:
|
from sonic_platform.eeprom import EepromS6000
|
||||||
|
except ImportError as e:
|
||||||
raise ImportError(str(e) + "- required module not found")
|
raise ImportError(str(e) + "- required module not found")
|
||||||
|
|
||||||
|
|
||||||
class board(eeprom_tlvinfo.TlvInfoDecoder):
|
class board(object):
|
||||||
|
|
||||||
def __init__(self, name, path, cpld_root, ro):
|
def __new__(cls, name, path, cpld_root, ro):
|
||||||
self.eeprom_path = "/sys/class/i2c-adapter/i2c-10/10-0053/eeprom"
|
eeprom_path = "/sys/class/i2c-adapter/i2c-10/10-0053/eeprom"
|
||||||
super(board, self).__init__(self.eeprom_path, 0, '', True)
|
|
||||||
|
with open("/sys/class/dmi/id/product_name", "r") as fd:
|
||||||
|
board_type = fd.read()
|
||||||
|
|
||||||
|
if 'S6000-ON' in board_type:
|
||||||
|
return TlvInfoDecoder(eeprom_path, 0, '', True)
|
||||||
|
else:
|
||||||
|
return EepromS6000(is_plugin=True)
|
||||||
|
@ -15,7 +15,7 @@ try:
|
|||||||
import subprocess
|
import subprocess
|
||||||
from sonic_platform_base.chassis_base import ChassisBase
|
from sonic_platform_base.chassis_base import ChassisBase
|
||||||
from sonic_platform.sfp import Sfp
|
from sonic_platform.sfp import Sfp
|
||||||
from sonic_platform.eeprom import Eeprom
|
from sonic_platform.eeprom import Eeprom, EepromS6000
|
||||||
from sonic_platform.fan import Fan
|
from sonic_platform.fan import Fan
|
||||||
from sonic_platform.psu import Psu
|
from sonic_platform.psu import Psu
|
||||||
from sonic_platform.thermal import Thermal
|
from sonic_platform.thermal import Thermal
|
||||||
@ -68,7 +68,14 @@ class Chassis(ChassisBase):
|
|||||||
# Get Transceiver status
|
# Get Transceiver status
|
||||||
self.modprs_register = self._get_transceiver_status()
|
self.modprs_register = self._get_transceiver_status()
|
||||||
|
|
||||||
|
with open("/sys/class/dmi/id/product_name", "r") as fd:
|
||||||
|
board_type = fd.read()
|
||||||
|
|
||||||
|
if 'S6000-ON' in board_type:
|
||||||
self._eeprom = Eeprom()
|
self._eeprom = Eeprom()
|
||||||
|
else:
|
||||||
|
self._eeprom = EepromS6000()
|
||||||
|
|
||||||
for i in range(MAX_S6000_FAN):
|
for i in range(MAX_S6000_FAN):
|
||||||
fan = Fan(i)
|
fan = Fan(i)
|
||||||
self._fan_list.append(fan)
|
self._fan_list.append(fan)
|
||||||
@ -138,7 +145,7 @@ class Chassis(ChassisBase):
|
|||||||
Returns:
|
Returns:
|
||||||
string: The name of the chassis
|
string: The name of the chassis
|
||||||
"""
|
"""
|
||||||
return self._eeprom.modelstr()
|
return self._eeprom.get_model()
|
||||||
|
|
||||||
def get_presence(self):
|
def get_presence(self):
|
||||||
"""
|
"""
|
||||||
@ -154,7 +161,7 @@ class Chassis(ChassisBase):
|
|||||||
Returns:
|
Returns:
|
||||||
string: Model/part number of chassis
|
string: Model/part number of chassis
|
||||||
"""
|
"""
|
||||||
return self._eeprom.part_number_str()
|
return self._eeprom.get_part_number()
|
||||||
|
|
||||||
def get_serial(self):
|
def get_serial(self):
|
||||||
"""
|
"""
|
||||||
@ -162,7 +169,7 @@ class Chassis(ChassisBase):
|
|||||||
Returns:
|
Returns:
|
||||||
string: Serial number of chassis
|
string: Serial number of chassis
|
||||||
"""
|
"""
|
||||||
return self._eeprom.serial_str()
|
return self._eeprom.get_serial()
|
||||||
|
|
||||||
def get_status(self):
|
def get_status(self):
|
||||||
"""
|
"""
|
||||||
@ -181,7 +188,7 @@ class Chassis(ChassisBase):
|
|||||||
A string containing the MAC address in the format
|
A string containing the MAC address in the format
|
||||||
'XX:XX:XX:XX:XX:XX'
|
'XX:XX:XX:XX:XX:XX'
|
||||||
"""
|
"""
|
||||||
return self._eeprom.base_mac_addr()
|
return self._eeprom.get_base_mac()
|
||||||
|
|
||||||
def get_serial_number(self):
|
def get_serial_number(self):
|
||||||
"""
|
"""
|
||||||
@ -191,7 +198,7 @@ class Chassis(ChassisBase):
|
|||||||
A string containing the hardware serial number for this
|
A string containing the hardware serial number for this
|
||||||
chassis.
|
chassis.
|
||||||
"""
|
"""
|
||||||
return self._eeprom.serial_number_str()
|
return self._eeprom.get_serial_number()
|
||||||
|
|
||||||
def get_system_eeprom_info(self):
|
def get_system_eeprom_info(self):
|
||||||
"""
|
"""
|
||||||
|
@ -17,12 +17,17 @@
|
|||||||
|
|
||||||
|
|
||||||
try:
|
try:
|
||||||
|
import binascii
|
||||||
import os
|
import os
|
||||||
|
import redis
|
||||||
|
import struct
|
||||||
|
from collections import OrderedDict
|
||||||
from sonic_platform_base.sonic_eeprom.eeprom_base import EepromDecoder
|
from sonic_platform_base.sonic_eeprom.eeprom_base import EepromDecoder
|
||||||
from sonic_platform_base.sonic_eeprom.eeprom_tlvinfo import TlvInfoDecoder
|
from sonic_platform_base.sonic_eeprom.eeprom_tlvinfo import TlvInfoDecoder
|
||||||
except ImportError as e:
|
except ImportError as e:
|
||||||
raise ImportError(str(e) + "- required module not found")
|
raise ImportError(str(e) + "- required module not found")
|
||||||
|
|
||||||
|
STATE_DB_INDEX = 6
|
||||||
|
|
||||||
# PSU eeprom fields in format required by EepromDecoder
|
# PSU eeprom fields in format required by EepromDecoder
|
||||||
psu_eeprom_format = [
|
psu_eeprom_format = [
|
||||||
@ -200,13 +205,13 @@ class Eeprom(TlvInfoDecoder):
|
|||||||
|
|
||||||
return (False, None)
|
return (False, None)
|
||||||
|
|
||||||
def serial_number_str(self):
|
def get_serial_number(self):
|
||||||
"""
|
"""
|
||||||
Returns the serial number.
|
Returns the serial number.
|
||||||
"""
|
"""
|
||||||
return self.serial_number
|
return self.serial_number
|
||||||
|
|
||||||
def part_number_str(self):
|
def get_part_number(self):
|
||||||
"""
|
"""
|
||||||
Returns the part number.
|
Returns the part number.
|
||||||
"""
|
"""
|
||||||
@ -222,19 +227,19 @@ class Eeprom(TlvInfoDecoder):
|
|||||||
return int(self.fan_type.encode('hex'), 16)
|
return int(self.fan_type.encode('hex'), 16)
|
||||||
|
|
||||||
# System EEPROM specific methods
|
# System EEPROM specific methods
|
||||||
def base_mac_addr(self):
|
def get_base_mac(self):
|
||||||
"""
|
"""
|
||||||
Returns the base MAC address found in the system EEPROM.
|
Returns the base MAC address found in the system EEPROM.
|
||||||
"""
|
"""
|
||||||
return self.base_mac
|
return self.base_mac
|
||||||
|
|
||||||
def modelstr(self):
|
def get_model(self):
|
||||||
"""
|
"""
|
||||||
Returns the Model name.
|
Returns the Model name.
|
||||||
"""
|
"""
|
||||||
return self.model_str
|
return self.model_str
|
||||||
|
|
||||||
def serial_str(self):
|
def get_serial(self):
|
||||||
"""
|
"""
|
||||||
Returns the servicetag number.
|
Returns the servicetag number.
|
||||||
"""
|
"""
|
||||||
@ -247,3 +252,252 @@ class Eeprom(TlvInfoDecoder):
|
|||||||
found in the system EEPROM.
|
found in the system EEPROM.
|
||||||
"""
|
"""
|
||||||
return self.eeprom_tlv_dict
|
return self.eeprom_tlv_dict
|
||||||
|
|
||||||
|
|
||||||
|
class EepromS6000(EepromDecoder):
|
||||||
|
|
||||||
|
_EEPROM_MAX_LEN = 128
|
||||||
|
|
||||||
|
_BLK_HDR_LEN = 6
|
||||||
|
_BLK_HDR_MAGIC = '\x3a\x29'
|
||||||
|
_BLK_HDR_REVID = 1
|
||||||
|
|
||||||
|
_BLK_CODE_MFG = 0x20
|
||||||
|
_BLK_CODE_SW = 0x1F
|
||||||
|
_BLK_CODE_MAC = 0x21
|
||||||
|
|
||||||
|
_BLK_MFG_FORMAT = [
|
||||||
|
("PPID", 20), ("DPN Rev", 3), ("Service Tag", 7), ("Part Number", 10),
|
||||||
|
("Part Number Rev", 3), ("Mfg Test Results", 2)
|
||||||
|
]
|
||||||
|
|
||||||
|
_BLK_SW_FORMAT = [("Card ID", 4), ("Module ID", 2)]
|
||||||
|
_BLK_MAC_FORMAT = [("Base MAC address", 6)]
|
||||||
|
|
||||||
|
_BLK_INFO = OrderedDict([
|
||||||
|
(_BLK_CODE_MFG, {"name": "MFG BLOCK", "size": 64,
|
||||||
|
"offset": 0x0, "format": _BLK_MFG_FORMAT}),
|
||||||
|
(_BLK_CODE_SW, {"name": "SW BLOCK", "size": 48,
|
||||||
|
"offset": 0x40, "format": _BLK_SW_FORMAT}),
|
||||||
|
(_BLK_CODE_MAC, {"name": "MAC BLOCK", "size": 16,
|
||||||
|
"offset": 0x70, "format": _BLK_MAC_FORMAT})
|
||||||
|
])
|
||||||
|
|
||||||
|
def __init__(self, is_plugin=False):
|
||||||
|
self.eeprom_path = "/sys/bus/i2c/devices/i2c-10/10-0053/eeprom"
|
||||||
|
super(EepromS6000, self).__init__(self.eeprom_path, None, 0, '', True)
|
||||||
|
|
||||||
|
if not is_plugin:
|
||||||
|
self.eeprom_data = self.read_eeprom()
|
||||||
|
|
||||||
|
def _is_valid_block_checksum(self, e):
|
||||||
|
crc = self.compute_dell_crc(e[:-2])
|
||||||
|
return crc == struct.unpack('<H', e[-2:])[0]
|
||||||
|
|
||||||
|
def _is_valid_block(self, e, blk_code):
|
||||||
|
return (e[:2] == self._BLK_HDR_MAGIC
|
||||||
|
and struct.unpack('<H', e[2:4])[0] == self._BLK_INFO[blk_code]["size"]
|
||||||
|
and ord(e[4]) == blk_code
|
||||||
|
and ord(e[5]) == self._BLK_HDR_REVID)
|
||||||
|
|
||||||
|
def _get_eeprom_field(self, e, blk_code, field_name):
|
||||||
|
"""
|
||||||
|
For a field name specified in the EEPROM format, returns the
|
||||||
|
presence of the field and the value for the same.
|
||||||
|
"""
|
||||||
|
blk_start = self._BLK_INFO[blk_code]["offset"]
|
||||||
|
blk_end = blk_start + self._BLK_INFO[blk_code]["size"]
|
||||||
|
if not self._is_valid_block(e[blk_start:blk_end], blk_code):
|
||||||
|
return (False, None)
|
||||||
|
|
||||||
|
field_start = blk_start + self._BLK_HDR_LEN
|
||||||
|
for field in self._BLK_INFO[blk_code]["format"]:
|
||||||
|
field_end = field_start + field[1]
|
||||||
|
if field[0] == field_name:
|
||||||
|
return (True, e[field_start:field_end])
|
||||||
|
field_start = field_end
|
||||||
|
|
||||||
|
return (False, None)
|
||||||
|
|
||||||
|
def decode_eeprom(self, e):
|
||||||
|
"""
|
||||||
|
Decode and print out the contents of the EEPROM.
|
||||||
|
"""
|
||||||
|
print " Field Name Len Value"
|
||||||
|
print "-------------------- --- --------------------"
|
||||||
|
for blk_code in self._BLK_INFO.keys():
|
||||||
|
blk_start = self._BLK_INFO[blk_code]["offset"]
|
||||||
|
blk_end = blk_start + self._BLK_INFO[blk_code]["size"]
|
||||||
|
if not self._is_valid_block(e[blk_start:blk_end], blk_code):
|
||||||
|
print "Invalid Block starting at EEPROM offset %d" % (blk_start)
|
||||||
|
return
|
||||||
|
|
||||||
|
offset = blk_start + self._BLK_HDR_LEN
|
||||||
|
for f in self._BLK_INFO[blk_code]["format"]:
|
||||||
|
if f[0] == "Num MACs" or f[0] == "Module ID":
|
||||||
|
data = str(struct.unpack('<H', e[offset:offset+f[1]])[0])
|
||||||
|
elif f[0] == "Card ID":
|
||||||
|
data = hex(struct.unpack('<I', e[offset:offset+f[1]])[0])
|
||||||
|
elif f[0] == "Base MAC address":
|
||||||
|
data = ":".join([binascii.b2a_hex(T) for T in e[offset:offset+f[1]]]).upper()
|
||||||
|
else:
|
||||||
|
data = e[offset:offset+f[1]]
|
||||||
|
print "{:<20s} {:>3d} {:<s}".format(f[0], f[1], data)
|
||||||
|
offset += f[1]
|
||||||
|
|
||||||
|
if not self._is_valid_block_checksum(e[blk_start:blk_end]):
|
||||||
|
print "(*** block checksum invalid)"
|
||||||
|
|
||||||
|
def read_eeprom(self):
|
||||||
|
"""
|
||||||
|
Read the EEPROM contents.
|
||||||
|
"""
|
||||||
|
return self.read_eeprom_bytes(self._EEPROM_MAX_LEN)
|
||||||
|
|
||||||
|
def read_eeprom_db(self):
|
||||||
|
"""
|
||||||
|
Print out the contents of the EEPROM from database.
|
||||||
|
"""
|
||||||
|
client = redis.Redis(db=STATE_DB_INDEX)
|
||||||
|
db_state = client.hget('EEPROM_INFO|State', 'Initialized')
|
||||||
|
if db_state != '1':
|
||||||
|
return -1
|
||||||
|
|
||||||
|
print " Field Name Len Value"
|
||||||
|
print "-------------------- --- --------------------"
|
||||||
|
for blk_code in self._BLK_INFO.keys():
|
||||||
|
blk_name = self._BLK_INFO[blk_code]["name"]
|
||||||
|
blk_start = self._BLK_INFO[blk_code]["offset"]
|
||||||
|
is_valid = client.hget('EEPROM_INFO|{}'.format(blk_name), 'Valid')
|
||||||
|
if is_valid == '0':
|
||||||
|
print "Invalid Block starting at EEPROM offset %d" % (blk_start)
|
||||||
|
break
|
||||||
|
|
||||||
|
for f in self._BLK_INFO[blk_code]["format"]:
|
||||||
|
data = client.hget('EEPROM_INFO|{}'.format(f[0]), 'Value')
|
||||||
|
print "{:<20s} {:>3d} {:<s}".format(f[0], f[1], data)
|
||||||
|
|
||||||
|
is_checksum_valid = client.hget('EEPROM_INFO|{}'.format(blk_name), 'Checksum_Valid')
|
||||||
|
if is_checksum_valid == '0':
|
||||||
|
print "(*** block checksum invalid)"
|
||||||
|
|
||||||
|
return 0
|
||||||
|
|
||||||
|
def update_eeprom_db(self, e):
|
||||||
|
"""
|
||||||
|
Decode the contents of the EEPROM and update the contents to database
|
||||||
|
"""
|
||||||
|
client = redis.Redis(db=STATE_DB_INDEX)
|
||||||
|
for blk_code in self._BLK_INFO.keys():
|
||||||
|
blk_name = self._BLK_INFO[blk_code]["name"]
|
||||||
|
blk_start = self._BLK_INFO[blk_code]["offset"]
|
||||||
|
blk_end = blk_start + self._BLK_INFO[blk_code]["size"]
|
||||||
|
if not self._is_valid_block(e[blk_start:blk_end], blk_code):
|
||||||
|
client.hset('EEPROM_INFO|{}'.format(blk_name), 'Valid', '0')
|
||||||
|
print "Invalid Block starting at EEPROM offset %d" % (blk_start)
|
||||||
|
break
|
||||||
|
else:
|
||||||
|
client.hset('EEPROM_INFO|{}'.format(blk_name), 'Valid', '1')
|
||||||
|
|
||||||
|
offset = blk_start + self._BLK_HDR_LEN
|
||||||
|
for f in self._BLK_INFO[blk_code]["format"]:
|
||||||
|
if f[0] == "Num MACs" or f[0] == "Module ID":
|
||||||
|
data = str(struct.unpack('<H', e[offset:offset+f[1]])[0])
|
||||||
|
elif f[0] == "Card ID":
|
||||||
|
data = hex(struct.unpack('<I', e[offset:offset+f[1]])[0])
|
||||||
|
elif f[0] == "Base MAC address":
|
||||||
|
data = ":".join([binascii.b2a_hex(T) for T in e[offset:offset+f[1]]]).upper()
|
||||||
|
else:
|
||||||
|
data = e[offset:offset+f[1]]
|
||||||
|
client.hset('EEPROM_INFO|{}'.format(f[0]), 'Value', data)
|
||||||
|
offset += f[1]
|
||||||
|
|
||||||
|
if not self._is_valid_block_checksum(e[blk_start:blk_end]):
|
||||||
|
client.hset('EEPROM_INFO|{}'.format(blk_name), 'Checksum_Valid', '0')
|
||||||
|
else:
|
||||||
|
client.hset('EEPROM_INFO|{}'.format(blk_name), 'Checksum_Valid', '1')
|
||||||
|
|
||||||
|
client.hset('EEPROM_INFO|State', 'Initialized', '1')
|
||||||
|
return 0
|
||||||
|
|
||||||
|
def get_base_mac(self):
|
||||||
|
"""
|
||||||
|
Returns the base MAC address found in the system EEPROM.
|
||||||
|
"""
|
||||||
|
(valid, data) = self._get_eeprom_field(self.eeprom_data,
|
||||||
|
self._BLK_CODE_MAC, "Base MAC address")
|
||||||
|
if valid:
|
||||||
|
return ":".join([binascii.b2a_hex(T) for T in data]).upper()
|
||||||
|
else:
|
||||||
|
return 'NA'
|
||||||
|
|
||||||
|
def get_model(self):
|
||||||
|
"""
|
||||||
|
Returns the Model name.
|
||||||
|
"""
|
||||||
|
return 'S6000'
|
||||||
|
|
||||||
|
def get_part_number(self):
|
||||||
|
"""
|
||||||
|
Returns the part number.
|
||||||
|
"""
|
||||||
|
(valid, data) = self._get_eeprom_field(self.eeprom_data,
|
||||||
|
self._BLK_CODE_MFG, "Part Number")
|
||||||
|
if valid:
|
||||||
|
return data
|
||||||
|
else:
|
||||||
|
return 'NA'
|
||||||
|
|
||||||
|
def get_serial(self):
|
||||||
|
"""
|
||||||
|
Returns the Service tag.
|
||||||
|
"""
|
||||||
|
(valid, data) = self._get_eeprom_field(self.eeprom_data,
|
||||||
|
self._BLK_CODE_MFG, "Service Tag")
|
||||||
|
if valid:
|
||||||
|
return data
|
||||||
|
else:
|
||||||
|
return 'NA'
|
||||||
|
|
||||||
|
def get_serial_number(self):
|
||||||
|
"""
|
||||||
|
Returns the serial number.
|
||||||
|
"""
|
||||||
|
(valid, data) = self._get_eeprom_field(self.eeprom_data,
|
||||||
|
self._BLK_CODE_MFG, "PPID")
|
||||||
|
if valid:
|
||||||
|
return data
|
||||||
|
else:
|
||||||
|
return 'NA'
|
||||||
|
|
||||||
|
# EEPROM Plugin specific methods
|
||||||
|
def is_checksum_valid(self, e):
|
||||||
|
# Checksum is already calculated before
|
||||||
|
return (True, 0)
|
||||||
|
|
||||||
|
def mgmtaddrstr(self, e):
|
||||||
|
"""
|
||||||
|
Returns the base MAC address.
|
||||||
|
"""
|
||||||
|
(valid, data) = self._get_eeprom_field(e, self._BLK_CODE_MAC, "Base MAC address")
|
||||||
|
if valid:
|
||||||
|
return ":".join([binascii.b2a_hex(T) for T in data]).upper()
|
||||||
|
else:
|
||||||
|
return 'NA'
|
||||||
|
|
||||||
|
def modelstr(self, e):
|
||||||
|
"""
|
||||||
|
Returns the Model name.
|
||||||
|
"""
|
||||||
|
return 'S6000'
|
||||||
|
|
||||||
|
def serial_number_str(self, e):
|
||||||
|
"""
|
||||||
|
Returns the Service Tag.
|
||||||
|
"""
|
||||||
|
(valid, data) = self._get_eeprom_field(e, self._BLK_CODE_MFG, "Service Tag")
|
||||||
|
|
||||||
|
if valid:
|
||||||
|
return data
|
||||||
|
else:
|
||||||
|
return 'NA'
|
||||||
|
@ -186,7 +186,7 @@ class Fan(FanBase):
|
|||||||
string: Part number of Fan
|
string: Part number of Fan
|
||||||
"""
|
"""
|
||||||
if not self.is_psu_fan:
|
if not self.is_psu_fan:
|
||||||
return self.eeprom.part_number_str()
|
return self.eeprom.get_part_number()
|
||||||
else:
|
else:
|
||||||
return 'NA'
|
return 'NA'
|
||||||
|
|
||||||
@ -199,7 +199,7 @@ class Fan(FanBase):
|
|||||||
"""
|
"""
|
||||||
# Sample Serial number format "US-01234D-54321-25A-0123-A00"
|
# Sample Serial number format "US-01234D-54321-25A-0123-A00"
|
||||||
if not self.is_psu_fan:
|
if not self.is_psu_fan:
|
||||||
return self.eeprom.serial_number_str()
|
return self.eeprom.get_serial_number()
|
||||||
else:
|
else:
|
||||||
return 'NA'
|
return 'NA'
|
||||||
|
|
||||||
|
@ -146,7 +146,7 @@ class Psu(PsuBase):
|
|||||||
Returns:
|
Returns:
|
||||||
string: Part number of PSU
|
string: Part number of PSU
|
||||||
"""
|
"""
|
||||||
return self.eeprom.part_number_str()
|
return self.eeprom.get_part_number()
|
||||||
|
|
||||||
def get_serial(self):
|
def get_serial(self):
|
||||||
"""
|
"""
|
||||||
@ -156,7 +156,7 @@ class Psu(PsuBase):
|
|||||||
string: Serial number of PSU
|
string: Serial number of PSU
|
||||||
"""
|
"""
|
||||||
# Sample Serial number format "US-01234D-54321-25A-0123-A00"
|
# Sample Serial number format "US-01234D-54321-25A-0123-A00"
|
||||||
return self.eeprom.serial_number_str()
|
return self.eeprom.get_serial_number()
|
||||||
|
|
||||||
def get_status(self):
|
def get_status(self):
|
||||||
"""
|
"""
|
||||||
|
Reference in New Issue
Block a user