| Seq | Timestamp | Type | Name | Duration |
|---|---|---|---|---|
| 0/0 | 2026/06/30 20:59 | flow | patch-triage |
3mArgs:null Results: {
"EnableConfigs": null,
"FocusSymbols": [],
"Reasoning": "The patch modifies the Hisilicon HNS3 network driver to support setting and getting PFC storm prevention timeout via ethtool. This is a hardware-specific PCI driver that requires actual hardware (or a dedicated emulator, which does not exist in standard QEMU/GCE environments) to successfully probe and register the netdev. Without the hardware, the driver probe fails during firmware communication, meaning the netdev is never registered and the modified ethtool callbacks cannot be reached.",
"WorthFuzzing": false
} |
| 1/1 | 2026/06/30 20:59 | action | read-patch-diff |
0mArgs:null Results: {
"PatchDiff": "commit ebd12f0a92b224db581ba03d2d6d940883ec5723\nAuthor: syz-cluster \u003ctriage@syzkaller.com\u003e\nDate: Tue Jun 30 20:59:45 2026 +0000\n\n syz-cluster: applied patch under review\n\ndiff --git a/drivers/net/ethernet/hisilicon/hns3/hnae3.h b/drivers/net/ethernet/hisilicon/hns3/hnae3.h\nindex a8798eecd9fbd0..4286af9239b015 100644\n--- a/drivers/net/ethernet/hisilicon/hns3/hnae3.h\n+++ b/drivers/net/ethernet/hisilicon/hns3/hnae3.h\n@@ -602,6 +602,10 @@ typedef int (*read_func)(struct seq_file *s, void *data);\n * Config wake on lan\n * dbg_get_read_func\n * Return the read func for debugfs seq file\n+ * set_pfc_prevention_tout\n+ * Set PFC storm prevention timeout\n+ * get_pfc_prevention_tout\n+ * Get PFC storm prevention timeout\n */\n struct hnae3_ae_ops {\n \tint (*init_ae_dev)(struct hnae3_ae_dev *ae_dev);\n@@ -810,6 +814,8 @@ struct hnae3_ae_ops {\n \tint (*hwtstamp_set)(struct hnae3_handle *handle,\n \t\t\t struct kernel_hwtstamp_config *config,\n \t\t\t struct netlink_ext_ack *extack);\n+\tint (*set_pfc_prevention_tout)(struct hnae3_handle *handle, u16 times);\n+\tint (*get_pfc_prevention_tout)(struct hnae3_handle *handle, u16 *times);\n };\n \n struct hnae3_dcb_ops {\n@@ -891,6 +897,14 @@ struct hnae3_roce_private_info {\n \tunsigned long state;\n };\n \n+struct hnae3_pfc_storm_para {\n+\tu32 dir;\n+\tu32 enable;\n+\tu32 period_ms;\n+\tu32 times;\n+\tu32 recovery_period_ms;\n+};\n+\n #define HNAE3_SUPPORT_APP_LOOPBACK BIT(0)\n #define HNAE3_SUPPORT_PHY_LOOPBACK BIT(1)\n #define HNAE3_SUPPORT_SERDES_SERIAL_LOOPBACK\tBIT(2)\ndiff --git a/drivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_cmd.h b/drivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_cmd.h\nindex 2c2a2f1e0d7a66..6dde07dde1e8eb 100644\n--- a/drivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_cmd.h\n+++ b/drivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_cmd.h\n@@ -314,6 +314,9 @@ enum hclge_opcode_type {\n \n \t/* Query link diagnosis info command */\n \tHCLGE_OPC_QUERY_LINK_DIAGNOSIS\t= 0x702A,\n+\n+\t/* Config pause storm param command */\n+\tHCLGE_OPC_CFG_PAUSE_STORM_PARA = 0x7019,\n };\n \n enum hclge_comm_cmd_return_status {\ndiff --git a/drivers/net/ethernet/hisilicon/hns3/hns3_ethtool.c b/drivers/net/ethernet/hisilicon/hns3/hns3_ethtool.c\nindex 442f15476af32a..e7318f23631576 100644\n--- a/drivers/net/ethernet/hisilicon/hns3/hns3_ethtool.c\n+++ b/drivers/net/ethernet/hisilicon/hns3/hns3_ethtool.c\n@@ -1895,6 +1895,12 @@ static int hns3_get_tunable(struct net_device *netdev,\n \tcase ETHTOOL_TX_COPYBREAK_BUF_SIZE:\n \t\t*(u32 *)data = h-\u003ekinfo.tx_spare_buf_size;\n \t\tbreak;\n+\tcase ETHTOOL_PFC_PREVENTION_TOUT:\n+\t\tif (!h-\u003eae_algo-\u003eops-\u003eget_pfc_prevention_tout)\n+\t\t\treturn -EOPNOTSUPP;\n+\n+\t\tret = h-\u003eae_algo-\u003eops-\u003eget_pfc_prevention_tout(h, (u16 *)data);\n+\t\tbreak;\n \tdefault:\n \t\tret = -EOPNOTSUPP;\n \t\tbreak;\n@@ -2020,6 +2026,12 @@ static int hns3_set_tunable(struct net_device *netdev,\n \t\t\tnetdev_info(netdev, \"the active tx spare buf size is %u, due to page order\\n\",\n \t\t\t\t priv-\u003ering-\u003etx_spare-\u003elen);\n \n+\t\tbreak;\n+\tcase ETHTOOL_PFC_PREVENTION_TOUT:\n+\t\tif (!h-\u003eae_algo-\u003eops-\u003eset_pfc_prevention_tout)\n+\t\t\treturn -EOPNOTSUPP;\n+\n+\t\tret = h-\u003eae_algo-\u003eops-\u003eset_pfc_prevention_tout(h, *(u16 *)data);\n \t\tbreak;\n \tdefault:\n \t\tret = -EOPNOTSUPP;\ndiff --git a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_cmd.h b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_cmd.h\nindex 4ce92ddefcded2..1c029dc32ab8f4 100644\n--- a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_cmd.h\n+++ b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_cmd.h\n@@ -890,6 +890,15 @@ struct hclge_query_wol_supported_cmd {\n \tu8 rsv[20];\n };\n \n+struct hclge_pfc_storm_para_cmd {\n+\t__le32 dir;\n+\t__le32 enable;\n+\t__le32 period_ms;\n+\t__le32 times;\n+\t__le32 recovery_period_ms;\n+\t__le32 rsv;\n+};\n+\n struct hclge_hw;\n int hclge_cmd_send(struct hclge_hw *hw, struct hclge_desc *desc, int num);\n #endif\ndiff --git a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c\nindex fc8587c8081371..a08d8a35aef985 100644\n--- a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c\n+++ b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c\n@@ -3524,6 +3524,122 @@ static int hclge_set_vf_link_state(struct hnae3_handle *handle, int vf,\n \treturn ret;\n }\n \n+static int hclge_set_pfc_storm_para(struct hclge_dev *hdev,\n+\t\t\t\t struct hnae3_pfc_storm_para *para)\n+{\n+\tstruct hclge_pfc_storm_para_cmd *para_cmd;\n+\tstruct hclge_desc desc;\n+\tint ret;\n+\n+\tif (hdev-\u003eae_dev-\u003edev_version \u003c HNAE3_DEVICE_VERSION_V3)\n+\t\treturn -EOPNOTSUPP;\n+\n+\thclge_cmd_setup_basic_desc(\u0026desc, HCLGE_OPC_CFG_PAUSE_STORM_PARA,\n+\t\t\t\t false);\n+\tpara_cmd = (struct hclge_pfc_storm_para_cmd *)desc.data;\n+\tpara_cmd-\u003edir = cpu_to_le32(para-\u003edir);\n+\tpara_cmd-\u003eenable = cpu_to_le32(para-\u003eenable);\n+\tpara_cmd-\u003eperiod_ms = cpu_to_le32(para-\u003eperiod_ms);\n+\tpara_cmd-\u003etimes = cpu_to_le32(para-\u003etimes);\n+\tpara_cmd-\u003erecovery_period_ms = cpu_to_le32(para-\u003erecovery_period_ms);\n+\n+\tret = hclge_cmd_send(\u0026hdev-\u003ehw, \u0026desc, 1);\n+\tif (ret)\n+\t\tdev_err(\u0026hdev-\u003epdev-\u003edev,\n+\t\t\t\"failed to set pfc storm para, ret = %d\\n\", ret);\n+\treturn ret;\n+}\n+\n+static int hclge_get_pfc_storm_para(struct hclge_dev *hdev,\n+\t\t\t\t struct hnae3_pfc_storm_para *para)\n+{\n+\tstruct hclge_pfc_storm_para_cmd *para_cmd;\n+\tstruct hclge_desc desc;\n+\tint ret;\n+\n+\tif (hdev-\u003eae_dev-\u003edev_version \u003c HNAE3_DEVICE_VERSION_V3)\n+\t\treturn -EOPNOTSUPP;\n+\n+\thclge_cmd_setup_basic_desc(\u0026desc, HCLGE_OPC_CFG_PAUSE_STORM_PARA, true);\n+\tpara_cmd = (struct hclge_pfc_storm_para_cmd *)desc.data;\n+\tpara_cmd-\u003edir = cpu_to_le32(para-\u003edir);\n+\tret = hclge_cmd_send(\u0026hdev-\u003ehw, \u0026desc, 1);\n+\tif (ret) {\n+\t\tdev_err(\u0026hdev-\u003epdev-\u003edev,\n+\t\t\t\"failed to get pfc storm para, ret = %d\\n\", ret);\n+\t\treturn ret;\n+\t}\n+\n+\tpara-\u003eenable = le32_to_cpu(para_cmd-\u003eenable);\n+\tpara-\u003eperiod_ms = le32_to_cpu(para_cmd-\u003eperiod_ms);\n+\tpara-\u003etimes = le32_to_cpu(para_cmd-\u003etimes);\n+\tpara-\u003erecovery_period_ms = le32_to_cpu(para_cmd-\u003erecovery_period_ms);\n+\n+\treturn 0;\n+}\n+\n+static int hclge_enable_pfc_storm_prevent(struct hclge_dev *hdev,\n+\t\t\t\t\t int dir, bool enable)\n+{\n+\tstruct hnae3_pfc_storm_para para = {0};\n+\tint ret;\n+\n+\tpara.dir = dir;\n+\tret = hclge_get_pfc_storm_para(hdev, \u0026para);\n+\tif (ret)\n+\t\treturn ret;\n+\n+\tpara.enable = enable;\n+\treturn hclge_set_pfc_storm_para(hdev, \u0026para);\n+}\n+\n+static int hclge_set_pfc_prevention_tout(struct hnae3_handle *h, u16 times)\n+{\n+\tstruct hclge_vport *vport = hclge_get_vport(h);\n+\tstruct hclge_dev *hdev = vport-\u003eback;\n+\tstruct hnae3_pfc_storm_para para;\n+\tint ret;\n+\n+\tif (times \u003e HCLGE_MAX_PFC_PREVENTION_TOUT) {\n+\t\tdev_err(\u0026hdev-\u003epdev-\u003edev,\n+\t\t\t\"times %u should be no more than %u!\\n\",\n+\t\t\ttimes, HCLGE_MAX_PFC_PREVENTION_TOUT);\n+\t\treturn -EINVAL;\n+\t}\n+\n+\tpara.dir = HCLGE_DIR_TX;\n+\tret = hclge_get_pfc_storm_para(hdev, \u0026para);\n+\tif (ret)\n+\t\treturn ret;\n+\n+\tpara.enable = times ? 1 : 0;\n+\tpara.times = (u32)times;\n+\tret = hclge_set_pfc_storm_para(hdev, \u0026para);\n+\tif (ret)\n+\t\treturn ret;\n+\n+\thdev-\u003epfc_prevention_tout = times;\n+\n+\treturn 0;\n+}\n+\n+static int hclge_get_pfc_prevention_tout(struct hnae3_handle *h, u16 *times)\n+{\n+\tstruct hclge_vport *vport = hclge_get_vport(h);\n+\tstruct hclge_dev *hdev = vport-\u003eback;\n+\tstruct hnae3_pfc_storm_para para;\n+\tint ret;\n+\n+\tpara.dir = HCLGE_DIR_TX;\n+\tret = hclge_get_pfc_storm_para(hdev, \u0026para);\n+\tif (ret)\n+\t\treturn ret;\n+\n+\t*times = para.enable ? (u16)para.times : 0;\n+\n+\treturn 0;\n+}\n+\n static void hclge_set_reset_pending(struct hclge_dev *hdev,\n \t\t\t\t enum hnae3_reset_type reset_type)\n {\n@@ -4317,6 +4433,26 @@ static int hclge_reset_prepare(struct hclge_dev *hdev)\n \treturn hclge_reset_prepare_wait(hdev);\n }\n \n+static void hclge_restore_pfc_storm_prevention_tout(struct hclge_dev *hdev)\n+{\n+\tstruct hnae3_handle *handle = \u0026hdev-\u003evport[0].nic;\n+\tint ret;\n+\n+\tret = hclge_enable_pfc_storm_prevent(hdev, HCLGE_DIR_RX, false);\n+\tif (ret == -EOPNOTSUPP)\n+\t\treturn;\n+\telse if (ret)\n+\t\tdev_warn(\u0026hdev-\u003epdev-\u003edev,\n+\t\t\t \"failed to disable rx pfc storm prevent, ret = %d\\n\",\n+\t\t\t ret);\n+\n+\tret = hclge_set_pfc_prevention_tout(handle, hdev-\u003epfc_prevention_tout);\n+\tif (ret)\n+\t\tdev_warn(\u0026hdev-\u003epdev-\u003edev,\n+\t\t\t \"failed to set tx pfc storm prevent, ret = %d\\n\",\n+\t\t\t ret);\n+}\n+\n static int hclge_reset_rebuild(struct hclge_dev *hdev)\n {\n \tint ret;\n@@ -9278,6 +9414,32 @@ static int hclge_init_wol(struct hclge_dev *hdev)\n \treturn hclge_update_wol(hdev);\n }\n \n+static void hclge_init_pfc_prevention_tout(struct hclge_dev *hdev)\n+{\n+\tstruct hnae3_handle *handle = \u0026hdev-\u003evport[0].nic;\n+\tu16 times;\n+\tint ret;\n+\n+\tret = hclge_enable_pfc_storm_prevent(hdev, HCLGE_DIR_RX, false);\n+\tif (ret == -EOPNOTSUPP)\n+\t\treturn;\n+\telse if (ret)\n+\t\tdev_warn(\u0026hdev-\u003epdev-\u003edev,\n+\t\t\t \"failed to disable rx pfc storm prevent, ret = %d\\n\",\n+\t\t\t ret);\n+\n+\tret = hclge_get_pfc_prevention_tout(handle, \u0026times);\n+\tif (ret) {\n+\t\tdev_warn(\u0026hdev-\u003epdev-\u003edev,\n+\t\t\t \"failed to get tx pfc prevention timeout, ret = %d\\n\",\n+\t\t\t ret);\n+\t\ttimes = HCLGE_DEFAULT_PFC_PREVENTION_TOUT;\n+\t}\n+\n+\thdev-\u003epfc_prevention_tout = times;\n+\thdev-\u003epfc_prevention_tout_default = times;\n+}\n+\n static void hclge_get_wol(struct hnae3_handle *handle,\n \t\t\t struct ethtool_wolinfo *wol)\n {\n@@ -9547,6 +9709,8 @@ static int hclge_init_ae_dev(struct hnae3_ae_dev *ae_dev)\n \t\tdev_warn(\u0026pdev-\u003edev,\n \t\t\t \"failed to wake on lan init, ret = %d\\n\", ret);\n \n+\thclge_init_pfc_prevention_tout(hdev);\n+\n \tret = hclge_devlink_init(hdev);\n \tif (ret)\n \t\tgoto err_ptp_uninit;\n@@ -9946,6 +10110,8 @@ static int hclge_reset_ae_dev(struct hnae3_ae_dev *ae_dev)\n \t\tdev_warn(\u0026pdev-\u003edev,\n \t\t\t \"failed to update wol config, ret = %d\\n\", ret);\n \n+\thclge_restore_pfc_storm_prevention_tout(hdev);\n+\n \tdev_info(\u0026pdev-\u003edev, \"Reset done, %s driver initialization finished.\\n\",\n \t\t HCLGE_DRIVER_NAME);\n \n@@ -9977,6 +10143,10 @@ static void hclge_uninit_ae_dev(struct hnae3_ae_dev *ae_dev)\n \thclge_config_nic_hw_error(hdev, false);\n \thclge_config_rocee_ras_interrupt(hdev, false);\n \n+\t/* Restore hw default values for the next initialization */\n+\thclge_set_pfc_prevention_tout(\u0026hdev-\u003evport-\u003enic,\n+\t\t\t\t hdev-\u003epfc_prevention_tout_default);\n+\n \thclge_comm_cmd_uninit(hdev-\u003eae_dev, \u0026hdev-\u003ehw.hw);\n \thclge_misc_irq_uninit(hdev);\n \thclge_devlink_uninit(hdev);\n@@ -10539,6 +10709,8 @@ static const struct hnae3_ae_ops hclge_ops = {\n \t.set_wol = hclge_set_wol,\n \t.hwtstamp_get = hclge_ptp_get_cfg,\n \t.hwtstamp_set = hclge_ptp_set_cfg,\n+\t.set_pfc_prevention_tout = hclge_set_pfc_prevention_tout,\n+\t.get_pfc_prevention_tout = hclge_get_pfc_prevention_tout,\n };\n \n static struct hnae3_ae_algo ae_algo = {\ndiff --git a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.h b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.h\nindex 7419481422c310..0cee8947f6b44e 100644\n--- a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.h\n+++ b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.h\n@@ -346,6 +346,11 @@ enum hclge_link_fail_code {\n #define HCLGE_LINK_STATUS_DOWN 0\n #define HCLGE_LINK_STATUS_UP 1\n \n+#define HCLGE_DIR_RX 0\n+#define HCLGE_DIR_TX 1\n+#define HCLGE_MAX_PFC_PREVENTION_TOUT\t\t2000\n+#define HCLGE_DEFAULT_PFC_PREVENTION_TOUT\t1000\n+\n #define HCLGE_PG_NUM\t\t4\n #define HCLGE_SCH_MODE_SP\t0\n #define HCLGE_SCH_MODE_DWRR\t1\n@@ -898,6 +903,8 @@ struct hclge_dev {\n \tu16 vf_rss_size_max;\t\t/* HW defined VF max RSS task queue */\n \tu16 pf_rss_size_max;\t\t/* HW defined PF max RSS task queue */\n \tu32 tx_spare_buf_size;\t\t/* HW defined TX spare buffer size */\n+\tu16 pfc_prevention_tout;\t/* User config, restored after reset */\n+\tu16 pfc_prevention_tout_default; /* HW default, to avoid stale state */\n \n \tu16 fdir_pf_filter_count; /* Num of guaranteed filters for this PF */\n \tu16 num_alloc_vport;\t\t/* Num vports this driver supports */\n"
} |
| 2/1 | 2026/06/30 20:59 | agent | patch-evaluator |
3mModel:gemini-3.1-pro-preview Args: null Results: {
"EnableConfigs": null,
"FocusSymbols": [],
"Reasoning": "The patch modifies the Hisilicon HNS3 network driver to support setting and getting PFC storm prevention timeout via ethtool. This is a hardware-specific PCI driver that requires actual hardware (or a dedicated emulator, which does not exist in standard QEMU/GCE environments) to successfully probe and register the netdev. Without the hardware, the driver probe fails during firmware communication, meaning the netdev is never registered and the modified ethtool callbacks cannot be reached.",
"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). 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. 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. Do not list too generic configs (we already have them enabled). Only list those that specifically cover the modified code. 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 ebd12f0a92b224db581ba03d2d6d940883ec5723
Author: syz-cluster <triage@syzkaller.com>
Date: Tue Jun 30 20:59:45 2026 +0000
syz-cluster: applied patch under review
diff --git a/drivers/net/ethernet/hisilicon/hns3/hnae3.h b/drivers/net/ethernet/hisilicon/hns3/hnae3.h
index a8798eecd9fbd0..4286af9239b015 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hnae3.h
+++ b/drivers/net/ethernet/hisilicon/hns3/hnae3.h
@@ -602,6 +602,10 @@ typedef int (*read_func)(struct seq_file *s, void *data);
* Config wake on lan
* dbg_get_read_func
* Return the read func for debugfs seq file
+ * set_pfc_prevention_tout
+ * Set PFC storm prevention timeout
+ * get_pfc_prevention_tout
+ * Get PFC storm prevention timeout
*/
struct hnae3_ae_ops {
int (*init_ae_dev)(struct hnae3_ae_dev *ae_dev);
@@ -810,6 +814,8 @@ struct hnae3_ae_ops {
int (*hwtstamp_set)(struct hnae3_handle *handle,
struct kernel_hwtstamp_config *config,
struct netlink_ext_ack *extack);
+ int (*set_pfc_prevention_tout)(struct hnae3_handle *handle, u16 times);
+ int (*get_pfc_prevention_tout)(struct hnae3_handle *handle, u16 *times);
};
struct hnae3_dcb_ops {
@@ -891,6 +897,14 @@ struct hnae3_roce_private_info {
unsigned long state;
};
+struct hnae3_pfc_storm_para {
+ u32 dir;
+ u32 enable;
+ u32 period_ms;
+ u32 times;
+ u32 recovery_period_ms;
+};
+
#define HNAE3_SUPPORT_APP_LOOPBACK BIT(0)
#define HNAE3_SUPPORT_PHY_LOOPBACK BIT(1)
#define HNAE3_SUPPORT_SERDES_SERIAL_LOOPBACK BIT(2)
diff --git a/drivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_cmd.h b/drivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_cmd.h
index 2c2a2f1e0d7a66..6dde07dde1e8eb 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_cmd.h
+++ b/drivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_cmd.h
@@ -314,6 +314,9 @@ enum hclge_opcode_type {
/* Query link diagnosis info command */
HCLGE_OPC_QUERY_LINK_DIAGNOSIS = 0x702A,
+
+ /* Config pause storm param command */
+ HCLGE_OPC_CFG_PAUSE_STORM_PARA = 0x7019,
};
enum hclge_comm_cmd_return_status {
diff --git a/drivers/net/ethernet/hisilicon/hns3/hns3_ethtool.c b/drivers/net/ethernet/hisilicon/hns3/hns3_ethtool.c
index 442f15476af32a..e7318f23631576 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hns3_ethtool.c
+++ b/drivers/net/ethernet/hisilicon/hns3/hns3_ethtool.c
@@ -1895,6 +1895,12 @@ static int hns3_get_tunable(struct net_device *netdev,
case ETHTOOL_TX_COPYBREAK_BUF_SIZE:
*(u32 *)data = h->kinfo.tx_spare_buf_size;
break;
+ case ETHTOOL_PFC_PREVENTION_TOUT:
+ if (!h->ae_algo->ops->get_pfc_prevention_tout)
+ return -EOPNOTSUPP;
+
+ ret = h->ae_algo->ops->get_pfc_prevention_tout(h, (u16 *)data);
+ break;
default:
ret = -EOPNOTSUPP;
break;
@@ -2020,6 +2026,12 @@ static int hns3_set_tunable(struct net_device *netdev,
netdev_info(netdev, "the active tx spare buf size is %u, due to page order\n",
priv->ring->tx_spare->len);
+ break;
+ case ETHTOOL_PFC_PREVENTION_TOUT:
+ if (!h->ae_algo->ops->set_pfc_prevention_tout)
+ return -EOPNOTSUPP;
+
+ ret = h->ae_algo->ops->set_pfc_prevention_tout(h, *(u16 *)data);
break;
default:
ret = -EOPNOTSUPP;
diff --git a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_cmd.h b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_cmd.h
index 4ce92ddefcded2..1c029dc32ab8f4 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_cmd.h
+++ b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_cmd.h
@@ -890,6 +890,15 @@ struct hclge_query_wol_supported_cmd {
u8 rsv[20];
};
+struct hclge_pfc_storm_para_cmd {
+ __le32 dir;
+ __le32 enable;
+ __le32 period_ms;
+ __le32 times;
+ __le32 recovery_period_ms;
+ __le32 rsv;
+};
+
struct hclge_hw;
int hclge_cmd_send(struct hclge_hw *hw, struct hclge_desc *desc, int num);
#endif
diff --git a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c
index fc8587c8081371..a08d8a35aef985 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c
+++ b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c
@@ -3524,6 +3524,122 @@ static int hclge_set_vf_link_state(struct hnae3_handle *handle, int vf,
return ret;
}
+static int hclge_set_pfc_storm_para(struct hclge_dev *hdev,
+ struct hnae3_pfc_storm_para *para)
+{
+ struct hclge_pfc_storm_para_cmd *para_cmd;
+ struct hclge_desc desc;
+ int ret;
+
+ if (hdev->ae_dev->dev_version < HNAE3_DEVICE_VERSION_V3)
+ return -EOPNOTSUPP;
+
+ hclge_cmd_setup_basic_desc(&desc, HCLGE_OPC_CFG_PAUSE_STORM_PARA,
+ false);
+ para_cmd = (struct hclge_pfc_storm_para_cmd *)desc.data;
+ para_cmd->dir = cpu_to_le32(para->dir);
+ para_cmd->enable = cpu_to_le32(para->enable);
+ para_cmd->period_ms = cpu_to_le32(para->period_ms);
+ para_cmd->times = cpu_to_le32(para->times);
+ para_cmd->recovery_period_ms = cpu_to_le32(para->recovery_period_ms);
+
+ ret = hclge_cmd_send(&hdev->hw, &desc, 1);
+ if (ret)
+ dev_err(&hdev->pdev->dev,
+ "failed to set pfc storm para, ret = %d\n", ret);
+ return ret;
+}
+
+static int hclge_get_pfc_storm_para(struct hclge_dev *hdev,
+ struct hnae3_pfc_storm_para *para)
+{
+ struct hclge_pfc_storm_para_cmd *para_cmd;
+ struct hclge_desc desc;
+ int ret;
+
+ if (hdev->ae_dev->dev_version < HNAE3_DEVICE_VERSION_V3)
+ return -EOPNOTSUPP;
+
+ hclge_cmd_setup_basic_desc(&desc, HCLGE_OPC_CFG_PAUSE_STORM_PARA, true);
+ para_cmd = (struct hclge_pfc_storm_para_cmd *)desc.data;
+ para_cmd->dir = cpu_to_le32(para->dir);
+ ret = hclge_cmd_send(&hdev->hw, &desc, 1);
+ if (ret) {
+ dev_err(&hdev->pdev->dev,
+ "failed to get pfc storm para, ret = %d\n", ret);
+ return ret;
+ }
+
+ para->enable = le32_to_cpu(para_cmd->enable);
+ para->period_ms = le32_to_cpu(para_cmd->period_ms);
+ para->times = le32_to_cpu(para_cmd->times);
+ para->recovery_period_ms = le32_to_cpu(para_cmd->recovery_period_ms);
+
+ return 0;
+}
+
+static int hclge_enable_pfc_storm_prevent(struct hclge_dev *hdev,
+ int dir, bool enable)
+{
+ struct hnae3_pfc_storm_para para = {0};
+ int ret;
+
+ para.dir = dir;
+ ret = hclge_get_pfc_storm_para(hdev, ¶);
+ if (ret)
+ return ret;
+
+ para.enable = enable;
+ return hclge_set_pfc_storm_para(hdev, ¶);
+}
+
+static int hclge_set_pfc_prevention_tout(struct hnae3_handle *h, u16 times)
+{
+ struct hclge_vport *vport = hclge_get_vport(h);
+ struct hclge_dev *hdev = vport->back;
+ struct hnae3_pfc_storm_para para;
+ int ret;
+
+ if (times > HCLGE_MAX_PFC_PREVENTION_TOUT) {
+ dev_err(&hdev->pdev->dev,
+ "times %u should be no more than %u!\n",
+ times, HCLGE_MAX_PFC_PREVENTION_TOUT);
+ return -EINVAL;
+ }
+
+ para.dir = HCLGE_DIR_TX;
+ ret = hclge_get_pfc_storm_para(hdev, ¶);
+ if (ret)
+ return ret;
+
+ para.enable = times ? 1 : 0;
+ para.times = (u32)times;
+ ret = hclge_set_pfc_storm_para(hdev, ¶);
+ if (ret)
+ return ret;
+
+ hdev->pfc_prevention_tout = times;
+
+ return 0;
+}
+
+static int hclge_get_pfc_prevention_tout(struct hnae3_handle *h, u16 *times)
+{
+ struct hclge_vport *vport = hclge_get_vport(h);
+ struct hclge_dev *hdev = vport->back;
+ struct hnae3_pfc_storm_para para;
+ int ret;
+
+ para.dir = HCLGE_DIR_TX;
+ ret = hclge_get_pfc_storm_para(hdev, ¶);
+ if (ret)
+ return ret;
+
+ *times = para.enable ? (u16)para.times : 0;
+
+ return 0;
+}
+
static void hclge_set_reset_pending(struct hclge_dev *hdev,
enum hnae3_reset_type reset_type)
{
@@ -4317,6 +4433,26 @@ static int hclge_reset_prepare(struct hclge_dev *hdev)
return hclge_reset_prepare_wait(hdev);
}
+static void hclge_restore_pfc_storm_prevention_tout(struct hclge_dev *hdev)
+{
+ struct hnae3_handle *handle = &hdev->vport[0].nic;
+ int ret;
+
+ ret = hclge_enable_pfc_storm_prevent(hdev, HCLGE_DIR_RX, false);
+ if (ret == -EOPNOTSUPP)
+ return;
+ else if (ret)
+ dev_warn(&hdev->pdev->dev,
+ "failed to disable rx pfc storm prevent, ret = %d\n",
+ ret);
+
+ ret = hclge_set_pfc_prevention_tout(handle, hdev->pfc_prevention_tout);
+ if (ret)
+ dev_warn(&hdev->pdev->dev,
+ "failed to set tx pfc storm prevent, ret = %d\n",
+ ret);
+}
+
static int hclge_reset_rebuild(struct hclge_dev *hdev)
{
int ret;
@@ -9278,6 +9414,32 @@ static int hclge_init_wol(struct hclge_dev *hdev)
return hclge_update_wol(hdev);
}
+static void hclge_init_pfc_prevention_tout(struct hclge_dev *hdev)
+{
+ struct hnae3_handle *handle = &hdev->vport[0].nic;
+ u16 times;
+ int ret;
+
+ ret = hclge_enable_pfc_storm_prevent(hdev, HCLGE_DIR_RX, false);
+ if (ret == -EOPNOTSUPP)
+ return;
+ else if (ret)
+ dev_warn(&hdev->pdev->dev,
+ "failed to disable rx pfc storm prevent, ret = %d\n",
+ ret);
+
+ ret = hclge_get_pfc_prevention_tout(handle, ×);
+ if (ret) {
+ dev_warn(&hdev->pdev->dev,
+ "failed to get tx pfc prevention timeout, ret = %d\n",
+ ret);
+ times = HCLGE_DEFAULT_PFC_PREVENTION_TOUT;
+ }
+
+ hdev->pfc_prevention_tout = times;
+ hdev->pfc_prevention_tout_default = times;
+}
+
static void hclge_get_wol(struct hnae3_handle *handle,
struct ethtool_wolinfo *wol)
{
@@ -9547,6 +9709,8 @@ static int hclge_init_ae_dev(struct hnae3_ae_dev *ae_dev)
dev_warn(&pdev->dev,
"failed to wake on lan init, ret = %d\n", ret);
+ hclge_init_pfc_prevention_tout(hdev);
+
ret = hclge_devlink_init(hdev);
if (ret)
goto err_ptp_uninit;
@@ -9946,6 +10110,8 @@ static int hclge_reset_ae_dev(struct hnae3_ae_dev *ae_dev)
dev_warn(&pdev->dev,
"failed to update wol config, ret = %d\n", ret);
+ hclge_restore_pfc_storm_prevention_tout(hdev);
+
dev_info(&pdev->dev, "Reset done, %s driver initialization finished.\n",
HCLGE_DRIVER_NAME);
@@ -9977,6 +10143,10 @@ static void hclge_uninit_ae_dev(struct hnae3_ae_dev *ae_dev)
hclge_config_nic_hw_error(hdev, false);
hclge_config_rocee_ras_interrupt(hdev, false);
+ /* Restore hw default values for the next initialization */
+ hclge_set_pfc_prevention_tout(&hdev->vport->nic,
+ hdev->pfc_prevention_tout_default);
+
hclge_comm_cmd_uninit(hdev->ae_dev, &hdev->hw.hw);
hclge_misc_irq_uninit(hdev);
hclge_devlink_uninit(hdev);
@@ -10539,6 +10709,8 @@ static const struct hnae3_ae_ops hclge_ops = {
.set_wol = hclge_set_wol,
.hwtstamp_get = hclge_ptp_get_cfg,
.hwtstamp_set = hclge_ptp_set_cfg,
+ .set_pfc_prevention_tout = hclge_set_pfc_prevention_tout,
+ .get_pfc_prevention_tout = hclge_get_pfc_prevention_tout,
};
static struct hnae3_ae_algo ae_algo = {
diff --git a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.h b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.h
index 7419481422c310..0cee8947f6b44e 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.h
+++ b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.h
@@ -346,6 +346,11 @@ enum hclge_link_fail_code {
#define HCLGE_LINK_STATUS_DOWN 0
#define HCLGE_LINK_STATUS_UP 1
+#define HCLGE_DIR_RX 0
+#define HCLGE_DIR_TX 1
+#define HCLGE_MAX_PFC_PREVENTION_TOUT 2000
+#define HCLGE_DEFAULT_PFC_PREVENTION_TOUT 1000
+
#define HCLGE_PG_NUM 4
#define HCLGE_SCH_MODE_SP 0
#define HCLGE_SCH_MODE_DWRR 1
@@ -898,6 +903,8 @@ struct hclge_dev {
u16 vf_rss_size_max; /* HW defined VF max RSS task queue */
u16 pf_rss_size_max; /* HW defined PF max RSS task queue */
u32 tx_spare_buf_size; /* HW defined TX spare buffer size */
+ u16 pfc_prevention_tout; /* User config, restored after reset */
+ u16 pfc_prevention_tout_default; /* HW default, to avoid stale state */
u16 fdir_pf_filter_count; /* Num of guaranteed filters for this PF */
u16 num_alloc_vport; /* Num vports this driver supports */
|
| 3/2 | 2026/06/30 20:59 | llm | patch-evaluator |
0mModel:gemini-3.1-pro-preview Args: null Results: null Tokens: input: 6995 output: 38 thoughts: 367 Thoughts: **Analyzing the PFC Storm Prevention Patch for the HNS3 Driver** Okay, so there's a patch coming in that adds the ability to set and get the Priority Flow Control (PFC) storm prevention timeout within the HNS3 driver. It looks like it primarily touches `drivers/net/ethernet/hisilicon/hns3/hns3_ethtool.c` to add the necessary `ETHTOOL_PFC_PREVENTION_TOUT` hooks for `hns3_get_tunable` and `hns3_set_tunable`. Then, on the HCLGE PF side, `drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c` gets the actual implementation for the get and set functions, namely `hclge_set_pfc_prevention_tout` and `hclge_get_pfc_prevention_tout`. My initial thought is, can we fuzz this? The driver in question is `hns3`, which I remember is a PCI driver. My immediate concern is the accessibility of this code in a virtualized environment. These hardware-specific PCI drivers are often difficult to reach directly unless we're using something like QEMU with specific hardware emulation or leveraging tools like syz-usb/syz-pci. Wait a minute, syzkaller *does* have PCI fuzzing capabilities now – `syz-pci`! But the question is, does it specifically cover the Hisilicon HNS3? I need to verify that `hns3` is indeed a PCI driver to confirm my fuzzing approach. Let's see... `drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c` is part of the `hns3` driver, so I need to check its parent directory for the PCI driver instantiation. I should search for `pci_driver` declarations within the `drivers/net/ethernet/hisilicon/hns3` directory to confirm. |
| 4/2 | 2026/06/30 20:59 | tool | grepper |
0mArgs:{
"Expression": "pci_driver",
"PathPrefix": "drivers/net/ethernet/hisilicon/hns3"
}Results: {
"Output": "drivers/net/ethernet/hisilicon/hns3/hns3_enet.c=3355=static SIMPLE_DEV_PM_OPS(hns3_pm_ops, hns3_suspend, hns3_resume);\ndrivers/net/ethernet/hisilicon/hns3/hns3_enet.c-3356-\ndrivers/net/ethernet/hisilicon/hns3/hns3_enet.c:3357:static struct pci_driver hns3_driver = {\ndrivers/net/ethernet/hisilicon/hns3/hns3_enet.c-3358-\t.name = hns3_driver_name,\n"
} |
| 5/2 | 2026/06/30 20:59 | llm | patch-evaluator |
0mModel:gemini-3.1-pro-preview Args: null Results: null Tokens: input: 8034 output: 48 thoughts: 257 Thoughts: **Analyzing the Fuzzing Potential of This PCI Driver** Okay, so it's confirmed, this is a PCI driver. The next question, naturally, is whether or not it's susceptible to fuzzing. Given the context, my initial thought is, can this PCI device be fuzzed using `syz-pci`? I know that's the common approach, especially when the PCI IDs are known and syzkaller is properly configured. PCI devices often *can* be emulated or fuzzed this way. However, I'm already anticipating some of the usual hurdles. Specifically, considering my experience, hardware-specific drivers, particularly complex ones like network cards, are notoriously difficult to meaningfully fuzz without a robust emulator. Even though syzkaller *does* have a PCI fuzzer, it's often not enough on its own. Now, wait a minute, the instructions say something important about virtualized environments. It mentions "Code paths that are impossible to reach in virtualized environments like GCE or QEMU." This raises a red flag. Is there a software-emulated hardware option specifically for Hisilicon HNS3? I don't recall seeing one, and that’s a problem. Can `syz-pci` even *reach* this thing? It can certainly probe it, but getting the device set up to a point where `ethtool` commands can even be sent to the netdev requires a *successful* probe. And, with these kinds of complex network cards, probe failures are the norm unless the hardware is physically present or perfectly emulated. Probes fail because they often involve reading hardware registers, waiting for specific bits to be set, and other hardware-dependent operations. Alright, time to dive into the code. I need to take a look at the probe function in `hclge_main.c` to understand exactly what's involved. |
| 6/2 | 2026/06/30 21:00 | tool | grepper |
0mError:no matches Args: {
"Expression": "probe",
"PathPrefix": "drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c"
}Results: {
"error": "no matches"
} |
| 7/2 | 2026/06/30 21:00 | llm | patch-evaluator |
0mModel:gemini-3.1-pro-preview Args: null Results: null Tokens: input: 8754 output: 43 thoughts: 29 Thoughts: Here's my thought process, as if I were considering this myself: **Tracing Down the PF Driver in the HCLGE Codebase** Okay, so I'm trying to figure out where the primary PF (Physical Function) driver is within the HCLGE code. Initially, my instincts pinged `hclge_main.c` as a likely contender. It seems like the obvious starting point for driver functionality. But, I know these things can be structured in a variety of ways, so I shouldn't jump to conclusions. It's best to verify this by checking other candidates. Therefore, I need to look at `hns3_enet.c` as well. That file name looks like a strong candidate to be a more detailed implementation of ethernet functions. Given the HNS3 architecture, there's a good chance that its handling some portion of the PF driver. I need to cross-reference and confirm which file contains the critical PF-related code. I'll need to dig into both files to understand the control and data plane interactions and pin down the true PF driver implementation. |
| 8/2 | 2026/06/30 21:00 | tool | grepper |
0mArgs:{
"Expression": "probe",
"PathPrefix": "drivers/net/ethernet/hisilicon/hns3/hns3_enet.c"
}Results: {
"Output": "drivers/net/ethernet/hisilicon/hns3/hns3_enet.c=3130=static void hns3_disable_sriov(struct pci_dev *pdev)\n--\ndrivers/net/ethernet/hisilicon/hns3/hns3_enet.c-3144-\ndrivers/net/ethernet/hisilicon/hns3/hns3_enet.c:3145:/* hns3_probe - Device initialization routine\ndrivers/net/ethernet/hisilicon/hns3/hns3_enet.c-3146- * @pdev: PCI device information struct\n--\ndrivers/net/ethernet/hisilicon/hns3/hns3_enet.c-3148- *\ndrivers/net/ethernet/hisilicon/hns3/hns3_enet.c:3149: * hns3_probe initializes a PF identified by a pci_dev structure.\ndrivers/net/ethernet/hisilicon/hns3/hns3_enet.c-3150- * The OS initialization, configuring of the PF private structure,\n--\ndrivers/net/ethernet/hisilicon/hns3/hns3_enet.c-3154- */\ndrivers/net/ethernet/hisilicon/hns3/hns3_enet.c:3155:static int hns3_probe(struct pci_dev *pdev, const struct pci_device_id *ent)\ndrivers/net/ethernet/hisilicon/hns3/hns3_enet.c-3156-{\n--\ndrivers/net/ethernet/hisilicon/hns3/hns3_enet.c=3357=static struct pci_driver hns3_driver = {\n--\ndrivers/net/ethernet/hisilicon/hns3/hns3_enet.c-3359-\t.id_table = hns3_pci_tbl,\ndrivers/net/ethernet/hisilicon/hns3/hns3_enet.c:3360:\t.probe = hns3_probe,\ndrivers/net/ethernet/hisilicon/hns3/hns3_enet.c-3361-\t.remove = hns3_remove,\n--\ndrivers/net/ethernet/hisilicon/hns3/hns3_enet.c=5374=static int hns3_client_init(struct hnae3_handle *handle)\n--\ndrivers/net/ethernet/hisilicon/hns3/hns3_enet.c-5484-\tif (ret) {\ndrivers/net/ethernet/hisilicon/hns3/hns3_enet.c:5485:\t\tdev_err(priv-\u003edev, \"probe register netdev fail!\\n\");\ndrivers/net/ethernet/hisilicon/hns3/hns3_enet.c-5486-\t\tgoto out_reg_netdev_fail;\n"
} |
| 9/2 | 2026/06/30 21:00 | llm | patch-evaluator |
0mModel:gemini-3.1-pro-preview Args: null Results: null Tokens: input: 9809 output: 52 thoughts: 14 Thoughts: Okay, let's dive into this. Here's my take on those thoughts, as if they're my own: **Initial Assessment of `hns3_probe`** Alright, let's get down to business. My first step is to figure out exactly what `hns3_probe` is all about. No assumptions, just pure, objective analysis. I'm going to start by getting a grasp on its function and purpose, without any preconceived notions. I need to understand its role within the larger system. Time to dissect and analyze. Let's see what this thing *actually* does. |
| 10/2 | 2026/06/30 21:00 | tool | read-file |
0mArgs:{
"File": "drivers/net/ethernet/hisilicon/hns3/hns3_enet.c",
"FirstLine": 3155,
"LineCount": 100
}Results: {
"Contents": "3155:\tstatic int hns3_probe(struct pci_dev *pdev, const struct pci_device_id *ent)\n3156:\t{\n3157:\t\tstruct hnae3_ae_dev *ae_dev;\n3158:\t\tint ret;\n3159:\t\n3160:\t\tae_dev = devm_kzalloc(\u0026pdev-\u003edev, sizeof(*ae_dev), GFP_KERNEL);\n3161:\t\tif (!ae_dev)\n3162:\t\t\treturn -ENOMEM;\n3163:\t\n3164:\t\tae_dev-\u003epdev = pdev;\n3165:\t\tae_dev-\u003eflag = ent-\u003edriver_data;\n3166:\t\tpci_set_drvdata(pdev, ae_dev);\n3167:\t\n3168:\t\tret = hnae3_register_ae_dev(ae_dev);\n3169:\t\tif (ret)\n3170:\t\t\tpci_set_drvdata(pdev, NULL);\n3171:\t\n3172:\t\treturn ret;\n3173:\t}\n3174:\t\n3175:\t/**\n3176:\t * hns3_clean_vf_config\n3177:\t * @pdev: pointer to a pci_dev structure\n3178:\t * @num_vfs: number of VFs allocated\n3179:\t *\n3180:\t * Clean residual vf config after disable sriov\n3181:\t **/\n3182:\tstatic void hns3_clean_vf_config(struct pci_dev *pdev, int num_vfs)\n3183:\t{\n3184:\t\tstruct hnae3_ae_dev *ae_dev = pci_get_drvdata(pdev);\n3185:\t\n3186:\t\tif (ae_dev-\u003eops-\u003eclean_vf_config)\n3187:\t\t\tae_dev-\u003eops-\u003eclean_vf_config(ae_dev, num_vfs);\n3188:\t}\n3189:\t\n3190:\t/* hns3_remove - Device removal routine\n3191:\t * @pdev: PCI device information struct\n3192:\t */\n3193:\tstatic void hns3_remove(struct pci_dev *pdev)\n3194:\t{\n3195:\t\tstruct hnae3_ae_dev *ae_dev = pci_get_drvdata(pdev);\n3196:\t\n3197:\t\tif (hns3_is_phys_func(pdev) \u0026\u0026 IS_ENABLED(CONFIG_PCI_IOV))\n3198:\t\t\thns3_disable_sriov(pdev);\n3199:\t\n3200:\t\thnae3_unregister_ae_dev(ae_dev);\n3201:\t\tpci_set_drvdata(pdev, NULL);\n3202:\t}\n3203:\t\n3204:\t/**\n3205:\t * hns3_pci_sriov_configure\n3206:\t * @pdev: pointer to a pci_dev structure\n3207:\t * @num_vfs: number of VFs to allocate\n3208:\t *\n3209:\t * Enable or change the number of VFs. Called when the user updates the number\n3210:\t * of VFs in sysfs.\n3211:\t **/\n3212:\tstatic int hns3_pci_sriov_configure(struct pci_dev *pdev, int num_vfs)\n3213:\t{\n3214:\t\tint ret;\n3215:\t\n3216:\t\tif (!(hns3_is_phys_func(pdev) \u0026\u0026 IS_ENABLED(CONFIG_PCI_IOV))) {\n3217:\t\t\tdev_warn(\u0026pdev-\u003edev, \"Can not config SRIOV\\n\");\n3218:\t\t\treturn -EINVAL;\n3219:\t\t}\n3220:\t\n3221:\t\tif (num_vfs) {\n3222:\t\t\tret = pci_enable_sriov(pdev, num_vfs);\n3223:\t\t\tif (ret)\n3224:\t\t\t\tdev_err(\u0026pdev-\u003edev, \"SRIOV enable failed %d\\n\", ret);\n3225:\t\t\telse\n3226:\t\t\t\treturn num_vfs;\n3227:\t\t} else if (!pci_vfs_assigned(pdev)) {\n3228:\t\t\tint num_vfs_pre = pci_num_vf(pdev);\n3229:\t\n3230:\t\t\tpci_disable_sriov(pdev);\n3231:\t\t\thns3_clean_vf_config(pdev, num_vfs_pre);\n3232:\t\t} else {\n3233:\t\t\tdev_warn(\u0026pdev-\u003edev,\n3234:\t\t\t\t \"Unable to free VFs because some are assigned to VMs.\\n\");\n3235:\t\t}\n3236:\t\n3237:\t\treturn 0;\n3238:\t}\n3239:\t\n3240:\tstatic void hns3_shutdown(struct pci_dev *pdev)\n3241:\t{\n3242:\t\tstruct hnae3_ae_dev *ae_dev = pci_get_drvdata(pdev);\n3243:\t\n3244:\t\thnae3_unregister_ae_dev(ae_dev);\n3245:\t\tpci_set_drvdata(pdev, NULL);\n3246:\t\n3247:\t\tif (system_state == SYSTEM_POWER_OFF)\n3248:\t\t\tpci_set_power_state(pdev, PCI_D3hot);\n3249:\t}\n3250:\t\n3251:\tstatic int __maybe_unused hns3_suspend(struct device *dev)\n3252:\t{\n3253:\t\tstruct hnae3_ae_dev *ae_dev = dev_get_drvdata(dev);\n3254:\t\n"
} |
| 11/2 | 2026/06/30 21:00 | llm | patch-evaluator |
0mModel:gemini-3.1-pro-preview Args: null Results: null Tokens: input: 11592 output: 43 thoughts: 53 Thoughts: Okay, let's break this down. **Initial Assessment of the `hns3_probe` Function** Right, so `hns3_probe` is pretty straightforward, at least on the surface. From what I'm seeing, it looks like all it's doing is allocating an `ae_dev` structure and then immediately passing it off to `hnae3_register_ae_dev` function. That's a classic pattern, usually indicating device initialization and registration with the system. It's almost too simple, which is making me want to delve deeper, specifically into what `hnae3_register_ae_dev` is actually *doing*. I need to understand what happens to this allocated `ae_dev` now, and what that registration process entails. This is where the real meat of the device initialization likely resides. |
| 12/2 | 2026/06/30 21:00 | tool | grepper |
0mArgs:{
"Expression": "hnae3_register_ae_dev",
"PathPrefix": "drivers/net/ethernet/hisilicon/hns3"
}Results: {
"Output": "drivers/net/ethernet/hisilicon/hns3/hnae3.c=304=EXPORT_SYMBOL(hnae3_unregister_ae_algo);\ndrivers/net/ethernet/hisilicon/hns3/hnae3.c-305-\ndrivers/net/ethernet/hisilicon/hns3/hnae3.c:306:/* hnae3_register_ae_dev - registers a AE device to hnae3 framework\ndrivers/net/ethernet/hisilicon/hns3/hnae3.c-307- * @ae_dev: the AE device\n--\ndrivers/net/ethernet/hisilicon/hns3/hnae3.c-309- */\ndrivers/net/ethernet/hisilicon/hns3/hnae3.c:310:int hnae3_register_ae_dev(struct hnae3_ae_dev *ae_dev)\ndrivers/net/ethernet/hisilicon/hns3/hnae3.c-311-{\n--\ndrivers/net/ethernet/hisilicon/hns3/hnae3.c-369-}\ndrivers/net/ethernet/hisilicon/hns3/hnae3.c:370:EXPORT_SYMBOL(hnae3_register_ae_dev);\ndrivers/net/ethernet/hisilicon/hns3/hnae3.c-371-\n--\ndrivers/net/ethernet/hisilicon/hns3/hnae3.h=972=static inline void hnae3_format_mac_addr(char *format_mac_addr,\n--\ndrivers/net/ethernet/hisilicon/hns3/hnae3.h-980-\ndrivers/net/ethernet/hisilicon/hns3/hnae3.h:981:int hnae3_register_ae_dev(struct hnae3_ae_dev *ae_dev);\ndrivers/net/ethernet/hisilicon/hns3/hnae3.h-982-void hnae3_unregister_ae_dev(struct hnae3_ae_dev *ae_dev);\n--\ndrivers/net/ethernet/hisilicon/hns3/hns3_enet.c=3155=static int hns3_probe(struct pci_dev *pdev, const struct pci_device_id *ent)\n--\ndrivers/net/ethernet/hisilicon/hns3/hns3_enet.c-3167-\ndrivers/net/ethernet/hisilicon/hns3/hns3_enet.c:3168:\tret = hnae3_register_ae_dev(ae_dev);\ndrivers/net/ethernet/hisilicon/hns3/hns3_enet.c-3169-\tif (ret)\n"
} |
| 13/2 | 2026/06/30 21:00 | llm | patch-evaluator |
0mModel:gemini-3.1-pro-preview Args: null Results: null Tokens: input: 12571 output: 48 thoughts: 15 Thoughts: Okay, here's my interpretation of that thought process, assuming I'm well-versed in embedded systems and device driver development: **Initial Thoughts on Registering a Device** Alright, the next step is to dive into the `hnae3_register_ae_dev` function. This is likely the core function responsible for, well, *registering* a device, specifically one related to the hnae3 driver and, I'm guessing, an "AE" device type. The naming convention suggests this might be related to a specific hardware accelerator or coprocessor on the platform. My experience tells me registration is a critical piece, and likely involves: * **Resource Allocation:** Defining and obtaining necessary resources from the kernel - memory regions, interrupt lines, DMA channels, etc. - all of which are critical for the hardware's interaction with the system. I have to think about how this device would access shared resources. * **Driver Initialization:** Setting up data structures within the driver to manage this particular device instance. This includes things like: device-specific configuration, pointers to the device's hardware registers, and internal state variables. * **Kernel Integration:** Registering the device with the appropriate kernel subsystems, which often means setting up device nodes, registering with power management, and providing callbacks to the system. This likely involves the creation of a device structure, and maybe even a character or block device. * **Error Handling:** It will be important to carefully examine the exception and error handling within this function to check for the conditions. I'm expecting to find a series of calls to kernel APIs for memory allocation (like `kmalloc`, `ioremap`, etc.), interrupt management (`request_irq`, `free_irq`), device tree lookups (if applicable), and potentially a call to a platform-specific registration function. I am also looking to see how device-specific data is linked to the kernel data, likely with some structure pointer. The function probably also will handle some sort of cleanup process, in case device registration fails midway, to avoid resource leaks. Now, let's get into the details and start reading the code! |
| 14/2 | 2026/06/30 21:00 | tool | read-file |
0mArgs:{
"File": "drivers/net/ethernet/hisilicon/hns3/hnae3.c",
"FirstLine": 310,
"LineCount": 50
}Results: {
"Contents": " 310:\tint hnae3_register_ae_dev(struct hnae3_ae_dev *ae_dev)\n 311:\t{\n 312:\t\tconst struct pci_device_id *id;\n 313:\t\tstruct hnae3_ae_algo *ae_algo;\n 314:\t\tstruct hnae3_client *client;\n 315:\t\tint ret;\n 316:\t\n 317:\t\tif (!ae_dev)\n 318:\t\t\treturn -ENODEV;\n 319:\t\n 320:\t\tmutex_lock(\u0026hnae3_common_lock);\n 321:\t\n 322:\t\tlist_add_tail(\u0026ae_dev-\u003enode, \u0026hnae3_ae_dev_list);\n 323:\t\n 324:\t\t/* Check if there are matched ae_algo */\n 325:\t\tlist_for_each_entry(ae_algo, \u0026hnae3_ae_algo_list, node) {\n 326:\t\t\tid = pci_match_id(ae_algo-\u003epdev_id_table, ae_dev-\u003epdev);\n 327:\t\t\tif (!id)\n 328:\t\t\t\tcontinue;\n 329:\t\n 330:\t\t\tif (!ae_algo-\u003eops) {\n 331:\t\t\t\tdev_err(\u0026ae_dev-\u003epdev-\u003edev, \"ae_algo ops are null\\n\");\n 332:\t\t\t\tret = -EOPNOTSUPP;\n 333:\t\t\t\tgoto out_err;\n 334:\t\t\t}\n 335:\t\t\tae_dev-\u003eops = ae_algo-\u003eops;\n 336:\t\n 337:\t\t\tret = ae_dev-\u003eops-\u003einit_ae_dev(ae_dev);\n 338:\t\t\tif (ret) {\n 339:\t\t\t\tdev_err(\u0026ae_dev-\u003epdev-\u003edev,\n 340:\t\t\t\t\t\"init ae_dev error, ret = %d\\n\", ret);\n 341:\t\t\t\tgoto out_err;\n 342:\t\t\t}\n 343:\t\n 344:\t\t\t/* ae_dev init should set flag */\n 345:\t\t\thnae3_set_bit(ae_dev-\u003eflag, HNAE3_DEV_INITED_B, 1);\n 346:\t\t\tbreak;\n 347:\t\t}\n 348:\t\n 349:\t\t/* check the client list for the match with this ae_dev type and\n 350:\t\t * initialize the figure out client instance\n 351:\t\t */\n 352:\t\tlist_for_each_entry(client, \u0026hnae3_client_list, node) {\n 353:\t\t\tret = hnae3_init_client_instance(client, ae_dev);\n 354:\t\t\tif (ret)\n 355:\t\t\t\tdev_err(\u0026ae_dev-\u003epdev-\u003edev,\n 356:\t\t\t\t\t\"match and instantiation failed, ret = %d\\n\",\n 357:\t\t\t\t\tret);\n 358:\t\t}\n 359:\t\n"
} |
| 15/2 | 2026/06/30 21:00 | llm | patch-evaluator |
0mModel:gemini-3.1-pro-preview Args: null Results: null Tokens: input: 13876 output: 57 thoughts: 50 Thoughts: Okay, here's my interpretation of this code snippet, expressed as if it were my thought process: **Initialising the AE Device** Right, so I see a function call: `ae_dev->ops->init_ae_dev(ae_dev)`. Looks like we're calling a function pointer, `init_ae_dev`, which is part of a set of operations associated with an `ae_dev` structure. That's standard practice; a generic interface with specific implementations. Now, I need to figure out *what* `init_ae_dev` actually *does* in this specific context. Based on the file reference "hclge_main.c", it seems we're dealing with an HCLGE (likely a hardware component or driver). And then I see that `init_ae_dev` is resolved to `hclge_init_ae_dev`. Aha! So, within the HCLGE code, the initialization routine for the AE (presumably "Auto Exposure" or a similar function) is `hclge_init_ae_dev`. This will contain all the hardware-specific register settings, clock configurations, DMA setup, and everything else needed to bring the AE device up to a usable state within the HCLGE framework. |
| 16/2 | 2026/06/30 21:01 | tool | read-file |
0mArgs:{
"File": "drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c",
"FirstLine": 9600,
"LineCount": 100
}Results: {
"Contents": "9600:\t\n9601:\t\tret = hclge_mac_init(hdev);\n9602:\t\tif (ret) {\n9603:\t\t\tdev_err(\u0026pdev-\u003edev, \"Mac init error, ret = %d\\n\", ret);\n9604:\t\t\tgoto err_mdiobus_unreg;\n9605:\t\t}\n9606:\t\n9607:\t\tret = hclge_config_tso(hdev, HCLGE_TSO_MSS_MIN, HCLGE_TSO_MSS_MAX);\n9608:\t\tif (ret) {\n9609:\t\t\tdev_err(\u0026pdev-\u003edev, \"Enable tso fail, ret =%d\\n\", ret);\n9610:\t\t\tgoto err_mdiobus_unreg;\n9611:\t\t}\n9612:\t\n9613:\t\tret = hclge_config_gro(hdev);\n9614:\t\tif (ret)\n9615:\t\t\tgoto err_mdiobus_unreg;\n9616:\t\n9617:\t\tret = hclge_init_vlan_config(hdev);\n9618:\t\tif (ret) {\n9619:\t\t\tdev_err(\u0026pdev-\u003edev, \"VLAN init fail, ret =%d\\n\", ret);\n9620:\t\t\tgoto err_mdiobus_unreg;\n9621:\t\t}\n9622:\t\n9623:\t\tret = hclge_tm_schd_init(hdev);\n9624:\t\tif (ret) {\n9625:\t\t\tdev_err(\u0026pdev-\u003edev, \"tm schd init fail, ret =%d\\n\", ret);\n9626:\t\t\tgoto err_mdiobus_unreg;\n9627:\t\t}\n9628:\t\n9629:\t\tret = hclge_comm_rss_init_cfg(\u0026hdev-\u003evport-\u003enic, hdev-\u003eae_dev,\n9630:\t\t\t\t\t \u0026hdev-\u003erss_cfg);\n9631:\t\tif (ret) {\n9632:\t\t\tdev_err(\u0026pdev-\u003edev, \"failed to init rss cfg, ret = %d\\n\", ret);\n9633:\t\t\tgoto err_mdiobus_unreg;\n9634:\t\t}\n9635:\t\n9636:\t\tret = hclge_rss_init_hw(hdev);\n9637:\t\tif (ret) {\n9638:\t\t\tdev_err(\u0026pdev-\u003edev, \"Rss init fail, ret =%d\\n\", ret);\n9639:\t\t\tgoto err_mdiobus_unreg;\n9640:\t\t}\n9641:\t\n9642:\t\tret = init_mgr_tbl(hdev);\n9643:\t\tif (ret) {\n9644:\t\t\tdev_err(\u0026pdev-\u003edev, \"manager table init fail, ret =%d\\n\", ret);\n9645:\t\t\tgoto err_mdiobus_unreg;\n9646:\t\t}\n9647:\t\n9648:\t\tret = hclge_init_fd_config(hdev);\n9649:\t\tif (ret) {\n9650:\t\t\tdev_err(\u0026pdev-\u003edev,\n9651:\t\t\t\t\"fd table init fail, ret=%d\\n\", ret);\n9652:\t\t\tgoto err_mdiobus_unreg;\n9653:\t\t}\n9654:\t\n9655:\t\tret = hclge_ptp_init(hdev);\n9656:\t\tif (ret)\n9657:\t\t\tgoto err_mdiobus_unreg;\n9658:\t\n9659:\t\tret = hclge_update_port_info(hdev);\n9660:\t\tif (ret)\n9661:\t\t\tgoto err_ptp_uninit;\n9662:\t\n9663:\t\tif (hdev-\u003ehw.mac.media_type != HNAE3_MEDIA_TYPE_COPPER) {\n9664:\t\t\thdev-\u003ehw.mac.req_autoneg = hdev-\u003ehw.mac.autoneg;\n9665:\t\t\tif (hdev-\u003ehw.mac.autoneg == AUTONEG_DISABLE \u0026\u0026\n9666:\t\t\t hdev-\u003ehw.mac.speed != SPEED_UNKNOWN)\n9667:\t\t\t\thdev-\u003ehw.mac.req_speed = hdev-\u003ehw.mac.speed;\n9668:\t\t}\n9669:\t\n9670:\t\tret = hclge_set_autoneg_speed_dup(hdev);\n9671:\t\tif (ret) {\n9672:\t\t\tdev_err(\u0026pdev-\u003edev,\n9673:\t\t\t\t\"failed to set autoneg speed duplex, ret = %d\\n\", ret);\n9674:\t\t\tgoto err_ptp_uninit;\n9675:\t\t}\n9676:\t\n9677:\t\tINIT_KFIFO(hdev-\u003emac_tnl_log);\n9678:\t\n9679:\t\thclge_dcb_ops_set(hdev);\n9680:\t\n9681:\t\ttimer_setup(\u0026hdev-\u003ereset_timer, hclge_reset_timer, 0);\n9682:\t\tINIT_DELAYED_WORK(\u0026hdev-\u003eservice_task, hclge_service_task);\n9683:\t\n9684:\t\thclge_clear_all_event_cause(hdev);\n9685:\t\thclge_clear_resetting_state(hdev);\n9686:\t\n9687:\t\t/* Log and clear the hw errors those already occurred */\n9688:\t\tif (hnae3_dev_ras_imp_supported(hdev))\n9689:\t\t\thclge_handle_occurred_error(hdev);\n9690:\t\telse\n9691:\t\t\thclge_handle_all_hns_hw_errors(ae_dev);\n9692:\t\n9693:\t\t/* request delayed reset for the error recovery because an immediate\n9694:\t\t * global reset on a PF affecting pending initialization of other PFs\n9695:\t\t */\n9696:\t\tif (ae_dev-\u003ehw_err_reset_req) {\n9697:\t\t\tenum hnae3_reset_type reset_level;\n9698:\t\n9699:\t\t\treset_level = hclge_get_reset_level(ae_dev,\n"
} |
| 17/2 | 2026/06/30 21:01 | llm | patch-evaluator |
0mModel:gemini-3.1-pro-preview Args: null Results: null Tokens: input: 15925 output: 54 thoughts: 64 Thoughts: **Analyzing the Hardware Initialization** Okay, hold on a second. Looking closer at this `hclge_init_ae_dev` function, it's pretty clear that it's doing a *lot* of low-level hardware initialization. I see it sending a bunch of commands directly to the hardware – using `hclge_cmd_send`, naturally. That's a crucial point. If the hardware isn't present, or isn't responding, those command transmissions are going to time out, or simply fail outright. We're going to get some telltale errors. So, where does that lead? The next logical step is to dive into `hclge_cmd_send` and really understand its behavior, and importantly, its error handling. That's where we'll likely find the key to pinpointing the root cause of any hardware-related issues. Let's see what that function is up to. |
| 18/2 | 2026/06/30 21:01 | tool | grepper |
0mError:no matches Args: {
"Expression": "hclge_cmd_send",
"PathPrefix": "drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_cmd.c"
}Results: {
"error": "no matches"
} |
| 19/2 | 2026/06/30 21:01 | llm | patch-evaluator |
0mModel:gemini-3.1-pro-preview Args: null Results: null Tokens: input: 16254 output: 42 thoughts: 31 Thoughts: Here's my thought process, summarized as you requested: **Navigating the Codebase** Okay, hold on a second. I was initially focused on `hclge_cmd.c`, but something doesn't feel quite right. I have a hunch that the function I'm looking for, specifically the `hclge_cmd_send` call, might be located in a different file altogether. I need to be more precise in my search. Let me pivot and instead of assuming, directly search for the function `hclge_cmd_send`. This will give me a more accurate picture of where it's actually defined and used within the project. It's a fundamental step to efficiently locate the relevant code sections and I'll see what the results tell me. |
| 20/2 | 2026/06/30 21:01 | tool | grepper |
0mArgs:{
"Expression": "int hclge_cmd_send",
"PathPrefix": "drivers/net/ethernet/hisilicon/hns3"
}Results: {
"Output": "drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_cmd.h=902=struct hclge_hw;\ndrivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_cmd.h:903:int hclge_cmd_send(struct hclge_hw *hw, struct hclge_desc *desc, int num);\ndrivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_cmd.h-904-#endif\n--\ndrivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c=302=static const struct hclge_mac_mgr_tbl_entry_cmd hclge_mgr_table[] = {\n--\ndrivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c-319- **/\ndrivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c:320:int hclge_cmd_send(struct hclge_hw *hw, struct hclge_desc *desc, int num)\ndrivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c-321-{\n"
} |
| 21/2 | 2026/06/30 21:01 | llm | patch-evaluator |
0mModel:gemini-3.1-pro-preview Args: null Results: null Tokens: input: 16833 output: 55 thoughts: 23 Thoughts: Okay, let's dive into this. Here's my take on those thoughts, as an expert in the field: **Internal Review of `hclge_cmd_send`** Alright, my immediate focus is on the `hclge_cmd_send` function, and I'm homing in on its definition within `hclge_main.c`. This is where the magic (or the potential headaches) likely reside. I'm essentially tracing the execution flow here; understanding *how* a command gets sent is fundamental to everything else. This is likely the core of the command and control path. I expect to find the actual mechanism for packet formatting, hardware interaction, error handling, and perhaps even some retry logic within this function. I am expecting this to be the initial entry point for any and all commands. |
| 22/2 | 2026/06/30 21:01 | tool | read-file |
0mArgs:{
"File": "drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c",
"FirstLine": 320,
"LineCount": 50
}Results: {
"Contents": " 320:\tint hclge_cmd_send(struct hclge_hw *hw, struct hclge_desc *desc, int num)\n 321:\t{\n 322:\t\treturn hclge_comm_cmd_send(\u0026hw-\u003ehw, desc, num);\n 323:\t}\n 324:\t\n 325:\tstatic void hclge_trace_cmd_send(struct hclge_comm_hw *hw, struct hclge_desc *desc,\n 326:\t\t\t\t\t int num, bool is_special)\n 327:\t{\n 328:\t\tint i;\n 329:\t\n 330:\t\ttrace_hclge_pf_cmd_send(hw, desc, 0, num);\n 331:\t\n 332:\t\tif (!is_special) {\n 333:\t\t\tfor (i = 1; i \u003c num; i++)\n 334:\t\t\t\ttrace_hclge_pf_cmd_send(hw, \u0026desc[i], i, num);\n 335:\t\t} else {\n 336:\t\t\tfor (i = 1; i \u003c num; i++)\n 337:\t\t\t\ttrace_hclge_pf_special_cmd_send(hw, (__le32 *)\u0026desc[i],\n 338:\t\t\t\t\t\t\t\ti, num);\n 339:\t\t}\n 340:\t}\n 341:\t\n 342:\tstatic void hclge_trace_cmd_get(struct hclge_comm_hw *hw, struct hclge_desc *desc,\n 343:\t\t\t\t\tint num, bool is_special)\n 344:\t{\n 345:\t\tint i;\n 346:\t\n 347:\t\tif (!HCLGE_COMM_SEND_SYNC(le16_to_cpu(desc-\u003eflag)))\n 348:\t\t\treturn;\n 349:\t\n 350:\t\ttrace_hclge_pf_cmd_get(hw, desc, 0, num);\n 351:\t\n 352:\t\tif (!is_special) {\n 353:\t\t\tfor (i = 1; i \u003c num; i++)\n 354:\t\t\t\ttrace_hclge_pf_cmd_get(hw, \u0026desc[i], i, num);\n 355:\t\t} else {\n 356:\t\t\tfor (i = 1; i \u003c num; i++)\n 357:\t\t\t\ttrace_hclge_pf_special_cmd_get(hw, (__le32 *)\u0026desc[i],\n 358:\t\t\t\t\t\t\t i, num);\n 359:\t\t}\n 360:\t}\n 361:\t\n 362:\tstatic const struct hclge_comm_cmq_ops hclge_cmq_ops = {\n 363:\t\t.trace_cmd_send = hclge_trace_cmd_send,\n 364:\t\t.trace_cmd_get = hclge_trace_cmd_get,\n 365:\t};\n 366:\t\n 367:\tstatic int hclge_mac_update_stats_defective(struct hclge_dev *hdev)\n 368:\t{\n 369:\t#define HCLGE_MAC_CMD_NUM 21\n"
} |
| 23/2 | 2026/06/30 21:01 | llm | patch-evaluator |
0mModel:gemini-3.1-pro-preview Args: null Results: null Tokens: input: 17934 output: 43 thoughts: 13 Thoughts: Okay, here's my interpretation of that thought process, assuming I'm an expert in this area and the context is clear: **Analyzing the Function Call: hclge_comm_cmd_send** Right, so the system is calling `hclge_comm_cmd_send`. That's the key. That function suggests we're dealing with command sending, and the "hclge" prefix strongly points to its integration into a specific Hardware Configuration Language GE (Global Environment) communication module. Immediately, my mind starts running through the implications. I know the likely purpose and structure. Depending on the previous context, which I'll assume is related to the specific scenario, the module this code interacts with likely requires specific messages and data to be set. Is this related to debugging, configuration, or control? Knowing that, and looking at the command, I'd then consider: what does the command *do*? Is it a query, a set command, or something more complex? The nature of the command would indicate to me what's going on, and from there I would infer the next steps, and potential issues or design decisions. From the mere calling of that function, I can infer a certain degree of complexity. It must require a specific format or structure of commands, and perhaps even some level of authentication or authorization. What data is it being sent? What is its response? Is there error handling built into the sending mechanism, or is that handled at a higher level? These are some of the most prominent questions I would be starting to work through when I see this line of code. It's a critical point in the system's execution. |
| 24/2 | 2026/06/30 21:01 | tool | grepper |
0mArgs:{
"Expression": "hclge_comm_cmd_send",
"PathPrefix": "drivers/net/ethernet/hisilicon/hns3"
}Results: {
"Output": "drivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_cmd.c=78=int hclge_comm_firmware_compat_config(struct hnae3_ae_dev *ae_dev,\n--\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_cmd.c-100-\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_cmd.c:101:\treturn hclge_comm_cmd_send(hw, \u0026desc, 1);\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_cmd.c-102-}\n--\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_cmd.c=228=int hclge_comm_cmd_query_version_and_capability(struct hnae3_ae_dev *ae_dev,\n--\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_cmd.c-239-\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_cmd.c:240:\tret = hclge_comm_cmd_send(hw, \u0026desc, 1);\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_cmd.c-241-\tif (ret)\n--\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_cmd.c=435=static int hclge_comm_cmd_check_result(struct hclge_comm_hw *hw,\n--\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_cmd.c-464-/**\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_cmd.c:465: * hclge_comm_cmd_send - send command to command queue\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_cmd.c-466- * @hw: pointer to the hw struct\n--\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_cmd.c-472- **/\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_cmd.c:473:int hclge_comm_cmd_send(struct hclge_comm_hw *hw, struct hclge_desc *desc,\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_cmd.c-474-\t\t\tint num)\n--\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_cmd.c-521-}\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_cmd.c:522:EXPORT_SYMBOL_GPL(hclge_comm_cmd_send);\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_cmd.c-523-\n--\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_cmd.h=485=int hclge_comm_alloc_cmd_queue(struct hclge_comm_hw *hw, int ring_type);\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_cmd.h:486:int hclge_comm_cmd_send(struct hclge_comm_hw *hw, struct hclge_desc *desc,\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_cmd.h-487-\t\t\tint num);\n--\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_rss.c=84=int hclge_comm_set_rss_tc_mode(struct hclge_comm_hw *hw, u16 *tc_offset,\n--\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_rss.c-110-\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_rss.c:111:\tret = hclge_comm_cmd_send(hw, \u0026desc, 1);\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_rss.c-112-\tif (ret)\n--\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_rss.c=151=int hclge_comm_set_rss_tuple(struct hnae3_ae_dev *ae_dev,\n--\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_rss.c-174-\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_rss.c:175:\tret = hclge_comm_cmd_send(hw, \u0026desc, 1);\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_rss.c-176-\tif (ret) {\n--\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_rss.c=276=int hclge_comm_set_rss_indir_table(struct hnae3_ae_dev *ae_dev,\n--\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_rss.c-304-\t\t}\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_rss.c:305:\t\tret = hclge_comm_cmd_send(hw, \u0026desc, 1);\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_rss.c-306-\t\tif (ret) {\n--\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_rss.c=317=int hclge_comm_set_rss_input_tuple(struct hclge_comm_hw *hw,\n--\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_rss.c-337-\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_rss.c:338:\tret = hclge_comm_cmd_send(hw, \u0026desc, 1);\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_rss.c-339-\tif (ret)\n--\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_rss.c=383=int hclge_comm_set_rss_algo_key(struct hclge_comm_hw *hw, const u8 hfunc,\n--\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_rss.c-411-\t\tkey_offset++;\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_rss.c:412:\t\tret = hclge_comm_cmd_send(hw, \u0026desc, 1);\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_rss.c-413-\t\tif (ret) {\n--\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_tqp_stats.c=58=int hclge_comm_tqps_update_stats(struct hnae3_handle *handle,\n--\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_tqp_stats.c-72-\t\tdesc.data[0] = cpu_to_le32(tqp-\u003eindex);\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_tqp_stats.c:73:\t\tret = hclge_comm_cmd_send(hw, \u0026desc, 1);\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_tqp_stats.c-74-\t\tif (ret) {\n--\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_tqp_stats.c-86-\t\tdesc.data[0] = cpu_to_le32(tqp-\u003eindex);\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_tqp_stats.c:87:\t\tret = hclge_comm_cmd_send(hw, \u0026desc, 1);\ndrivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_tqp_stats.c-88-\t\tif (ret) {\n--\ndrivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_err.c=3442=int hclge_handle_vf_queue_err_ras(struct hclge_dev *hdev)\n--\ndrivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_err.c-3459-\ndrivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_err.c:3460:\tret = hclge_comm_cmd_send(\u0026hdev-\u003ehw.hw, desc, 2);\ndrivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_err.c-3461-\tif (ret) {\n--\ndrivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c=320=int hclge_cmd_send(struct hclge_hw *hw, struct hclge_desc *desc, int num)\ndrivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c-321-{\ndrivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c:322:\treturn hclge_comm_cmd_send(\u0026hw-\u003ehw, desc, num);\ndrivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_main.c-323-}\n--\ndrivers/net/ethernet/hisilicon/hns3/hns3vf/hclgevf_main.c=50=int hclgevf_cmd_send(struct hclgevf_hw *hw, struct hclge_desc *desc, int num)\ndrivers/net/ethernet/hisilicon/hns3/hns3vf/hclgevf_main.c-51-{\ndrivers/net/ethernet/hisilicon/hns3/hns3vf/hclgevf_main.c:52:\treturn hclge_comm_cmd_send(\u0026hw-\u003ehw, desc, num);\ndrivers/net/ethernet/hisilicon/hns3/hns3vf/hclgevf_main.c-53-}\n"
} |
| 25/2 | 2026/06/30 21:01 | llm | patch-evaluator |
0mModel:gemini-3.1-pro-preview Args: null Results: null Tokens: input: 21374 output: 25 thoughts: 133 Thoughts: **Analyzing the Driver Probe Failure** Okay, so `hclge_comm_cmd_send` is the key function here for sending commands to the hardware's command queue. Makes sense. If the hardware isn't responding, this function is going to timeout or error out. That's a classic hardware initialization issue. And if `hclge_comm_cmd_send` fails during initialization, then `hclge_init_ae_dev` fails, and *boom*, the driver probe hits a roadblock and fails. Standard operating procedure for debugging device driver failures. But wait a minute…syz-pci can emulate PCI devices, right? That could be a way around this. The challenge with emulation, though, is that syzkaller needs very precise information: the exact PCI device ID and the specific registers to emulate. It's a significant undertaking to set that up correctly, especially without the hardware directly present. So, the crucial question: does syzkaller already have a specific emulation setup for this HNS3 device? That would be a huge shortcut. I need to check if there's any existing syzkaller description for HNS3. That's the next step – let's see what's in the syzkaller repository and related documentation. |
| 26/2 | 2026/06/30 21:01 | tool | grepper |
0mError:no matches Args: {
"Expression": "hns3",
"PathPrefix": "net/"
}Results: {
"error": "no matches"
} |
| 27/2 | 2026/06/30 21:01 | llm | patch-evaluator |
0mModel:gemini-3.1-pro-preview Args: null Results: null Tokens: input: 21816 output: 38 thoughts: 97 Thoughts: **Analyzing the HNS3 Driver and Syzkaller Integration** Okay, first things first, I need to remind myself that syzkaller descriptions aren't actually *in* the kernel tree, right? They're external, so I need to focus on how this driver interacts with that testing framework. My immediate thought is, can I find some sort of software emulation for the HNS3 hardware within the kernel itself? Just to clarify, no, it's a dedicated hardware driver. That's good to know. Now, a critical question for fuzzing: Can ethtool commands even be reached if the device probe fails? It's highly unlikely, I believe. The ethtool commands are routed to the netdev, and that `netdev` is only registered successfully after a successful probe. So, that's not a likely vulnerability path. Still, I should verify precisely where `register_netdev` is called within the driver. That’s the next thing to check. |
| 28/2 | 2026/06/30 21:01 | tool | grepper |
0mArgs:{
"Expression": "register_netdev",
"PathPrefix": "drivers/net/ethernet/hisilicon/hns3"
}Results: {
"Output": "drivers/net/ethernet/hisilicon/hns3/hns3_enet.c=5374=static int hns3_client_init(struct hnae3_handle *handle)\n--\ndrivers/net/ethernet/hisilicon/hns3/hns3_enet.c-5482-\ndrivers/net/ethernet/hisilicon/hns3/hns3_enet.c:5483:\tret = register_netdev(netdev);\ndrivers/net/ethernet/hisilicon/hns3/hns3_enet.c-5484-\tif (ret) {\n--\ndrivers/net/ethernet/hisilicon/hns3/hns3_enet.c=5517=static void hns3_client_uninit(struct hnae3_handle *handle, bool reset)\n--\ndrivers/net/ethernet/hisilicon/hns3/hns3_enet.c-5522-\tif (netdev-\u003ereg_state != NETREG_UNINITIALIZED)\ndrivers/net/ethernet/hisilicon/hns3/hns3_enet.c:5523:\t\tunregister_netdev(netdev);\ndrivers/net/ethernet/hisilicon/hns3/hns3_enet.c-5524-\n"
} |
| 29/2 | 2026/06/30 21:01 | llm | patch-evaluator |
0mModel:gemini-3.1-pro-preview Args: null Results: null Tokens: input: 22494 output: 58 thoughts: 249 Thoughts: **My Analysis of the HNS3 Client Initialization** Okay, so here's what's happening. `hns3_client_init` is the function that ultimately registers the network device, which is key. But `hns3_client_init` itself is called by `hnae3_init_client_instance`. And that, in turn, is triggered by `hnae3_register_ae_dev`, which gets called from `hns3_probe`. It's a chain, and the success of the whole thing relies on each step working. The crucial point here is `hclge_init_ae_dev`. If *that* fails, then `hnae3_register_ae_dev` will also fail, and then `hns3_client_init` will *never* get called. Meaning the netdev won't be registered. And if the netdev isn't registered, no ethtool commands can be sent to it. Pretty straightforward. So, in an environment like GCE or QEMU, which are virtualized environments, this whole path is likely dead on arrival. There's no actual HNS3 hardware for it to communicate with. The `hclge_init_ae_dev` call is going to fail because it needs to execute a command through `hclge_comm_cmd_send`. No hardware, no success. Wait a second, though... I'm missing something, aren't I? Is there *any* chance that `hclge_init_ae_dev` could succeed *without* the hardware? It's rare but it's important to be sure. Time to check `hclge_comm_cmd_send` and see if it has some kind of fallback or virtualized path. Because if it does, then some or all of this could be reachable. Let's see... |
| 30/2 | 2026/06/30 21:02 | tool | read-file |
0mArgs:{
"File": "drivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_cmd.c",
"FirstLine": 465,
"LineCount": 50
}Results: {
"Contents": " 465:\t * hclge_comm_cmd_send - send command to command queue\n 466:\t * @hw: pointer to the hw struct\n 467:\t * @desc: prefilled descriptor for describing the command\n 468:\t * @num : the number of descriptors to be sent\n 469:\t *\n 470:\t * This is the main send command for command queue, it\n 471:\t * sends the queue, cleans the queue, etc\n 472:\t **/\n 473:\tint hclge_comm_cmd_send(struct hclge_comm_hw *hw, struct hclge_desc *desc,\n 474:\t\t\t\tint num)\n 475:\t{\n 476:\t\tbool is_special = hclge_comm_is_special_opcode(le16_to_cpu(desc-\u003eopcode));\n 477:\t\tstruct hclge_comm_cmq_ring *csq = \u0026hw-\u003ecmq.csq;\n 478:\t\tint ret;\n 479:\t\tint ntc;\n 480:\t\n 481:\t\tif (hw-\u003ecmq.ops.trace_cmd_send)\n 482:\t\t\thw-\u003ecmq.ops.trace_cmd_send(hw, desc, num, is_special);\n 483:\t\n 484:\t\tspin_lock_bh(\u0026hw-\u003ecmq.csq.lock);\n 485:\t\n 486:\t\tif (test_bit(HCLGE_COMM_STATE_CMD_DISABLE, \u0026hw-\u003ecomm_state)) {\n 487:\t\t\tspin_unlock_bh(\u0026hw-\u003ecmq.csq.lock);\n 488:\t\t\treturn -EBUSY;\n 489:\t\t}\n 490:\t\n 491:\t\tif (num \u003e hclge_comm_ring_space(\u0026hw-\u003ecmq.csq)) {\n 492:\t\t\t/* If CMDQ ring is full, SW HEAD and HW HEAD may be different,\n 493:\t\t\t * need update the SW HEAD pointer csq-\u003enext_to_clean\n 494:\t\t\t */\n 495:\t\t\tcsq-\u003enext_to_clean =\n 496:\t\t\t\thclge_comm_read_dev(hw, HCLGE_COMM_NIC_CSQ_HEAD_REG);\n 497:\t\t\tspin_unlock_bh(\u0026hw-\u003ecmq.csq.lock);\n 498:\t\t\treturn -EBUSY;\n 499:\t\t}\n 500:\t\n 501:\t\t/**\n 502:\t\t * Record the location of desc in the ring for this time\n 503:\t\t * which will be use for hardware to write back\n 504:\t\t */\n 505:\t\tntc = hw-\u003ecmq.csq.next_to_use;\n 506:\t\n 507:\t\thclge_comm_cmd_copy_desc(hw, desc, num);\n 508:\t\n 509:\t\t/* Write to hardware */\n 510:\t\thclge_comm_write_dev(hw, HCLGE_COMM_NIC_CSQ_TAIL_REG,\n 511:\t\t\t\t hw-\u003ecmq.csq.next_to_use);\n 512:\t\n 513:\t\tret = hclge_comm_cmd_check_result(hw, desc, num, ntc);\n 514:\t\n"
} |
| 31/2 | 2026/06/30 21:02 | llm | patch-evaluator |
0mModel:gemini-3.1-pro-preview Args: null Results: null Tokens: input: 24082 output: 58 thoughts: 17 Thoughts: Okay, here's my attempt at summarizing that thought process, tailored for an expert audience: **Examining `hclge_comm_cmd_check_result`** Right, let's dive straight in. The first thing I need to do is to meticulously examine the `hclge_comm_cmd_check_result` function. I need to understand its exact purpose, what inputs it takes, and, crucially, how it determines the nature of its result. Is it primarily for error checking, validation, or something else entirely? What are the possible return values and what do they signify? Are there any side effects I should be aware of? I'll need to look at the function's definition, any related comments in the code, and ideally, any documentation that exists. I'll need to understand the logic behind this function completely. That means digging into the conditional statements, loops, and any external dependencies. Ultimately, my aim is to fully grasp how this check operates so I can apply that knowledge in my analysis. |
| 32/2 | 2026/06/30 21:02 | tool | read-file |
0mArgs:{
"File": "drivers/net/ethernet/hisilicon/hns3/hns3_common/hclge_comm_cmd.c",
"FirstLine": 435,
"LineCount": 30
}Results: {
"Contents": " 435:\tstatic int hclge_comm_cmd_check_result(struct hclge_comm_hw *hw,\n 436:\t\t\t\t\t struct hclge_desc *desc,\n 437:\t\t\t\t\t int num, int ntc)\n 438:\t{\n 439:\t\tbool is_completed = false;\n 440:\t\tint handle, ret;\n 441:\t\n 442:\t\t/* If the command is sync, wait for the firmware to write back,\n 443:\t\t * if multi descriptors to be sent, use the first one to check\n 444:\t\t */\n 445:\t\tif (HCLGE_COMM_SEND_SYNC(le16_to_cpu(desc-\u003eflag)))\n 446:\t\t\thclge_comm_wait_for_resp(hw, le16_to_cpu(desc-\u003eopcode),\n 447:\t\t\t\t\t\t \u0026is_completed);\n 448:\t\n 449:\t\tif (!is_completed)\n 450:\t\t\tret = -EBADE;\n 451:\t\telse\n 452:\t\t\tret = hclge_comm_cmd_check_retval(hw, desc, num, ntc);\n 453:\t\n 454:\t\t/* Clean the command send queue */\n 455:\t\thandle = hclge_comm_cmd_csq_clean(hw);\n 456:\t\tif (handle \u003c 0)\n 457:\t\t\tret = handle;\n 458:\t\telse if (handle != num)\n 459:\t\t\tdev_warn(\u0026hw-\u003ecmq.csq.pdev-\u003edev,\n 460:\t\t\t\t \"cleaned %d, need to clean %d\\n\", handle, num);\n 461:\t\treturn ret;\n 462:\t}\n 463:\t\n 464:\t/**\n"
} |
| 33/2 | 2026/06/30 21:02 | llm | patch-evaluator |
1mModel:gemini-3.1-pro-preview Args: null Results: null Tokens: input: 24854 output: 128 thoughts: 302 Thoughts: **Analyzing the Fuzzing Applicability** Okay, let's break this down. My initial observation is that the code is waiting for a firmware writeback, specifically within `hclge_comm_wait_for_resp`. If the hardware isn't present, we'll hit a timeout and get an `-EBADE` error. This means `hclge_init_ae_dev` fails, and consequently, the network device (`netdev`) won't register. My next line of thought is, could we find a way to circumvent this? Nope, this is a hardware driver, it's pretty explicit that it needs *actual* hardware or an emulator. It won't initialize without either. So, I need to figure out if there's any other route to `hclge_set_pfc_prevention_tout`, which is my target. I trace the call, and it’s called from `hns3_set_tunable`, which is an ethtool callback. Now, ethtool callbacks are only accessible when the netdev is registered. And as we've established, the netdev won't register without hardware. That's it! This code path, because of the hardware dependency, is unreachable in a virtualized environment like GCE or QEMU. Okay, let me confirm. The requirements are clear: "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)." There's no software-emulated hardware for the Hisilicon HNS3 that I'm aware of, and it's a PCIe device, which needs specific hardware responses to initialize. Therefore, this code path is impossible to reach in these environments. Based on this, I'm confident that `WorthFuzzing` should be set to `false`. |
| 34/2 | 2026/06/30 21:03 | tool | set-results |
0mArgs:{
"EnableConfigs": [],
"FocusSymbols": [],
"Reasoning": "The patch modifies the Hisilicon HNS3 network driver to support setting and getting PFC storm prevention timeout via ethtool. This is a hardware-specific PCI driver that requires actual hardware (or a dedicated emulator, which does not exist in standard QEMU/GCE environments) to successfully probe and register the netdev. Without the hardware, the driver probe fails during firmware communication, meaning the netdev is never registered and the modified ethtool callbacks cannot be reached.",
"WorthFuzzing": false
}Results: {
"EnableConfigs": null,
"FocusSymbols": [],
"Reasoning": "The patch modifies the Hisilicon HNS3 network driver to support setting and getting PFC storm prevention timeout via ethtool. This is a hardware-specific PCI driver that requires actual hardware (or a dedicated emulator, which does not exist in standard QEMU/GCE environments) to successfully probe and register the netdev. Without the hardware, the driver probe fails during firmware communication, meaning the netdev is never registered and the modified ethtool callbacks cannot be reached.",
"WorthFuzzing": false
} |
| Total Calls | Total Tokens | Avg Tokens | Total Duration (Seconds) | Avg Duration (Seconds) |
|---|
| Total Calls | Total Duration (Seconds) | Avg Duration (Seconds) |
|---|