From 2d0bad0523fadd0bdc6f7ea348de70cebb0e228e Mon Sep 17 00:00:00 2001 From: wilson-smci <133636887+wilson-smci@users.noreply.github.com> Date: Fri, 21 Jul 2023 01:24:56 +0800 Subject: [PATCH] [Supermicro]: Add a new supported device and platform, SSE-T7132S. (#15368) * * platform/innoviunm: Add a new supported device and platform, SSE-T7132S * Switch Vendor: Supermicro * Switch SKU: Supermicro_sse_t7132s * ASIC Vendor: innovium * Swich ASIC: TL7 * Port Configuration: 32x400G * SONiC Image: SONiC-ONIE-Innoviunm Signed-off-by: wilsonw --- .../CSV/TL7_DAC_1M.csv | 263 +++ .../CSV/TL7_DAC_3M.csv | 263 +++ .../CSV/TL7_Optics.csv | 263 +++ .../CSV/TL7_RJ45.csv | 7 + .../Supermicro_sse_t7132s/buffers.json.j2 | 167 ++ .../buffers_defaults_def_lossy.j2 | 45 + .../buffers_defaults_t1.j2 | 167 ++ .../config_32x400G_sse_t7132s.yaml | 440 +++++ .../Supermicro_sse_t7132s/innovium.77700_A | 60 + .../Supermicro_sse_t7132s/innovium.77700_B | 60 + .../Supermicro_sse_t7132s/ivm.sai.config.yaml | 10 + .../ivm.sai.datapath.config.yaml | 9 + .../pg_profile_lookup.ini | 22 + .../Supermicro_sse_t7132s/port_config.ini | 35 + .../Supermicro_sse_t7132s/qos.json.j2 | 195 ++ .../qos_defaults_def_lossy.j2 | 124 ++ .../Supermicro_sse_t7132s/qos_defaults_t1.j2 | 195 ++ .../Supermicro_sse_t7132s/sai.profile | 1 + .../default_sku | 1 + .../fast-reboot_plugin | 2 + .../installer.conf | 4 + .../lib_ivm_serdes_pltfm.so | Bin 0 -> 283696 bytes .../x86_64-supermicro_sse_t7132s-r0/pcie.yaml | 453 +++++ .../platform.json | 238 +++ .../platform_asic | 1 + .../plugins/eeprom.py | 20 + .../plugins/psuutil.py | 84 + .../plugins/sfputil.py | 211 ++ .../plugins/ssd_util.py | 8 + .../pmon_daemon_control.json | 6 + .../sensors.conf | 2 + .../system_health_monitoring_config.json | 11 + .../thermal_policy.json | 0 .../x86_64-supermicro_sse_t7132s-r0/topo.conf | 1 + .../warm-reboot_plugin | 2 + platform/innovium/one-image.mk | 1 + .../innovium/platform-modules-supermicro.mk | 9 + platform/innovium/rules.mk | 1 + .../debian/changelog | 5 + .../debian/compat | 1 + .../debian/control | 16 + .../platform-modules-sse-t7132s.install | 8 + .../platform-modules-sse-t7132s.postinst | 14 + .../debian/rules | 39 + .../sse-t7132s/cfg/iTCO_wdt.conf | 1 + .../sse-t7132s/cfg/t7132s-modules.conf | 16 + .../sse-t7132s/modules/Makefile | 1 + .../sse-t7132s/modules/t7132s.c | 1706 +++++++++++++++++ .../scripts/health_checker_thermal.py | 50 + .../sse-t7132s/scripts/platform.sh | 102 + .../sse-t7132s/scripts/sysledctl.py | 53 + .../sse-t7132s/scripts/test_cpld.py | 209 ++ .../sse-t7132s/setup.py | 30 + .../sse-t7132s/sonic_platform/__init__.py | 2 + .../sse-t7132s/sonic_platform/chassis.py | 566 ++++++ .../sse-t7132s/sonic_platform/component.py | 106 + .../sse-t7132s/sonic_platform/eeprom.py | 122 ++ .../sse-t7132s/sonic_platform/fan.py | 353 ++++ .../sse-t7132s/sonic_platform/fan_drawer.py | 121 ++ .../sse-t7132s/sonic_platform/helper.py | 108 ++ .../sse-t7132s/sonic_platform/pcie.py | 18 + .../sse-t7132s/sonic_platform/platform.py | 21 + .../sse-t7132s/sonic_platform/psu.py | 545 ++++++ .../sse-t7132s/sonic_platform/sfp.py | 444 +++++ .../sse-t7132s/sonic_platform/thermal.py | 253 +++ .../sse-t7132s/sonic_platform/watchdog.py | 317 +++ .../platform-modules-sse-t7132s.service | 14 + .../sse-t7132s/systemd/sysled.service | 15 + 68 files changed, 8637 insertions(+) create mode 100755 device/supermicro/x86_64-supermicro_sse_t7132s-r0/CSV/TL7_DAC_1M.csv create mode 100755 device/supermicro/x86_64-supermicro_sse_t7132s-r0/CSV/TL7_DAC_3M.csv create mode 100755 device/supermicro/x86_64-supermicro_sse_t7132s-r0/CSV/TL7_Optics.csv create mode 100755 device/supermicro/x86_64-supermicro_sse_t7132s-r0/CSV/TL7_RJ45.csv create mode 100755 device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/buffers.json.j2 create mode 100644 device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/buffers_defaults_def_lossy.j2 create mode 100755 device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/buffers_defaults_t1.j2 create mode 100644 device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/config_32x400G_sse_t7132s.yaml create mode 100644 device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/innovium.77700_A create mode 100644 device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/innovium.77700_B create mode 100755 device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/ivm.sai.config.yaml create mode 100644 device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/ivm.sai.datapath.config.yaml create mode 100644 device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/pg_profile_lookup.ini create mode 100755 device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/port_config.ini create mode 100755 device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/qos.json.j2 create mode 100644 device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/qos_defaults_def_lossy.j2 create mode 100644 device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/qos_defaults_t1.j2 create mode 100644 device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/sai.profile create mode 100755 device/supermicro/x86_64-supermicro_sse_t7132s-r0/default_sku create mode 100755 device/supermicro/x86_64-supermicro_sse_t7132s-r0/fast-reboot_plugin create mode 100755 device/supermicro/x86_64-supermicro_sse_t7132s-r0/installer.conf create mode 100755 device/supermicro/x86_64-supermicro_sse_t7132s-r0/lib_ivm_serdes_pltfm.so create mode 100755 device/supermicro/x86_64-supermicro_sse_t7132s-r0/pcie.yaml create mode 100644 device/supermicro/x86_64-supermicro_sse_t7132s-r0/platform.json create mode 100644 device/supermicro/x86_64-supermicro_sse_t7132s-r0/platform_asic create mode 100644 device/supermicro/x86_64-supermicro_sse_t7132s-r0/plugins/eeprom.py create mode 100644 device/supermicro/x86_64-supermicro_sse_t7132s-r0/plugins/psuutil.py create mode 100644 device/supermicro/x86_64-supermicro_sse_t7132s-r0/plugins/sfputil.py create mode 100644 device/supermicro/x86_64-supermicro_sse_t7132s-r0/plugins/ssd_util.py create mode 100644 device/supermicro/x86_64-supermicro_sse_t7132s-r0/pmon_daemon_control.json create mode 100755 device/supermicro/x86_64-supermicro_sse_t7132s-r0/sensors.conf create mode 100644 device/supermicro/x86_64-supermicro_sse_t7132s-r0/system_health_monitoring_config.json create mode 100644 device/supermicro/x86_64-supermicro_sse_t7132s-r0/thermal_policy.json create mode 100644 device/supermicro/x86_64-supermicro_sse_t7132s-r0/topo.conf create mode 100755 device/supermicro/x86_64-supermicro_sse_t7132s-r0/warm-reboot_plugin create mode 100644 platform/innovium/platform-modules-supermicro.mk create mode 100644 platform/innovium/sonic-platform-modules-supermicro/debian/changelog create mode 100644 platform/innovium/sonic-platform-modules-supermicro/debian/compat create mode 100644 platform/innovium/sonic-platform-modules-supermicro/debian/control create mode 100644 platform/innovium/sonic-platform-modules-supermicro/debian/platform-modules-sse-t7132s.install create mode 100644 platform/innovium/sonic-platform-modules-supermicro/debian/platform-modules-sse-t7132s.postinst create mode 100644 platform/innovium/sonic-platform-modules-supermicro/debian/rules create mode 100644 platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/cfg/iTCO_wdt.conf create mode 100644 platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/cfg/t7132s-modules.conf create mode 100644 platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/modules/Makefile create mode 100755 platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/modules/t7132s.c create mode 100755 platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/scripts/health_checker_thermal.py create mode 100755 platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/scripts/platform.sh create mode 100755 platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/scripts/sysledctl.py create mode 100755 platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/scripts/test_cpld.py create mode 100644 platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/setup.py create mode 100644 platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/__init__.py create mode 100644 platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/chassis.py create mode 100644 platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/component.py create mode 100644 platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/eeprom.py create mode 100644 platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/fan.py create mode 100644 platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/fan_drawer.py create mode 100644 platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/helper.py create mode 100644 platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/pcie.py create mode 100644 platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/platform.py create mode 100644 platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/psu.py create mode 100644 platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/sfp.py create mode 100644 platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/thermal.py create mode 100644 platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/watchdog.py create mode 100644 platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/systemd/platform-modules-sse-t7132s.service create mode 100644 platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/systemd/sysled.service diff --git a/device/supermicro/x86_64-supermicro_sse_t7132s-r0/CSV/TL7_DAC_1M.csv b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/CSV/TL7_DAC_1M.csv new file mode 100755 index 0000000000..00afc9d8ef --- /dev/null +++ b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/CSV/TL7_DAC_1M.csv @@ -0,0 +1,263 @@ +VERSION,CABLE TYPE,VENDOR,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,, +1.2,DAC_1M,GENERIC,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,, +,,,SPEED,ENCODING,,,,,,,,,SPEED,ENCODING,,,,,,,,,,,,,SPEED,ENCODING,,,,,,,SPEED,ENCODING,,,,,,,SPEED,ENCODING,,,,,,,,,, +,,,50G/400G,PAM4,,,,,,,,,25G/100G,NRZ,,,,,,,,,,,,,10G/40G,NRZ,,,,,,,LT 50G/400G ,PAM4,,,,,,,ANLT 25G/100G ,NRZ,,,,,,,,,, +index,Front Port,lane,TX_EQ_ATTN,TX_EQ_PRE1,TX_EQ_PRE2,TX_EQ_PRE3,TX_EQ_POST,RX_EQ_COARSE_TUNE_EFFORT_50G,RX_EQ_FINE_TUNE_EFFORT_50G,RX_GAINSHAPE1,RX_GAINSHAPE2,LINK_TRAINING,TX_EQ_ATTN,TX_EQ_PRE1,TX_EQ_PRE2,TX_EQ_PRE3,TX_EQ_POST,RX_GAINSHAPE1,RX_GAINSHAPE2,RX_AGC_TARGET,RX_EYE_DISQUALIFY_THRESHOLD_25G,RX_EQ_COARSE_TUNE_EFFORT_25G,RX_EQ_FINE_TUNE_EFFORT_25G,SD_RESET_THRESHOLD,SD_RESET_25G,LINK_TRAINING,TX_EQ_ATTN,TX_EQ_PRE1,TX_EQ_PRE2,TX_EQ_PRE3,TX_EQ_POST,RX_GAINSHAPE1,RX_GAINSHAPE2,LINK_TRAINING,RX_GAINSHAPE1,RX_GAINSHAPE2,RX_EQ_COARSE_TUNE_EFFORT_50G,RX_EQ_FINE_TUNE_EFFORT_50G,RX_CTLE_LF,RX_CTLE_HF,RX_CTLE_BW,LINK_TRAINING,RX_GAINSHAPE1,RX_GAINSHAPE2,RX_AGC_TARGET,RX_EYE_DISQUALIFY_THRESHOLD_25G,RX_EQ_COARSE_TUNE_EFFORT_25G,RX_EQ_FINE_TUNE_EFFORT_25G,SD_RESET_25G,SD_RESET_THRESHOLD_25G,LINK_TRAINING,AN,AN_ABILITY,FEC +0,0,0,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +1,0,1,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +2,0,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +3,0,3,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +4,0,4,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +5,0,5,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +6,0,6,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +7,0,7,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +8,1,0,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +9,1,1,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +10,1,2,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +11,1,3,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +12,1,4,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +13,1,5,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +14,1,6,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +15,1,7,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +16,2,0,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +17,2,1,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +18,2,2,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +19,2,3,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +20,2,4,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +21,2,5,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +22,2,6,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +23,2,7,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +24,3,0,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +25,3,1,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +26,3,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +27,3,3,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +28,3,4,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +29,3,5,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +30,3,6,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +31,3,7,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +32,4,0,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +33,4,1,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +34,4,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +35,4,3,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +36,4,4,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +37,4,5,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +38,4,6,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +39,4,7,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +40,5,0,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +41,5,1,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +42,5,2,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +43,5,3,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +44,5,4,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +45,5,5,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +46,5,6,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +47,5,7,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +48,6,0,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +49,6,1,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +50,6,2,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +51,6,3,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +52,6,4,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +53,6,5,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +54,6,6,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +55,6,7,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +56,7,0,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +57,7,1,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +58,7,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +59,7,3,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +60,7,4,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +61,7,5,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +62,7,6,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +63,7,7,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +64,8,0,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +65,8,1,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +66,8,2,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +67,8,3,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +68,8,4,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +69,8,5,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +70,8,6,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +71,8,7,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +72,9,0,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +73,9,1,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +74,9,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +75,9,3,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +76,9,4,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +77,9,5,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +78,9,6,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +79,9,7,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +80,10,0,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +81,10,1,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +82,10,2,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +83,10,3,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +84,10,4,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +85,10,5,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +86,10,6,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +87,10,7,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +88,11,0,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +89,11,1,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +90,11,2,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +91,11,3,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +92,11,4,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +93,11,5,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +94,11,6,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +95,11,7,0,2,0,0,2,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +96,12,0,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +97,12,1,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +98,12,2,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +99,12,3,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +100,12,4,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +101,12,5,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +102,12,6,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +103,12,7,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +104,13,0,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +105,13,1,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +106,13,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +107,13,3,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +108,13,4,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +109,13,5,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +110,13,6,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +111,13,7,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +112,14,0,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +113,14,1,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +114,14,2,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +115,14,3,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +116,14,4,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +117,14,5,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +118,14,6,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +119,14,7,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +120,15,0,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +121,15,1,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +122,15,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +123,15,3,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +124,15,4,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +125,15,5,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +126,15,6,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +127,15,7,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +128,16,0,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +129,16,1,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +130,16,2,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +131,16,3,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +132,16,4,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +133,16,5,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +134,16,6,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +135,16,7,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +136,17,0,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +137,17,1,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +138,17,2,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +139,17,3,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +140,17,4,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +141,17,5,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +142,17,6,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +143,17,7,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +144,18,0,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +145,18,1,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +146,18,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +147,18,3,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +148,18,4,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +149,18,5,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +150,18,6,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +151,18,7,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +152,19,0,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +153,19,1,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +154,19,2,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +155,19,3,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +156,19,4,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +157,19,5,0,4,0,0,4,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +158,19,6,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +159,19,7,0,2,0,0,2,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +160,20,0,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +161,20,1,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +162,20,2,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +163,20,3,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +164,20,4,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +165,20,5,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +166,20,6,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +167,20,7,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +168,21,0,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +169,21,1,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +170,21,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +171,21,3,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +172,21,4,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +173,21,5,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +174,21,6,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +175,21,7,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +176,22,0,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +177,22,1,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +178,22,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +179,22,3,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +180,22,4,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +181,22,5,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +182,22,6,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +183,22,7,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +184,23,0,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +185,23,1,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +186,23,2,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +187,23,3,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +188,23,4,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +189,23,5,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +190,23,6,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +191,23,7,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +192,24,0,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +193,24,1,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +194,24,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +195,24,3,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +196,24,4,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +197,24,5,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +198,24,6,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +199,24,7,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +200,25,0,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +201,25,1,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +202,25,2,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +203,25,3,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +204,25,4,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +205,25,5,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +206,25,6,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +207,25,7,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +208,26,0,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +209,26,1,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +210,26,2,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +211,26,3,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +212,26,4,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +213,26,5,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +214,26,6,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +215,26,7,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +216,27,0,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +217,27,1,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +218,27,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +219,27,3,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +220,27,4,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +221,27,5,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +222,27,6,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +223,27,7,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +224,28,0,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +225,28,1,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +226,28,2,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +227,28,3,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +228,28,4,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +229,28,5,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +230,28,6,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +231,28,7,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +232,29,0,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +233,29,1,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +234,29,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +235,29,3,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +236,29,4,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +237,29,5,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +238,29,6,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +239,29,7,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +240,30,0,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +241,30,1,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +242,30,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +243,30,3,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +244,30,4,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +245,30,5,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +246,30,6,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +247,30,7,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +248,31,0,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +249,31,1,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +250,31,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +251,31,3,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +252,31,4,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +253,31,5,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +254,31,6,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +255,31,7,0,8,0,0,8,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +256,32,0,0,0,0,0,0,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,10GBASE-CR4,NONE +257,32,1,0,0,0,0,0,Medium,HIGH,0,2,0,0,0,0,0,0,0,1,130,100,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,10GBASE-CR4,NONE diff --git a/device/supermicro/x86_64-supermicro_sse_t7132s-r0/CSV/TL7_DAC_3M.csv b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/CSV/TL7_DAC_3M.csv new file mode 100755 index 0000000000..6b9579b3d0 --- /dev/null +++ b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/CSV/TL7_DAC_3M.csv @@ -0,0 +1,263 @@ +VERSION,CABLE TYPE,VENDOR,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,, +1.2,DAC_3M,GENERIC,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,, +,,,SPEED,ENCODING,,,,,,,,,SPEED,ENCODING,,,,,,,,,,,,,SPEED,ENCODING,,,,,,,SPEED,ENCODING,,,,,,,SPEED,ENCODING,,,,,,,,,, +,,,50G/400G,PAM4,,,,,,,,,25G/100G,NRZ,,,,,,,,,,,,,10G/40G,NRZ,,,,,,,LT 50G/400G,PAM4,,,,,,,ANLT 25G/100G,NRZ,,,,,,,,,, +index,Front Port,lane,TX_EQ_ATTN,TX_EQ_PRE1,TX_EQ_PRE2,TX_EQ_PRE3,TX_EQ_POST,RX_EQ_COARSE_TUNE_EFFORT_50G,RX_EQ_FINE_TUNE_EFFORT_50G,RX_GAINSHAPE1,RX_GAINSHAPE2,LINK_TRAINING,TX_EQ_ATTN,TX_EQ_PRE1,TX_EQ_PRE2,TX_EQ_PRE3,TX_EQ_POST,RX_GAINSHAPE1,RX_GAINSHAPE2,RX_AGC_TARGET,RX_EYE_DISQUALIFY_THRESHOLD_25G,RX_EQ_COARSE_TUNE_EFFORT_25G,RX_EQ_FINE_TUNE_EFFORT_25G,SD_RESET_THRESHOLD,SD_RESET_25G,LINK_TRAINING,TX_EQ_ATTN,TX_EQ_PRE1,TX_EQ_PRE2,TX_EQ_PRE3,TX_EQ_POST,RX_GAINSHAPE1,RX_GAINSHAPE2,LINK_TRAINING,RX_GAINSHAPE1,RX_GAINSHAPE2,RX_EQ_COARSE_TUNE_EFFORT_50G,RX_EQ_FINE_TUNE_EFFORT_50G,RX_CTLE_LF,RX_CTLE_HF,RX_CTLE_BW,LINK_TRAINING,RX_GAINSHAPE1,RX_GAINSHAPE2,RX_AGC_TARGET,RX_EYE_DISQUALIFY_THRESHOLD_25G,RX_EQ_COARSE_TUNE_EFFORT_25G,RX_EQ_FINE_TUNE_EFFORT_25G,SD_RESET_25G,SD_RESET_THRESHOLD_25G,LINK_TRAINING,AN,AN_ABILITY,FEC +0,0,0,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +1,0,1,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +2,0,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +3,0,3,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +4,0,4,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +5,0,5,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +6,0,6,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +7,0,7,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +8,1,0,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +9,1,1,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +10,1,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +11,1,3,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +12,1,4,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +13,1,5,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +14,1,6,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +15,1,7,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +16,2,0,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +17,2,1,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +18,2,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +19,2,3,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +20,2,4,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +21,2,5,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +22,2,6,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +23,2,7,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +24,3,0,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +25,3,1,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +26,3,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +27,3,3,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +28,3,4,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +29,3,5,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +30,3,6,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +31,3,7,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +32,4,0,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +33,4,1,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +34,4,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +35,4,3,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +36,4,4,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +37,4,5,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +38,4,6,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +39,4,7,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +40,5,0,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +41,5,1,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +42,5,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +43,5,3,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +44,5,4,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +45,5,5,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +46,5,6,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +47,5,7,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +48,6,0,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +49,6,1,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +50,6,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +51,6,3,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +52,6,4,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +53,6,5,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +54,6,6,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +55,6,7,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +56,7,0,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +57,7,1,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +58,7,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +59,7,3,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +60,7,4,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +61,7,5,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +62,7,6,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +63,7,7,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +64,8,0,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +65,8,1,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +66,8,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +67,8,3,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +68,8,4,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +69,8,5,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +70,8,6,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +71,8,7,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +72,9,0,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +73,9,1,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +74,9,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +75,9,3,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +76,9,4,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +77,9,5,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +78,9,6,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +79,9,7,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +80,10,0,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +81,10,1,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +82,10,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +83,10,3,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +84,10,4,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +85,10,5,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +86,10,6,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +87,10,7,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +88,11,0,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +89,11,1,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +90,11,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +91,11,3,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +92,11,4,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +93,11,5,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +94,11,6,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +95,11,7,0,2,0,0,2,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +96,12,0,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +97,12,1,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +98,12,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +99,12,3,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +100,12,4,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +101,12,5,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +102,12,6,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +103,12,7,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +104,13,0,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +105,13,1,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +106,13,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +107,13,3,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +108,13,4,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +109,13,5,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +110,13,6,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +111,13,7,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +112,14,0,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +113,14,1,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +114,14,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +115,14,3,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +116,14,4,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +117,14,5,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +118,14,6,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +119,14,7,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +120,15,0,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +121,15,1,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +122,15,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +123,15,3,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +124,15,4,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +125,15,5,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +126,15,6,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +127,15,7,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +128,16,0,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +129,16,1,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +130,16,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +131,16,3,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +132,16,4,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +133,16,5,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +134,16,6,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +135,16,7,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +136,17,0,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +137,17,1,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +138,17,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +139,17,3,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +140,17,4,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +141,17,5,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +142,17,6,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +143,17,7,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +144,18,0,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +145,18,1,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +146,18,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +147,18,3,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +148,18,4,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +149,18,5,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +150,18,6,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +151,18,7,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +152,19,0,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +153,19,1,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +154,19,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +155,19,3,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +156,19,4,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +157,19,5,0,4,0,0,4,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +158,19,6,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +159,19,7,0,2,0,0,2,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +160,20,0,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +161,20,1,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +162,20,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +163,20,3,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +164,20,4,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +165,20,5,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +166,20,6,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +167,20,7,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +168,21,0,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +169,21,1,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +170,21,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +171,21,3,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +172,21,4,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +173,21,5,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +174,21,6,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +175,21,7,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +176,22,0,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +177,22,1,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +178,22,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +179,22,3,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +180,22,4,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +181,22,5,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +182,22,6,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +183,22,7,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +184,23,0,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +185,23,1,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +186,23,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +187,23,3,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +188,23,4,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +189,23,5,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +190,23,6,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +191,23,7,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +192,24,0,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +193,24,1,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +194,24,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +195,24,3,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +196,24,4,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +197,24,5,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +198,24,6,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +199,24,7,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +200,25,0,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +201,25,1,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +202,25,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +203,25,3,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +204,25,4,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +205,25,5,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +206,25,6,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +207,25,7,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +208,26,0,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +209,26,1,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +210,26,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +211,26,3,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +212,26,4,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +213,26,5,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +214,26,6,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +215,26,7,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +216,27,0,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +217,27,1,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +218,27,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +219,27,3,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +220,27,4,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +221,27,5,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +222,27,6,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +223,27,7,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +224,28,0,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +225,28,1,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +226,28,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +227,28,3,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +228,28,4,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +229,28,5,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +230,28,6,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +231,28,7,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +232,29,0,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +233,29,1,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +234,29,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +235,29,3,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +236,29,4,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +237,29,5,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +238,29,6,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +239,29,7,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +240,30,0,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +241,30,1,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +242,30,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +243,30,3,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +244,30,4,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +245,30,5,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +246,30,6,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +247,30,7,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +248,31,0,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +249,31,1,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +250,31,2,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +251,31,3,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +252,31,4,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +253,31,5,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +254,31,6,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +255,31,7,0,6,0,0,6,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,1,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,100GBASE-KR4,NONE +256,32,0,0,0,0,0,0,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,2,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,10GBASE-CR4,NONE +257,32,1,0,0,0,0,0,Medium,HIGH,0,2,0,0,0,0,0,0,2,2,130,150,Low,Low,5,TRUE,0,3,2,-2,0,4,0,2,0,0,2,Medium,High,0,10,10,1,0,1,130,100,Low,Low,0,NA,1,1,10GBASE-CR4,NONE diff --git a/device/supermicro/x86_64-supermicro_sse_t7132s-r0/CSV/TL7_Optics.csv b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/CSV/TL7_Optics.csv new file mode 100755 index 0000000000..07ac2b449d --- /dev/null +++ b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/CSV/TL7_Optics.csv @@ -0,0 +1,263 @@ +VERSION,CABLE TYPE,VENDOR,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,, +1.2,OPTICS,GENERIC,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,, +,,,SPEED,ENCODING,,,,,,,,,,SPEED,ENCODING,,,,,,,,,,,,,,SPEED,ENCODING,,,,,, +,,,50G/400G,PAM4,,,,,,,,,,25G/100G,NRZ,,,,,,,,,,,,,,10G/40G,NRZ,,,,,, +index,Front Port,lane,TX_EQ_ATTN,TX_EQ_PRE1,TX_EQ_PRE2,TX_EQ_PRE3,TX_EQ_POST,Optical Module CTLE,RX_EQ_COARSE_TUNE_EFFORT_50G,RX_EQ_FINE_TUNE_EFFORT_50G,RX_GAINSHAPE1,RX_GAINSHAPE2,LINK_TRAINING,TX_EQ_ATTN,TX_EQ_PRE1,TX_EQ_PRE2,TX_EQ_PRE3,TX_EQ_POST,Optical Module CTLE,RX_GAINSHAPE1,RX_GAINSHAPE2,RX_AGC_TARGET,RX_EYE_DISQUALIFY_THRESHOLD_25G,RX_EQ_COARSE_TUNE_EFFORT_25G,RX_EQ_FINE_TUNE_EFFORT_25G,SD_RESET_THRESHOLD,SD_RESET_25G,LINK_TRAINING,TX_EQ_ATTN,TX_EQ_PRE1,TX_EQ_PRE2,TX_EQ_PRE3,TX_EQ_POST,RX_GAINSHAPE1,RX_GAINSHAPE2,LINK_TRAINING +0,0,0,0,4,0,0,4,4.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,High,High,NA,FALSE,0,0,0,0,0,0,0,0,0 +1,0,1,0,4,-1,0,2,6,Medium,High,0,0,0,0,4,0,0,4,4,0,0,100,100,High,High,NA,FALSE,0,0,0,0,0,0,0,0,0 +2,0,2,0,4,0,0,0,6,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,High,High,NA,FALSE,0,0,0,0,0,0,0,0,0 +3,0,3,0,4,0,0,4,4.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,High,High,NA,FALSE,0,0,0,0,0,0,0,0,0 +4,0,4,0,4,0,0,4,5.5,Medium,High,0,0,0,0,4,0,0,4,4,0,0,100,100,High,High,NA,FALSE,0,0,0,0,0,0,0,0,0 +5,0,5,0,4,0,0,4,5.5,Medium,High,0,0,0,0,2,0,0,4,4,0,0,100,100,High,High,NA,FALSE,0,0,0,0,0,0,0,0,0 +6,0,6,0,4,0,0,4,5.5,Medium,High,0,0,0,0,4,0,0,4,4,0,0,100,100,High,High,NA,FALSE,0,0,0,0,0,0,0,0,0 +7,0,7,0,4,0,0,4,5,Medium,High,0,0,0,0,4,0,0,4,4,0,0,100,100,High,High,NA,FALSE,0,0,0,0,0,0,0,0,0 +8,1,0,0,4,0,0,2,4.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +9,1,1,0,4,0,0,2,5.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +10,1,2,0,4,0,0,0,6,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +11,1,3,0,4,0,0,2,5.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +12,1,4,0,4,0,0,2,5.5,Medium,High,0,0,0,0,4,-1,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +13,1,5,0,4,0,0,2,5.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +14,1,6,0,4,0,0,4,5,Medium,High,0,0,0,0,4,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +15,1,7,0,4,0,0,2,5.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +16,2,0,0,4,0,0,0,6,Medium,High,0,0,0,0,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +17,2,1,0,4,0,0,2,5.5,Medium,High,0,0,0,0,2,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +18,2,2,0,4,0,0,0,6,Medium,High,0,0,0,0,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +19,2,3,0,4,0,0,0,6,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +20,2,4,0,4,0,0,4,5,Medium,High,0,0,0,0,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +21,2,5,0,4,0,0,2,5.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +22,2,6,0,4,0,0,4,5,Medium,High,0,0,0,0,2,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +23,2,7,0,4,0,0,2,5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +24,3,0,0,4,0,0,2,5.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +25,3,1,0,4,0,0,2,5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +26,3,2,0,4,0,0,0,5.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +27,3,3,0,4,0,0,2,5.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +28,3,4,0,4,-1,0,0,5.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +29,3,5,0,4,0,0,2,5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +30,3,6,0,2,0,0,4,4.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +31,3,7,0,4,0,0,2,5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +32,4,0,0,4,0,0,2,4,Medium,High,0,0,0,0,6,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +33,4,1,0,2,0,0,2,5.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +34,4,2,0,4,0,0,2,4,Medium,High,0,0,0,1,0,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +35,4,3,0,4,0,0,2,4.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +36,4,4,0,4,0,0,2,5.5,Medium,High,0,0,0,0,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +37,4,5,0,4,0,0,2,5,Medium,High,0,0,0,0,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +38,4,6,0,4,0,0,2,5.5,Medium,High,0,0,0,0,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +39,4,7,0,4,0,0,2,4.5,Medium,High,0,0,0,0,4,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +40,5,0,0,4,0,0,0,5,Medium,High,0,0,0,0,4,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +41,5,1,0,4,0,0,0,5,Medium,High,0,0,0,0,4,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +42,5,2,0,4,0,0,2,5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +43,5,3,0,4,0,0,0,5,Medium,High,0,0,0,0,4,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +44,5,4,0,4,0,0,2,4.5,Medium,High,0,0,0,0,4,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +45,5,5,0,2,0,0,4,4,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +46,5,6,0,4,0,0,2,5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +47,5,7,0,4,0,0,0,5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +48,6,0,0,4,0,0,0,5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +49,6,1,0,4,0,0,2,5.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +50,6,2,0,4,0,0,2,4,Medium,High,0,0,0,0,4,-1,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +51,6,3,0,4,0,0,0,5.5,Medium,High,0,0,0,0,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +52,6,4,0,4,0,0,2,5.5,Medium,High,0,0,0,0,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +53,6,5,0,4,0,0,2,5.5,Medium,High,0,0,0,0,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +54,6,6,0,2,0,0,2,5.5,Medium,High,0,0,0,0,2,0,1,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +55,6,7,0,4,0,0,2,4.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +56,7,0,0,4,0,0,0,5.5,Medium,High,0,0,0,0,4,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +57,7,1,0,4,0,0,0,5.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +58,7,2,0,4,-1,0,0,5.5,Medium,High,0,0,0,0,4,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +59,7,3,0,4,0,0,2,4,Medium,High,0,0,0,0,4,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +60,7,4,0,4,0,0,0,5,Medium,High,0,0,0,0,4,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +61,7,5,0,4,0,0,0,4.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +62,7,6,0,4,0,0,0,5.5,Medium,High,0,0,0,0,4,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +63,7,7,0,4,0,0,4,4,Medium,High,0,0,0,1,4,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +64,8,0,0,4,0,0,4,4.5,Medium,High,0,0,0,0,4,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +65,8,1,0,4,0,0,4,5,Medium,High,0,0,0,0,4,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +66,8,2,0,4,0,0,2,6,Medium,High,0,0,0,0,4,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +67,8,3,0,4,0,0,2,5,Medium,High,0,0,0,0,4,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +68,8,4,0,4,0,0,4,6,Medium,High,0,0,0,0,2,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +69,8,5,0,4,0,0,4,5.5,Medium,High,0,0,0,0,4,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +70,8,6,0,2,0,0,4,6,Medium,High,0,0,0,0,4,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +71,8,7,0,4,0,0,4,4.5,Medium,High,0,0,0,0,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +72,9,0,0,4,0,0,4,5.5,Medium,High,0,0,0,0,2,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +73,9,1,0,4,0,0,0,6.5,Medium,High,0,0,0,0,4,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +74,9,2,0,4,0,0,4,5.5,Medium,High,0,0,0,0,2,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +75,9,3,0,4,0,0,0,6.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +76,9,4,0,4,0,0,4,6,Medium,High,0,0,0,0,4,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +77,9,5,0,4,0,0,4,5.5,Medium,High,0,0,0,0,4,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +78,9,6,0,4,0,0,2,6,Medium,High,0,0,0,0,2,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +79,9,7,0,4,0,0,4,5.5,Medium,High,0,0,0,0,4,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +80,10,0,0,4,0,0,4,4,Medium,High,0,0,0,0,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +81,10,1,0,4,0,0,4,5.5,Medium,High,0,0,0,0,4,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +82,10,2,0,4,0,0,4,4,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +83,10,3,0,4,0,0,2,6,Medium,High,0,0,0,0,4,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +84,10,4,0,4,-1,0,4,6,Medium,High,0,0,0,0,6,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +85,10,5,0,4,0,0,4,5.5,Medium,High,0,0,0,0,4,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +86,10,6,0,4,0,0,4,5,Medium,High,0,0,0,0,4,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +87,10,7,0,4,0,0,4,4.5,Medium,High,0,0,0,0,4,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +88,11,0,0,4,0,0,0,6.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +89,11,1,0,4,0,0,2,5.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +90,11,2,0,4,0,0,0,6,Medium,High,0,0,0,0,4,0,1,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +91,11,3,0,4,0,0,0,5.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +92,11,4,0,4,0,0,4,5,Medium,High,0,0,0,0,4,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +93,11,5,0,4,0,0,2,7,Medium,High,0,0,0,0,4,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +94,11,6,0,4,0,0,2,5.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +95,11,7,0,4,0,0,2,5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +96,12,0,0,4,0,0,0,5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +97,12,1,0,4,0,0,2,5.5,Medium,High,0,0,0,0,4,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +98,12,2,0,4,0,0,0,5.5,Medium,High,0,0,0,0,4,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +99,12,3,0,4,0,0,2,5,Medium,High,0,0,0,2,2,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +100,12,4,0,4,0,0,2,6,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +101,12,5,0,4,0,0,2,5.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +102,12,6,0,4,0,0,4,4.5,Medium,High,0,0,0,0,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +103,12,7,0,4,0,0,0,5.5,Medium,High,0,0,0,0,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +104,13,0,0,2,0,0,4,4.5,Medium,High,0,0,0,0,4,-1,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +105,13,1,0,4,0,0,0,5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +106,13,2,0,4,0,0,0,5,Medium,High,0,0,0,0,4,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +107,13,3,0,2,0,0,2,4.5,Medium,High,0,0,0,1,4,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +108,13,4,0,4,0,0,2,6,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +109,13,5,0,4,0,0,4,4,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +110,13,6,0,4,0,0,0,5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +111,13,7,0,4,-1,0,0,5,Medium,High,0,0,0,0,4,-1,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +112,14,0,0,4,0,0,0,5,Medium,High,0,0,0,4,0,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +113,14,1,0,4,0,0,2,4.5,Medium,High,0,0,0,0,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +114,14,2,0,4,0,0,0,5,Medium,High,0,0,0,0,4,0,1,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +115,14,3,0,4,0,0,0,5,Medium,High,0,0,0,1,4,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +116,14,4,0,4,0,0,4,4.5,Medium,High,0,0,0,0,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +117,14,5,0,4,0,0,2,5.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +118,14,6,0,4,0,0,0,5.5,Medium,High,0,0,0,0,4,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +119,14,7,0,4,0,0,0,5,Medium,High,0,0,0,1,4,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +120,15,0,0,4,0,0,2,5.5,Medium,High,0,0,0,0,4,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +121,15,1,0,4,0,0,0,5.5,Medium,High,0,0,0,0,4,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +122,15,2,0,4,0,0,0,5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +123,15,3,0,4,0,0,0,5.5,Medium,High,0,0,0,0,4,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +124,15,4,0,4,-1,0,0,5,Medium,High,0,0,0,0,4,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +125,15,5,0,4,0,0,0,5,Medium,High,0,0,0,0,4,-1,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +126,15,6,0,4,0,0,0,4.5,Medium,High,0,0,0,0,4,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +127,15,7,0,4,0,0,0,5.5,Medium,High,0,0,0,0,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +128,16,0,0,2,0,0,2,4.5,Medium,High,0,0,0,0,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +129,16,1,0,4,0,0,0,5,Medium,High,0,0,0,0,4,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +130,16,2,0,4,0,0,0,5.5,Medium,High,0,0,0,0,4,0,1,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +131,16,3,0,4,0,0,2,4.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +132,16,4,0,4,0,0,0,5.5,Medium,High,0,0,0,0,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +133,16,5,0,2,0,0,2,5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +134,16,6,0,4,0,0,0,6.5,Medium,High,0,0,0,0,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +135,16,7,0,4,0,0,2,5,Medium,High,0,0,0,0,4,0,1,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +136,17,0,0,4,0,0,0,5.5,Medium,High,0,0,0,0,4,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +137,17,1,0,4,0,0,0,5.5,Medium,High,0,0,0,0,4,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +138,17,2,0,4,0,0,0,5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +139,17,3,0,4,0,0,0,5.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +140,17,4,1,4,0,0,0,5.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +141,17,5,0,4,0,0,0,5.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +142,17,6,0,4,0,0,2,4.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +143,17,7,0,4,0,0,2,5,Medium,High,0,0,0,1,4,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +144,18,0,0,4,0,0,2,4.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +145,18,1,0,4,0,0,2,5,Medium,High,0,0,0,0,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +146,18,2,0,4,0,0,0,5.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +147,18,3,0,4,0,0,2,5,Medium,High,0,0,0,0,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +148,18,4,0,2,0,0,0,7,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +149,18,5,0,2,0,0,2,5.5,Medium,High,0,0,0,0,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +150,18,6,0,4,0,0,2,5.5,Medium,High,0,0,0,0,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +151,18,7,0,4,0,0,4,4,Medium,High,0,0,0,0,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +152,19,0,0,2,0,0,0,5.5,Medium,High,0,0,0,0,4,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +153,19,1,0,4,0,0,2,5.5,Medium,High,0,0,0,0,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +154,19,2,0,4,0,0,0,5,Medium,High,0,0,0,0,4,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +155,19,3,0,4,0,0,-2,6,Medium,High,0,0,0,0,4,-1,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +156,19,4,0,4,0,0,0,5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +157,19,5,0,4,0,0,0,4.5,Medium,High,0,0,0,0,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +158,19,6,0,4,0,0,2,4.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +159,19,7,0,4,0,0,0,5,Medium,High,0,0,0,0,4,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +160,20,0,0,4,0,0,2,5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +161,20,1,0,2,0,0,2,5,Medium,High,0,0,0,0,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +162,20,2,0,4,0,0,4,4.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +163,20,3,0,4,0,0,0,5.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +164,20,4,0,2,0,0,2,5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +165,20,5,0,4,0,0,2,5.5,Medium,High,0,0,0,0,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +166,20,6,0,4,0,0,4,4.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +167,20,7,0,4,0,0,2,5.5,Medium,High,0,0,0,0,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +168,21,0,0,4,0,0,0,5.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +169,21,1,0,4,-1,0,0,6,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +170,21,2,0,4,0,0,0,5.5,Medium,High,0,0,0,0,4,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +171,21,3,0,4,0,0,0,5.5,Medium,High,0,0,0,0,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +172,21,4,0,4,0,0,2,4.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +173,21,5,0,4,0,0,2,4.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +174,21,6,0,2,0,0,2,5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +175,21,7,0,4,0,0,2,4.5,Medium,High,0,0,0,0,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +176,22,0,0,4,0,0,4,5,Medium,High,0,0,0,0,2,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +177,22,1,0,4,0,0,2,5.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +178,22,2,0,4,0,0,2,5.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +179,22,3,0,4,-1,0,4,5.5,Medium,High,0,0,0,0,2,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +180,22,4,0,4,0,0,4,4.5,Medium,High,0,0,0,0,2,-1,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +181,22,5,0,4,0,0,4,4.5,Medium,High,0,0,0,0,2,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +182,22,6,0,4,0,0,4,5,Medium,High,0,0,0,0,4,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +183,22,7,0,4,0,0,4,5,Medium,High,0,0,0,0,2,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +184,23,0,0,2,0,0,2,6,Medium,High,0,0,0,0,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +185,23,1,0,4,0,0,4,4.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +186,23,2,0,4,0,0,2,6,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +187,23,3,0,4,0,0,0,6,Medium,High,0,0,0,0,4,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +188,23,4,0,4,0,0,2,5,Medium,High,0,0,0,0,2,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +189,23,5,0,4,0,0,2,5,Medium,High,0,0,0,0,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +190,23,6,0,4,0,0,2,5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +191,23,7,0,4,0,0,4,5.5,Medium,High,0,0,0,0,6,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +192,24,0,0,4,0,0,2,5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +193,24,1,0,2,0,0,2,5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +194,24,2,0,4,0,0,2,4.5,Medium,High,0,0,0,1,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +195,24,3,0,4,0,0,0,5.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +196,24,4,0,4,0,0,4,4.5,Medium,High,0,0,0,0,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +197,24,5,0,4,0,0,2,5,Medium,High,0,0,0,0,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +198,24,6,0,4,0,0,2,4.5,Medium,High,0,0,0,0,4,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +199,24,7,0,4,0,0,2,4,Medium,High,0,0,0,0,4,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +200,25,0,0,4,0,0,0,5.5,Medium,High,0,0,0,0,4,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +201,25,1,0,4,0,0,0,5,Medium,High,0,0,0,0,4,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +202,25,2,0,4,0,0,2,4.5,Medium,High,0,0,0,0,4,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +203,25,3,0,4,0,0,2,5,Medium,High,0,0,0,0,4,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +204,25,4,0,4,0,0,0,5.5,Medium,High,0,0,0,0,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +205,25,5,0,4,0,0,0,5,Medium,High,0,0,0,1,4,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +206,25,6,0,4,0,0,2,5,Medium,High,0,0,0,0,4,-1,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +207,25,7,0,4,0,0,2,5,Medium,High,0,0,0,0,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +208,26,0,0,4,0,0,2,5.5,Medium,High,0,0,0,0,4,0,-1,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +209,26,1,0,4,0,0,2,5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +210,26,2,0,4,0,0,0,5,Medium,High,0,0,0,0,4,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +211,26,3,0,4,0,0,2,4.5,Medium,High,0,0,0,0,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +212,26,4,0,2,0,0,2,5,Medium,High,0,0,0,0,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +213,26,5,0,4,0,0,0,5.5,Medium,High,0,0,0,0,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +214,26,6,0,4,0,0,4,3.5,Medium,High,0,0,0,0,2,-1,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +215,26,7,0,4,0,0,0,5,Medium,High,0,0,0,0,4,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +216,27,0,0,4,0,0,2,5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +217,27,1,0,4,0,0,2,6,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +218,27,2,0,4,0,0,2,5,Medium,High,0,0,0,0,4,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +219,27,3,0,4,0,0,4,5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +220,27,4,0,4,0,0,2,5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +221,27,5,0,4,0,0,4,4.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +222,27,6,0,2,0,0,0,6,Medium,High,0,0,0,0,4,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +223,27,7,0,4,0,0,2,5.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +224,28,0,0,4,0,0,0,5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +225,28,1,0,4,0,0,2,4.5,Medium,High,0,0,0,2,2,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +226,28,2,0,4,0,0,0,4.5,Medium,High,0,0,0,0,4,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +227,28,3,0,4,0,0,2,5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +228,28,4,0,4,0,0,2,4.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +229,28,5,0,2,0,0,2,5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +230,28,6,0,2,0,0,2,4.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +231,28,7,0,4,0,0,2,5,Medium,High,0,0,0,0,4,0,0,0,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +232,29,0,0,4,0,0,4,4,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +233,29,1,0,4,0,0,4,5.5,Medium,High,0,0,0,0,4,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +234,29,2,0,4,0,0,2,5,Medium,High,0,0,0,0,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +235,29,3,0,4,0,0,2,5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +236,29,4,0,4,0,0,2,5,Medium,High,0,0,0,0,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +237,29,5,0,4,0,0,4,5.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +238,29,6,0,4,0,0,2,5,Medium,High,0,0,0,0,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +239,29,7,0,4,0,0,2,5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +240,30,0,0,4,0,0,2,4.5,Medium,High,0,0,0,0,2,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +241,30,1,0,4,0,0,2,5.5,Medium,High,0,0,0,0,2,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +242,30,2,0,4,0,0,2,5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +243,30,3,0,2,0,0,2,6,Medium,High,0,0,0,0,2,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +244,30,4,0,4,0,0,2,5,Medium,High,0,0,0,0,4,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +245,30,5,0,4,0,0,4,5,Medium,High,0,0,0,0,4,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +246,30,6,0,4,0,0,4,4.5,Medium,High,0,0,0,0,4,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +247,30,7,0,4,0,0,4,5,Medium,High,0,0,0,0,2,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +248,31,0,0,4,0,0,4,4.5,Medium,High,0,0,0,0,4,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +249,31,1,0,4,0,-1,2,5.5,Medium,High,0,0,0,0,4,0,1,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +250,31,2,0,4,0,0,2,4.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +251,31,3,0,4,0,0,4,4.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +252,31,4,0,4,-1,0,4,5.5,Medium,High,0,0,0,0,4,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +253,31,5,0,4,0,0,4,6,Medium,High,0,0,0,0,4,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +254,31,6,0,4,0,0,2,5,Medium,High,0,0,0,0,4,-1,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +255,31,7,0,4,0,0,2,5.5,Medium,High,0,0,0,0,4,0,0,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +256,32,0,0,4,0,0,4,4.5,Medium,High,0,0,0,0,4,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +257,32,1,0,4,0,0,2,5.5,Medium,High,0,0,0,0,4,0,1,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 diff --git a/device/supermicro/x86_64-supermicro_sse_t7132s-r0/CSV/TL7_RJ45.csv b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/CSV/TL7_RJ45.csv new file mode 100755 index 0000000000..342eef9976 --- /dev/null +++ b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/CSV/TL7_RJ45.csv @@ -0,0 +1,7 @@ +VERSION,CABLE TYPE,VENDOR,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,, +1.2,RJ45,GENERIC,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,, +,,,SPEED,ENCODING,,,,,,,,,,SPEED,ENCODING,,,,,,,,,,,,,,SPEED,ENCODING,,,,,, +,,,50G/400G,PAM4,,,,,,,,,,25G/100G,NRZ,,,,,,,,,,,,,,10G/40G,NRZ,,,,,, +index,Front Port,lane,TX_EQ_ATTN,TX_EQ_PRE1,TX_EQ_PRE2,TX_EQ_PRE3,TX_EQ_POST,Optical Module CTLE,RX_EQ_COARSE_TUNE_EFFORT_50G,RX_EQ_FINE_TUNE_EFFORT_50G,RX_GAINSHAPE1,RX_GAINSHAPE2,LINK_TRAINING,TX_EQ_ATTN,TX_EQ_PRE1,TX_EQ_PRE2,TX_EQ_PRE3,TX_EQ_POST,Optical Module CTLE,RX_GAINSHAPE1,RX_GAINSHAPE2,RX_AGC_TARGET,RX_EYE_DISQUALIFY_THRESHOLD_25G,RX_EQ_COARSE_TUNE_EFFORT_25G,RX_EQ_FINE_TUNE_EFFORT_25G,SD_RESET_THRESHOLD,SD_RESET_25G,LINK_TRAINING,TX_EQ_ATTN,TX_EQ_PRE1,TX_EQ_PRE2,TX_EQ_PRE3,TX_EQ_POST,RX_GAINSHAPE1,RX_GAINSHAPE2,LINK_TRAINING +256,32,0,0,4,0,0,4,4.5,Medium,High,0,2,0,0,4,0,0,4,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 +257,32,1,0,4,0,0,2,5.5,Medium,High,0,2,0,0,4,0,1,2,4,0,0,100,100,LOW,LOW,NA,FALSE,0,0,0,0,0,0,0,0,0 diff --git a/device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/buffers.json.j2 b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/buffers.json.j2 new file mode 100755 index 0000000000..9b95afc21f --- /dev/null +++ b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/buffers.json.j2 @@ -0,0 +1,167 @@ +{# Default values which will be used if no actual configura available #} +{% set default_cable = '40m' %} +{% set mgmt_port_name = ['Ethernet256','Ethernet257'] %} + +{# Port configuration to cable length look-up table #} +{# Each record describes mapping of DUT (DUT port) role and neighbor role to cable length #} +{# Roles described in the minigraph #} +{% set ports2cable = { + 'torrouter_server' : '5m', + 'leafrouter_torrouter' : '40m', + 'spinerouter_leafrouter' : '300m' + } +%} + +{%- macro cable_length(port_name) %} + {%- set cable_len = [] %} + {%- for local_port in DEVICE_NEIGHBOR %} + {%- if local_port == port_name %} + {%- if DEVICE_NEIGHBOR_METADATA is defined and DEVICE_NEIGHBOR_METADATA[DEVICE_NEIGHBOR[local_port].name] %} + {%- set neighbor = DEVICE_NEIGHBOR_METADATA[DEVICE_NEIGHBOR[local_port].name] %} + {%- set neighbor_role = neighbor.type %} + {%- set roles1 = switch_role + '_' + neighbor_role %} + {%- set roles2 = neighbor_role + '_' + switch_role %} + {%- set roles1 = roles1 | lower %} + {%- set roles2 = roles2 | lower %} + {%- if roles1 in ports2cable %} + {%- if cable_len.append(ports2cable[roles1]) %}{% endif %} + {%- elif roles2 in ports2cable %} + {%- if cable_len.append(ports2cable[roles2]) %}{% endif %} + {%- endif %} + {%- endif %} + {%- endif %} + {%- endfor %} + {%- if cable_len -%} + {{ cable_len.0 }} + {%- else %} + {%- if switch_role.lower() == 'torrouter' %} + {%- for local_port in VLAN_MEMBER %} + {%- if local_port[1] == port_name %} + {%- set roles3 = switch_role + '_' + 'server' %} + {%- set roles3 = roles3 | lower %} + {%- if roles3 in ports2cable %} + {%- if cable_len.append(ports2cable[roles3]) %}{% endif %} + {%- endif %} + {%- endif %} + {%- endfor %} + {%- if cable_len -%} + {{ cable_len.0 }} + {%- else -%} + {{ default_cable }} + {%- endif %} + {%- else -%} + {{ default_cable }} + {%- endif %} + {%- endif %} +{%- endmacro %} + +{%- if DEVICE_METADATA is defined %} +{%- set switch_role = DEVICE_METADATA['localhost']['type'] %} +{%- endif -%} + +{% set port_names_list = [] %} +{% for port in PORT %} + {% if port not in mgmt_port_name %} + {%- if port_names_list.append(port) %}{% endif %} + {% endif %} +{% endfor %} +{% set port_names = port_names_list | join(',') -%} + +{ + "CABLE_LENGTH": { + "AZURE": { + {% for port in PORT %} + {% if port not in mgmt_port_name %} + {% set cable = cable_length(port) -%} + "{{ port }}": "{{ cable }}"{%- if not loop.last -%},{% endif %} + {% endif %} + {% endfor %} + } + }, + "BUFFER_POOL": { + "ingress_lossless_pool": { + "size": "51691264", + "type": "ingress", + "mode": "dynamic", + "xoff": "17708800" + }, + "lossy_pool": { + "size": "18874368", + "type": "egress", + "mode": "dynamic", + "xoff": "0" + }, + "egress_lossless_pool": { + "size": "70565632", + "type": "egress", + "mode": "static" + } + }, + "BUFFER_PROFILE": { + "ingress_lossless_profile": { + "pool":"ingress_lossless_pool", + "xoff":"38816", + "size":"1518", + "dynamic_th":"1", + "xon_offset":"9408" + }, + "egress_lossless_profile": { + "pool":"ingress_lossless_pool", + "size":"0", + "static_th":"10243072" + }, + "ingress_lossy_profile": { + "pool":"lossy_pool", + "size":"0", + "static_th":"10243072" + }, + "egress_lossy_profile": { + "pool":"lossy_pool", + "size":"1518", + "dynamic_th":"2" + } + }, + "BUFFER_PG": { +{% for port in port_names_list %} + "{{ port }}|3-4": { + {% set cable = cable_length(port) -%} + "profile" : "pg_lossless_400000_{{ cable }}_profile" + }, +{% endfor %} +{% for port in port_names_list %} + "{{ port }}|0": { + "profile" : "ingress_lossy_profile" + }, +{% endfor %} +{% for port in port_names_list %} + "{{ port }}|1-2": { + "profile" : "ingress_lossy_profile" + }, +{% endfor %} +{% for port in port_names_list %} + "{{ port }}|5-7": { + "profile" : "ingress_lossy_profile" + }{% if not loop.last %},{% endif %} + +{% endfor %} + }, + + "BUFFER_QUEUE": { +{% for port in port_names_list %} + "{{ port }}|3-4": { + "profile" : "egress_lossless_profile" + }, +{% endfor %} +{% for port in port_names_list %} + "{{ port }}|0-2": { + "profile" : "egress_lossy_profile" + }, +{% endfor %} +{% for port in port_names_list %} + "{{ port }}|5-7": { + "profile" : "egress_lossy_profile" + }{% if not loop.last %},{% endif %} + +{% endfor %} + } +} diff --git a/device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/buffers_defaults_def_lossy.j2 b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/buffers_defaults_def_lossy.j2 new file mode 100644 index 0000000000..8b1291ac26 --- /dev/null +++ b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/buffers_defaults_def_lossy.j2 @@ -0,0 +1,45 @@ +{% set mgmt_port_name = ['Ethernet256','Ethernet257'] %} +{% set port_names_list = [] %} +{% for port in PORT %} + {% if port not in mgmt_port_name %} + {%- if port_names_list.append(port) %}{% endif %} + {% endif %} +{% endfor %} +{% set port_names = port_names_list | join(',') -%} + +{ + "BUFFER_POOL": { + "lossy_pool": { + "size": "61458432", + "type": "egress", + "mode": "dynamic", + "xoff": "0" + } + }, + "BUFFER_PROFILE": { + "ingress_lossy_profile": { + "pool":"lossy_pool", + "size":"0", + "static_th":"10243072" + }, + "egress_lossy_profile": { + "pool":"lossy_pool", + "size":"1518", + "dynamic_th":"2" + } + }, + "BUFFER_PG": { +{% for port in port_names_list %} + "{{ port }}|0-7": { + "profile" : "ingress_lossy_profile" + }{% if not loop.last %},{% endif %} +{% endfor %} + }, + "BUFFER_QUEUE": { +{% for port in port_names_list %} + "{{ port }}|0-7": { + "profile" : "egress_lossy_profile" + }{% if not loop.last %},{% endif %} +{% endfor %} + } +} diff --git a/device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/buffers_defaults_t1.j2 b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/buffers_defaults_t1.j2 new file mode 100755 index 0000000000..9b95afc21f --- /dev/null +++ b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/buffers_defaults_t1.j2 @@ -0,0 +1,167 @@ +{# Default values which will be used if no actual configura available #} +{% set default_cable = '40m' %} +{% set mgmt_port_name = ['Ethernet256','Ethernet257'] %} + +{# Port configuration to cable length look-up table #} +{# Each record describes mapping of DUT (DUT port) role and neighbor role to cable length #} +{# Roles described in the minigraph #} +{% set ports2cable = { + 'torrouter_server' : '5m', + 'leafrouter_torrouter' : '40m', + 'spinerouter_leafrouter' : '300m' + } +%} + +{%- macro cable_length(port_name) %} + {%- set cable_len = [] %} + {%- for local_port in DEVICE_NEIGHBOR %} + {%- if local_port == port_name %} + {%- if DEVICE_NEIGHBOR_METADATA is defined and DEVICE_NEIGHBOR_METADATA[DEVICE_NEIGHBOR[local_port].name] %} + {%- set neighbor = DEVICE_NEIGHBOR_METADATA[DEVICE_NEIGHBOR[local_port].name] %} + {%- set neighbor_role = neighbor.type %} + {%- set roles1 = switch_role + '_' + neighbor_role %} + {%- set roles2 = neighbor_role + '_' + switch_role %} + {%- set roles1 = roles1 | lower %} + {%- set roles2 = roles2 | lower %} + {%- if roles1 in ports2cable %} + {%- if cable_len.append(ports2cable[roles1]) %}{% endif %} + {%- elif roles2 in ports2cable %} + {%- if cable_len.append(ports2cable[roles2]) %}{% endif %} + {%- endif %} + {%- endif %} + {%- endif %} + {%- endfor %} + {%- if cable_len -%} + {{ cable_len.0 }} + {%- else %} + {%- if switch_role.lower() == 'torrouter' %} + {%- for local_port in VLAN_MEMBER %} + {%- if local_port[1] == port_name %} + {%- set roles3 = switch_role + '_' + 'server' %} + {%- set roles3 = roles3 | lower %} + {%- if roles3 in ports2cable %} + {%- if cable_len.append(ports2cable[roles3]) %}{% endif %} + {%- endif %} + {%- endif %} + {%- endfor %} + {%- if cable_len -%} + {{ cable_len.0 }} + {%- else -%} + {{ default_cable }} + {%- endif %} + {%- else -%} + {{ default_cable }} + {%- endif %} + {%- endif %} +{%- endmacro %} + +{%- if DEVICE_METADATA is defined %} +{%- set switch_role = DEVICE_METADATA['localhost']['type'] %} +{%- endif -%} + +{% set port_names_list = [] %} +{% for port in PORT %} + {% if port not in mgmt_port_name %} + {%- if port_names_list.append(port) %}{% endif %} + {% endif %} +{% endfor %} +{% set port_names = port_names_list | join(',') -%} + +{ + "CABLE_LENGTH": { + "AZURE": { + {% for port in PORT %} + {% if port not in mgmt_port_name %} + {% set cable = cable_length(port) -%} + "{{ port }}": "{{ cable }}"{%- if not loop.last -%},{% endif %} + {% endif %} + {% endfor %} + } + }, + "BUFFER_POOL": { + "ingress_lossless_pool": { + "size": "51691264", + "type": "ingress", + "mode": "dynamic", + "xoff": "17708800" + }, + "lossy_pool": { + "size": "18874368", + "type": "egress", + "mode": "dynamic", + "xoff": "0" + }, + "egress_lossless_pool": { + "size": "70565632", + "type": "egress", + "mode": "static" + } + }, + "BUFFER_PROFILE": { + "ingress_lossless_profile": { + "pool":"ingress_lossless_pool", + "xoff":"38816", + "size":"1518", + "dynamic_th":"1", + "xon_offset":"9408" + }, + "egress_lossless_profile": { + "pool":"ingress_lossless_pool", + "size":"0", + "static_th":"10243072" + }, + "ingress_lossy_profile": { + "pool":"lossy_pool", + "size":"0", + "static_th":"10243072" + }, + "egress_lossy_profile": { + "pool":"lossy_pool", + "size":"1518", + "dynamic_th":"2" + } + }, + "BUFFER_PG": { +{% for port in port_names_list %} + "{{ port }}|3-4": { + {% set cable = cable_length(port) -%} + "profile" : "pg_lossless_400000_{{ cable }}_profile" + }, +{% endfor %} +{% for port in port_names_list %} + "{{ port }}|0": { + "profile" : "ingress_lossy_profile" + }, +{% endfor %} +{% for port in port_names_list %} + "{{ port }}|1-2": { + "profile" : "ingress_lossy_profile" + }, +{% endfor %} +{% for port in port_names_list %} + "{{ port }}|5-7": { + "profile" : "ingress_lossy_profile" + }{% if not loop.last %},{% endif %} + +{% endfor %} + }, + + "BUFFER_QUEUE": { +{% for port in port_names_list %} + "{{ port }}|3-4": { + "profile" : "egress_lossless_profile" + }, +{% endfor %} +{% for port in port_names_list %} + "{{ port }}|0-2": { + "profile" : "egress_lossy_profile" + }, +{% endfor %} +{% for port in port_names_list %} + "{{ port }}|5-7": { + "profile" : "egress_lossy_profile" + }{% if not loop.last %},{% endif %} + +{% endfor %} + } +} diff --git a/device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/config_32x400G_sse_t7132s.yaml b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/config_32x400G_sse_t7132s.yaml new file mode 100644 index 0000000000..9c84910a1f --- /dev/null +++ b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/config_32x400G_sse_t7132s.yaml @@ -0,0 +1,440 @@ +ifcs: + options: + log_level: "info" +nodes: +- node_id: "0" + options: + sd_low_power_mode_global_default: "true" + sku: "configs/sku/innovium.77700_A" + netdev: + - auto_create: "no" + multi_interface: "yes" + pcie_attn: "10, 0, 0, 0" + pcie_post: "10, 0, 0, 0" + pcie_pre1: "0, 0, 0, 0" + buffer_management_mode: "api_driven" + wred_cr_ip_proto_list: "17" + cr_assignment_mode: "1" + max_lossless_tc: "2" + ilpm_enable: "1" + ecn_stats_enable: "1" + forward_profile: "IFCS_FORWARD_PROFILE_ID_PROFILE_E" + led_cfg_sck_rate: "0x5" + led_refresh_precliff_timer: "0x18eec2" + led_refresh_cliff_timer: "0x15e" + led_cfg_pic_stream_mode: "1" + led_refresh_tmr_ctl_enable: "1" + txring: + - txring_id: "0" + desc_count: "1024" + prio: "1" + netdev: "true" + - txring_id: "1" + desc_count: "1024" + prio: "1" + netdev: "true" + - txring_id: "2" + desc_count: "1024" + prio: "1" + netdev: "true" + - txring_id: "3" + desc_count: "1024" + prio: "1" + netdev: "true" + rxring: + - rxring_id: "0" + desc_count: "1024" + prio: "1" + netdev: "true" + queues: "0, 3, 6, 9, 12, 15, 18, 21, 24, 27, 30, 33, 36, 39" + - rxring_id: "1" + desc_count: "1024" + prio: "1" + netdev: "true" + queues: "1, 4, 7, 10, 13, 16, 19, 22, 25, 28, 31, 34, 37, 40" + - rxring_id: "2" + desc_count: "1024" + prio: "1" + netdev: "true" + queues: "2, 5, 8, 11, 14, 17, 20, 23, 26, 29, 32, 35, 38, 41, 47" + - rxring_id: "3" + desc_count: "1024" + prio: "1" + queues: "42, 43, 44, 45, 46" + sys_clk: "1720" + ifc_clk: "1200" + mac_clk: "1340" + + devports: + - id: "0" + sysport: "1000" + type: "cpu" + - fec: "KPFEC" + id: "241" + lanes: "0:8" + serdes_group: "30" + speed: "400G" + sysport: "241" + type: "eth" + - fec: "KPFEC" + id: "249" + lanes: "0:8" + serdes_group: "31" + speed: "400G" + sysport: "249" + type: "eth" + - fec: "KPFEC" + id: "225" + lanes: "0:8" + serdes_group: "28" + speed: "400G" + sysport: "225" + type: "eth" + - fec: "KPFEC" + id: "233" + lanes: "0:8" + serdes_group: "29" + speed: "400G" + sysport: "233" + type: "eth" + - fec: "KPFEC" + id: "217" + lanes: "0:8" + serdes_group: "27" + speed: "400G" + sysport: "217" + type: "eth" + - fec: "KPFEC" + id: "209" + lanes: "0:8" + serdes_group: "26" + speed: "400G" + sysport: "209" + type: "eth" + - fec: "KPFEC" + id: "201" + lanes: "0:8" + serdes_group: "25" + speed: "400G" + sysport: "201" + type: "eth" + - fec: "KPFEC" + id: "193" + lanes: "0:8" + serdes_group: "24" + speed: "400G" + sysport: "193" + type: "eth" + - fec: "KPFEC" + id: "185" + lanes: "0:8" + serdes_group: "23" + speed: "400G" + sysport: "185" + type: "eth" + - fec: "KPFEC" + id: "177" + lanes: "0:8" + serdes_group: "22" + speed: "400G" + sysport: "177" + type: "eth" + - fec: "KPFEC" + id: "169" + lanes: "0:8" + serdes_group: "21" + speed: "400G" + sysport: "169" + type: "eth" + - fec: "KPFEC" + id: "161" + lanes: "0:8" + serdes_group: "20" + speed: "400G" + sysport: "161" + type: "eth" + - fec: "KPFEC" + id: "153" + lanes: "0:8" + serdes_group: "19" + speed: "400G" + sysport: "153" + type: "eth" + - fec: "KPFEC" + id: "145" + lanes: "0:8" + serdes_group: "18" + speed: "400G" + sysport: "145" + type: "eth" + - fec: "KPFEC" + id: "137" + lanes: "0:8" + serdes_group: "17" + speed: "400G" + sysport: "137" + type: "eth" + - fec: "KPFEC" + id: "129" + lanes: "0:8" + serdes_group: "16" + speed: "400G" + sysport: "129" + type: "eth" + - fec: "KPFEC" + id: "121" + lanes: "0:8" + serdes_group: "15" + speed: "400G" + sysport: "121" + type: "eth" + - fec: "KPFEC" + id: "113" + lanes: "0:8" + serdes_group: "14" + speed: "400G" + sysport: "113" + type: "eth" + - fec: "KPFEC" + id: "105" + lanes: "0:8" + serdes_group: "13" + speed: "400G" + sysport: "105" + type: "eth" + - fec: "KPFEC" + id: "97" + lanes: "0:8" + serdes_group: "12" + speed: "400G" + sysport: "97" + type: "eth" + - fec: "KPFEC" + id: "89" + lanes: "0:8" + serdes_group: "11" + speed: "400G" + sysport: "89" + type: "eth" + - fec: "KPFEC" + id: "81" + lanes: "0:8" + serdes_group: "10" + speed: "400G" + sysport: "81" + type: "eth" + - fec: "KPFEC" + id: "73" + lanes: "0:8" + serdes_group: "9" + speed: "400G" + sysport: "73" + type: "eth" + - fec: "KPFEC" + id: "65" + lanes: "0:8" + serdes_group: "8" + speed: "400G" + sysport: "65" + type: "eth" + - fec: "KPFEC" + id: "57" + lanes: "0:8" + serdes_group: "7" + speed: "400G" + sysport: "57" + type: "eth" + - fec: "KPFEC" + id: "49" + lanes: "0:8" + serdes_group: "6" + speed: "400G" + sysport: "49" + type: "eth" + - fec: "KPFEC" + id: "41" + lanes: "0:8" + serdes_group: "5" + speed: "400G" + sysport: "41" + type: "eth" + - fec: "KPFEC" + id: "33" + lanes: "0:8" + serdes_group: "4" + speed: "400G" + sysport: "33" + type: "eth" + - fec: "KPFEC" + id: "25" + lanes: "0:8" + serdes_group: "3" + speed: "400G" + sysport: "25" + type: "eth" + - fec: "KPFEC" + id: "17" + lanes: "0:8" + serdes_group: "2" + speed: "400G" + sysport: "17" + type: "eth" + - fec: "KPFEC" + id: "9" + lanes: "0:8" + serdes_group: "1" + speed: "400G" + sysport: "9" + type: "eth" + - fec: "KPFEC" + id: "1" + lanes: "0:8" + serdes_group: "0" + speed: "400G" + sysport: "1" + type: "eth" + - fec: "NONE" + id: "257" + lanes: "0:1" + serdes_group: "32" + sysport: "257" + type: "mgmt 0" + - fec: "NONE" + id: "258" + lanes: "1:1" + serdes_group: "32" + sysport: "258" + type: "mgmt 1" + isg: + - id: "0" + tx_polarity: "10100000" + rx_polarity: "11111011" + lane_swap: "37250416" + - id: "1" + tx_polarity: "01010011" + rx_polarity: "00000100" + lane_swap: "52407613" + - id: "2" + tx_polarity: "11010001" + rx_polarity: "01111100" + lane_swap: "06153427" + - id: "3" + tx_polarity: "00100000" + rx_polarity: "10001001" + lane_swap: "74501263" + - id: "4" + tx_polarity: "10100000" + rx_polarity: "11101000" + lane_swap: "05471632" + - id: "5" + tx_polarity: "00010100" + rx_polarity: "00111100" + lane_swap: "72604351" + - id: "6" + tx_polarity: "11011001" + rx_polarity: "00011001" + lane_swap: "16340725" + - id: "7" + tx_polarity: "11010000" + rx_polarity: "11000010" + lane_swap: "70615324" + - id: "8" + tx_polarity: "00111101" + rx_polarity: "11011000" + lane_swap: "25074613" + - id: "9" + tx_polarity: "00001010" + rx_polarity: "01000011" + lane_swap: "32706451" + - id: "10" + tx_polarity: "00100010" + rx_polarity: "01001011" + lane_swap: "07162543" + - id: "11" + tx_polarity: "01101001" + rx_polarity: "11110001" + lane_swap: "41706253" + - id: "12" + tx_polarity: "11001000" + rx_polarity: "11000011" + lane_swap: "07136524" + - id: "13" + tx_polarity: "01100001" + rx_polarity: "10010000" + lane_swap: "73506412" + - id: "14" + tx_polarity: "01010001" + rx_polarity: "10110110" + lane_swap: "26143705" + - id: "15" + tx_polarity: "00001000" + rx_polarity: "11101100" + lane_swap: "51602437" + - id: "16" + tx_polarity: "00010000" + rx_polarity: "11101011" + lane_swap: "45076312" + - id: "17" + tx_polarity: "01011000" + rx_polarity: "00000000" + lane_swap: "50642371" + - id: "18" + tx_polarity: "01010100" + rx_polarity: "00011001" + lane_swap: "07436125" + - id: "19" + tx_polarity: "00011010" + rx_polarity: "01001011" + lane_swap: "61734250" + - id: "20" + tx_polarity: "00111110" + rx_polarity: "10011100" + lane_swap: "04275631" + - id: "21" + tx_polarity: "10110100" + rx_polarity: "01110110" + lane_swap: "41620573" + - id: "22" + tx_polarity: "01100110" + rx_polarity: "10010000" + lane_swap: "17240635" + - id: "23" + tx_polarity: "01010000" + rx_polarity: "11110101" + lane_swap: "52704631" + - id: "24" + tx_polarity: "00010001" + rx_polarity: "10100100" + lane_swap: "16253704" + - id: "25" + tx_polarity: "01000101" + rx_polarity: "00010000" + lane_swap: "53607241" + - id: "26" + tx_polarity: "00110101" + rx_polarity: "11101110" + lane_swap: "16074325" + - id: "27" + tx_polarity: "10000111" + rx_polarity: "01011110" + lane_swap: "75604231" + - id: "28" + tx_polarity: "01010100" + rx_polarity: "01010101" + lane_swap: "70614235" + - id: "29" + tx_polarity: "01010001" + rx_polarity: "01000001" + lane_swap: "24610537" + - id: "30" + tx_polarity: "01101011" + rx_polarity: "01010011" + lane_swap: "70614352" + - id: "31" + tx_polarity: "01101001" + rx_polarity: "10100000" + lane_swap: "34250716" + - id: "32" + tx_polarity: "00000000" + rx_polarity: "00000000" + lane_swap: "01234567" diff --git a/device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/innovium.77700_A b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/innovium.77700_A new file mode 100644 index 0000000000..ec13307805 --- /dev/null +++ b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/innovium.77700_A @@ -0,0 +1,60 @@ +sku: innovium.77700_A + +device_id: 0x1b58 + +# Hardware constraint information +hardware: + num_ibs: 6 + ib_active: 0,1,2,3,4,5 + + ports_per_ib: 32, 32, 32, 32, 20, 20 + recirc_port_num: 32, 32, 32, 32, 32, 32 + cpu_port_num: 33 + cpu_port_ib: 0 + mgmt_port_num: 33 + mgmt_port_ibs: 1,2 + + pics_per_ib: 6, 7, 6, 5, 5, 5 + pic_ports_per_pic: 8 + max_serdes_speed: 50 + + num_shared_pics: 2 + + isg [0-4]: + ib: 0 + pic_id: [0-4] + + isg [5-9]: + ib: 5 + pic_id: [0-4] + + isg [10-14]: + ib: 1 + pic_id: [0-4] + + isg [16-20]: + ib: 3 + pic_id: [0-4] + + isg [21-25]: + ib: 4 + pic_id: [0-4] + + isg [26-30]: + ib: 2 + pic_id: [0-4] + + isg 15: + mode: 8:0 + ib: 1 + pic_id: 5 + + isg 31: + mode: 8:0 + ib: 0 + pic_id: 5 + + isg 32: + mode: 1:1 + ib: 1, 2 + pic_id: 6 diff --git a/device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/innovium.77700_B b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/innovium.77700_B new file mode 100644 index 0000000000..57ba52cbc3 --- /dev/null +++ b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/innovium.77700_B @@ -0,0 +1,60 @@ +sku: innovium.77700_B + +device_id: 0x1b58 + +# Hardware constraint information +hardware: + num_ibs: 6 + ib_active: 0,1,2,3,4,5 + + ports_per_ib: 32, 32, 32, 32, 20, 20 + recirc_port_num: 32, 32, 32, 32, 32, 32 + cpu_port_num: 33 + cpu_port_ib: 0 + mgmt_port_num: 33 + mgmt_port_ibs: 1,2 + + pics_per_ib: 6, 7, 7, 6, 5, 5 + pic_ports_per_pic: 8 + max_serdes_speed: 50 + + num_shared_pics: 2 + + isg [0-4]: + ib: 0 + pic_id: [0-4] + + isg [5-9]: + ib: 5 + pic_id: [0-4] + + isg [10-14]: + ib: 1 + pic_id: [0-4] + + isg [16-20]: + ib: 3 + pic_id: [0-4] + + isg [21-25]: + ib: 4 + pic_id: [0-4] + + isg [26-30]: + ib: 2 + pic_id: [0-4] + + isg 15: + mode: 4:4 + ib: 1, 3 + pic_id: 5 + + isg 31: + mode: 4:4 + ib: 0, 2 + pic_id: 5 + + isg 32: + mode: 1:1 + ib: 1, 2 + pic_id: 6 diff --git a/device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/ivm.sai.config.yaml b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/ivm.sai.config.yaml new file mode 100755 index 0000000000..e896723a03 --- /dev/null +++ b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/ivm.sai.config.yaml @@ -0,0 +1,10 @@ +IFCS_INIT_FILE : "/usr/share/sonic/hwsku/config_32x400G_sse_t7132s.yaml" +IFCS_SKU_FILE : "/usr/share/sonic/hwsku/innovium.77700_A" +IFCS_INNO_CLI_PORT : "9999" +IFCS_TARGET : "device" +ULIMIT : "65536" +INNOVIUM_DIR : "/innovium" +PYTHONPATH : "$INNOVIUM_DIR:$INNOVIUM_DIR/cmds:$INNOVIUM_DIR/scripts:$INNOVIUM_DIR/test/:$INNOVIUM_DIR/test/utils:$INNOVIUM_DIR/utils:$INNOVIUM_DIR/pyctypes:$INNOVIUM_DIR/ifcs_cmds:$INNOVIUM_DIR/testutil:$INNOVIUM_DIR/isai_cmds" +PLATFORM_LIBRARY: "/usr/share/sonic/platform/lib_ivm_serdes_pltfm.so" +IVM_SAI_DATAPATH_CONFIG_FILE: "/usr/share/sonic/hwsku/ivm.sai.datapath.config.yaml" +IVM_SAI_PARAM_A0008: "32" diff --git a/device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/ivm.sai.datapath.config.yaml b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/ivm.sai.datapath.config.yaml new file mode 100644 index 0000000000..891b0b3e28 --- /dev/null +++ b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/ivm.sai.datapath.config.yaml @@ -0,0 +1,9 @@ +ISAI_PARAM_P0_0_LS : "4608 4608 4608 4608 2880 2880" +ISAI_PARAM_P0_1_LS : "2226 1946 1946 1890 1218 1218" +ISAI_PARAM_P0_1_ALS : "434 154 154 98 98 98" +ISAI_PARAM_P1_0_LS : "1536 1536 1536 1536 960 960" +ISAI_PARAM_P1_0_LL : "3072 3072 3072 3072 1920 1920" +ISAI_PARAM_P1_1_LS : "1778 1498 1498 1442 938 938" +ISAI_PARAM_P1_1_LL : "2478 2478 2478 2478 2478 2478" +ISAI_PARAM_P1_1_ALS : "434 154 154 98 98 98" +ISAI_PARAM_P1_1_ALL : "126 126 126 126 126 126" diff --git a/device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/pg_profile_lookup.ini b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/pg_profile_lookup.ini new file mode 100644 index 0000000000..0d881737cf --- /dev/null +++ b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/pg_profile_lookup.ini @@ -0,0 +1,22 @@ +# PG lossless profiles. +# speed cable size xon xoff threshold xon_offset + 25000 5m 1518 0 15680 1 9408 + 50000 5m 1518 0 21248 1 9408 + 100000 5m 1518 0 34624 1 9408 + 200000 5m 1518 0 62368 1 9408 + 400000 5m 1518 0 117536 1 9408 + 25000 40m 1518 0 16928 1 9408 + 50000 40m 1518 0 23392 1 9408 + 100000 40m 1518 0 38816 1 9408 + 200000 40m 1518 0 71904 1 9408 + 400000 40m 1518 0 135520 1 9408 + 25000 100m 1518 0 18848 1 9408 + 50000 100m 1518 0 27264 1 9408 + 100000 100m 1518 0 46496 1 9408 + 200000 100m 1518 0 87168 1 9408 + 400000 100m 1518 0 166688 1 9408 + 25000 300m 1518 0 25184 1 9408 + 50000 300m 1518 0 40128 1 9408 + 100000 300m 1518 0 72384 1 9408 + 200000 300m 1518 0 138112 1 9408 + 400000 300m 1518 0 268640 1 9408 diff --git a/device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/port_config.ini b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/port_config.ini new file mode 100755 index 0000000000..950038f8a8 --- /dev/null +++ b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/port_config.ini @@ -0,0 +1,35 @@ +# name lanes alias speed index mtu fec +Ethernet0 241,242,243,244,245,246,247,248 Eth1 400000 1 9126 rs +Ethernet8 249,250,251,252,253,254,255,256 Eth2 400000 2 9126 rs +Ethernet16 225,226,227,228,229,230,231,232 Eth3 400000 3 9126 rs +Ethernet24 233,234,235,236,237,238,239,240 Eth4 400000 4 9126 rs +Ethernet32 217,218,219,220,221,222,223,224 Eth5 400000 5 9126 rs +Ethernet40 209,210,211,212,213,214,215,216 Eth6 400000 6 9126 rs +Ethernet48 201,202,203,204,205,206,207,208 Eth7 400000 7 9126 rs +Ethernet56 193,194,195,196,197,198,199,200 Eth8 400000 8 9126 rs +Ethernet64 185,186,187,188,189,190,191,192 Eth9 400000 9 9126 rs +Ethernet72 177,178,179,180,181,182,183,184 Eth10 400000 10 9126 rs +Ethernet80 169,170,171,172,173,174,175,176 Eth11 400000 11 9126 rs +Ethernet88 161,162,163,164,165,166,167,168 Eth12 400000 12 9126 rs +Ethernet96 153,154,155,156,157,158,159,160 Eth13 400000 13 9126 rs +Ethernet104 145,146,147,148,149,150,151,152 Eth14 400000 14 9126 rs +Ethernet112 137,138,139,140,141,142,143,144 Eth15 400000 15 9126 rs +Ethernet120 129,130,131,132,133,134,135,136 Eth16 400000 16 9126 rs +Ethernet128 121,122,123,124,125,126,127,128 Eth17 400000 17 9126 rs +Ethernet136 113,114,115,116,117,118,119,120 Eth18 400000 18 9126 rs +Ethernet144 105,106,107,108,109,110,111,112 Eth19 400000 19 9126 rs +Ethernet152 97,98,99,100,101,102,103,104 Eth20 400000 20 9126 rs +Ethernet160 89,90,91,92,93,94,95,96 Eth21 400000 21 9126 rs +Ethernet168 81,82,83,84,85,86,87,88 Eth22 400000 22 9126 rs +Ethernet176 73,74,75,76,77,78,79,80 Eth23 400000 23 9126 rs +Ethernet184 65,66,67,68,69,70,71,72 Eth24 400000 24 9126 rs +Ethernet192 57,58,59,60,61,62,63,64 Eth25 400000 25 9126 rs +Ethernet200 49,50,51,52,53,54,55,56 Eth26 400000 26 9126 rs +Ethernet208 41,42,43,44,45,46,47,48 Eth27 400000 27 9126 rs +Ethernet216 33,34,35,36,37,38,39,40 Eth28 400000 28 9126 rs +Ethernet224 25,26,27,28,29,30,31,32 Eth29 400000 29 9126 rs +Ethernet232 17,18,19,20,21,22,23,24 Eth30 400000 30 9126 rs +Ethernet240 9,10,11,12,13,14,15,16 Eth31 400000 31 9126 rs +Ethernet248 1,2,3,4,5,6,7,8 Eth32 400000 32 9126 rs +Ethernet256 257 Eth33 10000 33 9126 none +Ethernet257 258 Eth34 10000 34 9126 none diff --git a/device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/qos.json.j2 b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/qos.json.j2 new file mode 100755 index 0000000000..34f7413d95 --- /dev/null +++ b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/qos.json.j2 @@ -0,0 +1,195 @@ +{% set mgmt_port_name = ['Ethernet256','Ethernet257'] %} +{% set port_names_list = [] %} +{% for port in PORT %} + {% if port not in mgmt_port_name %} + {%- if port_names_list.append(port) %}{% endif %} + {% endif %} +{% endfor %} +{% set port_names = port_names_list | join(',') -%} + + +{ + "TC_TO_QUEUE_MAP":{ + "AZURE":{ + "0":"0", + "1":"1", + "2":"2", + "3":"3", + "4":"4", + "5":"5", + "6":"6", + "7":"7" + } + }, + "MAP_PFC_PRIORITY_TO_QUEUE": { + "AZURE": { + "0": "0", + "1": "1", + "2": "2", + "3": "3", + "4": "4", + "5": "5", + "6": "6", + "7": "7" + } + }, + "TC_TO_PRIORITY_GROUP_MAP": { + "AZURE": { + "0": "0", + "1": "0", + "2": "0", + "3": "3", + "4": "4", + "5": "0", + "6": "0", + "7": "0" + } + }, + "DSCP_TO_TC_MAP": { + "AZURE": { + "0" : "1", + "1" : "1", + "2" : "1", + "3" : "3", + "4" : "4", + "5" : "2", + "6" : "1", + "7" : "1", + "8" : "0", + "9" : "1", + "10": "1", + "11": "1", + "12": "1", + "13": "1", + "14": "1", + "15": "1", + "16": "1", + "17": "1", + "18": "1", + "19": "1", + "20": "1", + "21": "1", + "22": "1", + "23": "1", + "24": "1", + "25": "1", + "26": "1", + "27": "1", + "28": "1", + "29": "1", + "30": "1", + "31": "1", + "32": "1", + "33": "1", + "34": "1", + "35": "1", + "36": "1", + "37": "1", + "38": "1", + "39": "1", + "40": "1", + "41": "1", + "42": "1", + "43": "1", + "44": "1", + "45": "1", + "46": "5", + "47": "1", + "48": "6", + "49": "1", + "50": "1", + "51": "1", + "52": "1", + "53": "1", + "54": "1", + "55": "1", + "56": "1", + "57": "1", + "58": "1", + "59": "1", + "60": "1", + "61": "1", + "62": "1", + "63": "1" + } + }, + "SCHEDULER": { + "scheduler.0": { + "type" : "DWRR", + "weight": "1" + }, + "scheduler.1": { + "type" : "DWRR", + "weight": "1" + } + }, + "QUEUE": { +{% for port in port_names_list %} + "{{ port }}|3": { + "scheduler" : "scheduler.1", + "wred_profile" : "AZURE_LOSSLESS" + }, +{% endfor %} +{% for port in port_names_list %} + "{{ port }}|4": { + "scheduler" : "scheduler.1", + "wred_profile" : "AZURE_LOSSLESS" + }, +{% endfor %} +{% for port in port_names_list %} + "{{ port }}|0": { + "scheduler": "scheduler.0" + }, +{% endfor %} +{% for port in port_names_list %} + "{{ port }}|1": { + "scheduler": "scheduler.0" + }, +{% endfor %} +{% for port in port_names_list %} + "{{ port }}|2": { + "scheduler": "scheduler.0" + }, +{% endfor %} +{% for port in port_names_list %} + "{{ port }}|5": { + "scheduler": "scheduler.0" + }, +{% endfor %} +{% for port in port_names_list %} + "{{ port }}|6": { + "scheduler": "scheduler.0" + }{% if not loop.last %},{% endif %} + +{% endfor %} + }, + "PORT_QOS_MAP": { +{% for port in port_names_list %} + "{{ port }}": { + "tc_to_pg_map": "AZURE", + "tc_to_queue_map": "AZURE", + "dscp_to_tc_map": "AZURE", + "pfc_to_queue_map": "AZURE", + "pfc_enable": "3,4" + }{% if not loop.last %},{% endif %} + +{% endfor %} + }, + "WRED_PROFILE": { + "AZURE_LOSSLESS" : { + "wred_green_enable" : "true", + "wred_yellow_enable" : "true", + "wred_red_enable" : "true", + "ecn" : "ecn_all", + "green_max_threshold" : "2097152", + "green_min_threshold" : "1048576", + "yellow_max_threshold" : "2097152", + "yellow_min_threshold" : "1048576", + "red_max_threshold" : "2097152", + "red_min_threshold" : "1048576", + "green_drop_probability" : "5", + "yellow_drop_probability": "5", + "red_drop_probability" : "5" + } + } +} diff --git a/device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/qos_defaults_def_lossy.j2 b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/qos_defaults_def_lossy.j2 new file mode 100644 index 0000000000..a390d37b4f --- /dev/null +++ b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/qos_defaults_def_lossy.j2 @@ -0,0 +1,124 @@ +{% set mgmt_port_name = ['Ethernet256','Ethernet257'] %} +{% set port_names_list = [] %} +{% for port in PORT %} + {% if port not in mgmt_port_name %} + {%- if port_names_list.append(port) %}{% endif %} + {% endif %} +{% endfor %} +{% set port_names = port_names_list | join(',') -%} + + +{ + "TC_TO_QUEUE_MAP":{ + "AZURE":{ + "0":"0", + "1":"1", + "2":"2", + "3":"3", + "4":"4", + "5":"5", + "6":"6", + "7":"7" + } + }, + "TC_TO_PRIORITY_GROUP_MAP": { + "AZURE": { + "0": "0", + "1": "0", + "2": "0", + "3": "1", + "4": "2", + "5": "0", + "6": "0", + "7": "0" + } + }, + "DSCP_TO_TC_MAP": { + "AZURE": { + "0":"0", + "1":"0", + "2":"0", + "3":"0", + "4":"0", + "5":"0", + "6":"0", + "7":"0", + "8":"0", + "9":"0", + "10":"0", + "11":"0", + "12":"0", + "13":"0", + "14":"0", + "15":"0", + "16":"0", + "17":"0", + "18":"0", + "19":"0", + "20":"0", + "21":"0", + "22":"0", + "23":"0", + "24":"0", + "25":"0", + "26":"0", + "27":"0", + "28":"0", + "29":"0", + "30":"0", + "31":"0", + "32":"0", + "33":"0", + "34":"0", + "35":"0", + "36":"0", + "37":"0", + "38":"0", + "39":"0", + "40":"0", + "41":"0", + "42":"0", + "43":"0", + "44":"0", + "45":"0", + "46":"0", + "47":"0", + "48":"0", + "49":"0", + "50":"0", + "51":"0", + "52":"0", + "53":"0", + "54":"0", + "55":"0", + "56":"0", + "57":"0", + "58":"0", + "59":"0", + "60":"0", + "61":"0", + "62":"0", + "63":"0" + } + }, + "PORT_QOS_MAP": { +{% for port in port_names_list %} + "{{ port }}": { + "tc_to_pg_map": "AZURE", + "tc_to_queue_map": "AZURE", + "dscp_to_tc_map": "AZURE" + }{% if not loop.last %},{% endif %} + +{% endfor %} + }, + "SCHEDULER": { + "scheduler.7": { + "type": "STRICT" + } + }, + "QUEUE": { + "{{ port_names }}|7": { + "scheduler": "[SCHEDULER|scheduler.7]" + } + } +} diff --git a/device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/qos_defaults_t1.j2 b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/qos_defaults_t1.j2 new file mode 100644 index 0000000000..34f7413d95 --- /dev/null +++ b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/qos_defaults_t1.j2 @@ -0,0 +1,195 @@ +{% set mgmt_port_name = ['Ethernet256','Ethernet257'] %} +{% set port_names_list = [] %} +{% for port in PORT %} + {% if port not in mgmt_port_name %} + {%- if port_names_list.append(port) %}{% endif %} + {% endif %} +{% endfor %} +{% set port_names = port_names_list | join(',') -%} + + +{ + "TC_TO_QUEUE_MAP":{ + "AZURE":{ + "0":"0", + "1":"1", + "2":"2", + "3":"3", + "4":"4", + "5":"5", + "6":"6", + "7":"7" + } + }, + "MAP_PFC_PRIORITY_TO_QUEUE": { + "AZURE": { + "0": "0", + "1": "1", + "2": "2", + "3": "3", + "4": "4", + "5": "5", + "6": "6", + "7": "7" + } + }, + "TC_TO_PRIORITY_GROUP_MAP": { + "AZURE": { + "0": "0", + "1": "0", + "2": "0", + "3": "3", + "4": "4", + "5": "0", + "6": "0", + "7": "0" + } + }, + "DSCP_TO_TC_MAP": { + "AZURE": { + "0" : "1", + "1" : "1", + "2" : "1", + "3" : "3", + "4" : "4", + "5" : "2", + "6" : "1", + "7" : "1", + "8" : "0", + "9" : "1", + "10": "1", + "11": "1", + "12": "1", + "13": "1", + "14": "1", + "15": "1", + "16": "1", + "17": "1", + "18": "1", + "19": "1", + "20": "1", + "21": "1", + "22": "1", + "23": "1", + "24": "1", + "25": "1", + "26": "1", + "27": "1", + "28": "1", + "29": "1", + "30": "1", + "31": "1", + "32": "1", + "33": "1", + "34": "1", + "35": "1", + "36": "1", + "37": "1", + "38": "1", + "39": "1", + "40": "1", + "41": "1", + "42": "1", + "43": "1", + "44": "1", + "45": "1", + "46": "5", + "47": "1", + "48": "6", + "49": "1", + "50": "1", + "51": "1", + "52": "1", + "53": "1", + "54": "1", + "55": "1", + "56": "1", + "57": "1", + "58": "1", + "59": "1", + "60": "1", + "61": "1", + "62": "1", + "63": "1" + } + }, + "SCHEDULER": { + "scheduler.0": { + "type" : "DWRR", + "weight": "1" + }, + "scheduler.1": { + "type" : "DWRR", + "weight": "1" + } + }, + "QUEUE": { +{% for port in port_names_list %} + "{{ port }}|3": { + "scheduler" : "scheduler.1", + "wred_profile" : "AZURE_LOSSLESS" + }, +{% endfor %} +{% for port in port_names_list %} + "{{ port }}|4": { + "scheduler" : "scheduler.1", + "wred_profile" : "AZURE_LOSSLESS" + }, +{% endfor %} +{% for port in port_names_list %} + "{{ port }}|0": { + "scheduler": "scheduler.0" + }, +{% endfor %} +{% for port in port_names_list %} + "{{ port }}|1": { + "scheduler": "scheduler.0" + }, +{% endfor %} +{% for port in port_names_list %} + "{{ port }}|2": { + "scheduler": "scheduler.0" + }, +{% endfor %} +{% for port in port_names_list %} + "{{ port }}|5": { + "scheduler": "scheduler.0" + }, +{% endfor %} +{% for port in port_names_list %} + "{{ port }}|6": { + "scheduler": "scheduler.0" + }{% if not loop.last %},{% endif %} + +{% endfor %} + }, + "PORT_QOS_MAP": { +{% for port in port_names_list %} + "{{ port }}": { + "tc_to_pg_map": "AZURE", + "tc_to_queue_map": "AZURE", + "dscp_to_tc_map": "AZURE", + "pfc_to_queue_map": "AZURE", + "pfc_enable": "3,4" + }{% if not loop.last %},{% endif %} + +{% endfor %} + }, + "WRED_PROFILE": { + "AZURE_LOSSLESS" : { + "wred_green_enable" : "true", + "wred_yellow_enable" : "true", + "wred_red_enable" : "true", + "ecn" : "ecn_all", + "green_max_threshold" : "2097152", + "green_min_threshold" : "1048576", + "yellow_max_threshold" : "2097152", + "yellow_min_threshold" : "1048576", + "red_max_threshold" : "2097152", + "red_min_threshold" : "1048576", + "green_drop_probability" : "5", + "yellow_drop_probability": "5", + "red_drop_probability" : "5" + } + } +} diff --git a/device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/sai.profile b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/sai.profile new file mode 100644 index 0000000000..aba4fc81fb --- /dev/null +++ b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/Supermicro_sse_t7132s/sai.profile @@ -0,0 +1 @@ +SAI_INIT_CONFIG_FILE=/usr/share/sonic/hwsku/ivm.sai.config.yaml diff --git a/device/supermicro/x86_64-supermicro_sse_t7132s-r0/default_sku b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/default_sku new file mode 100755 index 0000000000..8feb806f2f --- /dev/null +++ b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/default_sku @@ -0,0 +1 @@ +Supermicro_sse_t7132s t1 diff --git a/device/supermicro/x86_64-supermicro_sse_t7132s-r0/fast-reboot_plugin b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/fast-reboot_plugin new file mode 100755 index 0000000000..6bc65e0edf --- /dev/null +++ b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/fast-reboot_plugin @@ -0,0 +1,2 @@ +#!/bin/bash +/usr/local/bin/sysledctl.py reboot diff --git a/device/supermicro/x86_64-supermicro_sse_t7132s-r0/installer.conf b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/installer.conf new file mode 100755 index 0000000000..1eb3e9e494 --- /dev/null +++ b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/installer.conf @@ -0,0 +1,4 @@ +CONSOLE_PORT=0x3f8 +CONSOLE_DEV=0 +CONSOLE_SPEED=115200 +ONIE_PLATFORM_EXTRA_CMDLINE_LINUX="intel_iommu=off pcie_aspm=off usbcore.old_scheme_first=1" diff --git a/device/supermicro/x86_64-supermicro_sse_t7132s-r0/lib_ivm_serdes_pltfm.so b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/lib_ivm_serdes_pltfm.so new file mode 100755 index 0000000000000000000000000000000000000000..651e66a19ff58a35c7ec56373fa7cab0cd746227 GIT binary patch literal 283696 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

(v$3O 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 literal 0 HcmV?d00001 diff --git a/device/supermicro/x86_64-supermicro_sse_t7132s-r0/pcie.yaml b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/pcie.yaml new file mode 100755 index 0000000000..2b8dce2e06 --- /dev/null +++ b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/pcie.yaml @@ -0,0 +1,453 @@ +- bus: '00' + dev: '00' + fn: '0' + id: 6f00 + name: 'Host bridge: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon D DMI2 + (rev 03)' +- bus: '00' + dev: '01' + fn: '0' + id: 6f02 + name: 'PCI bridge: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon D PCI + Express Root Port 1 (rev 03)' +- bus: '00' + dev: '01' + fn: '1' + id: 6f03 + name: 'PCI bridge: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon D PCI + Express Root Port 1 (rev 03)' +- bus: '00' + dev: '02' + fn: '0' + id: 6f04 + name: 'PCI bridge: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon D PCI + Express Root Port 2 (rev 03)' +- bus: '00' + dev: '02' + fn: '2' + id: 6f06 + name: 'PCI bridge: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon D PCI + Express Root Port 2 (rev 03)' +- bus: '00' + dev: '03' + fn: '0' + id: 6f08 + name: 'PCI bridge: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon D PCI + Express Root Port 3 (rev 03)' +- bus: '00' + dev: '03' + fn: '3' + id: 6f0b + name: 'PCI bridge: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon D PCI + Express Root Port 3 (rev 03)' +- bus: '00' + dev: '05' + fn: '0' + id: 6f28 + name: 'System peripheral: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D Map/VTd_Misc/System Management (rev 03)' +- bus: '00' + dev: '05' + fn: '1' + id: 6f29 + name: 'System peripheral: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D IIO Hot Plug (rev 03)' +- bus: '00' + dev: '05' + fn: '2' + id: 6f2a + name: 'System peripheral: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D IIO RAS/Control Status/Global Errors (rev 03)' +- bus: '00' + dev: '14' + fn: '0' + id: 8c31 + name: 'USB controller: Intel Corporation 8 Series/C220 Series Chipset Family USB + xHCI (rev 05)' +- bus: '00' + dev: '16' + fn: '0' + id: 8c3a + name: 'Communication controller: Intel Corporation 8 Series/C220 Series Chipset + Family MEI Controller #1 (rev 04)' +- bus: '00' + dev: '16' + fn: '1' + id: 8c3b + name: 'Communication controller: Intel Corporation 8 Series/C220 Series Chipset + Family MEI Controller #2 (rev 04)' +- bus: '00' + dev: 1a + fn: '0' + id: 8c2d + name: 'USB controller: Intel Corporation 8 Series/C220 Series Chipset Family USB + EHCI #2 (rev 05)' +- bus: '00' + dev: 1c + fn: '0' + id: 8c10 + name: 'PCI bridge: Intel Corporation 8 Series/C220 Series Chipset Family PCI Express + Root Port #1 (rev d5)' +- bus: '00' + dev: 1c + fn: '3' + id: 8c16 + name: 'PCI bridge: Intel Corporation 8 Series/C220 Series Chipset Family PCI Express + Root Port #4 (rev d5)' +- bus: '00' + dev: 1d + fn: '0' + id: 8c26 + name: 'USB controller: Intel Corporation 8 Series/C220 Series Chipset Family USB + EHCI #1 (rev 05)' +- bus: '00' + dev: 1f + fn: '0' + id: 8c54 + name: 'ISA bridge: Intel Corporation C224 Series Chipset Family Server Standard + SKU LPC Controller (rev 05)' +- bus: '00' + dev: 1f + fn: '2' + id: 8c02 + name: 'SATA controller: Intel Corporation 8 Series/C220 Series Chipset Family 6-port + SATA Controller 1 [AHCI mode] (rev 05)' +- bus: '00' + dev: 1f + fn: '3' + id: 8c22 + name: 'SMBus: Intel Corporation 8 Series/C220 Series Chipset Family SMBus Controller + (rev 05)' +- bus: '00' + dev: 1f + fn: '6' + id: 8c24 + name: 'Signal processing controller: Intel Corporation 8 Series Chipset Family Thermal + Management Controller (rev 05)' +- bus: '03' + dev: '00' + fn: '0' + id: 6f50 + name: 'System peripheral: Intel Corporation Xeon Processor D Family QuickData Technology + Register DMA Channel 0' +- bus: '03' + dev: '00' + fn: '1' + id: 6f51 + name: 'System peripheral: Intel Corporation Xeon Processor D Family QuickData Technology + Register DMA Channel 1' +- bus: '03' + dev: '00' + fn: '2' + id: 6f52 + name: 'System peripheral: Intel Corporation Xeon Processor D Family QuickData Technology + Register DMA Channel 2' +- bus: '03' + dev: '00' + fn: '3' + id: 6f53 + name: 'System peripheral: Intel Corporation Xeon Processor D Family QuickData Technology + Register DMA Channel 3' +- bus: '05' + dev: '00' + fn: '0' + id: 1b58 + name: 'Ethernet controller: Device 1d98:1b58 (rev 10)' +- bus: '06' + dev: '00' + fn: '0' + id: '9110' + name: 'Bridge: Asix Electronics Corporation Device 9110' +- bus: '07' + dev: '00' + fn: '0' + id: '1533' + name: 'Ethernet controller: Intel Corporation I210 Gigabit Network Connection (rev + 03)' +- bus: 08 + dev: '00' + fn: '0' + id: '1150' + name: 'PCI bridge: ASPEED Technology, Inc. AST1150 PCI-to-PCI Bridge (rev 06)' +- bus: 09 + dev: '00' + fn: '0' + id: '2000' + name: 'VGA compatible controller: ASPEED Technology, Inc. ASPEED Graphics Family + (rev 52)' +- bus: ff + dev: 0b + fn: '0' + id: 6f81 + name: 'System peripheral: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D R3 QPI Link 0/1 (rev 03)' +- bus: ff + dev: 0b + fn: '1' + id: 6f36 + name: 'Performance counters: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D R3 QPI Link 0/1 (rev 03)' +- bus: ff + dev: 0b + fn: '2' + id: 6f37 + name: 'Performance counters: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D R3 QPI Link 0/1 (rev 03)' +- bus: ff + dev: 0b + fn: '3' + id: 6f76 + name: 'System peripheral: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D R3 QPI Link Debug (rev 03)' +- bus: ff + dev: 0c + fn: '0' + id: 6fe0 + name: 'System peripheral: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D Caching Agent (rev 03)' +- bus: ff + dev: 0c + fn: '1' + id: 6fe1 + name: 'System peripheral: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D Caching Agent (rev 03)' +- bus: ff + dev: 0c + fn: '2' + id: 6fe2 + name: 'System peripheral: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D Caching Agent (rev 03)' +- bus: ff + dev: 0c + fn: '3' + id: 6fe3 + name: 'System peripheral: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D Caching Agent (rev 03)' +- bus: ff + dev: 0f + fn: '0' + id: 6ff8 + name: 'System peripheral: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D Caching Agent (rev 03)' +- bus: ff + dev: 0f + fn: '4' + id: 6ffc + name: 'System peripheral: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D Caching Agent (rev 03)' +- bus: ff + dev: 0f + fn: '5' + id: 6ffd + name: 'System peripheral: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D Caching Agent (rev 03)' +- bus: ff + dev: 0f + fn: '6' + id: 6ffe + name: 'System peripheral: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D Caching Agent (rev 03)' +- bus: ff + dev: '10' + fn: '0' + id: 6f1d + name: 'System peripheral: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D R2PCIe Agent (rev 03)' +- bus: ff + dev: '10' + fn: '1' + id: 6f34 + name: 'Performance counters: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D R2PCIe Agent (rev 03)' +- bus: ff + dev: '10' + fn: '5' + id: 6f1e + name: 'System peripheral: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D Ubox (rev 03)' +- bus: ff + dev: '10' + fn: '6' + id: 6f7d + name: 'Performance counters: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D Ubox (rev 03)' +- bus: ff + dev: '10' + fn: '7' + id: 6f1f + name: 'System peripheral: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D Ubox (rev 03)' +- bus: ff + dev: '12' + fn: '0' + id: 6fa0 + name: 'System peripheral: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D Home Agent 0 (rev 03)' +- bus: ff + dev: '12' + fn: '1' + id: 6f30 + name: 'Performance counters: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D Home Agent 0 (rev 03)' +- bus: ff + dev: '13' + fn: '0' + id: 6fa8 + name: 'System peripheral: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D Memory Controller 0 - Target Address/Thermal/RAS (rev 03)' +- bus: ff + dev: '13' + fn: '1' + id: 6f71 + name: 'System peripheral: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D Memory Controller 0 - Target Address/Thermal/RAS (rev 03)' +- bus: ff + dev: '13' + fn: '2' + id: 6faa + name: 'System peripheral: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D Memory Controller 0 - Channel Target Address Decoder (rev 03)' +- bus: ff + dev: '13' + fn: '3' + id: 6fab + name: 'System peripheral: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D Memory Controller 0 - Channel Target Address Decoder (rev 03)' +- bus: ff + dev: '13' + fn: '4' + id: 6fac + name: 'System peripheral: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D Memory Controller 0 - Channel Target Address Decoder (rev 03)' +- bus: ff + dev: '13' + fn: '5' + id: 6fad + name: 'System peripheral: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D Memory Controller 0 - Channel Target Address Decoder (rev 03)' +- bus: ff + dev: '13' + fn: '6' + id: 6fae + name: 'System peripheral: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D DDRIO Channel 0/1 Broadcast (rev 03)' +- bus: ff + dev: '13' + fn: '7' + id: 6faf + name: 'System peripheral: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D DDRIO Global Broadcast (rev 03)' +- bus: ff + dev: '14' + fn: '0' + id: 6fb0 + name: 'System peripheral: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D Memory Controller 0 - Channel 0 Thermal Control (rev 03)' +- bus: ff + dev: '14' + fn: '1' + id: 6fb1 + name: 'System peripheral: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D Memory Controller 0 - Channel 1 Thermal Control (rev 03)' +- bus: ff + dev: '14' + fn: '2' + id: 6fb2 + name: 'System peripheral: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D Memory Controller 0 - Channel 0 Error (rev 03)' +- bus: ff + dev: '14' + fn: '3' + id: 6fb3 + name: 'System peripheral: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D Memory Controller 0 - Channel 1 Error (rev 03)' +- bus: ff + dev: '14' + fn: '4' + id: 6fbc + name: 'System peripheral: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D DDRIO Channel 0/1 Interface (rev 03)' +- bus: ff + dev: '14' + fn: '5' + id: 6fbd + name: 'System peripheral: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D DDRIO Channel 0/1 Interface (rev 03)' +- bus: ff + dev: '14' + fn: '6' + id: 6fbe + name: 'System peripheral: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D DDRIO Channel 0/1 Interface (rev 03)' +- bus: ff + dev: '14' + fn: '7' + id: 6fbf + name: 'System peripheral: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D DDRIO Channel 0/1 Interface (rev 03)' +- bus: ff + dev: '15' + fn: '0' + id: 6fb4 + name: 'System peripheral: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D Memory Controller 0 - Channel 2 Thermal Control (rev 03)' +- bus: ff + dev: '15' + fn: '1' + id: 6fb5 + name: 'System peripheral: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D Memory Controller 0 - Channel 3 Thermal Control (rev 03)' +- bus: ff + dev: '15' + fn: '2' + id: 6fb6 + name: 'System peripheral: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D Memory Controller 0 - Channel 2 Error (rev 03)' +- bus: ff + dev: '15' + fn: '3' + id: 6fb7 + name: 'System peripheral: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D Memory Controller 0 - Channel 3 Error (rev 03)' +- bus: ff + dev: 1e + fn: '0' + id: 6f98 + name: 'System peripheral: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D Power Control Unit (rev 03)' +- bus: ff + dev: 1e + fn: '1' + id: 6f99 + name: 'System peripheral: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D Power Control Unit (rev 03)' +- bus: ff + dev: 1e + fn: '2' + id: 6f9a + name: 'System peripheral: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D Power Control Unit (rev 03)' +- bus: ff + dev: 1e + fn: '3' + id: 6fc0 + name: 'System peripheral: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D Power Control Unit (rev 03)' +- bus: ff + dev: 1e + fn: '4' + id: 6f9c + name: 'System peripheral: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D Power Control Unit (rev 03)' +- bus: ff + dev: 1f + fn: '0' + id: 6f88 + name: 'System peripheral: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D Power Control Unit (rev 03)' +- bus: ff + dev: 1f + fn: '2' + id: 6f8a + name: 'System peripheral: Intel Corporation Xeon E7 v4/Xeon E5 v4/Xeon E3 v4/Xeon + D Power Control Unit (rev 03)' diff --git a/device/supermicro/x86_64-supermicro_sse_t7132s-r0/platform.json b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/platform.json new file mode 100644 index 0000000000..e28ca23c7a --- /dev/null +++ b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/platform.json @@ -0,0 +1,238 @@ +{ + "chassis": { + "name": "Supermicro-SSE-T7132S-R0", + "components": [ + { + "name": "CPLD1" + }, + { + "name": "CPLD2" + } + ], + "fans": [ + { + "name": "FAN-1" + }, + { + "name": "FAN-2" + }, + { + "name": "FAN-3" + }, + { + "name": "FAN-4" + }, + { + "name": "FAN-5" + }, + { + "name": "FAN-6" + } + ], + "fan_drawers": [ + { + "name": "Drawer1", + "fans": [ + { + "name": "FAN-1" + } + ] + }, + { + "name": "Drawer2", + "fans": [ + { + "name": "FAN-2" + } + ] + }, + { + "name": "Drawer3", + "fans": [ + { + "name": "FAN-3" + } + ] + }, + { + "name": "Drawer4", + "fans": [ + { + "name": "FAN-4" + } + ] + }, + { + "name": "Drawer5", + "fans": [ + { + "name": "FAN-5" + } + ] + }, + { + "name": "Drawer6", + "fans": [ + { + "name": "FAN-6" + } + ] + } + ], + "psus": [ + { + "name": "PSU 1", + "fans": [ + { + "name": "PSU 1 FAN-1", + "speed": { + "controllable": false + }, + "status_led": { + "controllable": false + } + } + ] + }, + { + "name": "PSU 2", + "fans": [ + { + "name": "PSU 2 FAN-1", + "speed": { + "controllable": false + }, + "status_led": { + "controllable": false + } + } + ] + } + ], + "thermals": [ + { + "name": "CPU Temp" + }, + { + "name": "PCH Temp" + }, + { + "name": "Peripheral Temp" + }, + { + "name": "Switch Buttom-1" + }, + { + "name": "Switch Buttom-2" + }, + { + "name": "Switch Top-1" + }, + { + "name": "Switch Top-2" + }, + { + "name": "System Temp" + } + ], + "sfps": [ + { + "name": "Ethernet0" + }, + { + "name": "Ethernet8" + }, + { + "name": "Ethernet16" + }, + { + "name": "Ethernet24" + }, + { + "name": "Ethernet32" + }, + { + "name": "Ethernet40" + }, + { + "name": "Ethernet48" + }, + { + "name": "Ethernet56" + }, + { + "name": "Ethernet64" + }, + { + "name": "Ethernet72" + }, + { + "name": "Ethernet80" + }, + { + "name": "Ethernet88" + }, + { + "name": "Ethernet96" + }, + { + "name": "Ethernet104" + }, + { + "name": "Ethernet112" + }, + { + "name": "Ethernet120" + }, + { + "name": "Ethernet128" + }, + { + "name": "Ethernet136" + }, + { + "name": "Ethernet144" + }, + { + "name": "Ethernet152" + }, + { + "name": "Ethernet160" + }, + { + "name": "Ethernet168" + }, + { + "name": "Ethernet176" + }, + { + "name": "Ethernet184" + }, + { + "name": "Ethernet192" + }, + { + "name": "Ethernet200" + }, + { + "name": "Ethernet208" + }, + { + "name": "Ethernet216" + }, + { + "name": "Ethernet224" + }, + { + "name": "Ethernet232" + }, + { + "name": "Ethernet240" + }, + { + "name": "Ethernet248" + } + ] + }, + "interfaces": {} +} diff --git a/device/supermicro/x86_64-supermicro_sse_t7132s-r0/platform_asic b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/platform_asic new file mode 100644 index 0000000000..84083a7415 --- /dev/null +++ b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/platform_asic @@ -0,0 +1 @@ +innovium diff --git a/device/supermicro/x86_64-supermicro_sse_t7132s-r0/plugins/eeprom.py b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/plugins/eeprom.py new file mode 100644 index 0000000000..ba6a569c71 --- /dev/null +++ b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/plugins/eeprom.py @@ -0,0 +1,20 @@ +############################################################################# +# Celestica Silverstone +# +# 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: + from sonic_eeprom import eeprom_tlvinfo +except ImportError as e: + raise ImportError(str(e) + "- required module not found") + + +class board(eeprom_tlvinfo.TlvInfoDecoder): + + def __init__(self, name, path, cpld_root, ro): + self.eeprom_path = "/sys/class/i2c-adapter/i2c-0/0-0053/eeprom" + super(board, self).__init__(self.eeprom_path, 0, '', True) diff --git a/device/supermicro/x86_64-supermicro_sse_t7132s-r0/plugins/psuutil.py b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/plugins/psuutil.py new file mode 100644 index 0000000000..3bba2adc20 --- /dev/null +++ b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/plugins/psuutil.py @@ -0,0 +1,84 @@ +import os.path +import subprocess +import sys +import re + +IPMI_PSU1_DATA = "docker exec -it pmon ipmitool sdr list | grep PS1 | awk -F \"|\" '{print $2}'" +IPMI_PSU2_DATA = "docker exec -it pmon ipmitool sdr list | grep PS2 | awk -F \"|\" '{print $2}'" + +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 run_command(self, command): + proc = subprocess.Popen(command, shell=True, universal_newlines=True, stdout=subprocess.PIPE) + (out, err) = proc.communicate() + + if proc.returncode != 0: + sys.exit(proc.returncode) + + return out + + 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 + """ + return 2 + + def get_psu_status(self, index): + """ + Retrieves the oprational status of power supply unit (PSU) defined + by 1-based index + :param index: An integer, 1-based index of the PSU of which to query status + :return: Boolean, True if PSU is operating properly, False if PSU is faulty + """ + if index is None: + return False + if index == 1: + res_string = self.run_command(IPMI_PSU1_DATA) + else: + res_string = self.run_command(IPMI_PSU2_DATA) + + try: + ret_value = int(res_string, 0) + except ValueError as e: + return False + + if ret_value == 0x1: + return True + else: + return False + + def get_psu_presence(self, index): + """ + Retrieves the presence status of power supply unit (PSU) defined + by 1-based index + :param index: An integer, 1-based index of the PSU of which to query status + :return: Boolean, True if PSU is plugged, False if not + """ + if index is None: + return False + + if index == 1: + res_string = self.run_command(IPMI_PSU1_DATA) + else: + res_string = self.run_command(IPMI_PSU2_DATA) + + try: + ret_value = int(res_string, 0) + except ValueError as e: + return False + + if ret_value == 0x1 or ret_value == 0xb: + return True + else: + return False diff --git a/device/supermicro/x86_64-supermicro_sse_t7132s-r0/plugins/sfputil.py b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/plugins/sfputil.py new file mode 100644 index 0000000000..f8fb3d2744 --- /dev/null +++ b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/plugins/sfputil.py @@ -0,0 +1,211 @@ +# Platform-specific SFP transceiver interface for SONiC +# This plugin supports QSFP and SFP. + +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 = 34 + QSFP_PORT_START = 0 + QSFP_PORT_END = 32 + SFP_PORT_START = 33 + SFP_PORT_END = 34 + + EEPROM_OFFSET = 11 + PORT_INFO_PATH = '/sys/class/t7132s_cpld' + + _port_name = "" + _port_to_eeprom_mapping = {} + _port_to_i2cbus_mapping = {} + _port_to_offset = [11, 30, 12, 29, 13, 28, 14, 27, 15, 34, + 16, 33, 17, 32, 18, 31, 19, 38, 20, 37, + 21, 36, 22, 35, 23, 42, 24, 41, 25, 40, + 26, 39, + 43, 44] + _global_port_pres_dict = {} + + @property + def port_start(self): + return self.PORT_START + + @property + def port_end(self): + return self.PORT_END + + @property + def qsfp_ports(self): + return [] + + @property + def qsfp_ports(self): + return list(range(self.QSFP_PORT_START, self.QSFP_PORT_END)) + + @property + def port_to_eeprom_mapping(self): + return self._port_to_eeprom_mapping + + @property + def port_to_i2cbus_mapping(self): + return self._port_to_i2cbus_mapping + + def get_port_name(self, port_num): + if port_num in self.qsfp_ports: + self._port_name = "QSFP" + str(port_num + 1) + else: + self._port_name = "SFP" + str(port_num - self.QSFP_PORT_END + 1) + return self._port_name + + def get_eeprom_dom_raw(self, port_num): + if port_num in self.qsfp_ports: + # QSFP DOM EEPROM is also at addr 0x50 and thus also stored in eeprom_ifraw + return None + else: + # Read dom eeprom at addr 0x51 + return self._read_eeprom_devid(port_num, self.DOM_EEPROM_ADDR, 256) + + def __init__(self): + # Override port_to_eeprom_mapping for class initialization + eeprom_path = '/sys/bus/i2c/devices/i2c-{0}/{0}-0050/eeprom' + + for x in range(self.PORT_START, self.PORT_END): + self.port_to_i2cbus_mapping[x] = (x + self.EEPROM_OFFSET) + self.port_to_eeprom_mapping[x] = eeprom_path.format( + self._port_to_offset[x]) + self.init_global_port_presence() + SfpUtilBase.__init__(self) + + def init_global_port_presence(self): + for port_num in range(self.port_start, (self.port_end)): + presence = self.get_presence(port_num) + if(presence): + self._global_port_pres_dict[port_num] = '1' + else: + self._global_port_pres_dict[port_num] = '0' + + def get_presence(self, port_num): + # Check for invalid port_num + if port_num not in list(range(self.port_start, self.port_end + 1)): + return False + + # Get path for access port presence status + port_name = self.get_port_name(port_num) + sysfs_filename = "qsfp_modprs" if port_num in self.qsfp_ports else "sfp_modabs" + reg_path = "/".join([self.PORT_INFO_PATH, port_name, sysfs_filename]) + + # Read status + try: + reg_file = open(reg_path) + content = reg_file.readline().rstrip() + reg_value = int(content) + except IOError as e: + print("Error: unable to open file: %s" % str(e)) + return False + + # Module present is active low + if reg_value == 0: + return True + + return False + + def get_low_power_mode(self, port_num): + # Check for invalid QSFP port_num + if port_num not in self.qsfp_ports: + return False + + try: + port_name = self.get_port_name(port_num) + reg_file = open("/".join([self.PORT_INFO_PATH, + port_name, "qsfp_lpmode"])) + except IOError as e: + print("Error: unable to open file: %s" % str(e)) + return False + + # Read status + content = reg_file.readline().rstrip() + reg_value = int(content) + # low power mode is active high + if reg_value == 0: + return False + + return True + + def set_low_power_mode(self, port_num, lpmode): + # Check for invalid QSFP port_num + if port_num not in self.qsfp_ports: + return False + + try: + port_name = self.get_port_name(port_num) + reg_file = open("/".join([self.PORT_INFO_PATH, + port_name, "qsfp_lpmode"]), "r+") + except IOError as e: + print("Error: unable to open file: %s" % str(e)) + return False + + content = hex(lpmode) + + reg_file.seek(0) + reg_file.write(content) + reg_file.close() + + return True + + def reset(self, port_num): + # Check for invalid QSFP port_num + if port_num not in self.qsfp_ports: + return False + + try: + port_name = self.get_port_name(port_num) + reg_file = open("/".join([self.PORT_INFO_PATH, + port_name, "qsfp_reset"]), "w") + except IOError as e: + print("Error: unable to open file: %s" % str(e)) + return False + + # Convert our register value back to a hex string and write back + reg_file.seek(0) + reg_file.write(hex(0)) + reg_file.close() + + # Sleep 1 second to allow it to settle + time.sleep(1) + + # Flip the bit back high and write back to the register to take port out of reset + try: + reg_file = open( + "/".join([self.PORT_INFO_PATH, port_name, "qsfp_reset"]), "w") + except IOError as e: + print("Error: unable to open file: %s" % str(e)) + return False + + reg_file.seek(0) + reg_file.write(hex(1)) + reg_file.close() + + return True + + def get_transceiver_change_event(self): + port_dict = {} + while True: + for port_num in range(self.port_start, (self.port_end + 1)): + presence = self.get_presence(port_num) + if(presence and self._global_port_pres_dict[port_num] == '0'): + self._global_port_pres_dict[port_num] = '1' + port_dict[port_num] = '1' + elif(not presence and + self._global_port_pres_dict[port_num] == '1'): + self._global_port_pres_dict[port_num] = '0' + port_dict[port_num] = '0' + + if(len(port_dict) > 0): + return True, port_dict + + time.sleep(0.5) diff --git a/device/supermicro/x86_64-supermicro_sse_t7132s-r0/plugins/ssd_util.py b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/plugins/ssd_util.py new file mode 100644 index 0000000000..3a26dbfe43 --- /dev/null +++ b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/plugins/ssd_util.py @@ -0,0 +1,8 @@ +from sonic_platform_base.sonic_ssd.ssd_generic import SsdUtil as SsdUtilGeneric + +class SsdUtil(SsdUtilGeneric): + def parse_innodisk_info(self): + super().parse_innodisk_info() + if self.vendor_ssd_info: + # fix too lazy pattern 'Health:\s*(.+?)%?' + self.health = self._parse_re('Health:\s*(.+?)%', self.vendor_ssd_info) diff --git a/device/supermicro/x86_64-supermicro_sse_t7132s-r0/pmon_daemon_control.json b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/pmon_daemon_control.json new file mode 100644 index 0000000000..16f0755583 --- /dev/null +++ b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/pmon_daemon_control.json @@ -0,0 +1,6 @@ +{ + "skip_ledd": true, + "skip_xcvrd": false, + "skip_psud": false, + "skip_thermalctld": false +} diff --git a/device/supermicro/x86_64-supermicro_sse_t7132s-r0/sensors.conf b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/sensors.conf new file mode 100755 index 0000000000..7c9a6321df --- /dev/null +++ b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/sensors.conf @@ -0,0 +1,2 @@ +# libsensors configuration file for Celestica Midstone-200i. +# The i2c bus portion is omit because adapter name diff --git a/device/supermicro/x86_64-supermicro_sse_t7132s-r0/system_health_monitoring_config.json b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/system_health_monitoring_config.json new file mode 100644 index 0000000000..728dcb491e --- /dev/null +++ b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/system_health_monitoring_config.json @@ -0,0 +1,11 @@ +{ + "services_to_ignore": [], + "devices_to_ignore": ["asic", "psu.temperature"], + "user_defined_checkers": ["python3 /usr/local/bin/health_checker_thermal.py"], + "polling_interval": 60, + "led_color": { + "fault": "red", + "normal": "green", + "booting": "green_blink" + } +} diff --git a/device/supermicro/x86_64-supermicro_sse_t7132s-r0/thermal_policy.json b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/thermal_policy.json new file mode 100644 index 0000000000..e69de29bb2 diff --git a/device/supermicro/x86_64-supermicro_sse_t7132s-r0/topo.conf b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/topo.conf new file mode 100644 index 0000000000..795ea43143 --- /dev/null +++ b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/topo.conf @@ -0,0 +1 @@ +t1 diff --git a/device/supermicro/x86_64-supermicro_sse_t7132s-r0/warm-reboot_plugin b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/warm-reboot_plugin new file mode 100755 index 0000000000..6bc65e0edf --- /dev/null +++ b/device/supermicro/x86_64-supermicro_sse_t7132s-r0/warm-reboot_plugin @@ -0,0 +1,2 @@ +#!/bin/bash +/usr/local/bin/sysledctl.py reboot diff --git a/platform/innovium/one-image.mk b/platform/innovium/one-image.mk index 2cae779d71..bd63990f51 100755 --- a/platform/innovium/one-image.mk +++ b/platform/innovium/one-image.mk @@ -7,6 +7,7 @@ $(SONIC_ONE_IMAGE)_IMAGE_TYPE = onie $(SONIC_ONE_IMAGE)_LAZY_INSTALLS += $(CEL_MIDSTONE_200I_PLATFORM_MODULE) $(SONIC_ONE_IMAGE)_LAZY_INSTALLS += $(DELTA_PLATFORM_MODULE) $(SONIC_ONE_IMAGE)_LAZY_INSTALLS += $(NETBERG_AURORA_715_PLATFORM_MODULE) +$(SONIC_ONE_IMAGE)_LAZY_INSTALLS += $(SMCI_SSE_T7132S_PLATFORM_MODULE) $(SONIC_ONE_IMAGE)_LAZY_INSTALLS += $(WISTRON_PLATFORM_MODULE) $(SONIC_ONE_IMAGE)_INSTALLS += $(INVM_DRV) $(SONIC_ONE_IMAGE)_DOCKERS += $(SONIC_INSTALL_DOCKER_IMAGES) diff --git a/platform/innovium/platform-modules-supermicro.mk b/platform/innovium/platform-modules-supermicro.mk new file mode 100644 index 0000000000..f9efee4aed --- /dev/null +++ b/platform/innovium/platform-modules-supermicro.mk @@ -0,0 +1,9 @@ +SMCI_PLATFORM_MODULE_VERSION = 0.1 + +export SMCI_PLATFORM_MODULE_VERSION + +SMCI_SSE_T7132S_PLATFORM_MODULE = platform-modules-sse-t7132s_$(SMCI_PLATFORM_MODULE_VERSION)_$(CONFIGURED_ARCH).deb +$(SMCI_SSE_T7132S_PLATFORM_MODULE)_SRC_PATH = $(PLATFORM_PATH)/sonic-platform-modules-supermicro +$(SMCI_SSE_T7132S_PLATFORM_MODULE)_DEPENDS += $(LINUX_HEADERS) $(LINUX_HEADERS_COMMON) +$(SMCI_SSE_T7132S_PLATFORM_MODULE)_PLATFORM = x86_64-supermicro_sse_t7132s-r0 +SONIC_DPKG_DEBS += $(SMCI_SSE_T7132S_PLATFORM_MODULE) diff --git a/platform/innovium/rules.mk b/platform/innovium/rules.mk index 350ab8ef3f..03efa70b0d 100755 --- a/platform/innovium/rules.mk +++ b/platform/innovium/rules.mk @@ -1,5 +1,6 @@ include $(PLATFORM_PATH)/invm-sai.mk include $(PLATFORM_PATH)/platform-modules-cel.mk +include $(PLATFORM_PATH)/platform-modules-supermicro.mk #include $(PLATFORM_PATH)/platform-modules-delta.mk include $(PLATFORM_PATH)/platform-modules-wistron.mk #include $(PLATFORM_PATH)/platform-modules-netberg.mk diff --git a/platform/innovium/sonic-platform-modules-supermicro/debian/changelog b/platform/innovium/sonic-platform-modules-supermicro/debian/changelog new file mode 100644 index 0000000000..d7863facbb --- /dev/null +++ b/platform/innovium/sonic-platform-modules-supermicro/debian/changelog @@ -0,0 +1,5 @@ +sonic-supermicro-platform-modules (0.1) unstable; urgency=low + + * Inital release of SSE-T7132S platform module package. + + -- SuperMicro Team Fri, 22 Oct 2021 17:14:00 +0800 diff --git a/platform/innovium/sonic-platform-modules-supermicro/debian/compat b/platform/innovium/sonic-platform-modules-supermicro/debian/compat new file mode 100644 index 0000000000..ec635144f6 --- /dev/null +++ b/platform/innovium/sonic-platform-modules-supermicro/debian/compat @@ -0,0 +1 @@ +9 diff --git a/platform/innovium/sonic-platform-modules-supermicro/debian/control b/platform/innovium/sonic-platform-modules-supermicro/debian/control new file mode 100644 index 0000000000..1189c7d867 --- /dev/null +++ b/platform/innovium/sonic-platform-modules-supermicro/debian/control @@ -0,0 +1,16 @@ +Source: sonic-supermicro-platform-modules +Section: main +Priority: extra +Maintainer: SuperMicro Team +Build-Depends: + dh-python, + debhelper (>= 9.0.0), + python3(>=3.5), + python3-setuptools, + bzip2 + +Standards-Version: 3.9.3 +Package: platform-modules-sse-t7132s +Architecture: amd64 +Description: kernel modules for platform devices such as fan, led, sfp + diff --git a/platform/innovium/sonic-platform-modules-supermicro/debian/platform-modules-sse-t7132s.install b/platform/innovium/sonic-platform-modules-supermicro/debian/platform-modules-sse-t7132s.install new file mode 100644 index 0000000000..bf9378db1f --- /dev/null +++ b/platform/innovium/sonic-platform-modules-supermicro/debian/platform-modules-sse-t7132s.install @@ -0,0 +1,8 @@ +sse-t7132s/scripts/platform.sh /usr/local/bin +sse-t7132s/scripts/health_checker_thermal.py /usr/local/bin +sse-t7132s/scripts/sysledctl.py /usr/local/bin +sse-t7132s/cfg/t7132s-modules.conf etc/modules-load.d +sse-t7132s/cfg/iTCO_wdt.conf /etc/modprobe.d +sse-t7132s/systemd/platform-modules-sse-t7132s.service etc/systemd/system +sse-t7132s/systemd/sysled.service etc/systemd/system +sse-t7132s/modules/sonic_platform-1.0-py3-none-any.whl usr/share/sonic/device/x86_64-supermicro_sse_t7132s-r0 diff --git a/platform/innovium/sonic-platform-modules-supermicro/debian/platform-modules-sse-t7132s.postinst b/platform/innovium/sonic-platform-modules-supermicro/debian/platform-modules-sse-t7132s.postinst new file mode 100644 index 0000000000..fc0521a672 --- /dev/null +++ b/platform/innovium/sonic-platform-modules-supermicro/debian/platform-modules-sse-t7132s.postinst @@ -0,0 +1,14 @@ +# postinst script for SSE-T7132S + +# Enable SuperMicro SSE-T7132S +depmod -a +modprobe -r iTCO_wdt +modprobe -r t7132s +modprobe t7132s +systemctl enable platform-modules-sse-t7132s.service +systemctl start platform-modules-sse-t7132s.service +systemctl enable sysled.service + + +#DEBHELPER# + diff --git a/platform/innovium/sonic-platform-modules-supermicro/debian/rules b/platform/innovium/sonic-platform-modules-supermicro/debian/rules new file mode 100644 index 0000000000..1d733f22f4 --- /dev/null +++ b/platform/innovium/sonic-platform-modules-supermicro/debian/rules @@ -0,0 +1,39 @@ +#!/usr/bin/make -f + +export INSTALL_MOD_DIR:=extra + +KVERSION ?= $(shell uname -r) +KERNEL_SRC := /lib/modules/$(KVERSION) +MOD_SRC_DIR:= $(shell pwd) +MODULE_DIRS:= sse-t7132s + +%: + dh $@ + +override_dh_auto_build: + (for mod in $(MODULE_DIRS); do \ + make -C $(KERNEL_SRC)/build M=$(MOD_SRC_DIR)/$${mod}/modules; \ + cd $(MOD_SRC_DIR)/$${mod}; \ + python3 setup.py bdist_wheel -d $(MOD_SRC_DIR)/$${mod}/modules; \ + cd $(MOD_SRC_DIR); \ + done) + +override_dh_auto_install: + (for mod in $(MODULE_DIRS); do \ + dh_installdirs -pplatform-modules-$${mod} \ + $(KERNEL_SRC)/$(INSTALL_MOD_DIR); \ + cp $(MOD_SRC_DIR)/$${mod}/modules/*.ko \ + debian/platform-modules-$${mod}/$(KERNEL_SRC)/$(INSTALL_MOD_DIR); \ + done) + +override_dh_usrlocal: + +override_dh_clean: + dh_clean + (for mod in $(MODULE_DIRS); do \ + make -C $(KERNEL_SRC)/build M=$(MOD_SRC_DIR)/$${mod}/modules clean; \ + rm -f $(MOD_SRC_DIR)/$${mod}/modules/*.whl; \ + rm -rf $(MOD_SRC_DIR)/$${mod}/build; \ + rm -rf $(MOD_SRC_DIR)/$${mod}/*.egg-info; \ + done) + diff --git a/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/cfg/iTCO_wdt.conf b/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/cfg/iTCO_wdt.conf new file mode 100644 index 0000000000..99ded4c322 --- /dev/null +++ b/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/cfg/iTCO_wdt.conf @@ -0,0 +1 @@ +blacklist iTCO_wdt diff --git a/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/cfg/t7132s-modules.conf b/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/cfg/t7132s-modules.conf new file mode 100644 index 0000000000..ffb5b98feb --- /dev/null +++ b/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/cfg/t7132s-modules.conf @@ -0,0 +1,16 @@ +# /etc/modules: kernel modules to load at boot time. +# +# This file contains the names of kernel modules that should be loaded +# at boot time, one per line. Lines beginning with "#" are ignored. + +i2c-i801 +i2c-isch +i2c-ismt +i2c-dev +i2c-mux +i2c-smbus +i2c-mux-gpio +i2c-mux-pca954x +ipmi-devintf +ast +t7132s \ No newline at end of file diff --git a/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/modules/Makefile b/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/modules/Makefile new file mode 100644 index 0000000000..7288a5e59c --- /dev/null +++ b/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/modules/Makefile @@ -0,0 +1 @@ +obj-m := t7132s.o diff --git a/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/modules/t7132s.c b/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/modules/t7132s.c new file mode 100755 index 0000000000..2bc83f5b3a --- /dev/null +++ b/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/modules/t7132s.c @@ -0,0 +1,1706 @@ +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include /* For the watchdog specific items */ +#define REG_LACKSR 0x00 +#define LACKSR_CLKDIV 0x8 +#define LACKSR_CLKSEL (1 << 8) +#define LACKSR_DIVEN (1 << 10) +#define LACKSR_CLKODR (1 << 12) +#define LACKSR_CLKOEN (1 << 13) +#define LACKSR_ALERA (1 << 14) + +#define REG_LAS0CFGR 0x00C +#define REG_LAS0TIMR 0x010 +#define REG_LAS0ADDR 0x014 +#define REG_LAS1CFGR 0x018 +#define REG_LAS1TIMR 0x01C +#define REG_LAS1ADDR 0x020 +#define LASCFGR_INT_P (1 << 0) +#define LASCFGR_INT_L (1 << 1) +#define LASCFGR_DRQ_P (1 << 2) +#define LASCFGR_DAK_P (1 << 3) +#define LASCFGR_LSER (1 << 4) +#define LASCFGR_ENDIAN (1 << 5) +#define LASCFGR_BW16 (1 << 6) +#define REG_LIEMR 0x024 +#define LIEMR_RDYPOL (1 << 4) +#define LIEMR_ALEPOL (1 << 5) +#define LIEMR_SYNCBUS (1 << 6) +#define LIEMR_MULTBUS (1 << 7) +#define LIEMR_DMA0EN (1 << 8) +#define LIEMR_DMA1EN (1 << 9) +#define LIEMR_LRST (1 << 14) +#define LIEMR_SRST (1 << 15) +#define LIEMR_L0EINTEN (1 << 16) +#define LIEMR_L0RTOIEN (1 << 17) +#define LIEMR_L1EINTEN (1 << 18) +#define LIEMR_L1RTOIEN (1 << 19) +#define LIEMR_D0DIEN (1 << 24) +#define LIEMR_D0AIEN (1 << 25) +#define LIEMR_D1DIEN (1 << 26) +#define LIEMR_D1AIEN (1 << 27) + +#define DRIVER_NAME "switchboard" +#define DEVICE_NAME "fwupgrade" +#define CLASS_NAME "t7132s_cpld" +#define SFF_PORT_TOTAL 34 +#define QSFP_PORT_TOTAL 32 +#define SFP_PORT_TOTAL 2 + +/* Refer to SSE_T7132S_CPLD_spec_0820.docx for more details */ +/* Switch model ID */ +#define CPLD1_REG_SW_ID 0x1 +/* HW/CPLD version */ +#define CPLD1_REG_HWREV 0x2 +/* Power sequence module status */ +#define CPLD1_REG_PWR_GOOD 0x3 +/* Voltage Regulator Module ALERT/Thermal */ +#define CPLD1_REG_VRM 0x4 +/* Enable/ Reset misc. devices */ +#define CPLD1_REG_DEV_STATE_1 0x5 +/* Enable/ Reset misc. devices */ +#define CPLD1_REG_DEV_STATE_2 0x6 +/* System reset records */ +#define CPLD1_REG_SYS_RESET_REC 0x9 +/* PCA9548 I2C bus switch RSTn */ +#define CPLD1_REG_MUX_STATE 0xB +/* Transceiver Power Enable */ +#define CPLD1_REG_X_PWR_EN_1 0xC +/* Transceiver Power Enable */ +#define CPLD1_REG_X_PWR_EN_2 0xD +/* Transceiver Power Good */ +#define CPLD1_REG_X_PWR_GOOD_1 0xE +/* Transceiver Power Good */ +#define CPLD1_REG_X_PWR_GOOD_2 0xF +/* Watch Dog Timer maximum count setting by seconds */ +#define CPLD1_REG_WDT_MAX_COUNT_1 0x22 +#define CPLD1_REG_WDT_MAX_COUNT_2 0x23 +/* Watch Dog Timer current count value 16 bits */ +#define CPLD1_REG_WDT_CUR_COUNT_1 0x24 +#define CPLD1_REG_WDT_CUR_COUNT_2 0x25 +/* Version as BMC I2C Registers */ +#define CPLD1_REG_VER_BMC_I2C_1 0xF0 +#define CPLD1_REG_VER_BMC_I2C_2 0xF1 +#define CPLD1_REG_VER_BMC_I2C_3 0xF2 +#define CPLD1_REG_VER_BMC_I2C_4 0xF3 +/* CPLD JED Released Date */ +#define CPLD1_REG_JED_REL_MONTH 0xFE +#define CPLD1_REG_JED_REL_DAY 0xFF + +/* HW/CPLD version */ +#define CPLD2_REG_HWREV 0x2 +/* System Ready/Reset Status */ +#define CPLD2_REG_SYSRDY_RESET_STATUS 0x3 +/* All xcvr LED control */ +#define CPLD2_REG_ALL_LED_CTRL 0x4 +/* Version as BMC I2C Registers */ +#define CPLD2_REG_VER_BMC_I2C_1 0xF0 +#define CPLD2_REG_VER_BMC_I2C_2 0xF1 +#define CPLD2_REG_VER_BMC_I2C_3 0xF2 +#define CPLD2_REG_VER_BMC_I2C_4 0xF3 +/* CPLD JED Released Date */ +#define CPLD2_REG_JED_REL_MONTH 0xFE +#define CPLD2_REG_JED_REL_DAY 0xFF + +#define QSFP_T_RESET_LOf 0x10 +#define QSFP_T_RESET_HIf 0x11 + +#define QSFP_T_LPMODE_LOf 0x12 +#define QSFP_T_LPMODE_HIf 0x13 + +#define QSFP_T_INT_LOf 0x14 +#define QSFP_T_INT_HIf 0x15 + +#define QSFP_T_MODPRS_LOf 0x16 +#define QSFP_T_MODPRS_HIf 0x17 + +#define QSFP_B_RESET_LOf 0x18 +#define QSFP_B_RESET_HIf 0x19 + +#define QSFP_B_LPMODE_LOf 0x1A +#define QSFP_B_LPMODE_HIf 0x1B + +#define QSFP_B_INT_LOf 0x1C +#define QSFP_B_INT_HIf 0x1D + +#define QSFP_B_MODPRS_LOf 0x1E +#define QSFP_B_MODPRS_HIf 0x1F + +#define QSFP_REG_READ(_pbmp_, _reg_, _base_) \ + do { \ + _pbmp_ = readb(_base_ + _reg_##_HIf) | \ + (readb(_base_ + _reg_##_LOf) << 8); \ + } while (0); + +#define QSFP_REG_WRITE(_pbmp_, _reg_, _base_) \ + do { \ + writeb((_pbmp_ & 0x00ff), \ + _base_ + _reg_##_HIf); \ + writeb(((_pbmp_ >> 8) & 0x00ff), \ + _base_ + _reg_##_LOf); \ + } while (0); + +enum PORT_TYPE { NONE, QSFP, SFP }; + +struct t7132s_cpld { + struct mutex lock; + unsigned char __iomem *cpld_base; + unsigned char __iomem *cpld2_base; + struct device *sff_devices[SFF_PORT_TOTAL]; + struct i2c_client *sff_i2c_clients[SFF_PORT_TOTAL]; +}; + +static struct t7132s_cpld *cpld_data; +static struct class *cpld_class = NULL; + +enum i2c_adapter_type { + I2C_ADAPTER_I801 = 0, + I2C_ADAPTER_ISMT, + I2C_ADAPTER_CP2112, + I2C_ADAPTER_PCA954X +}; + +const char *bms_i2c_adapter_names[] = { + "SMBus I801 adapter", + "SMBus iSMT adapter", + "CP2112 SMBus Bridge", + "PCA954X Mux" }; + +struct i2c_topo_node { + int adapter_type; + int parent_index; + int chan_id; + struct i2c_board_info entry; + struct i2c_client *client; +}; + +static struct i2c_topo_node i2c_topo[] = { + { I2C_ADAPTER_CP2112, -1, -1, { I2C_BOARD_INFO("pca9548", 0x70) }, NULL }, + { I2C_ADAPTER_PCA954X, 0, 0, { I2C_BOARD_INFO("pca9548", 0x71) }, NULL }, + { I2C_ADAPTER_PCA954X, 0, 2, { I2C_BOARD_INFO("pca9548", 0x72) }, NULL }, + { I2C_ADAPTER_PCA954X, 0, 1, { I2C_BOARD_INFO("pca9548", 0x73) }, NULL }, + { I2C_ADAPTER_PCA954X, 0, 3, { I2C_BOARD_INFO("pca9548", 0x74) }, NULL }, + { I2C_ADAPTER_PCA954X, 0, 4, { I2C_BOARD_INFO("pca9548", 0x75) }, NULL }, + { I2C_ADAPTER_PCA954X, 5, 3, { I2C_BOARD_INFO("24c64", 0x53) }, NULL }, +}; + +static struct i2c_board_info sff_eeprom_info[] = { + { I2C_BOARD_INFO("optoe3", 0x50) }, + { I2C_BOARD_INFO("optoe2", 0x50) } +}; + +struct sff_device_data { + int portid; + enum PORT_TYPE port_type; + int parent_index; + int chan_id; +}; + +struct sff_device_data sff_device_tbl[SFF_PORT_TOTAL] = { + { 1, QSFP, 1, 0 }, { 2, QSFP, 3, 3 }, { 3, QSFP, 1, 1 }, + { 4, QSFP, 3, 2 }, { 5, QSFP, 1, 2 }, { 6, QSFP, 3, 1 }, + { 7, QSFP, 1, 3 }, { 8, QSFP, 3, 0 }, { 9, QSFP, 1, 4 }, + { 10, QSFP, 3, 7 }, { 11, QSFP, 1, 5 }, { 12, QSFP, 3, 6 }, + { 13, QSFP, 1, 6 }, { 14, QSFP, 3, 5 }, { 15, QSFP, 1, 7 }, + { 16, QSFP, 3, 4 }, { 17, QSFP, 2, 0 }, { 18, QSFP, 4, 3 }, + { 19, QSFP, 2, 1 }, { 20, QSFP, 4, 2 }, { 21, QSFP, 2, 2 }, + { 22, QSFP, 4, 1 }, { 23, QSFP, 2, 3 }, { 24, QSFP, 4, 0 }, + { 25, QSFP, 2, 4 }, { 26, QSFP, 4, 7 }, { 27, QSFP, 2, 5 }, + { 28, QSFP, 4, 6 }, { 29, QSFP, 2, 6 }, { 30, QSFP, 4, 5 }, + { 31, QSFP, 2, 7 }, { 32, QSFP, 4, 4 }, { 1, SFP, 5, 0 }, + { 2, SFP, 5, 1 }, +}; + +#define WATCHDOG_TIMEOUT 30 /* 30 sec default heartbeat */ + +static struct watchdog_device *pwddev; + +static const struct watchdog_info ident = { + .options = WDIOF_SETTIMEOUT | + WDIOF_KEEPALIVEPING | + WDIOF_MAGICCLOSE, + .firmware_version = 0, + .identity = "t7132s_wdt", +}; + +/* used to access CPLD register not defined in this driver with sys filesystem */ +uint8_t cpld_testee_offset[2] = {0, 0}; + +static ssize_t swid_show(struct device *dev, struct device_attribute *attr, + char *buf) +{ + uint8_t data = 0; + int err; + char *ptr = (cpld_data->cpld_base + CPLD1_REG_SW_ID); + + mutex_lock(&cpld_data->lock); + data = readb(cpld_data->cpld_base + CPLD1_REG_SW_ID); + mutex_unlock(&cpld_data->lock); + + return sprintf(buf, "0x%2.2x\n", data); +} +struct device_attribute dev_attr_swid = __ATTR(swid, 0400, swid_show, NULL); + +static ssize_t hwrev_show(struct device *dev, struct device_attribute *attr, + char *buf) +{ + uint8_t data = 0; + int err; + char *ptr = (cpld_data->cpld_base + CPLD1_REG_HWREV); + + mutex_lock(&cpld_data->lock); + data = readb(cpld_data->cpld_base + CPLD1_REG_HWREV); + mutex_unlock(&cpld_data->lock); + + return sprintf(buf, "0x%2.2x\n", data); +} +struct device_attribute dev_attr_hwrev = __ATTR(hw_rev, 0400, hwrev_show, NULL); + +static ssize_t pwrgood_show(struct device *dev, struct device_attribute *attr, + char *buf) +{ + uint8_t data = 0; + int err; + + mutex_lock(&cpld_data->lock); + data = readb(cpld_data->cpld_base + CPLD1_REG_PWR_GOOD); + mutex_unlock(&cpld_data->lock); + + return sprintf(buf, "0x%2.2x\n", data); +} +struct device_attribute dev_attr_pwrgood = + __ATTR(pwr_good, 0400, pwrgood_show, NULL); + +static ssize_t vrm_show(struct device *dev, struct device_attribute *attr, + char *buf) +{ + uint8_t data = 0; + int err; + + mutex_lock(&cpld_data->lock); + data = readb(cpld_data->cpld_base + CPLD1_REG_VRM); + mutex_unlock(&cpld_data->lock); + + return sprintf(buf, "0x%2.2x\n", data); +} +struct device_attribute dev_attr_vrm = __ATTR(vrm, 0400, vrm_show, NULL); + +static ssize_t devstate_show(struct device *dev, struct device_attribute *attr, + char *buf) +{ + uint8_t data = 0; + uint8_t data2 = 0; + long value = 0; + int err; + + mutex_lock(&cpld_data->lock); + data = readb(cpld_data->cpld_base + CPLD1_REG_DEV_STATE_1); + data2 = readb(cpld_data->cpld_base + CPLD1_REG_DEV_STATE_2); + value = data; + value |= (data2 << 8); + mutex_unlock(&cpld_data->lock); + + return sprintf(buf, "0x%4.4lx\n", value); +} +static ssize_t devstate_store(struct device *dev, struct device_attribute *attr, + const char *buf, size_t count) +{ + ssize_t status = 0; + long value = 0; + uint8_t data = 0; + uint8_t data2 = 0; + + mutex_lock(&cpld_data->lock); + status = kstrtol(buf, 0, &value); + if (status == 0) { + data = value & 0xff; + data2 = (value & 0xff00) >> 8; + writeb(data, cpld_data->cpld_base + CPLD1_REG_DEV_STATE_1); + writeb(data2, cpld_data->cpld_base + CPLD1_REG_DEV_STATE_2); + status = count; + } + mutex_unlock(&cpld_data->lock); + + return status; +} +struct device_attribute dev_attr_devstate = + __ATTR(dev_state, 0600, devstate_show, devstate_store); + +static ssize_t wdtmax_show(struct device *dev, struct device_attribute *attr, + char *buf) +{ + uint8_t data1 = 0; + uint8_t data2 = 0; + long value = 0; + + mutex_lock(&cpld_data->lock); + data1 = readb(cpld_data->cpld_base + CPLD1_REG_WDT_MAX_COUNT_1); + data2 = readb(cpld_data->cpld_base + CPLD1_REG_WDT_MAX_COUNT_2); + value = (data2 << 8) | data1; + mutex_unlock(&cpld_data->lock); + + return sprintf(buf, "0x%4.4lx\n", value); +} +static ssize_t wdtmax_store(struct device *dev, struct device_attribute *attr, + const char *buf, size_t count) +{ + ssize_t status = 0; + long value = 0; + uint8_t data1; + uint8_t data2; + + mutex_lock(&cpld_data->lock); + status = kstrtol(buf, 0, &value); + if (status == 0) { + data1 = value & 0xff; + data2 = (value & 0xff00) >> 8; + writeb(data1, cpld_data->cpld_base + CPLD1_REG_WDT_MAX_COUNT_1); + writeb(data2, cpld_data->cpld_base + CPLD1_REG_WDT_MAX_COUNT_2); + status = count; + } + mutex_unlock(&cpld_data->lock); + + return status; +} +struct device_attribute dev_attr_wdtmax = + __ATTR(wdt_max, 0600, wdtmax_show, wdtmax_store); + +static ssize_t wdtcount_show(struct device *dev, struct device_attribute *attr, + char *buf) +{ + uint8_t data1 = 0; + uint8_t data2 = 0; + long value = 0; + + mutex_lock(&cpld_data->lock); + data1 = readb(cpld_data->cpld_base + CPLD1_REG_WDT_CUR_COUNT_1); + data2 = readb(cpld_data->cpld_base + CPLD1_REG_WDT_CUR_COUNT_2); + value = (data2 << 8) | data1; + mutex_unlock(&cpld_data->lock); + + return sprintf(buf, "0x%4.4lx\n", value); +} +struct device_attribute dev_attr_wdtcount = + __ATTR(wdt_count, 0400, wdtcount_show, NULL); + +static ssize_t sysrst_rec_show(struct device *dev, struct device_attribute *attr, + char *buf) +{ + uint8_t data = 0; + int err; + + mutex_lock(&cpld_data->lock); + data = readb(cpld_data->cpld_base + CPLD1_REG_SYS_RESET_REC); + mutex_unlock(&cpld_data->lock); + + return sprintf(buf, "0x%2.2x\n", data); +} +static ssize_t sysrst_rec_store(struct device *dev, struct device_attribute *attr, + const char *buf, size_t count) +{ + ssize_t status = 0; + uint8_t data; + + mutex_lock(&cpld_data->lock); + status = kstrtou8(buf, 0, &data); + + if (status == 0) { + writeb(data, cpld_data->cpld_base + CPLD1_REG_SYS_RESET_REC); + status = count; + } + mutex_unlock(&cpld_data->lock); + + return status; +} +struct device_attribute dev_attr_sysrst_rec = + __ATTR(sysrst_rec, 0600, sysrst_rec_show, sysrst_rec_store); + +static ssize_t muxstate_show(struct device *dev, struct device_attribute *attr, + char *buf) +{ + uint8_t data = 0; + int err; + + mutex_lock(&cpld_data->lock); + data = readb(cpld_data->cpld_base + CPLD1_REG_MUX_STATE); + mutex_unlock(&cpld_data->lock); + + return sprintf(buf, "0x%2.2x\n", data); +} +static ssize_t muxstate_store(struct device *dev, struct device_attribute *attr, + const char *buf, size_t count) +{ + ssize_t status = 0; + uint8_t data; + + mutex_lock(&cpld_data->lock); + status = kstrtou8(buf, 0, &data); + if (status == 0) { + writeb(data, cpld_data->cpld_base + CPLD1_REG_MUX_STATE); + status = count; + } + mutex_unlock(&cpld_data->lock); + + return status; +} +struct device_attribute dev_attr_muxstate = + __ATTR(i2c_mux_state, 0600, muxstate_show, muxstate_store); + +static ssize_t xcvr_pwrstate_show(struct device *dev, + struct device_attribute *attr, char *buf) +{ + uint8_t data = 0; + uint8_t data2 = 0; + long value = 0; + int err; + + mutex_lock(&cpld_data->lock); + data = readb(cpld_data->cpld_base + CPLD1_REG_X_PWR_EN_2); + data2 = readb(cpld_data->cpld_base + CPLD1_REG_X_PWR_EN_1); + value = data; + value |= (data2 << 8); + mutex_unlock(&cpld_data->lock); + + return sprintf(buf, "0x%2.2x\n", value); +} +static ssize_t xcvr_pwrstate_store(struct device *dev, + struct device_attribute *attr, + const char *buf, size_t count) +{ + ssize_t status = 0; + long value = 0; + uint8_t data = 0; + uint8_t data2 = 0; + + mutex_lock(&cpld_data->lock); + status = kstrtol(buf, 0, &value); + if (status == 0) { + data = value & 0xff; + data2 = (value & 0xff00) >> 8; + writeb(data, cpld_data->cpld_base + CPLD1_REG_X_PWR_EN_2); + writeb(data2, cpld_data->cpld_base + CPLD1_REG_X_PWR_EN_1); + status = count; + } + mutex_unlock(&cpld_data->lock); + + return status; +} +struct device_attribute dev_attr_xcvr_pwrstate = + __ATTR(xcvr_pwr_state, 0600, xcvr_pwrstate_show, xcvr_pwrstate_store); + +static ssize_t xcvr_pwrgood_show(struct device *dev, + struct device_attribute *attr, char *buf) +{ + uint8_t data = 0; + uint8_t data2 = 0; + long value = 0; + int err; + + mutex_lock(&cpld_data->lock); + data = readb(cpld_data->cpld_base + CPLD1_REG_X_PWR_GOOD_2); + data2 = readb(cpld_data->cpld_base + CPLD1_REG_X_PWR_GOOD_1); + value = data; + value |= (data2 << 8); + mutex_unlock(&cpld_data->lock); + + return sprintf(buf, "0x%2.2x\n", value); +} +struct device_attribute dev_attr_xcvr_pwrgood = + __ATTR(xcvr_pwr_good, 0400, xcvr_pwrgood_show, NULL); + +static ssize_t cpld1_ver_bmc_i2c_show(struct device *dev, + struct device_attribute *attr, char *buf) +{ + uint8_t data = 0; + uint8_t data2 = 0; + uint8_t data3 = 0; + uint8_t data4 = 0; + long value = 0; + int err; + + mutex_lock(&cpld_data->lock); + data = readb(cpld_data->cpld_base + CPLD1_REG_VER_BMC_I2C_4); + data2 = readb(cpld_data->cpld_base + CPLD1_REG_VER_BMC_I2C_3); + data3 = readb(cpld_data->cpld_base + CPLD1_REG_VER_BMC_I2C_2); + data4 = readb(cpld_data->cpld_base + CPLD1_REG_VER_BMC_I2C_1); + value = data; + value |= (data2 << 8); + value |= (data3 << 16); + value |= (data4 << 24); + mutex_unlock(&cpld_data->lock); + + return sprintf(buf, "0x%8.8lx\n", value); +} +struct device_attribute dev_attr_cpld1_ver_bmc_i2c = + __ATTR(ver_bmc_i2c, 0444, cpld1_ver_bmc_i2c_show, NULL); + +static ssize_t cpld1_jed_rel_show(struct device *dev, + struct device_attribute *attr, char *buf) +{ + uint8_t data = 0; + uint8_t data2 = 0; + long value = 0; + int err; + + mutex_lock(&cpld_data->lock); + data = readb(cpld_data->cpld_base + CPLD1_REG_JED_REL_DAY); + data2 = readb(cpld_data->cpld_base + CPLD1_REG_JED_REL_MONTH); + value = data; + value |= (data2 << 8); + mutex_unlock(&cpld_data->lock); + + return sprintf(buf, "0x%4.4lx\n", value); +} +struct device_attribute dev_attr_cpld1_jed_rel = + __ATTR(jed_rel, 0400, cpld1_jed_rel_show, NULL); + +static ssize_t cpld1_testee_offset_show(struct device *dev, struct device_attribute *attr, + char *buf) +{ + return sprintf(buf, "0x%2.2x\n", cpld_testee_offset[0]); +} +static ssize_t cpld1_testee_offset_store(struct device *dev, struct device_attribute *attr, + const char *buf, size_t count) +{ + ssize_t status = 0; + uint8_t data; + + status = kstrtou8(buf, 0, &data); + if (status == 0) { + cpld_testee_offset[0] = data; + status = count; + } + + return status; +} +struct device_attribute dev_attr_cpld1_testee_offset = + __ATTR(testee_offset, 0600, cpld1_testee_offset_show, cpld1_testee_offset_store); + +static ssize_t cpld1_testee_value_show(struct device *dev, struct device_attribute *attr, + char *buf) +{ + uint8_t data = 0; + int err; + + mutex_lock(&cpld_data->lock); + data = readb(cpld_data->cpld_base + cpld_testee_offset[0]); + mutex_unlock(&cpld_data->lock); + + return sprintf(buf, "0x%2.2x\n", data); +} +static ssize_t cpld1_testee_value_store(struct device *dev, struct device_attribute *attr, + const char *buf, size_t count) +{ + ssize_t status = 0; + uint8_t data; + + mutex_lock(&cpld_data->lock); + status = kstrtou8(buf, 0, &data); + if (status == 0) { + writeb(data, cpld_data->cpld_base + cpld_testee_offset[0]); + status = count; + } + mutex_unlock(&cpld_data->lock); + + return status; +} +struct device_attribute dev_attr_cpld1_testee_value = + __ATTR(testee_value, 0600, cpld1_testee_value_show, cpld1_testee_value_store); + +static struct attribute *cpld1_attrs[] = { + &dev_attr_swid.attr, + &dev_attr_hwrev.attr, + &dev_attr_pwrgood.attr, + &dev_attr_vrm.attr, + &dev_attr_devstate.attr, + &dev_attr_sysrst_rec.attr, + &dev_attr_muxstate.attr, + &dev_attr_xcvr_pwrstate.attr, + &dev_attr_xcvr_pwrgood.attr, + &dev_attr_wdtmax.attr, + &dev_attr_wdtcount.attr, + &dev_attr_cpld1_ver_bmc_i2c.attr, + &dev_attr_cpld1_jed_rel.attr, + &dev_attr_cpld1_testee_offset.attr, + &dev_attr_cpld1_testee_value.attr, + NULL, +}; + +static struct attribute_group cpld1_attr_grp = { + .attrs = cpld1_attrs, +}; + +static ssize_t cpld2_ver_show(struct device *dev, struct device_attribute *attr, + char *buf) +{ + uint8_t data = 0; + int err; + + mutex_lock(&cpld_data->lock); + data = readb(cpld_data->cpld2_base + CPLD2_REG_HWREV); + mutex_unlock(&cpld_data->lock); + + return sprintf(buf, "0x%2.2x\n", data); +} +struct device_attribute dev_attr_cpld2_ver = __ATTR(cpld2_ver, 0400, cpld2_ver_show, NULL); + +static ssize_t sysrdy_rst_status_show(struct device *dev, + struct device_attribute *attr, char *buf) +{ + uint8_t data = 0; + long value = 0; + int err; + + mutex_lock(&cpld_data->lock); + data = readb(cpld_data->cpld2_base + + CPLD2_REG_SYSRDY_RESET_STATUS); + value = data; + mutex_unlock(&cpld_data->lock); + + return sprintf(buf, "0x%2.2x\n", value); +} +static ssize_t sysrdy_rst_status_store(struct device *dev, + struct device_attribute *attr, + const char *buf, size_t count) +{ + ssize_t status = 0; + long value = 0; + uint8_t data = 0; + + mutex_lock(&cpld_data->lock); + status = kstrtol(buf, 0, &value); + if (status == 0) { + data = value & 0xff; + writeb(data, cpld_data->cpld2_base + + CPLD2_REG_SYSRDY_RESET_STATUS); + status = count; + } + mutex_unlock(&cpld_data->lock); + + return status; +} +struct device_attribute dev_attr_sysrdy_rst_status = + __ATTR(sysrdy_rst_state, 0600, sysrdy_rst_status_show, + sysrdy_rst_status_store); + +static ssize_t all_xcvr_led_ctrl_show(struct device *dev, + struct device_attribute *attr, char *buf) +{ + uint8_t data = 0; + long value = 0; + int err; + + mutex_lock(&cpld_data->lock); + data = readb(cpld_data->cpld2_base + + CPLD2_REG_ALL_LED_CTRL); + value = data; + mutex_unlock(&cpld_data->lock); + + return sprintf(buf, "0x%2.2x\n", value); +} +static ssize_t all_xcvr_led_ctrl_store(struct device *dev, + struct device_attribute *attr, + const char *buf, size_t count) +{ + ssize_t status = 0; + long value = 0; + uint8_t data = 0; + + mutex_lock(&cpld_data->lock); + status = kstrtol(buf, 0, &value); + if (status == 0) { + data = value & 0x1f; + writeb(data, cpld_data->cpld2_base + + CPLD2_REG_ALL_LED_CTRL); + status = count; + } + mutex_unlock(&cpld_data->lock); + + return status; +} +struct device_attribute dev_attr_all_xcvr_led_ctrl = + __ATTR(all_xcvr_led_ctrl, 0600, all_xcvr_led_ctrl_show, + all_xcvr_led_ctrl_store); + +static ssize_t cpld2_ver_bmc_i2c_show(struct device *dev, + struct device_attribute *attr, char *buf) +{ + uint8_t data = 0; + uint8_t data2 = 0; + uint8_t data3 = 0; + uint8_t data4 = 0; + long value = 0; + int err; + + mutex_lock(&cpld_data->lock); + data = readb(cpld_data->cpld2_base + CPLD2_REG_VER_BMC_I2C_4); + data2 = readb(cpld_data->cpld2_base + CPLD2_REG_VER_BMC_I2C_3); + data3 = readb(cpld_data->cpld2_base + CPLD2_REG_VER_BMC_I2C_2); + data4 = readb(cpld_data->cpld2_base + CPLD2_REG_VER_BMC_I2C_1); + value = data; + value |= (data2 << 8); + value |= (data3 << 16); + value |= (data4 << 24); + mutex_unlock(&cpld_data->lock); + + return sprintf(buf, "0x%8.8lx\n", value); +} +struct device_attribute dev_attr_cpld2_ver_bmc_i2c = + __ATTR(ver_bmc_i2c, 0400, cpld2_ver_bmc_i2c_show, NULL); + +static ssize_t cpld2_jed_rel_show(struct device *dev, + struct device_attribute *attr, char *buf) +{ + uint8_t data = 0; + uint8_t data2 = 0; + long value = 0; + int err; + + mutex_lock(&cpld_data->lock); + data = readb(cpld_data->cpld2_base + CPLD2_REG_JED_REL_DAY); + data2 = readb(cpld_data->cpld2_base + CPLD2_REG_JED_REL_MONTH); + value = data; + value |= (data2 << 8); + mutex_unlock(&cpld_data->lock); + + return sprintf(buf, "0x%4.4lx\n", value); +} +struct device_attribute dev_attr_cpld2_jed_rel = + __ATTR(jed_rel, 0400, cpld2_jed_rel_show, NULL); + +static ssize_t cpld2_testee_offset_show(struct device *dev, struct device_attribute *attr, + char *buf) +{ + return sprintf(buf, "0x%2.2x\n", cpld_testee_offset[1]); +} +static ssize_t cpld2_testee_offset_store(struct device *dev, struct device_attribute *attr, + const char *buf, size_t count) +{ + ssize_t status = 0; + uint8_t data; + + status = kstrtou8(buf, 0, &data); + if (status == 0) { + cpld_testee_offset[1] = data; + status = count; + } + + return status; +} +struct device_attribute dev_attr_cpld2_testee_offset = + __ATTR(testee_offset, 0600, cpld2_testee_offset_show, cpld2_testee_offset_store); + +static ssize_t cpld2_testee_value_show(struct device *dev, struct device_attribute *attr, + char *buf) +{ + uint8_t data = 0; + int err; + + mutex_lock(&cpld_data->lock); + data = readb(cpld_data->cpld2_base + cpld_testee_offset[1]); + mutex_unlock(&cpld_data->lock); + + return sprintf(buf, "0x%2.2x\n", data); +} +static ssize_t cpld2_testee_value_store(struct device *dev, struct device_attribute *attr, + const char *buf, size_t count) +{ + ssize_t status = 0; + uint8_t data; + + mutex_lock(&cpld_data->lock); + status = kstrtou8(buf, 0, &data); + if (status == 0) { + writeb(data, cpld_data->cpld2_base + cpld_testee_offset[1]); + status = count; + } + mutex_unlock(&cpld_data->lock); + + return status; +} +struct device_attribute dev_attr_cpld2_testee_value = + __ATTR(testee_value, 0600, cpld2_testee_value_show, cpld2_testee_value_store); + +static struct attribute *cpld2_attrs[] = { + &dev_attr_cpld2_ver.attr, + &dev_attr_sysrdy_rst_status.attr, + &dev_attr_all_xcvr_led_ctrl.attr, + &dev_attr_cpld2_ver_bmc_i2c.attr, + &dev_attr_cpld2_jed_rel.attr, + &dev_attr_cpld2_testee_offset.attr, + &dev_attr_cpld2_testee_value.attr, + NULL, +}; + +static struct attribute_group cpld2_attr_grp = { + .attrs = cpld2_attrs, +}; + +struct t7132s { + unsigned char __iomem *cfg_mmio_start; + resource_size_t cfg_mmio_len; + unsigned char __iomem *dev_mmio_start; + resource_size_t dev_mmio_len; + unsigned char __iomem *dev2_mmio_start; + resource_size_t dev2_mmio_len; +}; + +static struct t7132s t7132s_dev; +static struct platform_device *t7132s_platform_dev; +static struct kobject *cpld1 = NULL; +static struct kobject *cpld2 = NULL; +static struct device *sff_dev = NULL; + +static ssize_t qsfp_modirq_show(struct device *dev, + struct device_attribute *attr, char *buf) +{ + struct sff_device_data *dev_data = dev_get_drvdata(dev); + unsigned int portid = dev_data->portid; + u8 index = 0; + u16 reg = 0; + u8 value = 0; + + mutex_lock(&cpld_data->lock); + if ((portid % 2) != 0) { + QSFP_REG_READ (reg, QSFP_T_INT, + cpld_data->cpld_base); + index = (portid + 1) / 2; + } else { + QSFP_REG_READ (reg, QSFP_B_INT, + cpld_data->cpld_base); + index = portid / 2; + } + value = reg >> (index - 1) & 1; + mutex_unlock(&cpld_data->lock); + + return sprintf(buf, "%d\n", value); +} +DEVICE_ATTR_RO(qsfp_modirq); + +static ssize_t qsfp_modprs_show(struct device *dev, + struct device_attribute *attr, char *buf) +{ + struct sff_device_data *dev_data = dev_get_drvdata(dev); + unsigned int portid = dev_data->portid; + u8 index = 0; + u16 reg = 0; + u8 value = 0; + + mutex_lock(&cpld_data->lock); + if ((portid % 2) != 0) { + QSFP_REG_READ (reg, QSFP_T_MODPRS, + cpld_data->cpld_base); + index = (portid + 1) / 2; + } else { + QSFP_REG_READ (reg, QSFP_B_MODPRS, + cpld_data->cpld_base); + index = portid / 2; + } + value = reg >> (index - 1) & 1; + mutex_unlock(&cpld_data->lock); + + return sprintf(buf, "%d\n", value); +} +DEVICE_ATTR_RO(qsfp_modprs); + +static ssize_t qsfp_lpmode_show(struct device *dev, + struct device_attribute *attr, char *buf) +{ + struct sff_device_data *dev_data = dev_get_drvdata(dev); + unsigned int portid = dev_data->portid; + u8 index = 0; + u16 reg = 0; + u8 value = 0; + + mutex_lock(&cpld_data->lock); + if ((portid % 2) != 0) { + QSFP_REG_READ (reg, QSFP_T_LPMODE, + cpld_data->cpld_base); + index = (portid + 1) / 2; + } else { + QSFP_REG_READ (reg, QSFP_B_LPMODE, + cpld_data->cpld_base); + index = portid / 2; + } + value = reg >> (index - 1) & 1; + mutex_unlock(&cpld_data->lock); + + return sprintf(buf, "%d\n", value); +} +static ssize_t qsfp_lpmode_store(struct device *dev, + struct device_attribute *attr, const char *buf, + size_t count) +{ + ssize_t status; + struct sff_device_data *dev_data = dev_get_drvdata(dev); + unsigned int portid = dev_data->portid; + u8 value = 0; + u8 index = 0; + u16 reg = 0; + + mutex_lock(&cpld_data->lock); + status = kstrtou8(buf, 0, &value); + + if ((status == 0) && (value <= 1)) { + if ((portid % 2) != 0) { + QSFP_REG_READ (reg, QSFP_T_LPMODE, + cpld_data->cpld_base); + index = (portid + 1) / 2; + if (value == 1) { + reg |= (1 << (index - 1)); + } else { + reg &= ~(1 << (index - 1)); + } + QSFP_REG_WRITE (reg, QSFP_T_LPMODE, + cpld_data->cpld_base); + } else { + QSFP_REG_READ (reg, QSFP_B_LPMODE, + cpld_data->cpld_base); + index = portid / 2; + if (value == 1) { + reg |= (1 << (index - 1)); + } else { + reg &= ~(1 << (index - 1)); + } + QSFP_REG_WRITE (reg, QSFP_B_LPMODE, + cpld_data->cpld_base); + } + status = count; + } + + mutex_unlock(&cpld_data->lock); + + return status; +} +DEVICE_ATTR_RW(qsfp_lpmode); + +static ssize_t qsfp_reset_show(struct device *dev, + struct device_attribute *attr, char *buf) +{ + struct sff_device_data *dev_data = dev_get_drvdata(dev); + unsigned int portid = dev_data->portid; + u8 index = 0; + u16 reg = 0; + u8 value = 0; + + mutex_lock(&cpld_data->lock); + if ((portid % 2) != 0) { + QSFP_REG_READ (reg, QSFP_T_RESET, + cpld_data->cpld_base); + index = (portid + 1) / 2; + } else { + QSFP_REG_READ (reg, QSFP_B_RESET, + cpld_data->cpld_base); + index = portid / 2; + } + value = reg >> (index - 1) & 1; + mutex_unlock(&cpld_data->lock); + + return sprintf(buf, "%d\n", value); +} + +static ssize_t qsfp_reset_store(struct device *dev, + struct device_attribute *attr, const char *buf, + size_t count) +{ + ssize_t status; + struct sff_device_data *dev_data = dev_get_drvdata(dev); + unsigned int portid = dev_data->portid; + u8 value = 0; + u8 index = 0; + u16 reg = 0; + + mutex_lock(&cpld_data->lock); + status = kstrtou8(buf, 0, &value); + + if ((status == 0) && (value <= 1)) { + if ((portid % 2) != 0) { + QSFP_REG_READ (reg, QSFP_T_RESET, + cpld_data->cpld_base); + index = (portid + 1) / 2; + if (value == 1) { + reg |= (1 << (index - 1)); + } else { + reg &= ~(1 << (index - 1)); + } + QSFP_REG_WRITE (reg, QSFP_T_RESET, + cpld_data->cpld_base); + } else { + QSFP_REG_READ (reg, QSFP_B_RESET, + cpld_data->cpld_base); + index = portid / 2; + if (value == 1) { + reg |= (1 << (index - 1)); + } else { + reg &= ~(1 << (index - 1)); + } + QSFP_REG_WRITE (reg, QSFP_B_RESET, + cpld_data->cpld_base); + } + status = count; + } + mutex_unlock(&cpld_data->lock); + + return status; +} +DEVICE_ATTR_RW(qsfp_reset); + +static struct attribute *sff_attrs[] = { + &dev_attr_qsfp_modprs.attr, + &dev_attr_qsfp_modirq.attr, + &dev_attr_qsfp_lpmode.attr, + &dev_attr_qsfp_reset.attr, + NULL, +}; +static struct attribute_group sff_attr_grp = { + .attrs = sff_attrs, +}; +static const struct attribute_group *sff_attr_grps[] = { &sff_attr_grp, NULL }; + +#define SFP_MOD_MASK (1 << 5) +#define SFP_LOS_MASK (1 << 4) +#define SFP_TXFAULT_MASK (1 << 3) +#define SFP_RS0_MASK (1 << 2) +#define SFP_RS1_MASK (1 << 1) +#define SFP_TXDISABLE_MASK (1) +#define CPLD1_SFP_OFFSET 0x20 +#define SFP_REG_READ(_portid_, _data_, _base_) \ + do { \ + _data_ = readb(_base_ + CPLD1_SFP_OFFSET + _portid_ - 1); \ + } while (0); +#define SFP_REG_WRITE(_portid_, _data_, _base_) \ + do { \ + writeb(_data_, _base_ + CPLD1_SFP_OFFSET + _portid_ - 1); \ + } while (0); + +static ssize_t sfp_modabs_show(struct device *dev, + struct device_attribute *attr, char *buf) +{ + struct sff_device_data *dev_data = dev_get_drvdata(dev); + unsigned int portid = dev_data->portid; + u8 value = 0; + + mutex_lock(&cpld_data->lock); + SFP_REG_READ (portid, value, cpld_data->cpld_base); + value = ((value & SFP_MOD_MASK) != 0) ? 1 : 0; + mutex_unlock(&cpld_data->lock); + + return sprintf(buf, "%d\n", value); +} +DEVICE_ATTR_RO(sfp_modabs); + +static ssize_t sfp_txfault_show(struct device *dev, + struct device_attribute *attr, char *buf) +{ + struct sff_device_data *dev_data = dev_get_drvdata(dev); + unsigned int portid = dev_data->portid; + u8 value = 0; + + mutex_lock(&cpld_data->lock); + SFP_REG_READ (portid, value, cpld_data->cpld_base); + value = ((value & SFP_TXFAULT_MASK) != 0) ? 1 : 0; + mutex_unlock(&cpld_data->lock); + + return sprintf(buf, "%d\n", value); +} +DEVICE_ATTR_RO(sfp_txfault); + +static ssize_t sfp_rxlos_show(struct device *dev, + struct device_attribute *attr, char *buf) +{ + struct sff_device_data *dev_data = dev_get_drvdata(dev); + unsigned int portid = dev_data->portid; + u8 index = 0; + u16 reg = 0; + u8 value = 0; + + mutex_lock(&cpld_data->lock); + SFP_REG_READ (portid, value, cpld_data->cpld_base); + value = ((value & SFP_LOS_MASK) != 0) ? 1 : 0; + mutex_unlock(&cpld_data->lock); + + return sprintf(buf, "%d\n", value); +} +DEVICE_ATTR_RO(sfp_rxlos); + +static ssize_t sfp_txdisable_show(struct device *dev, + struct device_attribute *attr, char *buf) +{ + struct sff_device_data *dev_data = dev_get_drvdata(dev); + unsigned int portid = dev_data->portid; + u8 value = 0; + + mutex_lock(&cpld_data->lock); + SFP_REG_READ (portid, value, cpld_data->cpld_base); + value = ((value & SFP_TXDISABLE_MASK) != 0) ? 1 : 0; + mutex_unlock(&cpld_data->lock); + + return sprintf(buf, "%d\n", value); +} + +static ssize_t sfp_txdisable_store(struct device *dev, + struct device_attribute *attr, const char *buf, + size_t count) +{ + ssize_t status; + struct sff_device_data *dev_data = dev_get_drvdata(dev); + unsigned int portid = dev_data->portid; + u8 value = 0; + u8 index = 0; + u8 reg = 0; + + mutex_lock(&cpld_data->lock); + status = kstrtou8(buf, 0, &value); + + if ((status == 0) && value <= 1) { + SFP_REG_READ (portid, reg, cpld_data->cpld_base); + if (value == 1) { + reg |= 1; + } else { + reg &= ~1; + } + SFP_REG_WRITE (portid, reg, cpld_data->cpld_base); + status = count; + } else { + status = -EINVAL; + } + + mutex_unlock(&cpld_data->lock); + + return status; +} +DEVICE_ATTR_RW(sfp_txdisable); + +static struct attribute *sff_sfp_attrs[] = { + &dev_attr_sfp_txfault.attr, + &dev_attr_sfp_rxlos.attr, + &dev_attr_sfp_modabs.attr, + &dev_attr_sfp_txdisable.attr, + NULL, +}; +static struct attribute_group sff_sfp_attr_grp = { + .attrs = sff_sfp_attrs, +}; +static const struct attribute_group *sff_sfp_attr_grps[] = + { &sff_sfp_attr_grp, NULL }; + +static struct device *t7132s_sff_init(int portid) +{ + struct sff_device_data *new_data; + struct device *new_device; + char tmpStr[20]; + + new_data = kzalloc(sizeof(*new_data), GFP_KERNEL); + + new_data->portid = sff_device_tbl[portid].portid; + new_data->port_type = sff_device_tbl[portid].port_type; + new_data->parent_index = sff_device_tbl[portid].parent_index; + new_data->chan_id = sff_device_tbl[portid].chan_id; + + if (sff_device_tbl[portid].port_type == QSFP) { + sprintf(tmpStr, "QSFP%d", new_data->portid); + new_device = device_create_with_groups(cpld_class, sff_dev, MKDEV(0, 0), + new_data, sff_attr_grps, "%s", + tmpStr); + } else { + sprintf(tmpStr, "SFP%d", new_data->portid); + new_device = device_create_with_groups(cpld_class, sff_dev, MKDEV(0, 0), + new_data, sff_sfp_attr_grps, "%s", + tmpStr); + } + + return new_device; +} + +static void t7132s_sff_deinit(int portid) +{ + struct sff_device_data *dev_data; + + dev_data = dev_get_drvdata(cpld_data->sff_devices[portid]); + device_unregister(cpld_data->sff_devices[portid]); + put_device(cpld_data->sff_devices[portid]); + kfree(dev_data); + + return; +} + +static int t7132s_wdt_start(struct watchdog_device *wd_dev) +{ + uint8_t data = 0; + + mutex_lock(&cpld_data->lock); + data = readb(cpld_data->cpld_base + CPLD1_REG_DEV_STATE_2); + data |= 0x01; + writeb(data, cpld_data->cpld_base + CPLD1_REG_DEV_STATE_2); + mutex_unlock(&cpld_data->lock); + return 0; +} + +static int t7132s_wdt_stop(struct watchdog_device *wd_dev) +{ + uint8_t data = 0; + + mutex_lock(&cpld_data->lock); + data = readb(cpld_data->cpld_base + CPLD1_REG_DEV_STATE_2); + data &= 0xfe; + writeb(data, cpld_data->cpld_base + CPLD1_REG_DEV_STATE_2); + mutex_unlock(&cpld_data->lock); + return 0; +} + +static int t7132s_wdt_ping(struct watchdog_device *wd_dev) +{ + uint8_t data = 0; + + mutex_lock(&cpld_data->lock); + data = readb(cpld_data->cpld_base + CPLD1_REG_DEV_STATE_2); + /* disable */ + data &= 0xfe; + writeb(data, cpld_data->cpld_base + CPLD1_REG_DEV_STATE_2); + /* enable */ + data |= 0x01; + writeb(data, cpld_data->cpld_base + CPLD1_REG_DEV_STATE_2); + mutex_unlock(&cpld_data->lock); + return 0; +} + +static int t7132s_wdt_set_timeout(struct watchdog_device *wd_dev, unsigned int t) +{ + uint8_t data1 = 0; + uint8_t data2 = 0; + uint8_t data = 0; + int is_enabled = 0; + + if (t > 65535) + return -EINVAL; + + data1 = t & 0xff; + data2 = (t & 0xff00) >> 8; + mutex_lock(&cpld_data->lock); + /* save and stop */ + data = readb(cpld_data->cpld_base + CPLD1_REG_DEV_STATE_2); + is_enabled = data & 0x01; + if (is_enabled != 0) { + data &= 0xfe; + writeb(data, cpld_data->cpld_base + CPLD1_REG_DEV_STATE_2); + } + /* update max */ + writeb(data1, cpld_data->cpld_base + CPLD1_REG_WDT_MAX_COUNT_1); + writeb(data2, cpld_data->cpld_base + CPLD1_REG_WDT_MAX_COUNT_2); + /* restore */ + if (is_enabled != 0) { + data = readb(cpld_data->cpld_base + CPLD1_REG_DEV_STATE_2); + data |= is_enabled; + writeb(data, cpld_data->cpld_base + CPLD1_REG_DEV_STATE_2); + } + mutex_unlock(&cpld_data->lock); + + wd_dev->timeout = t; + return 0; +} + +static unsigned int t7132s_wdt_get_timeleft(struct watchdog_device *wd_dev) +{ + unsigned int time_left = 0; + uint8_t data_max1 = 0; + uint8_t data_max2 = 0; + long time_max = 0; + uint8_t data_now1 = 0; + uint8_t data_now2 = 0; + long time_now = 0; + + mutex_lock(&cpld_data->lock); + data_max1 = readb(cpld_data->cpld_base + CPLD1_REG_WDT_MAX_COUNT_1); + data_max2 = readb(cpld_data->cpld_base + CPLD1_REG_WDT_MAX_COUNT_2); + data_now1 = readb(cpld_data->cpld_base + CPLD1_REG_WDT_CUR_COUNT_1); + data_now2 = readb(cpld_data->cpld_base + CPLD1_REG_WDT_CUR_COUNT_2); + mutex_unlock(&cpld_data->lock); + + /* our watchdog is counting up */ + time_max = (data_max2 << 8) | data_max1; + time_now = (data_now2 << 8) | data_now1; + if (time_max >= time_now) { + time_left = time_max - time_now; + } + else + { + /* for debug */ + time_left = 0; + printk("T7132S: t7132s_wdt_get_timeleft time_max=0x%04lx time_now=0x%04lx\n", + time_max, time_now); + } + + return time_left; + +} + +static const struct watchdog_ops t7132s_wdt_ops = { + .owner = THIS_MODULE, + .start = t7132s_wdt_start, + .stop = t7132s_wdt_stop, + .ping = t7132s_wdt_ping, + .set_timeout = t7132s_wdt_set_timeout, + .get_timeleft = t7132s_wdt_get_timeleft, +}; + +static int __init __find_i2c_adap(struct device *dev, const void *data) +{ + const char *name = data; + static const char *prefix = "i2c-"; + struct i2c_adapter *adapter; + + if (strncmp(dev_name(dev), prefix, strlen(prefix)) != 0) { + return 0; + } + adapter = to_i2c_adapter(dev); + + return (strncmp(adapter->name, name, strlen(name)) == 0); +} + +static int t7132s_drv_probe(struct platform_device *pdev) +{ + int ret = 0; + int port_count = 0; + struct sff_device_data *sff_data = NULL; + const char *name = NULL; + struct device *dev = NULL; + struct i2c_adapter *adapter = NULL; + struct i2c_board_info *entry = NULL; + struct i2c_client *client = NULL; + struct i2c_mux_core *muxc = NULL; + int index = 0; + int parent_idx = 0; + int max_index = sizeof(i2c_topo) / sizeof(struct i2c_topo_node); + int adapter_id = 0; + int chan_id = 0; + + cpld_class = class_create(THIS_MODULE, CLASS_NAME); + ret = PTR_ERR(cpld_class); + + cpld_data = devm_kzalloc(&pdev->dev, sizeof(struct t7132s_cpld), + GFP_KERNEL); + mutex_init(&cpld_data->lock); + cpld_data->cpld_base = t7132s_dev.dev_mmio_start; + cpld1 = kobject_create_and_add("CPLD1", &pdev->dev.kobj); + ret = sysfs_create_group(cpld1, &cpld1_attr_grp); + cpld_data->cpld2_base = t7132s_dev.dev2_mmio_start; + cpld2 = kobject_create_and_add("CPLD2", &pdev->dev.kobj); + ret = sysfs_create_group(cpld2, &cpld2_attr_grp); + + sff_dev = device_create(cpld_class, NULL, MKDEV(0, 0), NULL, "%s", + "sff_device"); + ret = sysfs_create_link(&pdev->dev.kobj, &sff_dev->kobj, "SFF"); + + /* Setup i2c MUX devices */ + for (index = 0; index < max_index; index++) { + if (i2c_topo[index].parent_index == -1) { + name = bms_i2c_adapter_names[i2c_topo[index] + .adapter_type]; + dev = bus_find_device(&i2c_bus_type, NULL, (void *)name, + __find_i2c_adap); + adapter = to_i2c_adapter(dev); + if (adapter != NULL) { + i2c_topo[index].client = i2c_new_client_device( + adapter, &i2c_topo[index].entry); + msleep(500); + } + } else if (i2c_topo[index].parent_index != -1) { + parent_idx = i2c_topo[index].parent_index; + if (i2c_topo[parent_idx].client != NULL) { + client = i2c_topo[parent_idx].client; + muxc = i2c_get_clientdata(client); + if (muxc != NULL) { + chan_id = i2c_topo[index].chan_id; + adapter_id = muxc->adapter[chan_id]->nr; + adapter = i2c_get_adapter(adapter_id); + if (adapter != NULL) { + i2c_topo[index] + .client = i2c_new_client_device( + adapter, + &i2c_topo[index].entry); + i2c_put_adapter(adapter); + msleep(100); + } + } + } + } + dev = NULL; + adapter = NULL; + } + + for (port_count = 0; port_count < SFF_PORT_TOTAL; port_count++) { + cpld_data->sff_devices[port_count] = + t7132s_sff_init(port_count); + sff_data = dev_get_drvdata(cpld_data->sff_devices[port_count]); + parent_idx = sff_data->parent_index; + chan_id = sff_data->chan_id; + muxc = i2c_get_clientdata(i2c_topo[parent_idx].client); + if (muxc != NULL) { + adapter_id = muxc->adapter[chan_id]->nr; + adapter = i2c_get_adapter(adapter_id); + } + if (adapter == NULL) + continue; + if (sff_data->port_type == QSFP) { + /* Initiate optoe1 device */ + cpld_data->sff_i2c_clients[port_count] = + i2c_new_client_device(adapter, &sff_eeprom_info[0]); + } else { + /* Initiate optoe2 device */ + cpld_data->sff_i2c_clients[port_count] = + i2c_new_client_device(adapter, &sff_eeprom_info[1]); + } + i2c_put_adapter(adapter); + sff_data = NULL; + adapter = NULL; + /* Create sysfs link */ + sysfs_create_link( + &cpld_data->sff_devices[port_count]->kobj, + &cpld_data->sff_i2c_clients[port_count]->dev.kobj, + "i2c"); + } + + /* watchdog */ + pwddev = devm_kzalloc(&pdev->dev, sizeof(*pwddev), GFP_KERNEL); + if (pwddev) { + pwddev->info = &ident, + pwddev->ops = &t7132s_wdt_ops, + pwddev->bootstatus = 0; + pwddev->timeout = WATCHDOG_TIMEOUT; + pwddev->parent = &pdev->dev; + pwddev->min_timeout = 1; + pwddev->max_timeout = 65535; + //pwddev->max_hw_heartbeat_ms = 65535 * 1000; + + ret = devm_watchdog_register_device(&pdev->dev, pwddev); + if (ret != 0) { + printk("T7132S: cannot register watchdog device (err=%d)\n", ret); + } + else { + t7132s_wdt_stop(pwddev); + t7132s_wdt_set_timeout(pwddev, WATCHDOG_TIMEOUT); + printk("T7132S: watchdog initialized. heartbeat=%d sec (nowayout=%d)\n", + pwddev->timeout, 0); + } + } + else { + printk("T7132S: devm_kzalloc fail for watchdog device\n"); + } + + return 0; +} + +static int t7132s_drv_remove(struct platform_device *pdev) +{ + int ret = 0; + int port_count = 0; + struct sff_device_data *sff_data = NULL; + const char *name = NULL; + struct device *dev = NULL; + struct i2c_adapter *adapter; + struct i2c_board_info *entry; + int index = 0; + int max_index = sizeof(i2c_topo) / sizeof(struct i2c_topo_node); + + for (port_count = 0; port_count < SFF_PORT_TOTAL; port_count++) { + sysfs_remove_link(&cpld_data->sff_devices[port_count]->kobj, + "i2c"); + if (cpld_data->sff_i2c_clients[port_count] != NULL) { + i2c_unregister_device( + cpld_data->sff_i2c_clients[port_count]); + } + } + + for (port_count = 0; port_count < SFF_PORT_TOTAL; port_count++) { + t7132s_sff_deinit(port_count); + } + + for (index = max_index - 1; index >= 0; index--) { + if (i2c_topo[index].client != NULL) { + i2c_unregister_device(i2c_topo[index].client); + } + } + + sysfs_remove_link(&pdev->dev.kobj, "SFF"); + device_destroy(cpld_class, MKDEV(0, 0)); + sysfs_remove_group(cpld1, &cpld1_attr_grp); + class_destroy(cpld_class); // remove the device class + cpld_class = NULL; + devm_kfree(&pdev->dev, cpld_data); + devm_kfree(&pdev->dev, pwddev); + + return 0; +} + +static struct platform_driver t7132s_drv = { + .probe = t7132s_drv_probe, + .remove = __exit_p(t7132s_drv_remove), + .driver = + { + .name = DRIVER_NAME, + .owner = THIS_MODULE, + }, +}; + +static void t7132s_remove(struct pci_dev *dev) +{ + platform_device_unregister(t7132s_platform_dev); + platform_driver_unregister(&t7132s_drv); + iounmap(t7132s_dev.cfg_mmio_start); + iounmap(t7132s_dev.dev_mmio_start); + iounmap(t7132s_dev.dev2_mmio_start); + + pci_disable_device(dev); +} + +static int t7132s_probe(struct pci_dev *dev, const struct pci_device_id *ent) +{ + int retval, ret; + unsigned long base; + resource_size_t len; + unsigned long val; + char *ptr = NULL; + + retval = pci_enable_device(dev); + pci_set_master(dev); + + len = pci_resource_len(dev, 5); + base = pci_resource_start(dev, 5); + t7132s_dev.cfg_mmio_start = ioremap(base, len); + t7132s_dev.cfg_mmio_len = len; + + len = pci_resource_len(dev, 0); + base = pci_resource_start(dev, 0); + t7132s_dev.dev_mmio_start = ioremap(base, len); + t7132s_dev.dev_mmio_len = len; + + len = pci_resource_len(dev, 1); + base = pci_resource_start(dev, 1); + t7132s_dev.dev2_mmio_start = ioremap(base, len); + t7132s_dev.dev2_mmio_len = len; + + /* Localbus bridge reset sequence */ + val = readl(t7132s_dev.cfg_mmio_start + REG_LIEMR); + printk("LIEMR = 0x%x", val); + writeb(val | LIEMR_SRST | LIEMR_LRST, + t7132s_dev.cfg_mmio_start + REG_LIEMR); + val = readl(t7132s_dev.cfg_mmio_start + REG_LIEMR); + printk("LIEMR(after hw reset) = 0x%x", val); + + /* Localbus init sequence */ + val = LIEMR_RDYPOL | LIEMR_ALEPOL | LIEMR_SYNCBUS | LIEMR_MULTBUS | + LIEMR_DMA0EN | LIEMR_DMA1EN | LIEMR_L0EINTEN | LIEMR_L0RTOIEN | + LIEMR_L1EINTEN | LIEMR_L1RTOIEN | LIEMR_D0DIEN | LIEMR_D0AIEN | + LIEMR_D1DIEN | LIEMR_D1AIEN; + printk("LIEMR(new) = 0x%x", val); + writel(val, t7132s_dev.cfg_mmio_start + REG_LIEMR); + val = readl(t7132s_dev.cfg_mmio_start + REG_LIEMR); + printk("LIEMR(modified) = 0x%x", val); + + val = readl(t7132s_dev.cfg_mmio_start + REG_LAS0CFGR); + val &= ~LASCFGR_BW16; + writel(val, t7132s_dev.cfg_mmio_start + REG_LAS0CFGR); + val = readl(t7132s_dev.cfg_mmio_start + REG_LAS0CFGR); /* flush */ + + val = readl(t7132s_dev.cfg_mmio_start + REG_LAS1CFGR); + val &= ~LASCFGR_BW16; + writel(val, t7132s_dev.cfg_mmio_start + REG_LAS1CFGR); + val = readl(t7132s_dev.cfg_mmio_start + REG_LAS1CFGR); /* flush */ + + val = readl(t7132s_dev.cfg_mmio_start + REG_LACKSR); + printk("LACKSR = 0x%x", val); + val &= ~LACKSR_ALERA; + val |= LACKSR_CLKOEN; + val = 0x2405; + writel(val, t7132s_dev.cfg_mmio_start + REG_LACKSR); + val = readl(t7132s_dev.cfg_mmio_start + REG_LACKSR); + printk("LACKSR(modified) = 0x%x", val); + + /* Read Switch ID from offset 0x1 */ + ptr = (t7132s_dev.dev_mmio_start + CPLD1_REG_SW_ID); + val = readb(t7132s_dev.dev_mmio_start + CPLD1_REG_SW_ID); + printk("Switch ID : 0x%x", val); + + platform_driver_register(&t7132s_drv); + t7132s_platform_dev = + platform_device_register_simple(DRIVER_NAME, -1, NULL, 0); + + return 0; +} + +static int t7132s_suspend(struct pci_dev *dev, pm_message_t state) +{ + return 0; +}; + +static int t7132s_resume(struct pci_dev *dev) +{ + return 0; +}; + +static struct pci_device_id t7132s_pci_tbl[] = { + { 0x125B, 0x9110, 0xa000, 0x7000, 0, 0, 0 }, + { 0x125B, 0x9100, 0xa000, 0x7000, 0, 0, 0 }, + { + 0, + }, +}; + +static struct pci_driver t7132s_pci_driver = { + .name = "t7132s", + .probe = t7132s_probe, + .remove = t7132s_remove, + .id_table = t7132s_pci_tbl, + .suspend = t7132s_suspend, + .resume = t7132s_resume, +}; + +static int __init t7132s_init(void) +{ + int ret; + + memset(&t7132s_dev, 0, sizeof(struct t7132s)); + ret = pci_register_driver(&t7132s_pci_driver); + + return ret; +} + +static void __exit t7132s_exit(void) +{ + pci_unregister_driver(&t7132s_pci_driver); +} + +module_init(t7132s_init); +module_exit(t7132s_exit); + +MODULE_DEVICE_TABLE(pci, t7132s_pci_tbl); +MODULE_DESCRIPTION("SuperMicro T7132S CPLD Module"); +MODULE_SUPPORTED_DEVICE("T7132S"); +MODULE_LICENSE("GPL"); diff --git a/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/scripts/health_checker_thermal.py b/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/scripts/health_checker_thermal.py new file mode 100755 index 0000000000..6f1ee13784 --- /dev/null +++ b/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/scripts/health_checker_thermal.py @@ -0,0 +1,50 @@ +#!/usr/bin/python3 + +''' +This script is for healthd user_defined_checkers. +''' + +from swsscommon.swsscommon import SonicV2Connector +from natsort import natsorted + +TEMPER_TABLE_NAME = 'TEMPERATURE_INFO' +TEMPER_FIELD_NAME = 'temperature' +TIMESTAMP_FIELD_NAME = 'timestamp' +HIGH_THRESH_FIELD_NAME = 'high_threshold' +LOW_THRESH_FIELD_NAME = 'low_threshold' +CRIT_HIGH_THRESH_FIELD_NAME = 'critical_high_threshold' +CRIT_LOW_THRESH_FIELD_NAME = 'critical_low_threshold' +WARNING_STATUS_FIELD_NAME = 'warning_status' + +class TemperCheck(object): + def __init__(self): + self.db = SonicV2Connector(host="127.0.0.1") + self.db.connect(self.db.STATE_DB) + + def show(self): + keys = self.db.keys(self.db.STATE_DB, TEMPER_TABLE_NAME + '*') + if not keys: + #print('Thermal Not detected\n') + return + + print("Thermal") + for key in natsorted(keys): + key_list = key.split('|') + if len(key_list) != 2: # error data in DB, log it and ignore + #print('Warn: Invalid key in table {}: {}'.format(TEMPER_TABLE_NAME, key)) + continue + + name = key_list[1] + data_dict = self.db.get_all(self.db.STATE_DB, key) + if data_dict[WARNING_STATUS_FIELD_NAME] == 'False': + print("{}:OK".format(name)) + else: + temperature = data_dict[TEMPER_FIELD_NAME] + high_threshold = data_dict[HIGH_THRESH_FIELD_NAME] + low_threshold = data_dict[LOW_THRESH_FIELD_NAME] + print("{}:{} status is warning about temperature {} (threshold high {} low {})". + format(name, name, temperature, high_threshold, low_threshold)) + +if __name__ == "__main__": + temperCheck = TemperCheck() + temperCheck.show() diff --git a/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/scripts/platform.sh b/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/scripts/platform.sh new file mode 100755 index 0000000000..91c7249b44 --- /dev/null +++ b/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/scripts/platform.sh @@ -0,0 +1,102 @@ +#!/bin/bash + +i2c_config() { + local count=0 + local MAX_BUS_RETRY=20 + local MAX_I2C_OP_RETRY=10 + + i2c_bus_op=`echo "$@" | cut -d'>' -f 2` + i2c_bus=$(dirname $i2c_bus_op) + + # check if bus exists + while [[ "$count" -lt "$MAX_BUS_RETRY" ]]; do + [[ -e $i2c_bus ]] && break || sleep .1 + count=$((count+1)) + done + + if [[ "$count" -eq "$MAX_BUS_RETRY" ]]; then + echo "dell_i2c_utils : ERROR: $@ : i2c bus not created" + return + fi + + # perform the add/delete + count=0 + while [[ "$count" -lt "$MAX_I2C_OP_RETRY" ]]; do + eval "$@" > /dev/null 2>&1 + [[ $? == 0 ]] && break || sleep .2 + count=$((count+1)) + done + + if [[ "$count" -eq "$MAX_I2C_OP_RETRY" ]]; then + echo "dell_i2c_utils : ERROR: $@ : i2c operation failed" + return + fi +} + +# Attach/Detach syseeprom on CPU board +sys_eeprom() { + case $1 in + "new_device") i2c_config "echo 24c02 0x53 > /sys/bus/i2c/devices/i2c-0/$1" + ;; + "delete_device") i2c_config "echo 0x53 > /sys/bus/i2c/devices/i2c-0/$1" + ;; + *) echo "platform: sys_eeprom : invalid command !" + ;; + esac +} + +install_python_api_package() { + device="/usr/share/sonic/device" + platform=$(/usr/local/bin/sonic-cfggen -H -v DEVICE_METADATA.localhost.platform) + + rv=$(pip3 install $device/$platform/sonic_platform-1.0-py3-none-any.whl) +} + +remove_python_api_package() { + rv=$(pip3 show sonic-platform > /dev/null 2>/dev/null) + if [ $? -eq 0 ]; then + rv=$(pip3 uninstall -y sonic-platform > /dev/null 2>/dev/null) + fi +} +update_share_password() { + echo "Update shared password !!!" + SONIC_VERSION=$(cat /etc/sonic/sonic_version.yml | grep "build_version" | sed -e "s/build_version: //g;s/'//g") + image_dir=$(cat /proc/cmdline | sed -e 's/.*loop=\(\S*\)\/.*/\1/') + if [ -f /host/reboot-cause/platform/last_boot_image ]; then + last_image_ver=$(cat /host/reboot-cause/platform/last_boot_image) + else + last_image_ver="" + fi + echo "last_image_ver=${last_image_ver}" + + find /host -name "*image-*" | sed -e 's/\/host\/image-//' | while read var ; do + #echo "var=${var} image_dir=${image_dir}" + if [ "image-${var}" != "$image_dir" ] && [ "$last_image_ver" != "${SONIC_VERSION}" ]; then + cp /host/image-${var}/rw/etc/shadow /host/${image_dir}/rw/etc/shadow + cp /host/image-${var}/rw/etc/passwd /host/${image_dir}/rw/etc/passwd + cp /host/image-${var}/rw/etc/gshadow /host/${image_dir}/rw/etc/gshadow + cp /host/image-${var}/rw/etc/group /host/${image_dir}/rw/etc/group + fi + done + + if [ -d /host/reboot-cause/platform ]; then + echo "${SONIC_VERSION}" | sudo tee /host/reboot-cause/platform/last_boot_image > /dev/null + fi +} + + +if [ "$1" == "init" ]; then + echo "Initializing hardware components ..." + depmod -a + sys_eeprom "new_device" + modprobe t7132s + install_python_api_package + update_share_password +elif [ "$1" == "deinit" ]; then + echo "De-initializing hardware components ..." + modprobe -r t7132s + sys_eeprom "delete_device" + remove_python_api_package +else + echo "Invalid options !" +fi diff --git a/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/scripts/sysledctl.py b/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/scripts/sysledctl.py new file mode 100755 index 0000000000..4493ee5502 --- /dev/null +++ b/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/scripts/sysledctl.py @@ -0,0 +1,53 @@ +#!/usr/bin/python3 +import sys +import subprocess +import re +import sonic_platform.platform + +def systemctl(): + log_path = sys.argv[0] + ".log" + with open(log_path, 'w') as f: + out = subprocess.run(['systemctl', 'list-jobs'], capture_output=True, text=True).stdout + f.write(out) + chassis = sonic_platform.platform.Platform().get_chassis() + + x = re.search("reboot.target[ ]+start", out) + if x: + f.write("starting reboot\n") + chassis.set_status_led('green_blink') + + x = re.search("kexec.target[ ]+start", out) + if x: + f.write("starting kexec\n") + chassis.set_status_led('green_blink') + + x = re.search("halt.target[ ]+start", out) + if x: + f.write("starting halt\n") + chassis.set_status_led('red') + + x = re.search("poweroff.target[ ]+start", out) + if x: + f.write("starting poweroff\n") + chassis.set_status_led('off') + chassis.set_cpld2_s3(1) + + f.write("done\n") + +def reboot(): + log_path = sys.argv[0] + ".log" + with open(log_path, 'w') as f: + f.write("fast/warm reboot\n") + chassis = sonic_platform.platform.Platform().get_chassis() + chassis.set_status_led('green_blink') + f.write("done\n") + +def main(): + if len(sys.argv)>=2 and sys.argv[1]=='start': + systemctl() + if len(sys.argv)>=2 and sys.argv[1]=='reboot': + reboot() + + +if __name__ == '__main__': + main() diff --git a/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/scripts/test_cpld.py b/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/scripts/test_cpld.py new file mode 100755 index 0000000000..69e0f8302a --- /dev/null +++ b/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/scripts/test_cpld.py @@ -0,0 +1,209 @@ +import pytest + +CPLD_INFO_PATH='/sys/devices/platform/switchboard/CPLD{}' + +@pytest.mark.parametrize( + "cpld, offset, default, valid_mask, writeable_mask, test_mask", + [ + pytest.param( 1, 0x00, 0x00, 0x00, 0x00, 0x00, id="CPLD1 0x00 Reserved"), + pytest.param( 1, 0x01, 0x00, 0x1f, 0x00, 0x00, id="CPLD1 0x01 Switch model ID"), + pytest.param( 1, 0x02, 0x10, 0xff, 0x00, 0x00, id="CPLD1 0x02 HW/CPLD version"), + pytest.param( 1, 0x03, 0xff, 0xff, 0x00, 0x00, id="CPLD1 0x03 Power sequence module status"), + pytest.param( 1, 0x04, 0x00, 0xff, 0x00, 0x00, id="CPLD1 0x04 Voltage Regulator Module ALERT/ Thermal"), + pytest.param( 1, 0x05, 0x7f, 0xff, 0x98, 0x18, id="CPLD1 0x05 Enable/ Reset misc. devices"), + pytest.param( 1, 0x06, 0xfe, 0xff, 0xff, 0x01, id="CPLD1 0x06 Enable/ Reset misc. devices"), + pytest.param( 1, 0x07, 0x0a, 0x0f, 0x0a, 0x0a, id="CPLD1 0x07 FACTORY_BTN event log and clear"), + pytest.param( 1, 0x09, 0xe0, 0xe0, 0xe0, 0xe0, id="CPLD1 0x09 System reset records"), + pytest.param( 1, 0x0B, 0xff, 0xff, 0x3f, 0x00, id="CPLD1 0x0B PCA9548 I2C bus switch RSTn"), + pytest.param( 1, 0x0C, 0x07, 0x07, 0x07, 0x07, id="CPLD1 0x0C Transceiver Power Enable"), + pytest.param( 1, 0x0D, 0xff, 0xff, 0xff, 0xff, id="CPLD1 0x0D Transceiver Power Enable"), + pytest.param( 1, 0x0E, 0x07, 0x07, 0x00, 0x00, id="CPLD1 0x0E Transceiver Power Good"), + pytest.param( 1, 0x0F, 0xff, 0xff, 0x00, 0x00, id="CPLD1 0x0F Transceiver Power Good"), + pytest.param( 1, 0x10, 0xff, 0xff, 0xff, 0xff, id="CPLD1 0x10 QSFP-DD Reset signals for Port QT16 to QT9"), + pytest.param( 1, 0x11, 0xff, 0xff, 0xff, 0xff, id="CPLD1 0x11 QSFP-DD Reset signals for Port QT8 to QT1"), + pytest.param( 1, 0x12, 0x00, 0xff, 0xff, 0xff, id="CPLD1 0x12 QSFP-DD LPMODE signals for Port QT16 to QT9"), + pytest.param( 1, 0x13, 0x00, 0xff, 0xff, 0xff, id="CPLD1 0x13 QSFP-DD LPMODE signals for Port QT8 to QT1"), + pytest.param( 1, 0x14, 0x00, 0x00, 0x00, 0x00, id="CPLD1 0x14 QSFP-DD INT signals from Port QT16 to QT9"), + pytest.param( 1, 0x15, 0x00, 0x00, 0x00, 0x00, id="CPLD1 0x15 QSFP-DD INT signals from Port QT8 to QT1"), + pytest.param( 1, 0x16, 0x00, 0x00, 0x00, 0x00, id="CPLD1 0x16 QSFP-DD MODPRS signals from Port QT16 to QT9"), + pytest.param( 1, 0x17, 0x00, 0x00, 0x00, 0x00, id="CPLD1 0x17 QSFP-DD MODPRS signals from Port QT8 to QT1"), + pytest.param( 1, 0x18, 0xff, 0xff, 0xff, 0xff, id="CPLD1 0x18 QSFP-DD Reset signals for Port QB16 to QB9"), + pytest.param( 1, 0x19, 0xff, 0xff, 0xff, 0xff, id="CPLD1 0x19 QSFP-DD Reset signals for Port QB8 to QB1"), + pytest.param( 1, 0x1A, 0x00, 0x00, 0xff, 0xff, id="CPLD1 0x1A QSFP-DD LPMODE signals for Port QB16 to QB9"), + pytest.param( 1, 0x1B, 0x00, 0x00, 0xff, 0xff, id="CPLD1 0x1B QSFP-DD LPMODE signals for Port QB8 to QB1"), + pytest.param( 1, 0x1C, 0x00, 0x00, 0x00, 0x00, id="CPLD1 0x1C QSFP-DD INT signals from Port QB16 to QB9"), + pytest.param( 1, 0x1D, 0x00, 0x00, 0x00, 0x00, id="CPLD1 0x1D QSFP-DD INT signals from Port QB8 to QB1"), + pytest.param( 1, 0x1E, 0x00, 0x00, 0x00, 0x00, id="CPLD1 0x1E QSFP-DD MODPRS signals from Port QB16 to QB9"), + pytest.param( 1, 0x1F, 0x00, 0x00, 0x00, 0x00, id="CPLD1 0x1F QSFP-DD MODPRS signals from Port QB8 to QB1"), + pytest.param( 1, 0x20, 0x06, 0x00, 0x07, 0x07, id="CPLD1 0x20 Top side SFPP"), + pytest.param( 1, 0x21, 0x06, 0x00, 0x07, 0x07, id="CPLD1 0x21 Bottom side SFPP"), + pytest.param( 1, 0x22, 0x00, 0x00, 0xff, 0xff, id="CPLD1 0x22 Watch Dog Maximum count setting, Least significant 8 bits"), + pytest.param( 1, 0x23, 0x00, 0x00, 0xff, 0xff, id="CPLD1 0x23 Watch Dog Maximum count setting, Most significant 8 bits"), + pytest.param( 1, 0x24, 0x00, 0x00, 0x00, 0x00, id="CPLD1 0x24 Watch Dog Current count value, Least significant 8 bits"), + pytest.param( 1, 0x25, 0x00, 0x00, 0x00, 0x00, id="CPLD1 0x25 Watch Dog Current count value, Most significant 8 bits"), + pytest.param( 1, 0xF0, 0x00, 0xff, 0x00, 0x00, id="CPLD1 0xF0 Version as BMC I2C Registers #0"), + pytest.param( 1, 0xF1, 0x48, 0xff, 0x00, 0x00, id="CPLD1 0xF1 Version as BMC I2C Registers #1"), + pytest.param( 1, 0xF2, 0x00, 0xff, 0x00, 0x00, id="CPLD1 0xF2 Version as BMC I2C Registers #2"), + pytest.param( 1, 0xF3, 0x02, 0xff, 0x00, 0x00, id="CPLD1 0xF3 Version as BMC I2C Registers #3"), + pytest.param( 1, 0xFE, 0x10, 0xff, 0x00, 0x00, id="CPLD1 0xFE CPLD JED Released Date Month"), + pytest.param( 1, 0xFF, 0x26, 0xff, 0x00, 0x00, id="CPLD1 0xFF CPLD JED Released Date Day"), + pytest.param( 2, 0x00, 0x00, 0x00, 0x00, 0x00, id="CPLD2 0x00 Reserved"), + pytest.param( 2, 0x01, 0x00, 0x00, 0x00, 0x00, id="CPLD2 0x01 Reserved"), + pytest.param( 2, 0x02, 0x00, 0x0f, 0x00, 0x00, id="CPLD2 0x02 CPLD2 FW version"), + pytest.param( 2, 0x03, 0x2c, 0x7f, 0x37, 0x33, id="CPLD2 0x03 System Ready/Reset Status and LED control"), + pytest.param( 2, 0x04, 0x00, 0xff, 0x1f, 0x1f, id="CPLD2 0x04 All transceiver LEDs control"), + pytest.param( 2, 0x05, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x05 SFPP LED manual control TSFPP"), + pytest.param( 2, 0x06, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x06 SFPP LED manual control BSFPP"), + pytest.param( 2, 0x07, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x07 QSFP-DD LED manual control QT1_Pn_G"), + pytest.param( 2, 0x08, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x08 QSFP-DD LED manual control QT1_Pn_Y"), + pytest.param( 2, 0x09, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x09 QSFP-DD LED manual control QB1_P1_G"), + pytest.param( 2, 0x0A, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x0A QSFP-DD LED manual control QB1_P1_Y"), + pytest.param( 2, 0x0B, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x0B QT2 Green 4 LEDs"), + pytest.param( 2, 0x0C, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x0C QT2 Yellow 4 LEDs"), + pytest.param( 2, 0x0D, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x0D QB2 Green 4 LEDs"), + pytest.param( 2, 0x0E, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x0E QB2Yellow 4 LEDs"), + pytest.param( 2, 0x0F, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x0F QT3 Green 4 LEDs"), + pytest.param( 2, 0x10, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x10 QT3 Yellow 4 LEDs"), + pytest.param( 2, 0x11, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x11 QB3 Green 4 LEDs"), + pytest.param( 2, 0x12, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x12 QB3Yellow 4 LEDs"), + pytest.param( 2, 0x13, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x13 QT4 Green 4 LEDs"), + pytest.param( 2, 0x14, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x14 QT4 Yellow 4 LEDs"), + pytest.param( 2, 0x15, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x15 QB4 Green 4 LEDs"), + pytest.param( 2, 0x16, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x16 QB4Yellow 4 LEDs"), + pytest.param( 2, 0x17, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x17 QT5 Green 4 LEDs"), + pytest.param( 2, 0x18, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x18 QT5 Yellow 4 LEDs"), + pytest.param( 2, 0x19, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x19 QB5 Green 4 LEDs"), + pytest.param( 2, 0x1A, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x1A QB5Yellow 4 LEDs"), + pytest.param( 2, 0x1B, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x1B QT6 Green 4 LEDs"), + pytest.param( 2, 0x1C, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x1C QT6 Yellow 4 LEDs"), + pytest.param( 2, 0x1D, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x1D QB6 Green 4 LEDs"), + pytest.param( 2, 0x1E, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x1E QB6 Yellow 4 LEDs"), + pytest.param( 2, 0x1F, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x1F QT7 Green 4 LEDs"), + pytest.param( 2, 0x20, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x20 QT7 Yellow 4 LEDs"), + pytest.param( 2, 0x21, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x21 QB7 Green 4 LEDs"), + pytest.param( 2, 0x22, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x22 QB7 Yellow 4 LEDs"), + pytest.param( 2, 0x23, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x23 QT8 Green 4 LEDs"), + pytest.param( 2, 0x24, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x24 QT8 Yellow 4 LEDs"), + pytest.param( 2, 0x25, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x25 QB8 Green 4 LEDs"), + pytest.param( 2, 0x26, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x26 QB8 Yellow 4 LEDs"), + pytest.param( 2, 0x27, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x27 QT9 Green 4 LEDs"), + pytest.param( 2, 0x28, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x28 QT9 Yellow 4 LEDs"), + pytest.param( 2, 0x29, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x29 QB9 Green 4 LEDs"), + pytest.param( 2, 0x2A, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x2A QB9 Yellow 4 LEDs"), + pytest.param( 2, 0x2B, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x2B QT10 Green 4 LEDs"), + pytest.param( 2, 0x2C, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x2C QT10 Yellow 4 LEDs"), + pytest.param( 2, 0x2D, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x2D QB10 Green 4 LEDs"), + pytest.param( 2, 0x2E, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x2E QB10 Yellow 4 LEDs"), + pytest.param( 2, 0x2F, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x2F QT11 Green 4 LEDs"), + pytest.param( 2, 0x30, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x30 QT11 Yellow 4 LEDs"), + pytest.param( 2, 0x31, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x31 QB11 Green 4 LEDs"), + pytest.param( 2, 0x32, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x32 QB11 Yellow 4 LEDs"), + pytest.param( 2, 0x33, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x33 QT12 Green 4 LEDs"), + pytest.param( 2, 0x34, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x34 QT12 Yellow 4 LEDs"), + pytest.param( 2, 0x35, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x35 QB12 Green 4 LEDs"), + pytest.param( 2, 0x36, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x36 QB12 Yellow 4 LEDs"), + pytest.param( 2, 0x37, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x37 QT13 Green 4 LEDs"), + pytest.param( 2, 0x38, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x38 QT13 Yellow 4 LEDs"), + pytest.param( 2, 0x39, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x39 QB13 Green 4 LEDs"), + pytest.param( 2, 0x3A, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x3A QB13 Yellow 4 LEDs"), + pytest.param( 2, 0x3B, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x3B QT14 Green 4 LEDs"), + pytest.param( 2, 0x3C, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x3C QT14 Yellow 4 LEDs"), + pytest.param( 2, 0x3D, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x3D QB14 Green 4 LEDs"), + pytest.param( 2, 0x3E, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x3E QB14 Yellow 4 LEDs"), + pytest.param( 2, 0x3F, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x3F QT15 Green 4 LEDs"), + pytest.param( 2, 0x40, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x40 QT15 Yellow 4 LEDs"), + pytest.param( 2, 0x41, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x41 QB15 Green 4 LEDs"), + pytest.param( 2, 0x42, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x42 QB15 Yellow 4 LEDs"), + pytest.param( 2, 0x43, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x43 QT16 Green 4 LEDs"), + pytest.param( 2, 0x44, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x44 QT16 Yellow 4 LEDs"), + pytest.param( 2, 0x45, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x45 QB16 Green 4 LEDs"), + pytest.param( 2, 0x46, 0x00, 0xff, 0xff, 0xff, id="CPLD2 0x46 QB16 Yellow 4 LEDs"), + pytest.param( 2, 0xF0, 0x00, 0xff, 0x00, 0x00, id="CPLD2 0xF0 Version as BMC I2C Registers #0"), + pytest.param( 2, 0xF1, 0x48, 0xff, 0x00, 0x00, id="CPLD2 0xF1 Version as BMC I2C Registers #1"), + pytest.param( 2, 0xF2, 0x20, 0xff, 0x00, 0x00, id="CPLD2 0xF2 Version as BMC I2C Registers #2"), + pytest.param( 2, 0xF3, 0x02, 0xff, 0x00, 0x00, id="CPLD2 0xF3 Version as BMC I2C Registers #3"), + pytest.param( 2, 0xFE, 0x10, 0xff, 0x00, 0x00, id="CPLD2 0xFE CPLD JED Released Date Month"), + pytest.param( 2, 0xFF, 0x27, 0xff, 0x00, 0x00, id="CPLD2 0xFF CPLD JED Released Date Day"), + ], +) +class TestClass: + def test_cpld_read_default(self, cpld, offset, default, valid_mask, writeable_mask, test_mask): + reg_offset = "/".join([CPLD_INFO_PATH.format(cpld), "testee_offset"]) + reg_value = "/".join([CPLD_INFO_PATH.format(cpld), "testee_value"]) + + # write offset + with open(reg_offset, "r+") as file_offset: + file_offset.write(hex(offset)) + + for i in range(2): + with open(reg_value, "r+") as file_value: + content = file_value.readline().strip() + content_value = int(content, 16) + assert hex(content_value & valid_mask) == hex(default & valid_mask) + + def test_cpld_read_stable(self, cpld, offset, default, valid_mask, writeable_mask, test_mask): + reg_offset = "/".join([CPLD_INFO_PATH.format(cpld), "testee_offset"]) + reg_value = "/".join([CPLD_INFO_PATH.format(cpld), "testee_value"]) + + # write offset + with open(reg_offset, "r+") as file_offset: + file_offset.write(hex(offset)) + + # read current value + with open(reg_value, "r+") as file_value: + content = file_value.readline().strip() + last_value = int(content, 16) + + for i in range(100): + with open(reg_value, "r+") as file_value: + content = file_value.readline().strip() + content_value = int(content, 16) + assert hex(content_value) == hex(last_value) + + def test_cpld_write_stable(self, cpld, offset, default, valid_mask, writeable_mask, test_mask): + reg_offset = "/".join([CPLD_INFO_PATH.format(cpld), "testee_offset"]) + reg_value = "/".join([CPLD_INFO_PATH.format(cpld), "testee_value"]) + + # write offset + with open(reg_offset, "r+") as file_offset: + file_offset.write(hex(offset)) + + # read and save current value + with open(reg_value, "r+") as file_value: + content = file_value.readline().strip() + last_value = int(content, 16) + + for i in range(100): + for j in range(8): + if (1< 0): + return True, change_dict + + if timeout: + now_ms = time.time() * 1000 + if (now_ms - start_ms >= timeout): + return True, change_dict + + ############################################################## + ######################## SFP methods ######################### + ############################################################## + + def get_num_sfps(self): + """ + Retrieves the number of sfps available on this chassis + Returns: + An integer, the number of sfps available on this chassis + """ + if not self.sfp_module_initialized: + self.__initialize_sfp() + + return len(self._sfp_list) + + def get_all_sfps(self): + """ + Retrieves all sfps available on this chassis + Returns: + A list of objects derived from SfpBase representing all sfps + available on this chassis + """ + if not self.sfp_module_initialized: + self.__initialize_sfp() + + return self._sfp_list + + def get_sfp(self, index): + """ + Retrieves sfp represented by (0-based) index + + Args: + index: An integer, the index (0-based) of the sfp to retrieve. + The index should be the sequence of a physical port in a chassis, + starting from 0. + For example, 0 for Ethernet0, 1 for Ethernet4 and so on. + + Returns: + An object dervied from SfpBase representing the specified sfp + """ + sfp = None + if not self.sfp_module_initialized: + self.__initialize_sfp() + + try: + # The index will start from 0 + sfp = self._sfp_list[index-1] + except IndexError: + sys.stderr.write("SFP index {} out of range (1-{})\n".format( + index, len(self._sfp_list))) + return sfp + + ############################################## + # System LED methods + ############################################## + + def set_status_led(self, color): + """ + Sets the state of the system LED + + Args: + color: A string representing the color with which to set the + system LED + + Returns: + bool: True if system LED state is set successfully, False if not + """ + if color not in self.supported_led_color: + return False + + reg_path = "/".join([CPLD2_INFO_PATH, "sysrdy_rst_state"]) + + # Read current status + try: + with open(reg_path, "r+") as reg_file: + content_str = reg_file.readline().rstrip() + reg_value = int(content_str, 16) + color_value = self.color_to_status_led_reg[color] + new_reg_value = reg_value & 0b11111100 | color_value + reg_file.seek(0) + reg_file.write(hex(new_reg_value)) + except IOError as e: + print("Error: unable to open file: %s" % str(e)) + return False + + # clear S3 and S5 if status led set 'green_blink' for booting + if color == 'green_blink': + if self.get_cpld2_s5() == 1: + self.set_cpld2_s5(0) #Clear S5 status + self.set_cpld2_s5(1) #Enable to record S5 status + if self.get_cpld2_s3() == 1: + self.set_cpld2_s3(0) #Clear S3 status + + return True + + def get_status_led(self): + """ + Gets the state of the system LED + + Returns: + A string, one of the valid LED color strings which could be vendor + specified. + """ + reg_path = "/".join([CPLD2_INFO_PATH, "sysrdy_rst_state"]) + + # Read status + try: + with open(reg_path) as reg_file: + content = reg_file.readline().rstrip() + except IOError as e: + print("Error: unable to open file: %s" % str(e)) + return False + + content_value = int(content, 16) + sysled_color_reg = content_value & 0b11 + return self.status_led_reg_to_color.get(sysled_color_reg, "Unknown " + content) + + def get_watchdog(self): + """ + Retreives hardware watchdog device on this chassis + + Returns: + An object derived from WatchdogBase representing the hardware + watchdog device + """ + if self._watchdog is None: + # Initialize watchdog + try: + self._watchdog = Watchdog() + except Exception as e: + self._watchdog = None + + return self._watchdog + + def set_cpld2_s3(self, s3): + """ + Sets the bit S3 in CPLD2 sysrdy_rst_state (offset 0x03) + + Args: + s3: integer 1 or 0 + + Returns: + bool: True if the bit is set successfully, False if not + """ + reg_path = "/".join([CPLD2_INFO_PATH, "sysrdy_rst_state"]) + + # Read current status + try: + with open(reg_path, "r+") as reg_file: + content_str = reg_file.readline().rstrip() + reg_value = int(content_str, 16) + bit_value = 0b10000 if s3!=0 else 0 + new_reg_value = reg_value & 0b11101111 | bit_value + reg_file.seek(0) + reg_file.write(hex(new_reg_value)) + except IOError as e: + print("Error: unable to open file: %s" % str(e)) + return False + + return True + + def get_cpld2_s3(self): + """ + Gets the bit S3 in CPLD2 sysrdy_rst_state (offset 0x03) + + Returns: + integer 1 or 0. + """ + reg_path = "/".join([CPLD2_INFO_PATH, "sysrdy_rst_state"]) + + # Read status + try: + with open(reg_path) as reg_file: + content = reg_file.readline().rstrip() + except IOError as e: + print("Error: unable to open file: %s" % str(e)) + return False + + content_value = int(content, 16) + bit_value = 1 if (content_value & 0b10000) != 0 else 0 + return bit_value + + def initizalize_system_led(self): + """ + called by system_health.py. do nothing here. + """ + return True + + def get_cpld2_s5(self): + """ + Gets the bit S5 in CPLD2 sysrdy_rst_state (offset 0x03) + + Returns: + integer 1 or 0. + """ + reg_path = "/".join([CPLD2_INFO_PATH, "sysrdy_rst_state"]) + + # Read status + try: + with open(reg_path) as reg_file: + content = reg_file.readline().rstrip() + except IOError as e: + print("Error: unable to open file: %s" % str(e)) + return False + + content_value = int(content, 16) + bit_value = 1 if (content_value & 0b1000000) != 0 else 0 + return bit_value + + def set_cpld2_s5(self, s5): + """ + Sets the bit S5 in CPLD2 sysrdy_rst_state (offset 0x03) + + Args: + s5: integer 1 or 0 + + Returns: + bool: True if the bit is set successfully, False if not + """ + reg_path = "/".join([CPLD2_INFO_PATH, "sysrdy_rst_state"]) + + # Read current status + try: + with open(reg_path, "r+") as reg_file: + content_str = reg_file.readline().rstrip() + reg_value = int(content_str, 16) + bit_value = 0b100000 if s5!=0 else 0 + new_reg_value = reg_value & 0b11011111 | bit_value + reg_file.seek(0) + reg_file.write(hex(new_reg_value)) + except IOError as e: + print("Error: unable to open file: %s" % str(e)) + return False + + return True + + def get_bmc_reboot_cause(self): + """ + Gets the reboot cause from BMC + """ + reboot_cause = -1 + status, raw_cause = self._api_helper.ipmi_raw( + IPMI_OEM_NETFN, IPMI_GET_REBOOT_CAUSE) + if status: + hx_cause_list = [] + if raw_cause == '': + return False + else: + hx_cause = int(raw_cause.split()[0], 16) + if hx_cause > 0: + self._api_helper.ipmi_raw(IPMI_OEM_NETFN, IPMI_CLEAR_REBOOT_CAUSE) #Clear BMC reboot cause + for i in range(0, NUM_BMC_REBOOT_CAUSE): + if ((hx_cause >> i) & 1): + hx_cause_list.append(i) + #Invalid case if multiple BMC reboot causes + if len(hx_cause_list) > 1: + sys.stderr.write("{} BMC reboot causes: {}\n".format( + len(hx_cause_list), f'0b{hx_cause:08b}')) + else: + reboot_cause = hx_cause_list[0] + else: + status = False + return status, reboot_cause + + def set_cpld1_wdt_rst(self, enable): + """ + Set bit 7 in CPLD1 sysrst_rec (offset 0x09) to clean bit 4. + + Args: + enable: 1: enable record + 0: clear + + Returns: + bool: True if the bit is set successfully, False if not + """ + reg_path = "/".join([CPLD1_INFO_PATH, "sysrst_rec"]) + + # Read current status + try: + with open(reg_path, "r+") as reg_file: + content_str = reg_file.readline().rstrip() + reg_value = int(content_str, 16) + bit_value = 0x80 if enable else 0 + new_reg_value = reg_value & 0x7f | bit_value + reg_file.seek(0) + reg_file.write(hex(new_reg_value)) + except IOError as e: + print("Error: unable to open file: %s" % str(e)) + return False + + return True + + def get_cpld1_wdt_rst(self): + """ + Get the bit 4 in CPLD1 sysrst_rec (offset 0x09). + + Returns: + integer 1 or 0. + """ + reg_path = "/".join([CPLD1_INFO_PATH, "sysrst_rec"]) + + # Read status + try: + with open(reg_path) as reg_file: + content = reg_file.readline().rstrip() + except IOError as e: + print("Error: unable to open file: %s" % str(e)) + return False + + content_value = int(content, 16) + bit_value = 1 if (content_value & 0x10) != 0 else 0 + return bit_value + + def get_cpld1_board_rev(self): + """ + Get the bit [5:3] from CPLD1 ver_bmc_i2c (offset 0xF0:0xF3). + + Returns: + String of board version. + """ + reg_path = "/".join([CPLD1_INFO_PATH, "ver_bmc_i2c"]) + + # Read status + try: + with open(reg_path) as reg_file: + content = reg_file.readline().rstrip() + except IOError as e: + print("Error: unable to open file: %s" % str(e)) + return 'N/A' + + content_value = int(content, 16) + # bit [5:3] offset 0xF1 + board_ver = (content_value >> 19) & 0x07 + str_dir = {0b000:'1.00', 0b001:'1.01', 0b010:'1.02'} + rev_str = str_dir.get(board_ver, 'Unknown({:#05b})'.format(board_ver)) + return rev_str diff --git a/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/component.py b/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/component.py new file mode 100644 index 0000000000..ee22ce843f --- /dev/null +++ b/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/component.py @@ -0,0 +1,106 @@ +############################################################################# +# SuperMicro SSE-T7132S +# +# Component contains an implementation of SONiC Platform Base API and +# provides the components firmware management function +# +############################################################################# + +try: + from sonic_platform_base.component_base import ComponentBase + from .helper import APIHelper +except ImportError as e: + raise ImportError(str(e) + "- required module not found") + +COMPONENT_LIST = [ + ("BIOS", "Basic Input/Output System"), + ("BMC", "Baseboard Management Controller"), + ("SWITCH_CPLD1", "Switch board CPLD1"), + ("SWITCH_CPLD2", "Switch board CPLD2") +] +SW_CPLD1_VER_PATH = "/sys/devices/platform/switchboard/CPLD1/ver_bmc_i2c" +SW_CPLD2_VER_PATH = "/sys/devices/platform/switchboard/CPLD2/ver_bmc_i2c" +CPLD_UPGRADE_OPT = 4 +BIOS_VER_PATH = "/sys/class/dmi/id/bios_version" +BIOS__UPGRADE_OPT = 2 +BMC_VER_CMD = "ipmitool mc info | grep 'Firmware Revision'" +IPMI_BMC_VER_NETFN = "0x6" +IPMI_BMC_VER_CMD = "0x1" +BMC_VER_MAJOR_OFFSET = 2 +BMC_VER_MINOR_OFFSET = 3 +BMC_VER_AUX_OFFSET = 11 +BMC_UPGRADE_OPT = 1 +CFUFLASH_FW_UPGRADE_CMD = "CFUFLASH -cd -d {} -mse 3 {}" +MEM_PCI_RESOURCE = "/sys/bus/pci/devices/0000:09:00.0/resource0" +FPGA_VER_MEM_OFFSET = 0 + + +class Component(ComponentBase): + """Platform-specific Component class""" + + DEVICE_TYPE = "component" + + def __init__(self, component_index): + ComponentBase.__init__(self) + self.index = component_index + self.name = self.get_name() + self._api_helper = APIHelper() + + def __get_bmc_ver(self): + bmc_ver = "Unknown" + status, raw_bmc_data = self._api_helper.ipmi_raw( + IPMI_BMC_VER_NETFN, IPMI_BMC_VER_CMD) + if status: + bmc_ver_data_list = raw_bmc_data.split() + bmc_ver = '{}.{}.{}'.format(bmc_ver_data_list[BMC_VER_MAJOR_OFFSET], + bmc_ver_data_list[BMC_VER_MINOR_OFFSET], + bmc_ver_data_list[BMC_VER_AUX_OFFSET]) + return bmc_ver + + def __get_cpld_ver(self,path): + cpld_data = self._api_helper.read_txt_file(path) + cpld_ver = cpld_data[-2:] + + return cpld_ver + + def get_name(self): + """ + Retrieves the name of the component + Returns: + A string containing the name of the component + """ + return COMPONENT_LIST[self.index][0] + + def get_description(self): + """ + Retrieves the description of the component + Returns: + A string containing the description of the component + """ + return COMPONENT_LIST[self.index][1] + + def get_firmware_version(self): + """ + Retrieves the firmware version of module + Returns: + string: The firmware versions of the module + """ + fw_version = { + "BIOS": self._api_helper.read_txt_file(BIOS_VER_PATH), + "BMC": self.__get_bmc_ver(), + "SWITCH_CPLD1": self.__get_cpld_ver(SW_CPLD1_VER_PATH), + "SWITCH_CPLD2": self.__get_cpld_ver(SW_CPLD2_VER_PATH), + }.get(self.name, "Unknown") + + return fw_version + + def install_firmware(self, image_path): + """ + Install firmware to module + Args: + image_path: A string, path to firmware image + Returns: + A boolean, True if install successfully, False if not + """ + """Not Implement""" + return False diff --git a/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/eeprom.py b/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/eeprom.py new file mode 100644 index 0000000000..bd73d93ad3 --- /dev/null +++ b/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/eeprom.py @@ -0,0 +1,122 @@ +############################################################################# +# SuperMicro SSE-T7132S +# +# 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 os + import sys + import re + + if sys.version_info.major == 3: + from io import StringIO + else: + from cStringIO import StringIO + + from sonic_platform_base.sonic_eeprom import eeprom_dts + from sonic_platform_base.sonic_eeprom import eeprom_tlvinfo +except ImportError as e: + raise ImportError(str(e) + "- required module not found") + +CACHE_ROOT = '/var/cache/sonic/decode-syseeprom' +CACHE_FILE = 'syseeprom_cache' +TLV_EEPROM_I2C_BUS = 0 +TLV_EEPROM_I2C_ADDR = 53 + + +class Tlv(eeprom_tlvinfo.TlvInfoDecoder): + + EEPROM_DECODE_HEADLINES = 6 + + def __init__(self): + self._eeprom_path = "/sys/class/i2c-adapter/i2c-{0}/{0}-00{1}/eeprom".format( + TLV_EEPROM_I2C_BUS, TLV_EEPROM_I2C_ADDR) + super(Tlv, self).__init__(self._eeprom_path, 0, '', True) + self._eeprom = self._load_eeprom() + + def __parse_output(self, decode_output): + decode_output.replace('\0', '') + lines = decode_output.split('\n') + lines = lines[self.EEPROM_DECODE_HEADLINES:] + _eeprom_info_dict = dict() + + for line in lines: + try: + match = re.search( + '(0x[0-9a-fA-F]{2})([\s]+[\S]+[\s]+)([\S]+)', line) + if match is not None: + idx = match.group(1) + value = match.group(3).rstrip('\0') + + _eeprom_info_dict[idx] = value + except Exception: + pass + return _eeprom_info_dict + + def _load_eeprom(self): + original_stdout = sys.stdout + sys.stdout = StringIO() + try: + self.read_eeprom_db() + except Exception as e: + decode_output = sys.stdout.getvalue() + sys.stdout = original_stdout + return self.__parse_output(decode_output) + + status = self.check_status() + if 'ok' not in status: + return False + + if not os.path.exists(CACHE_ROOT): + try: + os.makedirs(CACHE_ROOT) + except Exception: + pass + + # + # only the eeprom classes that inherit from eeprom_base + # support caching. Others will work normally + # + try: + self.set_cache_name(os.path.join(CACHE_ROOT, CACHE_FILE)) + except Exception: + pass + + e = self.read_eeprom() + if e is None: + return 0 + + try: + self.update_cache(e) + except Exception: + pass + + self.decode_eeprom(e) + decode_output = sys.stdout.getvalue() + sys.stdout = original_stdout + + (is_valid, valid_crc) = self.is_checksum_valid(e) + if not is_valid: + return False + + return self.__parse_output(decode_output) + + def get_eeprom(self): + return self._eeprom + + def get_serial(self): + return self._eeprom.get('0x23', "Undefined.") + + def get_mac(self): + return self._eeprom.get('0x24', "Undefined.") + + def get_productname(self): + return self._eeprom.get('0x21', "Undefined.") + + def get_partnumber(self): + return self._eeprom.get('0x22', "Undefined.") + diff --git a/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/fan.py b/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/fan.py new file mode 100644 index 0000000000..12e2ab0a75 --- /dev/null +++ b/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/fan.py @@ -0,0 +1,353 @@ +############################################################################# +# SuperMicro SSE-T7132S +# +# Module contains an implementation of SONiC Platform Base API and +# provides the fan status which are available in the platform +# +############################################################################# + +import subprocess + +try: + from sonic_platform_base.fan_base import FanBase + from .helper import APIHelper + from swsscommon.swsscommon import SonicV2Connector +except ImportError as e: + raise ImportError(str(e) + "- required module not found") + + +FAN_NAME_LIST = ["FAN-1", "FAN-2", "FAN-3", "FAN-4", "FAN-5", "FAN-6"] + +IPMI_SENSOR_NETFN = "0x04" +IPMI_SS_READ_CMD = "0x2D {}" +IPMI_OEM_NETFN = "0x30" +IPMI_GET_FAN_SPEED_CMD = "0x70 0x66 0x00 {}" +IPMI_SET_FAN_SPEED_CMD = "0x70 0x66 0x01 {} {}" +IPMI_GET_FAN_LED_CMD = "0x89 0x03 0x00 {}" +IPMI_SET_FAN_LED_CMD = "0x89 0x03 0x01 {} {}" +IPMI_FAN_LED_OFF = 0x00 +IPMI_FAN_LED_GREEN = 0x01 +IPMI_FAN_LED_AMBER = 0x02 +IPMI_FAN_LED_AMBER_BLINK = 0x03 +IPMI_GET_PSU_FAN_SPEED_CMD = "0x89 0x04 0x{:02x} {}" + +MAX_OUTLET = 29500 +MAX_INLET = 25500 +#MAX_PSU_FAN_OUTLET = 11200 # not a fixed value +#MAX_PSU_FAN_INLET = 11200 # not a fixed value +SPEED_TOLERANCE = 20 # based on the speed graph the slowest is about 20% + +FAN_LIST = [ + #name sensor_id led_num + ('FAN1', '0x41', '0x04'), + ('FAN2', '0x42', '0x05'), + ('FAN3', '0x43', '0x06'), + ('FAN4', '0x44', '0x07'), + ('FAN5', '0x45', '0x08'), + ('FAN6', '0x46', '0x09'), +] + +SYSLOG_IDENTIFIER = "fan.py" +NOT_AVAILABLE = 'N/A' + +class Fan(FanBase): + """Platform-specific Fan class""" + + def __init__(self, fan_pwn_number=0, fan_index=0, is_psu_fan=False, psu=None): + FanBase.__init__(self) + #self.logger = logger.Logger(SYSLOG_IDENTIFIER) + #self.logger.set_min_log_priority_debug() + #self.logger.log_debug('init fan_pwn_number={} fan_index={}'.format(fan_pwn_number, fan_index)) + self.fan_pwn_number = fan_pwn_number + self.is_psu_fan = is_psu_fan + if self.is_psu_fan: + self.psu = psu + self.psu_index = self.psu.index + self._api_helper = APIHelper() + self.index = fan_index + self.sensor_reading_addr = FAN_LIST[self.index][1] + self.led_number = FAN_LIST[self.index][2] + self.led_set = self.STATUS_LED_COLOR_OFF + self.speed_set = None + + def get_direction(self): + """ + Retrieves the direction of fan + + Returns: + A string, either FAN_DIRECTION_INTAKE or FAN_DIRECTION_EXHAUST + depending on fan direction + """ + # read part number from eeprom + # psu fan follows the same rule + db = SonicV2Connector() + db.connect(db.STATE_DB) + eeprom_table = db.get_all(db.STATE_DB, 'EEPROM_INFO|0x22') + if "Name" in eeprom_table and eeprom_table["Name"] == "Part Number" and "Value" in eeprom_table: + part_number = eeprom_table["Value"] + else: + part_number_cmd = "sudo decode-syseeprom | grep 'Part Number' | grep -oE '[^ ]+$'" + part_number = subprocess.Popen(part_number_cmd, shell=True, text=True, stdout=subprocess.PIPE).stdout.read() + + if "T7132SR" in part_number: + # "SSE-T7132SR" + direction = self.FAN_DIRECTION_INTAKE + else: + # "SSE-T7132S" + direction = self.FAN_DIRECTION_EXHAUST + + return direction + + def get_speed_rpm(self): + """ + Retrieves the speed of fan as RPM. + + Returns: + An integer of RPM. + """ + if self.is_psu_fan: + status, raw_ss_read = self._api_helper.ipmi_raw( + IPMI_OEM_NETFN, IPMI_GET_PSU_FAN_SPEED_CMD.format(self.psu_index + 1, "0x08")) + rpm_speed = int("".join(raw_ss_read.split()[::-1]), 16) if status else 0 + else: + status, raw_ss_read = self._api_helper.ipmi_raw( + IPMI_SENSOR_NETFN, IPMI_SS_READ_CMD.format(self.sensor_reading_addr)) + # factor 140 should read from SDR + rpm_speed = int(raw_ss_read.split()[0], 16) * 140 if status else 0 + + return rpm_speed + + def get_speed(self): + """ + Retrieves the speed of fan as a percentage of full speed + + Returns: + An integer, the percentage of full fan speed, in the range 0 (off) + to 100 (full speed) + """ + rpm_speed = self.get_speed_rpm() + + if self.is_psu_fan: + # psu fan do not know max speed, so return rpm + speed = rpm_speed + if speed <= 100: + speed = 0 # to prevent be taken as percentage + else: + # when intake, the whole fan module is reversed, so still MAX_OUTLET + max = MAX_OUTLET + speed = int(float(rpm_speed)/max * 100) + + return speed + + def get_target_speed(self): + """ + Retrieves the target (expected) speed of the fan + + Returns: + An integer, the percentage of full fan speed, in the range 0 (off) + to 100 (full speed) + """ + """ + status, raw_ss_read = self._api_helper.ipmi_raw( + IPMI_OEM_NETFN, IPMI_GET_FAN_SPEED_CMD.format(self.fan_pwn_number)) + ss_read = raw_ss_read.split()[0] + pwn = int(ss_read, 16) + target = pwn + """ + if self.is_psu_fan: + # not support so return current speed + target = self.get_speed() + else: + # set and get result are not the same with our ipmi oem command + # This is because of the scaling between 100-based and 255-based + # here just return the cached set value for tesstbed + target = self.speed_set + if target is None: + target = self.get_speed() + return target + + def get_speed_tolerance(self): + """ + Retrieves the speed tolerance of the fan + + Returns: + An integer, the percentage of variance from target speed which is + considered tolerable + """ + return SPEED_TOLERANCE + + def set_speed(self, speed): + """ + Sets the fan speed + + Args: + speed: An integer, the percentage of full fan speed to set fan to, + in the range 0 (off) to 100 (full speed) + + Returns: + A boolean, True if speed is set successfully, False if not + """ + if self.is_psu_fan: + # not support + return False + + speed_hex = hex(speed) + status, raw_ss_read = self._api_helper.ipmi_raw( + IPMI_OEM_NETFN, IPMI_SET_FAN_SPEED_CMD.format(self.fan_pwn_number, speed_hex)) + set_speed = False if not status else True + if set_speed: + self.speed_set = speed + return set_speed + + def set_status_led(self, color): + """ + Sets the state of the fan module status LED + + Args: + color: A string representing the color with which to set the + fan module status LED + + Returns: + bool: True if status LED state is set successfully, False if not + """ + if self.is_psu_fan: + # Not support + return False + + # there are only green and red led on fan + led_color = { + self.STATUS_LED_COLOR_GREEN: IPMI_FAN_LED_GREEN, + self.STATUS_LED_COLOR_AMBER: IPMI_FAN_LED_AMBER, + self.STATUS_LED_COLOR_RED: IPMI_FAN_LED_AMBER, + self.STATUS_LED_COLOR_OFF: IPMI_FAN_LED_OFF + }.get(color) + status, set_led = self._api_helper.ipmi_raw( + IPMI_OEM_NETFN, IPMI_SET_FAN_LED_CMD.format(self.led_number, led_color)) + if status: + set_status_led = True + self.led_set = color + else: + set_status_led = False + + return set_status_led + + def get_status_led(self): + """ + Gets the state of the fan status LED + + Returns: + A string, one of the predefined STATUS_LED_COLOR_* strings above + """ + if self.is_psu_fan: + # Not support + return NOT_AVAILABLE + + status, hx_color = self._api_helper.ipmi_raw( + IPMI_OEM_NETFN, IPMI_GET_FAN_LED_CMD.format(self.led_number)) + # there are only green and red led on fan + status_led = { + "00": self.STATUS_LED_COLOR_OFF, + "01": self.STATUS_LED_COLOR_GREEN, + "02": self.STATUS_LED_COLOR_RED, + }.get(hx_color, self.STATUS_LED_COLOR_OFF) + + # if it was set AMBER then return AMBER + if status_led == self.STATUS_LED_COLOR_RED: + if self.led_set == self.STATUS_LED_COLOR_AMBER: + status_led = self.STATUS_LED_COLOR_AMBER + + return status_led + + def get_name(self): + """ + Retrieves the name of the device + + Returns: + string: The name of the device + """ + if self.is_psu_fan: + fan_name = "PSU {} FAN-{}".format(self.psu_index+1, self.index+1) + else: + fan_name = FAN_NAME_LIST[self.index] + + return fan_name + + def get_presence(self): + """ + Retrieves the presence of the FAN + Returns: + bool: True if FAN is present, False if not + """ + if self.is_psu_fan: + presence = self.psu.get_presence() + return presence + + rpm_speed = self.get_speed_rpm() + if rpm_speed == 0: + presence = False + else: + presence = True + + return presence + + def get_model(self): + """ + Retrieves the model number (or part number) of the device + Returns: + string: Model/part number of device + """ + if self.is_psu_fan: + model = self.psu.get_model() + else: + model = "Unknown" + + return model + + def get_serial(self): + """ + Retrieves the serial number of the device + Returns: + string: Serial number of device + """ + if self.is_psu_fan: + serial = self.psu.get_serial() + else: + serial = "Unknown" + + return serial + + def get_status(self): + """ + Retrieves the operational status of the device + Returns: + A boolean value, True if device is operating properly, False if not + """ + if self.is_psu_fan: + # psu status dose not include psu fan status + # follow PWS-1K62A-1R HW P2 11122014.pdf defined slow fan (<1200rpm) + rpm = self.get_speed_rpm() + status = (rpm >= 1200) + return status + else: + return self.get_presence() and self.get_speed() > 0 + + def get_position_in_parent(self): + """ + Retrieves 1-based relative physical position in parent device. If the agent cannot determine the parent-relative position + for some reason, or if the associated value of entPhysicalContainedIn is '0', then the value '-1' is returned + Returns: + integer: The 1-based relative physical position in parent device or -1 if cannot determine the position + """ + return (self.index + 1) + + def is_replaceable(self): + """ + Indicate whether this device is replaceable. + Returns: + bool: True if it is replaceable. + """ + if self.is_psu_fan: + replaceable = self.psu.is_replaceable() + return replaceable + else: + return True diff --git a/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/fan_drawer.py b/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/fan_drawer.py new file mode 100644 index 0000000000..9ead756023 --- /dev/null +++ b/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/fan_drawer.py @@ -0,0 +1,121 @@ +#!/usr/bin/env python + +############################################################################# +# Celestica +# +# Module contains an implementation of SONiC Platform Base API and +# provides the the Fan-Drawers' information available in the platform +# +############################################################################# + +try: + from sonic_platform_base.fan_drawer_base import FanDrawerBase +except ImportError as e: + raise ImportError(str(e) + "- required module not found") + +NUM_FAN = 1 + + +class FanDrawer(FanDrawerBase): + def __init__(self, fantray_index): + FanDrawerBase.__init__(self) + self._index = fantray_index + 1 + self._init_fan(fantray_index) + + def _init_fan(self, fantray_index): + from sonic_platform.fan import Fan + self.PWN_LIST = [0, 1, 0, 1, 2, 2] # TODO: will change in next HW version + for index in range(NUM_FAN): + pwn = self.PWN_LIST[fantray_index] + fan = Fan(pwn, fantray_index) + self._fan_list.append(fan) + + def set_status_led(self, color): + """ + Sets the state of the fan drawer status LED + Args: + color: A string representing the color with which to set the + fan drawer status LED + Returns: + bool: True if status LED state is set successfully, False if not + """ + return self._fan_list[0].set_status_led(color) + + def get_status_led(self, color=None): + """ + Gets the state of the fan drawer LED + Returns: + A string, one of the predefined STATUS_LED_COLOR_* strings above + """ + return self._fan_list[0].get_status_led() + + def get_maximum_consumed_power(self): + """ + Retrives the maximum power drawn by Fan Drawer + + Returns: + A float, with value of the maximum consumable power of the + component. + """ + return 30.24 # by Eddie + + ############################################################## + ###################### Device methods ######################## + ############################################################## + + def get_name(self): + """ + Retrieves the name of the device + Returns: + string: The name of the device + """ + return "Drawer{}".format(self._index) + + def get_presence(self): + """ + Retrieves the presence of the device + Returns: + bool: True if device is present, False if not + """ + return self._fan_list[0].get_presence() + + def get_model(self): + """ + Retrieves the model number (or part number) of the device + Returns: + string: Model/part number of device + """ + return self._fan_list[0].get_model() + + def get_serial(self): + """ + Retrieves the serial number of the device + Returns: + string: Serial number of device + """ + return self._fan_list[0].get_serial() + + def get_status(self): + """ + Retrieves the operational status of the device + Returns: + A boolean value, True if device is operating properly, False if not + """ + return self._fan_list[0].get_status() + + def get_position_in_parent(self): + """ + Retrieves 1-based relative physical position in parent device. If the agent cannot determine the parent-relative position + for some reason, or if the associated value of entPhysicalContainedIn is '0', then the value '-1' is returned + Returns: + integer: The 1-based relative physical position in parent device or -1 if cannot determine the position + """ + return self._index + + def is_replaceable(self): + """ + Indicate whether this device is replaceable. + Returns: + bool: True if it is replaceable. + """ + return True diff --git a/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/helper.py b/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/helper.py new file mode 100644 index 0000000000..7acdedb5fa --- /dev/null +++ b/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/helper.py @@ -0,0 +1,108 @@ +import os +import struct +import subprocess +from mmap import * + +HOST_CHK_CMD = "docker > /dev/null 2>&1" +EMPTY_STRING = "" + + +class APIHelper(): + + def __init__(self): + pass + + def is_host(self): + return os.system(HOST_CHK_CMD) == 0 + + def pci_get_value(self, resource, offset): + status = True + result = "" + try: + fd = os.open(resource, os.O_RDWR) + mm = mmap(fd, 0) + mm.seek(int(offset)) + read_data_stream = mm.read(4) + result = struct.unpack('I', read_data_stream) + except Exception as e: + status = False + return status, result + + def run_command(self, cmd): + status = True + result = "" + try: + p = subprocess.Popen( + cmd, shell=True, universal_newlines=True, stdout=subprocess.PIPE, stderr=subprocess.PIPE) + raw_data, err = p.communicate() + if err == '': + result = raw_data.strip() + except Exception as e: + status = False + return status, result + + def run_interactive_command(self, cmd): + try: + os.system(cmd) + except Exception as e: + return False + return True + + def read_txt_file(self, file_path): + try: + with open(file_path, 'r') as fd: + data = fd.read() + return data.strip() + except IOError: + pass + return None + + def ipmi_raw(self, netfn, cmd): + status = True + result = "" + try: + cmd = ["ipmitool raw {} {}".format(str(netfn), str(cmd))] + p = subprocess.Popen( + cmd, shell=True, universal_newlines=True, stdout=subprocess.PIPE, stderr=subprocess.PIPE) + raw_data, err = p.communicate() + if err == '': + result = raw_data.strip() + else: + status = False + except Exception as e: + status = False + return status, result + + def ipmi_fru_id(self, id, key=None): + status = True + result = "" + try: + cmd = ["ipmitool fru print {}".format(str( + id))] if not key else ["ipmitool fru print {0} | grep '{1}' ".format(str(id), str(key))] + + p = subprocess.Popen( + cmd, shell=True, universal_newlines=True, stdout=subprocess.PIPE, stderr=subprocess.PIPE) + raw_data, err = p.communicate() + if err == '': + result = raw_data.strip() + else: + status = False + except Exception as e: + status = False + return status, result + + def ipmi_set_ss_thres(self, id, threshold_key, value): + status = True + result = "" + try: + cmd = ["ipmitool sensor thresh '{}' {} {}".format(str(id), str(threshold_key), str(value))] + p = subprocess.Popen( + cmd, shell=True, universal_newlines=True, stdout=subprocess.PIPE, stderr=subprocess.PIPE) + raw_data, err = p.communicate() + if err == '': + result = raw_data.strip() + else: + status = False + except Exception as e: + status = False + return status, result diff --git a/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/pcie.py b/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/pcie.py new file mode 100644 index 0000000000..6901f62ea8 --- /dev/null +++ b/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/pcie.py @@ -0,0 +1,18 @@ +############################################################################# +# SuperMicro SSE-T7132S +# +# Module contains an implementation of SONiC Platform Base API and +# provides the PCIe information which are available in the platform +# +############################################################################# + +try: + from sonic_platform_base.sonic_pcie.pcie_common import PcieUtil +except ImportError as e: + raise ImportError(str(e) + "- required module not found") + + +class Pcie(PcieUtil): + """ T7132S Platform-specific PCIe class """ + """ fallback to pcie_common.PcieUtil to avoid pcieutil warning message """ + diff --git a/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/platform.py b/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/platform.py new file mode 100644 index 0000000000..7d5424dc94 --- /dev/null +++ b/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/platform.py @@ -0,0 +1,21 @@ +############################################################################# +# SuperMicro SSE-T7132S +# +# Module contains an implementation of SONiC Platform Base API and +# provides the platform information +# +############################################################################# + +try: + from sonic_platform_base.platform_base import PlatformBase + from sonic_platform.chassis import Chassis +except ImportError as e: + raise ImportError(str(e) + "- required module not found") + + +class Platform(PlatformBase): + """Platform-specific Platform class""" + + def __init__(self): + PlatformBase.__init__(self) + self._chassis = Chassis() diff --git a/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/psu.py b/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/psu.py new file mode 100644 index 0000000000..1a77b75f74 --- /dev/null +++ b/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/psu.py @@ -0,0 +1,545 @@ +############################################################################# +# SuperMicro SSE-T7132S +# +# Module contains an implementation of SONiC Platform Base API and +# provides the PSUs status which are available in the platform +# +############################################################################# + +import re + +try: + from sonic_platform_base.psu_base import PsuBase + from .helper import APIHelper + from sonic_platform.fan import Fan + from sonic_platform_base.thermal_base import ThermalBase +except ImportError as e: + raise ImportError(str(e) + "- required module not found") + +PSU_NAME_LIST = ["PSU_1", "PSU_2"] +PSU_NUM_FAN = [1, 1] +PSU_NUM_TERMAL = [2, 2] + +IPMI_SENSOR_NETFN = "0x04" +IPMI_OEM_NETFN = "0x30" +IPMI_SS_READ_CMD = "0x2D {}" +IPMI_OEM_CMD = "0x89 {}" +IPMI_PSU_TYPE_CMD = "0x1 {}" +IPMI_GET_PSU_LED_MODE_CMD = "0x2 0x1" +IPMI_SET_PSU_LED_MODE_CMD = "0x2 0x2 {}" +IPMI_GET_PSU_LED_PATTERN_CMD = "0x3 0x0 {}" +IPMI_SET_PSU_LED_PATTERN_CMD = "0x3 0x1 {} {}" +IPMI_PSU_INFO_CMD= "0x4 {} {}" + +PSU_LED_OFF_CMD = "0x00" +PSU_LED_GREEN_CMD = "0x01" +PSU_LED_AMBER_CMD = "0x02" + +PSU_SERIAL_CMD = "0x00" +PSU_MODEL_CMD = "0x01" +PSU_VOUT_CMD = "0x02" +PSU_COUT_CMD = "0x03" +PSU_POUT_CMD = "0x04" +PSU_VIN_CMD = "0x05" +PSU_CIN_CMD = "0x06" +PSU_PIN_CMD = "0x07" +PSU_FAN1_CMD = "0x08" +PSU_FAN2_CMD = "0x09" +PSU_TEMP1_CMD = "0x0A" +PSU_TEMP2_CMD = "0x0B" +PSU_MAX_TEMP1_CMD = "0x0C" +PSU_MAX_TEMP2_CMD = "0x0D" +PSU_MAX_POUT_CMD = "0x0E" + +PSU1_STATUS_REG = "0xC4" +PSU2_STATUS_REG = "0xC5" + +PSU1_FRU_ID = 3 + +PSU_OUT_VOLTAGE = 12 + +SS_READ_OFFSET = 0 +OEM_READ_OFFSET = 0 + + +class Psu(PsuBase): + """Platform-specific Psu class""" + + def __init__(self, psu_index): + PsuBase.__init__(self) + self.index = psu_index + for fan_index in range(0, PSU_NUM_FAN[self.index]): + fan = Fan(0, fan_index, is_psu_fan=True, psu=self) + self._fan_list.append(fan) + for thermal_index in range(0, PSU_NUM_TERMAL[self.index]): + self._thermal_list.append(PsuThermal(self, thermal_index)) + self._api_helper = APIHelper() + + def find_value(self, in_string): + result = re.search("^.+ ([0-9a-f]{2}) .+$", in_string) + return result.group(1) if result else result + + def get_voltage(self): + """ + Retrieves current PSU voltage output + Returns: + A float number, the output voltage in volts, + e.g. 12.1 + """ + psu_voltage = 0.0 + psu_vout_key = IPMI_PSU_INFO_CMD.format(self.index+1, PSU_VOUT_CMD) + status, raw_oem_read = self._api_helper.ipmi_raw( + IPMI_OEM_NETFN, IPMI_OEM_CMD.format(psu_vout_key)) + + if raw_oem_read: + # Formula: R/10 + psu_voltage = int("".join(raw_oem_read.split()[::-1]), 16) / 10 + + return psu_voltage + + def get_voltage_high_threshold(self): + """ + Retrieves the high threshold PSU voltage output + Returns: + A float number, the high threshold output voltage in volts, + e.g. 12.1 + """ + # Formula: PSU_OUT_VOLTAGEx11/10 + psu_voltage = PSU_OUT_VOLTAGE * 11 / 10 + + return psu_voltage + + def get_voltage_low_threshold(self): + """ + Retrieves the low threshold PSU voltage output + Returns: + A float number, the low threshold output voltage in volts, + e.g. 12.1 + """ + # Formula: PSU_OUT_VOLTAGEx9/10 + psu_voltage = PSU_OUT_VOLTAGE * 9 / 10 + + return psu_voltage + + def get_current(self): + """ + Retrieves present electric current supplied by PSU + Returns: + A float number, the electric current in amperes, e.g 15.4 + """ + psu_current = 0.0 + psu_cout_key = IPMI_PSU_INFO_CMD.format(self.index+1, PSU_COUT_CMD) + status, raw_oem_read = self._api_helper.ipmi_raw( + IPMI_OEM_NETFN, IPMI_OEM_CMD.format(psu_cout_key)) + + if raw_oem_read: + # Formula: R/1000 + psu_current = int("".join(raw_oem_read.split()[::-1]), 16) / 1000 + + return psu_current + + def get_power(self): + """ + Retrieves current energy supplied by PSU + Returns: + A float number, the power in watts, e.g. 302.6 + """ + psu_power = 0.0 + psu_pout_key = IPMI_PSU_INFO_CMD.format(self.index+1, PSU_POUT_CMD) + status, raw_oem_read = self._api_helper.ipmi_raw( + IPMI_OEM_NETFN, IPMI_OEM_CMD.format(psu_pout_key)) + + if raw_oem_read: + # Formula: R + psu_power = int("".join(raw_oem_read.split()[::-1]), 16) + return psu_power + + def get_maximum_supplied_power(self): + """ + Retrieves the maximum supplied power by PSU + Returns: + A float number, the maximum power output in Watts. + e.g. 1200.1 + """ + psu_power = 0.0 + psu_pout_key = IPMI_PSU_INFO_CMD.format(self.index+1, PSU_MAX_POUT_CMD) + status, raw_oem_read = self._api_helper.ipmi_raw( + IPMI_OEM_NETFN, IPMI_OEM_CMD.format(psu_pout_key)) + + if raw_oem_read: + # Formula: R + psu_power = int("".join(raw_oem_read.split()[::-1]), 16) + return psu_power + + def get_powergood_status(self): + """ + Retrieves the powergood status of PSU + Returns: + A boolean, True if PSU has stablized its output voltages and passed all + its internal self-tests, False if not. + """ + return self.get_status() + + def set_status_led(self, color): + """ + Sets the state of the PSU status LED + Args: + color: A string representing the color with which to set the PSU status LED + Note: Only support green and off + Returns: + bool: True if status LED state is set successfully, False if not + Note + """ + led_cmd = { + self.STATUS_LED_COLOR_GREEN: PSU_LED_GREEN_CMD, + "orange": PSU_LED_AMBER_CMD, + self.STATUS_LED_COLOR_OFF: PSU_LED_OFF_CMD + }.get(color) + + psu_led_key = IPMI_SET_PSU_LED_PATTERN_CMD.format(self.index+2,led_cmd) + status, set_led = self._api_helper.ipmi_raw( + IPMI_OEM_NETFN, IPMI_OEM_CMD.format(psu_led_key)) + set_status_led = False if not status else True + + return set_status_led + + def get_status_led(self): + """ + Gets the state of the PSU status LED + Returns: + A string, one of the predefined STATUS_LED_COLOR_* strings above + """ + psu_led_key = IPMI_GET_PSU_LED_PATTERN_CMD.format(self.index+2) + status, hx_color = self._api_helper.ipmi_raw( + IPMI_OEM_NETFN, IPMI_OEM_CMD.format(psu_led_key)) + + status_led = { + "00": self.STATUS_LED_COLOR_OFF, + "01": self.STATUS_LED_COLOR_GREEN, + "02": "orange", + }.get(hx_color, self.STATUS_LED_COLOR_OFF) + + return status_led + + def get_temperature(self): + """ + Retrieves current temperature reading from PSU + Returns: + A float number of current temperature in Celsius up to nearest thousandth + of one degree Celsius, e.g. 30.125 + there are three temp sensors , we choose one of them + """ + # Need implement after BMC function ready + psu_temperature = None + + return psu_temperature + + def get_temperature_high_threshold(self): + """ + Retrieves the high threshold temperature of PSU + Returns: + A float number, the high threshold temperature of PSU in Celsius + up to nearest thousandth of one degree Celsius, e.g. 30.125 + there are three temp sensors , we choose one of them + """ + # Need implement after BMC function ready + psu_temperature = None + + return psu_temperature + + def get_name(self): + """ + Retrieves the name of the device + Returns: + string: The name of the device + """ + return PSU_NAME_LIST[self.index] + + def get_presence(self): + """ + Retrieves the presence of the PSU + Returns: + bool: True if PSU is present, False if not + """ + psu_presence = False + psu_pstatus_key = globals()['PSU{}_STATUS_REG'.format(self.index+1)] + status, raw_status_read = self._api_helper.ipmi_raw( + IPMI_SENSOR_NETFN, IPMI_SS_READ_CMD.format(psu_pstatus_key)) + status_byte = self.find_value(raw_status_read) + + if status: + presence_int = (int(status_byte, 16) >> 0) & 1 + psu_presence = True if presence_int else False + + return psu_presence + + def get_model(self): + """ + Retrieves the model number (or part number) of the device + Returns: + string: Model/part number of device + """ + model = "Unknown" + psu_model_key = IPMI_PSU_INFO_CMD.format(self.index+1, PSU_MODEL_CMD) + status, raw_model = self._api_helper.ipmi_raw( + IPMI_OEM_NETFN, IPMI_OEM_CMD.format(psu_model_key)) + + model_raw_list = raw_model.split() + if len(model_raw_list) > 0: + model="".join(map(chr,map(lambda x: int(x, 16), model_raw_list))) + return model + + def get_serial(self): + """ + Retrieves the serial number of the device + Returns: + string: Serial number of device + """ + serial = "Unknown" + psu_serial_key = IPMI_PSU_INFO_CMD.format(self.index+1, PSU_SERIAL_CMD) + status, raw_serial = self._api_helper.ipmi_raw( + IPMI_OEM_NETFN, IPMI_OEM_CMD.format(psu_serial_key)) + + serial_raw_list = raw_serial.split() + if len(serial_raw_list) > 0: + serial="".join(map(chr,map(lambda x: int(x, 16), serial_raw_list))) + + return serial + + def get_status(self): + """ + Retrieves the operational status of the device + Returns: + A boolean value, True if device is operating properly, False if not + """ + psu_status = False + psu_pstatus_key = globals()['PSU{}_STATUS_REG'.format(self.index+1)] + status, raw_status_read = self._api_helper.ipmi_raw( + IPMI_SENSOR_NETFN, IPMI_SS_READ_CMD.format(psu_pstatus_key)) + status_byte = self.find_value(raw_status_read) + + if status: + failure_detected = (int(status_byte, 16) >> 1) & 1 + input_lost = (int(status_byte, 16) >> 3) & 1 + psu_status = False if (input_lost or failure_detected) else True + + return psu_status + + def get_type(self): + """ + Retrives the Power Type of PSU + + Returns : + A string, PSU power type + """ + psu_type = [None, 'AC', 'AC', 'DC'] + psu_type_key = IPMI_PSU_TYPE_CMD.format(self.index+1) + status, raw_type_read = self._api_helper.ipmi_raw( + IPMI_OEM_NETFN, IPMI_OEM_CMD.format(psu_type_key)) + if status: + raw_type = raw_type_read.split()[OEM_READ_OFFSET] + type_index = int(raw_type, 16) + if type_index < 4: + return psu_type[type_index] + return None + + def get_position_in_parent(self): + """ + Retrieves 1-based relative physical position in parent device. + Returns: + integer: The 1-based relative physical position in parent + device or -1 if cannot determine the position + """ + return self.index + + def is_replaceable(self): + """ + Indicate whether this PSU is replaceable. + Returns: + bool: True if it is replaceable. + """ + return True + + + def get_num_thermals(self): + """ + Retrieves the number of thermals available on this PSU + + Returns: + An integer, the number of thermals available on this PSU + """ + return len(self._thermal_list) + + def get_all_thermals(self): + """ + Retrieves all thermals available on this PSU + + Returns: + A list of objects derived from ThermalBase representing all thermals + available on this PSU + """ + return self._thermal_list + + def get_thermal(self, index): + """ + Retrieves thermal unit represented by (0-based) index + + Args: + index: An integer, the index (0-based) of the thermal to + retrieve + + Returns: + An object derived from ThermalBase representing the specified thermal + """ + thermal = None + + try: + thermal = self._thermal_list[index] + except IndexError: + sys.stderr.write("THERMAL index {} out of range (0-{})\n".format( + index, len(self._thermal_list)-1)) + + return thermal + +class PsuThermal(ThermalBase): + """Platform-specific Thermal class for PSU """ + + def __init__(self, psu, index): + self._api_helper = APIHelper() + self.psu = psu + self.index = index + self.minimum_thermal = 999 + self.maximum_thermal = 0 + + def get_temperature(self): + """ + Retrieves current temperature reading from thermal + + Returns: + A float number of current temperature in Celsius up to nearest thousandth + of one degree Celsius, e.g. 30.125 + """ + if self.psu.get_presence() != True: + return None + + psu_temperature = 0.0 + psu_temp_cmd_key = globals()['PSU_TEMP{}_CMD'.format(self.index+1)] + psu_temp_key = IPMI_PSU_INFO_CMD.format(self.psu.index+1, psu_temp_cmd_key) + status, raw_oem_read = self._api_helper.ipmi_raw( + IPMI_OEM_NETFN, IPMI_OEM_CMD.format(psu_temp_key)) + + if raw_oem_read: + # Formula: R + psu_temperature = int("".join(raw_oem_read.split()[::-1]), 16) + + if psu_temperature > self.maximum_thermal: + self.maximum_thermal = psu_temperature + if psu_temperature < self.minimum_thermal: + self.minimum_thermal = psu_temperature + + return psu_temperature + + def get_high_threshold(self): + """ + Retrieves the high threshold temperature of thermal + + Returns: + A float number, the high threshold temperature of thermal in Celsius + up to nearest thousandth of one degree Celsius, e.g. 30.125 + """ + # ignore max_temp 1 to aviod false alarm because PSU fan control is not ready + if self.index == 0: + return None + + if self.get_presence() != True: + return None + + psu_temper_high = 0.0 + psu_temp_cmd_key = globals()['PSU_MAX_TEMP{}_CMD'.format(self.index+1)] + psu_temp_key = IPMI_PSU_INFO_CMD.format(self.psu.index+1, psu_temp_cmd_key) + status, raw_oem_read = self._api_helper.ipmi_raw( + IPMI_OEM_NETFN, IPMI_OEM_CMD.format(psu_temp_key)) + + if raw_oem_read: + # Formula: R + psu_temper_high = int("".join(raw_oem_read.split()[::-1]), 16) + + return psu_temper_high + + def get_minimum_recorded(self): + """ + Retrieves the minimum recorded temperature of thermal + + Returns: + A float number, the minimum recorded temperature of thermal in Celsius + up to nearest thousandth of one degree Celsius, e.g. 30.125 + """ + return self.minimum_thermal; + + def get_maximum_recorded(self): + """ + Retrieves the maximum recorded temperature of thermal + + Returns: + A float number, the maximum recorded temperature of thermal in Celsius + up to nearest thousandth of one degree Celsius, e.g. 30.125 + """ + return self.maximum_thermal + + def get_name(self): + """ + Retrieves the name of the thermal device + Returns: + string: The name of the thermal device + """ + return '{}_TEMP_{}'.format(self.psu.get_name(), self.index+1) + + def get_presence(self): + """ + Retrieves the presence of the device + Returns: + bool: True if device is present, False if not + """ + return self.psu.get_presence() + + def get_model(self): + """ + Retrieves the model number (or part number) of the device + Returns: + string: Model/part number of device + """ + return self.psu.get_model() + + def get_serial(self): + """ + Retrieves the serial number of the device + Returns: + string: Serial number of device + """ + return self.psu.get_serial() + + def get_status(self): + """ + Retrieves the operational status of the device + Returns: + A boolean value, True if device is operating properly, False if not + """ + return self.psu.get_status() + + def get_position_in_parent(self): + """ + Retrieves 1-based relative physical position in parent device. + Returns: + integer: The 1-based relative physical position in parent + device or -1 if cannot determine the position + """ + return (self.index + 1) + + def is_replaceable(self): + """ + Indicate whether this Thermal is replaceable. + Returns: + bool: True if it is replaceable. + """ + return False + diff --git a/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/sfp.py b/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/sfp.py new file mode 100644 index 0000000000..3bb0d7fdda --- /dev/null +++ b/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/sfp.py @@ -0,0 +1,444 @@ +#!/usr/bin/env python +""" +############################################################################# +# SuperMicro SSE-T7132S +# +# Sfp contains an implementation of SONiC Platform Base API and +# provides the sfp status which are available in the platform +# +############################################################################# +""" + +try: + import os + import time + from sonic_platform_base.sonic_xcvr.sfp_optoe_base import SfpOptoeBase + +except ImportError as err: + raise ImportError(str(err) + "- required module not found") + +QSFP_INFO_OFFSET = 128 +SFP_INFO_OFFSET = 0 +QSFP_DD_PAGE0 = 0 + +SFP_TYPE_LIST = [ + '0x3' # SFP/SFP+/SFP28 and later +] +QSFP_TYPE_LIST = [ + '0x0c', # QSFP + '0x0d', # QSFP+ or later + '0x11' # QSFP28 or later +] +QSFP_DD_TYPE_LIST = [ + '0x18' #QSFP_DD Type +] + +OSFP_TYPE_LIST = [ + '0x19' # OSFP 8X Type +] + +SFP_TYPE = "SFP" +QSFP_TYPE = "QSFP" +OSFP_TYPE = "OSFP" +QSFP_DD_TYPE = "QSFP_DD" +SFP_NAME = "Ethernet{}" + +PORT_START = 0 +PORT_END = 34 +QSFP_PORT_START = 0 +QSFP_PORT_END = 32 + +I2C_EEPROM_PATH = '/sys/bus/i2c/devices/i2c-{0}/{0}-0050/eeprom' +PORT_INFO_PATH= '/sys/class/t7132s_cpld' + +class Sfp(SfpOptoeBase): + """Platform-specific Sfp class""" + PLATFORM = "x86_64-supermicro_sse_t7132s-r0" + HWSKU = "Supermicro_sse_t7132s" + + _port_to_offset = [11, 30, 12, 29, 13, 28, 14, 27, 15, 34, + 16, 33, 17, 32, 18, 31, 19, 38, 20, 37, + 21, 36, 22, 35, 23, 42, 24, 41, 25, 40, + 26, 39, + 43, 44] + + def __init__(self, sfp_index=0): + SfpOptoeBase.__init__(self) + + self.index = sfp_index # for sfputil show error-status --fetch-from-hardware + self._master_port = self.index - 1 + self._port_num = self.index + self.sfp_type = QSFP_DD_TYPE + #port_type is the native port type and sfp_type is the transceiver type + #sfp_type will be detected in get_transceiver_info + if self._master_port < QSFP_PORT_END: + self.port_type = QSFP_DD_TYPE + self.NUM_CHANNELS = 8 + self.port_name = "QSFP" + str(self._port_num) + self._name = [SFP_NAME.format(str(self._master_port*8))] + else: + self.port_type = SFP_TYPE + self.NUM_CHANNELS = 1 + self.port_name = "SFP" + str(self._port_num - QSFP_PORT_END) + self._name = [SFP_NAME.format(str((QSFP_PORT_END*8)+(self._master_port - QSFP_PORT_END)))] + self.sfp_type = self.port_type + self.sfp_eeprom_path = self.get_eeprom_path() + self._initialize_media(delay=False) + + def _detect_sfp_type(self): + eeprom_raw = [] + eeprom_ready = True + + time_begin = time.time() + eeprom_ready = False + while (time.time() - time_begin) < 4: + # read 2 more bytes to check eeprom ready + eeprom_raw = self.read_eeprom(XCVR_TYPE_OFFSET, XCVR_TYPE_WIDTH + 2) + + if eeprom_raw: + if eeprom_raw[0] in SFP_TYPE_CODE_LIST: + self.sfp_type = SFP_TYPE + eeprom_ready = True + elif eeprom_raw[0] in QSFP_TYPE_CODE_LIST: + self.sfp_type = QSFP_TYPE + eeprom_ready = True + elif eeprom_raw[0] in QSFP_DD_TYPE_CODE_LIST: + self.sfp_type = QSFP_DD_TYPE + eeprom_ready = True + else: + self.sfp_type = self.port_type + if all([b == '00' for b in eeprom_raw]): + logger.Logger('SFP').log_warning( + "_detect_sfp_type: {} index {} by {} eeprom all 0". + format(self._name, self.index, + inspect.currentframe().f_back.f_code.co_name)) + else: + eeprom_ready = True + else: + logger.Logger('SFP').log_warning( + "_detect_sfp_type: {} index {} by {} eeprom none". + format(self._name, self.index, + inspect.currentframe().f_back.f_code.co_name)) + self.sfp_type = self.port_type + + if not eeprom_ready: + # retry after sleep + time.sleep(1) + else: + break; + + if self.sfp_type == QSFP_DD_TYPE: + self.NUM_CHANNELS = 8 + elif self.sfp_type == QSFP_TYPE: + self.NUM_CHANNELS = 4 + elif self.sfp_type == SFP_TYPE: + self.NUM_CHANNELS = 1 + + return eeprom_ready + + def get_eeprom_path(self): + """ + Returns SFP eeprom path + """ + port_eeprom_path = I2C_EEPROM_PATH.format(self._port_to_offset[self._master_port]) + return port_eeprom_path + + def get_name(self): + """ + Retrieves the name of the device + Returns: + string: The name of the device + """ + return self._name[0] + + def _initialize_media(self, delay=False): + """ + Initialize the media type and eeprom driver for SFP + """ + if delay: + time.sleep(1) + self._xcvr_api = None + self.get_xcvr_api() + + self.set_media_type() + self.reinit_sfp_driver() + + def get_presence(self): + """ + Retrieves the presence of the SFP + Returns: + bool: True if SFP is present, False if not + """ + sysfs_filename = "sfp_modabs" if self.port_type == SFP_TYPE else "qsfp_modprs" + reg_path = "/".join([PORT_INFO_PATH, self.port_name, sysfs_filename]) + + # Read status + try: + with open(reg_path) as reg_file: + content = reg_file.readline().rstrip() + reg_value = int(content) + # Module present is active low + if reg_value == 0: + return True + except IOError as e: + print("Error: unable to open file: %s" % str(e)) + return False + + # not present + return False + + def get_reset_status(self): + """ + Retrieves the reset status of SFP + Returns: + A Boolean, True if reset enabled, False if disabled + """ + if self.port_type != QSFP_DD_TYPE: + return False + + try: + with open( + "/".join([PORT_INFO_PATH, self.port_name, "qsfp_reset"])) as reg_file: + # Read status + content = reg_file.readline().rstrip() + reg_value = int(content) + # reset is active low + if reg_value == 0: + return True + except IOError as e: + print("Error: unable to open file: %s" % str(e)) + return False + + return False + + def get_lpmode(self): + """ + Retrieves the lpmode (low power mode) status of this SFP + Returns: + A Boolean, True if lpmode is enabled, False if disabled + """ + if self.port_type != QSFP_DD_TYPE: + return False + + try: + with open( + "/".join([PORT_INFO_PATH, self.port_name, "qsfp_lpmode"])) as reg_file: + # Read status + content = reg_file.readline().rstrip() + reg_value = int(content) + # low power mode is active high + if reg_value == 0: + return False + except IOError as e: + print("Error: unable to open file: %s" % str(e)) + return False + + return True + + def reset(self): + """ + Reset SFP and return all user module settings to their default srate. + Returns: + A boolean, True if successful, False if not + """ + if self.port_type != QSFP_DD_TYPE: + return False + + try: + with open( + "/".join([PORT_INFO_PATH, self.port_name, "qsfp_reset"]), "w") as reg_file: + # Convert our register value back to a hex string and write back + reg_file.seek(0) + reg_file.write(hex(0)) + except IOError as e: + print("Error: unable to open file: %s" % str(e)) + return False + + # Sleep 1 second to allow it to settle + time.sleep(1) + + # Flip the bit back high and write back to the register to take port out of reset + try: + with open( + "/".join([PORT_INFO_PATH, self.port_name, "qsfp_reset"]), "w") as reg_file: + reg_file.seek(0) + reg_file.write(hex(1)) + except IOError as e: + print("Error: unable to open file: %s" % str(e)) + return False + + return True + + def no_reset(self): + """ + Set CPLD qsfp_reset to 1 for non-reset status. + Returns: + A boolean, True if successful, False if not + """ + if self.port_type != QSFP_DD_TYPE: + return False + + try: + with open( + "/".join([PORT_INFO_PATH, self.port_name, "qsfp_reset"]), "w") as reg_file: + reg_file.seek(0) + reg_file.write(hex(1)) + except IOError as e: + print("Error: unable to open file: %s" % str(e)) + return False + + return True + + def set_lpmode(self, lpmode): + """ + Sets the lpmode (low power mode) of SFP + Args: + lpmode: A Boolean, True to enable lpmode, False to disable it + Note : lpmode can be overridden by set_power_override + Returns: + A boolean, True if lpmode is set successfully, False if not + """ + if not self._detect_sfp_type(): + return False + + if self.port_type != QSFP_DD_TYPE: + return False + + try: + reg_file = open( + "/".join([PORT_INFO_PATH, self.port_name, "qsfp_lpmode"]), "r+") + except IOError as e: + print("Error: unable to open file: %s" % str(e)) + return False + + content = hex(lpmode) + + reg_file.seek(0) + reg_file.write(content) + reg_file.close() + + return True + + def set_media_type(self): + """ + Reads optic eeprom byte to determine media type inserted + """ + eeprom_raw = [] + eeprom_raw = self._xcvr_api_factory._get_id() + if eeprom_raw is not None: + eeprom_raw = hex(eeprom_raw) + if eeprom_raw in SFP_TYPE_LIST: + self.sfp_type = SFP_TYPE + elif eeprom_raw in QSFP_TYPE_LIST: + self.sfp_type = QSFP_TYPE + elif eeprom_raw in QSFP_DD_TYPE_LIST: + self.sfp_type = QSFP_DD_TYPE + else: + #Set native port type if EEPROM type is not recognized/readable + self.sfp_type = self.port_type + else: + self.sfp_type = self.port_type + + return self.sfp_type + + def reinit_sfp_driver(self): + """ + Changes the driver based on media type detected + """ + + i2c_bus = self.sfp_eeprom_path[25:].split('/')[0] + del_sfp_path = "/sys/bus/i2c/devices/i2c-{0}/delete_device".format(i2c_bus) + new_sfp_path = "/sys/bus/i2c/devices/i2c-{0}/new_device".format(i2c_bus) + driver_path = "/sys/bus/i2c/devices/i2c-{0}/{0}-0050/name".format(i2c_bus) + + if not os.path.isfile(driver_path): + print(driver_path, "does not exist") + return False + + try: + with os.fdopen(os.open(driver_path, os.O_RDONLY)) as filed: + driver_name = filed.read() + driver_name = driver_name.rstrip('\r\n') + driver_name = driver_name.lstrip(" ") + + #Avoid re-initialization of the QSFP/SFP optic on QSFP/SFP port. + if self.sfp_type == SFP_TYPE and driver_name in ['optoe1', 'optoe3']: + with open(del_sfp_path, 'w') as f: + f.write('0x50\n') + time.sleep(0.2) + with open(new_sfp_path, 'w') as f: + f.write('optoe2 0x50\n') + time.sleep(2) + elif self.sfp_type == OSFP_TYPE and driver_name in ['optoe2', 'optoe3']: + with open(del_sfp_path, 'w') as f: + f.write('0x50\n') + time.sleep(0.2) + with open(new_sfp_path, 'w') as f: + f.write('optoe1 0x50\n') + time.sleep(2) + elif self.sfp_type == QSFP_DD_TYPE and driver_name in ['optoe1', 'optoe2']: + with open(del_sfp_path, 'w') as f: + f.write('0x50\n') + time.sleep(0.2) + with open(new_sfp_path, 'w') as f: + f.write('optoe3 0x50\n') + time.sleep(2) + + except IOError as err: + print("Error: Unable to open file: %s" %str(err)) + return False + + return True + + def get_position_in_parent(self): + """ + Retrieves 1-based relative physical position in parent device. + Returns: + integer: The 1-based relative physical position in parent + device or -1 if cannot determine the position + """ + return 0 + + @staticmethod + def is_replaceable(): + """ + Indicate whether this device is replaceable. + Returns: + bool: True if it is replaceable. + """ + return True + + def get_error_description(self): + """ + Retrives the error descriptions of the SFP module + + Returns: + String that represents the current error descriptions of vendor specific errors + In case there are multiple errors, they should be joined by '|', + like: "Bad EEPROM|Unsupported cable" + """ + if not self.get_presence(): + return self.SFP_STATUS_UNPLUGGED + else: + if not os.path.isfile(self.sfp_eeprom_path): + return "EEPROM driver is not attached" + + if self.sfp_type == SFP_TYPE: + offset = SFP_INFO_OFFSET + elif self.sfp_type == OSFP_TYPE: + offset = QSFP_INFO_OFFSET + elif self.sfp_type == QSFP_TYPE: + offset = QSFP_INFO_OFFSET + elif self.sfp_type == QSFP_DD_TYPE: + offset = QSFP_DD_PAGE0 + else: + return "Invalid SFP type {}".format(self.sfp_type) + + try: + with open(self.sfp_eeprom_path, mode="rb", buffering=0) as eeprom: + eeprom.seek(offset) + eeprom.read(1) + except OSError as e: + return "EEPROM read failed ({})".format(e.strerror) + + return self.SFP_STATUS_OK \ No newline at end of file diff --git a/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/thermal.py b/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/thermal.py new file mode 100644 index 0000000000..38e3b5b7dc --- /dev/null +++ b/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/thermal.py @@ -0,0 +1,253 @@ +############################################################################# +# SuperMicro SSE-T7132S +# +# Thermal contains an implementation of SONiC Platform Base API and +# provides the thermal device status which are available in the platform +# +############################################################################# + +try: + from sonic_platform_base.thermal_base import ThermalBase + from .helper import APIHelper +except ImportError as e: + raise ImportError(str(e) + "- required module not found") + +IPMI_SENSOR_NETFN = "0x04" +IPMI_SS_READ_CMD = "0x2D {}" +IPMI_SS_THRESHOLD_CMD = "0x27 {}" +HIGH_TRESHOLD_SET_KEY = "ucr" +LOW_TRESHOLD_SET_KEY = "lcr" +HIGH_CRIT_TRESHOLD_SET_KEY = "unr" +LOW_CRIT_TRESHOLD_SET_KEY = "lnr" + + +class Thermal(ThermalBase): + """Platform-specific Thermal class""" + + def __init__(self, thermal_index): + ThermalBase.__init__(self) + self._api_helper = APIHelper() + self.index = thermal_index + self.THERMAL_LIST = [ + ('CPU_Temp', 'CPU Temperature Sensor', '0x01'), + ('PCH_Temp', 'PCH Temperature Sensor', '0x0a'), + ('System_Temp', 'System Temperature Sensor', '0x0b'), + ('Peripheral_Temp', 'Peripheral Temperature Sensor', '0x0c'), + ('Switch_Top-1', 'Switchboard Left Inlet Temperature Sensor', '0xb4'), + ('Switch_Buttom-1', 'Switchboard Left Outlet Temperature Sensor', '0xb5'), + ('Switch_Top-2', 'Switchboard Right Inlet Temperature Sensor', '0xb6'), + ('Switch_Buttom-2', 'Switchboard Right Outlet Temperature Sensor','0xb7'), + ('Switch_Temp', 'Switch Temperature Sensor', '0xb8'), + ] + self.sensor_id = self.THERMAL_LIST[self.index][0] + self.sensor_des = self.THERMAL_LIST[self.index][1] + self.sensor_reading_addr = self.THERMAL_LIST[self.index][2] + self.minimum_thermal = self.get_temperature() + self.maximum_thermal = self.get_temperature() + + def __set_threshold(self, key, value): + print('{} {}'.format(key, value)) + + def get_temperature(self): + """ + Retrieves current temperature reading from thermal + Returns: + A float number of current temperature in Celsius up to nearest thousandth + of one degree Celsius, e.g. 30.125 + """ + temperature = 0.0 + status, raw_ss_read = self._api_helper.ipmi_raw( + IPMI_SENSOR_NETFN, IPMI_SS_READ_CMD.format(self.sensor_reading_addr)) + if status and len(raw_ss_read.split()) > 0: + ss_read = raw_ss_read.split()[0] + temperature = float(int(ss_read, 16)) + return temperature + + def get_high_threshold(self): + """ + Retrieves the high threshold temperature of thermal + Returns: + A float number, the high threshold temperature of thermal in Celsius + up to nearest thousandth of one degree Celsius, e.g. 30.125 + """ + high_threshold = 0.0 + status, raw_up_thres_read = self._api_helper.ipmi_raw( + IPMI_SENSOR_NETFN, IPMI_SS_THRESHOLD_CMD.format(self.sensor_reading_addr)) + if status and len(raw_up_thres_read.split()) > 6: + ss_read = raw_up_thres_read.split()[5] + high_threshold = float(int(ss_read, 16)) + return high_threshold + + def get_low_threshold(self): + """ + Retrieves the low threshold temperature of thermal + Returns: + A float number, the low threshold temperature of thermal in Celsius + up to nearest thousandth of one degree Celsius, e.g. 30.125 + """ + low_threshold = 0.0 + status, raw_up_thres_read = self._api_helper.ipmi_raw( + IPMI_SENSOR_NETFN, IPMI_SS_THRESHOLD_CMD.format(self.sensor_reading_addr)) + if status and len(raw_up_thres_read.split()) > 6: + ss_read = raw_up_thres_read.split()[2] + low_threshold = float(int(ss_read, 16)) + return low_threshold + + def set_high_threshold(self, temperature): + """ + Sets the high threshold temperature of thermal + Args : + temperature: A float number up to nearest thousandth of one degree Celsius, + e.g. 30.125 + Returns: + A boolean, True if threshold is set successfully, False if not + """ + status, ret_txt = self._api_helper.ipmi_set_ss_thres(self.sensor_id, HIGH_TRESHOLD_SET_KEY, temperature) + return status + + def set_low_threshold(self, temperature): + """ + Sets the low threshold temperature of thermal + Args : + temperature: A float number up to nearest thousandth of one degree Celsius, + e.g. 30.125 + Returns: + A boolean, True if threshold is set successfully, False if not + """ + status, ret_txt = self._api_helper.ipmi_set_ss_thres(self.sensor_id, LOW_TRESHOLD_SET_KEY, temperature) + return status + + def get_high_critical_threshold(self): + """ + Retrieves the high critical threshold temperature of thermal + Returns: + A float number, the high critical threshold temperature of thermal in Celsius + up to nearest thousandth of one degree Celsius, e.g. 30.125 + """ + high_critical_threshold = 0.0 + status, raw_up_thres_read = self._api_helper.ipmi_raw( + IPMI_SENSOR_NETFN, IPMI_SS_THRESHOLD_CMD.format(self.sensor_reading_addr)) + if status and len(raw_up_thres_read.split()) > 6: + ss_read = raw_up_thres_read.split()[6] + high_critical_threshold = float(int(ss_read, 16)) + return high_critical_threshold + + def get_low_critical_threshold(self): + """ + Retrieves the low critical threshold temperature of thermal + Returns: + A float number, the low critical threshold temperature of thermal in Celsius + up to nearest thousandth of one degree Celsius, e.g. 30.125 + """ + critical_low_threshold = 0.0 + status, raw_up_thres_read = self._api_helper.ipmi_raw( + IPMI_SENSOR_NETFN, IPMI_SS_THRESHOLD_CMD.format(self.sensor_reading_addr)) + if status and len(raw_up_thres_read.split()) > 6: + ss_read = raw_up_thres_read.split()[3] + critical_low_threshold = float(int(ss_read, 16)) + return critical_low_threshold + + def set_high_critical_threshold(self, temperature): + """ + Sets the critical high threshold temperature of thermal + Args : + temperature: A float number up to nearest thousandth of one degree Celsius, + e.g. 30.125 + Returns: + A boolean, True if threshold is set successfully, False if not + """ + status, ret_txt = self._api_helper.ipmi_set_ss_thres(self.sensor_id, HIGH_CRIT_TRESHOLD_SET_KEY, temperature) + return status + + def set_low_critical_threshold(self, temperature): + """ + Sets the critical low threshold temperature of thermal + Args : + temperature: A float number up to nearest thousandth of one degree Celsius, + e.g. 30.125 + Returns: + A boolean, True if threshold is set successfully, False if not + """ + status, ret_txt = self._api_helper.ipmi_set_ss_thres(self.sensor_id, LOW_CRIT_TRESHOLD_SET_KEY, temperature) + return status + + def get_name(self): + """ + Retrieves the name of the thermal device + Returns: + string: The name of the thermal device + """ + return self.THERMAL_LIST[self.index][0] + + def get_presence(self): + """ + Retrieves the presence of the device + Returns: + bool: True if device is present, False if not + """ + return True if self.get_temperature() > 0 else False + + def get_model(self): + """ + Retrieves the model number (or part number) of the device + Returns: + string: Model/part number of device + """ + return self.sensor_des + + def get_serial(self): + """ + Retrieves the serial number of the device + Returns: + string: Serial number of device + """ + return "Unknown" + + def get_status(self): + """ + Retrieves the operational status of the device + Returns: + A boolean value, True if device is operating properly, False if not + """ + return self.get_presence() + + def get_position_in_parent(self): + """ + Retrieves 1-based relative physical position in parent device. + Returns: + integer: The 1-based relative physical position in parent + device or -1 if cannot determine the position + """ + return (self.index + 1) + + def is_replaceable(self): + """ + Indicate whether this Thermal is replaceable. + Returns: + bool: True if it is replaceable. + """ + return False + + def get_minimum_recorded(self): + """ + Retrieves the minimum recorded temperature of thermal + Returns: + A float number, the minimum recorded temperature of thermal in Celsius + up to nearest thousandth of one degree Celsius, e.g. 30.125 + """ + tmp = self.get_temperature() + if tmp < self.minimum_thermal: + self.minimum_thermal = tmp + return self.minimum_thermal + + def get_maximum_recorded(self): + """ + Retrieves the maximum recorded temperature of thermal + Returns: + A float number, the maximum recorded temperature of thermal in Celsius + up to nearest thousandth of one degree Celsius, e.g. 30.125 + """ + tmp = self.get_temperature() + if tmp > self.maximum_thermal: + self.maximum_thermal = tmp + return self.maximum_thermal diff --git a/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/watchdog.py b/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/watchdog.py new file mode 100644 index 0000000000..35c55945de --- /dev/null +++ b/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/sonic_platform/watchdog.py @@ -0,0 +1,317 @@ +#!/usr/bin/env python + +############################################################################# +# +# Module contains an implementation of SONiC Platform Base API and +# provides the Watchdog information +# +############################################################################# + +import os + +try: + from sonic_platform_base.watchdog_base import WatchdogBase +except ImportError as e: + raise ImportError(str(e) + "- required module not found") + +""" ioctl constants """ +IO_WRITE = 0x40000000 +IO_READ = 0x80000000 +IO_READ_WRITE = 0xC0000000 +IO_SIZE_INT = 0x00040000 +IO_SIZE_40 = 0x00280000 +IO_TYPE_WATCHDOG = ord('W') << 8 + +WDR_INT = IO_READ | IO_SIZE_INT | IO_TYPE_WATCHDOG +WDR_40 = IO_READ | IO_SIZE_40 | IO_TYPE_WATCHDOG +WDWR_INT = IO_READ_WRITE | IO_SIZE_INT | IO_TYPE_WATCHDOG + +""" Watchdog ioctl commands """ +WDIOC_GETSUPPORT = 0 | WDR_40 +WDIOC_GETSTATUS = 1 | WDR_INT +WDIOC_GETBOOTSTATUS = 2 | WDR_INT +WDIOC_GETTEMP = 3 | WDR_INT +WDIOC_SETOPTIONS = 4 | WDR_INT +WDIOC_KEEPALIVE = 5 | WDR_INT +WDIOC_SETTIMEOUT = 6 | WDWR_INT +WDIOC_GETTIMEOUT = 7 | WDR_INT +WDIOC_SETPRETIMEOUT = 8 | WDWR_INT +WDIOC_GETPRETIMEOUT = 9 | WDR_INT +WDIOC_GETTIMELEFT = 10 | WDR_INT + +""" Watchdog status constants """ +WDIOS_DISABLECARD = 0x0001 +WDIOS_ENABLECARD = 0x0002 + +WDT_COMMON_ERROR = -1 +#WD_MAIN_IDENTITY = "iTCO_wdt" +WD_MAIN_IDENTITY = "t7132s_wdt" +WDT_SYSFS_PATH = "/sys/class/watchdog/" +DEV_STATE_PATH = "/sys/devices/platform/switchboard/CPLD1/dev_state" +WDT_MAX_PATH = "/sys/devices/platform/switchboard/CPLD1/wdt_max" +WDT_COUNT_PATH = "/sys/devices/platform/switchboard/CPLD1/wdt_count" + + +class Watchdog(WatchdogBase): + + def __init__(self): + self.watchdog = None + self.wdt_main_dev_name = None + self.armed = self.is_armed() + self.timeout = self._gettimeout() + + def _is_wd_main(self, dev): + """ + Checks watchdog identity + """ + identity = self._read_file( + "{}/{}/identity".format(WDT_SYSFS_PATH, dev)) + return identity == WD_MAIN_IDENTITY + + def _get_wdt(self): + """ + Retrieves watchdog device + """ + if self.watchdog is not None: + return + + wdt_main_dev_list = [dev for dev in os.listdir( + "/dev/") if dev.startswith("watchdog") and self._is_wd_main(dev)] + if not wdt_main_dev_list: + self.wdt_main_dev_name = None + return + self.wdt_main_dev_name = wdt_main_dev_list[0] + + watchdog_device_path = "/dev/{}".format(self.wdt_main_dev_name) + try: + self.watchdog = os.open(watchdog_device_path, os.O_RDWR) + except (FileNotFoundError, IOError, OSError): + self.watchdog = None + self.wdt_main_dev_name = None + except SystemExit: + pass + + return + + def _put_wdt(self): + """ + Release watchdog device + """ + if self.watchdog is not None: + os.close(self.watchdog) + self.watchdog = None + self.wdt_main_dev_name = None + + def _read_file(self, file_path): + """ + Read text file + """ + try: + with open(file_path, "r") as fd: + txt = fd.read() + except IOError: + return WDT_COMMON_ERROR + return txt.strip() + + def _enable(self): + """ + Turn on the watchdog timer + """ + try: + with open(DEV_STATE_PATH, "r+") as reg_file: + content = reg_file.readline().strip() + reg_value = int(content, 16) + bit_enable = 0x100 + reg_value_new = reg_value | bit_enable + reg_file.write(hex(reg_value_new)) + except IOError as e: + print("Error: unable to open file: %s" % str(e)) + + def _disable(self): + """ + Turn off the watchdog timer + """ + try: + with open(DEV_STATE_PATH, "r+") as reg_file: + content = reg_file.readline().strip() + reg_value = int(content, 16) + bit_enable = 0x100 + reg_value_new = reg_value & ~bit_enable + reg_file.write(hex(reg_value_new)) + except IOError as e: + print("Error: unable to open file: %s" % str(e)) + + def _keepalive(self): + """ + Keep alive watchdog timer + """ + self._disable() + self._enable() + + def _settimeout(self, seconds): + """ + Set watchdog timer timeout + @param seconds - timeout in seconds + @return is the actual set timeout + """ + if seconds > 65535: + seconds = 65535 + + try: + with open(WDT_MAX_PATH, "r+") as reg_file: + reg_value = seconds + reg_file.write(hex(reg_value)) + except IOError as e: + print("Error: unable to open file: %s" % str(e)) + + return seconds + + def _gettimeout(self): + """ + Get watchdog timeout + @return watchdog timeout + """ + seconds = 0 + try: + with open(WDT_MAX_PATH, "r+") as reg_file: + content = reg_file.readline().strip() + reg_value = int(content, 16) + seconds = reg_value + except IOError as e: + print("Error: unable to open file: %s" % str(e)) + + return seconds + + def _gettimeleft(self): + """ + Get time left before watchdog timer expires + @return time left in seconds + """ + try: + with open(WDT_MAX_PATH, "r+") as reg_file: + content = reg_file.readline().strip() + reg_value = int(content, 16) + state_seconds = reg_value + except IOError as e: + print("Error: unable to open file: %s" % str(e)) + + try: + with open(WDT_COUNT_PATH, "r+") as reg_file: + content = reg_file.readline().strip() + reg_value = int(content, 16) + count_seconds = reg_value + except IOError as e: + print("Error: unable to open file: %s" % str(e)) + + timeleft = state_seconds - count_seconds + if timeleft < 0: + timeleft = 0 + print("Error: incorrect counter: state={} count={}". + format(state_seconds, count_seconds)) + elif timeleft > 65535: + timeleft = 65535 + print("Error: incorrect counter: state={} count={}". + format(state_seconds, count_seconds)) + + return timeleft + + ################################################################# + + def arm(self, seconds): + """ + Arm the hardware watchdog with a timeout of seconds. + If the watchdog is currently armed, calling this function will + simply reset the timer to the provided value. If the underlying + hardware does not support the value provided in , this + method should arm the watchdog with the *next greater* available + value. + Returns: + An integer specifying the *actual* number of seconds the watchdog + was armed with. On failure returns -1. + """ + ret = WDT_COMMON_ERROR + if seconds < 0: + return ret + if seconds > 65535: + return ret + + try: + self._disable() + if self._gettimeout() != seconds: + self.timeout = self._settimeout(seconds) + self._enable() + self.armed = True + ret = self.timeout + except IOError as e: + pass + + return ret + + def disarm(self): + """ + Disarm the hardware watchdog + Returns: + A boolean, True if watchdog is disarmed successfully, False if not + """ + disarmed = False + + if self.is_armed(): + try: + self._disable() + self.armed = False + disarmed = True + except IOError: + pass + + return disarmed + + def is_armed(self): + """ + Retrieves the armed state of the hardware watchdog. + Returns: + A boolean, True if watchdog is armed, False if not + """ + """ + We always get the HW status because all new instance have + it's own self.armed. And only the instance had called arm() + has self.armed = True if self.armed is a class variable. + """ + # Read status + try: + with open(DEV_STATE_PATH) as reg_file: + content = reg_file.readline().rstrip() + reg_value = int(content, 16) + except IOError as e: + print("Error: unable to open file: %s" % str(e)) + return False + + bit_enable = 0x100 + if reg_value & bit_enable: + return True + + return False + + def get_remaining_time(self): + """ + If the watchdog is armed, retrieve the number of seconds remaining on + the watchdog timer + Returns: + An integer specifying the number of seconds remaining on thei + watchdog timer. If the watchdog is not armed, returns -1. + """ + timeleft = WDT_COMMON_ERROR + + if self.is_armed(): + try: + timeleft = self._gettimeleft() + except IOError: + pass + + return timeleft + + def __del__(self): + """ + Close watchdog + """ + if self.watchdog is not None: + os.close(self.watchdog) diff --git a/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/systemd/platform-modules-sse-t7132s.service b/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/systemd/platform-modules-sse-t7132s.service new file mode 100644 index 0000000000..71d2b0d98c --- /dev/null +++ b/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/systemd/platform-modules-sse-t7132s.service @@ -0,0 +1,14 @@ +[Unit] +Description=SuperMicro SSE-T7132S Platform modules +Before=pmon.service +DefaultDependencies=no + +[Service] +Type=oneshot +ExecStart=/usr/local/bin/platform.sh init +ExecStop=/usr/local/bin/platform.sh deinit +RemainAfterExit=yes + +[Install] +WantedBy=multi-user.target + diff --git a/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/systemd/sysled.service b/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/systemd/sysled.service new file mode 100644 index 0000000000..cde02505d4 --- /dev/null +++ b/platform/innovium/sonic-platform-modules-supermicro/sse-t7132s/systemd/sysled.service @@ -0,0 +1,15 @@ +[Unit] +Description=Set system LED before reboot/poweroff/halt +DefaultDependencies=no +#Conflicts=reboot.target +Before=poweroff.target halt.target reboot.target kexec.target shutdown.target +#Requires=poweroff.target + +[Service] +Type=oneshot +ExecStart=/usr/local/bin/sysledctl.py start +#ExecStop=/usr/local/bin/sysledctl.py stop +RemainAfterExit=yes + +[Install] +WantedBy=poweroff.target halt.target shutdown.target reboot.target kexec.target