Skip to content

Commit d08fcc9

Browse files
authored
[BFN] Updated syseeprom platform plugin to use onie-eeprom (#10556)
* Align system eeprom info with ONIE * revert linked sonic_platform implementation * refactor into one class * refactor after review
1 parent d9c9c70 commit d08fcc9

File tree

4 files changed

+336
-88
lines changed

4 files changed

+336
-88
lines changed

platform/barefoot/sonic-platform-modules-bfn-montara/sonic_platform/chassis.py

+13-19
Original file line numberDiff line numberDiff line change
@@ -13,8 +13,8 @@
1313
from sonic_platform.psu import psu_list_get
1414
from sonic_platform.fan_drawer import fan_drawer_list_get
1515
from sonic_platform.thermal import thermal_list_get
16-
from eeprom import Eeprom
17-
from platform_utils import file_create
16+
from sonic_platform.platform_utils import file_create
17+
from sonic_platform.eeprom import Eeprom
1818

1919
from sonic_platform.platform_thrift_client import pltfm_mgr_ready
2020
from sonic_platform.platform_thrift_client import thrift_try
@@ -40,7 +40,10 @@ class Chassis(ChassisBase):
4040
def __init__(self):
4141
ChassisBase.__init__(self)
4242

43-
self.__eeprom = None
43+
self._eeprom = Eeprom()
44+
self.__tlv_bin_eeprom = self._eeprom.get_raw_data()
45+
self.__tlv_dict_eeprom = self._eeprom.get_data()
46+
4447
self.__fan_drawers = None
4548
self.__fan_list = None
4649
self.__thermals = None
@@ -57,16 +60,6 @@ def __init__(self):
5760
file_create(config_dict['handlers']['file']['filename'], '646')
5861
logging.config.dictConfig(config_dict)
5962

60-
@property
61-
def _eeprom(self):
62-
if self.__eeprom is None:
63-
self.__eeprom = Eeprom()
64-
return self.__eeprom
65-
66-
@_eeprom.setter
67-
def _eeprom(self, value):
68-
pass
69-
7063
@property
7164
def _fan_drawer_list(self):
7265
if self.__fan_drawers is None:
@@ -152,7 +145,7 @@ def get_name(self):
152145
Returns:
153146
string: The name of the chassis
154147
"""
155-
return self._eeprom.modelstr()
148+
return self._eeprom.modelstr(self.__tlv_bin_eeprom)
156149

157150
def get_presence(self):
158151
"""
@@ -168,23 +161,24 @@ def get_model(self):
168161
Returns:
169162
string: Model/part number of chassis
170163
"""
171-
return self._eeprom.part_number_str()
164+
return self._eeprom.part_number_str(self.__tlv_bin_eeprom)
172165

173166
def get_serial(self):
174167
"""
175168
Retrieves the serial number of the chassis (Service tag)
176169
Returns:
177170
string: Serial number of chassis
178171
"""
179-
return self._eeprom.serial_number_str()
172+
return self._eeprom.serial_number_str(self.__tlv_bin_eeprom)
180173

181174
def get_revision(self):
182175
"""
183176
Retrieves the revision number of the chassis (Service tag)
184177
Returns:
185178
string: Revision number of chassis
186179
"""
187-
return self._eeprom.revision_str()
180+
return self.__tlv_dict_eeprom.get(
181+
"0x{:X}".format(Eeprom._TLV_CODE_LABEL_REVISION), 'N/A')
188182

189183
def get_sfp(self, index):
190184
"""
@@ -225,7 +219,7 @@ def get_base_mac(self):
225219
A string containing the MAC address in the format
226220
'XX:XX:XX:XX:XX:XX'
227221
"""
228-
return self._eeprom.base_mac_addr()
222+
return self._eeprom.base_mac_addr(self.__tlv_bin_eeprom)
229223

230224
def get_system_eeprom_info(self):
231225
"""
@@ -236,7 +230,7 @@ def get_system_eeprom_info(self):
236230
OCP ONIE TlvInfo EEPROM format and values are their corresponding
237231
values.
238232
"""
239-
return self._eeprom.system_eeprom_info()
233+
return self.__tlv_dict_eeprom
240234

241235
def __get_transceiver_change_event(self, timeout=0):
242236
forever = False

platform/barefoot/sonic-platform-modules-bfn-montara/sonic_platform/eeprom.py

+86-69
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,8 @@
22
import os
33
import sys
44
import datetime
5-
import re
5+
import logging
6+
import logging.config
67

78
sys.path.append(os.path.dirname(__file__))
89

@@ -13,13 +14,15 @@
1314

1415
from sonic_platform_base.sonic_eeprom import eeprom_base
1516
from sonic_platform_base.sonic_eeprom import eeprom_tlvinfo
16-
from platform_utils import file_create
1717

18-
from platform_thrift_client import thrift_try
18+
from sonic_py_common import device_info
19+
20+
from sonic_platform.platform_thrift_client import thrift_try
21+
from sonic_platform.platform_utils import file_create
22+
1923
except ImportError as e:
2024
raise ImportError (str(e) + "- required module not found")
2125

22-
2326
_platform_eeprom_map = {
2427
"prod_name" : ("Product Name", "0x21", 12),
2528
"odm_pcba_part_num" : ("Part Number", "0x22", 13),
@@ -44,25 +47,55 @@ class Eeprom(eeprom_tlvinfo.TlvInfoDecoder):
4447
def __init__(self):
4548
file_create(_EEPROM_SYMLINK, '646')
4649
file_create(_EEPROM_STATUS, '646')
47-
with open(_EEPROM_STATUS, 'w') as f:
48-
f.write("initializing..")
50+
super(Eeprom, self).__init__(_EEPROM_SYMLINK, 0, _EEPROM_STATUS, True)
4951

50-
self.eeprom_path = _EEPROM_SYMLINK
51-
super(Eeprom, self).__init__(self.eeprom_path, 0, _EEPROM_STATUS, True)
52-
53-
def sys_eeprom_get(client):
54-
return client.pltfm_mgr.pltfm_mgr_sys_eeprom_get()
52+
self._eeprom_bin = bytearray()
53+
self.report_status("initializing..")
5554
try:
56-
platform_eeprom = thrift_try(sys_eeprom_get)
57-
except Exception:
58-
raise RuntimeError("eeprom.py: Initialization failed")
55+
try:
56+
if device_info.get_platform() in ["x86_64-accton_as9516_32d-r0",
57+
"x86_64-accton_as9516bf_32d-r0"]:
58+
def tlv_eeprom_get(client):
59+
return client.pltfm_mgr.pltfm_mgr_tlv_eeprom_get()
60+
try:
61+
self._eeprom_bin = bytearray.fromhex(
62+
thrift_try(tlv_eeprom_get, 1).raw_content_hex)
63+
except TApplicationException as e:
64+
raise RuntimeError("api is not supported")
65+
except Exception as e:
66+
self._eeprom_bin = bytearray.fromhex(
67+
thrift_try(tlv_eeprom_get).raw_content_hex)
68+
else:
69+
raise RuntimeError("platform is not supported")
70+
71+
except RuntimeError as e:
72+
logging.warning("Tlv eeprom fetching failed: %s, using OpenBMC" % (str(e)))
73+
74+
def sys_eeprom_get(client):
75+
return client.pltfm_mgr.pltfm_mgr_sys_eeprom_get()
76+
77+
eeprom_params = self.platfrom_eeprom_to_params(thrift_try(sys_eeprom_get))
78+
stdout_stream = sys.stdout
79+
sys.stdout = open(os.devnull, 'w')
80+
self._eeprom_bin = self.set_eeprom(self._eeprom_bin, [eeprom_params])
81+
sys.stdout.close()
82+
sys.stdout = stdout_stream
83+
try:
84+
self.write_eeprom(self._eeprom_bin)
85+
self.report_status("ok")
86+
except IOError as e:
87+
logging.error("Failed to write eeprom: %s" % (str(e)))
5988

60-
self.__eeprom_init(platform_eeprom)
89+
except Exception as e:
90+
logging.error("eeprom.py: Initialization failed: %s" % (str(e)))
91+
raise RuntimeError("eeprom.py: Initialization failed: %s" % (str(e)))
6192

62-
def __eeprom_init(self, platform_eeprom):
63-
with open(_EEPROM_STATUS, 'w') as f:
64-
f.write("ok")
93+
self._system_eeprom_info = dict()
94+
visitor = EepromContentVisitor(self._system_eeprom_info)
95+
self.visit_eeprom(self._eeprom_bin, visitor)
6596

97+
@staticmethod
98+
def platfrom_eeprom_to_params(platform_eeprom):
6699
eeprom_params = ""
67100
for attr, val in platform_eeprom.__dict__.items():
68101
if val is None:
@@ -86,57 +119,41 @@ def __eeprom_init(self, platform_eeprom):
86119
if len(eeprom_params) > 0:
87120
eeprom_params += ","
88121
eeprom_params += "{0:s}={1:s}".format(elem[1], value)
122+
return eeprom_params
89123

90-
orig_stdout = sys.stdout
91-
sys.stdout = StringIO()
92-
try:
93-
eeprom_data = eeprom_tlvinfo.TlvInfoDecoder.set_eeprom(self, "", [eeprom_params])
94-
finally:
95-
decode_output = sys.stdout.getvalue()
96-
sys.stdout = orig_stdout
97-
98-
eeprom_base.EepromDecoder.write_eeprom(self, eeprom_data)
99-
self.__eeprom_tlv_dict = self.__parse_output(decode_output)
124+
def get_data(self):
125+
return self._system_eeprom_info
100126

101-
def __parse_output(self, decode_output):
102-
EEPROM_DECODE_HEADLINES = 6
103-
lines = decode_output.replace('\0', '').split('\n')
104-
lines = lines[EEPROM_DECODE_HEADLINES:]
105-
res = dict()
106-
107-
for line in lines:
108-
try:
109-
# match whitespace-separated tag hex, length and value (value is mathced with its whitespaces)
110-
match = re.search('(0x[0-9a-fA-F]{2})([\s]+[\S]+[\s]+)([\S]+[\s]*[\S]*)', line)
111-
if match is not None:
112-
code = match.group(1)
113-
value = match.group(3).rstrip('\0')
114-
res[code] = value
115-
except Exception:
116-
pass
117-
return res
118-
119-
def __tlv_get(self, code):
120-
return self.__eeprom_tlv_dict.get("0x{:X}".format(code), 'N/A')
121-
122-
def system_eeprom_info(self):
123-
return self.__eeprom_tlv_dict
124-
125-
def serial_number_str(self):
126-
return self.__tlv_get(self._TLV_CODE_SERIAL_NUMBER)
127-
128-
def serial_str(self):
129-
return self.serial_number_str()
130-
131-
def base_mac_addr(self):
132-
return self.__tlv_get(self._TLV_CODE_MAC_BASE)
133-
134-
def part_number_str(self):
135-
return self.__tlv_get(self._TLV_CODE_PART_NUMBER)
136-
137-
def modelstr(self):
138-
return self.__tlv_get(self._TLV_CODE_PRODUCT_NAME)
139-
140-
def revision_str(self):
141-
return self.__tlv_get(self._TLV_CODE_LABEL_REVISION)
127+
def get_raw_data(self):
128+
return self._eeprom_bin
142129

130+
def report_status(self, status):
131+
status_file = None
132+
try:
133+
status_file = open(_EEPROM_STATUS, "w")
134+
status_file.write(status)
135+
except IOError as e:
136+
logging.error("Failed to report state: %s" % (str(e)))
137+
finally:
138+
if status_file is not None:
139+
status_file.close()
140+
141+
class EepromContentVisitor(eeprom_tlvinfo.EepromDefaultVisitor):
142+
def __init__(self, content_dict):
143+
self.content_dict = content_dict
144+
145+
def visit_tlv(self, name, code, length, value):
146+
if code != Eeprom._TLV_CODE_VENDOR_EXT:
147+
self.content_dict["0x{:X}".format(code)] = value.rstrip('\0')
148+
else:
149+
if value:
150+
value = value.rstrip('\0')
151+
if value:
152+
code = "0x{:X}".format(code)
153+
if code not in self.content_dict:
154+
self.content_dict[code] = [value]
155+
else:
156+
self.content_dict[code].append(value)
157+
158+
def set_error(self, error):
159+
logging.error("EepromContentVisitor error: %s" % (str(error)))

0 commit comments

Comments
 (0)