AI Trajectory


Trajectory: (Expand/Collapse All)
Seq Timestamp Type Name Duration
0/0 2026/08/03 19:03 flow patch-triage
1m Args:
null

Results:
{
  "EnableConfigs": [
    "MAC80211",
    "MAC80211_HWSIM",
    "MAC80211_MESH"
  ],
  "FocusSymbols": [
    "ieee80211_tx_control_port",
    "ieee80211_tdls_prep_mgmt_packet",
    "ieee80211_probe_mesh_link"
  ],
  "Reasoning": "The patch modifies core mac80211 transmission logic, including TX info initialization, header building, and control port transmission. These changes are functional and reachable via virtualized wireless interfaces (mac80211_hwsim). We should focus fuzzing on the modified entry points like `ieee80211_tx_control_port` and `ieee80211_tdls_prep_mgmt_packet`. `MAC80211_MESH` is needed to reach the modified mesh-specific logic in `ieee80211_lookup_ra_sta`.",
  "WorthFuzzing": true
}

1/1 2026/08/03 19:03 action read-patch-diff
0m Args:
null

Results:
{
  "PatchDiff": "commit ed13bd1aac23c04dcc287bf236509fc64e88a005\nAuthor: syz-cluster \u003ctriage@syzkaller.com\u003e\nDate:   Mon Aug 3 19:03:45 2026 +0000\n\n    syz-cluster: applied patch under review\n\ndiff --git a/net/mac80211/ieee80211_i.h b/net/mac80211/ieee80211_i.h\nindex 5761e96214914..f4ac945b55088 100644\n--- a/net/mac80211/ieee80211_i.h\n+++ b/net/mac80211/ieee80211_i.h\n@@ -2233,8 +2233,7 @@ netdev_tx_t ieee80211_subif_start_xmit_8023(struct sk_buff *skb,\n void __ieee80211_subif_start_xmit(struct sk_buff *skb,\n \t\t\t\t  struct net_device *dev,\n \t\t\t\t  u32 info_flags,\n-\t\t\t\t  u32 ctrl_flags,\n-\t\t\t\t  u64 cookie);\n+\t\t\t\t  u32 ctrl_flags);\n struct sk_buff *\n ieee80211_build_data_template(struct ieee80211_sub_if_data *sdata,\n \t\t\t      struct sk_buff *skb, u32 info_flags);\n@@ -2472,11 +2471,6 @@ static inline bool ieee80211_require_encrypted_assoc(__le16 fc,\n \treturn sta \u0026\u0026 sta-\u003esta.epp_peer \u0026\u0026 ieee80211_is_assoc(fc);\n }\n \n-/* sta_out needs to be checked for ERR_PTR() before using */\n-int ieee80211_lookup_ra_sta(struct ieee80211_sub_if_data *sdata,\n-\t\t\t    struct sk_buff *skb,\n-\t\t\t    struct sta_info **sta_out);\n-\n static inline void\n ieee80211_tx_skb_tid_band(struct ieee80211_sub_if_data *sdata,\n \t\t\t  struct sk_buff *skb, int tid,\ndiff --git a/net/mac80211/tdls.c b/net/mac80211/tdls.c\nindex dc2f662fe4c46..4f4cae9fd274c 100644\n--- a/net/mac80211/tdls.c\n+++ b/net/mac80211/tdls.c\n@@ -1121,7 +1121,7 @@ ieee80211_tdls_prep_mgmt_packet(struct wiphy *wiphy, struct net_device *dev,\n \t/* disable bottom halves when entering the Tx path */\n \tlocal_bh_disable();\n \t__ieee80211_subif_start_xmit(skb, dev, flags,\n-\t\t\t\t     IEEE80211_TX_CTRL_MLO_LINK_UNSPEC, 0);\n+\t\t\t\t     IEEE80211_TX_CTRL_MLO_LINK_UNSPEC);\n \tlocal_bh_enable();\n \n \treturn ret;\ndiff --git a/net/mac80211/tx.c b/net/mac80211/tx.c\nindex 3a1e2c9e1565e..911c4b5700d09 100644\n--- a/net/mac80211/tx.c\n+++ b/net/mac80211/tx.c\n@@ -2504,9 +2504,16 @@ static inline bool ieee80211_is_tdls_setup(struct sk_buff *skb)\n \t       skb-\u003edata[14] == WLAN_TDLS_SNAP_RFTYPE;\n }\n \n-int ieee80211_lookup_ra_sta(struct ieee80211_sub_if_data *sdata,\n-\t\t\t    struct sk_buff *skb,\n-\t\t\t    struct sta_info **sta_out)\n+/*\n+ * Returns an error if the frame should be dropped, otherwise\n+ * the *sta_out pointer is filled:\n+ *  - valid sta pointer: frame goes to that station\n+ *  - NULL: frame will be unicast to a yet unknown station\n+ *  - ERR_PTR(-ENOENT): frame will be group addressed\n+ */\n+static int ieee80211_lookup_ra_sta(struct ieee80211_sub_if_data *sdata,\n+\t\t\t\t   struct sk_buff *skb,\n+\t\t\t\t   struct sta_info **sta_out)\n {\n \tstruct sta_info *sta;\n \n@@ -2531,6 +2538,10 @@ int ieee80211_lookup_ra_sta(struct ieee80211_sub_if_data *sdata,\n \t\tbreak;\n #ifdef CONFIG_MAC80211_MESH\n \tcase NL80211_IFTYPE_MESH_POINT:\n+\t\tif (is_multicast_ether_addr(skb-\u003edata)) {\n+\t\t\t*sta_out = ERR_PTR(-ENOENT);\n+\t\t\treturn 0;\n+\t\t}\n \t\t/* determined much later */\n \t\t*sta_out = NULL;\n \t\treturn 0;\n@@ -2573,17 +2584,15 @@ int ieee80211_lookup_ra_sta(struct ieee80211_sub_if_data *sdata,\n \t\treturn -EINVAL;\n \t}\n \n-\t*sta_out = sta ?: ERR_PTR(-ENOENT);\n+\t*sta_out = sta;\n \treturn 0;\n }\n \n-static u16 ieee80211_store_ack_skb(struct ieee80211_local *local,\n-\t\t\t\t   struct sk_buff *skb,\n-\t\t\t\t   u32 *info_flags,\n-\t\t\t\t   u64 cookie)\n+static void ieee80211_store_ack_skb(struct ieee80211_local *local,\n+\t\t\t\t    struct sk_buff *skb, u64 cookie)\n {\n+\tstruct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb);\n \tstruct sk_buff *ack_skb;\n-\tu16 info_id = 0;\n \n \tif (skb-\u003esk)\n \t\tack_skb = skb_clone_sk(skb);\n@@ -2600,58 +2609,41 @@ static u16 ieee80211_store_ack_skb(struct ieee80211_local *local,\n \t\tspin_unlock_irqrestore(\u0026local-\u003eack_status_lock, flags);\n \n \t\tif (id \u003e= 0) {\n-\t\t\tinfo_id = id;\n-\t\t\t*info_flags |= IEEE80211_TX_CTL_REQ_TX_STATUS;\n+\t\t\tinfo-\u003estatus_data = id;\n+\t\t\tinfo-\u003estatus_data_idr = 1;\n+\t\t\tinfo-\u003eflags |= IEEE80211_TX_CTL_REQ_TX_STATUS;\n \t\t\tif (cookie)\n \t\t\t\tIEEE80211_SKB_CB(ack_skb)-\u003eack.cookie = cookie;\n \t\t} else {\n \t\t\tkfree_skb(ack_skb);\n \t\t}\n \t}\n-\n-\treturn info_id;\n-}\n-\n-static void ieee80211_remove_ack_skb(struct ieee80211_local *local, u16 info_id)\n-{\n-\tstruct sk_buff *ack_skb;\n-\tunsigned long flags;\n-\n-\tspin_lock_irqsave(\u0026local-\u003eack_status_lock, flags);\n-\tack_skb = idr_remove(\u0026local-\u003eack_status_frames, info_id);\n-\tspin_unlock_irqrestore(\u0026local-\u003eack_status_lock, flags);\n-\n-\tkfree_skb(ack_skb);\n }\n \n /**\n  * ieee80211_build_hdr - build 802.11 header in the given frame\n  * @sdata: virtual interface to build the header for\n  * @skb: the skb to build the header in\n- * @info_flags: skb flags to set\n  * @sta: the station pointer\n- * @ctrl_flags: info control flags to set\n- * @cookie: cookie pointer to fill (if not %NULL)\n  *\n  * This function takes the skb with 802.3 header and reformats the header to\n  * the appropriate IEEE 802.11 header based on which interface the packet is\n  * being transmitted on.\n  *\n- * Note that this function also takes care of the TX status request and\n- * potential unsharing of the SKB - this needs to be interleaved with the\n- * header building.\n+ * Note that this function also takes care of the TX status request. The skb\n+ * must not be shared, and its TX info must already be initialised - this\n+ * function only fills in what it determines itself.\n  *\n  * The function requires the read-side RCU lock held\n  *\n  * Returns: the (possibly reallocated) skb or an ERR_PTR() code\n  */\n static struct sk_buff *ieee80211_build_hdr(struct ieee80211_sub_if_data *sdata,\n-\t\t\t\t\t   struct sk_buff *skb, u32 info_flags,\n-\t\t\t\t\t   struct sta_info *sta, u32 ctrl_flags,\n-\t\t\t\t\t   u64 cookie)\n+\t\t\t\t\t   struct sk_buff *skb,\n+\t\t\t\t\t   struct sta_info *sta)\n {\n+\tstruct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb);\n \tstruct ieee80211_local *local = sdata-\u003elocal;\n-\tstruct ieee80211_tx_info *info;\n \tint head_need;\n \tu16 ethertype, hdrlen,  meshhdrlen = 0;\n \t__le16 fc;\n@@ -2663,18 +2655,18 @@ static struct sk_buff *ieee80211_build_hdr(struct ieee80211_sub_if_data *sdata,\n \tbool wme_sta = false, authorized = false;\n \tbool tdls_peer;\n \tbool multicast;\n-\tu16 info_id = 0;\n \tstruct ieee80211_chanctx_conf *chanctx_conf = NULL;\n \tenum nl80211_band band;\n \tint ret;\n-\tu8 link_id = u32_get_bits(ctrl_flags, IEEE80211_TX_CTRL_MLO_LINK);\n+\tu8 link_id = u32_get_bits(info-\u003econtrol.flags,\n+\t\t\t\t  IEEE80211_TX_CTRL_MLO_LINK);\n \n \tif (IS_ERR(sta))\n \t\tsta = NULL;\n \n #ifdef CONFIG_MAC80211_DEBUGFS\n \tif (local-\u003eforce_tx_status)\n-\t\tinfo_flags |= IEEE80211_TX_CTL_REQ_TX_STATUS;\n+\t\tinfo-\u003eflags |= IEEE80211_TX_CTL_REQ_TX_STATUS;\n #endif\n \n \t/* convert Ethernet header to proper 802.11 header (based on\n@@ -2815,7 +2807,7 @@ static struct sk_buff *ieee80211_build_hdr(struct ieee80211_sub_if_data *sdata,\n \t\t/* For injected frames, fill RA right away as nexthop lookup\n \t\t * will be skipped.\n \t\t */\n-\t\tif ((ctrl_flags \u0026 IEEE80211_TX_CTRL_SKIP_MPATH_LOOKUP) \u0026\u0026\n+\t\tif ((info-\u003econtrol.flags \u0026 IEEE80211_TX_CTRL_SKIP_MPATH_LOOKUP) \u0026\u0026\n \t\t    is_zero_ether_addr(hdr.addr1))\n \t\t\tmemcpy(hdr.addr1, skb-\u003edata, ETH_ALEN);\n \t\tbreak;\n@@ -2944,21 +2936,6 @@ static struct sk_buff *ieee80211_build_hdr(struct ieee80211_sub_if_data *sdata,\n \t\tgoto free;\n \t}\n \n-\tif (unlikely(!multicast \u0026\u0026\n-\t\t     (sk_requests_wifi_status(skb-\u003esk) ||\n-\t\t      ctrl_flags \u0026 IEEE80211_TX_CTL_REQ_TX_STATUS)))\n-\t\tinfo_id = ieee80211_store_ack_skb(local, skb, \u0026info_flags,\n-\t\t\t\t\t\t  cookie);\n-\n-\t/*\n-\t * If the skb is shared we need to obtain our own copy.\n-\t */\n-\tskb = skb_share_check(skb, GFP_ATOMIC);\n-\tif (unlikely(!skb)) {\n-\t\tret = -ENOMEM;\n-\t\tgoto free;\n-\t}\n-\n \thdr.frame_control = fc;\n \thdr.duration_id = 0;\n \thdr.seq_ctrl = 0;\n@@ -2997,8 +2974,6 @@ static struct sk_buff *ieee80211_build_hdr(struct ieee80211_sub_if_data *sdata,\n \t\thead_need += local-\u003etx_headroom;\n \t\thead_need = max_t(int, 0, head_need);\n \t\tif (ieee80211_skb_resize(sdata, skb, head_need, ENCRYPT_DATA)) {\n-\t\t\tieee80211_free_txskb(\u0026local-\u003ehw, skb);\n-\t\t\tskb = NULL;\n \t\t\tret = -ENOMEM;\n \t\t\tgoto free;\n \t\t}\n@@ -3027,50 +3002,14 @@ static struct sk_buff *ieee80211_build_hdr(struct ieee80211_sub_if_data *sdata,\n \n \tskb_reset_mac_header(skb);\n \n-\tinfo = IEEE80211_SKB_CB(skb);\n-\tmemset(info, 0, sizeof(*info));\n-\n-\tinfo-\u003eflags = info_flags;\n-\tif (info_id) {\n-\t\tinfo-\u003estatus_data = info_id;\n-\t\tinfo-\u003estatus_data_idr = 1;\n-\t}\n \tinfo-\u003eband = band;\n \n-\tif (likely(!cookie)) {\n-\t\tctrl_flags |= u32_encode_bits(link_id,\n-\t\t\t\t\t      IEEE80211_TX_CTRL_MLO_LINK);\n-\t} else {\n-\t\tunsigned int pre_conf_link_id;\n-\n-\t\t/*\n-\t\t * ctrl_flags already have been set by\n-\t\t * ieee80211_tx_control_port(), here\n-\t\t * we just sanity check that\n-\t\t */\n-\n-\t\tpre_conf_link_id = u32_get_bits(ctrl_flags,\n-\t\t\t\t\t\tIEEE80211_TX_CTRL_MLO_LINK);\n-\n-\t\tif (pre_conf_link_id != link_id \u0026\u0026\n-\t\t    link_id != IEEE80211_LINK_UNSPECIFIED) {\n-#ifdef CONFIG_MAC80211_VERBOSE_DEBUG\n-\t\t\tnet_info_ratelimited(\"%s: dropped frame to %pM with bad link ID request (%d vs. %d)\\n\",\n-\t\t\t\t\t     sdata-\u003ename, hdr.addr1,\n-\t\t\t\t\t     pre_conf_link_id, link_id);\n-#endif\n-\t\t\tret = -EINVAL;\n-\t\t\tgoto free;\n-\t\t}\n-\t}\n-\n-\tinfo-\u003econtrol.flags = ctrl_flags;\n-\n+\tinfo-\u003econtrol.flags =\n+\t\tu32_replace_bits(info-\u003econtrol.flags, link_id,\n+\t\t\t\t IEEE80211_TX_CTRL_MLO_LINK);\n \treturn skb;\n  free:\n-\tif (info_id)\n-\t\tieee80211_remove_ack_skb(local, info_id);\n-\tkfree_skb(skb);\n+\tieee80211_free_txskb(\u0026local-\u003ehw, skb);\n \treturn ERR_PTR(ret);\n }\n \n@@ -4368,13 +4307,14 @@ EXPORT_SYMBOL(ieee80211_txq_schedule_start);\n void __ieee80211_subif_start_xmit(struct sk_buff *skb,\n \t\t\t\t  struct net_device *dev,\n \t\t\t\t  u32 info_flags,\n-\t\t\t\t  u32 ctrl_flags,\n-\t\t\t\t  u64 cookie)\n+\t\t\t\t  u32 ctrl_flags)\n {\n \tstruct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev);\n \tstruct ieee80211_local *local = sdata-\u003elocal;\n+\tstruct ieee80211_tx_info *info;\n \tstruct sta_info *sta;\n \tstruct sk_buff *next;\n+\tbool group_addressed;\n \tint len = skb-\u003elen;\n \n \tif (unlikely(!ieee80211_sdata_running(sdata) || skb-\u003elen \u003c ETH_HLEN)) {\n@@ -4394,6 +4334,7 @@ void __ieee80211_subif_start_xmit(struct sk_buff *skb,\n \tif (ieee80211_lookup_ra_sta(sdata, skb, \u0026sta))\n \t\tgoto out_free;\n \n+\tgroup_addressed = IS_ERR(sta);\n \tif (IS_ERR(sta))\n \t\tsta = NULL;\n \n@@ -4426,8 +4367,22 @@ void __ieee80211_subif_start_xmit(struct sk_buff *skb,\n \t\tif (skb-\u003eprotocol == sdata-\u003econtrol_port_protocol)\n \t\t\tctrl_flags |= IEEE80211_TX_CTRL_SKIP_MPATH_LOOKUP;\n \n-\t\tskb = ieee80211_build_hdr(sdata, skb, info_flags,\n-\t\t\t\t\t  sta, ctrl_flags, cookie);\n+\t\tskb = skb_share_check(skb, GFP_ATOMIC);\n+\t\tif (unlikely(!skb)) {\n+\t\t\tkfree_skb_list(next);\n+\t\t\tgoto out;\n+\t\t}\n+\n+\t\tinfo = IEEE80211_SKB_CB(skb);\n+\t\tmemset(info, 0, sizeof(*info));\n+\t\tinfo-\u003eflags = info_flags;\n+\t\tinfo-\u003econtrol.flags = ctrl_flags;\n+\n+\t\tif (unlikely(!group_addressed \u0026\u0026\n+\t\t\t     sk_requests_wifi_status(skb-\u003esk)))\n+\t\t\tieee80211_store_ack_skb(local, skb, 0);\n+\n+\t\tskb = ieee80211_build_hdr(sdata, skb, sta);\n \t\tif (IS_ERR(skb)) {\n \t\t\tkfree_skb_list(next);\n \t\t\tgoto out;\n@@ -4564,7 +4519,7 @@ static void ieee80211_mlo_multicast_tx_one(struct ieee80211_sub_if_data *sdata,\n \t\treturn;\n \n \tctrl_flags |= u32_encode_bits(link_id, IEEE80211_TX_CTRL_MLO_LINK);\n-\t__ieee80211_subif_start_xmit(out, sdata-\u003edev, 0, ctrl_flags, 0);\n+\t__ieee80211_subif_start_xmit(out, sdata-\u003edev, 0, ctrl_flags);\n }\n \n static void ieee80211_mlo_multicast_tx(struct net_device *dev,\n@@ -4579,7 +4534,7 @@ static void ieee80211_mlo_multicast_tx(struct net_device *dev,\n \t\tctrl_flags |= u32_encode_bits(__ffs(links),\n \t\t\t\t\t      IEEE80211_TX_CTRL_MLO_LINK);\n \n-\t\t__ieee80211_subif_start_xmit(skb, sdata-\u003edev, 0, ctrl_flags, 0);\n+\t\t__ieee80211_subif_start_xmit(skb, sdata-\u003edev, 0, ctrl_flags);\n \t\treturn;\n \t}\n \n@@ -4620,8 +4575,7 @@ netdev_tx_t ieee80211_subif_start_xmit(struct sk_buff *skb,\n \t\tieee80211_convert_to_unicast(skb, dev, \u0026queue);\n \t\twhile ((skb = __skb_dequeue(\u0026queue)))\n \t\t\t__ieee80211_subif_start_xmit(skb, dev, 0,\n-\t\t\t\t\t\t     IEEE80211_TX_CTRL_MLO_LINK_UNSPEC,\n-\t\t\t\t\t\t     0);\n+\t\t\t\t\t\t     IEEE80211_TX_CTRL_MLO_LINK_UNSPEC);\n \t} else if (ieee80211_vif_is_mld(\u0026sdata-\u003evif) \u0026\u0026\n \t\t   ((sdata-\u003evif.type == NL80211_IFTYPE_AP \u0026\u0026\n \t\t     !ieee80211_hw_check(\u0026sdata-\u003elocal-\u003ehw, MLO_MCAST_MULTI_LINK_TX)) ||\n@@ -4631,8 +4585,7 @@ netdev_tx_t ieee80211_subif_start_xmit(struct sk_buff *skb,\n \t} else {\n normal:\n \t\t__ieee80211_subif_start_xmit(skb, dev, 0,\n-\t\t\t\t\t     IEEE80211_TX_CTRL_MLO_LINK_UNSPEC,\n-\t\t\t\t\t     0);\n+\t\t\t\t\t     IEEE80211_TX_CTRL_MLO_LINK_UNSPEC);\n \t}\n \n \treturn NETDEV_TX_OK;\n@@ -4730,8 +4683,7 @@ static void ieee80211_8023_xmit(struct ieee80211_sub_if_data *sdata,\n \t\tif (!test_bit(HT_AGG_STATE_OPERATIONAL, \u0026tid_tx-\u003estate)) {\n \t\t\t/* fall back to non-offload slow path */\n \t\t\t__ieee80211_subif_start_xmit(skb, dev, 0,\n-\t\t\t\t\t\t     IEEE80211_TX_CTRL_MLO_LINK_UNSPEC,\n-\t\t\t\t\t\t     0);\n+\t\t\t\t\t\t     IEEE80211_TX_CTRL_MLO_LINK_UNSPEC);\n \t\t\treturn;\n \t\t}\n \n@@ -4765,12 +4717,8 @@ static void ieee80211_8023_xmit(struct ieee80211_sub_if_data *sdata,\n \t\t\tmemcpy(IEEE80211_SKB_CB(seg), info, sizeof(*info));\n \t}\n \n-\tif (unlikely(sk_requests_wifi_status(skb-\u003esk))) {\n-\t\tinfo-\u003estatus_data = ieee80211_store_ack_skb(local, skb,\n-\t\t\t\t\t\t\t    \u0026info-\u003eflags, 0);\n-\t\tif (info-\u003estatus_data)\n-\t\t\tinfo-\u003estatus_data_idr = 1;\n-\t}\n+\tif (unlikely(sk_requests_wifi_status(skb-\u003esk)))\n+\t\tieee80211_store_ack_skb(local, skb, 0);\n \n \tdev_sw_netstats_tx_add(dev, skbs, len);\n \n@@ -4899,6 +4847,7 @@ ieee80211_build_data_template(struct ieee80211_sub_if_data *sdata,\n \t\t.local = sdata-\u003elocal,\n \t\t.sdata = sdata,\n \t};\n+\tstruct ieee80211_tx_info *info;\n \tstruct sta_info *sta;\n \n \trcu_read_lock();\n@@ -4909,8 +4858,12 @@ ieee80211_build_data_template(struct ieee80211_sub_if_data *sdata,\n \t\tgoto out;\n \t}\n \n-\tskb = ieee80211_build_hdr(sdata, skb, info_flags, sta,\n-\t\t\t\t  IEEE80211_TX_CTRL_MLO_LINK_UNSPEC, 0);\n+\tinfo = IEEE80211_SKB_CB(skb);\n+\tmemset(info, 0, sizeof(*info));\n+\tinfo-\u003eflags = info_flags;\n+\tinfo-\u003econtrol.flags = IEEE80211_TX_CTRL_MLO_LINK_UNSPEC;\n+\n+\tskb = ieee80211_build_hdr(sdata, skb, sta);\n \tif (IS_ERR(skb))\n \t\tgoto out;\n \n@@ -6530,6 +6483,8 @@ int ieee80211_tx_control_port(struct wiphy *wiphy, struct net_device *dev,\n {\n \tstruct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev);\n \tstruct ieee80211_local *local = sdata-\u003elocal;\n+\tstruct ieee80211_tx_info *info;\n+\tbool group_addressed;\n \tstruct sta_info *sta;\n \tstruct sk_buff *skb;\n \tstruct ethhdr *ehdr;\n@@ -6554,9 +6509,6 @@ int ieee80211_tx_control_port(struct wiphy *wiphy, struct net_device *dev,\n \tif (unencrypted)\n \t\tflags |= IEEE80211_TX_INTFL_DONT_ENCRYPT;\n \n-\tif (cookie)\n-\t\tctrl_flags |= IEEE80211_TX_CTL_REQ_TX_STATUS;\n-\n \tflags |= IEEE80211_TX_INTFL_NL80211_FRAME_TX;\n \n \tskb = dev_alloc_skb(local-\u003ehw.extra_tx_headroom +\n@@ -6573,15 +6525,11 @@ int ieee80211_tx_control_port(struct wiphy *wiphy, struct net_device *dev,\n \n \t/* we may override the SA for MLO STA later */\n \tif (link_id \u003c 0) {\n-\t\tctrl_flags |= u32_encode_bits(IEEE80211_LINK_UNSPECIFIED,\n-\t\t\t\t\t      IEEE80211_TX_CTRL_MLO_LINK);\n+\t\tlink_id = IEEE80211_LINK_UNSPECIFIED;\n \t\tmemcpy(ehdr-\u003eh_source, sdata-\u003evif.addr, ETH_ALEN);\n \t} else {\n \t\tstruct ieee80211_bss_conf *link_conf;\n \n-\t\tctrl_flags |= u32_encode_bits(link_id,\n-\t\t\t\t\t      IEEE80211_TX_CTRL_MLO_LINK);\n-\n \t\trcu_read_lock();\n \t\tlink_conf = rcu_dereference(sdata-\u003evif.link_conf[link_id]);\n \t\tif (!link_conf) {\n@@ -6600,9 +6548,6 @@ int ieee80211_tx_control_port(struct wiphy *wiphy, struct net_device *dev,\n \tskb_reset_network_header(skb);\n \tskb_reset_mac_header(skb);\n \n-\tif (local-\u003ehw.queues \u003c IEEE80211_NUM_ACS)\n-\t\tgoto start_xmit;\n-\n \t/* update QoS header to prioritize control port frames if possible,\n \t * prioritization also happens for control port frames send over\n \t * AF_PACKET\n@@ -6615,24 +6560,48 @@ int ieee80211_tx_control_port(struct wiphy *wiphy, struct net_device *dev,\n \t\treturn err;\n \t}\n \n-\tif (!IS_ERR(sta)) {\n-\t\tu16 queue = ieee80211_select_queue(sdata, sta, skb);\n+\tgroup_addressed = IS_ERR(sta);\n+\tif (IS_ERR(sta))\n+\t\tsta = NULL;\n \n-\t\tskb_set_queue_mapping(skb, queue);\n+\tskb_set_queue_mapping(skb, ieee80211_select_queue(sdata, sta, skb));\n \n-\t\t/*\n-\t\t * for MLO STA, the SA should be the AP MLD address, but\n-\t\t * the link ID has been selected already\n-\t\t */\n-\t\tif (sta \u0026\u0026 sta-\u003esta.mlo)\n-\t\t\tmemcpy(ehdr-\u003eh_source, sdata-\u003evif.addr, ETH_ALEN);\n+\t/*\n+\t * for MLO STA, the SA should be the AP MLD address, but\n+\t * the link ID has been selected already\n+\t */\n+\tif (sta \u0026\u0026 sta-\u003esta.mlo)\n+\t\tmemcpy(ehdr-\u003eh_source, sdata-\u003evif.addr, ETH_ALEN);\n+\n+\tinfo = IEEE80211_SKB_CB(skb);\n+\tmemset(info, 0, sizeof(*info));\n+\tinfo-\u003eflags = flags;\n+\tctrl_flags |= u32_encode_bits(link_id, IEEE80211_TX_CTRL_MLO_LINK);\n+\tinfo-\u003econtrol.flags = ctrl_flags;\n+\n+\tif (!group_addressed)\n+\t\tieee80211_store_ack_skb(local, skb, cookie);\n+\n+\tskb = ieee80211_build_hdr(sdata, skb, sta);\n+\tif (IS_ERR(skb)) {\n+\t\trcu_read_unlock();\n+\t\treturn PTR_ERR(skb);\n \t}\n-\trcu_read_unlock();\n \n-start_xmit:\n+\tif (link_id != u32_get_bits(info-\u003econtrol.flags,\n+\t\t\t\t    IEEE80211_TX_CTRL_MLO_LINK)) {\n+\t\tieee80211_free_txskb(\u0026local-\u003ehw, skb);\n+\t\trcu_read_unlock();\n+\t\treturn -EINVAL;\n+\t}\n+\n+\tdev_sw_netstats_tx_add(dev, 1, skb-\u003elen);\n+\tieee80211_tpt_led_trig_tx(local, skb-\u003elen);\n+\n \tlocal_bh_disable();\n-\t__ieee80211_subif_start_xmit(skb, skb-\u003edev, flags, ctrl_flags, cookie);\n+\tieee80211_xmit(sdata, sta, skb);\n \tlocal_bh_enable();\n+\trcu_read_unlock();\n \n \treturn 0;\n }\n@@ -6660,8 +6629,7 @@ int ieee80211_probe_mesh_link(struct wiphy *wiphy, struct net_device *dev,\n \n \tlocal_bh_disable();\n \t__ieee80211_subif_start_xmit(skb, skb-\u003edev, 0,\n-\t\t\t\t     IEEE80211_TX_CTRL_SKIP_MPATH_LOOKUP,\n-\t\t\t\t     0);\n+\t\t\t\t     IEEE80211_TX_CTRL_SKIP_MPATH_LOOKUP);\n \tlocal_bh_enable();\n \n \treturn 0;\n"
}

2/1 2026/08/03 19:03 agent patch-evaluator
1m Model:
best-expensive

Args:
null

Results:
{
  "EnableConfigs": [
    "MAC80211",
    "MAC80211_HWSIM",
    "MAC80211_MESH"
  ],
  "FocusSymbols": [
    "ieee80211_tx_control_port",
    "ieee80211_tdls_prep_mgmt_packet",
    "ieee80211_probe_mesh_link"
  ],
  "Reasoning": "The patch modifies core mac80211 transmission logic, including TX info initialization, header building, and control port transmission. These changes are functional and reachable via virtualized wireless interfaces (mac80211_hwsim). We should focus fuzzing on the modified entry points like `ieee80211_tx_control_port` and `ieee80211_tdls_prep_mgmt_packet`. `MAC80211_MESH` is needed to reach the modified mesh-specific logic in `ieee80211_lookup_ra_sta`.",
  "WorthFuzzing": true
}

Instruction:
You are an expert Linux kernel maintainer.
Your job is to review a provided patch series and determine
if it makes functional changes to the kernel that should be fuzzed.

IMPORTANT: The changes have ALREADY been applied and committed as the HEAD commit in
your workspace. Do NOT rely on your internal knowledge of the kernel. You must actively
use your code access tools to examine the actual source code and confirm any assumptions.

Return WorthFuzzing=false if the patch only contains:
- Modifications to Documentation/, Kconfig files, or code comments.
- Purely decorative changes, such as logging (e.g., pr_err, printk) or tracepoints.
- Changes to numeric constants or macros that do not functionally alter execution flow.
- Code paths that are impossible to reach in virtualized environments like GCE or QEMU,
  even when utilizing software-emulated hardware (e.g., usb gadget, mac80211_hwsim).
- Code in vendor-specific PCIe switch, SmartNIC, or GPU drivers (e.g., mlxsw, pds_core, qed,
  ionic, amdgpu) that require physical PCIe hardware cards not emulated in standard QEMU.
- Driver .remove, .shutdown, or pci_unregister_driver teardown callbacks (e.g., igb_remove)
  that are executed only during PCI hot-unplug or sysfs driver unbind operations.

If it modifies reachable core kernel logic, drivers, or architectures, use your code search
tools to verify the code can be executed, then return WorthFuzzing=true.

When returning WorthFuzzing=true, you MUST ALSO:
1. Extract any specific kernel functions that should be heavily fuzzed into FocusSymbols.
   Avoid listing generic hot-path functions to prevent skewed test distributions.
   Prefer non-static, non-inlined API entrypoint functions over internal static helper functions
   (which are inlined by the compiler and do not have distinct symbol addresses).
2. Identify any specific CONFIG_ options required to properly test this new/modified feature.
   Go and look into the Kconfig files and check for ifdefs around the code, do not make assumptions.
   Also check "depends on" lines in Kconfig to include any non-standard parent subsystem configs
   needed for Kbuild to compile the code statically into vmlinux. List them in the EnableConfigs
   output array, and DO NOT add a 'CONFIG_' prefix (e.g., return "NET_IPV4" instead of "CONFIG_NET_IPV4").
Prefer calling several tools at the same time to save round-trips.


Use set-results tool to provide results of the analysis.
It must be called exactly once before the final reply.
Ignore results of this tool.

Prompt:
For your convenience, here is the diff of the changes:
commit ed13bd1aac23c04dcc287bf236509fc64e88a005
Author: syz-cluster <triage@syzkaller.com>
Date:   Mon Aug 3 19:03:45 2026 +0000

    syz-cluster: applied patch under review

diff --git a/net/mac80211/ieee80211_i.h b/net/mac80211/ieee80211_i.h
index 5761e96214914..f4ac945b55088 100644
--- a/net/mac80211/ieee80211_i.h
+++ b/net/mac80211/ieee80211_i.h
@@ -2233,8 +2233,7 @@ netdev_tx_t ieee80211_subif_start_xmit_8023(struct sk_buff *skb,
 void __ieee80211_subif_start_xmit(struct sk_buff *skb,
 				  struct net_device *dev,
 				  u32 info_flags,
-				  u32 ctrl_flags,
-				  u64 cookie);
+				  u32 ctrl_flags);
 struct sk_buff *
 ieee80211_build_data_template(struct ieee80211_sub_if_data *sdata,
 			      struct sk_buff *skb, u32 info_flags);
@@ -2472,11 +2471,6 @@ static inline bool ieee80211_require_encrypted_assoc(__le16 fc,
 	return sta && sta->sta.epp_peer && ieee80211_is_assoc(fc);
 }
 
-/* sta_out needs to be checked for ERR_PTR() before using */
-int ieee80211_lookup_ra_sta(struct ieee80211_sub_if_data *sdata,
-			    struct sk_buff *skb,
-			    struct sta_info **sta_out);
-
 static inline void
 ieee80211_tx_skb_tid_band(struct ieee80211_sub_if_data *sdata,
 			  struct sk_buff *skb, int tid,
diff --git a/net/mac80211/tdls.c b/net/mac80211/tdls.c
index dc2f662fe4c46..4f4cae9fd274c 100644
--- a/net/mac80211/tdls.c
+++ b/net/mac80211/tdls.c
@@ -1121,7 +1121,7 @@ ieee80211_tdls_prep_mgmt_packet(struct wiphy *wiphy, struct net_device *dev,
 	/* disable bottom halves when entering the Tx path */
 	local_bh_disable();
 	__ieee80211_subif_start_xmit(skb, dev, flags,
-				     IEEE80211_TX_CTRL_MLO_LINK_UNSPEC, 0);
+				     IEEE80211_TX_CTRL_MLO_LINK_UNSPEC);
 	local_bh_enable();
 
 	return ret;
diff --git a/net/mac80211/tx.c b/net/mac80211/tx.c
index 3a1e2c9e1565e..911c4b5700d09 100644
--- a/net/mac80211/tx.c
+++ b/net/mac80211/tx.c
@@ -2504,9 +2504,16 @@ static inline bool ieee80211_is_tdls_setup(struct sk_buff *skb)
 	       skb->data[14] == WLAN_TDLS_SNAP_RFTYPE;
 }
 
-int ieee80211_lookup_ra_sta(struct ieee80211_sub_if_data *sdata,
-			    struct sk_buff *skb,
-			    struct sta_info **sta_out)
+/*
+ * Returns an error if the frame should be dropped, otherwise
+ * the *sta_out pointer is filled:
+ *  - valid sta pointer: frame goes to that station
+ *  - NULL: frame will be unicast to a yet unknown station
+ *  - ERR_PTR(-ENOENT): frame will be group addressed
+ */
+static int ieee80211_lookup_ra_sta(struct ieee80211_sub_if_data *sdata,
+				   struct sk_buff *skb,
+				   struct sta_info **sta_out)
 {
 	struct sta_info *sta;
 
@@ -2531,6 +2538,10 @@ int ieee80211_lookup_ra_sta(struct ieee80211_sub_if_data *sdata,
 		break;
 #ifdef CONFIG_MAC80211_MESH
 	case NL80211_IFTYPE_MESH_POINT:
+		if (is_multicast_ether_addr(skb->data)) {
+			*sta_out = ERR_PTR(-ENOENT);
+			return 0;
+		}
 		/* determined much later */
 		*sta_out = NULL;
 		return 0;
@@ -2573,17 +2584,15 @@ int ieee80211_lookup_ra_sta(struct ieee80211_sub_if_data *sdata,
 		return -EINVAL;
 	}
 
-	*sta_out = sta ?: ERR_PTR(-ENOENT);
+	*sta_out = sta;
 	return 0;
 }
 
-static u16 ieee80211_store_ack_skb(struct ieee80211_local *local,
-				   struct sk_buff *skb,
-				   u32 *info_flags,
-				   u64 cookie)
+static void ieee80211_store_ack_skb(struct ieee80211_local *local,
+				    struct sk_buff *skb, u64 cookie)
 {
+	struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb);
 	struct sk_buff *ack_skb;
-	u16 info_id = 0;
 
 	if (skb->sk)
 		ack_skb = skb_clone_sk(skb);
@@ -2600,58 +2609,41 @@ static u16 ieee80211_store_ack_skb(struct ieee80211_local *local,
 		spin_unlock_irqrestore(&local->ack_status_lock, flags);
 
 		if (id >= 0) {
-			info_id = id;
-			*info_flags |= IEEE80211_TX_CTL_REQ_TX_STATUS;
+			info->status_data = id;
+			info->status_data_idr = 1;
+			info->flags |= IEEE80211_TX_CTL_REQ_TX_STATUS;
 			if (cookie)
 				IEEE80211_SKB_CB(ack_skb)->ack.cookie = cookie;
 		} else {
 			kfree_skb(ack_skb);
 		}
 	}
-
-	return info_id;
-}
-
-static void ieee80211_remove_ack_skb(struct ieee80211_local *local, u16 info_id)
-{
-	struct sk_buff *ack_skb;
-	unsigned long flags;
-
-	spin_lock_irqsave(&local->ack_status_lock, flags);
-	ack_skb = idr_remove(&local->ack_status_frames, info_id);
-	spin_unlock_irqrestore(&local->ack_status_lock, flags);
-
-	kfree_skb(ack_skb);
 }
 
 /**
  * ieee80211_build_hdr - build 802.11 header in the given frame
  * @sdata: virtual interface to build the header for
  * @skb: the skb to build the header in
- * @info_flags: skb flags to set
  * @sta: the station pointer
- * @ctrl_flags: info control flags to set
- * @cookie: cookie pointer to fill (if not %NULL)
  *
  * This function takes the skb with 802.3 header and reformats the header to
  * the appropriate IEEE 802.11 header based on which interface the packet is
  * being transmitted on.
  *
- * Note that this function also takes care of the TX status request and
- * potential unsharing of the SKB - this needs to be interleaved with the
- * header building.
+ * Note that this function also takes care of the TX status request. The skb
+ * must not be shared, and its TX info must already be initialised - this
+ * function only fills in what it determines itself.
  *
  * The function requires the read-side RCU lock held
  *
  * Returns: the (possibly reallocated) skb or an ERR_PTR() code
  */
 static struct sk_buff *ieee80211_build_hdr(struct ieee80211_sub_if_data *sdata,
-					   struct sk_buff *skb, u32 info_flags,
-					   struct sta_info *sta, u32 ctrl_flags,
-					   u64 cookie)
+					   struct sk_buff *skb,
+					   struct sta_info *sta)
 {
+	struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb);
 	struct ieee80211_local *local = sdata->local;
-	struct ieee80211_tx_info *info;
 	int head_need;
 	u16 ethertype, hdrlen,  meshhdrlen = 0;
 	__le16 fc;
@@ -2663,18 +2655,18 @@ static struct sk_buff *ieee80211_build_hdr(struct ieee80211_sub_if_data *sdata,
 	bool wme_sta = false, authorized = false;
 	bool tdls_peer;
 	bool multicast;
-	u16 info_id = 0;
 	struct ieee80211_chanctx_conf *chanctx_conf = NULL;
 	enum nl80211_band band;
 	int ret;
-	u8 link_id = u32_get_bits(ctrl_flags, IEEE80211_TX_CTRL_MLO_LINK);
+	u8 link_id = u32_get_bits(info->control.flags,
+				  IEEE80211_TX_CTRL_MLO_LINK);
 
 	if (IS_ERR(sta))
 		sta = NULL;
 
 #ifdef CONFIG_MAC80211_DEBUGFS
 	if (local->force_tx_status)
-		info_flags |= IEEE80211_TX_CTL_REQ_TX_STATUS;
+		info->flags |= IEEE80211_TX_CTL_REQ_TX_STATUS;
 #endif
 
 	/* convert Ethernet header to proper 802.11 header (based on
@@ -2815,7 +2807,7 @@ static struct sk_buff *ieee80211_build_hdr(struct ieee80211_sub_if_data *sdata,
 		/* For injected frames, fill RA right away as nexthop lookup
 		 * will be skipped.
 		 */
-		if ((ctrl_flags & IEEE80211_TX_CTRL_SKIP_MPATH_LOOKUP) &&
+		if ((info->control.flags & IEEE80211_TX_CTRL_SKIP_MPATH_LOOKUP) &&
 		    is_zero_ether_addr(hdr.addr1))
 			memcpy(hdr.addr1, skb->data, ETH_ALEN);
 		break;
@@ -2944,21 +2936,6 @@ static struct sk_buff *ieee80211_build_hdr(struct ieee80211_sub_if_data *sdata,
 		goto free;
 	}
 
-	if (unlikely(!multicast &&
-		     (sk_requests_wifi_status(skb->sk) ||
-		      ctrl_flags & IEEE80211_TX_CTL_REQ_TX_STATUS)))
-		info_id = ieee80211_store_ack_skb(local, skb, &info_flags,
-						  cookie);
-
-	/*
-	 * If the skb is shared we need to obtain our own copy.
-	 */
-	skb = skb_share_check(skb, GFP_ATOMIC);
-	if (unlikely(!skb)) {
-		ret = -ENOMEM;
-		goto free;
-	}
-
 	hdr.frame_control = fc;
 	hdr.duration_id = 0;
 	hdr.seq_ctrl = 0;
@@ -2997,8 +2974,6 @@ static struct sk_buff *ieee80211_build_hdr(struct ieee80211_sub_if_data *sdata,
 		head_need += local->tx_headroom;
 		head_need = max_t(int, 0, head_need);
 		if (ieee80211_skb_resize(sdata, skb, head_need, ENCRYPT_DATA)) {
-			ieee80211_free_txskb(&local->hw, skb);
-			skb = NULL;
 			ret = -ENOMEM;
 			goto free;
 		}
@@ -3027,50 +3002,14 @@ static struct sk_buff *ieee80211_build_hdr(struct ieee80211_sub_if_data *sdata,
 
 	skb_reset_mac_header(skb);
 
-	info = IEEE80211_SKB_CB(skb);
-	memset(info, 0, sizeof(*info));
-
-	info->flags = info_flags;
-	if (info_id) {
-		info->status_data = info_id;
-		info->status_data_idr = 1;
-	}
 	info->band = band;
 
-	if (likely(!cookie)) {
-		ctrl_flags |= u32_encode_bits(link_id,
-					      IEEE80211_TX_CTRL_MLO_LINK);
-	} else {
-		unsigned int pre_conf_link_id;
-
-		/*
-		 * ctrl_flags already have been set by
-		 * ieee80211_tx_control_port(), here
-		 * we just sanity check that
-		 */
-
-		pre_conf_link_id = u32_get_bits(ctrl_flags,
-						IEEE80211_TX_CTRL_MLO_LINK);
-
-		if (pre_conf_link_id != link_id &&
-		    link_id != IEEE80211_LINK_UNSPECIFIED) {
-#ifdef CONFIG_MAC80211_VERBOSE_DEBUG
-			net_info_ratelimited("%s: dropped frame to %pM with bad link ID request (%d vs. %d)\n",
-					     sdata->name, hdr.addr1,
-					     pre_conf_link_id, link_id);
-#endif
-			ret = -EINVAL;
-			goto free;
-		}
-	}
-
-	info->control.flags = ctrl_flags;
-
+	info->control.flags =
+		u32_replace_bits(info->control.flags, link_id,
+				 IEEE80211_TX_CTRL_MLO_LINK);
 	return skb;
  free:
-	if (info_id)
-		ieee80211_remove_ack_skb(local, info_id);
-	kfree_skb(skb);
+	ieee80211_free_txskb(&local->hw, skb);
 	return ERR_PTR(ret);
 }
 
@@ -4368,13 +4307,14 @@ EXPORT_SYMBOL(ieee80211_txq_schedule_start);
 void __ieee80211_subif_start_xmit(struct sk_buff *skb,
 				  struct net_device *dev,
 				  u32 info_flags,
-				  u32 ctrl_flags,
-				  u64 cookie)
+				  u32 ctrl_flags)
 {
 	struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev);
 	struct ieee80211_local *local = sdata->local;
+	struct ieee80211_tx_info *info;
 	struct sta_info *sta;
 	struct sk_buff *next;
+	bool group_addressed;
 	int len = skb->len;
 
 	if (unlikely(!ieee80211_sdata_running(sdata) || skb->len < ETH_HLEN)) {
@@ -4394,6 +4334,7 @@ void __ieee80211_subif_start_xmit(struct sk_buff *skb,
 	if (ieee80211_lookup_ra_sta(sdata, skb, &sta))
 		goto out_free;
 
+	group_addressed = IS_ERR(sta);
 	if (IS_ERR(sta))
 		sta = NULL;
 
@@ -4426,8 +4367,22 @@ void __ieee80211_subif_start_xmit(struct sk_buff *skb,
 		if (skb->protocol == sdata->control_port_protocol)
 			ctrl_flags |= IEEE80211_TX_CTRL_SKIP_MPATH_LOOKUP;
 
-		skb = ieee80211_build_hdr(sdata, skb, info_flags,
-					  sta, ctrl_flags, cookie);
+		skb = skb_share_check(skb, GFP_ATOMIC);
+		if (unlikely(!skb)) {
+			kfree_skb_list(next);
+			goto out;
+		}
+
+		info = IEEE80211_SKB_CB(skb);
+		memset(info, 0, sizeof(*info));
+		info->flags = info_flags;
+		info->control.flags = ctrl_flags;
+
+		if (unlikely(!group_addressed &&
+			     sk_requests_wifi_status(skb->sk)))
+			ieee80211_store_ack_skb(local, skb, 0);
+
+		skb = ieee80211_build_hdr(sdata, skb, sta);
 		if (IS_ERR(skb)) {
 			kfree_skb_list(next);
 			goto out;
@@ -4564,7 +4519,7 @@ static void ieee80211_mlo_multicast_tx_one(struct ieee80211_sub_if_data *sdata,
 		return;
 
 	ctrl_flags |= u32_encode_bits(link_id, IEEE80211_TX_CTRL_MLO_LINK);
-	__ieee80211_subif_start_xmit(out, sdata->dev, 0, ctrl_flags, 0);
+	__ieee80211_subif_start_xmit(out, sdata->dev, 0, ctrl_flags);
 }
 
 static void ieee80211_mlo_multicast_tx(struct net_device *dev,
@@ -4579,7 +4534,7 @@ static void ieee80211_mlo_multicast_tx(struct net_device *dev,
 		ctrl_flags |= u32_encode_bits(__ffs(links),
 					      IEEE80211_TX_CTRL_MLO_LINK);
 
-		__ieee80211_subif_start_xmit(skb, sdata->dev, 0, ctrl_flags, 0);
+		__ieee80211_subif_start_xmit(skb, sdata->dev, 0, ctrl_flags);
 		return;
 	}
 
@@ -4620,8 +4575,7 @@ netdev_tx_t ieee80211_subif_start_xmit(struct sk_buff *skb,
 		ieee80211_convert_to_unicast(skb, dev, &queue);
 		while ((skb = __skb_dequeue(&queue)))
 			__ieee80211_subif_start_xmit(skb, dev, 0,
-						     IEEE80211_TX_CTRL_MLO_LINK_UNSPEC,
-						     0);
+						     IEEE80211_TX_CTRL_MLO_LINK_UNSPEC);
 	} else if (ieee80211_vif_is_mld(&sdata->vif) &&
 		   ((sdata->vif.type == NL80211_IFTYPE_AP &&
 		     !ieee80211_hw_check(&sdata->local->hw, MLO_MCAST_MULTI_LINK_TX)) ||
@@ -4631,8 +4585,7 @@ netdev_tx_t ieee80211_subif_start_xmit(struct sk_buff *skb,
 	} else {
 normal:
 		__ieee80211_subif_start_xmit(skb, dev, 0,
-					     IEEE80211_TX_CTRL_MLO_LINK_UNSPEC,
-					     0);
+					     IEEE80211_TX_CTRL_MLO_LINK_UNSPEC);
 	}
 
 	return NETDEV_TX_OK;
@@ -4730,8 +4683,7 @@ static void ieee80211_8023_xmit(struct ieee80211_sub_if_data *sdata,
 		if (!test_bit(HT_AGG_STATE_OPERATIONAL, &tid_tx->state)) {
 			/* fall back to non-offload slow path */
 			__ieee80211_subif_start_xmit(skb, dev, 0,
-						     IEEE80211_TX_CTRL_MLO_LINK_UNSPEC,
-						     0);
+						     IEEE80211_TX_CTRL_MLO_LINK_UNSPEC);
 			return;
 		}
 
@@ -4765,12 +4717,8 @@ static void ieee80211_8023_xmit(struct ieee80211_sub_if_data *sdata,
 			memcpy(IEEE80211_SKB_CB(seg), info, sizeof(*info));
 	}
 
-	if (unlikely(sk_requests_wifi_status(skb->sk))) {
-		info->status_data = ieee80211_store_ack_skb(local, skb,
-							    &info->flags, 0);
-		if (info->status_data)
-			info->status_data_idr = 1;
-	}
+	if (unlikely(sk_requests_wifi_status(skb->sk)))
+		ieee80211_store_ack_skb(local, skb, 0);
 
 	dev_sw_netstats_tx_add(dev, skbs, len);
 
@@ -4899,6 +4847,7 @@ ieee80211_build_data_template(struct ieee80211_sub_if_data *sdata,
 		.local = sdata->local,
 		.sdata = sdata,
 	};
+	struct ieee80211_tx_info *info;
 	struct sta_info *sta;
 
 	rcu_read_lock();
@@ -4909,8 +4858,12 @@ ieee80211_build_data_template(struct ieee80211_sub_if_data *sdata,
 		goto out;
 	}
 
-	skb = ieee80211_build_hdr(sdata, skb, info_flags, sta,
-				  IEEE80211_TX_CTRL_MLO_LINK_UNSPEC, 0);
+	info = IEEE80211_SKB_CB(skb);
+	memset(info, 0, sizeof(*info));
+	info->flags = info_flags;
+	info->control.flags = IEEE80211_TX_CTRL_MLO_LINK_UNSPEC;
+
+	skb = ieee80211_build_hdr(sdata, skb, sta);
 	if (IS_ERR(skb))
 		goto out;
 
@@ -6530,6 +6483,8 @@ int ieee80211_tx_control_port(struct wiphy *wiphy, struct net_device *dev,
 {
 	struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev);
 	struct ieee80211_local *local = sdata->local;
+	struct ieee80211_tx_info *info;
+	bool group_addressed;
 	struct sta_info *sta;
 	struct sk_buff *skb;
 	struct ethhdr *ehdr;
@@ -6554,9 +6509,6 @@ int ieee80211_tx_control_port(struct wiphy *wiphy, struct net_device *dev,
 	if (unencrypted)
 		flags |= IEEE80211_TX_INTFL_DONT_ENCRYPT;
 
-	if (cookie)
-		ctrl_flags |= IEEE80211_TX_CTL_REQ_TX_STATUS;
-
 	flags |= IEEE80211_TX_INTFL_NL80211_FRAME_TX;
 
 	skb = dev_alloc_skb(local->hw.extra_tx_headroom +
@@ -6573,15 +6525,11 @@ int ieee80211_tx_control_port(struct wiphy *wiphy, struct net_device *dev,
 
 	/* we may override the SA for MLO STA later */
 	if (link_id < 0) {
-		ctrl_flags |= u32_encode_bits(IEEE80211_LINK_UNSPECIFIED,
-					      IEEE80211_TX_CTRL_MLO_LINK);
+		link_id = IEEE80211_LINK_UNSPECIFIED;
 		memcpy(ehdr->h_source, sdata->vif.addr, ETH_ALEN);
 	} else {
 		struct ieee80211_bss_conf *link_conf;
 
-		ctrl_flags |= u32_encode_bits(link_id,
-					      IEEE80211_TX_CTRL_MLO_LINK);
-
 		rcu_read_lock();
 		link_conf = rcu_dereference(sdata->vif.link_conf[link_id]);
 		if (!link_conf) {
@@ -6600,9 +6548,6 @@ int ieee80211_tx_control_port(struct wiphy *wiphy, struct net_device *dev,
 	skb_reset_network_header(skb);
 	skb_reset_mac_header(skb);
 
-	if (local->hw.queues < IEEE80211_NUM_ACS)
-		goto start_xmit;
-
 	/* update QoS header to prioritize control port frames if possible,
 	 * prioritization also happens for control port frames send over
 	 * AF_PACKET
@@ -6615,24 +6560,48 @@ int ieee80211_tx_control_port(struct wiphy *wiphy, struct net_device *dev,
 		return err;
 	}
 
-	if (!IS_ERR(sta)) {
-		u16 queue = ieee80211_select_queue(sdata, sta, skb);
+	group_addressed = IS_ERR(sta);
+	if (IS_ERR(sta))
+		sta = NULL;
 
-		skb_set_queue_mapping(skb, queue);
+	skb_set_queue_mapping(skb, ieee80211_select_queue(sdata, sta, skb));
 
-		/*
-		 * for MLO STA, the SA should be the AP MLD address, but
-		 * the link ID has been selected already
-		 */
-		if (sta && sta->sta.mlo)
-			memcpy(ehdr->h_source, sdata->vif.addr, ETH_ALEN);
+	/*
+	 * for MLO STA, the SA should be the AP MLD address, but
+	 * the link ID has been selected already
+	 */
+	if (sta && sta->sta.mlo)
+		memcpy(ehdr->h_source, sdata->vif.addr, ETH_ALEN);
+
+	info = IEEE80211_SKB_CB(skb);
+	memset(info, 0, sizeof(*info));
+	info->flags = flags;
+	ctrl_flags |= u32_encode_bits(link_id, IEEE80211_TX_CTRL_MLO_LINK);
+	info->control.flags = ctrl_flags;
+
+	if (!group_addressed)
+		ieee80211_store_ack_skb(local, skb, cookie);
+
+	skb = ieee80211_build_hdr(sdata, skb, sta);
+	if (IS_ERR(skb)) {
+		rcu_read_unlock();
+		return PTR_ERR(skb);
 	}
-	rcu_read_unlock();
 
-start_xmit:
+	if (link_id != u32_get_bits(info->control.flags,
+				    IEEE80211_TX_CTRL_MLO_LINK)) {
+		ieee80211_free_txskb(&local->hw, skb);
+		rcu_read_unlock();
+		return -EINVAL;
+	}
+
+	dev_sw_netstats_tx_add(dev, 1, skb->len);
+	ieee80211_tpt_led_trig_tx(local, skb->len);
+
 	local_bh_disable();
-	__ieee80211_subif_start_xmit(skb, skb->dev, flags, ctrl_flags, cookie);
+	ieee80211_xmit(sdata, sta, skb);
 	local_bh_enable();
+	rcu_read_unlock();
 
 	return 0;
 }
@@ -6660,8 +6629,7 @@ int ieee80211_probe_mesh_link(struct wiphy *wiphy, struct net_device *dev,
 
 	local_bh_disable();
 	__ieee80211_subif_start_xmit(skb, skb->dev, 0,
-				     IEEE80211_TX_CTRL_SKIP_MPATH_LOOKUP,
-				     0);
+				     IEEE80211_TX_CTRL_SKIP_MPATH_LOOKUP);
 	local_bh_enable();
 
 	return 0;

3/2 2026/08/03 19:03 llm patch-evaluator
0m Model:
gemini-3.1-pro-preview

Args:
null

Results:
null

Tokens:
							input: 10063
							output: 27
							thoughts: 728
						

Thoughts:
**Analyzing a mac80211 TX Path Patch**

Okay, so I'm looking at a patch in `net/mac80211/`. My initial impression is that this is touching some fundamental TX path code. Specifically, the commit affects a number of key functions: `ieee80211_subif_start_xmit`, `ieee80211_build_hdr`, `ieee80211_tx_control_port`, and so on. The core of the change seems to involve removing the `cookie` argument from `__ieee80211_subif_start_xmit` and altering the call to `ieee80211_store_ack_skb` along with how `info` (the skb's control block) gets initialized. This means we're dealing with a functional alteration in how mac80211 handles transmissions. This has wide implications, naturally, being right in the core of the 802.11 wireless stack.

First thing I think is, is this fuzzer-friendly? And, yes, it's definitely reachable in a virtualized environment. The existence of `mac80211_hwsim`, the software-emulated hardware driver, is crucial here.  It means I can test this easily in QEMU. Good.

I should list all the affected functions. Let me quickly note those down: `ieee80211_lookup_ra_sta`, `ieee80211_store_ack_skb`, `ieee80211_build_hdr`, `__ieee80211_subif_start_xmit`, `ieee80211_mlo_multicast_tx_one`, `ieee80211_mlo_multicast_tx`, `ieee80211_subif_start_xmit`, `ieee80211_8023_xmit`, `ieee80211_build_data_template`, `ieee80211_tx_control_port`, `ieee80211_probe_mesh_link`.

Now, let's zoom in a little. Based on a quick glance, I'll pay closer attention to `ieee80211_tx_control_port`, `ieee80211_probe_mesh_link`, `__ieee80211_subif_start_xmit`, `ieee80211_subif_start_xmit`, and `ieee80211_build_data_template`. Wait a minute, `ieee80211_subif_start_xmit` is *the* hot-path for mac80211 interfaces, it's the `ndo_start_xmit` function, so this change will be critical. `ieee80211_tx_control_port` is also interesting because it handles 802.1X/EAPOL traffic and related control port frames, which while less "hot" than the core TX path, is still vital. `ieee80211_probe_mesh_link` deals with mesh networks. `ieee80211_build_data_template` is used for, obviously, building data templates.

I need to dig deeper. I'll start by checking the usage of `ieee80211_tx_control_port` and `ieee80211_probe_mesh_link`. Also I need to understand what changed about data template building. I should search for `ieee80211_tx_control_port` in the source base and see where that's called.



4/2 2026/08/03 19:04 tool grepper
0m Args:
{
  "Expression": "ieee80211_tx_control_port"
}

Results:
{
  "Output": "net/mac80211/cfg.c=5976=const struct cfg80211_ops mac80211_config_ops = {\n--\nnet/mac80211/cfg.c-6070-\t.set_multicast_to_unicast = ieee80211_set_multicast_to_unicast,\nnet/mac80211/cfg.c:6071:\t.tx_control_port = ieee80211_tx_control_port,\nnet/mac80211/cfg.c-6072-\t.get_txq_stats = ieee80211_get_txq_stats,\n--\nnet/mac80211/ieee80211_i.h=2246=void ieee80211_clear_fast_xmit(struct sta_info *sta);\nnet/mac80211/ieee80211_i.h:2247:int ieee80211_tx_control_port(struct wiphy *wiphy, struct net_device *dev,\nnet/mac80211/ieee80211_i.h-2248-\t\t\t      const u8 *buf, size_t len,\n--\nnet/mac80211/tx.c=6448=void ieee80211_tx_skb_tid(struct ieee80211_sub_if_data *sdata,\n--\nnet/mac80211/tx.c-6478-\nnet/mac80211/tx.c:6479:int ieee80211_tx_control_port(struct wiphy *wiphy, struct net_device *dev,\nnet/mac80211/tx.c-6480-\t\t\t      const u8 *buf, size_t len,\n"
}

5/2 2026/08/03 19:04 llm patch-evaluator
0m Model:
gemini-3.1-pro-preview

Args:
null

Results:
null

Tokens:
							input: 11427
							output: 21
							thoughts: 703
						

Thoughts:
**Analyzing Changes to the 802.11 Stack for Fuzzing Potential**

Okay, so this patch is touching `net/mac80211/tx.c`, `net/mac80211/tdls.c`, and `net/mac80211/ieee80211_i.h`. That's right in the heart of the mac80211 core, which, for those not familiar, is the Linux kernel's implementation of the 802.11 stack. It looks like the changes are primarily focused on how transmit operations are handled.

Specifically, I see a refactoring effort going on. The signature of `__ieee80211_subif_start_xmit` is being changed, removing the `cookie` argument. Also, `ieee80211_build_hdr` is being refactored to rely on pre-populated information within the `skb` control block, removing the `info_flags`, `ctrl_flags`, and `cookie` arguments. It seems like a consolidation of data within the `skb`'s control block, `ieee80211_store_ack_skb` is also being updated, and `ieee80211_tx_control_port` is being modified to populate this `info` and call the relevant functions directly. This is good: removing function arguments and moving that responsibility to other variables in the struct helps prevent incorrect usage and reduces the amount of state passed as arguments.

Wait a second... *mac80211*? Yes, it's the 802.11 stack. And it's reachable through `mac80211_hwsim`, which is a software emulated hardware driver. This means we have a viable path for fuzzing! **WorthFuzzing=true** - this patch introduces changes to a key part of the network stack, and we have a path for fuzzing the components.

Now, let's identify the important symbols. I'm focusing on the functions directly modified or heavily involved in the changes: `__ieee80211_subif_start_xmit`, `ieee80211_tx_control_port`, `ieee80211_build_data_template`, `ieee80211_probe_mesh_link` (though that last one seems like just a call site, not a key entry point), `ieee80211_mlo_multicast_tx` (though it's static) and `ieee80211_subif_start_xmit` (the netdev_tx_t).

A closer look. `__ieee80211_subif_start_xmit` is *exported*. `ieee80211_tx_control_port` is used in `mac80211_config_ops` which means it's reachable via `cfg80211`. `ieee80211_subif_start_xmit` is the `ndo_start_xmit` for mac80211 interfaces. That's a good surface to target, particularly with our fuzzing setup.

I'm checking if these key functions are static, as static functions have limited visibility: `__ieee80211_subif_start_xmit` isn't static, `ieee80211_tx_control_port` isn't static, `ieee80211_build_data_template` isn't static, and `ieee80211_subif_start_xmit` is also not static. Great, means they can be easily called.

Alright, time to go and check the Kconfig to see what modules and dependencies we need to enable for fuzzing.



6/2 2026/08/03 19:04 tool grepper
0m Args:
{
  "Expression": "config MAC80211"
}

Results:
{
  "Output": "drivers/net/wireless/virtual/Kconfig:1:config MAC80211_HWSIM\ndrivers/net/wireless/virtual/Kconfig-2-\ttristate \"Simulated radio testing tool for mac80211\"\n--\nnet/mac80211/Kconfig-1-# SPDX-License-Identifier: GPL-2.0-only\nnet/mac80211/Kconfig:2:config MAC80211\nnet/mac80211/Kconfig-3-\ttristate \"Generic IEEE 802.11 Networking Stack (mac80211)\"\n--\nnet/mac80211/Kconfig=19=if MAC80211 != n\nnet/mac80211/Kconfig-20-\nnet/mac80211/Kconfig:21:config MAC80211_HAS_RC\nnet/mac80211/Kconfig-22-\tbool\nnet/mac80211/Kconfig-23-\nnet/mac80211/Kconfig:24:config MAC80211_RC_MINSTREL\nnet/mac80211/Kconfig-25-\tbool \"Minstrel\" if EXPERT\n--\nnet/mac80211/Kconfig=31=choice\n--\nnet/mac80211/Kconfig-40-\nnet/mac80211/Kconfig:41:config MAC80211_RC_DEFAULT_MINSTREL\nnet/mac80211/Kconfig-42-\tbool \"Minstrel\"\n--\nnet/mac80211/Kconfig=48=endchoice\nnet/mac80211/Kconfig-49-\nnet/mac80211/Kconfig:50:config MAC80211_RC_DEFAULT\nnet/mac80211/Kconfig-51-\tstring\n--\nnet/mac80211/Kconfig=57=comment \"Some wireless drivers require a rate control algorithm\"\n--\nnet/mac80211/Kconfig-59-\nnet/mac80211/Kconfig:60:config MAC80211_KUNIT_TEST\nnet/mac80211/Kconfig-61-\ttristate \"KUnit tests for mac80211\" if !KUNIT_ALL_TESTS\n--\nnet/mac80211/Kconfig-69-\nnet/mac80211/Kconfig:70:config MAC80211_MESH\nnet/mac80211/Kconfig-71-\tbool \"Enable mac80211 mesh networking support\"\n--\nnet/mac80211/Kconfig-78-\nnet/mac80211/Kconfig:79:config MAC80211_LEDS\nnet/mac80211/Kconfig-80-\tbool \"Enable LED triggers\"\n--\nnet/mac80211/Kconfig-87-\nnet/mac80211/Kconfig:88:config MAC80211_DEBUGFS\nnet/mac80211/Kconfig-89-\tbool \"Export mac80211 internals in DebugFS\"\n--\nnet/mac80211/Kconfig-96-\nnet/mac80211/Kconfig:97:config MAC80211_MESSAGE_TRACING\nnet/mac80211/Kconfig-98-\tbool \"Trace all mac80211 debug messages\"\n--\nnet/mac80211/Kconfig-109-\nnet/mac80211/Kconfig:110:menuconfig MAC80211_DEBUG_MENU\nnet/mac80211/Kconfig-111-\tbool \"Select mac80211 debugging features\"\n--\nnet/mac80211/Kconfig-115-\nnet/mac80211/Kconfig:116:config MAC80211_NOINLINE\nnet/mac80211/Kconfig-117-\tbool \"Do not inline TX/RX handlers\"\n--\nnet/mac80211/Kconfig-131-\nnet/mac80211/Kconfig:132:config MAC80211_VERBOSE_DEBUG\nnet/mac80211/Kconfig-133-\tbool \"Verbose debugging output\"\n--\nnet/mac80211/Kconfig-142-\nnet/mac80211/Kconfig:143:config MAC80211_MLME_DEBUG\nnet/mac80211/Kconfig-144-\tbool \"Verbose managed MLME output\"\n--\nnet/mac80211/Kconfig-153-\nnet/mac80211/Kconfig:154:config MAC80211_STA_DEBUG\nnet/mac80211/Kconfig-155-\tbool \"Verbose station debugging\"\n--\nnet/mac80211/Kconfig-162-\nnet/mac80211/Kconfig:163:config MAC80211_HT_DEBUG\nnet/mac80211/Kconfig-164-\tbool \"Verbose HT debugging\"\n--\nnet/mac80211/Kconfig-174-\nnet/mac80211/Kconfig:175:config MAC80211_OCB_DEBUG\nnet/mac80211/Kconfig-176-\tbool \"Verbose OCB debugging\"\n--\nnet/mac80211/Kconfig-185-\nnet/mac80211/Kconfig:186:config MAC80211_IBSS_DEBUG\nnet/mac80211/Kconfig-187-\tbool \"Verbose IBSS debugging\"\n--\nnet/mac80211/Kconfig-196-\nnet/mac80211/Kconfig:197:config MAC80211_PS_DEBUG\nnet/mac80211/Kconfig-198-\tbool \"Verbose powersave mode debugging\"\n--\nnet/mac80211/Kconfig-208-\nnet/mac80211/Kconfig:209:config MAC80211_MPL_DEBUG\nnet/mac80211/Kconfig-210-\tbool \"Verbose mesh peer link debugging\"\n--\nnet/mac80211/Kconfig-221-\nnet/mac80211/Kconfig:222:config MAC80211_MPATH_DEBUG\nnet/mac80211/Kconfig-223-\tbool \"Verbose mesh path debugging\"\n--\nnet/mac80211/Kconfig-234-\nnet/mac80211/Kconfig:235:config MAC80211_MHWMP_DEBUG\nnet/mac80211/Kconfig-236-\tbool \"Verbose mesh HWMP routing debugging\"\n--\nnet/mac80211/Kconfig-247-\nnet/mac80211/Kconfig:248:config MAC80211_MESH_SYNC_DEBUG\nnet/mac80211/Kconfig-249-\tbool \"Verbose mesh synchronization debugging\"\n--\nnet/mac80211/Kconfig-258-\nnet/mac80211/Kconfig:259:config MAC80211_MESH_CSA_DEBUG\nnet/mac80211/Kconfig-260-\tbool \"Verbose mesh channel switch debugging\"\n--\nnet/mac80211/Kconfig-269-\nnet/mac80211/Kconfig:270:config MAC80211_MESH_PS_DEBUG\nnet/mac80211/Kconfig-271-\tbool \"Verbose mesh powersave debugging\"\n--\nnet/mac80211/Kconfig-280-\nnet/mac80211/Kconfig:281:config MAC80211_TDLS_DEBUG\nnet/mac80211/Kconfig-282-\tbool \"Verbose TDLS debugging\"\n--\nnet/mac80211/Kconfig-292-\nnet/mac80211/Kconfig:293:config MAC80211_DEBUG_COUNTERS\nnet/mac80211/Kconfig-294-\tbool \"Extra statistics for TX/RX debugging\"\n--\nnet/mac80211/Kconfig-307-\nnet/mac80211/Kconfig:308:config MAC80211_STA_HASH_MAX_SIZE\nnet/mac80211/Kconfig-309-\tint \"Station hash table maximum size\" if MAC80211_DEBUG_MENU\n"
}

7/2 2026/08/03 19:04 llm patch-evaluator
0m Model:
gemini-3.1-pro-preview

Args:
null

Results:
null

Tokens:
							input: 15977
							output: 25
							thoughts: 77
						

Thoughts:
**My Configuration Check**

Alright, let's get down to brass tacks. I need to make absolutely certain that this fuzzing setup is going to work as intended. My immediate concerns revolve around the kernel configuration. To ensure the fuzzing is active and effective, I'm thinking I'll need `MAC80211` and `MAC80211_HWSIM` activated. But, hold on. I remember that `CFG80211` is a prerequisite for `MAC80211`. I should probably double-check that that dependency is met. And finally, I should confirm the dependencies for `MAC80211_HWSIM` to ensure I have everything in place.



8/2 2026/08/03 19:04 tool grepper
0m Args:
{
  "Expression": "config MAC80211_HWSIM"
}

Results:
{
  "Output": "drivers/net/wireless/virtual/Kconfig:1:config MAC80211_HWSIM\ndrivers/net/wireless/virtual/Kconfig-2-\ttristate \"Simulated radio testing tool for mac80211\"\n"
}

9/2 2026/08/03 19:04 llm patch-evaluator
0m Model:
gemini-3.1-pro-preview

Args:
null

Results:
null

Tokens:
							input: 16305
							output: 36
							thoughts: 21
						

Thoughts:
Here's my take on those thoughts:

**Analyzing the Kconfig for Virtual Wireless Drivers**

Alright, let's dive into the `drivers/net/wireless/virtual/Kconfig` file. I'm focusing specifically around line 1, as that's often the entry point for understanding the overall configuration structure for a particular subsystem or module. This Kconfig file will be critical in determining how the virtual wireless driver(s) are built, enabled, and configured within the larger kernel build process. I'm immediately looking for the fundamental building blocks - the top-level menu entries, any dependencies or prerequisites, and the default states of relevant options. It's time to build a mental map of the key configuration variables and how they relate to each other. I'll need to understand any conditional logic that impacts the availability of features or drivers.



10/2 2026/08/03 19:04 tool read-file
0m Args:
{
  "File": "drivers/net/wireless/virtual/Kconfig",
  "FirstLine": 1,
  "LineCount": 20
}

Results:
{
  "Contents": "   1:\tconfig MAC80211_HWSIM\n   2:\t\ttristate \"Simulated radio testing tool for mac80211\"\n   3:\t\tdepends on MAC80211\n   4:\t\thelp\n   5:\t\t  This driver is a developer testing tool that can be used to test\n   6:\t\t  IEEE 802.11 networking stack (mac80211) functionality. This is not\n   7:\t\t  needed for normal wireless LAN usage and is only for testing. See\n   8:\t\t  Documentation/networking/mac80211_hwsim for more information on how\n   9:\t\t  to use this tool.\n  10:\t\n  11:\t\t  To compile this driver as a module, choose M here: the module will be\n  12:\t\t  called mac80211_hwsim.  If unsure, say N.\n  13:\t\n  14:\tconfig VIRT_WIFI\n  15:\t\ttristate \"Wifi wrapper for ethernet drivers\"\n  16:\t\tdepends on CFG80211\n  17:\t\thelp\n  18:\t\t  This option adds support for ethernet connections to appear as if they\n  19:\t\t  are wifi connections through a special rtnetlink device.\n  20:\t\n"
}

11/2 2026/08/03 19:04 llm patch-evaluator
0m Model:
gemini-3.1-pro-preview

Args:
null

Results:
null

Tokens:
							input: 15335
							output: 242
							thoughts: 1516
						

Thoughts:
**Fuzzing Focus: mac80211 TX Logic**

Okay, so this patch is clearly messing with some fundamental mac80211 stuff – specifically, the core TX logic. It's touching `net/mac80211/tx.c`, `net/mac80211/tdls.c`, and a header file, so it's a deep dive. I'm seeing changes to the signatures of `__ieee80211_subif_start_xmit` and `ieee80211_lookup_ra_sta`, along with modifications to how TX info is handled in `ieee80211_build_hdr` and `ieee80211_tx_control_port`. This directly impacts packet transmission, queuing, and header construction. Given that this is core stuff, and reachable through `mac80211_hwsim` (which is great because that means QEMU/syzkaller are viable), it's screaming for some fuzzing.

My first thought is to nail down the specific functions this patch is targeting. After digging into the code, I can see that it's focusing on:

*   `ieee80211_tdls_prep_mgmt_packet`
*   `ieee80211_lookup_ra_sta` (though static, so worth considering context)
*   `ieee80211_store_ack_skb`
*   `ieee80211_build_hdr`
*   `__ieee80211_subif_start_xmit`
*   `ieee80211_mlo_multicast_tx_one`
*   `ieee80211_mlo_multicast_tx`
*   `ieee80211_subif_start_xmit`
*   `ieee80211_8023_xmit`
*   `ieee80211_build_data_template`
*   `ieee80211_tx_control_port`
*   `ieee80211_probe_mesh_link`

Let's refine the list. `ieee80211_subif_start_xmit` (both the internal and exported versions) look like hot paths – they're the `ndo_start_xmit` functions, making them high-priority candidates. `ieee80211_tx_control_port` is also good. It's used for control port frames like EAPOL, so a more specific target. Also, `ieee80211_build_data_template` will be useful and `ieee80211_probe_mesh_link` for mesh links. `ieee80211_tdls_prep_mgmt_packet` looks good too.

Since I'll be fuzzing, I'm going to focus my initial efforts on:

*   `ieee80211_tx_control_port` (API entrypoint)
*   `ieee80211_tdls_prep_mgmt_packet`
*   `ieee80211_probe_mesh_link`

For testing this, I'm going to make sure that I enable a few configurations:

*   `MAC80211` (obviously)
*   `MAC80211_HWSIM` (to use in a virtualized environment – essential for practical testing)
*   `MAC80211_MESH` (because there's a conditional block related to `CONFIG_MAC80211_MESH` in `ieee80211_lookup_ra_sta`).

Essentially, this patch is shaking up core transmission logic. By targeting specific entry points and setting up a proper environment (using HWSIM and relevant configurations), I think this fuzzing campaign will have a high likelihood of finding some interesting bugs.



12/2 2026/08/03 19:05 tool set-results
0m Args:
{
  "EnableConfigs": [
    "MAC80211",
    "MAC80211_HWSIM",
    "MAC80211_MESH"
  ],
  "FocusSymbols": [
    "ieee80211_tx_control_port",
    "ieee80211_tdls_prep_mgmt_packet",
    "ieee80211_probe_mesh_link"
  ],
  "Reasoning": "The patch modifies core mac80211 transmission logic, including TX info initialization, header building, and control port transmission. These changes are functional and reachable via virtualized wireless interfaces (mac80211_hwsim). We should focus fuzzing on the modified entry points like `ieee80211_tx_control_port` and `ieee80211_tdls_prep_mgmt_packet`. `MAC80211_MESH` is needed to reach the modified mesh-specific logic in `ieee80211_lookup_ra_sta`.",
  "WorthFuzzing": true
}

Results:
{
  "EnableConfigs": [
    "MAC80211",
    "MAC80211_HWSIM",
    "MAC80211_MESH"
  ],
  "FocusSymbols": [
    "ieee80211_tx_control_port",
    "ieee80211_tdls_prep_mgmt_packet",
    "ieee80211_probe_mesh_link"
  ],
  "Reasoning": "The patch modifies core mac80211 transmission logic, including TX info initialization, header building, and control port transmission. These changes are functional and reachable via virtualized wireless interfaces (mac80211_hwsim). We should focus fuzzing on the modified entry points like `ieee80211_tx_control_port` and `ieee80211_tdls_prep_mgmt_packet`. `MAC80211_MESH` is needed to reach the modified mesh-specific logic in `ieee80211_lookup_ra_sta`.",
  "WorthFuzzing": true
}

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)