The branch main has been updated by zlei:

URL: 
https://cgit.FreeBSD.org/src/commit/?id=3de231b4d956f7b9c22e31f75805030a417f7bf3

commit 3de231b4d956f7b9c22e31f75805030a417f7bf3
Author:     Zhenlei Huang <z...@freebsd.org>
AuthorDate: 2025-02-14 10:38:29 +0000
Commit:     Zhenlei Huang <z...@freebsd.org>
CommitDate: 2025-02-14 10:38:29 +0000

    bnxt_en: Retrieve maximum of 128 APP TLVs
    
    It appears that the maximum number of APP TLVs supported by the hardware
    is 128 according to D45005. Well Daniel Porsch reported an issue PR284073
    which shows that the number can exceed the limit, causing out of bound
    write to on-stack allocated variable app[128] and the kernel panics.
    
    Limit to 128 while retrieving APP TLVs.
    
    PR:             284073
    Reviewed by:    markj
    Tested by:      Daniel Porsch <daniel.por...@loopia.se>
    Fixes:  35b53f8c989f bnxt_en: Add PFC, ETS & App TLVs protocols support
    MFC after:      1 week
    Differential Revision:  https://reviews.freebsd.org/D48589
---
 sys/dev/bnxt/bnxt_en/bnxt.h        |  3 ++-
 sys/dev/bnxt/bnxt_en/bnxt_dcb.c    | 17 ++++++++++-------
 sys/dev/bnxt/bnxt_en/bnxt_mgmt.c   |  1 +
 sys/dev/bnxt/bnxt_en/bnxt_sysctl.c |  2 +-
 4 files changed, 14 insertions(+), 9 deletions(-)

diff --git a/sys/dev/bnxt/bnxt_en/bnxt.h b/sys/dev/bnxt/bnxt_en/bnxt.h
index e4f866807070..b0c3a8913622 100644
--- a/sys/dev/bnxt/bnxt_en/bnxt.h
+++ b/sys/dev/bnxt/bnxt_en/bnxt.h
@@ -1310,6 +1310,7 @@ int bnxt_dcb_ieee_getpfc(struct bnxt_softc *softc, struct 
bnxt_ieee_pfc *pfc);
 int bnxt_dcb_ieee_setpfc(struct bnxt_softc *softc, struct bnxt_ieee_pfc *pfc);
 int bnxt_dcb_ieee_setapp(struct bnxt_softc *softc, struct bnxt_dcb_app *app);
 int bnxt_dcb_ieee_delapp(struct bnxt_softc *softc, struct bnxt_dcb_app *app);
-int bnxt_dcb_ieee_listapp(struct bnxt_softc *softc, struct bnxt_dcb_app *app, 
int *num_inputs);
+int bnxt_dcb_ieee_listapp(struct bnxt_softc *softc, struct bnxt_dcb_app *app,
+    size_t nitems, int *num_inputs);
 
 #endif /* _BNXT_H */
diff --git a/sys/dev/bnxt/bnxt_en/bnxt_dcb.c b/sys/dev/bnxt/bnxt_en/bnxt_dcb.c
index e1e0581d3c24..e0643f200021 100644
--- a/sys/dev/bnxt/bnxt_en/bnxt_dcb.c
+++ b/sys/dev/bnxt/bnxt_en/bnxt_dcb.c
@@ -313,7 +313,8 @@ bnxt_hwrm_queue_pfc_qcfg(struct bnxt_softc *softc, struct 
bnxt_ieee_pfc *pfc)
 }
 
 static int
-bnxt_hwrm_get_dcbx_app(struct bnxt_softc *softc, struct bnxt_dcb_app *app, int 
*num_inputs)
+bnxt_hwrm_get_dcbx_app(struct bnxt_softc *softc, struct bnxt_dcb_app *app,
+    size_t nitems, int *num_inputs)
 {
        struct hwrm_fw_get_structured_data_input get = {0};
        struct hwrm_struct_data_dcbx_app *fw_app;
@@ -350,7 +351,7 @@ bnxt_hwrm_get_dcbx_app(struct bnxt_softc *softc, struct 
bnxt_dcb_app *app, int *
        }
 
        n = data->count;
-       for (i = 0; i < n; i++, fw_app++) {
+       for (i = 0; i < n && *num_inputs < nitems; i++, fw_app++) {
                app[*num_inputs].priority = fw_app->priority;
                app[*num_inputs].protocol = htobe16(fw_app->protocol_id);
                app[*num_inputs].selector = fw_app->protocol_selector;
@@ -472,7 +473,8 @@ bnxt_hwrm_queue_dscp_qcaps(struct bnxt_softc *softc)
 }
 
 static int
-bnxt_hwrm_queue_dscp2pri_qcfg(struct bnxt_softc *softc, struct bnxt_dcb_app 
*app, int *num_inputs)
+bnxt_hwrm_queue_dscp2pri_qcfg(struct bnxt_softc *softc, struct bnxt_dcb_app 
*app,
+    size_t nitems, int *num_inputs)
 {
        struct hwrm_queue_dscp2pri_qcfg_input req = {0};
        struct hwrm_queue_dscp2pri_qcfg_output *resp =
@@ -503,7 +505,7 @@ bnxt_hwrm_queue_dscp2pri_qcfg(struct bnxt_softc *softc, 
struct bnxt_dcb_app *app
                goto end;
 
        entry_cnt =  le16toh(resp->entry_cnt);
-       for (i = 0; i < entry_cnt; i++) {
+       for (i = 0; i < entry_cnt && *num_inputs < nitems; i++) {
                app[*num_inputs].priority = dscp2pri[i].pri;
                app[*num_inputs].protocol = dscp2pri[i].dscp;
                app[*num_inputs].selector = BNXT_IEEE_8021QAZ_APP_SEL_DSCP;
@@ -774,10 +776,11 @@ bnxt_dcb_ieee_delapp(struct bnxt_softc *softc, struct 
bnxt_dcb_app *app)
 }
 
 int
-bnxt_dcb_ieee_listapp(struct bnxt_softc *softc, struct bnxt_dcb_app *app, int 
*num_inputs)
+bnxt_dcb_ieee_listapp(struct bnxt_softc *softc, struct bnxt_dcb_app *app,
+    size_t nitems, int *num_inputs)
 {
-       bnxt_hwrm_get_dcbx_app(softc, app, num_inputs);
-       bnxt_hwrm_queue_dscp2pri_qcfg(softc, app, num_inputs);
+       bnxt_hwrm_get_dcbx_app(softc, app, nitems, num_inputs);
+       bnxt_hwrm_queue_dscp2pri_qcfg(softc, app, nitems, num_inputs);
 
        return 0;
 }
diff --git a/sys/dev/bnxt/bnxt_en/bnxt_mgmt.c b/sys/dev/bnxt/bnxt_en/bnxt_mgmt.c
index 72704c3db452..bbc12b96d8c6 100644
--- a/sys/dev/bnxt/bnxt_en/bnxt_mgmt.c
+++ b/sys/dev/bnxt/bnxt_en/bnxt_mgmt.c
@@ -139,6 +139,7 @@ bnxt_mgmt_process_dcb(struct cdev *dev, u_long cmd, caddr_t 
data,
                break;
        case BNXT_MGMT_DCB_LIST_APP:
                bnxt_dcb_ieee_listapp(softc, &mgmt_dcb.req.app_tlv.app[0],
+                                     nitems(mgmt_dcb.req.app_tlv.app),
                                      &mgmt_dcb.req.app_tlv.num_app);
                break;
        default:
diff --git a/sys/dev/bnxt/bnxt_en/bnxt_sysctl.c 
b/sys/dev/bnxt/bnxt_en/bnxt_sysctl.c
index 012903ce21b3..45524aa1d076 100644
--- a/sys/dev/bnxt/bnxt_en/bnxt_sysctl.c
+++ b/sys/dev/bnxt/bnxt_en/bnxt_sysctl.c
@@ -1952,7 +1952,7 @@ bnxt_dcb_list_app(SYSCTL_HANDLER_ARGS)
        if (!buf)
                return ENOMEM;
 
-       bnxt_dcb_ieee_listapp(softc, app, &num_inputs);
+       bnxt_dcb_ieee_listapp(softc, app, nitems(app), &num_inputs);
        bnxt_app_tlv_get_string(softc, buf, app, num_inputs);
 
        rc = sysctl_handle_string(oidp, buf, BNXT_APP_TLV_STR_LEN, req);

Reply via email to