AI Trajectory


Trajectory: (Expand/Collapse All)
Seq Timestamp Type Name Duration
0/0 2026/09/05 01:03 flow patch-triage
0m Args:
null

Results:
{
  "EnableConfigs": [
    "CFG80211"
  ],
  "FocusSymbols": [
    "reg_check_chans_work",
    "reg_check_channels",
    "reg_leave_invalid_chans"
  ],
  "KMSANReasoning": "The patch modifies the locking and RCU list traversal strategy in reg_check_chans_work() (net/wireless/reg.c) by dropping and re-acquiring rcu_read_lock() and rtnl_lock() around each iteration of cfg80211_rdev_list.\n\nThis change does not introduce any memory allocations, does not read or write uninitialized stack/heap fields, does not alter buffer length/bounds calculations, and does not pass kernel data to userspace. Any concurrency, use-after-free, or list corruption issues stemming from dropping RCU during list traversal are detectable by standard debugging tools (KASAN, LOCKDEP, and CONFIG_PROVE_RCU). Therefore, a dedicated KMSAN fuzzing session is not warranted.",
  "NeedsKMSAN": false,
  "Reasoning": "The patch changes locking and RCU iteration in reg_check_chans_work() within cfg80211 (net/wireless/reg.c), releasing and re-acquiring rcu_read_lock and rtnl_lock inside list_for_each_entry_rcu. This reachable code path handles regulatory domain channel validation and interface disconnection, which can be triggered via nl80211 regulatory commands. Fuzzing is warranted to test for concurrency bugs, list traversal issues, and RCU/lockdep warnings.",
  "WorthFuzzing": true
}

1/1 2026/09/05 01:03 action read-patch-diff
0m Args:
null

Results:
{
  "PatchDiff": "commit 909bae63e4cb8dbb8c2aea103eddd0caba9adc75\nAuthor: syz-cluster \u003ctriage@syzkaller.com\u003e\nDate:   Sat Sep 5 01:03:47 2026 +0000\n\n    syz-cluster: applied patch under review\n\ndiff --git a/net/wireless/reg.c b/net/wireless/reg.c\nindex a8336baf85dc6..a2e0d1cf8317c 100644\n--- a/net/wireless/reg.c\n+++ b/net/wireless/reg.c\n@@ -2466,12 +2466,21 @@ static void reg_check_chans_work(struct work_struct *work)\n \tstruct cfg80211_registered_device *rdev;\n \n \tpr_debug(\"Verifying active interfaces after reg change\\n\");\n-\trtnl_lock();\n-\n-\tfor_each_rdev(rdev)\n+\t/*\n+\t * Acquire rtnl per-device instead of holding it for the entire loop;\n+\t * cfg80211_leave() can be slow and starve other rtnl waiters otherwise.\n+\t * wiphy_unregister() holds rtnl across list_del_rcu() + synchronize_rcu(),\n+\t * so rdev cannot be freed while we hold rtnl_lock() below.\n+\t */\n+\trcu_read_lock();\n+\tlist_for_each_entry_rcu(rdev, \u0026cfg80211_rdev_list, list) {\n+\t\trcu_read_unlock();\n+\t\trtnl_lock();\n \t\treg_leave_invalid_chans(\u0026rdev-\u003ewiphy);\n-\n-\trtnl_unlock();\n+\t\trtnl_unlock();\n+\t\trcu_read_lock();\n+\t}\n+\trcu_read_unlock();\n }\n \n void reg_check_channels(void)\n"
}

2/1 2026/09/05 01:03 agent patch-evaluator
0m Model:
core

Args:
null

Results:
{
  "EnableConfigs": [
    "CFG80211"
  ],
  "FocusSymbols": [
    "reg_check_chans_work",
    "reg_check_channels",
    "reg_leave_invalid_chans"
  ],
  "Reasoning": "The patch changes locking and RCU iteration in reg_check_chans_work() within cfg80211 (net/wireless/reg.c), releasing and re-acquiring rcu_read_lock and rtnl_lock inside list_for_each_entry_rcu. This reachable code path handles regulatory domain channel validation and interface disconnection, which can be triggered via nl80211 regulatory commands. Fuzzing is warranted to test for concurrency bugs, list traversal issues, and RCU/lockdep warnings.",
  "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 909bae63e4cb8dbb8c2aea103eddd0caba9adc75
Author: syz-cluster <triage@syzkaller.com>
Date:   Sat Sep 5 01:03:47 2026 +0000

    syz-cluster: applied patch under review

diff --git a/net/wireless/reg.c b/net/wireless/reg.c
index a8336baf85dc6..a2e0d1cf8317c 100644
--- a/net/wireless/reg.c
+++ b/net/wireless/reg.c
@@ -2466,12 +2466,21 @@ static void reg_check_chans_work(struct work_struct *work)
 	struct cfg80211_registered_device *rdev;
 
 	pr_debug("Verifying active interfaces after reg change\n");
-	rtnl_lock();
-
-	for_each_rdev(rdev)
+	/*
+	 * Acquire rtnl per-device instead of holding it for the entire loop;
+	 * cfg80211_leave() can be slow and starve other rtnl waiters otherwise.
+	 * wiphy_unregister() holds rtnl across list_del_rcu() + synchronize_rcu(),
+	 * so rdev cannot be freed while we hold rtnl_lock() below.
+	 */
+	rcu_read_lock();
+	list_for_each_entry_rcu(rdev, &cfg80211_rdev_list, list) {
+		rcu_read_unlock();
+		rtnl_lock();
 		reg_leave_invalid_chans(&rdev->wiphy);
-
-	rtnl_unlock();
+		rtnl_unlock();
+		rcu_read_lock();
+	}
+	rcu_read_unlock();
 }
 
 void reg_check_channels(void)

3/2 2026/09/05 01:03 llm patch-evaluator
0m Model:
gemini-3.7-flash

Args:
null

Results:
null

Tokens:
							input: 3059
							output: 36
							thoughts: 52
						

Thoughts:
Okay, here's my take on those thoughts, framed as my own mental process:

**Diving into the Regulatory Domain Code**

Alright, the hint points me straight to `net/wireless/reg.c`. Good, that's where I'd expect to find the regulatory-related code. My first step is to get a handle on the changes. Time to pull up the diff and really get into the nitty-gritty. I need to understand *exactly* what's been modified and why. I'll need to examine the context around those changes – what's the surrounding code doing, how does this fit into the broader regulatory domain logic, and what's the intended impact?

Now, to locate the area in question, I'll leverage the line number – around line 2466 – it's always a good starting point. I'll use a `read-file` command, or similar, to quickly jump to that specific region of the `reg.c` file and start my analysis. This gives me a quick way to examine the code's immediate context.



4/2 2026/09/05 01:03 tool read-file
0m Args:
{
  "File": "net/wireless/reg.c",
  "FirstLine": 2455,
  "LineCount": 50
}

Results:
{
  "Contents": "2455:\t\t\tbool valid;\n2456:\t\n2457:\t\t\tscoped_guard(wiphy, wiphy)\n2458:\t\t\t\tvalid = reg_wdev_chan_valid(wiphy, wdev);\n2459:\t\t\tif (!valid)\n2460:\t\t\t\tcfg80211_leave(rdev, wdev, -1);\n2461:\t\t}\n2462:\t}\n2463:\t\n2464:\tstatic void reg_check_chans_work(struct work_struct *work)\n2465:\t{\n2466:\t\tstruct cfg80211_registered_device *rdev;\n2467:\t\n2468:\t\tpr_debug(\"Verifying active interfaces after reg change\\n\");\n2469:\t\t/*\n2470:\t\t * Acquire rtnl per-device instead of holding it for the entire loop;\n2471:\t\t * cfg80211_leave() can be slow and starve other rtnl waiters otherwise.\n2472:\t\t * wiphy_unregister() holds rtnl across list_del_rcu() + synchronize_rcu(),\n2473:\t\t * so rdev cannot be freed while we hold rtnl_lock() below.\n2474:\t\t */\n2475:\t\trcu_read_lock();\n2476:\t\tlist_for_each_entry_rcu(rdev, \u0026cfg80211_rdev_list, list) {\n2477:\t\t\trcu_read_unlock();\n2478:\t\t\trtnl_lock();\n2479:\t\t\treg_leave_invalid_chans(\u0026rdev-\u003ewiphy);\n2480:\t\t\trtnl_unlock();\n2481:\t\t\trcu_read_lock();\n2482:\t\t}\n2483:\t\trcu_read_unlock();\n2484:\t}\n2485:\t\n2486:\tvoid reg_check_channels(void)\n2487:\t{\n2488:\t\t/*\n2489:\t\t * Give usermode a chance to do something nicer (move to another\n2490:\t\t * channel, orderly disconnection), before forcing a disconnection.\n2491:\t\t */\n2492:\t\tmod_delayed_work(system_power_efficient_wq,\n2493:\t\t\t\t \u0026reg_check_chans,\n2494:\t\t\t\t msecs_to_jiffies(REG_ENFORCE_GRACE_MS));\n2495:\t}\n2496:\t\n2497:\tstatic void wiphy_update_regulatory(struct wiphy *wiphy,\n2498:\t\t\t\t\t    enum nl80211_reg_initiator initiator)\n2499:\t{\n2500:\t\tenum nl80211_band band;\n2501:\t\tstruct regulatory_request *lr = get_last_request();\n2502:\t\n2503:\t\tif (ignore_reg_update(wiphy, initiator)) {\n2504:\t\t\t/*\n"
}

5/2 2026/09/05 01:03 llm patch-evaluator
0m Model:
gemini-3.7-flash

Args:
null

Results:
null

Tokens:
							input: 4160
							output: 31
							thoughts: 347
						

Thoughts:
**Analyzing This Patch: A Potential RCU Violation**

Okay, let's dive into this patch concerning `reg_check_chans_work` within `net/wireless/reg.c`. The first thing that jumps out is the use of `list_for_each_entry_rcu`. Wait a second! I see it's iterating over `cfg80211_rdev_list` using `rdev->list.next`. Then I see the critical point: the code *drops* `rcu_read_unlock()` and then re-acquires `rcu_read_lock()` *within* the loop body. Alarm bells!

This is a textbook example of potentially breaking RCU invariants. When you're dealing with `list_for_each_entry_rcu`, you're supposed to hold the read lock across the *entire* iteration. If we drop the lock and re-acquire it inside the loop, we create a window where `rdev` could be unlinked, freed, or its `list.next` pointer could become invalid due to the RCU grace period after `list_del_rcu`. Essentially, we're violating the core assumption of RCU traversal. This is a very unsafe maneuver.

The fundamental issue is that by dropping the RCU read lock, `rdev` might have been freed during `synchronize_rcu` or after the `list_del_rcu` and during the grace period. Or even just accessing `rdev->list.next` might be problematic during that period. The traversal could become either safe or unsafe, and it's hard to predict.

Now the million-dollar question: is this reachable? Is this something we can trigger? Given that `net/wireless` – which includes `cfg80211`, `mac80211_hwsim`, `nl80211`, and so on – is a standard target for syzkaller fuzzing, there's a *very* good chance this is indeed reachable and fuzzer-triggerable. This makes me very nervous; this is the kind of subtle RCU bug that can lead to crashes or, worse, hard-to-debug memory corruption.

Next, I need to check the Kconfig requirements for `net/wireless/reg.c` to see if there are any specific dependencies that might limit or enable this vulnerability.



6/2 2026/09/05 01:04 tool grepper
0m Args:
{
  "Expression": "CFG80211",
  "PathPrefix": "net/wireless/"
}

Results:
{
  "Output": "\nFull output is too long, showing 500 out of 857 lines.\nUse more precise expression if possible.\n\nnet/wireless/Kconfig=5=config WEXT_CORE\nnet/wireless/Kconfig-6-\tdef_bool y\nnet/wireless/Kconfig:7:\tdepends on CFG80211_WEXT || WIRELESS_EXT\nnet/wireless/Kconfig-8-\n--\nnet/wireless/Kconfig=14=config WEXT_PRIV\n--\nnet/wireless/Kconfig-16-\nnet/wireless/Kconfig:17:config CFG80211\nnet/wireless/Kconfig-18-\ttristate \"cfg80211 - wireless configuration API\"\n--\nnet/wireless/Kconfig-24-\t# (this is here rather than below to allow it to be a module)\nnet/wireless/Kconfig:25:\tselect CRYPTO_SHA256 if CFG80211_USE_KERNEL_REGDB_KEYS\nnet/wireless/Kconfig-26-\thelp\n--\nnet/wireless/Kconfig-35-\nnet/wireless/Kconfig:36:if CFG80211\nnet/wireless/Kconfig-37-\nnet/wireless/Kconfig=38=config NL80211_TESTMODE\n--\nnet/wireless/Kconfig-51-\nnet/wireless/Kconfig:52:config CFG80211_DEVELOPER_WARNINGS\nnet/wireless/Kconfig-53-\tbool \"enable developer warnings\"\n--\nnet/wireless/Kconfig-67-\nnet/wireless/Kconfig:68:config CFG80211_CERTIFICATION_ONUS\nnet/wireless/Kconfig-69-\tbool \"cfg80211 certification onus\"\n--\nnet/wireless/Kconfig-88-\nnet/wireless/Kconfig:89:config CFG80211_REQUIRE_SIGNED_REGDB\nnet/wireless/Kconfig:90:\tbool \"require regdb signature\" if CFG80211_CERTIFICATION_ONUS\nnet/wireless/Kconfig-91-\tdefault y\n--\nnet/wireless/Kconfig-98-\nnet/wireless/Kconfig:99:config CFG80211_USE_KERNEL_REGDB_KEYS\nnet/wireless/Kconfig:100:\tbool \"allow regdb keys shipped with the kernel\" if CFG80211_CERTIFICATION_ONUS\nnet/wireless/Kconfig-101-\tdefault y\nnet/wireless/Kconfig:102:\tdepends on CFG80211_REQUIRE_SIGNED_REGDB\nnet/wireless/Kconfig-103-\thelp\n--\nnet/wireless/Kconfig-110-\nnet/wireless/Kconfig:111:config CFG80211_EXTRA_REGDB_KEYDIR\nnet/wireless/Kconfig:112:\tstring \"additional regdb key directory\" if CFG80211_CERTIFICATION_ONUS\nnet/wireless/Kconfig:113:\tdepends on CFG80211_REQUIRE_SIGNED_REGDB\nnet/wireless/Kconfig-114-\thelp\n--\nnet/wireless/Kconfig-121-\nnet/wireless/Kconfig:122:config CFG80211_REG_CELLULAR_HINTS\nnet/wireless/Kconfig-123-\tbool \"cfg80211 regulatory support for cellular base station hints\"\nnet/wireless/Kconfig:124:\tdepends on CFG80211_CERTIFICATION_ONUS\nnet/wireless/Kconfig-125-\thelp\n--\nnet/wireless/Kconfig-134-\nnet/wireless/Kconfig:135:config CFG80211_REG_RELAX_NO_IR\nnet/wireless/Kconfig-136-\tbool \"cfg80211 support for NO_IR relaxation\"\nnet/wireless/Kconfig:137:\tdepends on CFG80211_CERTIFICATION_ONUS\nnet/wireless/Kconfig-138-\thelp\n--\nnet/wireless/Kconfig-158-\nnet/wireless/Kconfig:159:config CFG80211_DEFAULT_PS\nnet/wireless/Kconfig-160-\tbool \"enable powersave by default\"\n--\nnet/wireless/Kconfig-168-\nnet/wireless/Kconfig:169:config CFG80211_DEBUGFS\nnet/wireless/Kconfig-170-\tbool \"cfg80211 DebugFS entries\"\n--\nnet/wireless/Kconfig-176-\nnet/wireless/Kconfig:177:config CFG80211_CRDA_SUPPORT\nnet/wireless/Kconfig-178-\tbool \"support CRDA\" if EXPERT\n--\nnet/wireless/Kconfig-186-\nnet/wireless/Kconfig:187:config CFG80211_WEXT\nnet/wireless/Kconfig-188-\tbool \"cfg80211 wireless extensions compatibility\"\n--\nnet/wireless/Kconfig-193-\nnet/wireless/Kconfig:194:config CFG80211_KUNIT_TEST\nnet/wireless/Kconfig-195-\ttristate \"KUnit tests for cfg80211\" if !KUNIT_ALL_TESTS\nnet/wireless/Kconfig-196-\tdepends on KUNIT\nnet/wireless/Kconfig:197:\tdepends on CFG80211\nnet/wireless/Kconfig-198-\tdefault KUNIT_ALL_TESTS\n--\nnet/wireless/Kconfig-203-\nnet/wireless/Kconfig:204:endif # CFG80211\n--\nnet/wireless/Makefile-1-# SPDX-License-Identifier: GPL-2.0\nnet/wireless/Makefile:2:obj-$(CONFIG_CFG80211) += cfg80211.o\nnet/wireless/Makefile-3-obj-y += tests/\n--\nnet/wireless/Makefile=12=cfg80211-$(CONFIG_OF) += of.o\nnet/wireless/Makefile:13:cfg80211-$(CONFIG_CFG80211_DEBUGFS) += debugfs.o\nnet/wireless/Makefile:14:cfg80211-$(CONFIG_CFG80211_WEXT) += wext-compat.o wext-sme.o\nnet/wireless/Makefile-15-\nnet/wireless/Makefile=16=CFLAGS_trace.o := -I$(src)\nnet/wireless/Makefile-17-\nnet/wireless/Makefile:18:cfg80211-$(CONFIG_CFG80211_USE_KERNEL_REGDB_KEYS) += shipped-certs.o\nnet/wireless/Makefile:19:ifneq ($(CONFIG_CFG80211_EXTRA_REGDB_KEYDIR),)\nnet/wireless/Makefile-20-cfg80211-y += extra-certs.o\n--\nnet/wireless/Makefile=23=$(obj)/shipped-certs.c: $(sort $(wildcard $(src)/certs/*.hex))\n--\nnet/wireless/Makefile-31-\nnet/wireless/Makefile:32:$(obj)/extra-certs.c: $(CONFIG_CFG80211_EXTRA_REGDB_KEYDIR) \\\nnet/wireless/Makefile:33:\t\t      $(sort $(wildcard $(CONFIG_CFG80211_EXTRA_REGDB_KEYDIR)/*.x509))\nnet/wireless/Makefile-34-\t@$(kecho) \"  GEN     $@\"\n--\nnet/wireless/chan.c=123=static const u16 puncturing_values_320mhz[] = {\n--\nnet/wireless/chan.c-128-\nnet/wireless/chan.c:129:#define CFG80211_PER_BW_VALID_PUNCTURING_VALUES(_bw) \\\nnet/wireless/chan.c-130-\t{ \\\n--\nnet/wireless/chan.c=135=static const struct cfg80211_per_bw_puncturing_values per_bw_puncturing[] = {\nnet/wireless/chan.c:136:\tCFG80211_PER_BW_VALID_PUNCTURING_VALUES(80),\nnet/wireless/chan.c:137:\tCFG80211_PER_BW_VALID_PUNCTURING_VALUES(160),\nnet/wireless/chan.c:138:\tCFG80211_PER_BW_VALID_PUNCTURING_VALUES(320)\nnet/wireless/chan.c-139-};\n--\nnet/wireless/chan.c=1695=static bool cfg80211_ir_permissive_chan(struct wiphy *wiphy,\n--\nnet/wireless/chan.c-1703-\nnet/wireless/chan.c:1704:\tif (!IS_ENABLED(CONFIG_CFG80211_REG_RELAX_NO_IR) ||\nnet/wireless/chan.c-1705-\t    !(wiphy-\u003eregulatory_flags \u0026 REGULATORY_ENABLE_RELAX_NO_IR))\n--\nnet/wireless/core.c=549=struct wiphy *wiphy_new_nm(const struct cfg80211_ops *ops, int sizeof_priv,\n--\nnet/wireless/core.c-636-\t\t\t  cfg80211_dfs_channels_update_work);\nnet/wireless/core.c:637:#ifdef CONFIG_CFG80211_WEXT\nnet/wireless/core.c-638-\trdev-\u003ewiphy.wext = \u0026cfg80211_wext_handler;\n--\nnet/wireless/core.c-658-\nnet/wireless/core.c:659:#ifdef CONFIG_CFG80211_DEFAULT_PS\nnet/wireless/core.c-660-\trdev-\u003ewiphy.flags |= WIPHY_FLAG_PS_ON_BY_DEFAULT;\n--\nnet/wireless/core.c=853=int wiphy_register(struct wiphy *wiphy)\n--\nnet/wireless/core.c-1122-\telse if (wiphy-\u003emax_num_akm_suites \u003c NL80211_MAX_NR_AKM_SUITES ||\nnet/wireless/core.c:1123:\t\t wiphy-\u003emax_num_akm_suites \u003e CFG80211_MAX_NUM_AKM_SUITES)\nnet/wireless/core.c-1124-\t\treturn -EINVAL;\n--\nnet/wireless/core.c=1408=static void _cfg80211_unregister_wdev(struct wireless_dev *wdev,\n--\nnet/wireless/core.c-1448-\nnet/wireless/core.c:1449:#ifdef CONFIG_CFG80211_WEXT\nnet/wireless/core.c-1450-\tkfree_sensitive(wdev-\u003ewext.keys);\n--\nnet/wireless/core.c=1503=void cfg80211_leave_locked(struct cfg80211_registered_device *rdev,\n--\nnet/wireless/core.c-1527-\nnet/wireless/core.c:1528:#ifdef CONFIG_CFG80211_WEXT\nnet/wireless/core.c-1529-\t\tkfree(wdev-\u003ewext.ie);\n--\nnet/wireless/core.c=1614=void cfg80211_init_wdev(struct wireless_dev *wdev)\n--\nnet/wireless/core.c-1622-\nnet/wireless/core.c:1623:#ifdef CONFIG_CFG80211_WEXT\nnet/wireless/core.c-1624-\twdev-\u003ewext.default_key = -1;\n--\nnet/wireless/core.c=1707=static int cfg80211_netdev_notifier_call(struct notifier_block *nb,\n--\nnet/wireless/core.c-1781-\t\tswitch (wdev-\u003eiftype) {\nnet/wireless/core.c:1782:#ifdef CONFIG_CFG80211_WEXT\nnet/wireless/core.c-1783-\t\tcase NL80211_IFTYPE_ADHOC:\n--\nnet/wireless/core.h=574=cfg80211_get_6ghz_power_type(const u8 *elems, size_t elems_len,\n--\nnet/wireless/core.h-576-\nnet/wireless/core.h:577:#ifdef CONFIG_CFG80211_DEVELOPER_WARNINGS\nnet/wireless/core.h:578:#define CFG80211_DEV_WARN_ON(cond)\tWARN_ON(cond)\nnet/wireless/core.h-579-#else\n--\nnet/wireless/core.h-584- */\nnet/wireless/core.h:585:#define CFG80211_DEV_WARN_ON(cond)\t({bool __r = (cond); __r; })\nnet/wireless/core.h-586-#endif\n--\nnet/wireless/core.h=624=struct cfg80211_colocated_ap {\n--\nnet/wireless/core.h-640-\nnet/wireless/core.h:641:#if IS_ENABLED(CONFIG_CFG80211_KUNIT_TEST)\nnet/wireless/core.h:642:#define EXPORT_SYMBOL_IF_CFG80211_KUNIT(sym) EXPORT_SYMBOL_IF_KUNIT(sym)\nnet/wireless/core.h:643:#define VISIBLE_IF_CFG80211_KUNIT\nnet/wireless/core.h-644-void cfg80211_free_coloc_ap_list(struct list_head *coloc_ap_list);\n--\nnet/wireless/core.h=649=size_t cfg80211_gen_new_ie(const u8 *ie, size_t ielen,\n--\nnet/wireless/core.h-652-#else\nnet/wireless/core.h:653:#define EXPORT_SYMBOL_IF_CFG80211_KUNIT(sym)\nnet/wireless/core.h:654:#define VISIBLE_IF_CFG80211_KUNIT static\nnet/wireless/core.h:655:#endif /* IS_ENABLED(CONFIG_CFG80211_KUNIT_TEST) */\nnet/wireless/core.h-656-\n--\nnet/wireless/debugfs.h-1-/* SPDX-License-Identifier: GPL-2.0 */\nnet/wireless/debugfs.h:2:#ifndef __CFG80211_DEBUGFS_H\nnet/wireless/debugfs.h:3:#define __CFG80211_DEBUGFS_H\nnet/wireless/debugfs.h-4-\nnet/wireless/debugfs.h:5:#ifdef CONFIG_CFG80211_DEBUGFS\nnet/wireless/debugfs.h-6-void cfg80211_debugfs_rdev_add(struct cfg80211_registered_device *rdev);\n--\nnet/wireless/debugfs.h=9=void cfg80211_debugfs_rdev_add(struct cfg80211_registered_device *rdev) {}\n--\nnet/wireless/debugfs.h-11-\nnet/wireless/debugfs.h:12:#endif /* __CFG80211_DEBUGFS_H */\n--\nnet/wireless/ibss.c=19=void __cfg80211_ibss_joined(struct net_device *dev, const u8 *bssid,\n--\nnet/wireless/ibss.c-23-\tstruct cfg80211_bss *bss;\nnet/wireless/ibss.c:24:#ifdef CONFIG_CFG80211_WEXT\nnet/wireless/ibss.c-25-\tunion iwreq_data wrqu;\n--\nnet/wireless/ibss.c-51-\t\t\t\tGFP_KERNEL);\nnet/wireless/ibss.c:52:#ifdef CONFIG_CFG80211_WEXT\nnet/wireless/ibss.c-53-\tmemset(\u0026wrqu, 0, sizeof(wrqu));\n--\nnet/wireless/ibss.c=87=int __cfg80211_join_ibss(struct cfg80211_registered_device *rdev,\n--\nnet/wireless/ibss.c-140-\nnet/wireless/ibss.c:141:#ifdef CONFIG_CFG80211_WEXT\nnet/wireless/ibss.c-142-\twdev-\u003ewext.ibss.chandef = params-\u003echandef;\n--\nnet/wireless/ibss.c=156=void cfg80211_clear_ibss(struct net_device *dev, bool nowext)\n--\nnet/wireless/ibss.c-184-\tmemset(\u0026wdev-\u003eu.ibss.chandef, 0, sizeof(wdev-\u003eu.ibss.chandef));\nnet/wireless/ibss.c:185:#ifdef CONFIG_CFG80211_WEXT\nnet/wireless/ibss.c-186-\tif (!nowext)\n--\nnet/wireless/ibss.c=192=int cfg80211_leave_ibss(struct cfg80211_registered_device *rdev,\n--\nnet/wireless/ibss.c-213-\nnet/wireless/ibss.c:214:#ifdef CONFIG_CFG80211_WEXT\nnet/wireless/ibss.c-215-int cfg80211_ibss_wext_join(struct cfg80211_registered_device *rdev,\n--\nnet/wireless/mlme.c=277=void cfg80211_michael_mic_failure(struct net_device *dev, const u8 *addr,\n--\nnet/wireless/mlme.c-282-\tstruct cfg80211_registered_device *rdev = wiphy_to_rdev(wiphy);\nnet/wireless/mlme.c:283:#ifdef CONFIG_CFG80211_WEXT\nnet/wireless/mlme.c-284-\tunion iwreq_data wrqu;\n--\nnet/wireless/nl80211.c=666=nl80211_nan_peer_map_policy[NL80211_NAN_PEER_MAP_ATTR_MAX + 1] = {\n--\nnet/wireless/nl80211.c-668-\t[NL80211_NAN_PEER_MAP_ATTR_TIME_SLOTS] =\nnet/wireless/nl80211.c:669:\t\tNLA_POLICY_EXACT_LEN(CFG80211_NAN_SCHED_NUM_TIME_SLOTS),\nnet/wireless/nl80211.c-670-};\n--\nnet/wireless/nl80211.c=700=static const struct nla_policy nl80211_policy[NUM_NL80211_ATTR] = {\n--\nnet/wireless/nl80211.c-1082-\t[NL80211_ATTR_NAN_TIME_SLOTS] =\nnet/wireless/nl80211.c:1083:\t\tNLA_POLICY_EXACT_LEN(CFG80211_NAN_SCHED_NUM_TIME_SLOTS),\nnet/wireless/nl80211.c-1084-\t[NL80211_ATTR_NAN_AVAIL_BLOB] =\n--\nnet/wireless/nl80211.c=5466=static int nl80211_set_key(struct sk_buff *skb, struct genl_info *info)\n--\nnet/wireless/nl80211.c-5508-\nnet/wireless/nl80211.c:5509:#ifdef CONFIG_CFG80211_WEXT\nnet/wireless/nl80211.c-5510-\t\twdev-\u003ewext.default_key = key.idx;\n--\nnet/wireless/nl80211.c-5531-\nnet/wireless/nl80211.c:5532:#ifdef CONFIG_CFG80211_WEXT\nnet/wireless/nl80211.c-5533-\t\twdev-\u003ewext.default_mgmt_key = key.idx;\n--\nnet/wireless/nl80211.c=5644=static int nl80211_del_key(struct sk_buff *skb, struct genl_info *info)\n--\nnet/wireless/nl80211.c-5690-\nnet/wireless/nl80211.c:5691:#ifdef CONFIG_CFG80211_WEXT\nnet/wireless/nl80211.c-5692-\tif (!err) {\n--\nnet/wireless/nl80211.c=7867=static int nl80211_fill_link_station(struct sk_buff *msg,\n--\nnet/wireless/nl80211.c-7914-\tswitch (rdev-\u003ewiphy.signal_type) {\nnet/wireless/nl80211.c:7915:\tcase CFG80211_SIGNAL_TYPE_MBM:\nnet/wireless/nl80211.c-7916-\t\tPUT_LINK_SINFO(SIGNAL, signal, u8);\n--\nnet/wireless/nl80211.c=8045=static int nl80211_put_sta_info_common(struct sk_buff *msg,\n--\nnet/wireless/nl80211.c-8094-\tswitch (rdev-\u003ewiphy.signal_type) {\nnet/wireless/nl80211.c:8095:\tcase CFG80211_SIGNAL_TYPE_MBM:\nnet/wireless/nl80211.c-8096-\t\tPUT_SINFO(SIGNAL, signal, u8);\n--\nnet/wireless/nl80211.c=8790=int cfg80211_check_station_change(struct wiphy *wiphy,\n--\nnet/wireless/nl80211.c-8794-\tif (params-\u003elisten_interval != -1 \u0026\u0026\nnet/wireless/nl80211.c:8795:\t    statype != CFG80211_STA_AP_CLIENT_UNASSOC)\nnet/wireless/nl80211.c-8796-\t\treturn -EINVAL;\n--\nnet/wireless/nl80211.c-8798-\tif (params-\u003esupport_p2p_ps != -1 \u0026\u0026\nnet/wireless/nl80211.c:8799:\t    statype != CFG80211_STA_AP_CLIENT_UNASSOC)\nnet/wireless/nl80211.c-8800-\t\treturn -EINVAL;\n--\nnet/wireless/nl80211.c-8803-\t    !(params-\u003esta_flags_set \u0026 BIT(NL80211_STA_FLAG_TDLS_PEER)) \u0026\u0026\nnet/wireless/nl80211.c:8804:\t    statype != CFG80211_STA_AP_CLIENT_UNASSOC)\nnet/wireless/nl80211.c-8805-\t\treturn -EINVAL;\n--\nnet/wireless/nl80211.c-8810-\tswitch (statype) {\nnet/wireless/nl80211.c:8811:\tcase CFG80211_STA_MESH_PEER_KERNEL:\nnet/wireless/nl80211.c:8812:\tcase CFG80211_STA_MESH_PEER_USER:\nnet/wireless/nl80211.c-8813-\t\t/*\n--\nnet/wireless/nl80211.c-8823-\t\tbreak;\nnet/wireless/nl80211.c:8824:\tcase CFG80211_STA_TDLS_PEER_SETUP:\nnet/wireless/nl80211.c:8825:\tcase CFG80211_STA_TDLS_PEER_ACTIVE:\nnet/wireless/nl80211.c-8826-\t\tif (!(params-\u003esta_flags_set \u0026 BIT(NL80211_STA_FLAG_TDLS_PEER)))\n--\nnet/wireless/nl80211.c-8840-\nnet/wireless/nl80211.c:8841:\tif (statype != CFG80211_STA_TDLS_PEER_SETUP \u0026\u0026\nnet/wireless/nl80211.c:8842:\t    statype != CFG80211_STA_TDLS_PEER_ACTIVE) {\nnet/wireless/nl80211.c-8843-\t\t/* TDLS can't be set, ... */\n--\nnet/wireless/nl80211.c-8853-\nnet/wireless/nl80211.c:8854:\tif (statype != CFG80211_STA_TDLS_PEER_SETUP \u0026\u0026\nnet/wireless/nl80211.c:8855:\t    statype != CFG80211_STA_AP_CLIENT_UNASSOC) {\nnet/wireless/nl80211.c-8856-\t\t/* reject other things that can't change */\n--\nnet/wireless/nl80211.c-8862-\t\t\treturn -EINVAL;\nnet/wireless/nl80211.c:8863:\t\tif (statype != CFG80211_STA_NAN_MGMT \u0026\u0026\nnet/wireless/nl80211.c-8864-\t\t    (params-\u003elink_sta_params.ht_capa ||\n--\nnet/wireless/nl80211.c-8874-\nnet/wireless/nl80211.c:8875:\tif (statype != CFG80211_STA_AP_CLIENT \u0026\u0026\nnet/wireless/nl80211.c:8876:\t    statype != CFG80211_STA_AP_CLIENT_UNASSOC) {\nnet/wireless/nl80211.c-8877-\t\tif (params-\u003evlan)\n--\nnet/wireless/nl80211.c-8881-\t/* Accept EMLSR capabilities only for AP client before association */\nnet/wireless/nl80211.c:8882:\tif (statype != CFG80211_STA_AP_CLIENT_UNASSOC \u0026\u0026\nnet/wireless/nl80211.c-8883-\t    params-\u003eeml_cap_present)\n--\nnet/wireless/nl80211.c-8886-\tswitch (statype) {\nnet/wireless/nl80211.c:8887:\tcase CFG80211_STA_AP_MLME_CLIENT:\nnet/wireless/nl80211.c-8888-\t\t/* Use this only for authorizing/unauthorizing a station */\n--\nnet/wireless/nl80211.c-8891-\t\tbreak;\nnet/wireless/nl80211.c:8892:\tcase CFG80211_STA_AP_CLIENT:\nnet/wireless/nl80211.c:8893:\tcase CFG80211_STA_AP_CLIENT_UNASSOC:\nnet/wireless/nl80211.c-8894-\t\t/* accept only the listed bits */\n--\nnet/wireless/nl80211.c-8911-\t\tbreak;\nnet/wireless/nl80211.c:8912:\tcase CFG80211_STA_IBSS:\nnet/wireless/nl80211.c:8913:\tcase CFG80211_STA_AP_STA:\nnet/wireless/nl80211.c-8914-\t\t/* reject any changes other than AUTHORIZED */\n--\nnet/wireless/nl80211.c-8917-\t\tbreak;\nnet/wireless/nl80211.c:8918:\tcase CFG80211_STA_TDLS_PEER_SETUP:\nnet/wireless/nl80211.c-8919-\t\t/* reject any changes other than AUTHORIZED or WME */\n--\nnet/wireless/nl80211.c-8927-\t\tbreak;\nnet/wireless/nl80211.c:8928:\tcase CFG80211_STA_TDLS_PEER_ACTIVE:\nnet/wireless/nl80211.c-8929-\t\t/* reject any changes */\nnet/wireless/nl80211.c-8930-\t\treturn -EINVAL;\nnet/wireless/nl80211.c:8931:\tcase CFG80211_STA_MESH_PEER_KERNEL:\nnet/wireless/nl80211.c-8932-\t\tif (params-\u003esta_modify_mask \u0026 STATION_PARAM_APPLY_PLINK_STATE)\n--\nnet/wireless/nl80211.c-8934-\t\tbreak;\nnet/wireless/nl80211.c:8935:\tcase CFG80211_STA_MESH_PEER_USER:\nnet/wireless/nl80211.c-8936-\t\tif (params-\u003eplink_action != NL80211_PLINK_ACTION_NO_ACTION \u0026\u0026\n--\nnet/wireless/nl80211.c-8939-\t\tbreak;\nnet/wireless/nl80211.c:8940:\tcase CFG80211_STA_NAN_MGMT:\nnet/wireless/nl80211.c-8941-\t\tif (params-\u003esta_flags_mask \u0026\n--\nnet/wireless/nl80211.c-8945-\t\tbreak;\nnet/wireless/nl80211.c:8946:\tcase CFG80211_STA_NAN_DATA:\nnet/wireless/nl80211.c-8947-\t\tif (params-\u003esta_flags_mask \u0026\n--\nnet/wireless/nl80211.c-8959-\t */\nnet/wireless/nl80211.c:8960:\tif (statype != CFG80211_STA_AP_CLIENT_UNASSOC \u0026\u0026\nnet/wireless/nl80211.c:8961:\t    statype != CFG80211_STA_TDLS_PEER_SETUP)\nnet/wireless/nl80211.c-8962-\t\tparams-\u003elink_sta_params.opmode_notif_used = false;\n--\nnet/wireless/nl80211.c=10804=static int nl80211_get_reg_dump(struct sk_buff *skb,\n--\nnet/wireless/nl80211.c-10845-\nnet/wireless/nl80211.c:10846:#ifdef CONFIG_CFG80211_CRDA_SUPPORT\nnet/wireless/nl80211.c-10847-static const struct nla_policy reg_rule_policy[NL80211_REG_RULE_ATTR_MAX + 1] = {\n--\nnet/wireless/nl80211.c=10897=static int nl80211_set_reg(struct sk_buff *skb, struct genl_info *info)\n--\nnet/wireless/nl80211.c-10975-}\nnet/wireless/nl80211.c:10976:#endif /* CONFIG_CFG80211_CRDA_SUPPORT */\nnet/wireless/nl80211.c-10977-\n--\nnet/wireless/nl80211.c=12399=static int nl80211_send_bss(struct sk_buff *msg, struct netlink_callback *cb,\n--\nnet/wireless/nl80211.c-12496-\t\tswitch (rdev-\u003ewiphy.signal_type) {\nnet/wireless/nl80211.c:12497:\t\tcase CFG80211_SIGNAL_TYPE_MBM:\nnet/wireless/nl80211.c-12498-\t\t\tif (nla_put_u32(msg, NL80211_BSS_SIGNAL_MBM,\n--\nnet/wireless/nl80211.c-12501-\t\t\tbreak;\nnet/wireless/nl80211.c:12502:\t\tcase CFG80211_SIGNAL_TYPE_UNSPEC:\nnet/wireless/nl80211.c-12503-\t\t\tif (nla_put_u8(msg, NL80211_BSS_SIGNAL_UNSPEC,\n--\nnet/wireless/nl80211.c=16543=static int nl80211_parse_nan_conf(struct wiphy *wiphy,\n--\nnet/wireless/nl80211.c-16557-\nnet/wireless/nl80211.c:16558:\t\tchanged |= CFG80211_NAN_CONF_CHANGED_PREF;\nnet/wireless/nl80211.c-16559-\t}\n--\nnet/wireless/nl80211.c-16570-\t\tconf-\u003ebands = bands;\nnet/wireless/nl80211.c:16571:\t\tchanged |= CFG80211_NAN_CONF_CHANGED_BANDS;\nnet/wireless/nl80211.c-16572-\t}\n--\nnet/wireless/nl80211.c-16592-\nnet/wireless/nl80211.c:16593:\tchanged |= CFG80211_NAN_CONF_CHANGED_CONFIG;\nnet/wireless/nl80211.c-16594-\tif (attrs[NL80211_NAN_CONF_CLUSTER_ID] \u0026\u0026 start) {\n--\nnet/wireless/nl80211.c=17404=nl80211_parse_nan_schedule(struct genl_info *info, struct nlattr *slots_attr,\nnet/wireless/nl80211.c:17405:\t\t\t   u8 schedule[CFG80211_NAN_SCHED_NUM_TIME_SLOTS],\nnet/wireless/nl80211.c-17406-\t\t\t   u8 n_channels)\nnet/wireless/nl80211.c-17407-{\nnet/wireless/nl80211.c:17408:\tif (WARN_ON(nla_len(slots_attr) != CFG80211_NAN_SCHED_NUM_TIME_SLOTS))\nnet/wireless/nl80211.c-17409-\t\treturn -EINVAL;\n--\nnet/wireless/nl80211.c-17412-\nnet/wireless/nl80211.c:17413:\tfor (int slot = 0; slot \u003c CFG80211_NAN_SCHED_NUM_TIME_SLOTS; slot++) {\nnet/wireless/nl80211.c-17414-\t\tif (schedule[slot] != NL80211_NAN_SCHED_NOT_AVAIL_SLOT \u0026\u0026\n--\nnet/wireless/nl80211.c=17510=static int nl80211_nan_set_peer_sched(struct sk_buff *skb,\n--\nnet/wireless/nl80211.c-17604-\tfor (int j = 0; j \u003c ARRAY_SIZE(sched.maps); j++)\nnet/wireless/nl80211.c:17605:\t\tsched.maps[j].map_id = CFG80211_NAN_INVALID_MAP_ID;\nnet/wireless/nl80211.c-17606-\n--\nnet/wireless/nl80211.c=19230=static int nl80211_set_hw_timestamp(struct sk_buff *skb,\n--\nnet/wireless/nl80211.c-19240-\tif (!info-\u003eattrs[NL80211_ATTR_MAC] \u0026\u0026\nnet/wireless/nl80211.c:19241:\t    rdev-\u003ewiphy.hw_timestamp_max_peers != CFG80211_HW_TIMESTAMP_ALL_PEERS)\nnet/wireless/nl80211.c-19242-\t\treturn -EOPNOTSUPP;\n--\nnet/wireless/nl80211.c=19733=static const struct genl_small_ops nl80211_small_ops[] = {\n--\nnet/wireless/nl80211.c-19906-\t},\nnet/wireless/nl80211.c:19907:#ifdef CONFIG_CFG80211_CRDA_SUPPORT\nnet/wireless/nl80211.c-19908-\t{\n--\nnet/wireless/nl80211.c=23407=void cfg80211_schedule_channels_check(struct wireless_dev *wdev)\n--\nnet/wireless/nl80211.c-23414-\t\t\t\t     NL80211_EXT_FEATURE_DFS_CONCURRENT) ||\nnet/wireless/nl80211.c:23415:\t    (IS_ENABLED(CONFIG_CFG80211_REG_RELAX_NO_IR) \u0026\u0026\nnet/wireless/nl80211.c-23416-\t     wiphy-\u003eregulatory_flags \u0026 REGULATORY_ENABLE_RELAX_NO_IR)))\n--\nnet/wireless/rdev-ops.h-6- */\nnet/wireless/rdev-ops.h:7:#ifndef __CFG80211_RDEV_OPS\nnet/wireless/rdev-ops.h:8:#define __CFG80211_RDEV_OPS\nnet/wireless/rdev-ops.h-9-\n--\nnet/wireless/rdev-ops.h=1625=rdev_set_epcs(struct cfg80211_registered_device *rdev,\n--\nnet/wireless/rdev-ops.h-1638-\nnet/wireless/rdev-ops.h:1639:#endif /* __CFG80211_RDEV_OPS */\n--\nnet/wireless/reg.c=497=static int reg_schedule_apply(const struct ieee80211_regdomain *regdom)\n--\nnet/wireless/reg.c-516-\nnet/wireless/reg.c:517:#ifdef CONFIG_CFG80211_CRDA_SUPPORT\nnet/wireless/reg.c-518-/* Max number of consecutive attempts to communicate with CRDA  */\n--\nnet/wireless/reg.c=586=static inline int call_crda(const char *alpha2)\n--\nnet/wireless/reg.c-589-}\nnet/wireless/reg.c:590:#endif /* CONFIG_CFG80211_CRDA_SUPPORT */\nnet/wireless/reg.c-591-\n--\nnet/wireless/reg.c=697=static bool valid_country(const u8 *data, unsigned int size,\n--\nnet/wireless/reg.c-729-\nnet/wireless/reg.c:730:#ifdef CONFIG_CFG80211_REQUIRE_SIGNED_REGDB\nnet/wireless/reg.c-731-#include \u003ckeys/asymmetric-type.h\u003e\n--\nnet/wireless/reg.c=735=static int __init load_builtin_regdb_keys(void)\n--\nnet/wireless/reg.c-747-\nnet/wireless/reg.c:748:#ifdef CONFIG_CFG80211_USE_KERNEL_REGDB_KEYS\nnet/wireless/reg.c-749-\tx509_load_certificate_list(shipped_regdb_certs,\n--\nnet/wireless/reg.c-752-#endif\nnet/wireless/reg.c:753:#ifdef CONFIG_CFG80211_EXTRA_REGDB_KEYDIR\nnet/wireless/reg.c:754:\tif (CONFIG_CFG80211_EXTRA_REGDB_KEYDIR[0] != '\\0')\nnet/wireless/reg.c-755-\t\tx509_load_certificate_list(extra_regdb_certs,\n--\nnet/wireless/reg.c=798=static void free_regdb_keyring(void)\n--\nnet/wireless/reg.c-800-}\nnet/wireless/reg.c:801:#endif /* CONFIG_CFG80211_REQUIRE_SIGNED_REGDB */\nnet/wireless/reg.c-802-\n--\nnet/wireless/reg.c=2038=bool reg_last_request_cell_base(void)\n--\nnet/wireless/reg.c-2042-\nnet/wireless/reg.c:2043:#ifdef CONFIG_CFG80211_REG_CELLULAR_HINTS\nnet/wireless/reg.c-2044-/* Core specific check */\n--\nnet/wireless/scan.c=230=static size_t cfg80211_copy_elem_with_frags(const struct element *elem,\n--\nnet/wireless/scan.c-267-\nnet/wireless/scan.c:268:VISIBLE_IF_CFG80211_KUNIT size_t\nnet/wireless/scan.c-269-cfg80211_gen_new_ie(const u8 *ie, size_t ielen,\n--\nnet/wireless/scan.c-406-}\nnet/wireless/scan.c:407:EXPORT_SYMBOL_IF_CFG80211_KUNIT(cfg80211_gen_new_ie);\nnet/wireless/scan.c-408-\n--\nnet/wireless/scan.c=546=static int cfg80211_calc_short_ssid(const struct cfg80211_bss_ies *ies,\n--\nnet/wireless/scan.c-557-\n\n"
}

7/2 2026/09/05 01:04 llm patch-evaluator
0m Model:
gemini-3.7-flash

Args:
null

Results:
null

Tokens:
							input: 16016
							output: 35
							thoughts: 28
						

Thoughts:
Here's my take on the process, considering my expertise:

**Dissecting wiphy_unregister() and cfg80211_rdev_list Manipulation**

Okay, so I'm digging into `wiphy_unregister()` and, as usual, my first thought is, "Where's the critical section? How are we protecting `cfg80211_rdev_list`?". I know the list is likely protected by a mutex or spinlock, and I need to identify which one and understand the locking order, especially given that it is a global resource. I'm looking for the dance of acquiring and releasing that lock. Is it a simple locking scheme, or something more complex with reader/writer locks? This is critical for preventing race conditions, particularly during the unregistration process when devices are likely being removed or deinitialized. I'm wondering if there are any callbacks or handlers that also access that global list and that must be considered with the synchronization primitive. I expect to see the code carefully iterating through `cfg80211_rdev_list` and, at each stage, safely handling the deallocation of the `wiphy` structure. I need to see how they're handling references, if there's any refcounting happening, or if some other mechanism exists to prevent use-after-free scenarios. I'm particularly interested in the interaction with the regulatory domain handling; is there anything specific happening there that needs to be considered in the unregistration? This is typically where things can get tricky. Also, what happens with any pending operations or workqueues associated with the `wiphy`? These need to be flushed or cancelled gracefully. I also must evaluate the potential for deadlocks.



8/2 2026/09/05 01:04 tool grepper
0m Args:
{
  "Expression": "cfg80211_rdev_list",
  "PathPrefix": "net/wireless/"
}

Results:
{
  "Output": "net/wireless/core.c=43=MODULE_ALIAS_GENL_FAMILY(NL80211_GENL_NAME);\n--\nnet/wireless/core.c-45-/* RCU-protected (and RTNL for writers) */\nnet/wireless/core.c:46:LIST_HEAD(cfg80211_rdev_list);\nnet/wireless/core.c:47:int cfg80211_rdev_list_generation;\nnet/wireless/core.c-48-\n--\nnet/wireless/core.c=853=int wiphy_register(struct wiphy *wiphy)\n--\nnet/wireless/core.c-1165-\nnet/wireless/core.c:1166:\tlist_add_rcu(\u0026rdev-\u003elist, \u0026cfg80211_rdev_list);\nnet/wireless/core.c:1167:\tcfg80211_rdev_list_generation++;\nnet/wireless/core.c-1168-\n--\nnet/wireless/core.c=1290=void wiphy_unregister(struct wiphy *wiphy)\n--\nnet/wireless/core.c-1324-\nnet/wireless/core.c:1325:\tcfg80211_rdev_list_generation++;\nnet/wireless/core.c-1326-\tdevice_del(\u0026rdev-\u003ewiphy.dev);\n--\nnet/wireless/core.h=166=extern struct workqueue_struct *cfg80211_wq;\nnet/wireless/core.h:167:extern struct list_head cfg80211_rdev_list;\nnet/wireless/core.h:168:extern int cfg80211_rdev_list_generation;\nnet/wireless/core.h-169-\n--\nnet/wireless/core.h=171=static inline int for_each_rdev_check_rtnl(void)\n--\nnet/wireless/core.h-177-\tif (for_each_rdev_check_rtnl()) {} else\t\t\t\t\\\nnet/wireless/core.h:178:\t\tlist_for_each_entry(rdev, \u0026cfg80211_rdev_list, list)\nnet/wireless/core.h-179-\n--\nnet/wireless/nl80211.c=3057=static int nl80211_send_wiphy(struct cfg80211_registered_device *rdev,\n--\nnet/wireless/nl80211.c-3083-\t    nla_put_u32(msg, NL80211_ATTR_GENERATION,\nnet/wireless/nl80211.c:3084:\t\t\tcfg80211_rdev_list_generation))\nnet/wireless/nl80211.c-3085-\t\tgoto nla_put_failure;\n--\nnet/wireless/nl80211.c=4659=static int nl80211_send_iface(struct sk_buff *msg, u32 portid, u32 seq, int flags,\n--\nnet/wireless/nl80211.c-4688-\t\t\trdev-\u003edevlist_generation ^\nnet/wireless/nl80211.c:4689:\t\t\t(cfg80211_rdev_list_generation \u003c\u003c 2)) ||\nnet/wireless/nl80211.c-4690-\t    nla_put_u8(msg, NL80211_ATTR_4ADDR, wdev-\u003euse_4addr) ||\n--\nnet/wireless/nl80211.c=10804=static int nl80211_get_reg_dump(struct sk_buff *skb,\n--\nnet/wireless/nl80211.c-10822-\treg_idx = 1;\nnet/wireless/nl80211.c:10823:\tlist_for_each_entry_rcu(rdev, \u0026cfg80211_rdev_list, list) {\nnet/wireless/nl80211.c-10824-\t\tregdom = get_wiphy_regdom(\u0026rdev-\u003ewiphy);\n--\nnet/wireless/nl80211.c=23115=static int nl80211_netlink_notify(struct notifier_block * nb,\n--\nnet/wireless/nl80211.c-23128-\nnet/wireless/nl80211.c:23129:\tlist_for_each_entry_rcu(rdev, \u0026cfg80211_rdev_list, list) {\nnet/wireless/nl80211.c-23130-\t\tstruct cfg80211_sched_scan_request *sched_scan_req;\n--\nnet/wireless/reg.c=2464=static void reg_check_chans_work(struct work_struct *work)\n--\nnet/wireless/reg.c-2475-\trcu_read_lock();\nnet/wireless/reg.c:2476:\tlist_for_each_entry_rcu(rdev, \u0026cfg80211_rdev_list, list) {\nnet/wireless/reg.c-2477-\t\trcu_read_unlock();\n"
}

9/2 2026/09/05 01:04 llm patch-evaluator
0m Model:
gemini-3.7-flash

Args:
null

Results:
null

Tokens:
							input: 17810
							output: 31
							thoughts: 109
						

Thoughts:
**Examining the Wireless Regulatory Domain Configuration**

Alright, let's break this down. My initial hunch is confirmed: `net/wireless/reg.c` is definitely brought into the build process when `CONFIG_CFG80211` is enabled. Time to verify that assumption. Let's dig into `net/wireless/Makefile`. Yup, just as expected, the `obj-$(CONFIG_CFG80211) += cfg80211.o` line clearly shows the conditional inclusion. And there it is, inside the `cfg80211-y` variable definition: `reg.o` is indeed being compiled along with the other core modules. Always good to double check, so let's make sure that's correct, going back to the `net/wireless/Makefile` to confirm.



10/2 2026/09/05 01:04 tool read-file
0m Args:
{
  "File": "net/wireless/Makefile",
  "FirstLine": 1,
  "LineCount": 30
}

Results:
{
  "Contents": "   1:\t# SPDX-License-Identifier: GPL-2.0\n   2:\tobj-$(CONFIG_CFG80211) += cfg80211.o\n   3:\tobj-y += tests/\n   4:\t\n   5:\tobj-$(CONFIG_WEXT_CORE) += wext-core.o\n   6:\tobj-$(CONFIG_WEXT_PROC) += wext-proc.o\n   7:\tobj-$(CONFIG_WEXT_PRIV) += wext-priv.o\n   8:\t\n   9:\tcfg80211-y += core.o sysfs.o radiotap.o util.o reg.o scan.o nl80211.o\n  10:\tcfg80211-y += mlme.o ibss.o sme.o chan.o ethtool.o mesh.o ap.o trace.o ocb.o\n  11:\tcfg80211-y += michael-mic.o pmsr.o\n  12:\tcfg80211-$(CONFIG_OF) += of.o\n  13:\tcfg80211-$(CONFIG_CFG80211_DEBUGFS) += debugfs.o\n  14:\tcfg80211-$(CONFIG_CFG80211_WEXT) += wext-compat.o wext-sme.o\n  15:\t\n  16:\tCFLAGS_trace.o := -I$(src)\n  17:\t\n  18:\tcfg80211-$(CONFIG_CFG80211_USE_KERNEL_REGDB_KEYS) += shipped-certs.o\n  19:\tifneq ($(CONFIG_CFG80211_EXTRA_REGDB_KEYDIR),)\n  20:\tcfg80211-y += extra-certs.o\n  21:\tendif\n  22:\t\n  23:\t$(obj)/shipped-certs.c: $(sort $(wildcard $(src)/certs/*.hex))\n  24:\t\t@$(kecho) \"  GEN     $@\"\n  25:\t\t$(Q)(echo '#include \"reg.h\"'; \\\n  26:\t\t  echo 'const u8 shipped_regdb_certs[] = {'; \\\n  27:\t\t  echo | cat - $^ ; \\\n  28:\t\t  echo '};'; \\\n  29:\t\t  echo 'unsigned int shipped_regdb_certs_len = sizeof(shipped_regdb_certs);'; \\\n  30:\t\t ) \u003e $@\n"
}

11/2 2026/09/05 01:04 llm patch-evaluator
0m Model:
gemini-3.7-flash

Args:
null

Results:
null

Tokens:
							input: 18767
							output: 32
							thoughts: 24
						

Thoughts:
Here's a summary of my thought process:

**Diving into the Kernel Wireless Configuration**

Okay, so I need to figure out the dependencies related to `CFG80211`. Time to head straight to the source – `net/wireless/Kconfig`. That's where all the kernel wireless configuration options are defined, and `CFG80211` is obviously a core component of that. I'll need to carefully examine that file to understand which other options, features, or modules rely on or are linked to `CFG80211`. Understanding those dependencies is crucial for any modifications or deeper analysis I'm planning. I need to ensure nothing breaks unexpectedly later on down the line.



12/2 2026/09/05 01:04 tool read-file
0m Args:
{
  "File": "net/wireless/Kconfig",
  "FirstLine": 1,
  "LineCount": 40
}

Results:
{
  "Contents": "   1:\t# SPDX-License-Identifier: GPL-2.0-only\n   2:\tconfig WIRELESS_EXT\n   3:\t\tbool\n   4:\t\n   5:\tconfig WEXT_CORE\n   6:\t\tdef_bool y\n   7:\t\tdepends on CFG80211_WEXT || WIRELESS_EXT\n   8:\t\n   9:\tconfig WEXT_PROC\n  10:\t\tdef_bool y\n  11:\t\tdepends on PROC_FS\n  12:\t\tdepends on WEXT_CORE\n  13:\t\n  14:\tconfig WEXT_PRIV\n  15:\t\tbool\n  16:\t\n  17:\tconfig CFG80211\n  18:\t\ttristate \"cfg80211 - wireless configuration API\"\n  19:\t\tdepends on RFKILL || !RFKILL\n  20:\t\tselect FW_LOADER\n  21:\t\tselect CRC32\n  22:\t\t# may need to update this when certificates are changed and are\n  23:\t\t# using a different algorithm, though right now they shouldn't\n  24:\t\t# (this is here rather than below to allow it to be a module)\n  25:\t\tselect CRYPTO_SHA256 if CFG80211_USE_KERNEL_REGDB_KEYS\n  26:\t\thelp\n  27:\t\t  cfg80211 is the Linux wireless LAN (802.11) configuration API.\n  28:\t\t  Enable this if you have a wireless device.\n  29:\t\n  30:\t\t  For more information refer to documentation on the wireless wiki:\n  31:\t\n  32:\t\t  https://wireless.wiki.kernel.org/en/developers/Documentation/cfg80211\n  33:\t\n  34:\t\t  When built as a module it will be called cfg80211.\n  35:\t\n  36:\tif CFG80211\n  37:\t\n  38:\tconfig NL80211_TESTMODE\n  39:\t\tbool \"nl80211 testmode command\"\n  40:\t\thelp\n"
}

13/2 2026/09/05 01:04 llm patch-evaluator
0m Model:
gemini-3.7-flash

Args:
null

Results:
null

Tokens:
							input: 19515
							output: 30
							thoughts: 510
						

Thoughts:
**Analyzing the Regulatory Domain Change in `net/wireless/reg.c`**

Okay, let's break down this code change in `net/wireless/reg.c`. My initial thought is to identify exactly *what* changed and why. I see the modification within `reg_check_chans_work`, a critical function involved in verifying active wireless interfaces after a regulatory change.

Before, it was a straightforward loop, holding the `rtnl_lock` while iterating through registered devices and calling `reg_leave_invalid_chans`.  Now, it's been refactored. The key difference is the introduction of `rcu_read_lock` and `rcu_read_unlock` surrounding a `list_for_each_entry_rcu` iteration, with `rtnl_lock` and `rtnl_unlock` nested within. The comment explaining this change is the important clue: this was done to address potential starvation of other RTNL waiters because `cfg80211_leave` can be slow, and to avoid issues around rdev unregistration. Specifically, `wiphy_unregister` holds `rtnl_lock` across `list_del_rcu` and `synchronize_rcu`, so the `rdev` can't be freed while the `rtnl_lock` is held. So, the original lock held the RTNL lock too long. The change ensures RTNL is held on a per-device basis.

Now, the important question for my work is: Is this code path reachable, particularly within my standard testing environments, like syzkaller or virtualized setups? Absolutely. The `cfg80211` subsystem, coupled with `mac80211` and `mac80211_hwsim`, provides multiple avenues. Regulatory domain changes via NL80211 commands, like `NL80211_CMD_REQ_SET_REG`, trigger `reg_check_channels()` or, as I see here, the delayed work function that ultimately leads to this `reg_check_chans_work` call.

My next immediate step is to trace the call paths to confirm, in detail, where `reg_check_channels` or `reg_check_chans_work` is called, and how it is scheduled. This will help determine the precise conditions under which this locking change becomes active and how likely a particular test case will exercise the changed code.



14/2 2026/09/05 01:04 tool grepper
0m Args:
{
  "Expression": "reg_check_chans",
  "PathPrefix": "net/wireless/"
}

Results:
{
  "Output": "net/wireless/reg.c=221=struct reg_beacon {\n--\nnet/wireless/reg.c-225-\nnet/wireless/reg.c:226:static void reg_check_chans_work(struct work_struct *work);\nnet/wireless/reg.c:227:static DECLARE_DELAYED_WORK(reg_check_chans, reg_check_chans_work);\nnet/wireless/reg.c-228-\n--\nnet/wireless/reg.c=2449=static void reg_leave_invalid_chans(struct wiphy *wiphy)\n--\nnet/wireless/reg.c-2463-\nnet/wireless/reg.c:2464:static void reg_check_chans_work(struct work_struct *work)\nnet/wireless/reg.c-2465-{\n--\nnet/wireless/reg.c=2486=void reg_check_channels(void)\n--\nnet/wireless/reg.c-2492-\tmod_delayed_work(system_power_efficient_wq,\nnet/wireless/reg.c:2493:\t\t\t \u0026reg_check_chans,\nnet/wireless/reg.c-2494-\t\t\t msecs_to_jiffies(REG_ENFORCE_GRACE_MS));\n--\nnet/wireless/reg.c=4359=void regulatory_exit(void)\n--\nnet/wireless/reg.c-4365-\tcancel_crda_timeout_sync();\nnet/wireless/reg.c:4366:\tcancel_delayed_work_sync(\u0026reg_check_chans);\nnet/wireless/reg.c-4367-\n"
}

15/2 2026/09/05 01:04 llm patch-evaluator
0m Model:
gemini-3.7-flash

Args:
null

Results:
null

Tokens:
							input: 21005
							output: 29
							thoughts: 15
						

Thoughts:
Here's my take on those thoughts:

**Tracing the Call Path: `reg_check_channels`**

Okay, so I need to understand the execution flow that leads to `reg_check_channels`. That's the key. I can't just look at the function definition; I need to see where it's being *used*. I need to identify the call sites. Time to get my bearings and trace the calls. I'm going to follow the breadcrumbs and see where that function is being invoked. Understanding the context will give me clues about its purpose and how it fits into the larger architecture. Let's dig in and find those call locations.



16/2 2026/09/05 01:04 tool grepper
0m Args:
{
  "Expression": "reg_check_channels",
  "PathPrefix": "net/wireless/"
}

Results:
{
  "Output": "net/wireless/nl80211.c=23407=void cfg80211_schedule_channels_check(struct wireless_dev *wdev)\n--\nnet/wireless/nl80211.c-23416-\t     wiphy-\u003eregulatory_flags \u0026 REGULATORY_ENABLE_RELAX_NO_IR)))\nnet/wireless/nl80211.c:23417:\t\treg_check_channels();\nnet/wireless/nl80211.c-23418-}\n--\nnet/wireless/reg.c=2464=static void reg_check_chans_work(struct work_struct *work)\n--\nnet/wireless/reg.c-2485-\nnet/wireless/reg.c:2486:void reg_check_channels(void)\nnet/wireless/reg.c-2487-{\n--\nnet/wireless/reg.c=2527=static void update_all_wiphy_regulatory(enum nl80211_reg_initiator initiator)\n--\nnet/wireless/reg.c-2538-\nnet/wireless/reg.c:2539:\treg_check_channels();\nnet/wireless/reg.c-2540-}\n--\nnet/wireless/reg.c=3025=static void reg_process_hint(struct regulatory_request *reg_request)\n--\nnet/wireless/reg.c-3068-\t\twiphy_all_share_dfs_chan_state(wiphy);\nnet/wireless/reg.c:3069:\t\treg_check_channels();\nnet/wireless/reg.c-3070-\t}\n--\nnet/wireless/reg.c=3197=static void reg_process_self_managed_hints(void)\n--\nnet/wireless/reg.c-3208-\nnet/wireless/reg.c:3209:\treg_check_channels();\nnet/wireless/reg.c-3210-}\n--\nnet/wireless/reg.c=3285=void regulatory_hint_indoor(bool is_indoor, u32 portid)\n--\nnet/wireless/reg.c-3306-\tif (!is_indoor)\nnet/wireless/reg.c:3307:\t\treg_check_channels();\nnet/wireless/reg.c-3308-}\n--\nnet/wireless/reg.c=3310=void regulatory_netlink_notify(u32 portid)\n--\nnet/wireless/reg.c-3323-\nnet/wireless/reg.c:3324:\treg_check_channels();\nnet/wireless/reg.c-3325-}\n--\nnet/wireless/reg.c=3489=static void restore_regulatory_settings(bool reset_user, bool cached)\n--\nnet/wireless/reg.c-3506-\t\treg_is_indoor = false;\nnet/wireless/reg.c:3507:\t\treg_check_channels();\nnet/wireless/reg.c-3508-\t}\n--\nnet/wireless/reg.c=4076=int regulatory_set_wiphy_regd_sync(struct wiphy *wiphy,\n--\nnet/wireless/reg.c-4088-\treg_process_self_managed_hint(wiphy);\nnet/wireless/reg.c:4089:\treg_check_channels();\nnet/wireless/reg.c-4090-\treturn 0;\n--\nnet/wireless/reg.h=174=int reg_reload_regdb(void);\n--\nnet/wireless/reg.h-176-/**\nnet/wireless/reg.h:177: * reg_check_channels - schedule regulatory enforcement\nnet/wireless/reg.h-178- */\nnet/wireless/reg.h:179:void reg_check_channels(void);\nnet/wireless/reg.h-180-\n"
}

17/2 2026/09/05 01:04 llm patch-evaluator
0m Model:
gemini-3.7-flash

Args:
null

Results:
null

Tokens:
							input: 22184
							output: 182
							thoughts: 629
						

Thoughts:
**My Analysis of a Concurrency Vulnerability in Wireless Regulatory Handling**

Okay, so I've been digging into this potential concurrency issue in the wireless stack, specifically around regulatory domain handling. It seems that `reg_check_chans_work` – which is called during regulatory domain settings, wifi configuration, join, and scan operations through nl80211 – is the culprit. The vulnerability arises from how it interacts with the RCU mechanism. There's this concurrency bug where unlocking the RCU read lock within the `list_for_each_entry_rcu` loop could lead to lockdep warnings, RCU warnings, or even use-after-free or list corruption if a wiphy is registered or unregistered simultaneously. That's a nasty situation, especially in a part of the kernel exposed to user-space.

The first thing I did was make sure the basics are in place. The obvious dependency here is `CFG80211`, and it looks like `reg_check_chans_work` is unconditionally compiled when that's enabled. Good.

Next, I looked at the symbols directly involved. I found these key functions: `reg_check_chans_work`, `reg_check_channels`, `reg_leave_invalid_chans`, and those scheduling functions like `cfg80211_schedule_channels_check`, `regulatory_hint_indoor`, and `regulatory_set_wiphy_regd_sync`. I double-checked that `reg_check_chans_work` calls `reg_leave_invalid_chans` and that `reg_check_channels` schedules the work. Also, while `reg_check_chans_work` and `reg_leave_invalid_chans` are both static, `reg_check_chans_work` will still show up as a distinct symbol in vmlinux as a work item callback. `reg_check_channels` is non-static.

Given all this, I'm pretty confident that fuzzing this is the right approach. The patch modifies `reg_check_chans_work` within `cfg80211`, and specifically modifies locking and RCU iterations over `cfg80211_rdev_list` by dropping and reacquiring locks inside the loop. This code is triggered from userspace, so concurrency problems are a real risk. The key is to test the RCU list traversal and the safety of concurrent regulatory domain operations.

So, the criteria are clear: `WorthFuzzing: true`, the necessary config is `CFG80211`, and the `FocusSymbols` are `reg_check_chans_work`, `reg_check_channels`, and `reg_leave_invalid_chans`. Time to call `set-results`.



18/2 2026/09/05 01:04 tool set-results
0m Args:
{
  "EnableConfigs": [
    "CFG80211"
  ],
  "FocusSymbols": [
    "reg_check_chans_work",
    "reg_check_channels",
    "reg_leave_invalid_chans"
  ],
  "Reasoning": "The patch changes locking and RCU iteration in reg_check_chans_work() within cfg80211 (net/wireless/reg.c), releasing and re-acquiring rcu_read_lock and rtnl_lock inside list_for_each_entry_rcu. This reachable code path handles regulatory domain channel validation and interface disconnection, which can be triggered via nl80211 regulatory commands. Fuzzing is warranted to test for concurrency bugs, list traversal issues, and RCU/lockdep warnings.",
  "WorthFuzzing": true
}

Results:
{
  "EnableConfigs": [
    "CFG80211"
  ],
  "FocusSymbols": [
    "reg_check_chans_work",
    "reg_check_channels",
    "reg_leave_invalid_chans"
  ],
  "Reasoning": "The patch changes locking and RCU iteration in reg_check_chans_work() within cfg80211 (net/wireless/reg.c), releasing and re-acquiring rcu_read_lock and rtnl_lock inside list_for_each_entry_rcu. This reachable code path handles regulatory domain channel validation and interface disconnection, which can be triggered via nl80211 regulatory commands. Fuzzing is warranted to test for concurrency bugs, list traversal issues, and RCU/lockdep warnings.",
  "WorthFuzzing": true
}

19/1 2026/09/05 01:04 action If
0m Args:
{
  "WorthFuzzing": true
}

Results:
null

20/2 2026/09/05 01:04 agent kmsan-evaluator
0m Model:
core

Args:
null

Results:
{
  "KMSANReasoning": "The patch modifies the locking and RCU list traversal strategy in reg_check_chans_work() (net/wireless/reg.c) by dropping and re-acquiring rcu_read_lock() and rtnl_lock() around each iteration of cfg80211_rdev_list.\n\nThis change does not introduce any memory allocations, does not read or write uninitialized stack/heap fields, does not alter buffer length/bounds calculations, and does not pass kernel data to userspace. Any concurrency, use-after-free, or list corruption issues stemming from dropping RCU during list traversal are detectable by standard debugging tools (KASAN, LOCKDEP, and CONFIG_PROVE_RCU). Therefore, a dedicated KMSAN fuzzing session is not warranted.",
  "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 909bae63e4cb8dbb8c2aea103eddd0caba9adc75
Author: syz-cluster <triage@syzkaller.com>
Date:   Sat Sep 5 01:03:47 2026 +0000

    syz-cluster: applied patch under review

diff --git a/net/wireless/reg.c b/net/wireless/reg.c
index a8336baf85dc6..a2e0d1cf8317c 100644
--- a/net/wireless/reg.c
+++ b/net/wireless/reg.c
@@ -2466,12 +2466,21 @@ static void reg_check_chans_work(struct work_struct *work)
 	struct cfg80211_registered_device *rdev;
 
 	pr_debug("Verifying active interfaces after reg change\n");
-	rtnl_lock();
-
-	for_each_rdev(rdev)
+	/*
+	 * Acquire rtnl per-device instead of holding it for the entire loop;
+	 * cfg80211_leave() can be slow and starve other rtnl waiters otherwise.
+	 * wiphy_unregister() holds rtnl across list_del_rcu() + synchronize_rcu(),
+	 * so rdev cannot be freed while we hold rtnl_lock() below.
+	 */
+	rcu_read_lock();
+	list_for_each_entry_rcu(rdev, &cfg80211_rdev_list, list) {
+		rcu_read_unlock();
+		rtnl_lock();
 		reg_leave_invalid_chans(&rdev->wiphy);
-
-	rtnl_unlock();
+		rtnl_unlock();
+		rcu_read_lock();
+	}
+	rcu_read_unlock();
 }
 
 void reg_check_channels(void)

21/3 2026/09/05 01:04 llm kmsan-evaluator
0m Model:
gemini-3.7-flash

Args:
null

Results:
null

Tokens:
							input: 2271
							output: 31
							thoughts: 995
						

Thoughts:
**KMSAN Evaluation: Patch Review**

Okay, let's break this down. My task is to determine if this patch necessitates a KMSAN fuzzing session, or if standard checks like KASAN and LOCKDEP are sufficient. It's a standard kernel QA decision, nothing too out of the ordinary.

First, I need to understand what this patch actually *does*. It looks like it's a change within `net/wireless/reg.c`, specifically in `reg_check_chans_work`. They're modifying how the code iterates through a list of registered devices (`cfg80211_rdev_list`) and calls `reg_leave_invalid_chans`. The original code held `rtnl_lock()` for the entire loop, but this patch introduces RCU locking around the list iteration, dropping and reacquiring the lock in each loop iteration, and dropping RTNL as well.

Now, the red flag. This RCU list traversal with locking manipulation pattern... that warrants close scrutiny. The use of `list_for_each_entry_rcu` inside the RCU read lock with dropping and re-acquiring the lock within the loop is a classic setup for potential concurrency issues. With the re-entrant locking, and unlocked window for other operations, a use-after-free scenario or list corruption is *highly* plausible. The comment claims `wiphy_unregister()` holds rtnl across `list_del_rcu()` and `synchronize_rcu()`, but even with that claim, the potential for a race with the synchronize_rcu/unregister and the un-locked section of the loop still exists. We could be dealing with a `rdev` that's been freed or had its list entries corrupted between the calls.

However, I need to consider whether it *introduces* new issues. Does this patch change anything that directly interacts with uninitialized memory? No. The code modifies locking and list traversal, but doesn't introduce allocations, copies of uninitialized data to userspace, access uninitialized variables, or struct padding issues. It is possible, but seems unlikely in this case, that an entirely new code-path could introduce such. I will check.

Therefore, since the potential vulnerabilities lie within concurrency issues, KASAN and LOCKDEP would catch use-after-free and locking / concurrency issues, as well as KCSAN. KMSAN is unnecessary for this patch. I'll double-check with a grep or code scan just to be absolutely certain I'm not missing anything that would involve reading from uninitialized memory.



22/3 2026/09/05 01:04 tool grepper
0m Args:
{
  "Expression": "reg_check_chans_work",
  "PathPrefix": "net/wireless"
}

Results:
{
  "Output": "net/wireless/reg.c=221=struct reg_beacon {\n--\nnet/wireless/reg.c-225-\nnet/wireless/reg.c:226:static void reg_check_chans_work(struct work_struct *work);\nnet/wireless/reg.c:227:static DECLARE_DELAYED_WORK(reg_check_chans, reg_check_chans_work);\nnet/wireless/reg.c-228-\n--\nnet/wireless/reg.c=2449=static void reg_leave_invalid_chans(struct wiphy *wiphy)\n--\nnet/wireless/reg.c-2463-\nnet/wireless/reg.c:2464:static void reg_check_chans_work(struct work_struct *work)\nnet/wireless/reg.c-2465-{\n"
}

23/3 2026/09/05 01:04 llm kmsan-evaluator
0m Model:
gemini-3.7-flash

Args:
null

Results:
null

Tokens:
							input: 4064
							output: 36
							thoughts: 24
						

Thoughts:
Here's my take on the thought process, as if it were my own:

**Diving into the Channel Regulation Code**

Okay, time to get my hands dirty. I need to understand how the system handles invalid channels during regulatory domain changes. Let's start by zeroing in on `reg_leave_invalid_chans` within `net/wireless/reg.c`. This function name seems like a good starting point. It's the logical place to see how the kernel deals with channels that are no longer allowed after a regulatory domain update. I expect it'll give me clues about how the driver is notified and how the system might handle ongoing transmissions on these channels. Hopefully, this function provides the key to understanding the specific logic of channel invalidation. I'm keen to dissect the code and see how robust the implementation is.



24/3 2026/09/05 01:04 tool read-file
0m Args:
{
  "File": "net/wireless/reg.c",
  "FirstLine": 2445,
  "LineCount": 45
}

Results:
{
  "Contents": "2445:\t\n2446:\t\treturn true;\n2447:\t}\n2448:\t\n2449:\tstatic void reg_leave_invalid_chans(struct wiphy *wiphy)\n2450:\t{\n2451:\t\tstruct wireless_dev *wdev;\n2452:\t\tstruct cfg80211_registered_device *rdev = wiphy_to_rdev(wiphy);\n2453:\t\n2454:\t\tlist_for_each_entry(wdev, \u0026rdev-\u003ewiphy.wdev_list, list) {\n2455:\t\t\tbool valid;\n2456:\t\n2457:\t\t\tscoped_guard(wiphy, wiphy)\n2458:\t\t\t\tvalid = reg_wdev_chan_valid(wiphy, wdev);\n2459:\t\t\tif (!valid)\n2460:\t\t\t\tcfg80211_leave(rdev, wdev, -1);\n2461:\t\t}\n2462:\t}\n2463:\t\n2464:\tstatic void reg_check_chans_work(struct work_struct *work)\n2465:\t{\n2466:\t\tstruct cfg80211_registered_device *rdev;\n2467:\t\n2468:\t\tpr_debug(\"Verifying active interfaces after reg change\\n\");\n2469:\t\t/*\n2470:\t\t * Acquire rtnl per-device instead of holding it for the entire loop;\n2471:\t\t * cfg80211_leave() can be slow and starve other rtnl waiters otherwise.\n2472:\t\t * wiphy_unregister() holds rtnl across list_del_rcu() + synchronize_rcu(),\n2473:\t\t * so rdev cannot be freed while we hold rtnl_lock() below.\n2474:\t\t */\n2475:\t\trcu_read_lock();\n2476:\t\tlist_for_each_entry_rcu(rdev, \u0026cfg80211_rdev_list, list) {\n2477:\t\t\trcu_read_unlock();\n2478:\t\t\trtnl_lock();\n2479:\t\t\treg_leave_invalid_chans(\u0026rdev-\u003ewiphy);\n2480:\t\t\trtnl_unlock();\n2481:\t\t\trcu_read_lock();\n2482:\t\t}\n2483:\t\trcu_read_unlock();\n2484:\t}\n2485:\t\n2486:\tvoid reg_check_channels(void)\n2487:\t{\n2488:\t\t/*\n2489:\t\t * Give usermode a chance to do something nicer (move to another\n"
}

25/3 2026/09/05 01:04 llm kmsan-evaluator
0m Model:
gemini-3.7-flash

Args:
null

Results:
null

Tokens:
							input: 5003
							output: 190
							thoughts: 473
						

Thoughts:
**KMSAN Assessment of this Patch**

Alright, let's break this down. My initial assessment is that KMSAN isn't needed here. I've walked through the standard KMSAN checks, and nothing screams "potential uninitialized memory read" at me.

Specifically, I looked for:
1.  Kernel structures sent to user space where initialization might be sloppy. Nope.
2.  Conditional logic based on potentially uninitialized data. Not seeing it.
3.  Complex data structure initialization that could lead to uninitialized reads later. Negative.
4.  Bounds check issues that could expose uninitialized buffer bytes. Nada.

The potential issues I *do* see are around concurrency, RCU list iteration, and locking: specifically, things like list iteration validity across RCU unlock/lock boundaries, sleepable locks inside RCU (though it unlocks RCU before locking RTNL), and use-after-free or list corruption if elements are removed during the iteration. However, those are *exactly* the kinds of issues KASAN, LOCKDEP, and the standard kernel debugging tools (like CONFIG_PROVE_RCU and CONFIG_DEBUG_LIST) are designed to catch. That's reassuring.

So, the patch is changing `reg_check_chans_work()` in `net/wireless/reg.c`. It's switching from holding `rtnl_lock()` for the entire `cfg80211_rdev_list` traversal to acquiring it per device, toggling `rcu_read_lock()` / `rtnl_lock()` within the loop. The potential bugs introduced here are related to RCU list traversal safety, use-after-free, or concurrency/locking - which are well-covered by the existing toolchain. No new allocations, stack/heap variables, or info-leaks to user space. No KMSAN required.

I'm confident in calling this. Let's set the results and move on.



26/3 2026/09/05 01:04 tool set-results
0m Args:
{
  "KMSANReasoning": "The patch modifies the locking and RCU list traversal strategy in reg_check_chans_work() (net/wireless/reg.c) by dropping and re-acquiring rcu_read_lock() and rtnl_lock() around each iteration of cfg80211_rdev_list.\n\nThis change does not introduce any memory allocations, does not read or write uninitialized stack/heap fields, does not alter buffer length/bounds calculations, and does not pass kernel data to userspace. Any concurrency, use-after-free, or list corruption issues stemming from dropping RCU during list traversal are detectable by standard debugging tools (KASAN, LOCKDEP, and CONFIG_PROVE_RCU). Therefore, a dedicated KMSAN fuzzing session is not warranted.",
  "NeedsKMSAN": false
}

Results:
{
  "KMSANReasoning": "The patch modifies the locking and RCU list traversal strategy in reg_check_chans_work() (net/wireless/reg.c) by dropping and re-acquiring rcu_read_lock() and rtnl_lock() around each iteration of cfg80211_rdev_list.\n\nThis change does not introduce any memory allocations, does not read or write uninitialized stack/heap fields, does not alter buffer length/bounds calculations, and does not pass kernel data to userspace. Any concurrency, use-after-free, or list corruption issues stemming from dropping RCU during list traversal are detectable by standard debugging tools (KASAN, LOCKDEP, and CONFIG_PROVE_RCU). Therefore, a dedicated KMSAN fuzzing session is not warranted.",
  "NeedsKMSAN": false
}

LLM Calls Summary:
Total Calls Total Tokens Avg Tokens Total Duration (Seconds) Avg Duration (Seconds)
Tool Calls Summary:
Total Calls Total Duration (Seconds) Avg Duration (Seconds)