2
0
mirror of https://opendev.org/x/pyghmi synced 2026-05-16 19:34:21 +00:00

Fix expired weakref reference exception

there is a global cache in sdr.py. Sensors and FRUs are cached here. So if ipmicmd is reinitialized, Sensors in cache still ref to old ipmicmd, then it will throw expired weakref reference exception when call these cached Sensors. Current changes will still cache Sensors and FRUs, but when call cached sensors every time, we pass in current using ipmicmd.

Change-Id: I976760d8cb0a7f78a4f6468c52212649790dbbc2
This commit is contained in:
Jarrod Johnson
2021-08-12 11:25:14 -04:00
committed by luyf5
parent 1cd47f71b2
commit 6d56f21772
3 changed files with 21 additions and 17 deletions
+3 -2
View File
@@ -759,7 +759,7 @@ class Command(object):
if 'error' in rsp:
raise exc.IpmiException(rsp['error'], rsp['code'])
return self._sdr.sensors[sensor].decode_sensor_reading(
rsp['data'])
self, rsp['data'])
self.oem_init()
return self._oem.get_sensor_reading(sensorname)
@@ -980,7 +980,8 @@ class Command(object):
if rsp['code'] == 203: # Sensor does not exist, optional dev
continue
raise exc.IpmiException(rsp['error'], code=rsp['code'])
yield self._sdr.sensors[sensor].decode_sensor_reading(rsp['data'])
yield self._sdr.sensors[sensor].\
decode_sensor_reading(self, rsp['data'])
self.oem_init()
for reading in self._oem.get_sensor_data():
yield reading
+8 -4
View File
@@ -305,6 +305,10 @@ class LenovoFirmwareConfig(object):
readonly = setting.get('gray-if')
if readonly:
readonly = _convert_syntax(readonly)
else:
access = setting.get('access')
if access == 'readonly':
readonly = 'true'
possible = []
current = None
default = None
@@ -485,10 +489,6 @@ class LenovoFirmwareConfig(object):
for option in options.keys():
if options[option]['new_value'] is None:
continue
if options[option]['current'] == options[option]['new_value']:
continue
if options[option]['pending'] == options[option]['new_value']:
continue
if options[option]['readonly']:
errstr = '{0} is read only'.format(option)
if options[option]['readonly_why']:
@@ -496,6 +496,10 @@ class LenovoFirmwareConfig(object):
','.join(sorted(options[option]['readonly_why'])))
errstr += ea
raise pygexc.InvalidParameterValue(errstr)
if options[option]['current'] == options[option]['new_value']:
continue
if options[option]['pending'] == options[option]['new_value']:
continue
if isinstance(options[option]['new_value'], six.string_types):
# Coerce a simple string parameter to the expected list format
options[option]['new_value'] = [options[option]['new_value']]
+10 -11
View File
@@ -288,7 +288,7 @@ class SDREntry(object):
external code to pay attention to this class.
"""
def __init__(self, entrybytes, ipmicmd, reportunsupported=False,
def __init__(self, entrybytes, reportunsupported=False,
mfg_id=0, prod_id=0):
self.mfg_id = mfg_id
self.prod_id = prod_id
@@ -296,7 +296,6 @@ class SDREntry(object):
# moment
self.readable = True
self.reportunsupported = reportunsupported
self.ipmicmd = ipmicmd
if entrybytes[2] != 0x51:
# only recognize '1.5', the only version defined at time of writing
raise NotImplementedError
@@ -478,7 +477,7 @@ class SDREntry(object):
health = const.Health.Warning
return desc, health
def decode_sensor_reading(self, reading):
def decode_sensor_reading(self, ipmicmd, reading):
numeric = None
output = {
'name': self.sensor_name,
@@ -498,8 +497,8 @@ class SDREntry(object):
if numeric is not None:
lowerbound = numeric - (0.5 + (self.tolerance / 2.0))
upperbound = numeric + (0.5 + (self.tolerance / 2.0))
lowerbound = self.decode_value(lowerbound)
upperbound = self.decode_value(upperbound)
lowerbound = self.decode_value(ipmicmd, lowerbound)
upperbound = self.decode_value(ipmicmd, upperbound)
output['value'] = (lowerbound + upperbound) / 2.0
output['imprecision'] = output['value'] - lowerbound
discrete = False
@@ -555,13 +554,13 @@ class SDREntry(object):
output['state_ids'].append(self.assert_trap_value(6))
return SensorReading(output, self.unit_suffix)
def _set_tmp_formula(self, value):
rsp = self.ipmicmd.raw_command(netfn=4, command=0x23,
data=(self.sensor_number, value))
def _set_tmp_formula(self, ipmicmd, value):
rsp = ipmicmd.raw_command(netfn=4, command=0x23,
data=(self.sensor_number, value))
# skip next reading field, not used in on-demand situation
self.decode_formula(rsp['data'][1:])
def decode_value(self, value):
def decode_value(self, ipmicmd, value):
# Take the input value and return meaningful value
linearization = self.linearization
if linearization > 11: # direct calling code to get factors
@@ -571,7 +570,7 @@ class SDREntry(object):
# fashion. However for now opt for retrieving rows as needed
# rather than tracking all that information for a relatively
# rare behavior
self._set_tmp_formula(value)
self._set_tmp_formula(ipmicmd, value)
linearization = 0
# time to compute the pre-linearization value.
decoded = float((value * self.m + self.b)
@@ -834,7 +833,7 @@ class SDR(object):
yield number
def add_sdr(self, sdrbytes):
newent = SDREntry(sdrbytes, self.ipmicmd, False, self.mfg_id,
newent = SDREntry(sdrbytes, False, self.mfg_id,
self.prod_id)
if newent.sdrtype == TYPE_SENSOR:
id = '{0}.{1}.{2}'.format(