[Mellanox] Refactor SFP related platform API and plugins with new SDK API (#5326)

Refactor SFP reset, low power get/set API, and plugins with new SDK SX APIs. Previously they were calling SDK SXD APIs which have glibc dependency because of shared memory usage.

Remove implementation "set_power_override", "tx_disable_channel", "tx_disable" which using SXD APIs, once related SDK SX API available, will add them back based on new SDK SX APIs.
This commit is contained in:
Kebo Liu 2020-09-12 04:23:23 +08:00 committed by GitHub
parent c44279a365
commit 72ec212fa7
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
4 changed files with 255 additions and 373 deletions

View File

@ -1,43 +1,51 @@
#!/usr/bin/env python #!/usr/bin/env python
"""
This utility get the power mode of a given module.
"""
import sys, errno import sys
import os import errno
from python_sdk_api.sxd_api import *
from python_sdk_api.sx_api import * from python_sdk_api.sx_api import *
def mgmt_phy_mod_pwr_attr_get(handle, module_id, power_attr_type):
sx_mgmt_phy_mod_pwr_attr_p = new_sx_mgmt_phy_mod_pwr_attr_t_p()
sx_mgmt_phy_mod_pwr_attr = sx_mgmt_phy_mod_pwr_attr_t()
sx_mgmt_phy_mod_pwr_attr.power_attr_type = power_attr_type
sx_mgmt_phy_mod_pwr_attr_t_p_assign(sx_mgmt_phy_mod_pwr_attr_p, sx_mgmt_phy_mod_pwr_attr)
try:
rc = sx_mgmt_phy_mod_pwr_attr_get(handle, module_id, sx_mgmt_phy_mod_pwr_attr_p)
assert SX_STATUS_SUCCESS == rc, "sx_mgmt_phy_mod_pwr_attr_get failed"
sx_mgmt_phy_mod_pwr_attr = sx_mgmt_phy_mod_pwr_attr_t_p_value(sx_mgmt_phy_mod_pwr_attr_p)
pwr_mode_attr = sx_mgmt_phy_mod_pwr_attr.pwr_mode_attr
return pwr_mode_attr.admin_pwr_mode_e, pwr_mode_attr.oper_pwr_mode_e
finally:
delete_sx_mgmt_phy_mod_pwr_attr_t_p(sx_mgmt_phy_mod_pwr_attr_p)
# Check if SFP port number is provided # Check if SFP port number is provided
if len(sys.argv) < 2: if len(sys.argv) < 2:
print "SFP module number is missed." print("SFP module number is missed.")
print "Usage: sfplpmget.py <SFP module>" print("Usage: sfplpmget.py <SFP module>")
sys.exit(errno.EINVAL) sys.exit(errno.EINVAL)
# Init SDK API # Init SDK API
rc, handle = sx_api_open(None) rc, handle = sx_api_open(None)
if (rc != SX_STATUS_SUCCESS): if (rc != SX_STATUS_SUCCESS):
print "Failed to open api handle.\nPlease check that SDK is running." print("Failed to open api handle.\nPlease check that SDK is running.")
sys.exit(errno.EACCES)
pid = os.getpid()
rc = sxd_access_reg_init(pid, None, 0)
if (rc != 0):
print "Failed to initializing register access.\nPlease check that SDK is running."
sys.exit(errno.EACCES) sys.exit(errno.EACCES)
# Get SFP module number # Get SFP module number
sfp_module = int(sys.argv[1]) - 1 sfp_module = int(sys.argv[1]) - 1
# Get MCION admin_pwr_mode, oper_pwr_mode = mgmt_phy_mod_pwr_attr_get(handle, sfp_module, SX_MGMT_PHY_MOD_PWR_ATTR_PWR_MODE_E)
mcion = ku_mcion_reg()
mcion.module = sfp_module
meta = sxd_reg_meta_t()
meta.dev_id = 1
meta.swid = 0
meta.access_cmd = SXD_ACCESS_CMD_GET
rc = sxd_access_reg_mcion(mcion, meta, 1, None, None) lpm_status = None
assert rc == SXD_STATUS_SUCCESS, "sxd_access_reg_mcion failed, rc = %d" % rc if oper_pwr_mode == SX_MGMT_PHY_MOD_PWR_MODE_HIGH_E:
lpm_status = False
elif oper_pwr_mode == SX_MGMT_PHY_MOD_PWR_MODE_LOW_E:
lpm_status = True
else:
print("LPM UNKNOWN")
# Get low power mode status
lpm_mask = 1 << 8
lpm_status = (lpm_mask & mcion.module_status_bits) != 0
print "LPM ON" if lpm_status else "LPM OFF" print "LPM ON" if lpm_status else "LPM OFF"
sx_api_close(handle)

View File

@ -1,23 +1,17 @@
#!/usr/bin/env python #!/usr/bin/env python
"""
This utility set the power mode of a given module.
"""
import sys, errno import sys
import os import errno
from python_sdk_api.sxd_api import *
from python_sdk_api.sx_api import * from python_sdk_api.sx_api import *
REGISTER_NUM = 1
SXD_LOG_VERBOSITY_LEVEL = 0
DEVICE_ID = 1 DEVICE_ID = 1
SWITCH_ID = 0 SWITCH_ID = 0
SX_PORT_ATTR_ARR_SIZE = 64 SX_PORT_ATTR_ARR_SIZE = 64
PMAOS_ASE = 1
PMAOS_EE = 1
PMAOS_E = 2
PMAOS_RST = 0
PMAOS_ENABLE = 1
PMAOS_DISABLE = 2
PORT_TYPE_CPU = 4 PORT_TYPE_CPU = 4
PORT_TYPE_NVE = 8 PORT_TYPE_NVE = 8
PORT_TYPE_OFFSET = 28 PORT_TYPE_OFFSET = 28
@ -36,7 +30,7 @@ def is_port_admin_status_up(log_port):
admin_state_p = new_sx_port_admin_state_t_p() admin_state_p = new_sx_port_admin_state_t_p()
module_state_p = new_sx_port_module_state_t_p() module_state_p = new_sx_port_module_state_t_p()
rc = sx_api_port_state_get(handle, log_port, oper_state_p, admin_state_p, module_state_p) rc = sx_api_port_state_get(handle, log_port, oper_state_p, admin_state_p, module_state_p)
assert rc == SXD_STATUS_SUCCESS, "sx_api_port_state_get failed, rc = %d" % rc assert rc == SX_STATUS_SUCCESS, "sx_api_port_state_get failed, rc = %d" % rc
admin_state = sx_port_admin_state_t_p_value(admin_state_p) admin_state = sx_port_admin_state_t_p_value(admin_state_p)
if admin_state == SX_PORT_ADMIN_STATUS_UP: if admin_state == SX_PORT_ADMIN_STATUS_UP:
@ -54,116 +48,109 @@ def get_log_ports(handle, sfp_module):
port_cnt_p = new_uint32_t_p() port_cnt_p = new_uint32_t_p()
uint32_t_p_assign(port_cnt_p, SX_PORT_ATTR_ARR_SIZE) uint32_t_p_assign(port_cnt_p, SX_PORT_ATTR_ARR_SIZE)
rc = sx_api_port_device_get(handle, DEVICE_ID , SWITCH_ID, port_attributes_list, port_cnt_p) rc = sx_api_port_device_get(handle, DEVICE_ID, SWITCH_ID, port_attributes_list, port_cnt_p)
assert rc == SX_STATUS_SUCCESS, "sx_api_port_device_get failed, rc = %d" % rc assert rc == SX_STATUS_SUCCESS, "sx_api_port_device_get failed, rc = %d" % rc
port_cnt = uint32_t_p_value(port_cnt_p) port_cnt = uint32_t_p_value(port_cnt_p)
log_port_list = [] log_port_list = []
for i in range(0, port_cnt): for i in range(0, port_cnt):
port_attributes = sx_port_attributes_t_arr_getitem(port_attributes_list, i) port_attributes = sx_port_attributes_t_arr_getitem(port_attributes_list, i)
if is_nve(int(port_attributes.log_port)) == False \ if not is_nve(int(port_attributes.log_port)) \
and is_cpu(int(port_attributes.log_port)) == False \ and not is_cpu(int(port_attributes.log_port)) \
and port_attributes.port_mapping.module_port == sfp_module \ and port_attributes.port_mapping.module_port == sfp_module \
and is_port_admin_status_up(port_attributes.log_port): and is_port_admin_status_up(port_attributes.log_port):
log_port_list.append(port_attributes.log_port) log_port_list.append(port_attributes.log_port)
return log_port_list return log_port_list
def init_sx_meta_data(): def mgmt_phy_mod_pwr_attr_set(handle, module_id, power_attr_type, admin_pwr_mode):
meta = sxd_reg_meta_t() sx_mgmt_phy_mod_pwr_attr = sx_mgmt_phy_mod_pwr_attr_t()
meta.dev_id = DEVICE_ID sx_mgmt_phy_mod_pwr_mode_attr = sx_mgmt_phy_mod_pwr_mode_attr_t()
meta.swid = SWITCH_ID sx_mgmt_phy_mod_pwr_attr.power_attr_type = power_attr_type
return meta sx_mgmt_phy_mod_pwr_mode_attr.admin_pwr_mode_e = admin_pwr_mode
sx_mgmt_phy_mod_pwr_attr.pwr_mode_attr = sx_mgmt_phy_mod_pwr_mode_attr
sx_mgmt_phy_mod_pwr_attr_p = new_sx_mgmt_phy_mod_pwr_attr_t_p()
sx_mgmt_phy_mod_pwr_attr_t_p_assign(sx_mgmt_phy_mod_pwr_attr_p, sx_mgmt_phy_mod_pwr_attr)
try:
rc = sx_mgmt_phy_mod_pwr_attr_set(handle, SX_ACCESS_CMD_SET, module_id, sx_mgmt_phy_mod_pwr_attr_p)
assert SX_STATUS_SUCCESS == rc, "sx_mgmt_phy_mod_pwr_attr_set failed"
finally:
delete_sx_mgmt_phy_mod_pwr_attr_t_p(sx_mgmt_phy_mod_pwr_attr_p)
def set_sfp_admin_status(sfp_module, admin_status): def mgmt_phy_mod_pwr_attr_get(handle, module_id, power_attr_type):
# Get PMAOS sx_mgmt_phy_mod_pwr_attr_p = new_sx_mgmt_phy_mod_pwr_attr_t_p()
pmaos = ku_pmaos_reg() sx_mgmt_phy_mod_pwr_attr = sx_mgmt_phy_mod_pwr_attr_t()
pmaos.module = sfp_module sx_mgmt_phy_mod_pwr_attr.power_attr_type = power_attr_type
meta = init_sx_meta_data() sx_mgmt_phy_mod_pwr_attr_t_p_assign(sx_mgmt_phy_mod_pwr_attr_p, sx_mgmt_phy_mod_pwr_attr)
meta.access_cmd = SXD_ACCESS_CMD_GET try:
rc = sxd_access_reg_pmaos(pmaos, meta, REGISTER_NUM, None, None) rc = sx_mgmt_phy_mod_pwr_attr_get(handle, module_id, sx_mgmt_phy_mod_pwr_attr_p)
assert rc == SXD_STATUS_SUCCESS, "sxd_access_reg_pmaos failed, rc = %d" % rc assert SX_STATUS_SUCCESS == rc, "sx_mgmt_phy_mod_pwr_attr_get failed"
sx_mgmt_phy_mod_pwr_attr = sx_mgmt_phy_mod_pwr_attr_t_p_value(sx_mgmt_phy_mod_pwr_attr_p)
pwr_mode_attr = sx_mgmt_phy_mod_pwr_attr.pwr_mode_attr
return pwr_mode_attr.admin_pwr_mode_e, pwr_mode_attr.oper_pwr_mode_e
finally:
delete_sx_mgmt_phy_mod_pwr_attr_t_p(sx_mgmt_phy_mod_pwr_attr_p)
# Set admin status to PMAOS
pmaos.ase = PMAOS_ASE def pwr_attr_set(handle, module_id, ports, attr_type, power_mode):
pmaos.ee = PMAOS_EE # Check if the module already works in the same mode
pmaos.e = PMAOS_E admin_pwr_mode, oper_pwr_mode = mgmt_phy_mod_pwr_attr_get(handle, module_id, attr_type)
pmaos.rst = PMAOS_RST if (power_mode == SX_MGMT_PHY_MOD_PWR_MODE_LOW_E and oper_pwr_mode == SX_MGMT_PHY_MOD_PWR_MODE_LOW_E) \
if admin_status == SX_PORT_ADMIN_STATUS_DOWN: or (power_mode == SX_MGMT_PHY_MOD_PWR_MODE_AUTO_E and admin_pwr_mode == SX_MGMT_PHY_MOD_PWR_MODE_AUTO_E):
pmaos.admin_status = PMAOS_DISABLE return
try:
# Bring the port down
for port in ports:
set_port_admin_status_by_log_port(handle, port, SX_PORT_ADMIN_STATUS_DOWN)
# Set the desired power mode
mgmt_phy_mod_pwr_attr_set(handle, module_id, attr_type, power_mode)
# Bring the port up
finally:
for port in ports:
set_port_admin_status_by_log_port(handle, port, SX_PORT_ADMIN_STATUS_UP)
def set_lpmode(handle, cmd, module_id):
# Construct the port module map.
log_port_list = get_log_ports(handle, module_id)
if cmd == "enable":
pwr_attr_set(handle, module_id, log_port_list, SX_MGMT_PHY_MOD_PWR_ATTR_PWR_MODE_E, SX_MGMT_PHY_MOD_PWR_MODE_LOW_E)
print("Enabled low power mode for module [%d]" % module_id)
elif cmd == "disable":
pwr_attr_set(handle, module_id, log_port_list, SX_MGMT_PHY_MOD_PWR_ATTR_PWR_MODE_E, SX_MGMT_PHY_MOD_PWR_MODE_AUTO_E)
print("Disabled low power mode for module [%d]" % module_id)
else: else:
pmaos.admin_status = PMAOS_ENABLE print("Error: Invalid command")
sys.exit(0)
meta.access_cmd = SXD_ACCESS_CMD_SET
rc = sxd_access_reg_pmaos(pmaos, meta, REGISTER_NUM, None, None)
assert rc == SXD_STATUS_SUCCESS, "sxd_access_reg_pmaos failed, rc = %d" % rc
def set_sfp_lpmode(sfp_module, lpm_enable):
# Get PMMP
pmmp = ku_pmmp_reg()
pmmp.module = sfp_module
meta = init_sx_meta_data()
meta.access_cmd = SXD_ACCESS_CMD_GET
rc = sxd_access_reg_pmmp(pmmp, meta, REGISTER_NUM, None, None)
assert rc == SXD_STATUS_SUCCESS, "sxd_access_reg_pmmp failed, rc = %d" % rc
# Set low power mode status
lpm_mask = 1 << 8
if lpm_enable:
pmmp.eeprom_override = pmmp.eeprom_override | lpm_mask
else:
pmmp.eeprom_override = pmmp.eeprom_override & (~lpm_mask)
meta.access_cmd = SXD_ACCESS_CMD_SET
rc = sxd_access_reg_pmmp(pmmp, meta, REGISTER_NUM, None, None)
assert rc == SXD_STATUS_SUCCESS, "sxd_access_reg_pmmp failed, rc = %d" % rc
# Check if SFP port number is provided
if len(sys.argv) < 3: if len(sys.argv) < 3:
print "SFP module number or LPM is missed." print("SFP module number or LPM is missed.")
print "Usage: sfplpmset.py <SFP module> <on|off>" print("Usage: sfplpmset.py <SFP module> <on|off>")
sys.exit(errno.EINVAL) sys.exit(errno.EINVAL)
cmd = None
lpm_enable = None lpm_enable = None
if sys.argv[2] == 'on': if sys.argv[2] == 'on':
lpm_enable = True lpm_enable = True
cmd = 'enable'
elif sys.argv[2] == 'off': elif sys.argv[2] == 'off':
lpm_enable = False lpm_enable = False
cmd = 'disable'
else: else:
print "Unrecognized LPM parameter. Please use <on> or <off> values" print("Unrecognized LPM parameter. Please use <on> or <off> values")
sys.exit(errno.EINVAL) sys.exit(errno.EINVAL)
# Init SDK API
rc, handle = sx_api_open(None)
if (rc != SX_STATUS_SUCCESS):
print "Failed to open api handle.\nPlease check that SDK is running."
sys.exit(errno.EACCES)
pid = os.getpid()
rc = sxd_access_reg_init(pid, None, SXD_LOG_VERBOSITY_LEVEL)
if (rc != SXD_STATUS_SUCCESS):
print "Failed to initializing register access.\nPlease check that SDK is running."
sys.exit(errno.EACCES);
# Get SFP module # Get SFP module
sfp_module = int(sys.argv[1]) - 1 sfp_module = int(sys.argv[1]) - 1
# Get all ports at admin up status that related to the SFP module print "[+] opening sdk"
log_port_list = get_log_ports(handle, sfp_module) rc, handle = sx_api_open(None)
# SET SFP related ports to admin down status if (rc != SX_STATUS_SUCCESS):
for log_port in log_port_list: print("Failed to open api handle.\nPlease check that SDK is running.")
set_port_admin_status_by_log_port(handle, log_port, SX_PORT_ADMIN_STATUS_DOWN) sys.exit(errno.EACCES)
# Disable admin status before LPM settings # Set low power mode
set_sfp_admin_status(sfp_module, SX_PORT_ADMIN_STATUS_DOWN) set_lpmode(handle, cmd, sfp_module)
# Set low power mode status sx_api_close(handle)
set_sfp_lpmode(sfp_module, lpm_enable)
# Enable admin status after LPM settings
set_sfp_admin_status(sfp_module, SX_PORT_ADMIN_STATUS_UP)
# SET SFP related ports to admin up status
for log_port in log_port_list:
set_port_admin_status_by_log_port(handle, log_port, SX_PORT_ADMIN_STATUS_UP)

View File

@ -1,45 +1,28 @@
#!/usr/bin/env python #!/usr/bin/env python
"""
import sys, errno This utility reset the given SFP module.
import os """
from python_sdk_api.sxd_api import *
from python_sdk_api.sx_api import * import sys
import errno
# Check if SFP port number is provided from python_sdk_api.sx_api import *
if len(sys.argv) < 2:
print "SFP module number or LPM is missed." # Check if SFP port number is provided
print "Usage: sfpreset.py <SFP module>" if len(sys.argv) < 2:
sys.exit(errno.EINVAL) print("SFP module number or LPM is missed.")
print("Usage: sfpreset.py <SFP module>")
# Init SDK API sys.exit(errno.EINVAL)
rc, handle = sx_api_open(None)
if (rc != SX_STATUS_SUCCESS): # Init SDK API
print "Failed to open api handle.\nPlease check that SDK is running." rc, handle = sx_api_open(None)
sys.exit(errno.EACCES) if rc != SX_STATUS_SUCCESS:
print("Failed to open api handle.\nPlease check that SDK is running.")
pid = os.getpid() sys.exit(errno.EACCES)
rc = sxd_access_reg_init(pid, None, 0)
if (rc != 0): # Get SFP module number
print "Failed to initializing register access.\nPlease check that SDK is running." sfp_module = int(sys.argv[1]) - 1
sys.exit(errno.EACCES)
rc = sx_mgmt_phy_mod_reset(handle, sfp_module)
# Get SFP module number assert rc == SX_STATUS_SUCCESS, "sx_mgmt_phy_mod_reset failed, rc = %d" % rc
sfp_module = int(sys.argv[1]) - 1
sx_api_close(handle)
# Get PMAOS
pmaos = ku_pmaos_reg()
pmaos.module = sfp_module
meta = sxd_reg_meta_t()
meta.dev_id = 1
meta.swid = 0
meta.access_cmd = SXD_ACCESS_CMD_GET
rc = sxd_access_reg_pmaos(pmaos, meta, 1, None, None)
assert rc == SXD_STATUS_SUCCESS, "sxd_access_reg_pmaos failed, rc = %d" % rc
# Reset SFP
pmaos.rst = 1
meta.access_cmd = SXD_ACCESS_CMD_SET
rc = sxd_access_reg_pmaos(pmaos, meta, 1, None, None)
assert rc == SXD_STATUS_SUCCESS, "sxd_access_reg_pmaos failed, rc = %d" % rc
print "Reset flag is set"

View File

@ -92,8 +92,8 @@ XCVR_SECOND_APPLICATION_LIST_WIDTH_QSFP_DD = 28
# in function get_transceiver_info and get_transceiver_bulk_status # in function get_transceiver_info and get_transceiver_bulk_status
# XCVR_INTERFACE_DATA_SIZE stands for the max size to be read # XCVR_INTERFACE_DATA_SIZE stands for the max size to be read
# this variable is only used by get_transceiver_info. # this variable is only used by get_transceiver_info.
# please be noted that each time some new value added to the function # please be noted that each time some new value added to the function
# we should make sure that it falls into the area # we should make sure that it falls into the area
# [XCVR_INTERFACE_DATA_START, XCVR_INTERFACE_DATA_SIZE] or # [XCVR_INTERFACE_DATA_START, XCVR_INTERFACE_DATA_SIZE] or
# adjust XCVR_INTERFACE_MAX_SIZE to contain the new data # adjust XCVR_INTERFACE_MAX_SIZE to contain the new data
# It's same for [QSFP_DOM_BULK_DATA_START, QSFP_DOM_BULK_DATA_SIZE] and # It's same for [QSFP_DOM_BULK_DATA_START, QSFP_DOM_BULK_DATA_SIZE] and
@ -197,12 +197,12 @@ QSFP_DD_CHANNL_STATUS_WIDTH = 1
# identifier value of xSFP module which is in the first byte of the EEPROM # identifier value of xSFP module which is in the first byte of the EEPROM
# if the identifier value falls into SFP_TYPE_CODE_LIST the module is treated as a SFP module and parsed according to 8472 # if the identifier value falls into SFP_TYPE_CODE_LIST the module is treated as a SFP module and parsed according to 8472
# for QSFP_TYPE_CODE_LIST the module is treated as a QSFP module and parsed according to 8436/8636 # for QSFP_TYPE_CODE_LIST the module is treated as a QSFP module and parsed according to 8436/8636
# Originally the type (SFP/QSFP) of each module is determined according to the SKU dictionary # Originally the type (SFP/QSFP) of each module is determined according to the SKU dictionary
# where the type of each FP port is defined. The content of EEPROM is parsed according to its type. # where the type of each FP port is defined. The content of EEPROM is parsed according to its type.
# However, sometimes the SFP module can be fit in an adapter and then pluged into a QSFP port. # However, sometimes the SFP module can be fit in an adapter and then pluged into a QSFP port.
# In this case the EEPROM content is in format of SFP but parsed as QSFP, causing failure. # In this case the EEPROM content is in format of SFP but parsed as QSFP, causing failure.
# To resolve that issue the type field of the xSFP module is also fetched so that we can know exectly what type the # To resolve that issue the type field of the xSFP module is also fetched so that we can know exectly what type the
# module is. Currently only the following types are recognized as SFP/QSFP module. # module is. Currently only the following types are recognized as SFP/QSFP module.
# Meanwhile, if the a module's identifier value can't be recognized, it will be parsed according to the SKU dictionary. # Meanwhile, if the a module's identifier value can't be recognized, it will be parsed according to the SKU dictionary.
# This is because in the future it's possible that some new identifier value which is not regonized but backward compatible # This is because in the future it's possible that some new identifier value which is not regonized but backward compatible
# with the current format and by doing so it can be parsed as much as possible. # with the current format and by doing so it can be parsed as much as possible.
@ -217,7 +217,7 @@ QSFP_DD_TYPE_CODE_LIST = [
'18' # QSFP-DD Double Density 8X Pluggable Transceiver '18' # QSFP-DD Double Density 8X Pluggable Transceiver
] ]
qsfp_cable_length_tup = ('Length(km)', 'Length OM3(2m)', qsfp_cable_length_tup = ('Length(km)', 'Length OM3(2m)',
'Length OM2(m)', 'Length OM1(m)', 'Length OM2(m)', 'Length OM1(m)',
'Length Cable Assembly(m)') 'Length Cable Assembly(m)')
@ -225,7 +225,7 @@ sfp_cable_length_tup = ('LengthSMFkm-UnitsOfKm', 'LengthSMF(UnitsOf100m)',
'Length50um(UnitsOf10m)', 'Length62.5um(UnitsOfm)', 'Length50um(UnitsOf10m)', 'Length62.5um(UnitsOfm)',
'LengthCable(UnitsOfm)', 'LengthOM3(UnitsOf10m)') 'LengthCable(UnitsOfm)', 'LengthOM3(UnitsOf10m)')
sfp_compliance_code_tup = ('10GEthernetComplianceCode', 'InfinibandComplianceCode', sfp_compliance_code_tup = ('10GEthernetComplianceCode', 'InfinibandComplianceCode',
'ESCONComplianceCodes', 'SONETComplianceCodes', 'ESCONComplianceCodes', 'SONETComplianceCodes',
'EthernetComplianceCodes','FibreChannelLinkLength', 'EthernetComplianceCodes','FibreChannelLinkLength',
'FibreChannelTechnology', 'SFP+CableTechnology', 'FibreChannelTechnology', 'SFP+CableTechnology',
@ -274,9 +274,11 @@ MCIA_ADDR_TX_DISABLE = 110
MCIA_ADDR_TX_DISABLE_BIT = 6 MCIA_ADDR_TX_DISABLE_BIT = 6
PORT_TYPE_NVE = 8 PORT_TYPE_NVE = 8
PORT_TYPE_CPU = 4
PORT_TYPE_OFFSET = 28 PORT_TYPE_OFFSET = 28
PORT_TYPE_MASK = 0xF0000000 PORT_TYPE_MASK = 0xF0000000
NVE_MASK = PORT_TYPE_MASK & (PORT_TYPE_NVE << PORT_TYPE_OFFSET) NVE_MASK = PORT_TYPE_MASK & (PORT_TYPE_NVE << PORT_TYPE_OFFSET)
CPU_MASK = PORT_TYPE_MASK & (PORT_TYPE_CPU << PORT_TYPE_OFFSET)
# Global logger class instance # Global logger class instance
logger = Logger() logger = Logger()
@ -555,7 +557,7 @@ class SFP(SfpBase):
Returns: Returns:
A dict which contains following keys/values : A dict which contains following keys/values :
================================================================================ ================================================================================
keys |Value Format |Information keys |Value Format |Information
---------------------------|---------------|---------------------------- ---------------------------|---------------|----------------------------
type |1*255VCHAR |type of SFP type |1*255VCHAR |type of SFP
hardware_rev |1*255VCHAR |hardware version of SFP hardware_rev |1*255VCHAR |hardware version of SFP
@ -714,7 +716,7 @@ class SFP(SfpBase):
sfp_cable_len_data = sfpi_obj.parse_cable_len(sfp_cable_len_raw, 0) sfp_cable_len_data = sfpi_obj.parse_cable_len(sfp_cable_len_raw, 0)
else: else:
return None return None
sfp_media_type_raw = self._read_eeprom_specific_bytes(XCVR_MEDIA_TYPE_OFFSET_QSFP_DD, XCVR_MEDIA_TYPE_WIDTH_QSFP_DD) sfp_media_type_raw = self._read_eeprom_specific_bytes(XCVR_MEDIA_TYPE_OFFSET_QSFP_DD, XCVR_MEDIA_TYPE_WIDTH_QSFP_DD)
if sfp_media_type_raw is not None: if sfp_media_type_raw is not None:
sfp_media_type_dict = sfpi_obj.parse_media_type(sfp_media_type_raw, 0) sfp_media_type_dict = sfpi_obj.parse_media_type(sfp_media_type_raw, 0)
@ -828,14 +830,14 @@ class SFP(SfpBase):
for key in qsfp_compliance_code_tup: for key in qsfp_compliance_code_tup:
if key in sfp_interface_bulk_data['data']['Specification compliance']['value']: if key in sfp_interface_bulk_data['data']['Specification compliance']['value']:
compliance_code_dict[key] = sfp_interface_bulk_data['data']['Specification compliance']['value'][key]['value'] compliance_code_dict[key] = sfp_interface_bulk_data['data']['Specification compliance']['value'][key]['value']
sfp_ext_specification_compliance_raw = self._read_eeprom_specific_bytes(offset + XCVR_EXT_SPECIFICATION_COMPLIANCE_OFFSET, XCVR_EXT_SPECIFICATION_COMPLIANCE_WIDTH) sfp_ext_specification_compliance_raw = self._read_eeprom_specific_bytes(offset + XCVR_EXT_SPECIFICATION_COMPLIANCE_OFFSET, XCVR_EXT_SPECIFICATION_COMPLIANCE_WIDTH)
if sfp_ext_specification_compliance_raw is not None: if sfp_ext_specification_compliance_raw is not None:
sfp_ext_specification_compliance_data = sfpi_obj.parse_ext_specification_compliance(sfp_ext_specification_compliance_raw[0 : 1], 0) sfp_ext_specification_compliance_data = sfpi_obj.parse_ext_specification_compliance(sfp_ext_specification_compliance_raw[0 : 1], 0)
if sfp_ext_specification_compliance_data['data']['Extended Specification compliance']['value'] != "Unspecified": if sfp_ext_specification_compliance_data['data']['Extended Specification compliance']['value'] != "Unspecified":
compliance_code_dict['Extended Specification compliance'] = sfp_ext_specification_compliance_data['data']['Extended Specification compliance']['value'] compliance_code_dict['Extended Specification compliance'] = sfp_ext_specification_compliance_data['data']['Extended Specification compliance']['value']
transceiver_info_dict['specification_compliance'] = str(compliance_code_dict) transceiver_info_dict['specification_compliance'] = str(compliance_code_dict)
transceiver_info_dict['nominal_bit_rate'] = str(sfp_interface_bulk_data['data']['Nominal Bit Rate(100Mbs)']['value']) transceiver_info_dict['nominal_bit_rate'] = str(sfp_interface_bulk_data['data']['Nominal Bit Rate(100Mbs)']['value'])
else: else:
for key in sfp_cable_length_tup: for key in sfp_cable_length_tup:
@ -849,7 +851,7 @@ class SFP(SfpBase):
transceiver_info_dict['specification_compliance'] = str(compliance_code_dict) transceiver_info_dict['specification_compliance'] = str(compliance_code_dict)
transceiver_info_dict['nominal_bit_rate'] = str(sfp_interface_bulk_data['data']['NominalSignallingRate(UnitsOf100Mbd)']['value']) transceiver_info_dict['nominal_bit_rate'] = str(sfp_interface_bulk_data['data']['NominalSignallingRate(UnitsOf100Mbd)']['value'])
return transceiver_info_dict return transceiver_info_dict
@ -860,7 +862,7 @@ class SFP(SfpBase):
Returns: Returns:
A dict which contains following keys/values : A dict which contains following keys/values :
======================================================================== ========================================================================
keys |Value Format |Information keys |Value Format |Information
---------------------------|---------------|---------------------------- ---------------------------|---------------|----------------------------
RX LOS |BOOLEAN |RX lost-of-signal status, RX LOS |BOOLEAN |RX lost-of-signal status,
| |True if has RX los, False if not. | |True if has RX los, False if not.
@ -1237,12 +1239,12 @@ class SFP(SfpBase):
A Boolean, True if reset enabled, False if disabled A Boolean, True if reset enabled, False if disabled
for QSFP, originally I would like to make use of Initialization complete flag bit for QSFP, originally I would like to make use of Initialization complete flag bit
which is at Page a0 offset 6 bit 0 to test whether reset is complete. which is at Page a0 offset 6 bit 0 to test whether reset is complete.
However as unit testing was carried out I find this approach may fail because: However as unit testing was carried out I find this approach may fail because:
1. we make use of ethtool to read data on I2C bus rather than to read directly 1. we make use of ethtool to read data on I2C bus rather than to read directly
2. ethtool is unable to access I2C during QSFP module being reset 2. ethtool is unable to access I2C during QSFP module being reset
In other words, whenever the flag is able to be retrived, the value is always be 1 In other words, whenever the flag is able to be retrived, the value is always be 1
As a result, it doesn't make sense to retrieve that flag. Just treat successfully As a result, it doesn't make sense to retrieve that flag. Just treat successfully
retrieving data as "data ready". retrieving data as "data ready".
for SFP it seems that there is not flag indicating whether reset succeed. However, for SFP it seems that there is not flag indicating whether reset succeed. However,
we can also do it in the way for QSFP. we can also do it in the way for QSFP.
@ -1444,7 +1446,7 @@ class SFP(SfpBase):
Returns: Returns:
A hex of 4 bits (bit 0 to bit 3 as channel 0 to channel 3) to represent A hex of 4 bits (bit 0 to bit 3 as channel 0 to channel 3) to represent
TX channels which have been disabled in this SFP. TX channels which have been disabled in this SFP.
As an example, a returned value of 0x5 indicates that channel 0 As an example, a returned value of 0x5 indicates that channel 0
and channel 2 have been disabled. and channel 2 have been disabled.
""" """
tx_disable_list = self.get_tx_disable() tx_disable_list = self.get_tx_disable()
@ -1457,6 +1459,21 @@ class SFP(SfpBase):
return tx_disabled return tx_disabled
def mgmt_phy_mod_pwr_attr_get(self, power_attr_type):
sx_mgmt_phy_mod_pwr_attr_p = new_sx_mgmt_phy_mod_pwr_attr_t_p()
sx_mgmt_phy_mod_pwr_attr = sx_mgmt_phy_mod_pwr_attr_t()
sx_mgmt_phy_mod_pwr_attr.power_attr_type = power_attr_type
sx_mgmt_phy_mod_pwr_attr_t_p_assign(sx_mgmt_phy_mod_pwr_attr_p, sx_mgmt_phy_mod_pwr_attr)
try:
rc = sx_mgmt_phy_mod_pwr_attr_get(self.sdk_handle, self.sdk_index, sx_mgmt_phy_mod_pwr_attr_p)
assert SX_STATUS_SUCCESS == rc, "sx_mgmt_phy_mod_pwr_attr_get failed"
sx_mgmt_phy_mod_pwr_attr = sx_mgmt_phy_mod_pwr_attr_t_p_value(sx_mgmt_phy_mod_pwr_attr_p)
pwr_mode_attr = sx_mgmt_phy_mod_pwr_attr.pwr_mode_attr
return pwr_mode_attr.admin_pwr_mode_e, pwr_mode_attr.oper_pwr_mode_e
finally:
delete_sx_mgmt_phy_mod_pwr_attr_t_p(sx_mgmt_phy_mod_pwr_attr_p)
def get_lpmode(self): def get_lpmode(self):
""" """
Retrieves the lpmode (low power mode) status of this SFP Retrieves the lpmode (low power mode) status of this SFP
@ -1464,28 +1481,15 @@ class SFP(SfpBase):
Returns: Returns:
A Boolean, True if lpmode is enabled, False if disabled A Boolean, True if lpmode is enabled, False if disabled
""" """
if self.sfp_type == QSFP_TYPE: handle = self._open_sdk()
if self._open_sdk(): if handle is None:
# Get MCION logger.log_error("SDK handler is missing for sfp %d object" % self.index)
mcion = ku_mcion_reg() return False
mcion.module = self.sdk_index
meta = self._init_sx_meta_data()
meta.access_cmd = SXD_ACCESS_CMD_GET
rc = sxd_access_reg_mcion(mcion, meta, REGISTER_NUM, None, None) admin_pwr_mode, oper_pwr_mode = self.mgmt_phy_mod_pwr_attr_get(SX_MGMT_PHY_MOD_PWR_ATTR_PWR_MODE_E)
self._close_sdk()
if rc != SXD_STATUS_SUCCESS: self._close_sdk()
logger.log_warning("sxd_access_reg_mcion getting failed, rc = %d" % rc) return oper_pwr_mode == SX_MGMT_PHY_MOD_PWR_MODE_LOW_E
return None
# Get low power mode status
lpm_mask = 1 << 8
lpm_status = (lpm_mask & mcion.module_status_bits) != 0
return lpm_status
else:
return NotImplementedError
def get_power_override(self): def get_power_override(self):
@ -1580,7 +1584,7 @@ class SFP(SfpBase):
if self.sfp_type == QSFP_TYPE: if self.sfp_type == QSFP_TYPE:
offset = 0 offset = 0
offset_xcvr = 128 offset_xcvr = 128
sfpd_obj = sff8436Dom() sfpd_obj = sff8436Dom()
if sfpd_obj is None: if sfpd_obj is None:
return None return None
@ -1596,7 +1600,7 @@ class SFP(SfpBase):
return None return None
if self.sfp_type == QSFP_DD_TYPE: if self.sfp_type == QSFP_DD_TYPE:
offset = 128 offset = 128
sfpd_obj = qsfp_dd_Dom() sfpd_obj = qsfp_dd_Dom()
if sfpd_obj is None: if sfpd_obj is None:
@ -1641,7 +1645,7 @@ class SFP(SfpBase):
if self.sfp_type == QSFP_TYPE: if self.sfp_type == QSFP_TYPE:
offset = 0 offset = 0
offset_xcvr = 128 offset_xcvr = 128
sfpd_obj = sff8436Dom() sfpd_obj = sff8436Dom()
if sfpd_obj is None: if sfpd_obj is None:
return None return None
@ -1653,7 +1657,7 @@ class SFP(SfpBase):
tx_bias_list.append(self._convert_string_to_num(dom_channel_monitor_data['data']['TX2Bias']['value'])) tx_bias_list.append(self._convert_string_to_num(dom_channel_monitor_data['data']['TX2Bias']['value']))
tx_bias_list.append(self._convert_string_to_num(dom_channel_monitor_data['data']['TX3Bias']['value'])) tx_bias_list.append(self._convert_string_to_num(dom_channel_monitor_data['data']['TX3Bias']['value']))
tx_bias_list.append(self._convert_string_to_num(dom_channel_monitor_data['data']['TX4Bias']['value'])) tx_bias_list.append(self._convert_string_to_num(dom_channel_monitor_data['data']['TX4Bias']['value']))
elif self.sfp_type == QSFP_DD_TYPE: elif self.sfp_type == QSFP_DD_TYPE:
# page 11h # page 11h
if self.dom_rx_tx_power_bias_supported: if self.dom_rx_tx_power_bias_supported:
@ -1713,7 +1717,7 @@ class SFP(SfpBase):
elif self.sfp_type == QSFP_TYPE: elif self.sfp_type == QSFP_TYPE:
offset = 0 offset = 0
offset_xcvr = 128 offset_xcvr = 128
sfpd_obj = sff8436Dom() sfpd_obj = sff8436Dom()
if sfpd_obj is None: if sfpd_obj is None:
return None return None
@ -1861,64 +1865,15 @@ class SFP(SfpBase):
""" """
handle = self._open_sdk() handle = self._open_sdk()
if handle is None: if handle is None:
logger.log_error("SDK handler is missing for sfp %d object" % self.index)
return False return False
# Get PMAOS rc = sx_mgmt_phy_mod_reset(self.sdk_handle, self.sdk_index)
pmaos = ku_pmaos_reg() if rc != SX_STATUS_SUCCESS:
pmaos.module = self.sdk_index logger.log_warning("sx_mgmt_phy_mod_reset failed, rc = %d" % rc)
meta = self._init_sx_meta_data()
meta.access_cmd = SXD_ACCESS_CMD_GET
rc = sxd_access_reg_pmaos(pmaos, meta, REGISTER_NUM, None, None)
if rc != SXD_STATUS_SUCCESS:
logger.log_warning("sxd_access_reg_pmaos getting failed, rc = %d" % rc)
self._close_sdk()
return None
# Reset SFP
pmaos.rst = 1
meta.access_cmd = SXD_ACCESS_CMD_SET
rc = sxd_access_reg_pmaos(pmaos, meta, REGISTER_NUM, None, None)
if rc != SXD_STATUS_SUCCESS:
logger.log_warning("sxd_access_reg_pmaos setting failed, rc = %d" % rc)
self._close_sdk() self._close_sdk()
return rc == SXD_STATUS_SUCCESS return rc == SX_STATUS_SUCCESS
def _write_i2c_via_mcia(self, page, i2caddr, address, data, mask):
handle = self._open_sdk()
if handle is None:
return False
mcia = ku_mcia_reg()
meta = self._init_sx_meta_data()
meta.access_cmd = SXD_ACCESS_CMD_GET
mcia.module = self.sdk_index
mcia.page_number = page
mcia.i2c_device_address = i2caddr
mcia.device_address = address
mcia.size = 1
rc = sxd_access_reg_mcia(mcia, meta, REGISTER_NUM, None, None)
if rc != SXD_STATUS_SUCCESS:
logger.log_warning("sxd_access_reg_mcia getting failed, rc = %d" % rc)
self._close_sdk()
return False
original_data = (mcia.dword_0 >> 24) & 0x000000FF
updated_data = original_data & (~mask)
updated_data |= (data & mask)
mcia.dword_0 = (updated_data << 24) & 0xFF000000
meta.access_cmd = SXD_ACCESS_CMD_SET
rc = sxd_access_reg_mcia(mcia, meta, REGISTER_NUM, None, None)
if rc != SXD_STATUS_SUCCESS:
logger.log_warning("sxd_access_reg_mcia setting failed, rc = %d" % rc)
self._close_sdk()
return rc == SXD_STATUS_SUCCESS
def tx_disable(self, tx_disable): def tx_disable(self, tx_disable):
@ -1935,34 +1890,7 @@ class SFP(SfpBase):
for SFP, make use of bit 6 of byte at (offset 110, a2h (i2c addr 0x51)) to disable/enable tx for SFP, make use of bit 6 of byte at (offset 110, a2h (i2c addr 0x51)) to disable/enable tx
for QSFP, set all channels to disable/enable tx for QSFP, set all channels to disable/enable tx
""" """
if self.sfp_type == SFP_TYPE: return NotImplementedError
if self.dom_tx_disable_supported:
handle = self._open_sdk()
if handle is None:
return False
tx_disable_mask = 1 << MCIA_ADDR_TX_DISABLE_BIT
if tx_disable:
tx_disable_bit = tx_disable_mask
else:
tx_disable_bit = 0
return self._write_i2c_via_mcia(2, 0x51, MCIA_ADDR_TX_DISABLE, tx_disable_bit, tx_disable_mask)
else:
return False
elif self.sfp_type == QSFP_TYPE:
if self.dom_tx_disable_supported:
channel_mask = 0x0f
if tx_disable:
disable_flag = channel_mask
else:
disable_flag = 0
return self._write_i2c_via_mcia(0, 0x50, MCIA_ADDR_TX_CHANNEL_DISABLE, disable_flag, channel_mask)
else:
return False
else:
return NotImplementedError
def tx_disable_channel(self, channel, disable): def tx_disable_channel(self, channel, disable):
@ -1980,25 +1908,17 @@ class SFP(SfpBase):
QSFP: page a0, address 86, lower 4 bits QSFP: page a0, address 86, lower 4 bits
""" """
if self.sfp_type == QSFP_TYPE: return NotImplementedError
if self.dom_tx_disable_supported:
channel_mask = 1 << channel
if disable:
disable_flag = channel_mask
else:
disable_flag = 0
return self._write_i2c_via_mcia(0, 0x50, MCIA_ADDR_TX_CHANNEL_DISABLE, disable_flag, channel_mask)
else:
return False
else:
return NotImplementedError
def is_nve(self, port): def is_nve(self, port):
return (port & NVE_MASK) != 0 return (port & NVE_MASK) != 0
def is_cpu(self, port):
return (port & CPU_MASK) != 0
def is_port_admin_status_up(self, log_port): def is_port_admin_status_up(self, log_port):
oper_state_p = new_sx_port_oper_state_t_p() oper_state_p = new_sx_port_oper_state_t_p()
admin_state_p = new_sx_port_admin_state_t_p() admin_state_p = new_sx_port_admin_state_t_p()
@ -2015,11 +1935,14 @@ class SFP(SfpBase):
def set_port_admin_status_by_log_port(self, log_port, admin_status): def set_port_admin_status_by_log_port(self, log_port, admin_status):
rc = sx_api_port_state_set(self.sdk_handle, log_port, admin_status) rc = sx_api_port_state_set(self.sdk_handle, log_port, admin_status)
assert rc == SX_STATUS_SUCCESS, "sx_api_port_state_set failed, rc = %d" % rc if SX_STATUS_SUCCESS != rc:
logger.log_error("sx_api_port_state_set failed, rc = %d" % rc)
return SX_STATUS_SUCCESS == rc
# Get all the ports related to the sfp, if port admin status is up, put it to list def get_logical_ports(self):
def get_log_ports(self): # Get all the ports related to the sfp, if port admin status is up, put it to list
port_attributes_list = new_sx_port_attributes_t_arr(SX_PORT_ATTR_ARR_SIZE) port_attributes_list = new_sx_port_attributes_t_arr(SX_PORT_ATTR_ARR_SIZE)
port_cnt_p = new_uint32_t_p() port_cnt_p = new_uint32_t_p()
uint32_t_p_assign(port_cnt_p, SX_PORT_ATTR_ARR_SIZE) uint32_t_p_assign(port_cnt_p, SX_PORT_ATTR_ARR_SIZE)
@ -2031,58 +1954,56 @@ class SFP(SfpBase):
log_port_list = [] log_port_list = []
for i in range(0, port_cnt): for i in range(0, port_cnt):
port_attributes = sx_port_attributes_t_arr_getitem(port_attributes_list, i) port_attributes = sx_port_attributes_t_arr_getitem(port_attributes_list, i)
if self.is_nve(int(port_attributes.log_port)) == False \ if not self.is_nve(int(port_attributes.log_port)) \
and port_attributes.port_mapping.module_port == self.sdk_index \ and not self.is_cpu(int(port_attributes.log_port)) \
and self.is_port_admin_status_up(port_attributes.log_port): and port_attributes.port_mapping.module_port == self.sdk_index \
and self.is_port_admin_status_up(port_attributes.log_port):
log_port_list.append(port_attributes.log_port) log_port_list.append(port_attributes.log_port)
return log_port_list return log_port_list
def _set_sfp_admin_status_raw(self, admin_status): def mgmt_phy_mod_pwr_attr_set(self, power_attr_type, admin_pwr_mode):
# Get PMAOS result = False
pmaos = ku_pmaos_reg() sx_mgmt_phy_mod_pwr_attr = sx_mgmt_phy_mod_pwr_attr_t()
pmaos.module = self.sdk_index sx_mgmt_phy_mod_pwr_mode_attr = sx_mgmt_phy_mod_pwr_mode_attr_t()
meta = self._init_sx_meta_data() sx_mgmt_phy_mod_pwr_attr.power_attr_type = power_attr_type
meta.access_cmd = SXD_ACCESS_CMD_GET sx_mgmt_phy_mod_pwr_mode_attr.admin_pwr_mode_e = admin_pwr_mode
rc = sxd_access_reg_pmaos(pmaos, meta, REGISTER_NUM, None, None) sx_mgmt_phy_mod_pwr_attr.pwr_mode_attr = sx_mgmt_phy_mod_pwr_mode_attr
assert rc == SXD_STATUS_SUCCESS, "sxd_access_reg_pmaos failed, rc = %d" % rc sx_mgmt_phy_mod_pwr_attr_p = new_sx_mgmt_phy_mod_pwr_attr_t_p()
sx_mgmt_phy_mod_pwr_attr_t_p_assign(sx_mgmt_phy_mod_pwr_attr_p, sx_mgmt_phy_mod_pwr_attr)
try:
rc = sx_mgmt_phy_mod_pwr_attr_set(self.sdk_handle, SX_ACCESS_CMD_SET, self.sdk_index, sx_mgmt_phy_mod_pwr_attr_p)
if SX_STATUS_SUCCESS != rc:
logger.log_error("sx_mgmt_phy_mod_pwr_attr_set failed, rc = %d" % rc)
result = False
else:
result = True
finally:
delete_sx_mgmt_phy_mod_pwr_attr_t_p(sx_mgmt_phy_mod_pwr_attr_p)
# Set admin status to PMAOS return result
pmaos.ase = PMAOS_ASE
pmaos.ee = PMAOS_EE
pmaos.e = PMAOS_E
pmaos.rst = PMAOS_RST
if admin_status == SX_PORT_ADMIN_STATUS_DOWN:
pmaos.admin_status = PMAOS_DISABLE
else:
pmaos.admin_status = PMAOS_ENABLE
meta.access_cmd = SXD_ACCESS_CMD_SET
rc = sxd_access_reg_pmaos(pmaos, meta, REGISTER_NUM, None, None)
assert rc == SXD_STATUS_SUCCESS, "sxd_access_reg_pmaos failed, rc = %d" % rc
def _set_lpmode_raw(self, lpmode): def _set_lpmode_raw(self, ports, attr_type, power_mode):
# Get PMMP result = False
pmmp = ku_pmmp_reg() # Check if the module already works in the same mode
pmmp.module = self.sdk_index admin_pwr_mode, oper_pwr_mode = self.mgmt_phy_mod_pwr_attr_get(attr_type)
meta = self._init_sx_meta_data() if (power_mode == SX_MGMT_PHY_MOD_PWR_MODE_LOW_E and oper_pwr_mode == SX_MGMT_PHY_MOD_PWR_MODE_LOW_E) \
meta.access_cmd = SXD_ACCESS_CMD_GET or (power_mode == SX_MGMT_PHY_MOD_PWR_MODE_AUTO_E and admin_pwr_mode == SX_MGMT_PHY_MOD_PWR_MODE_AUTO_E):
rc = sxd_access_reg_pmmp(pmmp, meta, REGISTER_NUM, None, None) return True
assert rc == SXD_STATUS_SUCCESS, "sxd_access_reg_pmmp failed, rc = %d" % rc try:
# Bring the port down
for port in ports:
self.set_port_admin_status_by_log_port(port, SX_PORT_ADMIN_STATUS_DOWN)
# Set the desired power mode
result = self.mgmt_phy_mod_pwr_attr_set(attr_type, power_mode)
finally:
# Bring the port up
for port in ports:
self.set_port_admin_status_by_log_port(port, SX_PORT_ADMIN_STATUS_UP)
# Set low power mode status return result
lpm_mask = 1 << PMMP_LPMODE_BIT
if lpmode:
pmmp.eeprom_override = pmmp.eeprom_override | lpm_mask
else:
pmmp.eeprom_override = pmmp.eeprom_override & (~lpm_mask)
meta.access_cmd = SXD_ACCESS_CMD_SET
rc = sxd_access_reg_pmmp(pmmp, meta, REGISTER_NUM, None, None)
return rc
def set_lpmode(self, lpmode): def set_lpmode(self, lpmode):
@ -2098,24 +2019,18 @@ class SFP(SfpBase):
""" """
handle = self._open_sdk() handle = self._open_sdk()
if handle is None: if handle is None:
logger.log_error("SDK handler is missing for sfp %d object" % self.index)
return False return False
try:
log_port_list = self.get_log_ports()
for log_port in log_port_list:
self.set_port_admin_status_by_log_port(log_port, SX_PORT_ADMIN_STATUS_DOWN)
self._set_sfp_admin_status_raw(SX_PORT_ADMIN_STATUS_DOWN)
result = self._set_lpmode_raw(lpmode) log_port_list = self.get_logical_ports()
if lpmode:
self._set_sfp_admin_status_raw(SX_PORT_ADMIN_STATUS_UP) self._set_lpmode_raw(log_port_list, SX_MGMT_PHY_MOD_PWR_ATTR_PWR_MODE_E, SX_MGMT_PHY_MOD_PWR_MODE_LOW_E)
for log_port in log_port_list: logger.log_info("Enabled low power mode for module [%d]" % (self.sdk_index))
self.set_port_admin_status_by_log_port(log_port, SX_PORT_ADMIN_STATUS_DOWN) else:
self._set_lpmode_raw(log_port_list, SX_MGMT_PHY_MOD_PWR_ATTR_PWR_MODE_E, SX_MGMT_PHY_MOD_PWR_MODE_AUTO_E)
return result == SXD_STATUS_SUCCESS logger.log_info( "Disabled low power mode for module [%d]" % (self.sdk_index))
except: self._close_sdk()
logger.log_warning("set_lpmode failed due to some SDK failure") return True
self._close_sdk()
return False
def set_power_override(self, power_override, power_set): def set_power_override(self, power_override, power_set):
@ -2123,7 +2038,7 @@ class SFP(SfpBase):
Sets SFP power level using power_override and power_set Sets SFP power level using power_override and power_set
Args: Args:
power_override : power_override :
A Boolean, True to override set_lpmode and use power_set A Boolean, True to override set_lpmode and use power_set
to control SFP power, False to disable SFP power control to control SFP power, False to disable SFP power control
through power_override/power_set and use set_lpmode through power_override/power_set and use set_lpmode
@ -2137,15 +2052,4 @@ class SFP(SfpBase):
A boolean, True if power-override and power_set are set successfully, A boolean, True if power-override and power_set are set successfully,
False if not False if not
""" """
if self.sfp_type == QSFP_TYPE: return NotImplementedError
power_override_bit = 0
if power_override:
power_override_bit |= 1 << MCIA_ADDR_POWER_OVERRIDE_POR_BIT
power_set_bit = 0
if power_set:
power_set_bit |= 1 << MCIA_ADDR_POWER_OVERRIDE_PS_BIT
power_override_mask = 1 << MCIA_ADDR_POWER_OVERRIDE_PS_BIT | 1 << MCIA_ADDR_POWER_OVERRIDE_POR_BIT
return self._write_i2c_via_mcia(0, 0x50, MCIA_ADDR_POWER_OVERRIDE, power_set_bit|power_override_bit, power_override_mask)
else:
return NotImplementedError