| Seq | Timestamp | Type | Name | Duration |
|---|---|---|---|---|
| 0/0 | 2026/09/05 02:34 | flow | patch-triage |
0mArgs:null Results: {
"EnableConfigs": [
"USB_USBNET",
"USB_NET_DRIVERS",
"USB",
"NET"
],
"FocusSymbols": [
"usbnet_skb_return",
"tx_complete"
],
"KMSANReasoning": "The patch modifies `usbnet_skb_return` and `tx_complete` in `drivers/net/usb/usbnet.c` to fetch the per-CPU pointer `this_cpu_ptr(dev-\u003enet-\u003etstats)` inside a `local_irq_save`/`local_irq_restore` block rather than calling `u64_stats_update_begin_irqsave` on a pointer obtained prior to disabling interrupts/preemption.\n\nThis change is purely a locking/concurrency fix for per-CPU statistics updating. All local variables (`flags`, `stats64`) are explicitly initialized prior to use, no new buffers or structures are allocated, no data is copied to user space, and no uninitialized memory branches or info-leaks are introduced. Therefore, dedicated KMSAN fuzzing is not required.",
"NeedsKMSAN": false,
"Reasoning": "The patch modifies per-CPU network statistics update routines in usbnet (usbnet_skb_return and tx_complete) by disabling local IRQs before calling this_cpu_ptr(dev-\u003enet-\u003etstats), ensuring safe per-CPU access. USB network devices are reachable and fuzzable via USB device emulation / raw-gadget in standard virtualized environments.",
"WorthFuzzing": true
} |
| 1/1 | 2026/09/05 02:34 | action | read-patch-diff |
0mArgs:null Results: {
"PatchDiff": "commit 4cbc0a18e62b873c7528559d745479914333fba4\nAuthor: syz-cluster \u003ctriage@syzkaller.com\u003e\nDate: Sat Sep 5 02:34:33 2026 +0000\n\n syz-cluster: applied patch under review\n\ndiff --git a/drivers/net/usb/usbnet.c b/drivers/net/usb/usbnet.c\nindex a19ecf718f36a..6a48f38e105d4 100644\n--- a/drivers/net/usb/usbnet.c\n+++ b/drivers/net/usb/usbnet.c\n@@ -325,7 +325,7 @@ static void __usbnet_status_stop_force(struct usbnet *dev)\n */\n void usbnet_skb_return(struct usbnet *dev, struct sk_buff *skb)\n {\n-\tstruct pcpu_sw_netstats *stats64 = this_cpu_ptr(dev-\u003enet-\u003etstats);\n+\tstruct pcpu_sw_netstats *stats64;\n \tunsigned long flags;\n \tint\tstatus;\n \n@@ -338,10 +338,13 @@ void usbnet_skb_return(struct usbnet *dev, struct sk_buff *skb)\n \tif (skb-\u003eprotocol == 0)\n \t\tskb-\u003eprotocol = eth_type_trans(skb, dev-\u003enet);\n \n-\tflags = u64_stats_update_begin_irqsave(\u0026stats64-\u003esyncp);\n+\tlocal_irq_save(flags);\n+\tstats64 = this_cpu_ptr(dev-\u003enet-\u003etstats);\n+\tu64_stats_update_begin(\u0026stats64-\u003esyncp);\n \tu64_stats_inc(\u0026stats64-\u003erx_packets);\n \tu64_stats_add(\u0026stats64-\u003erx_bytes, skb-\u003elen);\n-\tu64_stats_update_end_irqrestore(\u0026stats64-\u003esyncp, flags);\n+\tu64_stats_update_end(\u0026stats64-\u003esyncp);\n+\tlocal_irq_restore(flags);\n \n \tnetif_dbg(dev, rx_status, dev-\u003enet, \"\u003c rx, len %zu, type 0x%x\\n\",\n \t\t skb-\u003elen + sizeof(struct ethhdr), skb-\u003eprotocol);\n@@ -1298,13 +1301,16 @@ static void tx_complete(struct urb *urb)\n \tstruct usbnet\t\t*dev = entry-\u003edev;\n \n \tif (urb-\u003estatus == 0) {\n-\t\tstruct pcpu_sw_netstats *stats64 = this_cpu_ptr(dev-\u003enet-\u003etstats);\n+\t\tstruct pcpu_sw_netstats *stats64;\n \t\tunsigned long flags;\n \n-\t\tflags = u64_stats_update_begin_irqsave(\u0026stats64-\u003esyncp);\n+\t\tlocal_irq_save(flags);\n+\t\tstats64 = this_cpu_ptr(dev-\u003enet-\u003etstats);\n+\t\tu64_stats_update_begin(\u0026stats64-\u003esyncp);\n \t\tu64_stats_add(\u0026stats64-\u003etx_packets, entry-\u003epackets);\n \t\tu64_stats_add(\u0026stats64-\u003etx_bytes, entry-\u003elength);\n-\t\tu64_stats_update_end_irqrestore(\u0026stats64-\u003esyncp, flags);\n+\t\tu64_stats_update_end(\u0026stats64-\u003esyncp);\n+\t\tlocal_irq_restore(flags);\n \t} else {\n \t\tdev-\u003enet-\u003estats.tx_errors++;\n \n"
} |
| 2/1 | 2026/09/05 02:34 | agent | patch-evaluator |
0mModel:core Args: null Results: {
"EnableConfigs": [
"USB_USBNET",
"USB_NET_DRIVERS",
"USB",
"NET"
],
"FocusSymbols": [
"usbnet_skb_return",
"tx_complete"
],
"Reasoning": "The patch modifies per-CPU network statistics update routines in usbnet (usbnet_skb_return and tx_complete) by disabling local IRQs before calling this_cpu_ptr(dev-\u003enet-\u003etstats), ensuring safe per-CPU access. USB network devices are reachable and fuzzable via USB device emulation / raw-gadget in standard virtualized environments.",
"WorthFuzzing": true
}Instruction: You are an expert Linux kernel maintainer and security engineer.
Your job is to review a provided patch series and evaluate whether it warrants fuzzing with syzkaller.
IMPORTANT: The changes have ALREADY been applied and committed as the HEAD commit in
your workspace. Do NOT rely on internal assumptions. You must actively use your code access
tools to inspect the actual source code, callers, and surrounding context.
================================================================================
1. CORE TRIAGE PHILOSOPHY
================================================================================
The goal of patch fuzzing is to discover crashes, regressions, exposed latent bugs,
and newly triggered assertions introduced by the patch series.
- REACHABILITY IS THE PRIMARY GATE:
Fuzzing can only discover bugs in code that can actually execute in standard virtualized
environments (GCE or QEMU, utilizing software-emulated devices like USB gadgets, netdev, tun/tap).
If the modified code is structurally unreachable (see Section 2), it MUST NOT be fuzzed,
regardless of whether it adds assertions or complex logic.
- DO NOT BLINDLY TRUST "NO FUNCTIONAL CHANGE" (NFCI) OR "REFACTORING" CLAIMS:
Patch authors routinely label changes as "cleanups", "refactorings", or state
"No functional change intended". Do NOT take these claims at face value.
Code refactorings that rearrange logic, introduce helper functions, or alter state management
in core subsystems frequently introduce subtle semantic shifts or uncover latent kernel bugs.
If reachable executable code is modified or refactored, it MUST be fuzzed.
- NEW OR MODIFIED ASSERTIONS IN REACHABLE CODE MUST BE FUZZED:
When a patch introduces or modifies runtime checks or assertions (e.g., WARN_ON*, VM_WARN_ON*,
BUG_ON*, lockdep_assert*) in reachable code paths, it enforces new or stricter invariants.
Even if the author believes the invariant always holds, fuzzing is essential to verify whether
an unusual sequence of operations can violate it.
================================================================================
2. WHEN TO RETURN WorthFuzzing=false (NEGATIVE CRITERIA)
================================================================================
Return WorthFuzzing=false ONLY IF all modified code falls strictly into one or more of these categories:
- Non-kernel and non-executable changes:
* Modifications to Documentation/, comments, or spelling fixes.
* User-space directories, self-tests, samples, or scripts (e.g., tools/, samples/, scripts/, usr/)
that do not affect the compiled kernel image (vmlinux) or kernel modules.
* Purely decorative logging (e.g., message strings in pr_err, printk, dev_info) or tracepoints
that do not alter control flow or data structures.
* Build system or Kconfig changes that do not alter compiled C logic.
- Structurally unreachable hardware:
* Vendor-specific PCIe switches, SmartNICs, or GPU drivers (e.g., mlxsw, pds_core, qed,
ionic, amdgpu) requiring physical ASIC/PCIe cards not emulated in standard QEMU.
- Unreachable execution paths:
* Driver teardown callbacks (.remove, .shutdown, pci_unregister_driver) executed only during
physical PCI hot-unplug or manual sysfs driver unbinding.
* Code paths exclusive to architectures other than the target architecture.
================================================================================
3. WHEN TO RETURN WorthFuzzing=true (POSITIVE CRITERIA)
================================================================================
Return WorthFuzzing=true whenever the patch touches reachable executable code, including:
- Core Subsystems:
* Any logic modifications in memory management (mm/), synchronization/locking (kernel/locking/),
BPF, scheduler, core networking, VFS, or syscall handling.
- Refactorings and Code Cleanups:
* Any restructuring of reachable data structures, helper abstractions, or algorithm flows.
- Runtime Assertions and Defensive Checks:
* Any introduction or alteration of assertions (WARN_ON*, VM_WARN_ON*, BUG_ON*, etc.) in reachable paths.
- Reachable Drivers and Protocols:
* Drivers accessible via virtual buses (virtio, USB gadget, loopback, netlink, binder, sockets, etc.).
================================================================================
4. EXTRACTING FocusSymbols (PREVENTING DILUTION)
================================================================================
When WorthFuzzing=true, you must extract specific kernel functions into FocusSymbols to guide the fuzzer:
- AVOID UBIQUITOUS LIFECYCLE HOT-PATHS:
Do NOT list generic, ubiquitous functions called by almost every program in the corpus
(including, but not limited to: general memory allocators and deallocators, page fault
and trap handlers, or core synchronization primitives; this is not an exhaustive list).
Listing ubiquitous functions causes the fuzzer to classify thousands of unrelated tests as "focused",
which severely dilutes fuzzing effort away from the actual changes.
- TARGET SPECIFIC FEATURE LOGIC AND ENTRYPOINTS:
List functions that specifically implement the logic being added or altered, or direct API entrypoints
for the subsystem feature under review.
- HANDLING STATIC INLINE FUNCTIONS IN HEADERS (.h):
Compiler-inlined static functions (such as static inlines in mm/*.h or include/linux/*.h) lack
distinct symbol addresses in vmlinux and cannot be targeted directly by symbol coverage filters.
If the changes are primarily in static inline helpers, identify non-static, feature-specific caller
functions in .c files that exercise them (avoiding ubiquitous lifecycle wrappers).
================================================================================
5. IDENTIFYING EnableConfigs
================================================================================
Identify any specific CONFIG_ options required to properly compile and reach the modified code:
- Inspect Kconfig files and #ifdef guards; do not make assumptions.
- Check "depends on" lines in Kconfig to include any non-standard parent subsystem configs needed.
- Strip any '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: Target architecture: amd64
For your convenience, here is the diff of the changes:
commit 4cbc0a18e62b873c7528559d745479914333fba4
Author: syz-cluster <triage@syzkaller.com>
Date: Sat Sep 5 02:34:33 2026 +0000
syz-cluster: applied patch under review
diff --git a/drivers/net/usb/usbnet.c b/drivers/net/usb/usbnet.c
index a19ecf718f36a..6a48f38e105d4 100644
--- a/drivers/net/usb/usbnet.c
+++ b/drivers/net/usb/usbnet.c
@@ -325,7 +325,7 @@ static void __usbnet_status_stop_force(struct usbnet *dev)
*/
void usbnet_skb_return(struct usbnet *dev, struct sk_buff *skb)
{
- struct pcpu_sw_netstats *stats64 = this_cpu_ptr(dev->net->tstats);
+ struct pcpu_sw_netstats *stats64;
unsigned long flags;
int status;
@@ -338,10 +338,13 @@ void usbnet_skb_return(struct usbnet *dev, struct sk_buff *skb)
if (skb->protocol == 0)
skb->protocol = eth_type_trans(skb, dev->net);
- flags = u64_stats_update_begin_irqsave(&stats64->syncp);
+ local_irq_save(flags);
+ stats64 = this_cpu_ptr(dev->net->tstats);
+ u64_stats_update_begin(&stats64->syncp);
u64_stats_inc(&stats64->rx_packets);
u64_stats_add(&stats64->rx_bytes, skb->len);
- u64_stats_update_end_irqrestore(&stats64->syncp, flags);
+ u64_stats_update_end(&stats64->syncp);
+ local_irq_restore(flags);
netif_dbg(dev, rx_status, dev->net, "< rx, len %zu, type 0x%x\n",
skb->len + sizeof(struct ethhdr), skb->protocol);
@@ -1298,13 +1301,16 @@ static void tx_complete(struct urb *urb)
struct usbnet *dev = entry->dev;
if (urb->status == 0) {
- struct pcpu_sw_netstats *stats64 = this_cpu_ptr(dev->net->tstats);
+ struct pcpu_sw_netstats *stats64;
unsigned long flags;
- flags = u64_stats_update_begin_irqsave(&stats64->syncp);
+ local_irq_save(flags);
+ stats64 = this_cpu_ptr(dev->net->tstats);
+ u64_stats_update_begin(&stats64->syncp);
u64_stats_add(&stats64->tx_packets, entry->packets);
u64_stats_add(&stats64->tx_bytes, entry->length);
- u64_stats_update_end_irqrestore(&stats64->syncp, flags);
+ u64_stats_update_end(&stats64->syncp);
+ local_irq_restore(flags);
} else {
dev->net->stats.tx_errors++;
|
| 3/2 | 2026/09/05 02:34 | llm | patch-evaluator |
0mModel:gemini-3.7-flash Args: null Results: null Tokens: input: 3503 output: 28 thoughts: 725 Thoughts: **Analyzing a USB Network Driver Patch** Okay, let's dive into this patch. First, I see it's touching `drivers/net/usb/usbnet.c`, which is a key driver for USB network interfaces. Seems like we're looking at some critical changes in interrupt handling or statistics gathering – always an area that demands close scrutiny. The functions modified are `usbnet_skb_return` and `tx_complete`, which are pretty fundamental components: handling received SKBs (socket buffer) and transmission completion, respectively. Right, let's dissect the code diffs. In both `usbnet_skb_return` and `tx_complete`, the core change involves reordering the sequence of operations around the per-CPU statistics updates. Specifically, the original code had `this_cpu_ptr(dev->net->tstats)` *before* disabling interrupts or saving the interrupt state with `u64_stats_update_begin_irqsave`. The revised version places `local_irq_save(flags)` *before* the `this_cpu_ptr` call and `local_irq_restore(flags)` at the end. They switched the atomic update functions with the non-atomic ones (`u64_stats_update_begin` and `u64_stats_update_end`). The *why* is the key question. The comment clues us in. The original order could have led to a race condition. If `this_cpu_ptr` is called with preemption enabled, or before disabling interrupts, the CPU could potentially migrate or be preempted. This could cause it to access incorrect per-CPU statistics (or even the wrong CPU's stats), potentially triggering `DEBUG_PREEMPT` or worse. The interrupt handlers are sensitive. Now, let's assess the impact. USB network devices, including those supported by `usbnet`, are definitely within the purview of syzkaller and its USB fuzzing capabilities. I know that because of my experience. We can instantiate `usbnet` devices such as CDC Ethernet, ASIX, etc. or raw usb gadgets through various means: USB gadget, Raw Gadget, USB emulation, and, most importantly, syzkaller's USB fuzzing. USB network interfaces are, therefore, fuzzable using syzkaller, e.g. using `syz_usb_connect`. To fully understand the context, I need to verify that `usbnet` is correctly configured in the kernel. I should quickly check the Kconfig entry for `drivers/net/usb/usbnet.c` using tools such as `grepper` or by examining the `drivers/net/usb/Makefile` and `drivers/net/usb/Kconfig` files. That'll confirm its dependencies and enable status, just to make sure there are no other configurations in play. |
| 4/2 | 2026/09/05 02:34 | tool | grepper |
0mArgs:{
"Expression": "usbnet",
"PathPrefix": "drivers/net/usb/"
}Results: {
"Output": "\nFull output is too long, showing 500 out of 4874 lines.\nUse more precise expression if possible.\n\ndrivers/net/usb/Kconfig=132=config USB_USBNET\n--\ndrivers/net/usb/Kconfig-140-\ndrivers/net/usb/Kconfig:141:\t The USB host runs \"usbnet\", and the other end of the link might be:\ndrivers/net/usb/Kconfig-142-\n--\ndrivers/net/usb/Kconfig-160-\ndrivers/net/usb/Kconfig:161:\t For more information see \u003chttp://www.linux-usb.org/usbnet/\u003e.\ndrivers/net/usb/Kconfig-162-\ndrivers/net/usb/Kconfig-163-\t To compile this driver as a module, choose M here: the\ndrivers/net/usb/Kconfig:164:\t module will be called usbnet.\ndrivers/net/usb/Kconfig-165-\n--\ndrivers/net/usb/Makefile=29=obj-$(CONFIG_USB_NET_MCS7830)\t+= mcs7830.o\ndrivers/net/usb/Makefile:30:obj-$(CONFIG_USB_USBNET)\t+= usbnet.o\ndrivers/net/usb/Makefile-31-obj-$(CONFIG_USB_NET_INT51X1)\t+= int51x1.o\n--\ndrivers/net/usb/aqc111.c-17-#include \u003clinux/usb/cdc.h\u003e\ndrivers/net/usb/aqc111.c:18:#include \u003clinux/usb/usbnet.h\u003e\ndrivers/net/usb/aqc111.c-19-#include \u003clinux/linkmode.h\u003e\n--\ndrivers/net/usb/aqc111.c-22-\ndrivers/net/usb/aqc111.c:23:static int aqc111_read_cmd_nopm(struct usbnet *dev, u8 cmd, u16 value,\ndrivers/net/usb/aqc111.c-24-\t\t\t\tu16 index, u16 size, void *data)\n--\ndrivers/net/usb/aqc111.c-27-\ndrivers/net/usb/aqc111.c:28:\tret = usbnet_read_cmd_nopm(dev, cmd, USB_DIR_IN | USB_TYPE_VENDOR |\ndrivers/net/usb/aqc111.c-29-\t\t\t\t USB_RECIP_DEVICE, value, index, data, size);\n--\ndrivers/net/usb/aqc111.c-41-\ndrivers/net/usb/aqc111.c:42:static int aqc111_read_cmd(struct usbnet *dev, u8 cmd, u16 value,\ndrivers/net/usb/aqc111.c-43-\t\t\t u16 index, u16 size, void *data)\n--\ndrivers/net/usb/aqc111.c-46-\ndrivers/net/usb/aqc111.c:47:\tret = usbnet_read_cmd(dev, cmd, USB_DIR_IN | USB_TYPE_VENDOR |\ndrivers/net/usb/aqc111.c-48-\t\t\t USB_RECIP_DEVICE, value, index, data, size);\n--\ndrivers/net/usb/aqc111.c-60-\ndrivers/net/usb/aqc111.c:61:static int aqc111_read16_cmd_nopm(struct usbnet *dev, u8 cmd, u16 value,\ndrivers/net/usb/aqc111.c-62-\t\t\t\t u16 index, u16 *data)\n--\ndrivers/net/usb/aqc111.c-71-\ndrivers/net/usb/aqc111.c:72:static int aqc111_read16_cmd(struct usbnet *dev, u8 cmd, u16 value,\ndrivers/net/usb/aqc111.c-73-\t\t\t u16 index, u16 *data)\n--\ndrivers/net/usb/aqc111.c-82-\ndrivers/net/usb/aqc111.c:83:static int __aqc111_write_cmd(struct usbnet *dev, u8 cmd, u8 reqtype,\ndrivers/net/usb/aqc111.c-84-\t\t\t u16 value, u16 index, u16 size, const void *data)\n--\ndrivers/net/usb/aqc111.c-113-\ndrivers/net/usb/aqc111.c:114:static int aqc111_write_cmd_nopm(struct usbnet *dev, u8 cmd, u16 value,\ndrivers/net/usb/aqc111.c-115-\t\t\t\t u16 index, u16 size, void *data)\n--\ndrivers/net/usb/aqc111.c-124-\ndrivers/net/usb/aqc111.c:125:static int aqc111_write_cmd(struct usbnet *dev, u8 cmd, u16 value,\ndrivers/net/usb/aqc111.c-126-\t\t\t u16 index, u16 size, const void *data)\n--\ndrivers/net/usb/aqc111.c-140-\ndrivers/net/usb/aqc111.c:141:static int aqc111_write16_cmd_nopm(struct usbnet *dev, u8 cmd, u16 value,\ndrivers/net/usb/aqc111.c-142-\t\t\t\t u16 index, u16 *data)\n--\ndrivers/net/usb/aqc111.c-150-\ndrivers/net/usb/aqc111.c:151:static int aqc111_write16_cmd(struct usbnet *dev, u8 cmd, u16 value,\ndrivers/net/usb/aqc111.c-152-\t\t\t u16 index, u16 *data)\n--\ndrivers/net/usb/aqc111.c-160-\ndrivers/net/usb/aqc111.c:161:static int aqc111_write32_cmd_nopm(struct usbnet *dev, u8 cmd, u16 value,\ndrivers/net/usb/aqc111.c-162-\t\t\t\t u16 index, u32 *data)\n--\ndrivers/net/usb/aqc111.c-170-\ndrivers/net/usb/aqc111.c:171:static int aqc111_write32_cmd(struct usbnet *dev, u8 cmd, u16 value,\ndrivers/net/usb/aqc111.c-172-\t\t\t u16 index, u32 *data)\n--\ndrivers/net/usb/aqc111.c-180-\ndrivers/net/usb/aqc111.c:181:static int aqc111_write_cmd_async(struct usbnet *dev, u8 cmd, u16 value,\ndrivers/net/usb/aqc111.c-182-\t\t\t\t u16 index, u16 size, void *data)\ndrivers/net/usb/aqc111.c-183-{\ndrivers/net/usb/aqc111.c:184:\treturn usbnet_write_cmd_async(dev, cmd, USB_DIR_OUT | USB_TYPE_VENDOR |\ndrivers/net/usb/aqc111.c-185-\t\t\t\t USB_RECIP_DEVICE, value, index, data,\n--\ndrivers/net/usb/aqc111.c-188-\ndrivers/net/usb/aqc111.c:189:static int aqc111_write16_cmd_async(struct usbnet *dev, u8 cmd, u16 value,\ndrivers/net/usb/aqc111.c-190-\t\t\t\t u16 index, u16 *data)\n--\ndrivers/net/usb/aqc111.c=200=static void aqc111_get_drvinfo(struct net_device *net,\n--\ndrivers/net/usb/aqc111.c-202-{\ndrivers/net/usb/aqc111.c:203:\tstruct usbnet *dev = netdev_priv(net);\ndrivers/net/usb/aqc111.c-204-\tstruct aqc111_data *aqc111_data = dev-\u003edriver_priv;\n--\ndrivers/net/usb/aqc111.c-206-\t/* Inherit standard device info */\ndrivers/net/usb/aqc111.c:207:\tusbnet_get_drvinfo(net, info);\ndrivers/net/usb/aqc111.c-208-\tsnprintf(info-\u003efw_version, sizeof(info-\u003efw_version), \"%u.%u.%u\",\n--\ndrivers/net/usb/aqc111.c=214=static void aqc111_get_wol(struct net_device *net,\n--\ndrivers/net/usb/aqc111.c-216-{\ndrivers/net/usb/aqc111.c:217:\tstruct usbnet *dev = netdev_priv(net);\ndrivers/net/usb/aqc111.c-218-\tstruct aqc111_data *aqc111_data = dev-\u003edriver_priv;\n--\ndrivers/net/usb/aqc111.c=227=static int aqc111_set_wol(struct net_device *net,\n--\ndrivers/net/usb/aqc111.c-229-{\ndrivers/net/usb/aqc111.c:230:\tstruct usbnet *dev = netdev_priv(net);\ndrivers/net/usb/aqc111.c-231-\tstruct aqc111_data *aqc111_data = dev-\u003edriver_priv;\n--\ndrivers/net/usb/aqc111.c=266=static int aqc111_get_link_ksettings(struct net_device *net,\n--\ndrivers/net/usb/aqc111.c-268-{\ndrivers/net/usb/aqc111.c:269:\tstruct usbnet *dev = netdev_priv(net);\ndrivers/net/usb/aqc111.c-270-\tstruct aqc111_data *aqc111_data = dev-\u003edriver_priv;\n--\ndrivers/net/usb/aqc111.c-320-\ndrivers/net/usb/aqc111.c:321:static void aqc111_set_phy_speed(struct usbnet *dev, u8 autoneg, u16 speed)\ndrivers/net/usb/aqc111.c-322-{\n--\ndrivers/net/usb/aqc111.c=368=static int aqc111_set_link_ksettings(struct net_device *net,\n--\ndrivers/net/usb/aqc111.c-370-{\ndrivers/net/usb/aqc111.c:371:\tstruct usbnet *dev = netdev_priv(net);\ndrivers/net/usb/aqc111.c-372-\tstruct aqc111_data *aqc111_data = dev-\u003edriver_priv;\n--\ndrivers/net/usb/aqc111.c=411=static const struct ethtool_ops aqc111_ethtool_ops = {\n--\ndrivers/net/usb/aqc111.c-414-\t.set_wol = aqc111_set_wol,\ndrivers/net/usb/aqc111.c:415:\t.get_msglevel = usbnet_get_msglevel,\ndrivers/net/usb/aqc111.c:416:\t.set_msglevel = usbnet_set_msglevel,\ndrivers/net/usb/aqc111.c-417-\t.get_link = ethtool_op_get_link,\n--\ndrivers/net/usb/aqc111.c=422=static int aqc111_change_mtu(struct net_device *net, int new_mtu)\ndrivers/net/usb/aqc111.c-423-{\ndrivers/net/usb/aqc111.c:424:\tstruct usbnet *dev = netdev_priv(net);\ndrivers/net/usb/aqc111.c-425-\tu16 reg16 = 0;\n--\ndrivers/net/usb/aqc111.c=464=static int aqc111_set_mac_addr(struct net_device *net, void *p)\ndrivers/net/usb/aqc111.c-465-{\ndrivers/net/usb/aqc111.c:466:\tstruct usbnet *dev = netdev_priv(net);\ndrivers/net/usb/aqc111.c-467-\tint ret = 0;\n--\ndrivers/net/usb/aqc111.c=478=static int aqc111_vlan_rx_kill_vid(struct net_device *net,\n--\ndrivers/net/usb/aqc111.c-480-{\ndrivers/net/usb/aqc111.c:481:\tstruct usbnet *dev = netdev_priv(net);\ndrivers/net/usb/aqc111.c-482-\tu8 vlan_ctrl = 0;\n--\ndrivers/net/usb/aqc111.c=504=static int aqc111_vlan_rx_add_vid(struct net_device *net, __be16 proto, u16 vid)\ndrivers/net/usb/aqc111.c-505-{\ndrivers/net/usb/aqc111.c:506:\tstruct usbnet *dev = netdev_priv(net);\ndrivers/net/usb/aqc111.c-507-\tu8 vlan_ctrl = 0;\n--\ndrivers/net/usb/aqc111.c=529=static void aqc111_set_rx_mode(struct net_device *net)\ndrivers/net/usb/aqc111.c-530-{\ndrivers/net/usb/aqc111.c:531:\tstruct usbnet *dev = netdev_priv(net);\ndrivers/net/usb/aqc111.c-532-\tstruct aqc111_data *aqc111_data = dev-\u003edriver_priv;\n--\ndrivers/net/usb/aqc111.c=566=static int aqc111_set_features(struct net_device *net,\n--\ndrivers/net/usb/aqc111.c-568-{\ndrivers/net/usb/aqc111.c:569:\tstruct usbnet *dev = netdev_priv(net);\ndrivers/net/usb/aqc111.c-570-\tstruct aqc111_data *aqc111_data = dev-\u003edriver_priv;\n--\ndrivers/net/usb/aqc111.c=640=static const struct net_device_ops aqc111_netdev_ops = {\ndrivers/net/usb/aqc111.c:641:\t.ndo_open\t\t= usbnet_open,\ndrivers/net/usb/aqc111.c:642:\t.ndo_stop\t\t= usbnet_stop,\ndrivers/net/usb/aqc111.c:643:\t.ndo_start_xmit\t\t= usbnet_start_xmit,\ndrivers/net/usb/aqc111.c:644:\t.ndo_tx_timeout\t\t= usbnet_tx_timeout,\ndrivers/net/usb/aqc111.c-645-\t.ndo_get_stats64\t= dev_get_tstats64,\n--\ndrivers/net/usb/aqc111.c-654-\ndrivers/net/usb/aqc111.c:655:static int aqc111_read_perm_mac(struct usbnet *dev)\ndrivers/net/usb/aqc111.c-656-{\n--\ndrivers/net/usb/aqc111.c-670-\ndrivers/net/usb/aqc111.c:671:static void aqc111_read_fw_version(struct usbnet *dev,\ndrivers/net/usb/aqc111.c-672-\t\t\t\t struct aqc111_data *aqc111_data)\n--\ndrivers/net/usb/aqc111.c-684-\ndrivers/net/usb/aqc111.c:685:static int aqc111_bind(struct usbnet *dev, struct usb_interface *intf)\ndrivers/net/usb/aqc111.c-686-{\n--\ndrivers/net/usb/aqc111.c-699-\ndrivers/net/usb/aqc111.c:700:\tret = usbnet_get_endpoints(dev, intf);\ndrivers/net/usb/aqc111.c-701-\tif (ret \u003c 0) {\ndrivers/net/usb/aqc111.c:702:\t\tnetdev_dbg(dev-\u003enet, \"usbnet_get_endpoints failed\");\ndrivers/net/usb/aqc111.c-703-\t\treturn ret;\n--\ndrivers/net/usb/aqc111.c-752-\ndrivers/net/usb/aqc111.c:753:static void aqc111_unbind(struct usbnet *dev, struct usb_interface *intf)\ndrivers/net/usb/aqc111.c-754-{\n--\ndrivers/net/usb/aqc111.c-775-\ndrivers/net/usb/aqc111.c:776:static void aqc111_status(struct usbnet *dev, struct urb *urb)\ndrivers/net/usb/aqc111.c-777-{\n--\ndrivers/net/usb/aqc111.c-797-\tif (netif_carrier_ok(dev-\u003enet) != link)\ndrivers/net/usb/aqc111.c:798:\t\tusbnet_defer_kevent(dev, EVENT_LINK_RESET);\ndrivers/net/usb/aqc111.c-799-}\ndrivers/net/usb/aqc111.c-800-\ndrivers/net/usb/aqc111.c:801:static void aqc111_configure_rx(struct usbnet *dev,\ndrivers/net/usb/aqc111.c-802-\t\t\t\tstruct aqc111_data *aqc111_data)\n--\ndrivers/net/usb/aqc111.c-880-\ndrivers/net/usb/aqc111.c:881:static void aqc111_configure_csum_offload(struct usbnet *dev)\ndrivers/net/usb/aqc111.c-882-{\n--\ndrivers/net/usb/aqc111.c-900-\ndrivers/net/usb/aqc111.c:901:static int aqc111_link_reset(struct usbnet *dev)\ndrivers/net/usb/aqc111.c-902-{\n--\ndrivers/net/usb/aqc111.c-989-\ndrivers/net/usb/aqc111.c:990:static int aqc111_reset(struct usbnet *dev)\ndrivers/net/usb/aqc111.c-991-{\n--\ndrivers/net/usb/aqc111.c-1033-\ndrivers/net/usb/aqc111.c:1034:static int aqc111_stop(struct usbnet *dev)\ndrivers/net/usb/aqc111.c-1035-{\n--\ndrivers/net/usb/aqc111.c=1057=static void aqc111_rx_checksum(struct sk_buff *skb, u64 pkt_desc)\n--\ndrivers/net/usb/aqc111.c-1071-\ndrivers/net/usb/aqc111.c:1072:static int aqc111_rx_fixup(struct usbnet *dev, struct sk_buff *skb)\ndrivers/net/usb/aqc111.c-1073-{\n--\ndrivers/net/usb/aqc111.c-1162-\ndrivers/net/usb/aqc111.c:1163:\t\tusbnet_skb_return(dev, new_skb);\ndrivers/net/usb/aqc111.c-1164-\t\tif (pkt_count == 0)\n--\ndrivers/net/usb/aqc111.c-1180-\ndrivers/net/usb/aqc111.c:1181:static struct sk_buff *aqc111_tx_fixup(struct usbnet *dev, struct sk_buff *skb,\ndrivers/net/usb/aqc111.c-1182-\t\t\t\t gfp_t flags)\n--\ndrivers/net/usb/aqc111.c-1236-\ndrivers/net/usb/aqc111.c:1237:\tusbnet_set_skb_tx_stats(skb, 1, 0);\ndrivers/net/usb/aqc111.c-1238-\n--\ndrivers/net/usb/aqc111.c=1322=static int aqc111_suspend(struct usb_interface *intf, pm_message_t message)\ndrivers/net/usb/aqc111.c-1323-{\ndrivers/net/usb/aqc111.c:1324:\tstruct usbnet *dev = usb_get_intfdata(intf);\ndrivers/net/usb/aqc111.c-1325-\tstruct aqc111_data *aqc111_data = dev-\u003edriver_priv;\n--\ndrivers/net/usb/aqc111.c-1329-\ndrivers/net/usb/aqc111.c:1330:\tusbnet_suspend(intf, message);\ndrivers/net/usb/aqc111.c-1331-\n--\ndrivers/net/usb/aqc111.c=1418=static int aqc111_resume(struct usb_interface *intf)\ndrivers/net/usb/aqc111.c-1419-{\ndrivers/net/usb/aqc111.c:1420:\tstruct usbnet *dev = usb_get_intfdata(intf);\ndrivers/net/usb/aqc111.c-1421-\tstruct aqc111_data *aqc111_data = dev-\u003edriver_priv;\n--\ndrivers/net/usb/aqc111.c-1456-\ndrivers/net/usb/aqc111.c:1457:\treturn usbnet_resume(intf);\ndrivers/net/usb/aqc111.c-1458-}\n--\ndrivers/net/usb/aqc111.c=1481=static struct usb_driver aq_driver = {\n--\ndrivers/net/usb/aqc111.c-1483-\t.id_table\t= products,\ndrivers/net/usb/aqc111.c:1484:\t.probe\t\t= usbnet_probe,\ndrivers/net/usb/aqc111.c-1485-\t.suspend\t= aqc111_suspend,\ndrivers/net/usb/aqc111.c-1486-\t.resume\t\t= aqc111_resume,\ndrivers/net/usb/aqc111.c:1487:\t.disconnect\t= usbnet_disconnect,\ndrivers/net/usb/aqc111.c-1488-};\n--\ndrivers/net/usb/asix.h-24-#include \u003clinux/crc32.h\u003e\ndrivers/net/usb/asix.h:25:#include \u003clinux/usb/usbnet.h\u003e\ndrivers/net/usb/asix.h-26-#include \u003clinux/slab.h\u003e\n--\ndrivers/net/usb/asix.h=178=struct asix_common_private {\ndrivers/net/usb/asix.h:179:\tvoid (*resume)(struct usbnet *dev);\ndrivers/net/usb/asix.h:180:\tvoid (*suspend)(struct usbnet *dev);\ndrivers/net/usb/asix.h:181:\tint (*reset)(struct usbnet *dev, int in_pm);\ndrivers/net/usb/asix.h-182-\tu16 presvd_phy_advertise;\n--\ndrivers/net/usb/asix.h=195=extern const struct driver_info ax88172a_info;\n--\ndrivers/net/usb/asix.h-199-\ndrivers/net/usb/asix.h:200:int __must_check asix_read_cmd(struct usbnet *dev, u8 cmd, u16 value, u16 index,\ndrivers/net/usb/asix.h-201-\t\t\t u16 size, void *data, int in_pm);\ndrivers/net/usb/asix.h-202-\ndrivers/net/usb/asix.h:203:int asix_write_cmd(struct usbnet *dev, u8 cmd, u16 value, u16 index,\ndrivers/net/usb/asix.h-204-\t\t u16 size, void *data, int in_pm);\ndrivers/net/usb/asix.h-205-\ndrivers/net/usb/asix.h:206:void asix_write_cmd_async(struct usbnet *dev, u8 cmd, u16 value,\ndrivers/net/usb/asix.h-207-\t\t\t u16 index, u16 size, void *data);\ndrivers/net/usb/asix.h-208-\ndrivers/net/usb/asix.h:209:int asix_rx_fixup_internal(struct usbnet *dev, struct sk_buff *skb,\ndrivers/net/usb/asix.h-210-\t\t\t struct asix_rx_fixup_info *rx);\ndrivers/net/usb/asix.h:211:int asix_rx_fixup_common(struct usbnet *dev, struct sk_buff *skb);\ndrivers/net/usb/asix.h-212-void asix_rx_fixup_common_free(struct asix_common_private *dp);\ndrivers/net/usb/asix.h-213-\ndrivers/net/usb/asix.h:214:struct sk_buff *asix_tx_fixup(struct usbnet *dev, struct sk_buff *skb,\ndrivers/net/usb/asix.h-215-\t\t\t gfp_t flags);\ndrivers/net/usb/asix.h-216-\ndrivers/net/usb/asix.h:217:int asix_read_phy_addr(struct usbnet *dev, bool internal);\ndrivers/net/usb/asix.h-218-\ndrivers/net/usb/asix.h:219:int asix_sw_reset(struct usbnet *dev, u8 flags, int in_pm);\ndrivers/net/usb/asix.h-220-\ndrivers/net/usb/asix.h:221:u16 asix_read_rx_ctl(struct usbnet *dev, int in_pm);\ndrivers/net/usb/asix.h:222:int asix_write_rx_ctl(struct usbnet *dev, u16 mode, int in_pm);\ndrivers/net/usb/asix.h-223-\ndrivers/net/usb/asix.h:224:u16 asix_read_medium_status(struct usbnet *dev, int in_pm);\ndrivers/net/usb/asix.h:225:int asix_write_medium_mode(struct usbnet *dev, u16 mode, int in_pm);\ndrivers/net/usb/asix.h-226-\ndrivers/net/usb/asix.h:227:int asix_write_gpio(struct usbnet *dev, u16 value, int sleep, int in_pm);\ndrivers/net/usb/asix.h-228-\n--\ndrivers/net/usb/asix_common.c-13-\ndrivers/net/usb/asix_common.c:14:int __must_check asix_read_cmd(struct usbnet *dev, u8 cmd, u16 value, u16 index,\ndrivers/net/usb/asix_common.c-15-\t\t\t u16 size, void *data, int in_pm)\n--\ndrivers/net/usb/asix_common.c-17-\tint ret;\ndrivers/net/usb/asix_common.c:18:\tint (*fn)(struct usbnet *, u8, u8, u16, u16, void *, u16);\ndrivers/net/usb/asix_common.c-19-\n--\ndrivers/net/usb/asix_common.c-22-\tif (!in_pm)\ndrivers/net/usb/asix_common.c:23:\t\tfn = usbnet_read_cmd;\ndrivers/net/usb/asix_common.c-24-\telse\ndrivers/net/usb/asix_common.c:25:\t\tfn = usbnet_read_cmd_nopm;\ndrivers/net/usb/asix_common.c-26-\n--\ndrivers/net/usb/asix_common.c-39-\ndrivers/net/usb/asix_common.c:40:int asix_write_cmd(struct usbnet *dev, u8 cmd, u16 value, u16 index,\ndrivers/net/usb/asix_common.c-41-\t\t u16 size, void *data, int in_pm)\n--\ndrivers/net/usb/asix_common.c-43-\tint ret;\ndrivers/net/usb/asix_common.c:44:\tint (*fn)(struct usbnet *, u8, u8, u16, u16, const void *, u16);\ndrivers/net/usb/asix_common.c-45-\n--\ndrivers/net/usb/asix_common.c-48-\tif (!in_pm)\ndrivers/net/usb/asix_common.c:49:\t\tfn = usbnet_write_cmd;\ndrivers/net/usb/asix_common.c-50-\telse\ndrivers/net/usb/asix_common.c:51:\t\tfn = usbnet_write_cmd_nopm;\ndrivers/net/usb/asix_common.c-52-\n--\ndrivers/net/usb/asix_common.c-62-\ndrivers/net/usb/asix_common.c:63:void asix_write_cmd_async(struct usbnet *dev, u8 cmd, u16 value, u16 index,\ndrivers/net/usb/asix_common.c-64-\t\t\t u16 size, void *data)\ndrivers/net/usb/asix_common.c-65-{\ndrivers/net/usb/asix_common.c:66:\tusbnet_write_cmd_async(dev, cmd,\ndrivers/net/usb/asix_common.c-67-\t\t\t USB_DIR_OUT | USB_TYPE_VENDOR | USB_RECIP_DEVICE,\n--\ndrivers/net/usb/asix_common.c-70-\ndrivers/net/usb/asix_common.c:71:static int asix_set_sw_mii(struct usbnet *dev, int in_pm)\ndrivers/net/usb/asix_common.c-72-{\n--\ndrivers/net/usb/asix_common.c-81-\ndrivers/net/usb/asix_common.c:82:static int asix_set_hw_mii(struct usbnet *dev, int in_pm)\ndrivers/net/usb/asix_common.c-83-{\n--\ndrivers/net/usb/asix_common.c-91-\ndrivers/net/usb/asix_common.c:92:static int asix_check_host_enable(struct usbnet *dev, int in_pm)\ndrivers/net/usb/asix_common.c-93-{\n--\ndrivers/net/usb/asix_common.c=115=static void reset_asix_rx_fixup_info(struct asix_rx_fixup_info *rx)\n--\ndrivers/net/usb/asix_common.c-135-\ndrivers/net/usb/asix_common.c:136:int asix_rx_fixup_internal(struct usbnet *dev, struct sk_buff *skb,\ndrivers/net/usb/asix_common.c-137-\t\t\t struct asix_rx_fixup_info *rx)\n--\ndrivers/net/usb/asix_common.c-223-\t\t\tif (!rx-\u003eremaining) {\ndrivers/net/usb/asix_common.c:224:\t\t\t\tusbnet_skb_return(dev, rx-\u003eax_skb);\ndrivers/net/usb/asix_common.c-225-\t\t\t\trx-\u003eax_skb = NULL;\n--\ndrivers/net/usb/asix_common.c-241-\ndrivers/net/usb/asix_common.c:242:int asix_rx_fixup_common(struct usbnet *dev, struct sk_buff *skb)\ndrivers/net/usb/asix_common.c-243-{\n--\ndrivers/net/usb/asix_common.c=250=void asix_rx_fixup_common_free(struct asix_common_private *dp)\n--\ndrivers/net/usb/asix_common.c-264-\ndrivers/net/usb/asix_common.c:265:struct sk_buff *asix_tx_fixup(struct usbnet *dev, struct sk_buff *skb,\ndrivers/net/usb/asix_common.c-266-\t\t\t gfp_t flags)\n--\ndrivers/net/usb/asix_common.c-316-\ndrivers/net/usb/asix_common.c:317:\tusbnet_set_skb_tx_stats(skb, 1, 0);\ndrivers/net/usb/asix_common.c-318-\treturn skb;\n--\ndrivers/net/usb/asix_common.c-320-\ndrivers/net/usb/asix_common.c:321:int asix_read_phy_addr(struct usbnet *dev, bool internal)\ndrivers/net/usb/asix_common.c-322-{\n--\ndrivers/net/usb/asix_common.c-353-\ndrivers/net/usb/asix_common.c:354:int asix_sw_reset(struct usbnet *dev, u8 flags, int in_pm)\ndrivers/net/usb/asix_common.c-355-{\n--\ndrivers/net/usb/asix_common.c-364-\ndrivers/net/usb/asix_common.c:365:u16 asix_read_rx_ctl(struct usbnet *dev, int in_pm)\ndrivers/net/usb/asix_common.c-366-{\n--\ndrivers/net/usb/asix_common.c-378-\ndrivers/net/usb/asix_common.c:379:int asix_write_rx_ctl(struct usbnet *dev, u16 mode, int in_pm)\ndrivers/net/usb/asix_common.c-380-{\n--\ndrivers/net/usb/asix_common.c-391-\ndrivers/net/usb/asix_common.c:392:u16 asix_read_medium_status(struct usbnet *dev, int in_pm)\ndrivers/net/usb/asix_common.c-393-{\n--\ndrivers/net/usb/asix_common.c-407-\ndrivers/net/usb/asix_common.c:408:int asix_write_medium_mode(struct usbnet *dev, u16 mode, int in_pm)\ndrivers/net/usb/asix_common.c-409-{\n--\ndrivers/net/usb/asix_common.c-421-\ndrivers/net/usb/asix_common.c:422:int asix_write_gpio(struct usbnet *dev, u16 value, int sleep, int in_pm)\ndrivers/net/usb/asix_common.c-423-{\n--\ndrivers/net/usb/asix_common.c=441=void asix_set_multicast(struct net_device *net)\ndrivers/net/usb/asix_common.c-442-{\ndrivers/net/usb/asix_common.c:443:\tstruct usbnet *dev = netdev_priv(net);\ndrivers/net/usb/asix_common.c-444-\tstruct asix_data *data = (struct asix_data *)\u0026dev-\u003edata;\n--\ndrivers/net/usb/asix_common.c=480=static int __asix_mdio_read(struct net_device *netdev, int phy_id, int loc,\n--\ndrivers/net/usb/asix_common.c-482-{\ndrivers/net/usb/asix_common.c:483:\tstruct usbnet *dev = netdev_priv(netdev);\ndrivers/net/usb/asix_common.c-484-\t__le16 res;\n--\ndrivers/net/usb/asix_common.c=515=static int __asix_mdio_write(struct net_device *netdev, int phy_id, int loc,\n--\ndrivers/net/usb/asix_common.c-517-{\ndrivers/net/usb/asix_common.c:518:\tstruct usbnet *dev = netdev_priv(netdev);\ndrivers/net/usb/asix_common.c-519-\t__le16 res = cpu_to_le16(val);\n--\ndrivers/net/usb/asix_common.c=549=int asix_mdio_bus_read(struct mii_bus *bus, int phy_id, int regnum)\ndrivers/net/usb/asix_common.c-550-{\ndrivers/net/usb/asix_common.c:551:\tstruct usbnet *priv = bus-\u003epriv;\ndrivers/net/usb/asix_common.c-552-\n--\ndrivers/net/usb/asix_common.c=556=int asix_mdio_bus_write(struct mii_bus *bus, int phy_id, int regnum, u16 val)\ndrivers/net/usb/asix_common.c-557-{\ndrivers/net/usb/asix_common.c:558:\tstruct usbnet *priv = bus-\u003epriv;\ndrivers/net/usb/asix_common.c-559-\n--\ndrivers/net/usb/asix_common.c=574=void asix_get_wol(struct net_device *net, struct ethtool_wolinfo *wolinfo)\ndrivers/net/usb/asix_common.c-575-{\ndrivers/net/usb/asix_common.c:576:\tstruct usbnet *dev = netdev_priv(net);\ndrivers/net/usb/asix_common.c-577-\tu8 opt;\n--\ndrivers/net/usb/asix_common.c=593=int asix_set_wol(struct net_device *net, struct ethtool_wolinfo *wolinfo)\ndrivers/net/usb/asix_common.c-594-{\ndrivers/net/usb/asix_common.c:595:\tstruct usbnet *dev = netdev_priv(net);\ndrivers/net/usb/asix_common.c-596-\tu8 opt = 0;\n--\ndrivers/net/usb/asix_common.c=618=int asix_get_eeprom(struct net_device *net, struct ethtool_eeprom *eeprom,\n--\ndrivers/net/usb/asix_common.c-620-{\ndrivers/net/usb/asix_common.c:621:\tstruct usbnet *dev = netdev_priv(net);\ndrivers/net/usb/asix_common.c-622-\tu16 *eeprom_buff;\n--\ndrivers/net/usb/asix_common.c=653=int asix_set_eeprom(struct net_device *net, struct ethtool_eeprom *eeprom,\n--\ndrivers/net/usb/asix_common.c-655-{\ndrivers/net/usb/asix_common.c:656:\tstruct usbnet *dev = netdev_priv(net);\ndrivers/net/usb/asix_common.c-657-\tu16 *eeprom_buff;\n--\ndrivers/net/usb/asix_common.c=734=int asix_set_mac_address(struct net_device *net, void *p)\ndrivers/net/usb/asix_common.c-735-{\ndrivers/net/usb/asix_common.c:736:\tstruct usbnet *dev = netdev_priv(net);\ndrivers/net/usb/asix_common.c-737-\tstruct asix_data *data = (struct asix_data *)\u0026dev-\u003edata;\n--\ndrivers/net/usb/asix_devices.c=35=struct ax88172_int_data {\n--\ndrivers/net/usb/asix_devices.c-42-\ndrivers/net/usb/asix_devices.c:43:static void asix_status(struct usbnet *dev, struct urb *urb)\ndrivers/net/usb/asix_devices.c-44-{\n--\ndrivers/net/usb/asix_devices.c-53-\tif (netif_carrier_ok(dev-\u003enet) != link) {\ndrivers/net/usb/asix_devices.c:54:\t\tusbnet_link_change(dev, link, 1);\ndrivers/net/usb/asix_devices.c-55-\t\tnetdev_dbg(dev-\u003enet, \"Link Status is: %d\\n\", link);\n--\ndrivers/net/usb/asix_devices.c-58-\ndrivers/net/usb/asix_devices.c:59:static void asix_set_netdev_dev_addr(struct usbnet *dev, u8 *addr)\ndrivers/net/usb/asix_devices.c-60-{\n--\ndrivers/net/usb/asix_devices.c-69-/* Get the PHY Identifier from the PHYSID1 \u0026 PHYSID2 MII registers */\ndrivers/net/usb/asix_devices.c:70:static u32 asix_get_phyid(struct usbnet *dev)\ndrivers/net/usb/asix_devices.c-71-{\n--\ndrivers/net/usb/asix_devices.c-100-/* We need to override some ethtool_ops so we require our\ndrivers/net/usb/asix_devices.c:101: own structure so we don't interfere with other usbnet\ndrivers/net/usb/asix_devices.c-102- devices that may be connected at the same time. */\ndrivers/net/usb/asix_devices.c=103=static const struct ethtool_ops ax88172_ethtool_ops = {\ndrivers/net/usb/asix_devices.c:104:\t.get_drvinfo\t\t= usbnet_get_drvinfo,\ndrivers/net/usb/asix_devices.c:105:\t.get_link\t\t= usbnet_get_link,\ndrivers/net/usb/asix_devices.c:106:\t.get_msglevel\t\t= usbnet_get_msglevel,\ndrivers/net/usb/asix_devices.c:107:\t.set_msglevel\t\t= usbnet_set_msglevel,\ndrivers/net/usb/asix_devices.c-108-\t.get_wol\t\t= asix_get_wol,\n--\ndrivers/net/usb/asix_devices.c-112-\t.set_eeprom\t\t= asix_set_eeprom,\ndrivers/net/usb/asix_devices.c:113:\t.nway_reset\t\t= usbnet_nway_reset,\ndrivers/net/usb/asix_devices.c:114:\t.get_link_ksettings\t= usbnet_get_link_ksettings_mii,\ndrivers/net/usb/asix_devices.c:115:\t.set_link_ksettings\t= usbnet_set_link_ksettings_mii,\ndrivers/net/usb/asix_devices.c-116-};\n--\ndrivers/net/usb/asix_devices.c=118=static void ax88172_set_multicast(struct net_device *net)\ndrivers/net/usb/asix_devices.c-119-{\ndrivers/net/usb/asix_devices.c:120:\tstruct usbnet *dev = netdev_priv(net);\ndrivers/net/usb/asix_devices.c-121-\tstruct asix_data *data = (struct asix_data *)\u0026dev-\u003edata;\n--\ndrivers/net/usb/asix_devices.c-156-\ndrivers/net/usb/asix_devices.c:157:static int ax88172_link_reset(struct usbnet *dev)\ndrivers/net/usb/asix_devices.c-158-{\n\n"
} |
| 5/2 | 2026/09/05 02:34 | llm | patch-evaluator |
0mModel:gemini-3.7-flash Args: null Results: null Tokens: input: 16684 output: 36 thoughts: 29 Thoughts: Okay, here's my interpretation of that thought process, as if I were having it: **Digging into the USB_USBNET Configuration** Alright, time to get specific. I need to understand the nuts and bolts of the `USB_USBNET` configuration. Let's head straight for the source: `drivers/net/usb/Kconfig`. This is where the real meat of the matter is. I need to see the exact config options – the specific settings available – and, critically, the dependencies. What other features or hardware does `USB_USBNET` rely on? Are there any hidden gotchas I need to be aware of, any preconditions that must be met before I can even *consider* enabling it? Time to get granular and map out the complete configuration landscape. Knowing the Kconfig is key to a robust understanding of its implications. |
| 6/2 | 2026/09/05 02:34 | tool | read-file |
0mArgs:{
"File": "drivers/net/usb/Kconfig",
"FirstLine": 130,
"LineCount": 40
}Results: {
"Contents": " 130:\t\t module will be called lan78xx.\n 131:\t\n 132:\tconfig USB_USBNET\n 133:\t\ttristate \"Multi-purpose USB Networking Framework\"\n 134:\t\tselect MII\n 135:\t\thelp\n 136:\t\t This driver supports several kinds of network links over USB,\n 137:\t\t with \"minidrivers\" built around a common network driver core\n 138:\t\t that supports deep queues for efficient transfers. (This gives\n 139:\t\t better performance with small packets and at high speeds).\n 140:\t\n 141:\t\t The USB host runs \"usbnet\", and the other end of the link might be:\n 142:\t\n 143:\t\t - Another USB host, when using USB \"network\" or \"data transfer\"\n 144:\t\t cables. These are often used to network laptops to PCs, like\n 145:\t\t \"Laplink\" parallel cables or some motherboards. These rely\n 146:\t\t on specialized chips from many suppliers.\n 147:\t\n 148:\t\t - An intelligent USB gadget, perhaps embedding a Linux system.\n 149:\t\t These include PDAs running Linux (iPaq, Yopy, Zaurus, and\n 150:\t\t others), and devices that interoperate using the standard\n 151:\t\t CDC-Ethernet specification (including many cable modems).\n 152:\t\n 153:\t\t - Network adapter hardware (like those for 10/100 Ethernet) which\n 154:\t\t uses this driver framework.\n 155:\t\n 156:\t\t The link will appear with a name like \"usb0\", when the link is\n 157:\t\t a two-node link, or \"eth0\" for most CDC-Ethernet devices. Those\n 158:\t\t two-node links are most easily managed with Ethernet Bridging\n 159:\t\t (CONFIG_BRIDGE) instead of routing.\n 160:\t\n 161:\t\t For more information see \u003chttp://www.linux-usb.org/usbnet/\u003e.\n 162:\t\n 163:\t\t To compile this driver as a module, choose M here: the\n 164:\t\t module will be called usbnet.\n 165:\t\n 166:\tconfig USB_NET_AX8817X\n 167:\t\ttristate \"ASIX AX88xxx Based USB 2.0 Ethernet Adapters\"\n 168:\t\tdepends on USB_USBNET\n 169:\t\tselect CRC32\n"
} |
| 7/2 | 2026/09/05 02:34 | llm | patch-evaluator |
0mModel:gemini-3.7-flash Args: null Results: null Tokens: input: 17607 output: 34 thoughts: 36 Thoughts: Here's my take on the thought process: **Diving into the USB Networking Kconfig** Okay, time to get my hands dirty. I need to understand the configuration structure for USB networking drivers within the kernel. Let's start by cracking open `drivers/net/usb/Kconfig` and take a look at the file's first few lines. I want to see if there's any immediate menu structure or any dependencies defined for `USB_NET_DRIVERS` or even the broader `USB` feature set. This will give me a quick high-level view of how things are organized and what the prerequisites might be for enabling these drivers. Knowing the dependencies is crucial; it’ll let me quickly grasp how these parts plug into the larger kernel configuration. Let's see what's what. |
| 8/2 | 2026/09/05 02:34 | tool | read-file |
0mArgs:{
"File": "drivers/net/usb/Kconfig",
"FirstLine": 1,
"LineCount": 40
}Results: {
"Contents": " 1:\t# SPDX-License-Identifier: GPL-2.0-only\n 2:\t#\n 3:\t# USB Network devices configuration\n 4:\t#\n 5:\tcomment \"Host-side USB support is needed for USB Network Adapter support\"\n 6:\t\tdepends on !USB \u0026\u0026 NET\n 7:\t\n 8:\tmenuconfig USB_NET_DRIVERS\n 9:\t\ttristate \"USB Network Adapters\"\n 10:\t\tdefault USB if USB\n 11:\t\tdepends on USB \u0026\u0026 NET\n 12:\t\n 13:\tif USB_NET_DRIVERS\n 14:\t\n 15:\tconfig USB_CATC\n 16:\t\ttristate \"USB CATC NetMate-based Ethernet device support\"\n 17:\t\tselect CRC32\n 18:\t\thelp\n 19:\t\t Say Y if you want to use one of the following 10Mbps USB Ethernet\n 20:\t\t device based on the EL1210A chip. Supported devices are:\n 21:\t\t Belkin F5U011\n 22:\t\t Belkin F5U111\n 23:\t\t CATC NetMate\n 24:\t\t CATC NetMate II\n 25:\t\t smartBridges smartNIC\n 26:\t\n 27:\t\t This driver makes the adapter appear as a normal Ethernet interface,\n 28:\t\t typically on eth0, if it is the only ethernet device, or perhaps on\n 29:\t\t eth1, if you have a PCI or ISA ethernet card installed.\n 30:\t\n 31:\t\t To compile this driver as a module, choose M here: the\n 32:\t\t module will be called catc.\n 33:\t\n 34:\tconfig USB_KAWETH\n 35:\t\ttristate \"USB KLSI KL5USB101-based ethernet device support\"\n 36:\t\thelp\n 37:\t\t Say Y here if you want to use one of the following 10Mbps only\n 38:\t\t USB Ethernet adapters based on the KLSI KL5KUSB101B chipset:\n 39:\t\t 3Com 3C19250\n 40:\t\t ADS USB-10BT\n"
} |
| 9/2 | 2026/09/05 02:34 | llm | patch-evaluator |
0mModel:gemini-3.7-flash Args: null Results: null Tokens: input: 18409 output: 38 thoughts: 38 Thoughts: Here's my analysis of the provided code inspection request, from my perspective as an expert in the field: **Diving into the USBnet Driver: Key Sections for Review** Okay, so the prompt wants me to examine `drivers/net/usb/usbnet.c`, specifically focusing on lines 320-360 and 1290-1325. That's a reasonable request. Those line ranges likely cover critical areas within the USB network driver. Given my experience, I'd immediately hypothesize what might be there. Lines 320-360 could deal with some initialization aspect, perhaps device probe and connection handling, or possibly interrupt setup within the driver, given the usual layout of a USB driver. I expect some device configuration or basic setup, maybe even resource allocation. The latter section, 1290-1325, is a bit further into the file. Depending on the size of the function, this range could deal with the core data transfer logic - maybe the send path or receive path handling for network packets. I would predict that, if the former is interrupt setup, this section is likely where the interrupt handlers live, including data transfer completion processing. It could be related to bulk transfer, interrupt transfer, or even isochronous transfers, depending on the architecture. Also, given the location within the driver, it's very likely related to the device's interaction with the USB host controller and how the data streams are managed. I'll need to dig into the actual code to confirm my hypotheses. It'll be interesting to see how the author structured the data flow and any error handling they've implemented. My goal is to quickly understand the code's behavior within these areas, looking for any potential bottlenecks, inefficiencies, or, of course, any glaring bugs or vulnerabilities. That's the challenge. Let's see what's there. |
| 10/2 | 2026/09/05 02:35 | tool | read-file |
0mArgs:{
"File": "drivers/net/usb/usbnet.c",
"FirstLine": 320,
"LineCount": 40
}Results: {
"Contents": " 320:\t}\n 321:\t\n 322:\t/* Passes this packet up the stack, updating its accounting.\n 323:\t * Some link protocols batch packets, so their rx_fixup paths\n 324:\t * can return clones as well as just modify the original skb.\n 325:\t */\n 326:\tvoid usbnet_skb_return(struct usbnet *dev, struct sk_buff *skb)\n 327:\t{\n 328:\t\tstruct pcpu_sw_netstats *stats64;\n 329:\t\tunsigned long flags;\n 330:\t\tint\tstatus;\n 331:\t\n 332:\t\tif (test_bit(EVENT_RX_PAUSED, \u0026dev-\u003eflags)) {\n 333:\t\t\tskb_queue_tail(\u0026dev-\u003erxq_pause, skb);\n 334:\t\t\treturn;\n 335:\t\t}\n 336:\t\n 337:\t\t/* only update if unset to allow minidriver rx_fixup override */\n 338:\t\tif (skb-\u003eprotocol == 0)\n 339:\t\t\tskb-\u003eprotocol = eth_type_trans(skb, dev-\u003enet);\n 340:\t\n 341:\t\tlocal_irq_save(flags);\n 342:\t\tstats64 = this_cpu_ptr(dev-\u003enet-\u003etstats);\n 343:\t\tu64_stats_update_begin(\u0026stats64-\u003esyncp);\n 344:\t\tu64_stats_inc(\u0026stats64-\u003erx_packets);\n 345:\t\tu64_stats_add(\u0026stats64-\u003erx_bytes, skb-\u003elen);\n 346:\t\tu64_stats_update_end(\u0026stats64-\u003esyncp);\n 347:\t\tlocal_irq_restore(flags);\n 348:\t\n 349:\t\tnetif_dbg(dev, rx_status, dev-\u003enet, \"\u003c rx, len %zu, type 0x%x\\n\",\n 350:\t\t\t skb-\u003elen + sizeof(struct ethhdr), skb-\u003eprotocol);\n 351:\t\tmemset(skb-\u003ecb, 0, sizeof(struct skb_data));\n 352:\t\n 353:\t\tif (skb_defer_rx_timestamp(skb))\n 354:\t\t\treturn;\n 355:\t\n 356:\t\tstatus = netif_rx (skb);\n 357:\t\tif (status != NET_RX_SUCCESS)\n 358:\t\t\tnetif_dbg(dev, rx_err, dev-\u003enet,\n 359:\t\t\t\t \"netif_rx status %d\\n\", status);\n"
} |
| 11/2 | 2026/09/05 02:35 | llm | patch-evaluator |
0mModel:gemini-3.7-flash Args: null Results: null Tokens: input: 19585 output: 39 thoughts: 23 Thoughts: Here's a summary of my thought process, as requested: **Diving Deep into USBnet Transmission Completion** Okay, so we're looking at network drivers, specifically the USB network interface, and I'm focusing in on the `drivers/net/usb/usbnet.c` file. My attention is drawn to the `tx_complete` function. I know this is a critical spot for understanding how data packets are successfully sent over the USB bus. I need to understand what happens when a transmission is complete, or, more likely, what needs to happen to make the transmission *appear* to be complete. Is it about error handling? Resource release? Notification to the upper networking layers? I expect there to be some interaction with the USB controller and the network stack in here. I'm imagining there's a good chance there are some subtle performance bottlenecks or potential race conditions that are dealt with here. I'll need to carefully dissect the code around this function to see how the driver handles both successful and potentially problematic transmission scenarios. |
| 12/2 | 2026/09/05 02:35 | tool | read-file |
0mArgs:{
"File": "drivers/net/usb/usbnet.c",
"FirstLine": 1290,
"LineCount": 40
}Results: {
"Contents": "1290:\t\n1291:\t\tif (dev-\u003eflags)\n1292:\t\t\tnetdev_dbg(dev-\u003enet, \"kevent done, flags = 0x%lx\\n\", dev-\u003eflags);\n1293:\t}\n1294:\t\n1295:\t/*-------------------------------------------------------------------------*/\n1296:\t\n1297:\tstatic void tx_complete(struct urb *urb)\n1298:\t{\n1299:\t\tstruct sk_buff\t\t*skb = (struct sk_buff *) urb-\u003econtext;\n1300:\t\tstruct skb_data\t\t*entry = (struct skb_data *) skb-\u003ecb;\n1301:\t\tstruct usbnet\t\t*dev = entry-\u003edev;\n1302:\t\n1303:\t\tif (urb-\u003estatus == 0) {\n1304:\t\t\tstruct pcpu_sw_netstats *stats64;\n1305:\t\t\tunsigned long flags;\n1306:\t\n1307:\t\t\tlocal_irq_save(flags);\n1308:\t\t\tstats64 = this_cpu_ptr(dev-\u003enet-\u003etstats);\n1309:\t\t\tu64_stats_update_begin(\u0026stats64-\u003esyncp);\n1310:\t\t\tu64_stats_add(\u0026stats64-\u003etx_packets, entry-\u003epackets);\n1311:\t\t\tu64_stats_add(\u0026stats64-\u003etx_bytes, entry-\u003elength);\n1312:\t\t\tu64_stats_update_end(\u0026stats64-\u003esyncp);\n1313:\t\t\tlocal_irq_restore(flags);\n1314:\t\t} else {\n1315:\t\t\tdev-\u003enet-\u003estats.tx_errors++;\n1316:\t\n1317:\t\t\tswitch (urb-\u003estatus) {\n1318:\t\t\tcase -EPIPE:\n1319:\t\t\t\tusbnet_defer_kevent(dev, EVENT_TX_HALT);\n1320:\t\t\t\tbreak;\n1321:\t\n1322:\t\t\t/* software-driven interface shutdown */\n1323:\t\t\tcase -ECONNRESET:\t\t// async unlink\n1324:\t\t\tcase -ESHUTDOWN:\t\t// hardware gone\n1325:\t\t\t\tbreak;\n1326:\t\n1327:\t\t\t/* like rx, tx gets controller i/o faults during hub_wq\n1328:\t\t\t * delays and so it uses the same throttling mechanism.\n1329:\t\t\t */\n"
} |
| 13/2 | 2026/09/05 02:35 | llm | patch-evaluator |
0mModel:gemini-3.7-flash Args: null Results: null Tokens: input: 20496 output: 33 thoughts: 292 Thoughts: **Analyzing the USB Networking Patch** Okay, let's break this patch down. Is this code even *reachable*? Yep, no doubt about it. This is `usbnet.c`, the heart of USB networking drivers in Linux. We're talking about devices like CDC Ethernet, ASIX, the whole shebang. Specifically, we're looking at `usbnet_skb_return()`, which handles incoming packets and updates stats, and `tx_complete()`, the URB completion callback for transmission, also with stat updates. These are *definitely* going to be hit when a USB network device transmits or receives. That's trivial to trigger even in typical virtualized environments – think syzkaller with raw gadgets or just straight-up USB emulation. This is definitely worth a fuzzing shot. Now, let's nail down the key functions. We need to focus on `usbnet_skb_return` and `tx_complete`. Wait, hold on – which symbols are actually being *modified*? It looks like `usbnet_skb_return` and `tx_complete` themselves. Okay, good to know. Now, is `tx_complete` even accessible? Let's see... `static void tx_complete(struct urb *urb)`. Ah, it's static in `drivers/net/usb/usbnet.c`. That might be a problem. We need to confirm it's a valid symbol visible in `vmlinux`. I'll run `grepper` or check the callers of `tx_complete`. We need to verify that we can actually get to it. |
| 14/2 | 2026/09/05 02:35 | tool | grepper |
0mArgs:{
"Expression": "tx_complete",
"PathPrefix": "drivers/net/usb/usbnet.c"
}Results: {
"Output": "drivers/net/usb/usbnet.c=1186=usbnet_deferred_kevent(struct work_struct *work)\n--\ndrivers/net/usb/usbnet.c-1296-\ndrivers/net/usb/usbnet.c:1297:static void tx_complete(struct urb *urb)\ndrivers/net/usb/usbnet.c-1298-{\n--\ndrivers/net/usb/usbnet.c=1404=netdev_tx_t usbnet_start_xmit(struct sk_buff *skb, struct net_device *net)\n--\ndrivers/net/usb/usbnet.c-1440-\tusb_fill_bulk_urb(urb, dev-\u003eudev, dev-\u003eout,\ndrivers/net/usb/usbnet.c:1441:\t\t\t skb-\u003edata, skb-\u003elen, tx_complete, skb);\ndrivers/net/usb/usbnet.c-1442-\tif (dev-\u003ecan_dma_sg) {\n"
} |
| 15/2 | 2026/09/05 02:35 | llm | patch-evaluator |
0mModel:gemini-3.7-flash Args: null Results: null Tokens: input: 21424 output: 146 thoughts: 460 Thoughts: **My Analysis of the USB Networking Framework for Fuzzing** Okay, so here's the breakdown of my thinking regarding fuzzing this USB networking functionality. The compiler *has* to keep `tx_complete` around because its address is taken within `usb_fill_bulk_urb`. This means it will be accessible in the symbol tables (kallsyms/vmlinux). Similarly, `usbnet_skb_return` is an exported function, so we can definitely target both. I should probably also examine `usbnet_start_xmit`, but at a minimum I'll focus on `usbnet_skb_return` and `tx_complete`. Now, let's nail down the configuration requirements. The key is `CONFIG_USB_USBNET`. This is what enables the USB network drivers, and depends on `CONFIG_USB_NET_DRIVERS`, which in turn requires `CONFIG_USB` and `CONFIG_NET`. Looking into `drivers/net/usb/Kconfig`, I can confirm that `USB_USBNET` also requires the selection of `MII`. Therefore, we need to ensure that `USB_USBNET`, `USB_NET_DRIVERS`, `USB`, and `NET` are all enabled in the build. Let me just double-check that this is all in line with my overall strategy: 1. `WorthFuzzing`: Absolutely, yes! 2. `FocusSymbols`: Confirmed. `["usbnet_skb_return", "tx_complete"]` are the prime targets. 3. `EnableConfigs`: `["USB_USBNET", "USB_NET_DRIVERS", "USB", "NET"]`. These configs are essential. 4. `Reasoning`: We've got a clear explanation of *why* this is a good target - fixing issues accessing per-CPU stats, and its accessibility via USB networking devices, meaning it is fuzzable via USB gadget/emulation, all of which I've explicitly verified. Right, time to call `set-results`. We're ready to go. |
| 16/2 | 2026/09/05 02:35 | tool | set-results |
0mArgs:{
"EnableConfigs": [
"USB_USBNET",
"USB_NET_DRIVERS",
"USB",
"NET"
],
"FocusSymbols": [
"usbnet_skb_return",
"tx_complete"
],
"Reasoning": "The patch modifies per-CPU network statistics update routines in usbnet (usbnet_skb_return and tx_complete) by disabling local IRQs before calling this_cpu_ptr(dev-\u003enet-\u003etstats), ensuring safe per-CPU access. USB network devices are reachable and fuzzable via USB device emulation / raw-gadget in standard virtualized environments.",
"WorthFuzzing": true
}Results: {
"EnableConfigs": [
"USB_USBNET",
"USB_NET_DRIVERS",
"USB",
"NET"
],
"FocusSymbols": [
"usbnet_skb_return",
"tx_complete"
],
"Reasoning": "The patch modifies per-CPU network statistics update routines in usbnet (usbnet_skb_return and tx_complete) by disabling local IRQs before calling this_cpu_ptr(dev-\u003enet-\u003etstats), ensuring safe per-CPU access. USB network devices are reachable and fuzzable via USB device emulation / raw-gadget in standard virtualized environments.",
"WorthFuzzing": true
} |
| 17/1 | 2026/09/05 02:35 | action | If |
0mArgs:{
"WorthFuzzing": true
}Results: null |
| 18/2 | 2026/09/05 02:35 | agent | kmsan-evaluator |
0mModel:core Args: null Results: {
"KMSANReasoning": "The patch modifies `usbnet_skb_return` and `tx_complete` in `drivers/net/usb/usbnet.c` to fetch the per-CPU pointer `this_cpu_ptr(dev-\u003enet-\u003etstats)` inside a `local_irq_save`/`local_irq_restore` block rather than calling `u64_stats_update_begin_irqsave` on a pointer obtained prior to disabling interrupts/preemption.\n\nThis change is purely a locking/concurrency fix for per-CPU statistics updating. All local variables (`flags`, `stats64`) are explicitly initialized prior to use, no new buffers or structures are allocated, no data is copied to user space, and no uninitialized memory branches or info-leaks are introduced. Therefore, dedicated KMSAN fuzzing is not required.",
"NeedsKMSAN": false
}Instruction: You are an expert Linux kernel security engineer specializing in kernel memory
error detectors (KASAN and KMSAN). Your job is to review the provided patch series and
determine if the code changes justify spawning a dedicated KMSAN (KernelMemorySanitizer)
fuzzing session in addition to standard KASAN fuzzing.
CRITICAL DISTINCTION BETWEEN KASAN AND KMSAN:
- Standard KASAN kernel builds (upstream-apparmor-kasan.config) already enable
a comprehensive suite of debugging tools and sanitizers, including KASAN
(out-of-bounds accesses, use-after-free, double free, invalid free), LOCKDEP
(locking bugs and deadlocks), UB-sanitizers, and memory corruption checks.
- KMSAN (KernelMemorySanitizer) detects reads of UNINITIALIZED memory (stack, heap,
or page allocations) and kernel-to-user memory info-leaks.
Rule: THERE IS NO SENSE IN RUNNING A KMSAN SESSION IF A BUG CAN BE CAUGHT BY KASAN,
LOCKDEP, OR OTHER STANDARD BUG DETECTORS.
A dedicated KMSAN fuzzing session incurs significant resource costs. You must ONLY
set NeedsKMSAN=true if the code changes introduce or expose UNINITIALIZED MEMORY risks
that are detected ONLY by KMSAN.
Look holistically at the patch series and surrounding code. Even if no direct
uninitialized field accesses or new buffer allocations are added in the diff itself,
a patch may alter control flow, bounds checking, or data length calculations in ways
that change how the rest of the code operates on existing buffers (e.g. allowing
uninitialized stack/heap memory to be read, copied to user space, or used in control
flow). Do not hesitate to use your code access tools to inspect the surrounding code,
called functions, and callers.
Set NeedsKMSAN=true ONLY IF the patch introduces or modifies:
1. Kernel structures sent to user space (via copy_to_user, put_user, netlink skb
attributes, ioctl output arguments, socket options, or BPF buffers) where fields
or structure padding might not be fully initialized/zeroed.
2. Conditional logic or branching that depends on potentially uninitialized variables
or struct fields.
3. Allocation or initialization of complex data structures where uninitialized fields
could be read later in reachable code paths.
4. Bounds checks, lengths, or logic in a way that allows surrounding code to access
uninitialized bytes of existing buffers.
Set NeedsKMSAN=false IF:
- The code changes primarily risk out-of-bounds access, array overflows, NULL pointer
dereferences, locking deadlocks, or use-after-free bugs (these are already caught
by KASAN, LOCKDEP, or standard bug detectors).
- All stack/heap structures touched or introduced by the patch are fully zeroed
or initialized (e.g. using = {0}, memset, kzalloc) before being read or copied.
- The patch does not introduce any risk of uninitialized memory usage or info-leaks.
Use your code access tools to inspect the surrounding code if necessary, then provide
detailed KMSANReasoning contrasting KASAN vs KMSAN applicability for this patch.
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: Target architecture: amd64
For your convenience, here is the diff of the changes:
commit 4cbc0a18e62b873c7528559d745479914333fba4
Author: syz-cluster <triage@syzkaller.com>
Date: Sat Sep 5 02:34:33 2026 +0000
syz-cluster: applied patch under review
diff --git a/drivers/net/usb/usbnet.c b/drivers/net/usb/usbnet.c
index a19ecf718f36a..6a48f38e105d4 100644
--- a/drivers/net/usb/usbnet.c
+++ b/drivers/net/usb/usbnet.c
@@ -325,7 +325,7 @@ static void __usbnet_status_stop_force(struct usbnet *dev)
*/
void usbnet_skb_return(struct usbnet *dev, struct sk_buff *skb)
{
- struct pcpu_sw_netstats *stats64 = this_cpu_ptr(dev->net->tstats);
+ struct pcpu_sw_netstats *stats64;
unsigned long flags;
int status;
@@ -338,10 +338,13 @@ void usbnet_skb_return(struct usbnet *dev, struct sk_buff *skb)
if (skb->protocol == 0)
skb->protocol = eth_type_trans(skb, dev->net);
- flags = u64_stats_update_begin_irqsave(&stats64->syncp);
+ local_irq_save(flags);
+ stats64 = this_cpu_ptr(dev->net->tstats);
+ u64_stats_update_begin(&stats64->syncp);
u64_stats_inc(&stats64->rx_packets);
u64_stats_add(&stats64->rx_bytes, skb->len);
- u64_stats_update_end_irqrestore(&stats64->syncp, flags);
+ u64_stats_update_end(&stats64->syncp);
+ local_irq_restore(flags);
netif_dbg(dev, rx_status, dev->net, "< rx, len %zu, type 0x%x\n",
skb->len + sizeof(struct ethhdr), skb->protocol);
@@ -1298,13 +1301,16 @@ static void tx_complete(struct urb *urb)
struct usbnet *dev = entry->dev;
if (urb->status == 0) {
- struct pcpu_sw_netstats *stats64 = this_cpu_ptr(dev->net->tstats);
+ struct pcpu_sw_netstats *stats64;
unsigned long flags;
- flags = u64_stats_update_begin_irqsave(&stats64->syncp);
+ local_irq_save(flags);
+ stats64 = this_cpu_ptr(dev->net->tstats);
+ u64_stats_update_begin(&stats64->syncp);
u64_stats_add(&stats64->tx_packets, entry->packets);
u64_stats_add(&stats64->tx_bytes, entry->length);
- u64_stats_update_end_irqrestore(&stats64->syncp, flags);
+ u64_stats_update_end(&stats64->syncp);
+ local_irq_restore(flags);
} else {
dev->net->stats.tx_errors++;
|
| 19/3 | 2026/09/05 02:35 | llm | kmsan-evaluator |
0mModel:gemini-3.7-flash Args: null Results: null Tokens: input: 2715 output: 38 thoughts: 1266 Thoughts: **Analyzing the USBnet Statistics Update Patch** Okay, so I'm looking at a patch for `drivers/net/usb/usbnet.c`, specifically around the statistic updates for RX and TX packets. The diff is interesting. It seems like the core change involves the placement of the `this_cpu_ptr()` call. Previously, we were fetching the per-CPU statistics pointer before disabling interrupts/preemption using `u64_stats_update_begin_irqsave()`. Now, the code saves the interrupt state first with `local_irq_save(flags)`, *then* fetches the `stats64` pointer using `this_cpu_ptr()`, and *finally* uses `u64_stats_update_begin()`/`u64_stats_update_end()` to handle the update, followed by restoring the interrupt state with `local_irq_restore(flags)`. My initial thought is that this addresses a potential race condition or data corruption issue. If the task were preempted or migrated to another CPU *after* fetching the per-CPU pointer but *before* disabling interrupts, or if dealing with architectures where per-cpu pointers require preemption disabled, the wrong statistics could be updated. Fetching the pointer under interrupt/preemption control guarantees that we are accessing the correct per-CPU structure, ensuring data consistency, especially in SMP/multicore systems. It's a classic concurrency bug fix. Now, let's critically examine if this change introduces any new issues. A quick check for uninitialized variables is crucial. It looks like `flags` is definitely initialized by the `local_irq_save` call. `stats64` is assigned by `this_cpu_ptr(dev->net->tstats)`, which should return a valid pointer. The `u64_stats_update_begin` and `u64_stats_update_end` functions work on the syncp of stats64, so those are all valid, and `local_irq_restore(flags)` uses the initialized `flags` value. So, no uninitialized variables, no potential for memory leaks or other nasty side effects that I can see immediately. The variables are all safe. There are no concerns about copy_to_user calls, or info leaks here. There are no uninitialized memory branches that look concerning. I'm confident this is a safe and correct change to increase the performance and reliability. It's good practice to protect the integrity of the per-cpu pointers during the update. Given the nature of the change, it doesn't appear like this necessitates any KMSAN checks. Still, it's good to do a sanity check to verify the lines of code. I'll probably run `grepper` or `read-file` to confirm that the relevant sections look as expected, just to be absolutely sure. |
| 20/3 | 2026/09/05 02:35 | tool | read-file |
0mArgs:{
"File": "drivers/net/usb/usbnet.c",
"FirstLine": 325,
"LineCount": 40
}Results: {
"Contents": " 325:\t */\n 326:\tvoid usbnet_skb_return(struct usbnet *dev, struct sk_buff *skb)\n 327:\t{\n 328:\t\tstruct pcpu_sw_netstats *stats64;\n 329:\t\tunsigned long flags;\n 330:\t\tint\tstatus;\n 331:\t\n 332:\t\tif (test_bit(EVENT_RX_PAUSED, \u0026dev-\u003eflags)) {\n 333:\t\t\tskb_queue_tail(\u0026dev-\u003erxq_pause, skb);\n 334:\t\t\treturn;\n 335:\t\t}\n 336:\t\n 337:\t\t/* only update if unset to allow minidriver rx_fixup override */\n 338:\t\tif (skb-\u003eprotocol == 0)\n 339:\t\t\tskb-\u003eprotocol = eth_type_trans(skb, dev-\u003enet);\n 340:\t\n 341:\t\tlocal_irq_save(flags);\n 342:\t\tstats64 = this_cpu_ptr(dev-\u003enet-\u003etstats);\n 343:\t\tu64_stats_update_begin(\u0026stats64-\u003esyncp);\n 344:\t\tu64_stats_inc(\u0026stats64-\u003erx_packets);\n 345:\t\tu64_stats_add(\u0026stats64-\u003erx_bytes, skb-\u003elen);\n 346:\t\tu64_stats_update_end(\u0026stats64-\u003esyncp);\n 347:\t\tlocal_irq_restore(flags);\n 348:\t\n 349:\t\tnetif_dbg(dev, rx_status, dev-\u003enet, \"\u003c rx, len %zu, type 0x%x\\n\",\n 350:\t\t\t skb-\u003elen + sizeof(struct ethhdr), skb-\u003eprotocol);\n 351:\t\tmemset(skb-\u003ecb, 0, sizeof(struct skb_data));\n 352:\t\n 353:\t\tif (skb_defer_rx_timestamp(skb))\n 354:\t\t\treturn;\n 355:\t\n 356:\t\tstatus = netif_rx (skb);\n 357:\t\tif (status != NET_RX_SUCCESS)\n 358:\t\t\tnetif_dbg(dev, rx_err, dev-\u003enet,\n 359:\t\t\t\t \"netif_rx status %d\\n\", status);\n 360:\t}\n 361:\tEXPORT_SYMBOL_GPL(usbnet_skb_return);\n 362:\t\n 363:\t/* must be called if hard_mtu or rx_urb_size changed */\n 364:\tvoid usbnet_update_max_qlen(struct usbnet *dev)\n"
} |
| 21/3 | 2026/09/05 02:35 | llm | kmsan-evaluator |
0mModel:gemini-3.7-flash Args: null Results: null Tokens: input: 5332 output: 204 thoughts: 149 Thoughts: **KMSAN Assessment: USBnet Interrupt Handling** Okay, so looking at these changes to `usbnet_skb_return` and `tx_complete`, it's pretty straightforward. It's really just a reordering of how the traffic statistics are accessed. Specifically, it shifts the fetching of `this_cpu_ptr(dev->net->tstats)` to *inside* the `local_irq_save`/`local_irq_restore` critical section, rather than relying on `u64_stats_update_begin_irqsave`, which had the stats retrieval *before* the IRQ disabling. Given my understanding of potential KMSAN issues, I'm not seeing any red flags here. There's no hint of uninitialized memory being accessed, no risk of leaking kernel information to user space, nothing complex being allocated with uninitialized fields, and definitely no conditional logic branching based on the value of uninitialized data. These are all common KMSAN triggers, and none of them are present. Therefore, the `NeedsKMSAN` flag is definitively false in this case. Time to call `set-results` and provide this clear reasoning. |
| 22/3 | 2026/09/05 02:35 | tool | set-results |
0mArgs:{
"KMSANReasoning": "The patch modifies `usbnet_skb_return` and `tx_complete` in `drivers/net/usb/usbnet.c` to fetch the per-CPU pointer `this_cpu_ptr(dev-\u003enet-\u003etstats)` inside a `local_irq_save`/`local_irq_restore` block rather than calling `u64_stats_update_begin_irqsave` on a pointer obtained prior to disabling interrupts/preemption.\n\nThis change is purely a locking/concurrency fix for per-CPU statistics updating. All local variables (`flags`, `stats64`) are explicitly initialized prior to use, no new buffers or structures are allocated, no data is copied to user space, and no uninitialized memory branches or info-leaks are introduced. Therefore, dedicated KMSAN fuzzing is not required.",
"NeedsKMSAN": false
}Results: {
"KMSANReasoning": "The patch modifies `usbnet_skb_return` and `tx_complete` in `drivers/net/usb/usbnet.c` to fetch the per-CPU pointer `this_cpu_ptr(dev-\u003enet-\u003etstats)` inside a `local_irq_save`/`local_irq_restore` block rather than calling `u64_stats_update_begin_irqsave` on a pointer obtained prior to disabling interrupts/preemption.\n\nThis change is purely a locking/concurrency fix for per-CPU statistics updating. All local variables (`flags`, `stats64`) are explicitly initialized prior to use, no new buffers or structures are allocated, no data is copied to user space, and no uninitialized memory branches or info-leaks are introduced. Therefore, dedicated KMSAN fuzzing is not required.",
"NeedsKMSAN": false
} |
| Total Calls | Total Tokens | Avg Tokens | Total Duration (Seconds) | Avg Duration (Seconds) |
|---|
| Total Calls | Total Duration (Seconds) | Avg Duration (Seconds) |
|---|