| Seq | Timestamp | Type | Name | Duration |
|---|---|---|---|---|
| 0/0 | 2026/07/25 11:38 | flow | patch-triage |
0mArgs:null Results: {
"EnableConfigs": null,
"FocusSymbols": [],
"Reasoning": "The patch modifies the Marvell OcteonTX2 network driver, which is a vendor-specific hardware driver. This hardware is not emulated in standard QEMU or GCE environments, making the code unreachable during fuzzing.",
"WorthFuzzing": false
} |
| 1/1 | 2026/07/25 11:38 | action | read-patch-diff |
0mArgs:null Results: {
"PatchDiff": "commit b9a2d8bba7be908f711b861fd0183fc984815de2\nAuthor: syz-cluster \u003ctriage@syzkaller.com\u003e\nDate: Sat Jul 25 11:38:05 2026 +0000\n\n syz-cluster: applied patch under review\n\ndiff --git a/drivers/net/ethernet/marvell/octeontx2/af/rvu_nix.c b/drivers/net/ethernet/marvell/octeontx2/af/rvu_nix.c\nindex 78667a0977c013..5ed6c225bd7352 100644\n--- a/drivers/net/ethernet/marvell/octeontx2/af/rvu_nix.c\n+++ b/drivers/net/ethernet/marvell/octeontx2/af/rvu_nix.c\n@@ -323,8 +323,12 @@ static bool is_valid_txschq(struct rvu *rvu, int blkaddr,\n \t\t\treturn true;\n \t}\n \n-\tif (map_func != pcifunc)\n+\tif (map_func != pcifunc) {\n+\t\tdev_err(rvu-\u003edev,\n+\t\t\t\"pcifunc %x map pcifunc %x not equal, lvl=%u schq=%u\\n\",\n+\t\t\tpcifunc, map_func, lvl, schq);\n \t\treturn false;\n+\t}\n \n \treturn true;\n }\ndiff --git a/drivers/net/ethernet/marvell/octeontx2/nic/otx2_common.c b/drivers/net/ethernet/marvell/octeontx2/nic/otx2_common.c\nindex ca73a94db79436..b0b9e273e06c3e 100644\n--- a/drivers/net/ethernet/marvell/octeontx2/nic/otx2_common.c\n+++ b/drivers/net/ethernet/marvell/octeontx2/nic/otx2_common.c\n@@ -614,6 +614,76 @@ void otx2_get_mac_from_af(struct net_device *netdev)\n }\n EXPORT_SYMBOL(otx2_get_mac_from_af);\n \n+int otx2_nix_tm_clear_queue_shaper(struct otx2_nic *pfvf)\n+{\n+\tstruct mbox *mbox = \u0026pfvf-\u003embox;\n+\tstruct nix_txschq_config *req;\n+\tint err, smq;\n+\n+\tsmq = otx2_get_smq_idx(pfvf, 0);\n+\n+\tmutex_lock(\u0026mbox-\u003elock);\n+\treq = otx2_mbox_alloc_msg_nix_txschq_cfg(mbox);\n+\tif (!req) {\n+\t\tmutex_unlock(\u0026mbox-\u003elock);\n+\t\treturn -ENOMEM;\n+\t}\n+\n+\treq-\u003elvl = NIX_TXSCH_LVL_MDQ;\n+\treq-\u003enum_regs = 2;\n+\n+\treq-\u003ereg[0] = NIX_AF_MDQX_PIR(smq);\n+\treq-\u003eregval[0] = 0;\n+\n+\treq-\u003ereg[1] = NIX_AF_MDQX_CIR(smq);\n+\treq-\u003eregval[1] = 0;\n+\n+\terr = otx2_sync_mbox_msg(mbox);\n+\tmutex_unlock(\u0026mbox-\u003elock);\n+\treturn err;\n+}\n+\n+int otx2_nix_tm_set_queue_shaper(struct otx2_nic *pfvf,\n+\t\t\t\t int txq, u64 minrate, u64 maxrate)\n+{\n+\tstruct mbox *mbox = \u0026pfvf-\u003embox;\n+\tstruct nix_txschq_config *req;\n+\tint err, smq, n = 0;\n+\tu64 rate;\n+\n+\tif (!maxrate \u0026\u0026 !minrate)\n+\t\treturn 0;\n+\n+\tsmq = otx2_get_smq_idx(pfvf, txq);\n+\n+\tmutex_lock(\u0026mbox-\u003elock);\n+\treq = otx2_mbox_alloc_msg_nix_txschq_cfg(mbox);\n+\tif (!req) {\n+\t\tmutex_unlock(\u0026mbox-\u003elock);\n+\t\treturn -ENOMEM;\n+\t}\n+\n+\treq-\u003elvl = NIX_TXSCH_LVL_MDQ;\n+\n+\tif (maxrate) {\n+\t\treq-\u003ereg[n] = NIX_AF_MDQX_PIR(smq);\n+\t\trate = otx2_convert_rate(maxrate);\n+\t\treq-\u003eregval[n] = otx2_get_txschq_rate_regval(pfvf, rate, 0);\n+\t\tn++;\n+\t}\n+\tif (minrate) {\n+\t\treq-\u003ereg[n] = NIX_AF_MDQX_CIR(smq);\n+\t\trate = otx2_convert_rate(minrate);\n+\t\treq-\u003eregval[n] = otx2_get_txschq_rate_regval(pfvf, rate, 0);\n+\t\tn++;\n+\t}\n+\treq-\u003enum_regs = n;\n+\n+\terr = otx2_sync_mbox_msg(mbox);\n+\tmutex_unlock(\u0026mbox-\u003elock);\n+\treturn err;\n+}\n+\n int otx2_txschq_config(struct otx2_nic *pfvf, int lvl, int prio, bool txschq_for_pfc)\n {\n \tu16 (*schq_list)[MAX_TXSCHQ_PER_FUNC];\n@@ -650,7 +720,11 @@ int otx2_txschq_config(struct otx2_nic *pfvf, int lvl, int prio, bool txschq_for\n \t\t\t\t\t\t(u64)hw-\u003esmq_link_type);\n \t\treq-\u003enum_regs++;\n \t\t/* MDQ config */\n-\t\tparent = schq_list[NIX_TXSCH_LVL_TL4][prio];\n+\t\tif (pfvf-\u003eflags \u0026 OTX2_FLAG_PER_Q_RATE_LIMIT_ENABLED)\n+\t\t\tparent = schq_list[NIX_TXSCH_LVL_TL4][0];\n+\t\telse\n+\t\t\tparent = schq_list[NIX_TXSCH_LVL_TL4][prio];\n+\n \t\treq-\u003ereg[1] = NIX_AF_MDQX_PARENT(schq);\n \t\treq-\u003eregval[1] = parent \u003c\u003c 16;\n \t\treq-\u003enum_regs++;\n@@ -778,6 +852,9 @@ int otx2_txsch_alloc(struct otx2_nic *pfvf)\n \t\treq-\u003eschq[NIX_TXSCH_LVL_TL4] = chan_cnt;\n \t}\n \n+\tif (pfvf-\u003eflags \u0026 OTX2_FLAG_PER_Q_RATE_LIMIT_ENABLED)\n+\t\treq-\u003eschq[NIX_TXSCH_LVL_SMQ] = pfvf-\u003ehw.non_qos_queues;\n+\n \trc = otx2_sync_mbox_msg(\u0026pfvf-\u003embox);\n \tif (rc)\n \t\treturn rc;\ndiff --git a/drivers/net/ethernet/marvell/octeontx2/nic/otx2_common.h b/drivers/net/ethernet/marvell/octeontx2/nic/otx2_common.h\nindex eecee612b7b2c9..65687840d005f8 100644\n--- a/drivers/net/ethernet/marvell/octeontx2/nic/otx2_common.h\n+++ b/drivers/net/ethernet/marvell/octeontx2/nic/otx2_common.h\n@@ -512,6 +512,7 @@ struct otx2_nic {\n #define OTX2_FLAG_REP_MODE_ENABLED\t\t BIT_ULL(18)\n #define OTX2_FLAG_PORT_UP\t\t\tBIT_ULL(19)\n #define OTX2_FLAG_IPSEC_OFFLOAD_ENABLED\t\tBIT_ULL(20)\n+#define OTX2_FLAG_PER_Q_RATE_LIMIT_ENABLED\tBIT_ULL(21)\n \tu64\t\t\tflags;\n \tu64\t\t\t*cq_op_addr;\n \n@@ -1246,6 +1247,9 @@ dma_addr_t otx2_dma_map_skb_frag(struct otx2_nic *pfvf,\n \t\t\t\t struct sk_buff *skb, int seg, int *len);\n void otx2_dma_unmap_skb_frags(struct otx2_nic *pfvf, struct sg_list *sg);\n int otx2_read_free_sqe(struct otx2_nic *pfvf, u16 qidx);\n+int otx2_nix_tm_set_queue_shaper(struct otx2_nic *pfvf, int txq,\n+\t\t\t\t u64 minrate, u64 maxrate);\n+int otx2_nix_tm_clear_queue_shaper(struct otx2_nic *pfvf);\n void otx2_queue_vf_work(struct mbox *mw, struct workqueue_struct *mbox_wq,\n \t\t\tint first, int mdevs, u64 intr);\n int otx2_del_mcam_flow_entry(struct otx2_nic *nic, u16 entry,\ndiff --git a/drivers/net/ethernet/marvell/octeontx2/nic/otx2_tc.c b/drivers/net/ethernet/marvell/octeontx2/nic/otx2_tc.c\nindex 40162b08014dd6..bce8a866b4957f 100644\n--- a/drivers/net/ethernet/marvell/octeontx2/nic/otx2_tc.c\n+++ b/drivers/net/ethernet/marvell/octeontx2/nic/otx2_tc.c\n@@ -16,6 +16,7 @@\n #include \u003cnet/tc_act/tc_mirred.h\u003e\n #include \u003cnet/tc_act/tc_vlan.h\u003e\n #include \u003cnet/ipv6.h\u003e\n+#include \u003cnet/pkt_sched.h\u003e\n \n #include \"cn10k.h\"\n #include \"otx2_common.h\"\n@@ -1595,6 +1596,110 @@ static int otx2_setup_tc_block(struct net_device *netdev,\n \t\t\t\t\t nic, nic, ingress);\n }\n \n+static int otx2_teardown_tc_mqprio(struct otx2_nic *pfvf,\n+\t\t\t\t struct tc_mqprio_qopt_offload *mqprio)\n+{\n+\tstruct tc_mqprio_qopt *qopt = \u0026mqprio-\u003eqopt;\n+\tstruct net_device *netdev = pfvf-\u003enetdev;\n+\tbool if_up = netif_running(netdev);\n+\n+\tif (!if_up) {\n+\t\tnetdev_err(netdev, \"mqprio: clear requires interface UP\\n\");\n+\t\treturn -EOPNOTSUPP;\n+\t}\n+\n+\tpfvf-\u003eflags \u0026= ~OTX2_FLAG_PER_Q_RATE_LIMIT_ENABLED;\n+\totx2_stop(pfvf-\u003enetdev);\n+\totx2_open(pfvf-\u003enetdev);\n+\n+\totx2_nix_tm_clear_queue_shaper(pfvf);\n+\n+\tqopt-\u003ehw = 0;\n+\tnetdev_set_num_tc(netdev, 0);\n+\n+\treturn 0;\n+}\n+\n+static int otx2_setup_tc_mqprio(struct net_device *netdev,\n+\t\t\t\tstruct tc_mqprio_qopt_offload *mqprio)\n+{\n+\tstruct otx2_nic *pfvf = netdev_priv(netdev);\n+\tstruct tc_mqprio_qopt *qopt = \u0026mqprio-\u003eqopt;\n+\tbool if_up = netif_running(netdev);\n+\tint tc, txq, err, i;\n+\n+\tif (!if_up) {\n+\t\tnetdev_err(netdev, \"mqprio: setup requires interface UP\\n\");\n+\t\treturn -EOPNOTSUPP;\n+\t}\n+\n+\tif (!qopt-\u003ehw) {\n+\t\totx2_teardown_tc_mqprio(pfvf, mqprio);\n+\t\treturn 0;\n+\t}\n+\n+\tif (mqprio-\u003eshaper != TC_MQPRIO_SHAPER_BW_RATE) {\n+\t\tnetdev_err(netdev, \"Unsupported mqprio shaper %#x\\n\", mqprio-\u003eshaper);\n+\t\treturn -EOPNOTSUPP;\n+\t}\n+\n+\tif (qopt-\u003enum_tc \u003e pfvf-\u003ehw.non_qos_queues) {\n+\t\tnetdev_err(netdev, \"Number of TCs (%u) exceeds hw queues %u\\n\",\n+\t\t\t qopt-\u003enum_tc, pfvf-\u003ehw.non_qos_queues);\n+\t\treturn -EINVAL;\n+\t}\n+\n+\tpfvf-\u003eflags |= OTX2_FLAG_PER_Q_RATE_LIMIT_ENABLED;\n+\n+\totx2_stop(pfvf-\u003enetdev);\n+\totx2_open(pfvf-\u003enetdev);\n+\n+\tfor (tc = 0; tc \u003c qopt-\u003enum_tc; tc++) {\n+\t\tu64 min_rate = 0, max_rate = 0;\n+\n+\t\tif (mqprio-\u003eflags \u0026 TC_MQPRIO_F_MIN_RATE)\n+\t\t\tmin_rate = mqprio-\u003emin_rate[tc];\n+\t\tif (mqprio-\u003eflags \u0026 TC_MQPRIO_F_MAX_RATE)\n+\t\t\tmax_rate = mqprio-\u003emax_rate[tc];\n+\n+\t\tif (min_rate \u0026\u0026 max_rate \u0026\u0026 min_rate \u003e max_rate) {\n+\t\t\totx2_teardown_tc_mqprio(pfvf, mqprio);\n+\t\t\tnetdev_err(netdev,\n+\t\t\t\t \"min_rate %llu exceeds max_rate %llu for tc %d\\n\",\n+\t\t\t\t min_rate, max_rate, tc);\n+\t\t\treturn -EINVAL;\n+\t\t}\n+\n+\t\tfor (txq = qopt-\u003eoffset[tc];\n+\t\t txq \u003c qopt-\u003eoffset[tc] + qopt-\u003ecount[tc]; txq++) {\n+\t\t\tif (txq \u003e= netdev-\u003ereal_num_tx_queues) {\n+\t\t\t\totx2_teardown_tc_mqprio(pfvf, mqprio);\n+\t\t\t\treturn -EINVAL;\n+\t\t\t}\n+\n+\t\t\tnetdev_dbg(netdev,\n+\t\t\t\t \"mqprio: tc %d txq %d min_rate %llu max_rate %llu\\n\",\n+\t\t\t\t tc, txq, min_rate, max_rate);\n+\n+\t\t\terr = otx2_nix_tm_set_queue_shaper(pfvf, txq,\n+\t\t\t\t\t\t\t min_rate, max_rate);\n+\t\t\tif (err)\n+\t\t\t\tgoto cleanup;\n+\t\t}\n+\t}\n+\n+\tnetdev_set_num_tc(netdev, qopt-\u003enum_tc);\n+\tfor (i = 0; i \u003c qopt-\u003enum_tc; i++)\n+\t\tnetdev_set_tc_queue(netdev, i, qopt-\u003ecount[i], qopt-\u003eoffset[i]);\n+\n+\tqopt-\u003ehw = TC_MQPRIO_HW_OFFLOAD_TCS;\n+\treturn 0;\n+\n+cleanup:\n+\totx2_teardown_tc_mqprio(pfvf, mqprio);\n+\treturn err;\n+}\n+\n int otx2_setup_tc(struct net_device *netdev, enum tc_setup_type type,\n \t\t void *type_data)\n {\n@@ -1603,6 +1708,8 @@ int otx2_setup_tc(struct net_device *netdev, enum tc_setup_type type,\n \t\treturn otx2_setup_tc_block(netdev, type_data);\n \tcase TC_SETUP_QDISC_HTB:\n \t\treturn otx2_setup_tc_htb(netdev, type_data);\n+\tcase TC_SETUP_QDISC_MQPRIO:\n+\t\treturn otx2_setup_tc_mqprio(netdev, type_data);\n \tdefault:\n \t\treturn -EOPNOTSUPP;\n \t}\n"
} |
| 2/1 | 2026/07/25 11:38 | agent | patch-evaluator |
0mModel:best-expensive Args: null Results: {
"EnableConfigs": null,
"FocusSymbols": [],
"Reasoning": "The patch modifies the Marvell OcteonTX2 network driver, which is a vendor-specific hardware driver. This hardware is not emulated in standard QEMU or GCE environments, making the code unreachable during fuzzing.",
"WorthFuzzing": false
}Instruction: You are an expert Linux kernel maintainer. Your job is to review a provided patch series and determine if it makes functional changes to the kernel that should be fuzzed. IMPORTANT: The changes have ALREADY been applied and committed as the HEAD commit in your workspace. Do NOT rely on your internal knowledge of the kernel. You must actively use your code access tools to examine the actual source code and confirm any assumptions. Return WorthFuzzing=false if the patch only contains: - Modifications to Documentation/, Kconfig files, or code comments. - Purely decorative changes, such as logging (e.g., pr_err, printk) or tracepoints. - Changes to numeric constants or macros that do not functionally alter execution flow. - Code paths that are impossible to reach in virtualized environments like GCE or QEMU, even when utilizing software-emulated hardware (e.g., usb gadget, mac80211_hwsim). - Code in vendor-specific PCIe switch, SmartNIC, or GPU drivers (e.g., mlxsw, pds_core, qed, ionic, amdgpu) that require physical PCIe hardware cards not emulated in standard QEMU. - Driver .remove, .shutdown, or pci_unregister_driver teardown callbacks (e.g., igb_remove) that are executed only during PCI hot-unplug or sysfs driver unbind operations. If it modifies reachable core kernel logic, drivers, or architectures, use your code search tools to verify the code can be executed, then return WorthFuzzing=true. When returning WorthFuzzing=true, you MUST ALSO: 1. Extract any specific kernel functions that should be heavily fuzzed into FocusSymbols. Avoid listing generic hot-path functions to prevent skewed test distributions. Prefer non-static, non-inlined API entrypoint functions over internal static helper functions (which are inlined by the compiler and do not have distinct symbol addresses). 2. Identify any specific CONFIG_ options required to properly test this new/modified feature. Go and look into the Kconfig files and check for ifdefs around the code, do not make assumptions. Also check "depends on" lines in Kconfig to include any non-standard parent subsystem configs needed for Kbuild to compile the code statically into vmlinux. List them in the EnableConfigs output array, and DO NOT add a 'CONFIG_' prefix (e.g., return "NET_IPV4" instead of "CONFIG_NET_IPV4"). Prefer calling several tools at the same time to save round-trips. Use set-results tool to provide results of the analysis. It must be called exactly once before the final reply. Ignore results of this tool. Prompt: For your convenience, here is the diff of the changes:
commit b9a2d8bba7be908f711b861fd0183fc984815de2
Author: syz-cluster <triage@syzkaller.com>
Date: Sat Jul 25 11:38:05 2026 +0000
syz-cluster: applied patch under review
diff --git a/drivers/net/ethernet/marvell/octeontx2/af/rvu_nix.c b/drivers/net/ethernet/marvell/octeontx2/af/rvu_nix.c
index 78667a0977c013..5ed6c225bd7352 100644
--- a/drivers/net/ethernet/marvell/octeontx2/af/rvu_nix.c
+++ b/drivers/net/ethernet/marvell/octeontx2/af/rvu_nix.c
@@ -323,8 +323,12 @@ static bool is_valid_txschq(struct rvu *rvu, int blkaddr,
return true;
}
- if (map_func != pcifunc)
+ if (map_func != pcifunc) {
+ dev_err(rvu->dev,
+ "pcifunc %x map pcifunc %x not equal, lvl=%u schq=%u\n",
+ pcifunc, map_func, lvl, schq);
return false;
+ }
return true;
}
diff --git a/drivers/net/ethernet/marvell/octeontx2/nic/otx2_common.c b/drivers/net/ethernet/marvell/octeontx2/nic/otx2_common.c
index ca73a94db79436..b0b9e273e06c3e 100644
--- a/drivers/net/ethernet/marvell/octeontx2/nic/otx2_common.c
+++ b/drivers/net/ethernet/marvell/octeontx2/nic/otx2_common.c
@@ -614,6 +614,76 @@ void otx2_get_mac_from_af(struct net_device *netdev)
}
EXPORT_SYMBOL(otx2_get_mac_from_af);
+int otx2_nix_tm_clear_queue_shaper(struct otx2_nic *pfvf)
+{
+ struct mbox *mbox = &pfvf->mbox;
+ struct nix_txschq_config *req;
+ int err, smq;
+
+ smq = otx2_get_smq_idx(pfvf, 0);
+
+ mutex_lock(&mbox->lock);
+ req = otx2_mbox_alloc_msg_nix_txschq_cfg(mbox);
+ if (!req) {
+ mutex_unlock(&mbox->lock);
+ return -ENOMEM;
+ }
+
+ req->lvl = NIX_TXSCH_LVL_MDQ;
+ req->num_regs = 2;
+
+ req->reg[0] = NIX_AF_MDQX_PIR(smq);
+ req->regval[0] = 0;
+
+ req->reg[1] = NIX_AF_MDQX_CIR(smq);
+ req->regval[1] = 0;
+
+ err = otx2_sync_mbox_msg(mbox);
+ mutex_unlock(&mbox->lock);
+ return err;
+}
+
+int otx2_nix_tm_set_queue_shaper(struct otx2_nic *pfvf,
+ int txq, u64 minrate, u64 maxrate)
+{
+ struct mbox *mbox = &pfvf->mbox;
+ struct nix_txschq_config *req;
+ int err, smq, n = 0;
+ u64 rate;
+
+ if (!maxrate && !minrate)
+ return 0;
+
+ smq = otx2_get_smq_idx(pfvf, txq);
+
+ mutex_lock(&mbox->lock);
+ req = otx2_mbox_alloc_msg_nix_txschq_cfg(mbox);
+ if (!req) {
+ mutex_unlock(&mbox->lock);
+ return -ENOMEM;
+ }
+
+ req->lvl = NIX_TXSCH_LVL_MDQ;
+
+ if (maxrate) {
+ req->reg[n] = NIX_AF_MDQX_PIR(smq);
+ rate = otx2_convert_rate(maxrate);
+ req->regval[n] = otx2_get_txschq_rate_regval(pfvf, rate, 0);
+ n++;
+ }
+ if (minrate) {
+ req->reg[n] = NIX_AF_MDQX_CIR(smq);
+ rate = otx2_convert_rate(minrate);
+ req->regval[n] = otx2_get_txschq_rate_regval(pfvf, rate, 0);
+ n++;
+ }
+ req->num_regs = n;
+
+ err = otx2_sync_mbox_msg(mbox);
+ mutex_unlock(&mbox->lock);
+ return err;
+}
+
int otx2_txschq_config(struct otx2_nic *pfvf, int lvl, int prio, bool txschq_for_pfc)
{
u16 (*schq_list)[MAX_TXSCHQ_PER_FUNC];
@@ -650,7 +720,11 @@ int otx2_txschq_config(struct otx2_nic *pfvf, int lvl, int prio, bool txschq_for
(u64)hw->smq_link_type);
req->num_regs++;
/* MDQ config */
- parent = schq_list[NIX_TXSCH_LVL_TL4][prio];
+ if (pfvf->flags & OTX2_FLAG_PER_Q_RATE_LIMIT_ENABLED)
+ parent = schq_list[NIX_TXSCH_LVL_TL4][0];
+ else
+ parent = schq_list[NIX_TXSCH_LVL_TL4][prio];
+
req->reg[1] = NIX_AF_MDQX_PARENT(schq);
req->regval[1] = parent << 16;
req->num_regs++;
@@ -778,6 +852,9 @@ int otx2_txsch_alloc(struct otx2_nic *pfvf)
req->schq[NIX_TXSCH_LVL_TL4] = chan_cnt;
}
+ if (pfvf->flags & OTX2_FLAG_PER_Q_RATE_LIMIT_ENABLED)
+ req->schq[NIX_TXSCH_LVL_SMQ] = pfvf->hw.non_qos_queues;
+
rc = otx2_sync_mbox_msg(&pfvf->mbox);
if (rc)
return rc;
diff --git a/drivers/net/ethernet/marvell/octeontx2/nic/otx2_common.h b/drivers/net/ethernet/marvell/octeontx2/nic/otx2_common.h
index eecee612b7b2c9..65687840d005f8 100644
--- a/drivers/net/ethernet/marvell/octeontx2/nic/otx2_common.h
+++ b/drivers/net/ethernet/marvell/octeontx2/nic/otx2_common.h
@@ -512,6 +512,7 @@ struct otx2_nic {
#define OTX2_FLAG_REP_MODE_ENABLED BIT_ULL(18)
#define OTX2_FLAG_PORT_UP BIT_ULL(19)
#define OTX2_FLAG_IPSEC_OFFLOAD_ENABLED BIT_ULL(20)
+#define OTX2_FLAG_PER_Q_RATE_LIMIT_ENABLED BIT_ULL(21)
u64 flags;
u64 *cq_op_addr;
@@ -1246,6 +1247,9 @@ dma_addr_t otx2_dma_map_skb_frag(struct otx2_nic *pfvf,
struct sk_buff *skb, int seg, int *len);
void otx2_dma_unmap_skb_frags(struct otx2_nic *pfvf, struct sg_list *sg);
int otx2_read_free_sqe(struct otx2_nic *pfvf, u16 qidx);
+int otx2_nix_tm_set_queue_shaper(struct otx2_nic *pfvf, int txq,
+ u64 minrate, u64 maxrate);
+int otx2_nix_tm_clear_queue_shaper(struct otx2_nic *pfvf);
void otx2_queue_vf_work(struct mbox *mw, struct workqueue_struct *mbox_wq,
int first, int mdevs, u64 intr);
int otx2_del_mcam_flow_entry(struct otx2_nic *nic, u16 entry,
diff --git a/drivers/net/ethernet/marvell/octeontx2/nic/otx2_tc.c b/drivers/net/ethernet/marvell/octeontx2/nic/otx2_tc.c
index 40162b08014dd6..bce8a866b4957f 100644
--- a/drivers/net/ethernet/marvell/octeontx2/nic/otx2_tc.c
+++ b/drivers/net/ethernet/marvell/octeontx2/nic/otx2_tc.c
@@ -16,6 +16,7 @@
#include <net/tc_act/tc_mirred.h>
#include <net/tc_act/tc_vlan.h>
#include <net/ipv6.h>
+#include <net/pkt_sched.h>
#include "cn10k.h"
#include "otx2_common.h"
@@ -1595,6 +1596,110 @@ static int otx2_setup_tc_block(struct net_device *netdev,
nic, nic, ingress);
}
+static int otx2_teardown_tc_mqprio(struct otx2_nic *pfvf,
+ struct tc_mqprio_qopt_offload *mqprio)
+{
+ struct tc_mqprio_qopt *qopt = &mqprio->qopt;
+ struct net_device *netdev = pfvf->netdev;
+ bool if_up = netif_running(netdev);
+
+ if (!if_up) {
+ netdev_err(netdev, "mqprio: clear requires interface UP\n");
+ return -EOPNOTSUPP;
+ }
+
+ pfvf->flags &= ~OTX2_FLAG_PER_Q_RATE_LIMIT_ENABLED;
+ otx2_stop(pfvf->netdev);
+ otx2_open(pfvf->netdev);
+
+ otx2_nix_tm_clear_queue_shaper(pfvf);
+
+ qopt->hw = 0;
+ netdev_set_num_tc(netdev, 0);
+
+ return 0;
+}
+
+static int otx2_setup_tc_mqprio(struct net_device *netdev,
+ struct tc_mqprio_qopt_offload *mqprio)
+{
+ struct otx2_nic *pfvf = netdev_priv(netdev);
+ struct tc_mqprio_qopt *qopt = &mqprio->qopt;
+ bool if_up = netif_running(netdev);
+ int tc, txq, err, i;
+
+ if (!if_up) {
+ netdev_err(netdev, "mqprio: setup requires interface UP\n");
+ return -EOPNOTSUPP;
+ }
+
+ if (!qopt->hw) {
+ otx2_teardown_tc_mqprio(pfvf, mqprio);
+ return 0;
+ }
+
+ if (mqprio->shaper != TC_MQPRIO_SHAPER_BW_RATE) {
+ netdev_err(netdev, "Unsupported mqprio shaper %#x\n", mqprio->shaper);
+ return -EOPNOTSUPP;
+ }
+
+ if (qopt->num_tc > pfvf->hw.non_qos_queues) {
+ netdev_err(netdev, "Number of TCs (%u) exceeds hw queues %u\n",
+ qopt->num_tc, pfvf->hw.non_qos_queues);
+ return -EINVAL;
+ }
+
+ pfvf->flags |= OTX2_FLAG_PER_Q_RATE_LIMIT_ENABLED;
+
+ otx2_stop(pfvf->netdev);
+ otx2_open(pfvf->netdev);
+
+ for (tc = 0; tc < qopt->num_tc; tc++) {
+ u64 min_rate = 0, max_rate = 0;
+
+ if (mqprio->flags & TC_MQPRIO_F_MIN_RATE)
+ min_rate = mqprio->min_rate[tc];
+ if (mqprio->flags & TC_MQPRIO_F_MAX_RATE)
+ max_rate = mqprio->max_rate[tc];
+
+ if (min_rate && max_rate && min_rate > max_rate) {
+ otx2_teardown_tc_mqprio(pfvf, mqprio);
+ netdev_err(netdev,
+ "min_rate %llu exceeds max_rate %llu for tc %d\n",
+ min_rate, max_rate, tc);
+ return -EINVAL;
+ }
+
+ for (txq = qopt->offset[tc];
+ txq < qopt->offset[tc] + qopt->count[tc]; txq++) {
+ if (txq >= netdev->real_num_tx_queues) {
+ otx2_teardown_tc_mqprio(pfvf, mqprio);
+ return -EINVAL;
+ }
+
+ netdev_dbg(netdev,
+ "mqprio: tc %d txq %d min_rate %llu max_rate %llu\n",
+ tc, txq, min_rate, max_rate);
+
+ err = otx2_nix_tm_set_queue_shaper(pfvf, txq,
+ min_rate, max_rate);
+ if (err)
+ goto cleanup;
+ }
+ }
+
+ netdev_set_num_tc(netdev, qopt->num_tc);
+ for (i = 0; i < qopt->num_tc; i++)
+ netdev_set_tc_queue(netdev, i, qopt->count[i], qopt->offset[i]);
+
+ qopt->hw = TC_MQPRIO_HW_OFFLOAD_TCS;
+ return 0;
+
+cleanup:
+ otx2_teardown_tc_mqprio(pfvf, mqprio);
+ return err;
+}
+
int otx2_setup_tc(struct net_device *netdev, enum tc_setup_type type,
void *type_data)
{
@@ -1603,6 +1708,8 @@ int otx2_setup_tc(struct net_device *netdev, enum tc_setup_type type,
return otx2_setup_tc_block(netdev, type_data);
case TC_SETUP_QDISC_HTB:
return otx2_setup_tc_htb(netdev, type_data);
+ case TC_SETUP_QDISC_MQPRIO:
+ return otx2_setup_tc_mqprio(netdev, type_data);
default:
return -EOPNOTSUPP;
}
|
| 3/2 | 2026/07/25 11:38 | llm | patch-evaluator |
0mModel:gemini-3.1-pro-preview Args: null Results: null Tokens: input: 6002 output: 42 thoughts: 198 Thoughts: **Analyzing the OcteonTX2 Network Driver Patch** Okay, so I'm looking at a patch for the Marvell OcteonTX2 network driver, specifically in `drivers/net/ethernet/marvell/octeontx2/`. It seems the patch adds support for `TC_SETUP_QDISC_MQPRIO`, which means we're dealing with queue shaping and configuring the multi-queue priority shaper using `otx2_setup_tc_mqprio` and `otx2_nix_tm_set_queue_shaper`. Given that this is a Marvell OcteonTX2 driver, I need to quickly determine the scope of this work. This is a hardware-specific driver, so the question immediately arises: is this something I can readily test within standard QEMU or a cloud environment like GCE? I need to be realistic about my testing capabilities here. To answer that, I need to figure out how this driver is exposed. Is it a PCI driver? Does it rely on specific Marvell hardware configurations that I won't have access to without specialized resources? The path is in `drivers/net/ethernet/marvell/octeontx2/`, so let's start digging. I'm going to grep within that directory for instances of `pci_register_driver` or something similar, which will give me a solid clue as to the driver's underlying hardware interface and dependencies. That should point me in the right direction. |
| 4/2 | 2026/07/25 11:38 | tool | grepper |
0mArgs:{
"Expression": "pci_register_driver",
"PathPrefix": "drivers/net/ethernet/marvell/octeontx2/"
}Results: {
"Output": "drivers/net/ethernet/marvell/octeontx2/af/rvu.c=3751=static int __init rvu_init_module(void)\n--\ndrivers/net/ethernet/marvell/octeontx2/af/rvu.c-3756-\ndrivers/net/ethernet/marvell/octeontx2/af/rvu.c:3757:\terr = pci_register_driver(\u0026cgx_driver);\ndrivers/net/ethernet/marvell/octeontx2/af/rvu.c-3758-\tif (err \u003c 0)\n--\ndrivers/net/ethernet/marvell/octeontx2/af/rvu.c-3760-\ndrivers/net/ethernet/marvell/octeontx2/af/rvu.c:3761:\terr = pci_register_driver(\u0026ptp_driver);\ndrivers/net/ethernet/marvell/octeontx2/af/rvu.c-3762-\tif (err \u003c 0)\n--\ndrivers/net/ethernet/marvell/octeontx2/af/rvu.c-3764-\ndrivers/net/ethernet/marvell/octeontx2/af/rvu.c:3765:\terr = pci_register_driver(\u0026mcs_driver);\ndrivers/net/ethernet/marvell/octeontx2/af/rvu.c-3766-\tif (err \u003c 0)\n--\ndrivers/net/ethernet/marvell/octeontx2/af/rvu.c-3768-\ndrivers/net/ethernet/marvell/octeontx2/af/rvu.c:3769:\terr = pci_register_driver(\u0026rvu_driver);\ndrivers/net/ethernet/marvell/octeontx2/af/rvu.c-3770-\tif (err \u003c 0)\n--\ndrivers/net/ethernet/marvell/octeontx2/nic/otx2_pf.c=3581=static int __init otx2_rvupf_init_module(void)\n--\ndrivers/net/ethernet/marvell/octeontx2/nic/otx2_pf.c-3584-\ndrivers/net/ethernet/marvell/octeontx2/nic/otx2_pf.c:3585:\treturn pci_register_driver(\u0026otx2_pf_driver);\ndrivers/net/ethernet/marvell/octeontx2/nic/otx2_pf.c-3586-}\n--\ndrivers/net/ethernet/marvell/octeontx2/nic/otx2_vf.c=869=static int __init otx2vf_init_module(void)\n--\ndrivers/net/ethernet/marvell/octeontx2/nic/otx2_vf.c-872-\ndrivers/net/ethernet/marvell/octeontx2/nic/otx2_vf.c:873:\treturn pci_register_driver(\u0026otx2vf_driver);\ndrivers/net/ethernet/marvell/octeontx2/nic/otx2_vf.c-874-}\n--\ndrivers/net/ethernet/marvell/octeontx2/nic/rep.c=869=static int __init rvu_rep_init_module(void)\ndrivers/net/ethernet/marvell/octeontx2/nic/rep.c-870-{\ndrivers/net/ethernet/marvell/octeontx2/nic/rep.c:871:\treturn pci_register_driver(\u0026rvu_rep_driver);\ndrivers/net/ethernet/marvell/octeontx2/nic/rep.c-872-}\n"
} |
| 5/2 | 2026/07/25 11:38 | llm | patch-evaluator |
0mModel:gemini-3.1-pro-preview Args: null Results: null Tokens: input: 7532 output: 78 thoughts: 291 Thoughts: **Analyzing the Fuzzing Potential of This Patch** Okay, let's break this down. The patch in question targets a driver for the Marvell OcteonTX2. I know that's a hardware Network Interface Card (NIC), a specific System on a Chip (SoC). The prompt directs me to return `WorthFuzzing=false` if the code falls into vendor-specific PCIe switch, SmartNIC, or GPU drivers. Since this is a vendor-specific hardware driver, and it's for a NIC, specifically the OcteonTX2, I'm already leaning towards it *not* being fuzzable using standard QEMU. This seems to require physical hardware. Now, let me just confirm my understanding. I'll quickly check what QEMU typically emulates for network devices. I know it handles the usual suspects: `e1000`, `e1000e`, `rtl8139`, `virtio-net`, `vmxnet3`, `pcnet`, `ne2k_pci`, `i82559er`, and `tulip` – the workhorses of virtual networking. But, no, I don't see anything in that list that mentions the Marvell OcteonTX2. Therefore, my conclusion is solid. Because this code is for a specific, vendor-specific hardware – the OcteonTX2 NIC – and that hardware isn't emulated by the standard QEMU environment we're using, it's unreachable in a virtualized setting. Consequently, I'll return `WorthFuzzing=false` with the reasoning that the patch involves a vendor-specific hardware driver that requires physical hardware and is not emulated in standard QEMU. |
| 6/2 | 2026/07/25 11:38 | tool | set-results |
0mArgs:{
"EnableConfigs": [],
"FocusSymbols": [],
"Reasoning": "The patch modifies the Marvell OcteonTX2 network driver, which is a vendor-specific hardware driver. This hardware is not emulated in standard QEMU or GCE environments, making the code unreachable during fuzzing.",
"WorthFuzzing": false
}Results: {
"EnableConfigs": null,
"FocusSymbols": [],
"Reasoning": "The patch modifies the Marvell OcteonTX2 network driver, which is a vendor-specific hardware driver. This hardware is not emulated in standard QEMU or GCE environments, making the code unreachable during fuzzing.",
"WorthFuzzing": false
} |
| Total Calls | Total Tokens | Avg Tokens | Total Duration (Seconds) | Avg Duration (Seconds) |
|---|
| Total Calls | Total Duration (Seconds) | Avg Duration (Seconds) |
|---|