The SFF-8636 decoder reads the alarm and warning thresholds
from page 03h (offsets 0x200 to 0x247) unconditionally,
but they are printed only if the EEPROM data is 640 bytes long.

The telemetry command /ethdev/module_eeprom allocates exactly
the length reported by the driver, and several drivers report
256 bytes for QSFP modules, for example i40e for SFF-8436
and bnxt for flat memory QSFP28.
On such ports, the command reads past the end of the heap buffer.

Read the thresholds only when they are going to be printed.

Fixes: c42754fd581a ("ethdev: support SFF-8636 module telemetry")
Cc: [email protected]

Signed-off-by: Roman Khromenok <[email protected]>
---
v3: new patch, split from the length checks to be backported

 .mailmap              |  1 +
 lib/ethdev/sff_8636.c | 52 ++++++++++++++++++++++---------------------
 2 files changed, 28 insertions(+), 25 deletions(-)

diff --git a/.mailmap b/.mailmap
index 57f7a9f87a..45d4e92fbd 100644
--- a/.mailmap
+++ b/.mailmap
@@ -1445,6 +1445,7 @@ Romain Delhomel <[email protected]>
 Roman Dementiev <[email protected]>
 Roman Fridlyand <[email protected]>
 Roman Kapl <[email protected]>
+Roman Khromenok <[email protected]>
 Roman Korynkevych <[email protected]>
 Roman Storozhenko <[email protected]>
 Roman Zhukov <[email protected]> <[email protected]>
diff --git a/lib/ethdev/sff_8636.c b/lib/ethdev/sff_8636.c
index 6b65f47efe..9dfff41a3b 100644
--- a/lib/ethdev/sff_8636.c
+++ b/lib/ethdev/sff_8636.c
@@ -600,34 +600,36 @@ static void sff_8636_dom_parse(const uint8_t *data, 
struct sff_diags *sd)
 {
        int i = 0;
 
-       /* Monitoring Thresholds for Alarms and Warnings */
        sd->sfp_voltage[SFF_MCURR] = SFF_OFFSET_TO_U16(SFF_8636_VCC_CURR);
-       sd->sfp_voltage[SFF_HALRM] = SFF_OFFSET_TO_U16(SFF_8636_VCC_HALRM);
-       sd->sfp_voltage[SFF_LALRM] = SFF_OFFSET_TO_U16(SFF_8636_VCC_LALRM);
-       sd->sfp_voltage[SFF_HWARN] = SFF_OFFSET_TO_U16(SFF_8636_VCC_HWARN);
-       sd->sfp_voltage[SFF_LWARN] = SFF_OFFSET_TO_U16(SFF_8636_VCC_LWARN);
-
        sd->sfp_temp[SFF_MCURR] = SFF_8636_OFFSET_TO_TEMP(SFF_8636_TEMP_CURR);
-       sd->sfp_temp[SFF_HALRM] = SFF_8636_OFFSET_TO_TEMP(SFF_8636_TEMP_HALRM);
-       sd->sfp_temp[SFF_LALRM] = SFF_8636_OFFSET_TO_TEMP(SFF_8636_TEMP_LALRM);
-       sd->sfp_temp[SFF_HWARN] = SFF_8636_OFFSET_TO_TEMP(SFF_8636_TEMP_HWARN);
-       sd->sfp_temp[SFF_LWARN] = SFF_8636_OFFSET_TO_TEMP(SFF_8636_TEMP_LWARN);
-
-       sd->bias_cur[SFF_HALRM] = SFF_OFFSET_TO_U16(SFF_8636_TX_BIAS_HALRM);
-       sd->bias_cur[SFF_LALRM] = SFF_OFFSET_TO_U16(SFF_8636_TX_BIAS_LALRM);
-       sd->bias_cur[SFF_HWARN] = SFF_OFFSET_TO_U16(SFF_8636_TX_BIAS_HWARN);
-       sd->bias_cur[SFF_LWARN] = SFF_OFFSET_TO_U16(SFF_8636_TX_BIAS_LWARN);
-
-       sd->tx_power[SFF_HALRM] = SFF_OFFSET_TO_U16(SFF_8636_TX_PWR_HALRM);
-       sd->tx_power[SFF_LALRM] = SFF_OFFSET_TO_U16(SFF_8636_TX_PWR_LALRM);
-       sd->tx_power[SFF_HWARN] = SFF_OFFSET_TO_U16(SFF_8636_TX_PWR_HWARN);
-       sd->tx_power[SFF_LWARN] = SFF_OFFSET_TO_U16(SFF_8636_TX_PWR_LWARN);
-
-       sd->rx_power[SFF_HALRM] = SFF_OFFSET_TO_U16(SFF_8636_RX_PWR_HALRM);
-       sd->rx_power[SFF_LALRM] = SFF_OFFSET_TO_U16(SFF_8636_RX_PWR_LALRM);
-       sd->rx_power[SFF_HWARN] = SFF_OFFSET_TO_U16(SFF_8636_RX_PWR_HWARN);
-       sd->rx_power[SFF_LWARN] = SFF_OFFSET_TO_U16(SFF_8636_RX_PWR_LWARN);
 
+       /* Monitoring Thresholds for Alarms and Warnings are in page 03h */
+       if (sd->supports_alarms) {
+               sd->sfp_voltage[SFF_HALRM] = 
SFF_OFFSET_TO_U16(SFF_8636_VCC_HALRM);
+               sd->sfp_voltage[SFF_LALRM] = 
SFF_OFFSET_TO_U16(SFF_8636_VCC_LALRM);
+               sd->sfp_voltage[SFF_HWARN] = 
SFF_OFFSET_TO_U16(SFF_8636_VCC_HWARN);
+               sd->sfp_voltage[SFF_LWARN] = 
SFF_OFFSET_TO_U16(SFF_8636_VCC_LWARN);
+
+               sd->sfp_temp[SFF_HALRM] = 
SFF_8636_OFFSET_TO_TEMP(SFF_8636_TEMP_HALRM);
+               sd->sfp_temp[SFF_LALRM] = 
SFF_8636_OFFSET_TO_TEMP(SFF_8636_TEMP_LALRM);
+               sd->sfp_temp[SFF_HWARN] = 
SFF_8636_OFFSET_TO_TEMP(SFF_8636_TEMP_HWARN);
+               sd->sfp_temp[SFF_LWARN] = 
SFF_8636_OFFSET_TO_TEMP(SFF_8636_TEMP_LWARN);
+
+               sd->bias_cur[SFF_HALRM] = 
SFF_OFFSET_TO_U16(SFF_8636_TX_BIAS_HALRM);
+               sd->bias_cur[SFF_LALRM] = 
SFF_OFFSET_TO_U16(SFF_8636_TX_BIAS_LALRM);
+               sd->bias_cur[SFF_HWARN] = 
SFF_OFFSET_TO_U16(SFF_8636_TX_BIAS_HWARN);
+               sd->bias_cur[SFF_LWARN] = 
SFF_OFFSET_TO_U16(SFF_8636_TX_BIAS_LWARN);
+
+               sd->tx_power[SFF_HALRM] = 
SFF_OFFSET_TO_U16(SFF_8636_TX_PWR_HALRM);
+               sd->tx_power[SFF_LALRM] = 
SFF_OFFSET_TO_U16(SFF_8636_TX_PWR_LALRM);
+               sd->tx_power[SFF_HWARN] = 
SFF_OFFSET_TO_U16(SFF_8636_TX_PWR_HWARN);
+               sd->tx_power[SFF_LWARN] = 
SFF_OFFSET_TO_U16(SFF_8636_TX_PWR_LWARN);
+
+               sd->rx_power[SFF_HALRM] = 
SFF_OFFSET_TO_U16(SFF_8636_RX_PWR_HALRM);
+               sd->rx_power[SFF_LALRM] = 
SFF_OFFSET_TO_U16(SFF_8636_RX_PWR_LALRM);
+               sd->rx_power[SFF_HWARN] = 
SFF_OFFSET_TO_U16(SFF_8636_RX_PWR_HWARN);
+               sd->rx_power[SFF_LWARN] = 
SFF_OFFSET_TO_U16(SFF_8636_RX_PWR_LWARN);
+       }
 
        /* Channel Specific Data */
        for (i = 0; i < SFF_MAX_CHANNEL_NUM; i++) {
-- 
2.47.3

Reply via email to