git: 2f3a1ebba812 - main - if_bnxt: add CAGR interrupt coalescing tick-resolution support
- Go to: [ bottom of page ] [ top of archives ] [ this month ]
Date: Fri, 09 Oct 2026 10:12:32 UTC
The branch main has been updated by ssaxena:
URL: https://cgit.FreeBSD.org/src/commit/?id=2f3a1ebba81266b5f21640f88d73e03415cf13be
commit 2f3a1ebba81266b5f21640f88d73e03415cf13be
Author: Sumit Saxena <sumit.saxena@broadcom.com>
AuthorDate: 2026-07-29 08:36:18 +0000
Commit: Sumit Saxena <ssaxena@FreeBSD.org>
CommitDate: 2026-10-09 08:24:42 +0000
if_bnxt: add CAGR interrupt coalescing tick-resolution support
Add the P7 CAGR (Completion AGgregation Ring) NQ-aggregation timer
tick-resolution knob, programmed via a direct GRC-window register
write, with a new dev.bnxt.<unit>.cagr_tick_res read-only tunable.
This is independent of the existing per-ring AGGINT_PARAMS coalescing.
Reviewed by: gallatin
MFC after: 2 weeks
Sponsored by: Broadcom Inc.
Differential Revision: https://reviews.freebsd.org/D58598
---
sys/dev/bnxt/bnxt_en/bnxt.h | 8 ++++++++
sys/dev/bnxt/bnxt_en/bnxt_sysctl.c | 27 +++++++++++++++++++++++++++
sys/dev/bnxt/bnxt_en/if_bnxt.c | 32 ++++++++++++++++++++++++++++++++
3 files changed, 67 insertions(+)
diff --git a/sys/dev/bnxt/bnxt_en/bnxt.h b/sys/dev/bnxt/bnxt_en/bnxt.h
index 98f8c1d3f5fa..35f1b9e97a00 100644
--- a/sys/dev/bnxt/bnxt_en/bnxt.h
+++ b/sys/dev/bnxt/bnxt_en/bnxt.h
@@ -1423,6 +1423,14 @@ struct bnxt_softc {
struct bnxt_ptp_cfg *ptp_cfg;
bool rx_ts_enabled;
+
+#define BNXT_CAGR_CQCOAL_OFFSET 0xc00
+#define BNXT_CAGR_NQAGG_MAXTIMER 0x5930000
+#define BNXT_CAGR_TICK_RES_DEFAULT 0x2
+#define BNXT_CAGR_TICK_RES_MIN 0x0
+#define BNXT_CAGR_TICK_RES_MAX 0x4
+#define BNXT_CAGR_TICK_RES_OFFSET 16
+ uint32_t cagr_tick_res;
};
struct bnxt_filter_info {
diff --git a/sys/dev/bnxt/bnxt_en/bnxt_sysctl.c b/sys/dev/bnxt/bnxt_en/bnxt_sysctl.c
index 88afc83edd9d..c8a0f1962a13 100644
--- a/sys/dev/bnxt/bnxt_en/bnxt_sysctl.c
+++ b/sys/dev/bnxt/bnxt_en/bnxt_sysctl.c
@@ -1556,6 +1556,30 @@ bnxt_set_coal_tx_frames_irq(SYSCTL_HANDLER_ARGS) {
return rc;
}
+static int
+bnxt_set_cagr_tick_res(SYSCTL_HANDLER_ARGS) {
+ struct bnxt_softc *softc = arg1;
+ int rc;
+ int val;
+
+ if (softc == NULL)
+ return EBUSY;
+
+ val = softc->cagr_tick_res;
+
+ rc = sysctl_handle_int(oidp, &val, 0, req);
+ if (rc || !req->newptr)
+ return rc;
+
+ if (val < BNXT_CAGR_TICK_RES_MIN ||
+ val > BNXT_CAGR_TICK_RES_MAX)
+ return EINVAL;
+
+ softc->cagr_tick_res = val;
+
+ return rc;
+}
+
static
void simulate_reset(struct bnxt_softc *bp, char *fwcli_string)
{
@@ -1648,6 +1672,9 @@ bnxt_create_config_sysctls_pre(struct bnxt_softc *softc)
CTLTYPE_INT | CTLFLAG_RWTUN | CTLFLAG_MPSAFE, softc, 0,
bnxt_set_coal_tx_frames_irq, "I",
"interrupt coalescing Tx Frames IRQ");
+ SYSCTL_ADD_PROC(ctx, children, OID_AUTO, "cagr_tick_res",
+ CTLTYPE_INT | CTLFLAG_RDTUN | CTLFLAG_MPSAFE, softc, 0,
+ bnxt_set_cagr_tick_res, "I", "CAGR tick resolution");
SYSCTL_ADD_U32(ctx, children, OID_AUTO, "flags", CTLFLAG_RD,
&softc->flags, 0, "flags");
SYSCTL_ADD_U64(ctx, children, OID_AUTO, "fw_cap", CTLFLAG_RD,
diff --git a/sys/dev/bnxt/bnxt_en/if_bnxt.c b/sys/dev/bnxt/bnxt_en/if_bnxt.c
index 044ab619c399..188311b2d7d4 100644
--- a/sys/dev/bnxt/bnxt_en/if_bnxt.c
+++ b/sys/dev/bnxt/bnxt_en/if_bnxt.c
@@ -2065,6 +2065,26 @@ static inline void __bnxt_map_fw_health_reg(struct bnxt_softc *bp, u32 reg)
BNXT_HWRM_BAR_IDX, reg & BNXT_GRC_BASE_MASK);
}
+static void
+bnxt_set_cqcoal_tick_res(struct bnxt_softc *bp)
+{
+ u32 val = 0;
+ u32 cagr_addr = BNXT_GRCPF_REG_WINDOW_BASE_OUT + BNXT_CAGR_CQCOAL_OFFSET;
+
+ if (!BNXT_CHIP_P7(bp))
+ return;
+
+ writel_fbsd(bp, BNXT_GRCPF_REG_WINDOW_BASE_OUT, BNXT_HWRM_BAR_IDX,
+ BNXT_CAGR_NQAGG_MAXTIMER);
+ val = readl_fbsd(bp, cagr_addr, BNXT_HWRM_BAR_IDX);
+
+ /* Clear out CAGR tick resolution bits(16-19), before writing new value */
+ val &= ~(0xf << BNXT_CAGR_TICK_RES_OFFSET);
+
+ writel_fbsd(bp, cagr_addr, BNXT_HWRM_BAR_IDX,
+ (val | bp->cagr_tick_res << BNXT_CAGR_TICK_RES_OFFSET));
+}
+
static int bnxt_map_fw_health_regs(struct bnxt_softc *bp)
{
struct bnxt_fw_health *fw_health = bp->fw_health;
@@ -2203,6 +2223,12 @@ static bool bnxt_fw_reset_timeout(struct bnxt_softc *bp)
static int bnxt_open(struct bnxt_softc *bp)
{
int rc = 0;
+
+ /* A function/chip reset drops the CAGR tick-resolution register
+ * programmed in bnxt_attach_pre(); restore it before we start
+ * relying on interrupt coalescing again. */
+ bnxt_set_cqcoal_tick_res(bp);
+
if (BNXT_PF(bp))
rc = bnxt_hwrm_nvm_get_dev_info(bp, &bp->nvm_info->mfg_id,
&bp->nvm_info->device_id, &bp->nvm_info->sector_size,
@@ -2886,6 +2912,10 @@ bnxt_attach_pre(if_ctx_t ctx)
HWRM_VNIC_RSS_CFG_INPUT_HASH_TYPE_IPV6 |
HWRM_VNIC_RSS_CFG_INPUT_HASH_TYPE_TCP_IPV6 |
HWRM_VNIC_RSS_CFG_INPUT_HASH_TYPE_UDP_IPV6;
+
+ if (BNXT_CHIP_P7(softc))
+ softc->cagr_tick_res = BNXT_CAGR_TICK_RES_DEFAULT;
+
rc = bnxt_create_config_sysctls_pre(softc);
if (rc)
goto failed;
@@ -2930,6 +2960,8 @@ bnxt_attach_pre(if_ctx_t ctx)
snprintf(softc->board_partno, sizeof(softc->board_partno), "%s", part_num);
}
+ bnxt_set_cqcoal_tick_res(softc);
+
return (rc);