diff -Nru backport-iwlwifi-dkms-11289/Android-make-iwlwifi.mk backport-iwlwifi-dkms-11510/Android-make-iwlwifi.mk --- backport-iwlwifi-dkms-11289/Android-make-iwlwifi.mk 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/Android-make-iwlwifi.mk 1970-01-01 08:00:00.000000000 +0800 @@ -1,78 +0,0 @@ - -# Run only this build if variant define the needed configuration -# e.g. Enabling iwlwifi for XMM6321 -# BOARD_USING_INTEL_IWL := true - this will enable iwlwifi building -# INTEL_IWL_BOARD_CONFIG := xmm6321 - the configuration, defconfig-xmm6321 -# INTEL_IWL_USE_COMPAT_INSTALL := y - this will use kernel modules installation -# INTEL_IWL_COMPAT_INSTALL_DIR := updates - the folder that the modules will be installed in -# INTEL_IWL_COMPAT_INSTALL_PATH ?= $(ANDROID_BUILD_TOP)/$(TARGET_OUT) - the install path for the modules -.PHONY: iwlwifi - -INTEL_IWL_SRC_DIR := $(call my-dir) -INTEL_IWL_OUT_DIR := $(abspath $(PRODUCT_OUT)/iwlwifi) -INTEL_IWL_COMPAT_INSTALL_PATH ?= $(abspath $(TARGET_OUT)) - -ifeq ($(CROSS_COMPILE),) -ifneq ($(TARGET_TOOLS_PREFIX),) -CROSS_COMPILE := CROSS_COMPILE=$(notdir $(TARGET_TOOLS_PREFIX)) -endif -endif - -ifeq ($(CROSS_COMPILE),) -ifeq ($(TARGET_ARCH),arm) -$(warning You are building for an ARM platform, but no CROSS_COMPILE is set. This is likely an error.) -else -$(warning CROSS_COMPILE variant is not set; Defaulting to host gcc.) -endif -endif - -ifeq ($(INTEL_IWL_USE_COMPAT_INSTALL),y) -INTEL_IWL_COMPAT_INSTALL := iwlwifi_install -INTEL_IWL_KERNEL_DEPEND := $(INSTALLED_KERNEL_TARGET) -else -# use system install -copy_modules_to_root: iwlwifi -ALL_KERNEL_MODULES += $(INTEL_IWL_OUT_DIR) -INTEL_IWL_KERNEL_DEPEND := build_bzImage -endif - -ifeq ($(INTEL_IWL_USE_RM_MAC_CFG),y) -copy_modules_to_root: iwlwifi -INTEL_IWL_COMPAT_INSTALL_PATH := $(abspath $(KERNEL_OUT_MODINSTALL)) -INTEL_IWL_KERNEL_DEPEND := modules_install -INTEL_IWL_RM_MAC_CFG_DEPEND := iwlwifi_rm_mac_cfg -INTEL_IWL_INSTALL_MOD_STRIP := INSTALL_MOD_STRIP=1 -endif - -# IWLWIFI_CONFIGURE is a rule to use a defconfig for iwlwifi -IWLWIFI_CONFIGURE := $(INTEL_IWL_OUT_DIR)/.config - -KERNEL_OUT_ABS_DIR := $(abspath $(KERNEL_OUT_DIR)) - -iwlwifi: iwlwifi_build $(INTEL_IWL_COMPAT_INSTALL) $(INTEL_IWL_MOD_DEP) - -INTEL_IWL_SRC_FILES := $(shell find $(INTEL_IWL_SRC_DIR) -path $(INTEL_IWL_SRC_DIR)/.git -prune -o -print) -$(INTEL_IWL_OUT_DIR): $(INTEL_IWL_SRC_FILES) - @echo Syncing directory $(INTEL_IWL_SRC_DIR) to $(INTEL_IWL_OUT_DIR) - @rsync -rt --del $(INTEL_IWL_SRC_DIR)/ $(INTEL_IWL_OUT_DIR) - -$(IWLWIFI_CONFIGURE): $(INTEL_IWL_KERNEL_DEPEND) $(INTEL_IWL_OUT_DIR) - @echo Configuring kernel module iwlwifi with defconfig-$(INTEL_IWL_BOARD_CONFIG) - @$(MAKE) -C $(INTEL_IWL_OUT_DIR)/ ARCH=$(TARGET_ARCH) $(CROSS_COMPILE) KLIB_BUILD=$(KERNEL_OUT_ABS_DIR) defconfig-$(INTEL_IWL_BOARD_CONFIG) - -iwlwifi_build: $(IWLWIFI_CONFIGURE) - @$(info Building kernel module iwlwifi in $(INTEL_IWL_OUT_DIR)) - @$(MAKE) -C $(INTEL_IWL_OUT_DIR)/ ARCH=$(TARGET_ARCH) $(CROSS_COMPILE) KLIB_BUILD=$(KERNEL_OUT_ABS_DIR) - -iwlwifi_install: iwlwifi_build $(INTEL_IWL_RM_MAC_CFG_DEPEND) - @$(info Installing kernel modules in $(INTEL_IWL_COMPAT_INSTALL_PATH)) - @$(MAKE) -C $(KERNEL_OUT_ABS_DIR) ARCH=$(TARGET_ARCH) M=$(INTEL_IWL_OUT_DIR)/ INSTALL_MOD_DIR=$(INTEL_IWL_COMPAT_INSTALL_DIR) INSTALL_MOD_PATH=$(INTEL_IWL_COMPAT_INSTALL_PATH) $(INTEL_IWL_INSTALL_MOD_STRIP) modules_install - -iwlwifi_rm_mac_cfg: iwlwifi_build - $(info Remove kernel cfg80211.ko and mac80211.ko) - @find $(KERNEL_OUT_MODINSTALL)/lib/modules/ -name "mac80211.ko" | xargs rm -f - @find $(KERNEL_OUT_MODINSTALL)/lib/modules/ -name "cfg80211.ko" | xargs rm -f - -.PHONY: iwlwifi_clean -iwlwifi_clean: - rm -rf $(INTEL_IWL_OUT_DIR) diff -Nru backport-iwlwifi-dkms-11289/Android.mk backport-iwlwifi-dkms-11510/Android.mk --- backport-iwlwifi-dkms-11289/Android.mk 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/Android.mk 1970-01-01 08:00:00.000000000 +0800 @@ -1,82 +0,0 @@ -# including iwlwifi Android mk only if it was declared. -ifeq ($(BOARD_USING_INTEL_IWL),true) - -# Run only this build if variant define the needed configuration -# e.g. Enabling iwlwifi for XMM6321 -# BOARD_USING_INTEL_IWL := true - this will enable iwlwifi building -# INTEL_IWL_BOARD_CONFIG := xmm6321 - the configuration, defconfig-xmm6321 -# INTEL_IWL_USE_COMPAT_INSTALL := y - this will use kernel modules installation -# INTEL_IWL_COMPAT_INSTALL_DIR := updates - the folder that the modules will be installed in -# INTEL_IWL_COMPAT_INSTALL_PATH ?= $(ANDROID_BUILD_TOP)/$(TARGET_OUT) - the install path for the modules -.PHONY: iwlwifi - -INTEL_IWL_SRC_DIR := $(call my-dir) -INTEL_IWL_OUT_DIR := $(abspath $(PRODUCT_OUT)/iwlwifi) -INTEL_IWL_COMPAT_INSTALL_PATH ?= $(abspath $(TARGET_OUT)) - -ifeq ($(CROSS_COMPILE),) -ifneq ($(TARGET_TOOLS_PREFIX),) -CROSS_COMPILE := CROSS_COMPILE=$(notdir $(TARGET_TOOLS_PREFIX)) -endif -endif - -ifeq ($(CROSS_COMPILE),) -ifeq ($(TARGET_ARCH),arm) -$(warning You are building for an ARM platform, but no CROSS_COMPILE is set. This is likely an error.) -else -$(warning CROSS_COMPILE variant is not set; Defaulting to host gcc.) -endif -endif - -ifeq ($(INTEL_IWL_USE_COMPAT_INSTALL),y) -INTEL_IWL_COMPAT_INSTALL := iwlwifi_install -INTEL_IWL_KERNEL_DEPEND := $(INSTALLED_KERNEL_TARGET) -else -# use system install -copy_modules_to_root: iwlwifi -ALL_KERNEL_MODULES += $(INTEL_IWL_OUT_DIR) -INTEL_IWL_KERNEL_DEPEND := build_bzImage -endif - -ifeq ($(INTEL_IWL_USE_RM_MAC_CFG),y) -copy_modules_to_root: iwlwifi -INTEL_IWL_COMPAT_INSTALL_PATH := $(abspath $(KERNEL_OUT_MODINSTALL)) -INTEL_IWL_KERNEL_DEPEND := modules_install -INTEL_IWL_RM_MAC_CFG_DEPEND := iwlwifi_rm_mac_cfg -INTEL_IWL_INSTALL_MOD_STRIP := INSTALL_MOD_STRIP=1 -endif - -# IWLWIFI_CONFIGURE is a rule to use a defconfig for iwlwifi -IWLWIFI_CONFIGURE := $(INTEL_IWL_OUT_DIR)/.config - -KERNEL_OUT_ABS_DIR := $(abspath $(KERNEL_OUT_DIR)) - -iwlwifi: iwlwifi_build $(INTEL_IWL_COMPAT_INSTALL) $(INTEL_IWL_MOD_DEP) - -INTEL_IWL_SRC_FILES := $(shell find $(INTEL_IWL_SRC_DIR) -path $(INTEL_IWL_SRC_DIR)/.git -prune -o -print) -$(INTEL_IWL_OUT_DIR): $(INTEL_IWL_SRC_FILES) - @echo Syncing directory $(INTEL_IWL_SRC_DIR) to $(INTEL_IWL_OUT_DIR) - @rsync -rt --del $(INTEL_IWL_SRC_DIR)/ $(INTEL_IWL_OUT_DIR) - -$(IWLWIFI_CONFIGURE): $(INTEL_IWL_KERNEL_DEPEND) $(INTEL_IWL_OUT_DIR) - @echo Configuring kernel module iwlwifi with defconfig-$(INTEL_IWL_BOARD_CONFIG) - @$(MAKE) -C $(INTEL_IWL_OUT_DIR)/ ARCH=$(TARGET_ARCH) $(CROSS_COMPILE) KLIB_BUILD=$(KERNEL_OUT_ABS_DIR) defconfig-$(INTEL_IWL_BOARD_CONFIG) - -iwlwifi_build: $(IWLWIFI_CONFIGURE) - @$(info Building kernel module iwlwifi in $(INTEL_IWL_OUT_DIR)) - @$(MAKE) -C $(INTEL_IWL_OUT_DIR)/ ARCH=$(TARGET_ARCH) $(CROSS_COMPILE) KLIB_BUILD=$(KERNEL_OUT_ABS_DIR) - -iwlwifi_install: iwlwifi_build $(INTEL_IWL_RM_MAC_CFG_DEPEND) - @$(info Installing kernel modules in $(INTEL_IWL_COMPAT_INSTALL_PATH)) - @$(MAKE) -C $(KERNEL_OUT_ABS_DIR) ARCH=$(TARGET_ARCH) M=$(INTEL_IWL_OUT_DIR)/ INSTALL_MOD_DIR=$(INTEL_IWL_COMPAT_INSTALL_DIR) INSTALL_MOD_PATH=$(INTEL_IWL_COMPAT_INSTALL_PATH) $(INTEL_IWL_INSTALL_MOD_STRIP) modules_install - -iwlwifi_rm_mac_cfg: iwlwifi_build - $(info Remove kernel cfg80211.ko and mac80211.ko) - @find $(KERNEL_OUT_MODINSTALL)/lib/modules/ -name "mac80211.ko" | xargs rm -f - @find $(KERNEL_OUT_MODINSTALL)/lib/modules/ -name "cfg80211.ko" | xargs rm -f - -.PHONY: iwlwifi_clean -iwlwifi_clean: - rm -rf $(INTEL_IWL_OUT_DIR) - -endif diff -Nru backport-iwlwifi-dkms-11289/Android-upper-folder.mk backport-iwlwifi-dkms-11510/Android-upper-folder.mk --- backport-iwlwifi-dkms-11289/Android-upper-folder.mk 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/Android-upper-folder.mk 1970-01-01 08:00:00.000000000 +0800 @@ -1,5 +0,0 @@ -LOCAL_PATH := $(call my-dir) - -ifneq ($(INTEL_IWL_MODULE_SUB_FOLDER),) -include $(LOCAL_PATH)/$(INTEL_IWL_MODULE_SUB_FOLDER)/Android.mk -endif diff -Nru backport-iwlwifi-dkms-11289/backport-include/kunit/resource.h backport-iwlwifi-dkms-11510/backport-include/kunit/resource.h --- backport-iwlwifi-dkms-11289/backport-include/kunit/resource.h 1970-01-01 08:00:00.000000000 +0800 +++ backport-iwlwifi-dkms-11510/backport-include/kunit/resource.h 2023-10-04 04:18:43.000000000 +0800 @@ -0,0 +1,102 @@ +#ifndef __BP_KUNIT_RESOURCE_H +#define __BP_KUNIT_RESOURCE_H +#include + +#include_next + +#if LINUX_VERSION_IS_LESS(6,6,0) && LINUX_VERSION_IS_GEQ(6,2,0) +/* A 'deferred action' function to be used with kunit_add_action. */ +typedef void (kunit_action_t)(void *); + +/** + * kunit_add_action() - Call a function when the test ends. + * @test: Test case to associate the action with. + * @action: The function to run on test exit + * @ctx: Data passed into @func + * + * Defer the execution of a function until the test exits, either normally or + * due to a failure. @ctx is passed as additional context. All functions + * registered with kunit_add_action() will execute in the opposite order to that + * they were registered in. + * + * This is useful for cleaning up allocated memory and resources, as these + * functions are called even if the test aborts early due to, e.g., a failed + * assertion. + * + * See also: devm_add_action() for the devres equivalent. + * + * Returns: + * 0 on success, an error if the action could not be deferred. + */ +int kunit_add_action(struct kunit *test, kunit_action_t *action, void *ctx); + +/** + * kunit_add_action_or_reset() - Call a function when the test ends. + * @test: Test case to associate the action with. + * @action: The function to run on test exit + * @ctx: Data passed into @func + * + * Defer the execution of a function until the test exits, either normally or + * due to a failure. @ctx is passed as additional context. All functions + * registered with kunit_add_action() will execute in the opposite order to that + * they were registered in. + * + * This is useful for cleaning up allocated memory and resources, as these + * functions are called even if the test aborts early due to, e.g., a failed + * assertion. + * + * If the action cannot be created (e.g., due to the system being out of memory), + * then action(ctx) will be called immediately, and an error will be returned. + * + * See also: devm_add_action_or_reset() for the devres equivalent. + * + * Returns: + * 0 on success, an error if the action could not be deferred. + */ +int kunit_add_action_or_reset(struct kunit *test, kunit_action_t *action, + void *ctx); + +/** + * kunit_remove_action() - Cancel a matching deferred action. + * @test: Test case the action is associated with. + * @action: The deferred function to cancel. + * @ctx: The context passed to the deferred function to trigger. + * + * Prevent an action deferred via kunit_add_action() from executing when the + * test terminates. + * + * If the function/context pair was deferred multiple times, only the most + * recent one will be cancelled. + * + * See also: devm_remove_action() for the devres equivalent. + */ +void kunit_remove_action(struct kunit *test, + kunit_action_t *action, + void *ctx); + +/** + * kunit_release_action() - Run a matching action call immediately. + * @test: Test case the action is associated with. + * @action: The deferred function to trigger. + * @ctx: The context passed to the deferred function to trigger. + * + * Execute a function deferred via kunit_add_action()) immediately, rather than + * when the test ends. + * + * If the function/context pair was deferred multiple times, it will only be + * executed once here. The most recent deferral will no longer execute when + * the test ends. + * + * kunit_release_action(test, func, ctx); + * is equivalent to + * func(ctx); + * kunit_remove_action(test, func, ctx); + * + * See also: devm_release_action() for the devres equivalent. + */ +void kunit_release_action(struct kunit *test, + kunit_action_t *action, + void *ctx); +#endif /* LINUX_VERSION_IS_LESS(6,6,0) && LINUX_VERSION_IS_GEQ(6,2,0) */ + +#endif /* __BP_KUNIT_RESOURCE_H */ diff -Nru backport-iwlwifi-dkms-11289/backport-include/kunit/skbuff.h backport-iwlwifi-dkms-11510/backport-include/kunit/skbuff.h --- backport-iwlwifi-dkms-11289/backport-include/kunit/skbuff.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/backport-include/kunit/skbuff.h 2023-10-04 04:18:43.000000000 +0800 @@ -2,36 +2,48 @@ #define __BP_KUNIT_SKBUFF_H #include -#if LINUX_VERSION_IS_LESS(6,5,0) -#include +#if LINUX_VERSION_IS_LESS(6,7,0) +#include #include /** * kunit_zalloc_skb() - Allocate and initialize a resource managed skb. * @test: The test case to which the skb belongs * @len: size to allocate - * @gfp: allocation mask * - * Allocate a new struct sk_buff, zero fill the give length and add it as a - * resource to the kunit test for automatic cleanup. + * Allocate a new struct sk_buff with GFP_KERNEL, zero fill the give length + * and add it as a resource to the kunit test for automatic cleanup. * - * The function will not return in case of an allocation error. + * Returns: newly allocated SKB, or %NULL on error */ static inline struct sk_buff *kunit_zalloc_skb(struct kunit *test, int len, gfp_t gfp) { - struct sk_buff *res = alloc_skb(len, gfp); + struct sk_buff *res = alloc_skb(len, GFP_KERNEL); - KUNIT_ASSERT_NOT_NULL(test, res); - KUNIT_ASSERT_EQ(test, skb_pad(res, len), 0); + if (!res || skb_pad(res, len)) + return NULL; - kunit_add_cleanup(test, (kunit_cleanup_t) kfree_skb, res, gfp); + if (kunit_add_action_or_reset(test, (kunit_action_t*)kfree_skb, res)) + return NULL; return res; } -#else /* LINUX_VERSION_IS_LESS(6,4,0) */ +/** + * kunit_kfree_skb() - Like kfree_skb except for allocations managed by KUnit. + * @test: The test case to which the resource belongs. + * @skb: The SKB to free. + */ +static inline void kunit_kfree_skb(struct kunit *test, struct sk_buff *skb) +{ + if (!skb) + return; + + kunit_release_action(test, (kunit_action_t *)kfree_skb, (void *)skb); +} +#else /* LINUX_VERSION_IS_LESS(6,6,0) */ #include_next -#endif /* LINUX_VERSION_IS_LESS(6,4,0) */ +#endif /* LINUX_VERSION_IS_LESS(6,6,0) */ #endif /* __BP_KUNIT_SKBUFF_H */ diff -Nru backport-iwlwifi-dkms-11289/backport-include/kunit/test.h backport-iwlwifi-dkms-11510/backport-include/kunit/test.h --- backport-iwlwifi-dkms-11289/backport-include/kunit/test.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/backport-include/kunit/test.h 2023-10-04 04:18:43.000000000 +0800 @@ -4,7 +4,7 @@ #include_next -#if LINUX_VERSION_IS_LESS(6,5,0) +#if LINUX_VERSION_IS_LESS(6,7,0) /** * KUNIT_ARRAY_PARAM_DESC() - Define test parameter generator from an array. * @name: prefix for the test parameter generator function. @@ -23,26 +23,6 @@ } \ return NULL; \ } - -typedef void (*kunit_cleanup_t)(const void *); - -/** - * kunit_add_cleanup() - Add post-test cleanup action. - * @test: The test case to which the resource belongs. - * @cleanup_func: function to call at end of test. - * @data: data to pass to @free_func. - * @internal_gfp: gfp to use for internal allocations, if unsure, use GFP_KERNEL - * - * This adds a cleanup action to be executed after the test completes. - * Internally this is handled using a *test managed resource*. - * - * This function will abort the test on failure. - * - * Note: KUnit needs to allocate memory for a kunit_resource object. You must - * specify an @internal_gfp that is compatible with the current context. - */ -void kunit_add_cleanup(struct kunit *test, kunit_cleanup_t cleanup_func, - const void *data, gfp_t internal_gfp); -#endif /* LINUX_VERSION_IS_LESS(6,4,0) */ +#endif /* LINUX_VERSION_IS_LESS(6,6,0) */ #endif /* __BP_KUNIT_TEST_H */ diff -Nru backport-iwlwifi-dkms-11289/backport-include/linux/leds.h backport-iwlwifi-dkms-11510/backport-include/linux/leds.h --- backport-iwlwifi-dkms-11289/backport-include/linux/leds.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/backport-include/linux/leds.h 2023-10-04 04:18:43.000000000 +0800 @@ -26,4 +26,25 @@ struct led_trigger *trigger); #endif /* < 4.5 */ +#if LINUX_VERSION_IS_LESS(6,5,0) + +static inline void backport_led_trigger_blink_oneshot(struct led_trigger *trigger, + unsigned long delay_on, + unsigned long delay_off, + int invert) +{ + led_trigger_blink_oneshot(trigger, &delay_on, &delay_off, invert); +} +#define led_trigger_blink_oneshot LINUX_BACKPORT(led_trigger_blink_oneshot) + +static inline void backport_led_trigger_blink(struct led_trigger *trigger, + unsigned long delay_on, + unsigned long delay_off) +{ + led_trigger_blink(trigger, &delay_on, &delay_off); +} +#define led_trigger_blink LINUX_BACKPORT(led_trigger_blink) + +#endif /* < 6.5 */ + #endif /* __BACKPORT_LINUX_LEDS_H */ diff -Nru backport-iwlwifi-dkms-11289/backport-include/linux/tracepoint.h backport-iwlwifi-dkms-11510/backport-include/linux/tracepoint.h --- backport-iwlwifi-dkms-11289/backport-include/linux/tracepoint.h 1970-01-01 08:00:00.000000000 +0800 +++ backport-iwlwifi-dkms-11510/backport-include/linux/tracepoint.h 2023-10-04 04:18:43.000000000 +0800 @@ -0,0 +1,18 @@ +/* SPDX-License-Identifier: GPL-2.0 */ +/* careful - must be multi-include capable */ +#include_next +#ifndef __BP_TRACEPOINT_H +#define __BP_TRACEPOINT_H + +#if LINUX_VERSION_IS_LESS(5,10,0) +#define DECLARE_TRACEPOINT(tp) \ + extern struct tracepoint __tracepoint_##tp +#ifdef CONFIG_TRACEPOINTS +# define tracepoint_enabled(tp) \ + static_key_false(&(__tracepoint_##tp).key) +#else +# define tracepoint_enabled(tracepoint) false +#endif +#endif /* < 5.10 */ + +#endif /* __BP_TRACEPOINT_H */ diff -Nru backport-iwlwifi-dkms-11289/backport-include/net/genetlink.h backport-iwlwifi-dkms-11510/backport-include/net/genetlink.h --- backport-iwlwifi-dkms-11289/backport-include/net/genetlink.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/backport-include/net/genetlink.h 2023-10-04 04:18:43.000000000 +0800 @@ -3,6 +3,7 @@ #include_next #include +#if LINUX_VERSION_IS_LESS(4,12,0) static inline void __bp_genl_info_userhdr_set(struct genl_info *info, void *userhdr) { @@ -14,7 +15,6 @@ return info->userhdr; } -#if LINUX_VERSION_IS_LESS(4,12,0) #define GENL_SET_ERR_MSG(info, msg) NL_SET_ERR_MSG(genl_info_extack(info), msg) static inline int genl_err_attr(struct genl_info *info, int err, @@ -44,11 +44,13 @@ #endif } +#if LINUX_VERSION_IS_LESS(6,6,0) /* this gets put in place of info->userhdr, since we use that above */ static inline void *genl_info_userhdr(struct genl_info *info) { return (u8 *)info->genlhdr + GENL_HDRLEN; } +#endif #if LINUX_VERSION_IS_LESS(4,10,0) #define __genl_ro_after_init diff -Nru backport-iwlwifi-dkms-11289/backport-include/net/gso.h backport-iwlwifi-dkms-11510/backport-include/net/gso.h --- backport-iwlwifi-dkms-11289/backport-include/net/gso.h 1970-01-01 08:00:00.000000000 +0800 +++ backport-iwlwifi-dkms-11510/backport-include/net/gso.h 2023-10-04 04:18:43.000000000 +0800 @@ -0,0 +1,9 @@ +#ifndef __BACKPORT_GSO_H +#define __BACKPORT_GSO_H + +#if LINUX_VERSION_IS_GEQ(6,4,10) +#include_next +#else +#include +#endif /* < 6.5.0 */ +#endif /* __BACKPORT_GSO_H */ diff -Nru backport-iwlwifi-dkms-11289/compat/backport-6.5.c backport-iwlwifi-dkms-11510/compat/backport-6.5.c --- backport-iwlwifi-dkms-11289/compat/backport-6.5.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/compat/backport-6.5.c 2023-10-04 04:18:43.000000000 +0800 @@ -2,44 +2,108 @@ #include #include +#include #if LINUX_VERSION_IS_GEQ(6,2,0) && IS_ENABLED(CONFIG_KUNIT) #include +#include -struct kunit_auto_cleanup { - struct kunit_resource resource; - kunit_cleanup_t cleanup_func; +struct kunit_action_ctx { + struct kunit_resource res; + void (*func)(void *); + void *ctx; }; -static void kunit_auto_cleanup_free(struct kunit_resource *res) +static void __kunit_action_free(struct kunit_resource *res) { - struct kunit_auto_cleanup *cleanup; + struct kunit_action_ctx *action_ctx = container_of(res, struct kunit_action_ctx, res); - cleanup = container_of(res, struct kunit_auto_cleanup, resource); + action_ctx->func(action_ctx->ctx); +} + + +int kunit_add_action(struct kunit *test, void (*action)(void *), void *ctx) +{ + struct kunit_action_ctx *action_ctx; + + KUNIT_ASSERT_NOT_NULL_MSG(test, action, "Tried to action a NULL function!"); + + action_ctx = kzalloc(sizeof(*action_ctx), GFP_KERNEL); + if (!action_ctx) + return -ENOMEM; - cleanup->cleanup_func(cleanup->resource.data); + action_ctx->func = action; + action_ctx->ctx = ctx; + + action_ctx->res.should_kfree = true; + /* As init is NULL, this cannot fail. */ + __kunit_add_resource(test, NULL, __kunit_action_free, &action_ctx->res, action_ctx); + + return 0; } +EXPORT_SYMBOL_GPL(kunit_add_action); -void kunit_add_cleanup(struct kunit *test, kunit_cleanup_t cleanup_func, - const void *data, gfp_t internal_gfp) +int kunit_add_action_or_reset(struct kunit *test, void (*action)(void *), + void *ctx) { - struct kunit_auto_cleanup *res; + int res = kunit_add_action(test, action, ctx); - KUNIT_ASSERT_NOT_NULL_MSG(test, cleanup_func, - "Cleanup function must not be NULL"); + if (res) + action(ctx); + return res; +} +EXPORT_SYMBOL_GPL(kunit_add_action_or_reset); + +static bool __kunit_action_match(struct kunit *test, + struct kunit_resource *res, void *match_data) +{ + struct kunit_action_ctx *match_ctx = (struct kunit_action_ctx *)match_data; + struct kunit_action_ctx *res_ctx = container_of(res, struct kunit_action_ctx, res); - res = kzalloc(sizeof(*res), internal_gfp); - if (!res) { - cleanup_func(data); - KUNIT_ASSERT_FAILURE(test, "Could not allocate resource for cleanup"); + /* Make sure this is a free function. */ + if (res->free != __kunit_action_free) + return false; + + /* Both the function and context data should match. */ + return (match_ctx->func == res_ctx->func) && (match_ctx->ctx == res_ctx->ctx); +} + +void kunit_remove_action(struct kunit *test, + void (*action)(void *), + void *ctx) +{ + struct kunit_action_ctx match_ctx; + struct kunit_resource *res; + + match_ctx.func = action; + match_ctx.ctx = ctx; + + res = kunit_find_resource(test, __kunit_action_match, &match_ctx); + if (res) { + /* Remove the free function so we don't run the action. */ + res->free = NULL; + kunit_remove_resource(test, res); + kunit_put_resource(res); } +} +EXPORT_SYMBOL_GPL(kunit_remove_action); - res->cleanup_func = cleanup_func; - res->resource.should_kfree = true; +void kunit_release_action(struct kunit *test, + void (*action)(void *), + void *ctx) +{ + struct kunit_action_ctx match_ctx; + struct kunit_resource *res; - /* Cannot fail as init is NULL */ - __kunit_add_resource(test, NULL, kunit_auto_cleanup_free, - &res->resource, (void *)data); + match_ctx.func = action; + match_ctx.ctx = ctx; + + res = kunit_find_resource(test, __kunit_action_match, &match_ctx); + if (res) { + kunit_remove_resource(test, res); + /* We have to put() this here, else free won't be called. */ + kunit_put_resource(res); + } } -EXPORT_SYMBOL_GPL(kunit_add_cleanup); -#endif /* LINUX_VERSION_IS_GEQ(6,2,0) */ +EXPORT_SYMBOL_GPL(kunit_release_action); +#endif /* LINUX_VERSION_IS_GEQ(6,2,0) && IS_ENABLED(CONFIG_KUNIT) */ diff -Nru backport-iwlwifi-dkms-11289/compat/verification/x509_public_key.c backport-iwlwifi-dkms-11510/compat/verification/x509_public_key.c --- backport-iwlwifi-dkms-11289/compat/verification/x509_public_key.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/compat/verification/x509_public_key.c 2023-10-04 04:18:43.000000000 +0800 @@ -6,11 +6,13 @@ */ #define pr_fmt(fmt) "X.509: "fmt +#include +#include +#include #include #include #include -#include -#include +#include #include "x509_parser.h" /* @@ -27,9 +29,6 @@ pr_devel("==>%s()\n", __func__); - sig->data = cert->tbs; - sig->data_size = cert->tbs_size; - sig->s = kmemdup(cert->raw_sig, cert->raw_sig_size, GFP_KERNEL); if (!sig->s) return -ENOMEM; @@ -62,7 +61,21 @@ desc->tfm = tfm; - ret = crypto_shash_digest(desc, cert->tbs, cert->tbs_size, sig->digest); + if (strcmp(cert->pub->pkey_algo, "sm2") == 0) { + ret = strcmp(sig->hash_algo, "sm3") != 0 ? -EINVAL : + crypto_shash_init(desc) ?: + sm2_compute_z_digest(desc, cert->pub->key, + cert->pub->keylen, sig->digest) ?: + crypto_shash_init(desc) ?: + crypto_shash_update(desc, sig->digest, + sig->digest_size) ?: + crypto_shash_finup(desc, cert->tbs, cert->tbs_size, + sig->digest); + } else { + ret = crypto_shash_digest(desc, cert->tbs, cert->tbs_size, + sig->digest); + } + if (ret < 0) goto error_2; diff -Nru backport-iwlwifi-dkms-11289/debian/backport-iwlwifi-dkms.dkms.in backport-iwlwifi-dkms-11510/debian/backport-iwlwifi-dkms.dkms.in --- backport-iwlwifi-dkms-11289/debian/backport-iwlwifi-dkms.dkms.in 2023-05-01 20:33:39.000000000 +0800 +++ backport-iwlwifi-dkms-11510/debian/backport-iwlwifi-dkms.dkms.in 2023-10-31 14:39:23.000000000 +0800 @@ -6,7 +6,7 @@ PACKAGE_NAME="@DKMS_PACKAGE_NAME@" PACKAGE_VERSION="#MODULE_VERSION#" AUTOINSTALL="yes" -OBSOLETE_BY="6.5.0" +OBSOLETE_BY="6.7.0" BUILT_MODULE_NAME[0]="iwlwifi-compat" BUILT_MODULE_LOCATION[0]="compat" diff -Nru backport-iwlwifi-dkms-11289/debian/changelog backport-iwlwifi-dkms-11510/debian/changelog --- backport-iwlwifi-dkms-11289/debian/changelog 2023-05-01 20:33:39.000000000 +0800 +++ backport-iwlwifi-dkms-11510/debian/changelog 2023-10-31 14:39:23.000000000 +0800 @@ -1,3 +1,13 @@ +backport-iwlwifi-dkms (11510-0ubuntu1) noble; urgency=low + + [You-Sheng Yang] + * New release + - upstream version 11510 commit 41e354fb5f32f. (LP: #2042059) + - debian: refresh patches + * dkms: bump OBSOLETE_BY version to v6.7.0 + + -- You-Sheng Yang Tue, 31 Oct 2023 14:39:23 +0800 + backport-iwlwifi-dkms (11289-0ubuntu1) mantic; urgency=low [You-Sheng Yang] diff -Nru backport-iwlwifi-dkms-11289/debian/patches/0012-UBUNTU-SAUCE-backport-fix-led_trigger_blink_oneshot.patch backport-iwlwifi-dkms-11510/debian/patches/0012-UBUNTU-SAUCE-backport-fix-led_trigger_blink_oneshot.patch --- backport-iwlwifi-dkms-11289/debian/patches/0012-UBUNTU-SAUCE-backport-fix-led_trigger_blink_oneshot.patch 2023-05-01 20:33:39.000000000 +0800 +++ backport-iwlwifi-dkms-11510/debian/patches/0012-UBUNTU-SAUCE-backport-fix-led_trigger_blink_oneshot.patch 1970-01-01 08:00:00.000000000 +0800 @@ -1,56 +0,0 @@ -From: You-Sheng Yang -Date: Tue, 11 Jul 2023 12:32:28 +0800 -Subject: UBUNTU: SAUCE: backport: fix led_trigger_blink_oneshot - -In v6.5-rc1 commit e298d8a38b23 ("leds: Change -led_trigger_blink[_oneshot]() delay parameters to pass-by-value") now -passes two parameters by value. - -Signed-off-by: You-Sheng Yang ---- - backport-include/linux/leds.h | 11 +++++++++++ - net/mac80211/led.h | 4 ++-- - 2 files changed, 13 insertions(+), 2 deletions(-) - -diff --git a/backport-include/linux/leds.h b/backport-include/linux/leds.h -index dbafd413..869ebdf 100644 ---- a/backport-include/linux/leds.h -+++ b/backport-include/linux/leds.h -@@ -26,4 +26,15 @@ extern int devm_led_trigger_register(struct device *dev, - struct led_trigger *trigger); - #endif /* < 4.5 */ - -+#if LINUX_VERSION_IS_LESS(6,5,0) -+static inline void backport_led_trigger_blink_oneshot(struct led_trigger *trigger, -+ unsigned long delay_on, -+ unsigned long delay_off, -+ int invert) -+{ -+ led_trigger_blink_oneshot(trigger, &delay_on, &delay_off, invert); -+} -+#define led_trigger_blink_oneshot LINUX_BACKPORT(led_trigger_blink_oneshot) -+#endif /* < 6.5 */ -+ - #endif /* __BACKPORT_LINUX_LEDS_H */ -diff --git a/net/mac80211/led.h b/net/mac80211/led.h -index 2abb1d0..46b9489 100644 ---- a/net/mac80211/led.h -+++ b/net/mac80211/led.h -@@ -17,7 +17,7 @@ static inline void ieee80211_led_rx(struct ieee80211_local *local) - - if (!atomic_read(&local->rx_led_active)) - return; -- led_trigger_blink_oneshot(&local->rx_led, &led_delay, &led_delay, 0); -+ led_trigger_blink_oneshot(&local->rx_led, led_delay, led_delay, 0); - #endif - } - -@@ -28,7 +28,7 @@ static inline void ieee80211_led_tx(struct ieee80211_local *local) - - if (!atomic_read(&local->tx_led_active)) - return; -- led_trigger_blink_oneshot(&local->tx_led, &led_delay, &led_delay, 0); -+ led_trigger_blink_oneshot(&local->tx_led, led_delay, led_delay, 0); - #endif - } - diff -Nru backport-iwlwifi-dkms-11289/debian/patches/0013-UBUNTU-SAUCE-backport-wrap-net-gso.h.patch backport-iwlwifi-dkms-11510/debian/patches/0013-UBUNTU-SAUCE-backport-wrap-net-gso.h.patch --- backport-iwlwifi-dkms-11289/debian/patches/0013-UBUNTU-SAUCE-backport-wrap-net-gso.h.patch 2023-05-01 20:33:39.000000000 +0800 +++ backport-iwlwifi-dkms-11510/debian/patches/0013-UBUNTU-SAUCE-backport-wrap-net-gso.h.patch 1970-01-01 08:00:00.000000000 +0800 @@ -1,55 +0,0 @@ -From: You-Sheng Yang -Date: Tue, 11 Jul 2023 12:52:05 +0800 -Subject: UBUNTU: SAUCE: backport: wrap net/gso.h - -In v6.5-rc1 commit d457a0e329b0 ("net: move gso declarations and -functions to their own files"), gso symbols were moved to net/gso.h. - -Signed-off-by: You-Sheng Yang ---- - backport-include/net/gso.h | 10 ++++++++++ - drivers/net/wireless/intel/iwlwifi/mvm/tx.c | 1 + - net/mac80211/tx.c | 1 + - 3 files changed, 12 insertions(+) - create mode 100644 backport-include/net/gso.h - -diff --git a/backport-include/net/gso.h b/backport-include/net/gso.h -new file mode 100644 -index 00000000..60ee842 ---- /dev/null -+++ b/backport-include/net/gso.h -@@ -0,0 +1,10 @@ -+#ifndef __BACKPORT_NET_GSO_H -+#define __BACKPORT_NET_GSO_H -+ -+#if LINUX_VERSION_IS_GEQ(6,5,0) -+#include_next -+#else -+#include -+#endif -+ -+#endif /* __BACKPORT_NET_GSO_H */ -diff --git a/drivers/net/wireless/intel/iwlwifi/mvm/tx.c b/drivers/net/wireless/intel/iwlwifi/mvm/tx.c -index 1c70584..5c7c4bf 100644 ---- a/drivers/net/wireless/intel/iwlwifi/mvm/tx.c -+++ b/drivers/net/wireless/intel/iwlwifi/mvm/tx.c -@@ -7,6 +7,7 @@ - #include - #include - #include -+#include - #include - #include - -diff --git a/net/mac80211/tx.c b/net/mac80211/tx.c -index 7e055a7..c11a7c7 100644 ---- a/net/mac80211/tx.c -+++ b/net/mac80211/tx.c -@@ -26,6 +26,7 @@ - #include - #include - #include -+#include - - #include "ieee80211_i.h" - #include "driver-ops.h" diff -Nru backport-iwlwifi-dkms-11289/debian/patches/0014-UBUNTU-SAUCE-wifi-iwlwifi-fix-build-against-CONF.patch backport-iwlwifi-dkms-11510/debian/patches/0014-UBUNTU-SAUCE-wifi-iwlwifi-fix-build-against-CONF.patch --- backport-iwlwifi-dkms-11289/debian/patches/0014-UBUNTU-SAUCE-wifi-iwlwifi-fix-build-against-CONF.patch 2023-05-01 20:33:39.000000000 +0800 +++ backport-iwlwifi-dkms-11510/debian/patches/0014-UBUNTU-SAUCE-wifi-iwlwifi-fix-build-against-CONF.patch 2023-10-31 14:39:23.000000000 +0800 @@ -9,10 +9,10 @@ 2 files changed, 11 insertions(+), 5 deletions(-) diff --git a/drivers/net/wireless/intel/iwlwifi/mvm/fw.c b/drivers/net/wireless/intel/iwlwifi/mvm/fw.c -index bc9fde6..94a7b5c 100644 +index a31b068..793b288 100644 --- a/drivers/net/wireless/intel/iwlwifi/mvm/fw.c +++ b/drivers/net/wireless/intel/iwlwifi/mvm/fw.c -@@ -1546,6 +1546,11 @@ static int iwl_mvm_ppag_init(struct iwl_mvm *mvm) +@@ -1628,6 +1628,11 @@ static int iwl_mvm_ppag_init(struct iwl_mvm *mvm) return 0; } @@ -25,10 +25,10 @@ { } diff --git a/drivers/net/wireless/intel/iwlwifi/xvt/xvt.c b/drivers/net/wireless/intel/iwlwifi/xvt/xvt.c -index 506430a..a741495 100644 +index 52d3604..ea6b54f 100644 --- a/drivers/net/wireless/intel/iwlwifi/xvt/xvt.c +++ b/drivers/net/wireless/intel/iwlwifi/xvt/xvt.c -@@ -936,11 +936,6 @@ static int iwl_xvt_sar_geo_init(struct iwl_xvt *xvt) +@@ -937,11 +937,6 @@ static int iwl_xvt_sar_geo_init(struct iwl_xvt *xvt) { return 0; } @@ -40,7 +40,7 @@ #endif /* CONFIG_ACPI */ int iwl_xvt_sar_select_profile(struct iwl_xvt *xvt, int prof_a, int prof_b) -@@ -1123,6 +1118,7 @@ void iwl_xvt_txpath_flush_send_cmd(struct iwl_xvt *xvt, u32 sta_id, u16 tids) +@@ -1124,6 +1119,7 @@ void iwl_xvt_txpath_flush_send_cmd(struct iwl_xvt *xvt, u32 sta_id, u16 tids) iwl_xvt_txpath_flush(xvt, cmd.resp_pkt); } @@ -48,7 +48,7 @@ void iwl_xvt_lari_cfg(struct iwl_xvt *xvt) { int ret; -@@ -1186,3 +1182,8 @@ void iwl_xvt_lari_cfg(struct iwl_xvt *xvt) +@@ -1210,3 +1206,8 @@ void iwl_xvt_lari_cfg(struct iwl_xvt *xvt) ret); } } diff -Nru backport-iwlwifi-dkms-11289/debian/patches/0014-UBUNTU-SAUCE-wifi-iwlwifi-xvt-fix-build-against-CONF.patch backport-iwlwifi-dkms-11510/debian/patches/0014-UBUNTU-SAUCE-wifi-iwlwifi-xvt-fix-build-against-CONF.patch --- backport-iwlwifi-dkms-11289/debian/patches/0014-UBUNTU-SAUCE-wifi-iwlwifi-xvt-fix-build-against-CONF.patch 2023-05-01 20:33:39.000000000 +0800 +++ backport-iwlwifi-dkms-11510/debian/patches/0014-UBUNTU-SAUCE-wifi-iwlwifi-xvt-fix-build-against-CONF.patch 1970-01-01 08:00:00.000000000 +0800 @@ -1,42 +0,0 @@ -From: You-Sheng Yang -Date: Tue, 11 Jul 2023 13:02:34 +0800 -Subject: UBUNTU: SAUCE: wifi: iwlwifi: xvt: fix build against !CONFIG_ACPI - -Signed-off-by: You-Sheng Yang ---- - drivers/net/wireless/intel/iwlwifi/xvt/xvt.c | 11 ++++++----- - 1 file changed, 6 insertions(+), 5 deletions(-) - -diff --git a/drivers/net/wireless/intel/iwlwifi/xvt/xvt.c b/drivers/net/wireless/intel/iwlwifi/xvt/xvt.c -index 506430a..a741495 100644 ---- a/drivers/net/wireless/intel/iwlwifi/xvt/xvt.c -+++ b/drivers/net/wireless/intel/iwlwifi/xvt/xvt.c -@@ -936,11 +936,6 @@ static int iwl_xvt_sar_geo_init(struct iwl_xvt *xvt) - { - return 0; - } -- --void iwl_xvt_lari_cfg(struct iwl_xvt *xvt) --{ --} -- - #endif /* CONFIG_ACPI */ - - int iwl_xvt_sar_select_profile(struct iwl_xvt *xvt, int prof_a, int prof_b) -@@ -1123,6 +1118,7 @@ void iwl_xvt_txpath_flush_send_cmd(struct iwl_xvt *xvt, u32 sta_id, u16 tids) - iwl_xvt_txpath_flush(xvt, cmd.resp_pkt); - } - -+#ifdef CONFIG_ACPI - void iwl_xvt_lari_cfg(struct iwl_xvt *xvt) - { - int ret; -@@ -1186,3 +1182,8 @@ void iwl_xvt_lari_cfg(struct iwl_xvt *xvt) - ret); - } - } -+#else /* CONFIG_ACPI */ -+void iwl_xvt_lari_cfg(struct iwl_xvt *xvt) -+{ -+} -+#endif /* CONFIG_ACPI */ diff -Nru backport-iwlwifi-dkms-11289/debian/patches/series backport-iwlwifi-dkms-11510/debian/patches/series --- backport-iwlwifi-dkms-11289/debian/patches/series 2023-05-01 20:33:39.000000000 +0800 +++ backport-iwlwifi-dkms-11510/debian/patches/series 2023-10-31 14:39:23.000000000 +0800 @@ -2,6 +2,4 @@ 0002-fix-format-overflow-compile-error-in-kconf-confdata..patch 0008-compat-rename-built-module-to-iwlwifi-compat.ko.patch 0011-UBUNTU-SAUCE-iwlwifi-mei-disable-by-default.patch -0012-UBUNTU-SAUCE-backport-fix-led_trigger_blink_oneshot.patch -0013-UBUNTU-SAUCE-backport-wrap-net-gso.h.patch 0014-UBUNTU-SAUCE-wifi-iwlwifi-fix-build-against-CONF.patch diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/cfg/ax210.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/cfg/ax210.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/cfg/ax210.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/cfg/ax210.c 2023-10-04 04:18:43.000000000 +0800 @@ -10,7 +10,7 @@ #include "fw/api/txq.h" /* Highest firmware API version supported */ -#define IWL_AX210_UCODE_API_MAX 83 +#define IWL_AX210_UCODE_API_MAX 86 /* Lowest firmware API version supported */ #define IWL_AX210_UCODE_API_MIN 59 diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/cfg/bz.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/cfg/bz.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/cfg/bz.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/cfg/bz.c 2023-10-04 04:18:43.000000000 +0800 @@ -10,7 +10,7 @@ #include "fw/api/txq.h" /* Highest firmware API version supported */ -#define IWL_BZ_UCODE_API_MAX 83 +#define IWL_BZ_UCODE_API_MAX 86 /* Lowest firmware API version supported */ #define IWL_BZ_UCODE_API_MIN 80 @@ -153,12 +153,13 @@ }; const char iwl_bz_name[] = "Intel(R) TBD Bz device"; +const char iwl_mtp_name[] = "Intel(R) TBD MtP device"; const struct iwl_cfg iwl_cfg_bz = { .fw_name_mac = "bz", .uhb_supported = true, IWL_DEVICE_BZ, - .features = IWL_TX_CSUM_NETIF_FLAGS_BZ | NETIF_F_RXCSUM, + .features = IWL_TX_CSUM_NETIF_FLAGS | NETIF_F_RXCSUM, .num_rbds = IWL_NUM_RBDS_BZ_EHT, }; @@ -166,7 +167,7 @@ .fw_name_mac = "gl", .uhb_supported = true, IWL_DEVICE_BZ, - .features = IWL_TX_CSUM_NETIF_FLAGS_BZ | NETIF_F_RXCSUM, + .features = IWL_TX_CSUM_NETIF_FLAGS | NETIF_F_RXCSUM, .num_rbds = IWL_NUM_RBDS_BZ_EHT, }; diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/cfg/sc.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/cfg/sc.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/cfg/sc.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/cfg/sc.c 2023-10-04 04:18:43.000000000 +0800 @@ -10,7 +10,7 @@ #include "fw/api/txq.h" /* Highest firmware API version supported */ -#define IWL_SC_UCODE_API_MAX 83 +#define IWL_SC_UCODE_API_MAX 86 /* Lowest firmware API version supported */ #define IWL_SC_UCODE_API_MIN 82 @@ -151,7 +151,7 @@ .fw_name_mac = "sc", .uhb_supported = true, IWL_DEVICE_SC, - .features = IWL_TX_CSUM_NETIF_FLAGS_BZ | NETIF_F_RXCSUM, + .features = IWL_TX_CSUM_NETIF_FLAGS | NETIF_F_RXCSUM, .num_rbds = IWL_NUM_RBDS_SC_EHT, }; diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/acpi.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/acpi.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/acpi.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/acpi.c 2023-10-04 04:18:43.000000000 +0800 @@ -15,10 +15,10 @@ 0x8E, 0x28, 0x5A, 0xDE); IWL_EXPORT_SYMBOL(iwl_guid); -const guid_t iwl_rfi_guid = GUID_INIT(0x7266172C, 0x220B, 0x4B29, - 0x81, 0x4F, 0x75, 0xE4, - 0xDD, 0x26, 0xB5, 0xFD); -IWL_EXPORT_SYMBOL(iwl_rfi_guid); +const guid_t iwl_internal_guid = GUID_INIT(0x7266172C, 0x220B, 0x4B29, + 0x81, 0x4F, 0x75, 0xE4, + 0xDD, 0x26, 0xB5, 0xFD); +IWL_EXPORT_SYMBOL(iwl_internal_guid); static const struct dmi_system_id dmi_ppag_approved_list[] = { { .ident = "HP", @@ -1019,15 +1019,25 @@ __le32 config_bitmap = 0; /* - ** Evaluate func 'DSM_FUNC_ENABLE_INDONESIA_5G2' + * Evaluate func 'DSM_FUNC_ENABLE_INDONESIA_5G2'. + * Setting config_bitmap Indonesia bit is valid only for HR/JF. */ - ret = iwl_acpi_get_dsm_u8(fwrt->dev, 0, - DSM_FUNC_ENABLE_INDONESIA_5G2, - &iwl_guid, &value); + switch (CSR_HW_RFID_TYPE(fwrt->trans->hw_rf_id)) { + case IWL_CFG_RF_TYPE_HR1: + case IWL_CFG_RF_TYPE_HR2: + case IWL_CFG_RF_TYPE_JF1: + case IWL_CFG_RF_TYPE_JF2: + ret = iwl_acpi_get_dsm_u8(fwrt->dev, 0, + DSM_FUNC_ENABLE_INDONESIA_5G2, + &iwl_guid, &value); - if (!ret && value == DSM_VALUE_INDONESIA_ENABLE) - config_bitmap |= - cpu_to_le32(LARI_CONFIG_ENABLE_5G2_IN_INDONESIA_MSK); + if (!ret && value == DSM_VALUE_INDONESIA_ENABLE) + config_bitmap |= + cpu_to_le32(LARI_CONFIG_ENABLE_5G2_IN_INDONESIA_MSK); + break; + default: + break; + } /* ** Evaluate func 'DSM_FUNC_DISABLE_SRD' @@ -1211,8 +1221,9 @@ gain = cmd->v1.gain[0]; *cmd_size = sizeof(cmd->v1); if (fwrt->ppag_ver == 1 || fwrt->ppag_ver == 2) { + /* in this case FW supports revision 0 */ IWL_DEBUG_RADIO(fwrt, - "PPAG table rev is %d but FW supports rev 0, sending truncated table\n", + "PPAG table rev is %d, send truncated table\n", fwrt->ppag_ver); } } else if (cmd_ver >= 2 && cmd_ver <= 4) { @@ -1220,15 +1231,16 @@ gain = cmd->v2.gain[0]; *cmd_size = sizeof(cmd->v2); if (fwrt->ppag_ver == 0) { + /* in this case FW supports revisions 1 or 2 */ IWL_DEBUG_RADIO(fwrt, - "PPAG table rev is 0 but FW supports rev 1 or 2, sending padded table\n"); + "PPAG table rev is 0, send padded table\n"); } } else { IWL_DEBUG_RADIO(fwrt, "Unsupported PPAG command version\n"); return -EINVAL; } - // ppag mode + /* ppag mode */ IWL_DEBUG_RADIO(fwrt, "PPAG MODE bits were read from bios: %d\n", cmd->v1.flags & cpu_to_le32(ACPI_PPAG_MASK)); diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/acpi.h backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/acpi.h --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/acpi.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/acpi.h 2023-10-04 04:18:43.000000000 +0800 @@ -139,6 +139,7 @@ DSM_FUNC_ENABLE_UNII4_CHAN = 7, DSM_FUNC_ACTIVATE_CHANNEL = 8, DSM_FUNC_FORCE_DISABLE_CHANNELS = 9, + DSM_FUNC_ENERGY_DETECTION_THRESHOLD = 10, DSM_FUNC_RFI_DLVR_CONFIG = 11 }; @@ -156,9 +157,11 @@ DSM_VALUE_INDONESIA_MAX }; -/* DSM RFI uses a different GUID, so need separate definitions */ +/* CNV internal DSM functions / definitions */ -#define DSM_RFI_DDR_FUNC_ENABLE 3 +enum iwl_dsm_internal_funcs { + DSM_INTERNAL_FUNC_RFI_DDR_ENABLE = 3, +}; enum iwl_dsm_values_rfi_ddr { DSM_VALUE_RFI_DDR_ENABLE, @@ -181,7 +184,7 @@ struct iwl_fw_runtime; extern const guid_t iwl_guid; -extern const guid_t iwl_rfi_guid; +extern const guid_t iwl_internal_guid; int iwl_acpi_get_dsm_u8(struct device *dev, int rev, int func, const guid_t *guid, u8 *value); diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/api/commands.h backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/api/commands.h --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/api/commands.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/api/commands.h 2023-10-04 04:18:43.000000000 +0800 @@ -31,6 +31,8 @@ * &enum iwl_regulatory_and_nvm_subcmd_ids * @XVT_GROUP: XVT group, uses command IDs from &enum iwl_xvt_subcmd_ids * @DEBUG_GROUP: Debug group, uses command IDs from &enum iwl_debug_cmds + * @STATISTICS_GROUP: Statistics group, uses command IDs from + * &enum iwl_statistics_subcmd_ids */ enum iwl_mvm_command_groups { LEGACY_GROUP = 0x0, @@ -46,6 +48,7 @@ REGULATORY_AND_NVM_GROUP = 0xc, XVT_GROUP = 0xe, DEBUG_GROUP = 0xf, + STATISTICS_GROUP = 0x10, }; /** @@ -629,6 +632,16 @@ SYSTEM_FEATURES_CONTROL_CMD = 0xd, /** + * @SYSTEM_STATISTICS_CMD: &struct iwl_system_statistics_cmd + */ + SYSTEM_STATISTICS_CMD = 0xf, + + /** + * @SYSTEM_STATISTICS_END_NOTIF: &struct iwl_system_statistics_end_notif + */ + SYSTEM_STATISTICS_END_NOTIF = 0xfd, + + /** * @RFI_SUPPORT_NOTIF: &struct iwl_rfi_support_notif */ RFI_SUPPORT_NOTIF = 0xff, @@ -672,4 +685,36 @@ IQ_CALIB_CONFIG_NOTIF = 0xFF, }; +/** + * enum iwl_statistics_subcmd_ids - Statistics group command IDs + */ +enum iwl_statistics_subcmd_ids { + /** + * @STATISTICS_OPER_NOTIF: Notification about operational + * statistics &struct iwl_system_statistics_notif_oper + */ + STATISTICS_OPER_NOTIF = 0x0, + + /** + * @STATISTICS_OPER_PART1_NOTIF: Notification about operational part1 + * statistics &struct iwl_system_statistics_part1_notif_oper + */ + STATISTICS_OPER_PART1_NOTIF = 0x1, + + /** + * @STATISTICS_OPER_PART2_NOTIF: Notification about operational part2 + */ + STATISTICS_OPER_PART2_NOTIF = 0x2, + + /** + * @STATISTICS_OPER_PART3_NOTIF: Notification about operational part3 + */ + STATISTICS_OPER_PART3_NOTIF = 0x3, + + /** + * @STATISTICS_OPER_PART4_NOTIF: Notification about operational part4 + */ + STATISTICS_OPER_PART4_NOTIF = 0x4, +}; + #endif /* __iwl_fw_api_commands_h__ */ diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/api/dbg-tlv.h backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/api/dbg-tlv.h --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/api/dbg-tlv.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/api/dbg-tlv.h 2023-10-04 04:18:43.000000000 +0800 @@ -1,6 +1,6 @@ /* SPDX-License-Identifier: GPL-2.0 OR BSD-3-Clause */ /* - * Copyright (C) 2018-2022 Intel Corporation + * Copyright (C) 2018-2023 Intel Corporation */ #ifndef __iwl_fw_dbg_tlv_h__ #define __iwl_fw_dbg_tlv_h__ @@ -44,6 +44,30 @@ } __packed; /* FW_TLV_DEBUG_HEADER_S_VER_1 */ /** + * struct iwl_fw_ini_addr_size - Base address and size that defines + * a chunk of memory + * + * @addr: the base address (fixed size - 4 bytes) + * @size: the size to read + */ +struct iwl_fw_ini_addr_size { + __le32 addr; + __le32 size; +} __packed; /* FW_TLV_DEBUG_ADDR_SIZE_VER_1 */ + +/** + * struct iwl_fw_ini_region_dev_addr_range - Configuration to read + * device address range + * + * @offset: offset to add to the base address of each chunk + * The addrs[] array will be treated as an array of &iwl_fw_ini_addr_size - + * an array of (addr, size) pairs. + */ +struct iwl_fw_ini_region_dev_addr_range { + __le32 offset; +} __packed; /* FW_TLV_DEBUG_DEVICE_ADDR_RANGE_API_S_VER_1 */ + +/** * struct iwl_fw_ini_region_dev_addr - Configuration to read device addresses * * @size: size of each memory chunk @@ -136,6 +160,10 @@ * &IWL_FW_INI_REGION_PAGING, &IWL_FW_INI_REGION_CSR, * &IWL_FW_INI_REGION_DRAM_IMR and &IWL_FW_INI_REGION_PCI_IOSF_CONFIG * &IWL_FW_INI_REGION_DBGI_SRAM, &FW_TLV_DEBUG_REGION_TYPE_DBGI_SRAM, + * &IWL_FW_INI_REGION_PERIPHERY_SNPS_DPHYIP, + * @dev_addr_range: device address range configuration. Used by + * &IWL_FW_INI_REGION_PERIPHERY_MAC_RANGE and + * &IWL_FW_INI_REGION_PERIPHERY_PHY_RANGE * @fifos: fifos configuration. Used by &IWL_FW_INI_REGION_TXF and * &IWL_FW_INI_REGION_RXF * @err_table: error table configuration. Used by @@ -158,6 +186,7 @@ u8 name[IWL_FW_INI_MAX_NAME]; union { struct iwl_fw_ini_region_dev_addr dev_addr; + struct iwl_fw_ini_region_dev_addr_range dev_addr_range; struct iwl_fw_ini_region_fifos fifos; struct iwl_fw_ini_region_err_table err_table; struct iwl_fw_ini_region_internal_buffer internal_buffer; @@ -363,6 +392,9 @@ * @IWL_FW_INI_REGION_PCI_IOSF_CONFIG: PCI/IOSF config * @IWL_FW_INI_REGION_SPECIAL_DEVICE_MEMORY: special device memory * @IWL_FW_INI_REGION_DBGI_SRAM: periphery registers of DBGI SRAM + * @IWL_FW_INI_REGION_PERIPHERY_MAC_RANGE: a range of periphery registers of MAC + * @IWL_FW_INI_REGION_PERIPHERY_PHY_RANGE: a range of periphery registers of PHY + * @IWL_FW_INI_REGION_PERIPHERY_SNPS_DPHYIP: periphery registers of SNPS DPHYIP * @IWL_FW_INI_REGION_NUM: number of region types */ enum iwl_fw_ini_region_type { @@ -385,6 +417,9 @@ IWL_FW_INI_REGION_PCI_IOSF_CONFIG, IWL_FW_INI_REGION_SPECIAL_DEVICE_MEMORY, IWL_FW_INI_REGION_DBGI_SRAM, + IWL_FW_INI_REGION_PERIPHERY_MAC_RANGE, + IWL_FW_INI_REGION_PERIPHERY_PHY_RANGE, + IWL_FW_INI_REGION_PERIPHERY_SNPS_DPHYIP, IWL_FW_INI_REGION_NUM }; /* FW_TLV_DEBUG_REGION_TYPE_API_E */ diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/api/dhc.h backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/api/dhc.h --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/api/dhc.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/api/dhc.h 2023-10-04 04:18:43.000000000 +0800 @@ -62,7 +62,7 @@ struct iwl_dhc_cmd { __le32 length; __le32 index_and_mask; - __le32 data[0]; + __le32 data[]; } __packed; /* DHC_CMD_API_S */ /** diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/api/mac-cfg.h backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/api/mac-cfg.h --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/api/mac-cfg.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/api/mac-cfg.h 2023-10-04 04:18:43.000000000 +0800 @@ -1,6 +1,6 @@ /* SPDX-License-Identifier: GPL-2.0 OR BSD-3-Clause */ /* - * Copyright (C) 2012-2014, 2018-2019, 2021-2022 Intel Corporation + * Copyright (C) 2012-2014, 2018-2019, 2021-2023 Intel Corporation * Copyright (C) 2013-2015 Intel Mobile Communications GmbH * Copyright (C) 2016-2017 Intel Deutschland GmbH */ @@ -58,6 +58,14 @@ */ STA_DISABLE_TX_CMD = 0xD, /** + * @ROC_CMD: &struct iwl_roc_req + */ + ROC_CMD = 0xE, + /** + * @ROC_NOTIF: &struct iwl_roc_notif + */ + ROC_NOTIF = 0xF8, + /** * @SESSION_PROTECTION_NOTIF: &struct iwl_mvm_session_prot_notif */ SESSION_PROTECTION_NOTIF = 0xFB, @@ -159,7 +167,7 @@ #define CS_ERR_TX_BLOCK_TIMER_EXPIRED BIT(3) /** - * struct iwl_channel_switch_error_notif - Channel switch error notification + * struct iwl_channel_switch_error_notif_v1 - Channel switch error notification * * @mac_id: the mac for which the ucode sends the notification for * @csa_err_mask: mask of channel switch error that can occur @@ -231,11 +239,12 @@ * struct iwl_mac_client_data - configuration data for client MAC context * * @is_assoc: 1 for associated state, 0 otherwise - * @esr_transition_timeout: the timeout required by the AP for the eSR transition. + * @esr_transition_timeout: the timeout required by the AP for the + * eSR transition. * Available only from version 2 of the command. - * This values comes from the EMLSR transition delay in the EML Capabilities - * subfield. - * @medium_sync_delay: the value as it appeasr in P802.11be_D2.2 Figure 9-1002j. + * This value comes from the EMLSR transition delay in the EML + * Capabilities subfield. + * @medium_sync_delay: the value as it appears in P802.11be_D2.2 Figure 9-1002j. * @assoc_id: unique ID assigned by the AP during association * @reserved1: alignment * @data_policy: see &enum iwl_mac_data_policy diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/api/mac.h backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/api/mac.h --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/api/mac.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/api/mac.h 2023-10-04 04:18:43.000000000 +0800 @@ -353,7 +353,7 @@ } __packed; /* NON_QOS_TX_COUNTER_GET_SET_API_S_VER_1 */ /** - * struct iwl_missed_beacons_notif - information on missed beacons + * struct iwl_missed_beacons_notif_ver_3 - information on missed beacons * ( MISSED_BEACONS_NOTIFICATION = 0xa2 ) * @mac_id: interface ID * @consec_missed_beacons_since_last_rx: number of consecutive missed diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/api/nan.h backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/api/nan.h --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/api/nan.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/api/nan.h 2023-10-04 04:18:43.000000000 +0800 @@ -1,7 +1,7 @@ /* SPDX-License-Identifier: GPL-2.0 OR BSD-3-Clause */ /* * Copyright (C) 2015-2017 Intel Deutschland GmbH - * Copyright (C) 2018, 2022 Intel Corporation + * Copyright (C) 2018, 2022-2023 Intel Corporation */ #ifndef __iwl_fw_api_nan_h__ #define __iwl_fw_api_nan_h__ @@ -251,7 +251,7 @@ u8 cipher_suite_id; __le16 security_ctx_len; __le16 sdea_ctrl; - u8 data[0]; + u8 data[]; } __packed; /* NAN_DISCO_FUNC_FIXED_CMD_API_S_VER_2 */ /** @@ -264,7 +264,7 @@ struct iwl_nan_add_func_cmd { struct iwl_nan_add_func_common cmn; u8 reserved[2]; - u8 data[0]; + u8 data[]; } __packed; /* NAN_DISCO_FUNC_FIXED_CMD_API_S_VER_1 */ enum iwl_nan_add_func_resp_status { @@ -340,7 +340,7 @@ u8 peer_instance; u8 service_info_len; __le32 attrs_len; - u8 buf[0]; + u8 buf[]; } __packed; /* NAN_DISCO_EVENT_NTFY_API_S_VER_1 */ /** @@ -355,7 +355,7 @@ u8 type; u8 reserved; __le16 len; - u8 buf[0]; + u8 buf[]; } __packed; /* NAN_DISCO_SEC_CTXT_ID_API_S_VER_1 */ /** @@ -384,7 +384,7 @@ __le16 sec_ctxt_len; u8 cipher_suite_ids; u8 sdea_update_indicator; - u8 buf[0]; + u8 buf[]; } __packed; /* NAN_DISCO_INFO_API_S_VER_1 */ /** @@ -404,7 +404,7 @@ __le16 reserved1; __le32 match_len; __le32 avail_attrs_len; - u8 buf[0]; + u8 buf[]; } __packed; /* NAN_DISCO_EVENT_NTFY_API_S_VER_2 */ /* NAN function termination reasons */ diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/api/nvm-reg.h backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/api/nvm-reg.h --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/api/nvm-reg.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/api/nvm-reg.h 2023-10-04 04:18:43.000000000 +0800 @@ -21,8 +21,9 @@ * &struct iwl_lari_config_change_cmd_v2, * &struct iwl_lari_config_change_cmd_v3, * &struct iwl_lari_config_change_cmd_v4, - * &struct iwl_lari_config_change_cmd_v5 or - * &struct iwl_lari_config_change_cmd_v6 + * &struct iwl_lari_config_change_cmd_v5, + * &struct iwl_lari_config_change_cmd_v6 or + * &struct iwl_lari_config_change_cmd_v7 */ LARI_CONFIG_CHANGE = 0x1, @@ -44,6 +45,11 @@ SAR_OFFSET_MAPPING_TABLE_CMD = 0x4, /** + * @UATS_TABLE_CMD: &struct iwl_uats_table_cmd + */ + UATS_TABLE_CMD = 0x5, + + /** * @PNVM_INIT_COMPLETE_NTFY: &struct iwl_pnvm_init_complete_ntfy */ PNVM_INIT_COMPLETE_NTFY = 0xFE, @@ -603,6 +609,45 @@ } __packed; /* LARI_CHANGE_CONF_CMD_S_VER_6 */ /** + * struct iwl_lari_config_change_cmd_v7 - change LARI configuration + * This structure is used also for lari cmd version 8. + * @config_bitmap: Bitmap of the config commands. Each bit will trigger a + * different predefined FW config operation. + * @oem_uhb_allow_bitmap: Bitmap of UHB enabled MCC sets. + * @oem_11ax_allow_bitmap: Bitmap of 11ax allowed MCCs. There are two bits + * per country, one to indicate whether to override and the other to + * indicate the value to use. + * @oem_unii4_allow_bitmap: Bitmap of unii4 allowed MCCs.There are two bits + * per country, one to indicate whether to override and the other to + * indicate allow/disallow unii4 channels. + * @chan_state_active_bitmap: Bitmap to enable different bands per country + * or region. + * Each bit represents a country or region, and a band to activate + * according to the BIOS definitions. + * For LARI cmd version 7 - bits 0:3 are supported. + * For LARI cmd version 8 - bits 0:4 are supported. + * @force_disable_channels_bitmap: Bitmap of disabled bands/channels. + * Each bit represents a set of channels in a specific band that should be + * disabled + * @edt_bitmap: Bitmap of energy detection threshold table. + * Disable/enable the EDT optimization method for different band. + */ +struct iwl_lari_config_change_cmd_v7 { + __le32 config_bitmap; + __le32 oem_uhb_allow_bitmap; + __le32 oem_11ax_allow_bitmap; + __le32 oem_unii4_allow_bitmap; + __le32 chan_state_active_bitmap; + __le32 force_disable_channels_bitmap; + __le32 edt_bitmap; +} __packed; +/* LARI_CHANGE_CONF_CMD_S_VER_7 */ +/* LARI_CHANGE_CONF_CMD_S_VER_8 */ + +/* Activate UNII-1 (5.2GHz) for World Wide */ +#define ACTIVATE_5G2_IN_WW_MASK BIT(4) + +/** * struct iwl_pnvm_init_complete_ntfy - PNVM initialization complete * @status: PNVM image loading status */ @@ -610,4 +655,17 @@ __le32 status; } __packed; /* PNVM_INIT_COMPLETE_NTFY_S_VER_1 */ +#define UATS_TABLE_ROW_SIZE 26 +#define UATS_TABLE_COL_SIZE 13 + +/** + * struct iwl_uats_table_cmd - struct for UATS_TABLE_CMD + * @offset_map: mapping a mcc to UHB AP type support (UATS) allowed + * @reserved: reserved + */ +struct iwl_uats_table_cmd { + u8 offset_map[UATS_TABLE_ROW_SIZE][UATS_TABLE_COL_SIZE]; + __le16 reserved; +} __packed; /* UATS_TABLE_CMD_S_VER_1 */ + #endif /* __iwl_fw_api_nvm_reg_h__ */ diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/api/phy-ctxt.h backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/api/phy-ctxt.h --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/api/phy-ctxt.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/api/phy-ctxt.h 2023-10-04 04:18:43.000000000 +0800 @@ -1,6 +1,6 @@ /* SPDX-License-Identifier: GPL-2.0 OR BSD-3-Clause */ /* - * Copyright (C) 2012-2014, 2018, 2020-2022 Intel Corporation + * Copyright (C) 2012-2014, 2018, 2020-2023 Intel Corporation * Copyright (C) 2013-2015 Intel Mobile Communications GmbH * Copyright (C) 2016-2017 Intel Deutschland GmbH */ @@ -25,8 +25,8 @@ * For legacy set bit means upper channel, otherwise lower. * For VHT - bit-2 marks if the control is lower/upper relative to center-freq * bits-1:0 mark the distance from the center freq. for 20Mhz, offset is 0. - * center_freq * For EHT - bit-3 is used for extended distance + * center_freq * | * 40Mhz |____|____| * 80Mhz |____|____|____|____| diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/api/rx.h backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/api/rx.h --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/api/rx.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/api/rx.h 2023-10-04 04:18:43.000000000 +0800 @@ -1,6 +1,6 @@ /* SPDX-License-Identifier: GPL-2.0 OR BSD-3-Clause */ /* - * Copyright (C) 2012-2014, 2018-2022 Intel Corporation + * Copyright (C) 2012-2014, 2018-2023 Intel Corporation * Copyright (C) 2013-2015 Intel Mobile Communications GmbH * Copyright (C) 2015-2017 Intel Deutschland GmbH */ @@ -372,7 +372,7 @@ IWL_RX_PHY_DATA1_EHT_RU_ALLOC_B1_B7 = 0x0000fe00, }; -/* goes into Metadata DW 7 */ +/* goes into Metadata DW 7 (Qu) or 8 (So or higher) */ enum iwl_rx_phy_he_data2 { /* info type: HE MU-EXT */ /* the a1/a2/... is what the PHY/firmware calls the values */ @@ -388,7 +388,7 @@ IWL_RX_PHY_DATA2_HE_TB_EXT_SPTL_REUSE4 = 0x0000f000, }; -/* goes into Metadata DW 8 */ +/* goes into Metadata DW 8 (Qu) or 7 (So or higher) */ enum iwl_rx_phy_he_data3 { /* info type: HE MU-EXT */ IWL_RX_PHY_DATA3_HE_MU_EXT_CH1_RU1 = 0x000000ff, /* c1 */ @@ -409,10 +409,9 @@ IWL_RX_PHY_DATA4_HE_MU_EXT_PREAMBLE_PUNC_TYPE_MASK = 0x0600, }; -/* goes into Metadata DW 7 */ +/* goes into Metadata DW 8 (Qu has no EHT) */ enum iwl_rx_phy_eht_data2 { /* info type: EHT-MU-EXT */ - /* OFDM_RX_VECTOR_COMMON_RU_ALLOC_0_OUT */ IWL_RX_PHY_DATA2_EHT_MU_EXT_RU_ALLOC_A1 = 0x000001ff, IWL_RX_PHY_DATA2_EHT_MU_EXT_RU_ALLOC_A2 = 0x0003fe00, IWL_RX_PHY_DATA2_EHT_MU_EXT_RU_ALLOC_B1 = 0x07fc0000, @@ -421,11 +420,10 @@ IWL_RX_PHY_DATA2_EHT_TB_EXT_TRIG_SIGA1 = 0xffffffff, }; -/* goes into Metadata DW 8 */ +/* goes into Metadata DW 7 (Qu has no EHT) */ enum iwl_rx_phy_eht_data3 { + /* note: low 8 bits cannot be used */ /* info type: EHT-MU-EXT */ - /* OFDM_RX_VECTOR_COMMON_RU_ALLOC_1_OUT */ - IWL_RX_PHY_DATA3_EHT_MU_EXT_RU_ALLOC_B2 = 0x000001ff, IWL_RX_PHY_DATA3_EHT_MU_EXT_RU_ALLOC_C1 = 0x0003fe00, IWL_RX_PHY_DATA3_EHT_MU_EXT_RU_ALLOC_C2 = 0x07fc0000, }; @@ -433,10 +431,10 @@ /* goes into Metadata DW 4 */ enum iwl_rx_phy_eht_data4 { /* info type: EHT-MU-EXT */ - /* OFDM_RX_VECTOR_COMMON_RU_ALLOC_2_OUT */ IWL_RX_PHY_DATA4_EHT_MU_EXT_RU_ALLOC_D1 = 0x000001ff, IWL_RX_PHY_DATA4_EHT_MU_EXT_RU_ALLOC_D2 = 0x0003fe00, IWL_RX_PHY_DATA4_EHT_MU_EXT_SIGB_MCS = 0x000c0000, + IWL_RX_PHY_DATA4_EHT_MU_EXT_RU_ALLOC_B2 = 0x1ff00000, }; /* goes into Metadata DW 16 */ diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/api/stats.h backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/api/stats.h --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/api/stats.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/api/stats.h 2023-10-04 04:18:43.000000000 +0800 @@ -1,12 +1,13 @@ /* SPDX-License-Identifier: GPL-2.0 OR BSD-3-Clause */ /* - * Copyright (C) 2012-2014, 2018, 2020 - 2021 Intel Corporation + * Copyright (C) 2012-2014, 2018, 2020 - 2021, 2023 Intel Corporation * Copyright (C) 2013-2015 Intel Mobile Communications GmbH * Copyright (C) 2016-2017 Intel Deutschland GmbH */ #ifndef __iwl_fw_api_stats_h__ #define __iwl_fw_api_stats_h__ #include "mac.h" +#include "mac-cfg.h" struct mvm_statistics_dbg { __le32 burst_check; @@ -412,6 +413,49 @@ #define MAX_BCAST_FILTER_NUM 8 /** + * enum iwl_statistics_notify_type_id - type_id used in system statistics + * command + * @IWL_STATS_NTFY_TYPE_ID_OPER: request legacy statistics + * @IWL_STATS_NTFY_TYPE_ID_OPER_PART1: request operational part1 statistics + * @IWL_STATS_NTFY_TYPE_ID_OPER_PART2: request operational part2 statistics + * @IWL_STATS_NTFY_TYPE_ID_OPER_PART3: request operational part3 statistics + * @IWL_STATS_NTFY_TYPE_ID_OPER_PART4: request operational part4 statistics + */ +enum iwl_statistics_notify_type_id { + IWL_STATS_NTFY_TYPE_ID_OPER = BIT(0), + IWL_STATS_NTFY_TYPE_ID_OPER_PART1 = BIT(1), + IWL_STATS_NTFY_TYPE_ID_OPER_PART2 = BIT(2), + IWL_STATS_NTFY_TYPE_ID_OPER_PART3 = BIT(3), + IWL_STATS_NTFY_TYPE_ID_OPER_PART4 = BIT(4), +}; + +/** + * enum iwl_statistics_cfg_flags - cfg_mask used in system statistics command + * @IWL_STATS_CFG_FLG_DISABLE_NTFY_MSK: 0 for enable, 1 for disable + * @IWL_STATS_CFG_FLG_ON_DEMAND_NTFY_MSK: 0 for periodic, 1 for on-demand + * @IWL_STATS_CFG_FLG_RESET_MSK: 0 for reset statistics after + * sending the notification, 1 for do not reset statistics after sending + * the notification + */ +enum iwl_statistics_cfg_flags { + IWL_STATS_CFG_FLG_DISABLE_NTFY_MSK = BIT(0), + IWL_STATS_CFG_FLG_ON_DEMAND_NTFY_MSK = BIT(1), + IWL_STATS_CFG_FLG_RESET_MSK = BIT(2), +}; + +/** + * struct iwl_system_statistics_cmd - system statistics command + * @cfg_mask: configuration mask, &enum iwl_statistics_cfg_flags + * @config_time_sec: time in sec for periodic notification + * @type_id_mask: type_id masks, &enum iwl_statistics_notify_type_id + */ +struct iwl_system_statistics_cmd { + __le32 cfg_mask; + __le32 config_time_sec; + __le32 type_id_mask; +} __packed; /* STATISTICS_FW_CMD_API_S_VER_1 */ + +/** * enum iwl_fw_statistics_type * * @FW_STATISTICS_OPERATIONAL: operational statistics @@ -447,7 +491,49 @@ }; /* STATISTICS_NTFY_HDR_API_S_VER_1 */ /** - * struct iwl_statistics_ntfy_per_mac + * struct iwl_stats_ntfy_per_link + * + * @beacon_filter_average_energy: Average energy [-dBm] of the 2 + * antennas. + * @air_time: air time + * @beacon_counter: all beacons (both filtered and not filtered) + * @beacon_average_energy: Average energy [-dBm] of all beacons + * (both filtered and not filtered) + * @beacon_rssi_a: beacon RSSI on antenna A + * @beacon_rssi_b: beacon RSSI on antenna B + * @rx_bytes: RX byte count + */ +struct iwl_stats_ntfy_per_link { + __le32 beacon_filter_average_energy; + __le32 air_time; + __le32 beacon_counter; + __le32 beacon_average_energy; + __le32 beacon_rssi_a; + __le32 beacon_rssi_b; + __le32 rx_bytes; +} __packed; /* STATISTICS_NTFY_PER_LINK_API_S_VER_1 */ + +/** + * struct iwl_stats_ntfy_part1_per_link + * + * @rx_time: rx time + * @tx_time: tx time + * @rx_action: action frames handled by FW + * @tx_action: action frames generated and transmitted by FW + * @cca_defers: cca defer count + * @beacon_filtered: filtered out beacons + */ +struct iwl_stats_ntfy_part1_per_link { + __le64 rx_time; + __le64 tx_time; + __le32 rx_action; + __le32 tx_action; + __le32 cca_defers; + __le32 beacon_filtered; +} __packed; /* STATISTICS_FW_NTFY_OPERATIONAL_PART1_PER_LINK_API_S_VER_1 */ + +/** + * struct iwl_stats_ntfy_per_mac * * @beacon_filter_average_energy: Average energy [-dBm] of the 2 * antennas. @@ -459,7 +545,7 @@ * @beacon_rssi_b: beacon RSSI on antenna B * @rx_bytes: RX byte count */ -struct iwl_statistics_ntfy_per_mac { +struct iwl_stats_ntfy_per_mac { __le32 beacon_filter_average_energy; __le32 air_time; __le32 beacon_counter; @@ -470,7 +556,7 @@ } __packed; /* STATISTICS_NTFY_PER_MAC_API_S_VER_1 */ #define IWL_STATS_MAX_BW_INDEX 5 -/** struct iwl_statistics_ntfy_per_phy +/** struct iwl_stats_ntfy_per_phy * @channel_load: channel load * @channel_load_by_us: device contribution to MCLM * @channel_load_not_by_us: other devices' contribution to MCLM @@ -485,7 +571,7 @@ * per channel BW. note BACK counted as 1 * @last_tx_ch_width_indx: last txed frame channel width index */ -struct iwl_statistics_ntfy_per_phy { +struct iwl_stats_ntfy_per_phy { __le32 channel_load; __le32 channel_load_by_us; __le32 channel_load_not_by_us; @@ -499,23 +585,62 @@ } __packed; /* STATISTICS_NTFY_PER_PHY_API_S_VER_1 */ /** - * struct iwl_statistics_ntfy_per_sta + * struct iwl_stats_ntfy_per_sta * * @average_energy: in fact it is minus the energy.. */ -struct iwl_statistics_ntfy_per_sta { +struct iwl_stats_ntfy_per_sta { __le32 average_energy; } __packed; /* STATISTICS_NTFY_PER_STA_API_S_VER_1 */ -#define IWL_STATS_MAX_PHY_OPERTINAL 3 +#define IWL_STATS_MAX_PHY_OPERATIONAL 3 +#define IWL_STATS_MAX_FW_LINKS (IWL_MVM_FW_MAX_LINK_ID + 1) + +/** + * struct iwl_system_statistics_notif_oper + * + * @time_stamp: time when the notification is sent from firmware + * @per_link: per link statistics, &struct iwl_stats_ntfy_per_link + * @per_phy: per phy statistics, &struct iwl_stats_ntfy_per_phy + * @per_sta: per sta statistics, &struct iwl_stats_ntfy_per_sta + */ +struct iwl_system_statistics_notif_oper { + __le32 time_stamp; + struct iwl_stats_ntfy_per_link per_link[IWL_STATS_MAX_FW_LINKS]; + struct iwl_stats_ntfy_per_phy per_phy[IWL_STATS_MAX_PHY_OPERATIONAL]; + struct iwl_stats_ntfy_per_sta per_sta[IWL_MVM_STATION_COUNT_MAX]; +} __packed; /* STATISTICS_FW_NTFY_OPERATIONAL_API_S_VER_3 */ + +/** + * struct iwl_system_statistics_part1_notif_oper + * + * @time_stamp: time when the notification is sent from firmware + * @per_link: per link statistics &struct iwl_stats_ntfy_part1_per_link + * @per_phy_crc_error_stats: per phy crc error statistics + */ +struct iwl_system_statistics_part1_notif_oper { + __le32 time_stamp; + struct iwl_stats_ntfy_part1_per_link per_link[IWL_STATS_MAX_FW_LINKS]; + __le32 per_phy_crc_error_stats[IWL_STATS_MAX_PHY_OPERATIONAL]; +} __packed; /* STATISTICS_FW_NTFY_OPERATIONAL_PART1_API_S_VER_4 */ + +/** + * struct iwl_system_statistics_end_notif + * + * @time_stamp: time when the notification is sent from firmware + */ +struct iwl_system_statistics_end_notif { + __le32 time_stamp; +} __packed; /* STATISTICS_FW_NTFY_END_API_S_VER_1 */ + /** * struct iwl_statistics_operational_ntfy * * @hdr: general statistics header * @flags: bitmap of possible notification structures - * @per_mac_stats: per mac statistics, &struct iwl_statistics_ntfy_per_mac - * @per_phy_stats: per phy statistics, &struct iwl_statistics_ntfy_per_phy - * @per_sta_stats: per sta statistics, &struct iwl_statistics_ntfy_per_sta + * @per_mac: per mac statistics, &struct iwl_stats_ntfy_per_mac + * @per_phy: per phy statistics, &struct iwl_stats_ntfy_per_phy + * @per_sta: per sta statistics, &struct iwl_stats_ntfy_per_sta * @rx_time: rx time * @tx_time: usec the radio is transmitting. * @on_time_rf: The total time in usec the RF is awake. @@ -524,9 +649,9 @@ struct iwl_statistics_operational_ntfy { struct iwl_statistics_ntfy_hdr hdr; __le32 flags; - struct iwl_statistics_ntfy_per_mac per_mac_stats[MAC_INDEX_AUX]; - struct iwl_statistics_ntfy_per_phy per_phy_stats[IWL_STATS_MAX_PHY_OPERTINAL]; - struct iwl_statistics_ntfy_per_sta per_sta_stats[IWL_MVM_STATION_COUNT_MAX]; + struct iwl_stats_ntfy_per_mac per_mac[MAC_INDEX_AUX]; + struct iwl_stats_ntfy_per_phy per_phy[IWL_STATS_MAX_PHY_OPERATIONAL]; + struct iwl_stats_ntfy_per_sta per_sta[IWL_MVM_STATION_COUNT_MAX]; __le64 rx_time; __le64 tx_time; __le64 on_time_rf; diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/api/testing.h backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/api/testing.h --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/api/testing.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/api/testing.h 2023-10-04 04:18:43.000000000 +0800 @@ -1,6 +1,7 @@ /* SPDX-License-Identifier: GPL-2.0 OR BSD-3-Clause */ /* * Copyright (C) 2017 Intel Deutschland GmbH + * Copyright (C) 2023 Intel Corporation */ #ifndef __iwl_fw_api_testing_h__ #define __iwl_fw_api_testing_h__ @@ -56,7 +57,7 @@ __le16 reserved; u8 nonce[FIPS_MAX_NONCE_LEN]; u8 reserved2[3]; - u8 payload[0]; + u8 payload[]; } __packed; /* AES_SEC_TEST_VECTOR_HDR_API_S_VER_1 */ /** @@ -78,7 +79,7 @@ */ struct iwl_fips_test_resp { __le32 len; - u8 payload[0]; + u8 payload[]; } __packed; /* AES_SEC_TEST_VECTOR_RESP_API_S_VER_1 */ #endif diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/api/time-event.h backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/api/time-event.h --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/api/time-event.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/api/time-event.h 2023-10-04 04:18:43.000000000 +0800 @@ -1,6 +1,6 @@ /* SPDX-License-Identifier: GPL-2.0 OR BSD-3-Clause */ /* - * Copyright (C) 2012-2014, 2018-2020, 2022 Intel Corporation + * Copyright (C) 2012-2014, 2018-2020, 2022-2023 Intel Corporation * Copyright (C) 2013-2015 Intel Mobile Communications GmbH * Copyright (C) 2016-2017 Intel Deutschland GmbH */ @@ -335,6 +335,63 @@ __le32 status; } __packed; /* HOT_SPOT_RSP_API_S_VER_1 */ +/* + * Activity types for the ROC command + * @ROC_ACTIVITY_HOTSPOT: ROC for hs20 activity + * @ROC_ACTIVITY_P2P_DISC: ROC for p2p discoverability activity + * @ROC_ACTIVITY_P2P_TXRX: ROC for p2p action frames activity + */ +enum iwl_roc_activity { + ROC_ACTIVITY_HOTSPOT, + ROC_ACTIVITY_P2P_DISC, + ROC_ACTIVITY_P2P_TXRX, + ROC_NUM_ACTIVITIES +}; /* ROC_ACTIVITY_API_E_VER_1 */ + +/* + * ROC command + * + * Command requests the firmware to remain on a channel for a certain duration. + * + * ( MAC_CONF_GROUP 0x3, ROC_CMD 0xE ) + * + * @action: action to perform, see &enum iwl_ctxt_action + * @activity: type of activity, see &enum iwl_roc_activity + * @sta_id: station id, resumed during "Remain On Channel" activity. + * @channel_info: &struct iwl_fw_channel_info + * @node_addr: node MAC address for Rx filtering + * @reserved: align to a dword + * @max_delay: max delay the ROC can start in TU + * @duration: remain on channel duration in TU + */ +struct iwl_roc_req { + __le32 action; + __le32 activity; + __le32 sta_id; + struct iwl_fw_channel_info channel_info; + u8 node_addr[ETH_ALEN]; + __le16 reserved; + __le32 max_delay; + __le32 duration; +} __packed; /* ROC_CMD_API_S_VER_3 */ + +/* + * ROC notification + * + * Notification when ROC startes and when ROC ended. + * + * ( MAC_CONF_GROUP 0x3, ROC_NOTIF 0xf8 ) + * + * @status: true if ROC succeeded to start + * @start_end: true if ROC started, false if ROC ended + * @activity: notification to which activity - &enum iwl_roc_activity + */ +struct iwl_roc_notif { + __le32 success; + __le32 started; + __le32 activity; +} __packed; /* ROC_NOTIF_API_S_VER_1 */ + /** * enum iwl_mvm_session_prot_conf_id - session protection's configurations * @SESSION_PROTECT_CONF_ASSOC: Start a session protection for association. @@ -375,8 +432,8 @@ /** * struct iwl_mvm_session_prot_cmd - configure a session protection - * @id_and_color: the id and color of the mac for which this session protection - * is sent + * @id_and_color: the id and color of the link (or mac, for command version 1) + * for which this session protection is sent * @action: can be either FW_CTXT_ACTION_ADD or FW_CTXT_ACTION_REMOVE, * see &enum iwl_ctxt_action * @conf_id: see &enum iwl_mvm_session_prot_conf_id @@ -397,11 +454,15 @@ __le32 duration_tu; __le32 repetition_count; __le32 interval; -} __packed; /* SESSION_PROTECTION_CMD_API_S_VER_1 */ +} __packed; +/* SESSION_PROTECTION_CMD_API_S_VER_1 and + * SESSION_PROTECTION_CMD_API_S_VER_2 + */ /** * struct iwl_mvm_session_prot_notif - session protection started / ended - * @mac_id: the mac id for which the session protection started / ended + * @mac_link_id: the mac id (or link id, for notif ver > 2) for which the + * session protection started / ended * @status: 1 means success, 0 means failure * @start: 1 means the session protection started, 0 means it ended * @conf_id: see &enum iwl_mvm_session_prot_conf_id @@ -410,10 +471,13 @@ * and end even the firmware could not schedule it. */ struct iwl_mvm_session_prot_notif { - __le32 mac_id; + __le32 mac_link_id; __le32 status; __le32 start; __le32 conf_id; -} __packed; /* SESSION_PROTECTION_NOTIFICATION_API_S_VER_2 */ +} __packed; +/* SESSION_PROTECTION_NOTIFICATION_API_S_VER_2 and + * SESSION_PROTECTION_NOTIFICATION_API_S_VER_3 + */ #endif /* __iwl_fw_api_time_event_h__ */ diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/dbg.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/dbg.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/dbg.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/dbg.c 2023-10-04 04:18:43.000000000 +0800 @@ -1023,22 +1023,18 @@ struct iwl_fwrt_dump_data *dump_data; }; -static int -iwl_dump_ini_prph_mac_iter(struct iwl_fw_runtime *fwrt, - struct iwl_dump_ini_region_data *reg_data, - void *range_ptr, u32 range_len, int idx) +static int iwl_dump_ini_prph_mac_iter_common(struct iwl_fw_runtime *fwrt, + void *range_ptr, u32 addr, + __le32 size) { - struct iwl_fw_ini_region_tlv *reg = (void *)reg_data->reg_tlv->data; struct iwl_fw_ini_error_dump_range *range = range_ptr; __le32 *val = range->data; u32 prph_val; - u32 addr = le32_to_cpu(reg->addrs[idx]) + - le32_to_cpu(reg->dev_addr.offset); int i; range->internal_base_addr = cpu_to_le32(addr); - range->range_data_size = reg->dev_addr.size; - for (i = 0; i < le32_to_cpu(reg->dev_addr.size); i += 4) { + range->range_data_size = size; + for (i = 0; i < le32_to_cpu(size); i += 4) { prph_val = iwl_read_prph(fwrt->trans, addr + i); if (iwl_trans_is_hw_error_value(prph_val)) return -EBUSY; @@ -1049,38 +1045,61 @@ } static int -iwl_dump_ini_prph_phy_iter(struct iwl_fw_runtime *fwrt, +iwl_dump_ini_prph_mac_iter(struct iwl_fw_runtime *fwrt, struct iwl_dump_ini_region_data *reg_data, void *range_ptr, u32 range_len, int idx) { struct iwl_fw_ini_region_tlv *reg = (void *)reg_data->reg_tlv->data; + u32 addr = le32_to_cpu(reg->addrs[idx]) + + le32_to_cpu(reg->dev_addr.offset); + + return iwl_dump_ini_prph_mac_iter_common(fwrt, range_ptr, addr, + reg->dev_addr.size); +} + +static int +iwl_dump_ini_prph_mac_block_iter(struct iwl_fw_runtime *fwrt, + struct iwl_dump_ini_region_data *reg_data, + void *range_ptr, u32 range_len, int idx) +{ + struct iwl_fw_ini_region_tlv *reg = (void *)reg_data->reg_tlv->data; + struct iwl_fw_ini_addr_size *pairs = (void *)reg->addrs; + u32 addr = le32_to_cpu(reg->dev_addr_range.offset) + + le32_to_cpu(pairs[idx].addr); + + return iwl_dump_ini_prph_mac_iter_common(fwrt, range_ptr, addr, + pairs[idx].size); +} + +static int iwl_dump_ini_prph_phy_iter_common(struct iwl_fw_runtime *fwrt, + void *range_ptr, u32 addr, + __le32 size, __le32 offset) +{ struct iwl_fw_ini_error_dump_range *range = range_ptr; __le32 *val = range->data; u32 indirect_wr_addr = WMAL_INDRCT_RD_CMD1; u32 indirect_rd_addr = WMAL_MRSPF_1; u32 prph_val; - u32 addr = le32_to_cpu(reg->addrs[idx]); u32 dphy_state; u32 dphy_addr; int i; range->internal_base_addr = cpu_to_le32(addr); - range->range_data_size = reg->dev_addr.size; + range->range_data_size = size; if (fwrt->trans->trans_cfg->device_family < IWL_DEVICE_FAMILY_AX210) indirect_wr_addr = WMAL_INDRCT_CMD1; - indirect_wr_addr += le32_to_cpu(reg->dev_addr.offset); - indirect_rd_addr += le32_to_cpu(reg->dev_addr.offset); + indirect_wr_addr += le32_to_cpu(offset); + indirect_rd_addr += le32_to_cpu(offset); if (!iwl_trans_grab_nic_access(fwrt->trans)) return -EBUSY; - dphy_addr = (reg->dev_addr.offset) ? WFPM_LMAC2_PS_CTL_RW : - WFPM_LMAC1_PS_CTL_RW; + dphy_addr = (offset) ? WFPM_LMAC2_PS_CTL_RW : WFPM_LMAC1_PS_CTL_RW; dphy_state = iwl_read_umac_prph_no_grab(fwrt->trans, dphy_addr); - for (i = 0; i < le32_to_cpu(reg->dev_addr.size); i += 4) { + for (i = 0; i < le32_to_cpu(size); i += 4) { if (dphy_state == HBUS_TIMEOUT || (dphy_state & WFPM_PS_CTL_RW_PHYRF_PD_FSM_CURSTATE_MSK) != WFPM_PHYRF_STATE_ON) { @@ -1099,6 +1118,33 @@ return sizeof(*range) + le32_to_cpu(range->range_data_size); } +static int +iwl_dump_ini_prph_phy_iter(struct iwl_fw_runtime *fwrt, + struct iwl_dump_ini_region_data *reg_data, + void *range_ptr, u32 range_len, int idx) +{ + struct iwl_fw_ini_region_tlv *reg = (void *)reg_data->reg_tlv->data; + u32 addr = le32_to_cpu(reg->addrs[idx]); + + return iwl_dump_ini_prph_phy_iter_common(fwrt, range_ptr, addr, + reg->dev_addr.size, + reg->dev_addr.offset); +} + +static int +iwl_dump_ini_prph_phy_block_iter(struct iwl_fw_runtime *fwrt, + struct iwl_dump_ini_region_data *reg_data, + void *range_ptr, u32 range_len, int idx) +{ + struct iwl_fw_ini_region_tlv *reg = (void *)reg_data->reg_tlv->data; + struct iwl_fw_ini_addr_size *pairs = (void *)reg->addrs; + u32 addr = le32_to_cpu(pairs[idx].addr); + + return iwl_dump_ini_prph_phy_iter_common(fwrt, range_ptr, addr, + pairs[idx].size, + reg->dev_addr_range.offset); +} + static int iwl_dump_ini_csr_iter(struct iwl_fw_runtime *fwrt, struct iwl_dump_ini_region_data *reg_data, void *range_ptr, u32 range_len, int idx) @@ -1372,6 +1418,53 @@ return sizeof(*range) + le32_to_cpu(range->range_data_size); } +static int +iwl_dump_ini_prph_snps_dphyip_iter(struct iwl_fw_runtime *fwrt, + struct iwl_dump_ini_region_data *reg_data, + void *range_ptr, u32 range_len, int idx) +{ + struct iwl_fw_ini_region_tlv *reg = (void *)reg_data->reg_tlv->data; + struct iwl_fw_ini_error_dump_range *range = range_ptr; + __le32 *val = range->data; + __le32 offset = reg->dev_addr.offset; + u32 indirect_rd_wr_addr = DPHYIP_INDIRECT; + u32 addr = le32_to_cpu(reg->addrs[idx]); + u32 dphy_state, dphy_addr, prph_val; + int i; + + range->internal_base_addr = cpu_to_le32(addr); + range->range_data_size = reg->dev_addr.size; + + if (!iwl_trans_grab_nic_access(fwrt->trans)) + return -EBUSY; + + indirect_rd_wr_addr += le32_to_cpu(offset); + + dphy_addr = offset ? WFPM_LMAC2_PS_CTL_RW : WFPM_LMAC1_PS_CTL_RW; + dphy_state = iwl_read_umac_prph_no_grab(fwrt->trans, dphy_addr); + + for (i = 0; i < le32_to_cpu(reg->dev_addr.size); i += 4) { + if (dphy_state == HBUS_TIMEOUT || + (dphy_state & WFPM_PS_CTL_RW_PHYRF_PD_FSM_CURSTATE_MSK) != + WFPM_PHYRF_STATE_ON) { + *val++ = cpu_to_le32(WFPM_DPHY_OFF); + continue; + } + + iwl_write_prph_no_grab(fwrt->trans, indirect_rd_wr_addr, + addr + i); + /* wait a bit for value to be ready in register */ + udelay(1); + prph_val = iwl_read_prph_no_grab(fwrt->trans, + indirect_rd_wr_addr); + *val++ = cpu_to_le32((prph_val & DPHYIP_INDIRECT_RD_MSK) >> + DPHYIP_INDIRECT_RD_SHIFT); + } + + iwl_trans_release_nic_access(fwrt->trans); + return sizeof(*range) + le32_to_cpu(range->range_data_size); +} + struct iwl_ini_rxf_data { u32 fifo_num; u32 size; @@ -1785,6 +1878,16 @@ return iwl_tlv_array_len(reg_data->reg_tlv, reg, addrs); } +static u32 +iwl_dump_ini_mem_block_ranges(struct iwl_fw_runtime *fwrt, + struct iwl_dump_ini_region_data *reg_data) +{ + struct iwl_fw_ini_region_tlv *reg = (void *)reg_data->reg_tlv->data; + size_t size = sizeof(struct iwl_fw_ini_addr_size); + + return iwl_tlv_array_len_with_size(reg_data->reg_tlv, reg, size); +} + static u32 iwl_dump_ini_paging_ranges(struct iwl_fw_runtime *fwrt, struct iwl_dump_ini_region_data *reg_data) { @@ -1871,6 +1974,25 @@ } static u32 +iwl_dump_ini_mem_block_get_size(struct iwl_fw_runtime *fwrt, + struct iwl_dump_ini_region_data *reg_data) +{ + struct iwl_fw_ini_region_tlv *reg = (void *)reg_data->reg_tlv->data; + struct iwl_fw_ini_addr_size *pairs = (void *)reg->addrs; + u32 ranges = iwl_dump_ini_mem_block_ranges(fwrt, reg_data); + u32 size = sizeof(struct iwl_fw_ini_error_dump); + int range; + + if (!ranges) + return 0; + + for (range = 0; range < ranges; range++) + size += le32_to_cpu(pairs[range].size); + + return size + ranges * sizeof(struct iwl_fw_ini_error_dump_range); +} + +static u32 iwl_dump_ini_paging_get_size(struct iwl_fw_runtime *fwrt, struct iwl_dump_ini_region_data *reg_data) { @@ -2419,6 +2541,18 @@ .fill_mem_hdr = iwl_dump_ini_mem_fill_header, .fill_range = iwl_dump_ini_prph_phy_iter, }, + [IWL_FW_INI_REGION_PERIPHERY_MAC_RANGE] = { + .get_num_of_ranges = iwl_dump_ini_mem_block_ranges, + .get_size = iwl_dump_ini_mem_block_get_size, + .fill_mem_hdr = iwl_dump_ini_mem_fill_header, + .fill_range = iwl_dump_ini_prph_mac_block_iter, + }, + [IWL_FW_INI_REGION_PERIPHERY_PHY_RANGE] = { + .get_num_of_ranges = iwl_dump_ini_mem_block_ranges, + .get_size = iwl_dump_ini_mem_block_get_size, + .fill_mem_hdr = iwl_dump_ini_mem_fill_header, + .fill_range = iwl_dump_ini_prph_phy_block_iter, + }, [IWL_FW_INI_REGION_PERIPHERY_AUX] = {}, [IWL_FW_INI_REGION_PAGING] = { .fill_mem_hdr = iwl_dump_ini_mem_fill_header, @@ -2456,6 +2590,12 @@ .fill_mem_hdr = iwl_dump_ini_mon_dbgi_fill_header, .fill_range = iwl_dump_ini_dbgi_sram_iter, }, + [IWL_FW_INI_REGION_PERIPHERY_SNPS_DPHYIP] = { + .get_num_of_ranges = iwl_dump_ini_mem_ranges, + .get_size = iwl_dump_ini_mem_get_size, + .fill_mem_hdr = iwl_dump_ini_mem_fill_header, + .fill_range = iwl_dump_ini_prph_snps_dphyip_iter, + }, }; static u32 iwl_dump_ini_trigger(struct iwl_fw_runtime *fwrt, @@ -2498,7 +2638,9 @@ if (reg_type >= ARRAY_SIZE(iwl_dump_ini_region_ops)) continue; - if (reg_type == IWL_FW_INI_REGION_PERIPHERY_PHY && + if ((reg_type == IWL_FW_INI_REGION_PERIPHERY_PHY || + reg_type == IWL_FW_INI_REGION_PERIPHERY_PHY_RANGE || + reg_type == IWL_FW_INI_REGION_PERIPHERY_SNPS_DPHYIP) && tp_id != IWL_FW_INI_TIME_POINT_FW_ASSERT) { IWL_WARN(fwrt, "WRT: trying to collect phy prph at time point: %d, skipping\n", @@ -3288,3 +3430,13 @@ iwl_trans_send_cmd(fwrt->trans, &hcmd); } IWL_EXPORT_SYMBOL(iwl_fw_disable_dbg_asserts); + +void iwl_fw_dbg_clear_monitor_buf(struct iwl_fw_runtime *fwrt) +{ + struct iwl_fw_dbg_params params = {0}; + + iwl_fw_dbg_stop_sync(fwrt); + iwl_dbg_tlv_init_cfg(fwrt); + iwl_fw_dbg_stop_restart_recording(fwrt, ¶ms, false); +} +IWL_EXPORT_SYMBOL(iwl_fw_dbg_clear_monitor_buf); diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/dbg.h backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/dbg.h --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/dbg.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/dbg.h 2023-10-04 04:18:43.000000000 +0800 @@ -328,6 +328,7 @@ u32 timepoint_data); void iwl_fw_disable_dbg_asserts(struct iwl_fw_runtime *fwrt); +void iwl_fw_dbg_clear_monitor_buf(struct iwl_fw_runtime *fwrt); #ifdef CPTCFG_IWLWIFI_SUPPORT_DEBUG_OVERRIDES #define IWL_FW_CHECK_FAILED(_obj, _fmt, ...) \ diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/debugfs.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/debugfs.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/debugfs.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/debugfs.c 2023-10-04 04:18:43.000000000 +0800 @@ -142,7 +142,11 @@ event_cfg.enabled_severities = cpu_to_le32(enabled_severities); - ret = iwl_trans_send_cmd(fwrt->trans, &hcmd); + if (fwrt->ops && fwrt->ops->send_hcmd) + ret = fwrt->ops->send_hcmd(fwrt->ops_ctx, &hcmd); + else + ret = -EPERM; + IWL_INFO(fwrt, "sent host event cfg with enabled_severities: %u, ret: %d\n", enabled_severities, ret); diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/dump.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/dump.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/dump.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/dump.c 2023-10-04 04:18:43.000000000 +0800 @@ -513,10 +513,12 @@ if (!iwl_trans_grab_nic_access(fwrt->trans)) return; - for (count = 0; count < fwrt->trans->dbg.num_pc; count++, pc_data++) + for (count = 0; count < fwrt->trans->dbg.num_pc; + count++, pc_data++) IWL_ERR(fwrt, "%s: 0x%x\n", pc_data->pc_name, - iwl_read_prph_no_grab(fwrt->trans, pc_data->pc_address)); + iwl_read_prph_no_grab(fwrt->trans, + pc_data->pc_address)); iwl_trans_release_nic_access(fwrt->trans); } diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/error-dump.h backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/error-dump.h --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/error-dump.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/error-dump.h 2023-10-04 04:18:43.000000000 +0800 @@ -1,6 +1,6 @@ /* SPDX-License-Identifier: GPL-2.0 OR BSD-3-Clause */ /* - * Copyright (C) 2014, 2018-2022 Intel Corporation + * Copyright (C) 2014, 2018-2023 Intel Corporation * Copyright (C) 2014-2015 Intel Mobile Communications GmbH * Copyright (C) 2016-2017 Intel Deutschland GmbH */ @@ -310,9 +310,9 @@ struct iwl_fw_ini_error_dump_range { __le32 range_data_size; union { - __le32 internal_base_addr; - __le64 dram_base_addr; - __le32 page_num; + __le32 internal_base_addr __packed; + __le64 dram_base_addr __packed; + __le32 page_num __packed; struct iwl_fw_ini_fifo_hdr fifo_hdr; struct iwl_cmd_header fw_pkt_hdr; }; diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/file.h backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/file.h --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/file.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/file.h 2023-10-04 04:18:43.000000000 +0800 @@ -20,7 +20,7 @@ __le32 init_size; /* bytes of init code */ __le32 init_data_size; /* bytes of init data */ __le32 boot_size; /* bytes of bootstrap code */ - u8 data[0]; /* in same order as sizes */ + u8 data[]; /* in same order as sizes */ } v1; struct { __le32 build; /* build number */ @@ -29,7 +29,7 @@ __le32 init_size; /* bytes of init code */ __le32 init_data_size; /* bytes of init data */ __le32 boot_size; /* bytes of bootstrap code */ - u8 data[0]; /* in same order as sizes */ + u8 data[]; /* in same order as sizes */ } v2; } u; }; @@ -248,6 +248,8 @@ * version tables. * @IWL_UCODE_TLV_API_REDUCED_SCAN_CONFIG: This ucode supports v3 of * SCAN_CONFIG_DB_CMD_API_S. + * @IWL_UCODE_TLV_API_NO_HOST_DISABLE_TX: Firmware offloaded the station disable tx + * logic. * * @NUM_IWL_UCODE_TLV_API: number of bits used */ @@ -286,6 +288,7 @@ IWL_UCODE_TLV_API_ADWELL_HB_DEF_N_AP = (__force iwl_ucode_tlv_api_t)57, IWL_UCODE_TLV_API_SCAN_EXT_CHAN_VER = (__force iwl_ucode_tlv_api_t)58, IWL_UCODE_TLV_API_BAND_IN_RX_DATA = (__force iwl_ucode_tlv_api_t)59, + IWL_UCODE_TLV_API_NO_HOST_DISABLE_TX = (__force iwl_ucode_tlv_api_t)66, NUM_IWL_UCODE_TLV_API /* @@ -333,6 +336,7 @@ * is supported. * @IWL_UCODE_TLV_CAPA_BT_COEX_RRC: supports BT Coex RRC * @IWL_UCODE_TLV_CAPA_GSCAN_SUPPORT: supports gscan (no longer used) + * @IWL_UCODE_TLV_CAPA_FRAGMENTED_PNVM_IMG: supports fragmented PNVM image * @IWL_UCODE_TLV_CAPA_NAN_SUPPORT: supports NAN * @IWL_UCODE_TLV_CAPA_UMAC_UPLOAD: supports upload mode in umac (1=supported, * 0=no support) @@ -421,7 +425,7 @@ /* set 1 */ IWL_UCODE_TLV_CAPA_FRAGMENTED_PNVM_IMG = (__force iwl_ucode_tlv_capa_t)32, - //place for paging + /* place for paging */ IWL_UCODE_TLV_CAPA_NAN_SUPPORT = (__force iwl_ucode_tlv_capa_t)34, IWL_UCODE_TLV_CAPA_UMAC_UPLOAD = (__force iwl_ucode_tlv_capa_t)35, IWL_UCODE_TLV_CAPA_SOC_LATENCY_SUPPORT = (__force iwl_ucode_tlv_capa_t)37, @@ -1000,4 +1004,6 @@ _iwl_tlv_array_len((_tlv_ptr), sizeof(*(_struct_ptr)), \ sizeof(_struct_ptr->_memb[0])) +#define iwl_tlv_array_len_with_size(_tlv_ptr, _struct_ptr, _size) \ + _iwl_tlv_array_len((_tlv_ptr), sizeof(*(_struct_ptr)), _size) #endif /* __iwl_fw_file_h__ */ diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/pnvm.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/pnvm.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/pnvm.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/pnvm.c 2023-10-04 04:18:43.000000000 +0800 @@ -12,6 +12,8 @@ #include "fw/api/alive.h" #include "fw/uefi.h" +#define IWL_PNVM_REDUCED_CAP_BIT BIT(25) + struct iwl_pnvm_section { __le32 offset; const u8 data[]; @@ -173,6 +175,7 @@ while (len >= sizeof(*tlv)) { u32 tlv_len, tlv_type; + u32 rf_type; len -= sizeof(*tlv); tlv = (const void *)data; @@ -201,6 +204,16 @@ data += sizeof(*tlv) + ALIGN(tlv_len, 4); len -= ALIGN(tlv_len, 4); + trans->reduced_cap_sku = false; + rf_type = CSR_HW_RFID_TYPE(trans->hw_rf_id); + if ((trans->sku_id[0] & IWL_PNVM_REDUCED_CAP_BIT) && + rf_type == IWL_CFG_RF_TYPE_FM) + trans->reduced_cap_sku = true; + + IWL_DEBUG_FW(trans, + "Reduced SKU device %d\n", + trans->reduced_cap_sku); + if (trans->sku_id[0] == le32_to_cpu(sku_id->data[0]) && trans->sku_id[1] == le32_to_cpu(sku_id->data[1]) && trans->sku_id[2] == le32_to_cpu(sku_id->data[2])) { diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/runtime.h backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/runtime.h --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/runtime.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/runtime.h 2023-10-04 04:18:43.000000000 +0800 @@ -97,6 +97,8 @@ * @cur_fw_img: current firmware image, must be maintained by * the driver by calling &iwl_fw_set_current_image() * @dump: debug dump data + * @uats_enabled: VLP or AFC AP is enabled + * @uats_table: AP type table */ struct iwl_fw_runtime { struct iwl_trans *trans; @@ -170,6 +172,8 @@ struct iwl_sar_offset_mapping_cmd sgom_table; bool sgom_enabled; u8 reduced_power_flags; + bool uats_enabled; + struct iwl_uats_table_cmd uats_table; #endif }; diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/uefi.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/uefi.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/uefi.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/uefi.c 2023-10-04 04:18:43.000000000 +0800 @@ -394,5 +394,55 @@ kfree(data); } IWL_EXPORT_SYMBOL(iwl_uefi_get_sgom_table); + +static int iwl_uefi_uats_parse(struct uefi_cnv_wlan_uats_data *uats_data, + struct iwl_fw_runtime *fwrt) +{ + if (uats_data->revision != 1) + return -EINVAL; + + memcpy(fwrt->uats_table.offset_map, uats_data->offset_map, + sizeof(fwrt->uats_table.offset_map)); + return 0; +} + +int iwl_uefi_get_uats_table(struct iwl_trans *trans, + struct iwl_fw_runtime *fwrt) +{ + struct uefi_cnv_wlan_uats_data *data; + unsigned long package_size; + int ret; + + data = iwl_uefi_get_variable(IWL_UEFI_UATS_NAME, &IWL_EFI_VAR_GUID, + &package_size); + if (IS_ERR(data)) { + IWL_DEBUG_FW(trans, + "UATS UEFI variable not found 0x%lx\n", + PTR_ERR(data)); + return -EINVAL; + } + + if (package_size < sizeof(*data)) { + IWL_DEBUG_FW(trans, + "Invalid UATS table UEFI variable len (%lu)\n", + package_size); + kfree(data); + return -EINVAL; + } + + IWL_DEBUG_FW(trans, "Read UATS from UEFI with size %lu\n", + package_size); + + ret = iwl_uefi_uats_parse(data, fwrt); + if (ret < 0) { + IWL_DEBUG_FW(trans, "Cannot read UATS table. rev is invalid\n"); + kfree(data); + return ret; + } + + kfree(data); + return 0; +} +IWL_EXPORT_SYMBOL(iwl_uefi_get_uats_table); #endif /* CONFIG_ACPI */ #endif /* >= 5.4 */ diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/uefi.h backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/uefi.h --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/fw/uefi.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/fw/uefi.h 2023-10-04 04:18:43.000000000 +0800 @@ -9,8 +9,10 @@ #define IWL_UEFI_REDUCED_POWER_NAME L"UefiCnvWlanReducedPower" #define IWL_UEFI_SGOM_NAME L"UefiCnvWlanSarGeoOffsetMapping" #define IWL_UEFI_STEP_NAME L"UefiCnvCommonSTEP" +#define IWL_UEFI_UATS_NAME L"CnvUefiWlanUATS" #define IWL_SGOM_MAP_SIZE 339 +#define IWL_UATS_MAP_SIZE 339 struct pnvm_sku_package { u8 rev; @@ -25,6 +27,11 @@ u8 offset_map[IWL_SGOM_MAP_SIZE - 1]; } __packed; +struct uefi_cnv_wlan_uats_data { + u8 revision; + u8 offset_map[IWL_UATS_MAP_SIZE - 1]; +} __packed; + struct uefi_cnv_common_step_data { u8 revision; u8 step_mode; @@ -82,10 +89,20 @@ #if defined(CONFIG_EFI) && defined(CONFIG_ACPI) && LINUX_VERSION_IS_GEQ(5,4,0) void iwl_uefi_get_sgom_table(struct iwl_trans *trans, struct iwl_fw_runtime *fwrt); +int iwl_uefi_get_uats_table(struct iwl_trans *trans, + struct iwl_fw_runtime *fwrt); #else static inline void iwl_uefi_get_sgom_table(struct iwl_trans *trans, struct iwl_fw_runtime *fwrt) { } + +static inline +int iwl_uefi_get_uats_table(struct iwl_trans *trans, + struct iwl_fw_runtime *fwrt) +{ + return 0; +} + #endif #endif /* __iwl_fw_uefi__ */ diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/iwl-config.h backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/iwl-config.h --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/iwl-config.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/iwl-config.h 2023-10-04 04:18:43.000000000 +0800 @@ -86,10 +86,7 @@ #define IWL_DEFAULT_MAX_TX_POWER 22 #define IWL_TX_CSUM_NETIF_FLAGS (NETIF_F_IPV6_CSUM | NETIF_F_IP_CSUM |\ NETIF_F_TSO | NETIF_F_TSO6) -#define IWL_TX_CSUM_NETIF_FLAGS_BZ (NETIF_F_HW_CSUM | NETIF_F_TSO | NETIF_F_TSO6) -#define IWL_CSUM_NETIF_FLAGS_MASK (IWL_TX_CSUM_NETIF_FLAGS | \ - IWL_TX_CSUM_NETIF_FLAGS_BZ | \ - NETIF_F_RXCSUM) +#define IWL_CSUM_NETIF_FLAGS_MASK (IWL_TX_CSUM_NETIF_FLAGS | NETIF_F_RXCSUM) /* Antenna presence definitions */ #define ANT_NONE 0x0 @@ -446,6 +443,9 @@ #define IWL_CFG_NO_160 0x1 #define IWL_CFG_160 0x0 +#define IWL_CFG_NO_320 0x1 +#define IWL_CFG_320 0x0 + #define IWL_CFG_CORES_BT 0x0 #define IWL_CFG_CORES_BT_GNSS 0x5 @@ -530,6 +530,7 @@ extern const char iwl_ax231_name[]; extern const char iwl_ax411_name[]; extern const char iwl_bz_name[]; +extern const char iwl_mtp_name[]; extern const char iwl_sc_name[]; #if IS_ENABLED(CPTCFG_IWLMVM) extern const struct iwl_ht_params iwl_22000_ht_params; diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/iwl-csr.h backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/iwl-csr.h --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/iwl-csr.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/iwl-csr.h 2023-10-04 04:18:43.000000000 +0800 @@ -1,6 +1,6 @@ /* SPDX-License-Identifier: GPL-2.0 OR BSD-3-Clause */ /* - * Copyright (C) 2005-2014, 2018-2022 Intel Corporation + * Copyright (C) 2005-2014, 2018-2023 Intel Corporation * Copyright (C) 2013-2014 Intel Mobile Communications GmbH * Copyright (C) 2016 Intel Deutschland GmbH */ @@ -313,6 +313,7 @@ SILICON_C_STEP, SILICON_D_STEP, SILICON_E_STEP, + SILICON_TC_STEP = 0xe, SILICON_Z_STEP = 0xf, }; diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/iwl-dbg-cfg.h backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/iwl-dbg-cfg.h --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/iwl-dbg-cfg.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/iwl-dbg-cfg.h 2023-10-04 04:18:43.000000000 +0800 @@ -189,6 +189,7 @@ IWL_DBG_CFG(u8, MVM_MIN_BEACON_INTERVAL_TU) IWL_DBG_CFG_RANGE(u8, MVM_ADAPTIVE_DWELL_NUM_APS_OVERRIDE, 0, 10) IWL_DBG_CFG_DEF(int, eml_capa_override, -1) + IWL_DBG_CFG(bool, MVM_AUTO_EML_ENABLE) #endif /* CPTCFG_IWLMVM */ #ifdef CPTCFG_IWLWIFI_DEVICE_TESTMODE IWL_DBG_CFG_NODEF(u32, dnt_out_mode) diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/iwl-dbg-tlv.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/iwl-dbg-tlv.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/iwl-dbg-tlv.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/iwl-dbg-tlv.c 2023-10-04 04:18:43.000000000 +0800 @@ -1289,7 +1289,7 @@ return 0; } -static void iwl_dbg_tlv_init_cfg(struct iwl_fw_runtime *fwrt) +void iwl_dbg_tlv_init_cfg(struct iwl_fw_runtime *fwrt) { enum iwl_fw_ini_buffer_location *ini_dest = &fwrt->trans->dbg.ini_dest; int ret, i; @@ -1307,8 +1307,7 @@ iwl_dbg_tlv_gen_active_trig_list(fwrt, tp); } } else if (*ini_dest != IWL_FW_INI_LOCATION_DRAM_PATH) { - /* - * For DRAM, go through the loop below to clear all the buffers + /* For DRAM, go through the loop below to clear all the buffers * properly on restart, otherwise garbage may be left there and * leak into new debug dumps. */ diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/iwl-dbg-tlv.h backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/iwl-dbg-tlv.h --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/iwl-dbg-tlv.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/iwl-dbg-tlv.h 2023-10-04 04:18:43.000000000 +0800 @@ -57,6 +57,7 @@ enum iwl_fw_ini_time_point tp_id, union iwl_dbg_tlv_tp_data *tp_data, bool sync); +void iwl_dbg_tlv_init_cfg(struct iwl_fw_runtime *fwrt); static inline void iwl_dbg_tlv_time_point(struct iwl_fw_runtime *fwrt, enum iwl_fw_ini_time_point tp_id, diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/iwl-devtrace.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/iwl-devtrace.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/iwl-devtrace.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/iwl-devtrace.c 2023-10-04 04:18:43.000000000 +0800 @@ -2,7 +2,7 @@ /****************************************************************************** * * Copyright(c) 2009 - 2014 Intel Corporation. All rights reserved. - * Copyright (C) 2018 Intel Corporation + * Copyright (C) 2018, 2023 Intel Corporation *****************************************************************************/ #include @@ -20,4 +20,17 @@ EXPORT_TRACEPOINT_SYMBOL(iwlwifi_dev_ucode_event); EXPORT_TRACEPOINT_SYMBOL(iwlwifi_dev_ucode_cont_event); EXPORT_TRACEPOINT_SYMBOL(iwlwifi_dev_ucode_wrap_event); +#else +#include "iwl-devtrace.h" #endif /* __CHECKER__ */ + +void __trace_iwlwifi_dev_rx(struct iwl_trans *trans, void *pkt, size_t len) +{ + size_t hdr_offset = 0, trace_len; + + trace_len = iwl_rx_trace_len(trans, pkt, len, &hdr_offset); + trace_iwlwifi_dev_rx(trans->dev, pkt, len, trace_len, hdr_offset); + + if (trace_len < len) + trace_iwlwifi_dev_rx_data(trans->dev, pkt, len, trace_len); +} diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/iwl-devtrace-data.h backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/iwl-devtrace-data.h --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/iwl-devtrace-data.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/iwl-devtrace-data.h 2023-10-04 04:18:43.000000000 +0800 @@ -3,7 +3,7 @@ * * Copyright(c) 2009 - 2014 Intel Corporation. All rights reserved. * Copyright(c) 2015 Intel Deutschland GmbH - * Copyright(c) 2018 - 2019 Intel Corporation + * Copyright(c) 2018 - 2019, 2023 Intel Corporation *****************************************************************************/ #if !defined(__IWLWIFI_DEVICE_TRACE_DATA) || defined(TRACE_HEADER_MULTI_READ) @@ -36,20 +36,17 @@ TRACE_EVENT(iwlwifi_dev_rx_data, TP_PROTO(const struct device *dev, - const struct iwl_trans *trans, - void *rxbuf, size_t len), - TP_ARGS(dev, trans, rxbuf, len), + void *rxbuf, size_t len, size_t start), + TP_ARGS(dev, rxbuf, len, start), TP_STRUCT__entry( DEV_ENTRY - __dynamic_array(u8, data, - len - iwl_rx_trace_len(trans, rxbuf, len, NULL)) + __dynamic_array(u8, data, len - start) ), TP_fast_assign( - size_t offs = iwl_rx_trace_len(trans, rxbuf, len, NULL); DEV_ASSIGN; - if (offs < len) + if (start < len) memcpy(__get_dynamic_array(data), - ((u8 *)rxbuf) + offs, len - offs); + ((u8 *)rxbuf) + start, len - start); ), TP_printk("[%s] RX frame data", __get_str(dev)) ); diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/iwl-devtrace.h backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/iwl-devtrace.h --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/iwl-devtrace.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/iwl-devtrace.h 2023-10-04 04:18:43.000000000 +0800 @@ -3,17 +3,19 @@ * * Copyright(c) 2009 - 2014 Intel Corporation. All rights reserved. * Copyright(C) 2016 Intel Deutschland GmbH - * Copyright(c) 2018 Intel Corporation + * Copyright(c) 2018, 2023 Intel Corporation *****************************************************************************/ #ifndef __IWLWIFI_DEVICE_TRACE +#define __IWLWIFI_DEVICE_TRACE #include #include #include +#include #include "iwl-trans.h" -#if !defined(__IWLWIFI_DEVICE_TRACE) static inline bool iwl_trace_data(struct sk_buff *skb) { + struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb); struct ieee80211_hdr *hdr = (void *)skb->data; __le16 fc = hdr->frame_control; int offs = 24; /* start with normal header length */ @@ -21,6 +23,10 @@ if (!ieee80211_is_data(fc)) return false; + /* If upper layers wanted TX status it's an important frame */ + if (info->flags & IEEE80211_TX_CTL_REQ_TX_STATUS) + return false; + /* Try to determine if the frame is EAPOL. This might have false * positives (if there's no RFC 1042 header and we compare to some * payload instead) but since we're only doing tracing that's not @@ -64,14 +70,10 @@ return sizeof(__le32) + sizeof(*cmd) + trans->rx_mpdu_cmd_hdr_size + ieee80211_hdrlen(hdr->frame_control); } -#endif - -#define __IWLWIFI_DEVICE_TRACE #include #include - #if !defined(CPTCFG_IWLWIFI_DEVICE_TRACING) || defined(__CHECKER__) #undef TRACE_EVENT #define TRACE_EVENT(name, proto, ...) \ @@ -92,4 +94,20 @@ #include "iwl-devtrace-data.h" #include "iwl-devtrace-iwlwifi.h" +#ifdef CPTCFG_IWLWIFI_DEVICE_TRACING +DECLARE_TRACEPOINT(iwlwifi_dev_rx); +DECLARE_TRACEPOINT(iwlwifi_dev_rx_data); +#endif + +void __trace_iwlwifi_dev_rx(struct iwl_trans *trans, void *pkt, size_t len); + +static inline void maybe_trace_iwlwifi_dev_rx(struct iwl_trans *trans, + void *pkt, size_t len) +{ +#ifdef CPTCFG_IWLWIFI_DEVICE_TRACING + if (tracepoint_enabled(iwlwifi_dev_rx) || + tracepoint_enabled(iwlwifi_dev_rx_data)) + __trace_iwlwifi_dev_rx(trans, pkt, len); +#endif +} #endif /* __IWLWIFI_DEVICE_TRACE */ diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/iwl-devtrace-iwlwifi.h backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/iwl-devtrace-iwlwifi.h --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/iwl-devtrace-iwlwifi.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/iwl-devtrace-iwlwifi.h 2023-10-04 04:18:43.000000000 +0800 @@ -4,7 +4,7 @@ * Copyright(c) 2009 - 2014 Intel Corporation. All rights reserved. * Copyright(c) 2015 Intel Mobile Communications GmbH * Copyright(c) 2016 - 2017 Intel Deutschland GmbH - * Copyright(c) 2018 Intel Corporation + * Copyright(c) 2018, 2023 Intel Corporation *****************************************************************************/ #if !defined(__IWLWIFI_DEVICE_TRACE_IWLWIFI) || defined(TRACE_HEADER_MULTI_READ) @@ -50,23 +50,20 @@ ); TRACE_EVENT(iwlwifi_dev_rx, - TP_PROTO(const struct device *dev, const struct iwl_trans *trans, - struct iwl_rx_packet *pkt, size_t len), - TP_ARGS(dev, trans, pkt, len), + TP_PROTO(const struct device *dev, + struct iwl_rx_packet *pkt, size_t len, size_t trace_len, + size_t hdr_offset), + TP_ARGS(dev, pkt, len, trace_len, hdr_offset), TP_STRUCT__entry( DEV_ENTRY __field(u16, cmd) __field(u8, hdr_offset) - __dynamic_array(u8, rxbuf, - iwl_rx_trace_len(trans, pkt, len, NULL)) + __dynamic_array(u8, rxbuf, trace_len) ), TP_fast_assign( - size_t hdr_offset = 0; - DEV_ASSIGN; __entry->cmd = WIDE_ID(pkt->hdr.group_id, pkt->hdr.cmd); - memcpy(__get_dynamic_array(rxbuf), pkt, - iwl_rx_trace_len(trans, pkt, len, &hdr_offset)); + memcpy(__get_dynamic_array(rxbuf), pkt, trace_len); __entry->hdr_offset = hdr_offset; ), TP_printk("[%s] RX cmd %#.2x", diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/iwl-dnt-cfg.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/iwl-dnt-cfg.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/iwl-dnt-cfg.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/iwl-dnt-cfg.c 2023-10-04 04:18:43.000000000 +0800 @@ -1,6 +1,6 @@ // SPDX-License-Identifier: GPL-2.0 OR BSD-3-Clause /* - * Copyright (C) 2014, 2018 Intel Corporation + * Copyright (C) 2014, 2018, 2023 Intel Corporation * Copyright (C) 2014 Intel Mobile Communications GmbH * Copyright (C) 2016-2017 Intel Deutschland GmbH */ @@ -271,6 +271,8 @@ if (!dnt) return; + trans->tmdev->dnt = NULL; + #ifdef CPTCFG_IWLWIFI_DEBUGFS debugfs_remove_recursive(dnt->debugfs_entry); if (dnt->debugfs_counter) { diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/iwl-drv.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/iwl-drv.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/iwl-drv.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/iwl-drv.c 2023-10-04 04:18:43.000000000 +0800 @@ -373,6 +373,8 @@ { if (step == SILICON_Z_STEP) return 'z'; + if (step == SILICON_TC_STEP) + return 'a'; return 'a' + step; } @@ -389,6 +391,8 @@ mac_step = iwl_drv_get_step(trans->hw_rev_step); + rf_step = iwl_drv_get_step(CSR_HW_RFID_STEP(trans->hw_rf_id)); + switch (CSR_HW_RFID_TYPE(trans->hw_rf_id)) { case IWL_CFG_RF_TYPE_HR1: case IWL_CFG_RF_TYPE_HR2: @@ -407,7 +411,13 @@ rf = "fm"; break; case IWL_CFG_RF_TYPE_WH: - rf = "wh"; + if (SILICON_Z_STEP == + CSR_HW_RFID_STEP(trans->hw_rf_id)) { + rf = "whtc"; + rf_step = 'a'; + } else { + rf = "wh"; + } break; default: return "unknown-rf"; @@ -415,8 +425,6 @@ cdb = CSR_HW_RFID_IS_CDB(trans->hw_rf_id) ? "4" : ""; - rf_step = iwl_drv_get_step(CSR_HW_RFID_STEP(trans->hw_rf_id)); - scnprintf(buf, FW_NAME_PRE_BUFSIZE, "iwlwifi-%s-%c0-%s%s-%c0", trans->cfg->fw_name_mac, mac_step, diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/iwl-io.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/iwl-io.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/iwl-io.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/iwl-io.c 2023-10-04 04:18:43.000000000 +0800 @@ -1,6 +1,6 @@ // SPDX-License-Identifier: GPL-2.0 OR BSD-3-Clause /* - * Copyright (C) 2003-2014, 2018-2022 Intel Corporation + * Copyright (C) 2003-2014, 2018-2023 Intel Corporation * Copyright (C) 2015-2016 Intel Deutschland GmbH */ #include @@ -477,7 +477,8 @@ * device-internal resources is supported, e.g. iwl_write_prph() * and accesses to uCode SRAM. */ - err = iwl_poll_bit(trans, CSR_GP_CNTRL, poll_ready, poll_ready, 25000); + err = iwl_poll_bit(trans, CSR_GP_CNTRL, poll_ready, poll_ready, + 25000 * CPTCFG_IWL_TIMEOUT_FACTOR); if (err < 0) { IWL_DEBUG_INFO(trans, "Failed to wake NIC\n"); diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/iwl-nvm-parse.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/iwl-nvm-parse.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/iwl-nvm-parse.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/iwl-nvm-parse.c 2023-10-04 04:18:43.000000000 +0800 @@ -262,10 +262,9 @@ */ #define REG_CAPA_V2_RESP_VER 6 -/* -* API v4 for reg_capa_flags is relevant from version 8 and onwards of the -* MCC update command response. -*/ +/* API v4 for reg_capa_flags is relevant from version 8 and onwards of the + * MCC update command response. + */ #define REG_CAPA_V4_RESP_VER 8 /** @@ -674,7 +673,8 @@ IEEE80211_EHT_MAC_CAP0_EPCS_PRIO_ACCESS | IEEE80211_EHT_MAC_CAP0_OM_CONTROL | IEEE80211_EHT_MAC_CAP0_TRIG_TXOP_SHARING_MODE1 | - IEEE80211_EHT_MAC_CAP0_TRIG_TXOP_SHARING_MODE2, + IEEE80211_EHT_MAC_CAP0_TRIG_TXOP_SHARING_MODE2 | + IEEE80211_EHT_MAC_CAP0_SCS_TRAFFIC_DESC, .phy_cap_info[0] = IEEE80211_EHT_PHY_CAP0_242_TONE_RU_GT20MHZ | IEEE80211_EHT_PHY_CAP0_NDP_4_EHT_LFT_32_GI | @@ -1031,7 +1031,8 @@ IEEE80211_EHT_PHY_CAP3_NG_16_MU_FEEDBACK | IEEE80211_EHT_PHY_CAP3_CODEBOOK_4_2_SU_FDBK | IEEE80211_EHT_PHY_CAP3_CODEBOOK_7_5_MU_FDBK | - IEEE80211_EHT_PHY_CAP3_TRIG_MU_BF_PART_BW_FDBK); + IEEE80211_EHT_PHY_CAP3_TRIG_MU_BF_PART_BW_FDBK | + IEEE80211_EHT_PHY_CAP3_TRIG_CQI_FDBK); iftype_data->eht_cap.eht_cap_elem.phy_cap_info[4] &= ~(IEEE80211_EHT_PHY_CAP4_PART_BW_DL_MU_MIMO | IEEE80211_EHT_PHY_CAP4_POWER_BOOST_FACT_SUPP); @@ -1240,6 +1241,9 @@ IEEE80211_HE_PHY_CAP0_CHANNEL_WIDTH_SET_80PLUS80_MHZ_IN_5G | IEEE80211_HE_PHY_CAP0_CHANNEL_WIDTH_SET_RU_MAPPING_IN_5G); } + if (trans->no_160) + iftype_data->he_cap.he_cap_elem.phy_cap_info[0] &= + ~IEEE80211_HE_PHY_CAP0_CHANNEL_WIDTH_SET_160MHZ_IN_5G; IWL_COPY_BIN(he_mac_cap, he_cap.he_cap_elem.mac_cap_info); @@ -1293,12 +1297,22 @@ IWL_COPY_BIN(eht_mcs_320, eht_cap.eht_mcs_nss_supp.bw._320); } - if (trans->dbg_cfg.eht_disable_320 || sband->band != NL80211_BAND_6GHZ) { + if (trans->dbg_cfg.eht_disable_320 || + trans->reduced_cap_sku || + sband->band != NL80211_BAND_6GHZ) { memset(&iftype_data->eht_cap.eht_mcs_nss_supp.bw._320, 0, sizeof(iftype_data->eht_cap.eht_mcs_nss_supp.bw._320)); iftype_data->eht_cap.eht_cap_elem.phy_cap_info[0] &= ~IEEE80211_EHT_PHY_CAP0_320MHZ_IN_6GHZ; } + if (trans->reduced_cap_sku) { + iftype_data->eht_cap.eht_mcs_nss_supp.bw._80.rx_tx_mcs13_max_nss = 0; + iftype_data->eht_cap.eht_mcs_nss_supp.bw._160.rx_tx_mcs13_max_nss = 0; + iftype_data->eht_cap.eht_cap_elem.phy_cap_info[8] &= + ~IEEE80211_EHT_PHY_CAP8_RX_4096QAM_WIDER_BW_DL_OFDMA; + iftype_data->eht_cap.eht_cap_elem.phy_cap_info[2] &= + ~IEEE80211_EHT_PHY_CAP2_SOUNDING_DIM_320MHZ_MASK; + } } } @@ -1849,10 +1863,17 @@ /* Set the GO concurrent flag only in case that NO_IR is set. * Otherwise it is meaningless */ - if ((nvm_flags & NVM_CHANNEL_GO_CONCURRENT) && - (flags & NL80211_RRF_NO_IR)) - flags |= NL80211_RRF_GO_CONCURRENT; - + if ((nvm_flags & NVM_CHANNEL_GO_CONCURRENT)) { + if (flags & NL80211_RRF_NO_IR) + flags |= NL80211_RRF_GO_CONCURRENT; + if (flags & NL80211_RRF_DFS) { + flags |= NL80211_RRF_DFS_CONCURRENT; + /* Our device doesn't set active bit for DFS channels + * however, once marked as DFS no-ir is not needed. + */ + flags &= ~NL80211_RRF_NO_IR; + } + } /* * reg_capa is per regulatory domain so apply it for every channel */ @@ -2317,6 +2338,14 @@ "mac address from config file is invalid\n"); } #endif + + /* WA for wrong multicast MAC address */ + if ((CSR_HW_REV_TYPE(trans->hw_rev) == IWL_CFG_MAC_TYPE_GL) && + (CSR_HW_REV_STEP_DASH(trans->hw_rev) == SILICON_C_STEP) && + (CSR_HW_RFID_TYPE(trans->hw_rf_id) == IWL_CFG_RF_TYPE_FM) && + (CSR_HW_RFID_STEP(trans->hw_rf_id) == SILICON_C_STEP)) + nvm->hw_addr[0] &= ~BIT(0); + if (!is_valid_ether_addr(nvm->hw_addr)) { IWL_ERR(trans, "no valid mac address was found\n"); ret = -EINVAL; diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/iwl-op-mode.h backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/iwl-op-mode.h --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/iwl-op-mode.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/iwl-op-mode.h 2023-10-04 04:18:43.000000000 +0800 @@ -90,8 +90,6 @@ * received on the RSS queue(s). The queue parameter indicates which of the * RSS queues received this frame; it will always be non-zero. * This method must not sleep. - * @async_cb: called when an ASYNC command with CMD_WANT_ASYNC_CALLBACK set - * completes. Must be atomic. * @queue_full: notifies that a HW queue is full. * Must be atomic and called with BH disabled. * @queue_not_full: notifies that a HW queue is not full any more. @@ -122,8 +120,6 @@ struct iwl_rx_cmd_buffer *rxb); void (*rx_rss)(struct iwl_op_mode *op_mode, struct napi_struct *napi, struct iwl_rx_cmd_buffer *rxb, unsigned int queue); - void (*async_cb)(struct iwl_op_mode *op_mode, - const struct iwl_device_cmd *cmd); void (*queue_full)(struct iwl_op_mode *op_mode, int queue); void (*queue_not_full)(struct iwl_op_mode *op_mode, int queue); bool (*hw_rf_kill)(struct iwl_op_mode *op_mode, bool state); @@ -179,13 +175,6 @@ op_mode->ops->rx_rss(op_mode, napi, rxb, queue); } -static inline void iwl_op_mode_async_cb(struct iwl_op_mode *op_mode, - const struct iwl_device_cmd *cmd) -{ - if (op_mode->ops->async_cb) - op_mode->ops->async_cb(op_mode, cmd); -} - static inline void iwl_op_mode_queue_full(struct iwl_op_mode *op_mode, int queue) { diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/iwl-prph.h backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/iwl-prph.h --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/iwl-prph.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/iwl-prph.h 2023-10-04 04:18:43.000000000 +0800 @@ -350,8 +350,8 @@ #define RFIC_REG_RD 0xAD0470 #define WFPM_CTRL_REG 0xA03030 #define WFPM_OTP_CFG1_ADDR 0x00a03098 -#define WFPM_OTP_CFG1_IS_JACKET_BIT BIT(4) -#define WFPM_OTP_CFG1_IS_CDB_BIT BIT(5) +#define WFPM_OTP_CFG1_IS_JACKET_BIT BIT(5) +#define WFPM_OTP_CFG1_IS_CDB_BIT BIT(4) #define WFPM_OTP_BZ_BNJ_JACKET_BIT 5 #define WFPM_OTP_BZ_BNJ_CDB_BIT 4 #define WFPM_OTP_CFG1_IS_JACKET(_val) (((_val) & 0x00000020) >> WFPM_OTP_BZ_BNJ_JACKET_BIT) @@ -387,7 +387,7 @@ #define SB_CFG_OVERRIDE_ENABLE 0x8000 #define SB_CFG_BASE_OVERRIDE 0xA20000 #define SB_MODIFY_CFG_FLAG 0xA03088 -#define SB_CFG_RESIDES_IN_OTP_MASK 0x10 +#define SB_CFG_RESIDES_IN_ROM 0x80 #define SB_CPU_1_STATUS 0xA01E30 #define SB_CPU_2_STATUS 0xA01E34 #define UMAG_SB_CPU_1_STATUS 0xA038C0 @@ -422,14 +422,14 @@ * reserved: bits 12-18 * slave_exist: bit 19 * dash: bits 20-23 - * step: bits 24-26 - * flavor: bits 27-31 + * step: bits 24-27 + * flavor: bits 28-31 */ #define REG_CRF_ID_TYPE(val) (((val) & 0x00000FFF) >> 0) #define REG_CRF_ID_SLAVE(val) (((val) & 0x00080000) >> 19) #define REG_CRF_ID_DASH(val) (((val) & 0x00F00000) >> 20) -#define REG_CRF_ID_STEP(val) (((val) & 0x07000000) >> 24) -#define REG_CRF_ID_FLAVOR(val) (((val) & 0xF8000000) >> 27) +#define REG_CRF_ID_STEP(val) (((val) & 0x0F000000) >> 24) +#define REG_CRF_ID_FLAVOR(val) (((val) & 0xF0000000) >> 28) #define UREG_CHICK (0xA05C00) @@ -516,4 +516,8 @@ #define WFPM_LMAC2_PD_NOTIFICATION 0xA033CC #define WFPM_LMAC2_PD_RE_READ BIT(31) +#define DPHYIP_INDIRECT 0xA2D800 +#define DPHYIP_INDIRECT_RD_MSK 0xFF000000 +#define DPHYIP_INDIRECT_RD_SHIFT 24 + #endif /* __iwl_prph_h__ */ diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/iwl-tm-infc.h backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/iwl-tm-infc.h --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/iwl-tm-infc.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/iwl-tm-infc.h 2023-10-04 04:18:43.000000000 +0800 @@ -95,6 +95,12 @@ IWL_TM_USER_CMD_NOTIF_MPAPD_EXEC_DONE, IWL_TM_USER_CMD_NOTIF_DTS_MEASUREMENTS_XVT, IWL_TM_USER_CMD_NOTIF_STATISTICS, + IWL_TM_USER_CMD_NOTIF_STATS_OPER, + IWL_TM_USER_CMD_NOTIF_STATS_OPER_PART1, + IWL_TM_USER_CMD_NOTIF_STATS_OPER_PART2, + IWL_TM_USER_CMD_NOTIF_STATS_OPER_PART3, + IWL_TM_USER_CMD_NOTIF_STATS_OPER_PART4, + IWL_TM_USER_CMD_NOTIF_STATS_END, }; /* @@ -583,7 +589,7 @@ struct iwl_xvt_driver_command_req { __u32 command_id; __u32 max_out_length; - __u8 input_data[0]; + __u8 input_data[]; } __packed __aligned(4); /** @@ -595,7 +601,7 @@ struct iwl_xvt_driver_command_resp { __u32 command_id; __u32 length; - __u8 resp_data[0]; + __u8 resp_data[]; } __packed __aligned(4); /** @@ -874,7 +880,7 @@ */ struct iwl_xvt_fw_tlv_data_response { u32 bytes_len; - u8 data[0]; + u8 data[]; } __packed __aligned(4); /** diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/iwl-trans.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/iwl-trans.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/iwl-trans.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/iwl-trans.c 2023-10-04 04:18:43.000000000 +0800 @@ -172,10 +172,6 @@ return -EIO; } - if (WARN_ON((cmd->flags & CMD_WANT_ASYNC_CALLBACK) && - !(cmd->flags & CMD_ASYNC))) - return -EINVAL; - if (!(cmd->flags & CMD_ASYNC)) lock_map_acquire_read(&trans->sync_cmd_lockdep_map); diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/iwl-trans.h backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/iwl-trans.h --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/iwl-trans.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/iwl-trans.h 2023-10-04 04:18:43.000000000 +0800 @@ -120,8 +120,7 @@ * @CMD_WANT_SKB: Not valid with CMD_ASYNC. The caller needs the buffer of * the response. The caller needs to call iwl_free_resp when done. * @CMD_SEND_IN_RFKILL: Send the command even if the NIC is in RF-kill. - * @CMD_WANT_ASYNC_CALLBACK: the op_mode's async callback function must be - * called after this command completes. Valid only with CMD_ASYNC. + * @CMD_BLOCK_TXQS: Block TXQs while the comment is executing. * @CMD_SEND_IN_D3: Allow the command to be sent in D3 mode, relevant to * SUSPEND and RESUME commands. We are in D3 mode when we set * trans->system_pm_mode to IWL_PLAT_PM_MODE_D3. @@ -130,7 +129,7 @@ CMD_ASYNC = BIT(0), CMD_WANT_SKB = BIT(1), CMD_SEND_IN_RFKILL = BIT(2), - CMD_WANT_ASYNC_CALLBACK = BIT(3), + CMD_BLOCK_TXQS = BIT(3), CMD_SEND_IN_D3 = BIT(4), }; @@ -289,7 +288,7 @@ #define IWL_MGMT_TID 15 #define IWL_FRAME_LIMIT 64 #define IWL_MAX_RX_HW_QUEUES 16 -#define IWL_9000_MAX_RX_HW_QUEUES 6 +#define IWL_9000_MAX_RX_HW_QUEUES 1 /** * enum iwl_wowlan_status - WoWLAN image/device status @@ -545,11 +544,6 @@ * @wait_txq_empty: wait until specific tx queue is empty. May sleep. * @freeze_txq_timer: prevents the timer of the queue from firing until the * queue is set to awake. Must be atomic. - * @block_txq_ptrs: stop updating the write pointers of the Tx queues. Note - * that the transport needs to refcount the calls since this function - * will be called several times with block = true, and then the queues - * need to be unblocked only after the same number of calls with - * block = false. * @write8: write a u8 to a register at offset ofs from the BAR * @write32: write a u32 to a register at offset ofs from the BAR * @read32: read a u32 register at offset ofs from the BAR @@ -578,6 +572,8 @@ * @load_pnvm: save the pnvm data in DRAM * @set_pnvm: set the pnvm data in the prph scratch buffer, inside the * context info. + * @load_reduce_power: copy reduce power table to the corresponding DRAM memory + * @set_reduce_power: set reduce power table addresses in the sratch buffer * @interrupts: disable/enable interrupts to transport */ struct iwl_trans_ops { @@ -603,7 +599,7 @@ int (*tx)(struct iwl_trans *trans, struct sk_buff *skb, struct iwl_device_tx_cmd *dev_cmd, int queue); void (*reclaim)(struct iwl_trans *trans, int queue, int ssn, - struct sk_buff_head *skbs); + struct sk_buff_head *skbs, bool is_flush); void (*set_q_ptrs)(struct iwl_trans *trans, int queue, int ptr); @@ -627,7 +623,6 @@ int (*wait_txq_empty)(struct iwl_trans *trans, int queue); void (*freeze_txq_timer)(struct iwl_trans *trans, unsigned long txqs, bool freeze); - void (*block_txq_ptrs)(struct iwl_trans *trans, bool block); void (*write8)(struct iwl_trans *trans, u32 ofs, u8 val); void (*write32)(struct iwl_trans *trans, u32 ofs, u32 val); @@ -1066,6 +1061,8 @@ * @hw_rev_step: The mac step of the HW * @pm_support: set to true in start_hw if link pm is supported * @ltr_enabled: set to true if the LTR is enabled + * @fail_to_parse_pnvm_image: set to true if pnvm parsing failed + * @failed_to_load_reduce_power_image: set to true if pnvm loading failed * @wide_cmd_header: true when ucode supports wide command header format * @wait_command_queue: wait queue for sync commands * @num_rx_queues: number of RX queues allocated by the transport; @@ -1087,6 +1084,8 @@ * @pcie_link_speed: current PCIe link speed (%PCI_EXP_LNKSTA_CLS_*), * only valid for discrete (not integrated) NICs * @invalid_tx_cmd: invalid TX command buffer + * @reduced_cap_sku: reduced capability supported SKU + * @no_160: device not supporting 160Mhz */ struct iwl_trans { bool csme_own; @@ -1110,6 +1109,8 @@ u32 hw_id; char hw_id_str[52]; u32 sku_id[3]; + bool reduced_cap_sku; + u8 no_160; u8 rx_mpdu_cmd, rx_mpdu_cmd_hdr_size; @@ -1325,14 +1326,15 @@ } static inline void iwl_trans_reclaim(struct iwl_trans *trans, int queue, - int ssn, struct sk_buff_head *skbs) + int ssn, struct sk_buff_head *skbs, + bool is_flush) { if (WARN_ON_ONCE(trans->state != IWL_TRANS_FW_ALIVE)) { IWL_ERR(trans, "%s bad state = %d\n", __func__, trans->state); return; } - trans->ops->reclaim(trans, queue, ssn, skbs); + trans->ops->reclaim(trans, queue, ssn, skbs, is_flush); } static inline void iwl_trans_set_q_ptrs(struct iwl_trans *trans, int queue, @@ -1457,18 +1459,6 @@ trans->ops->freeze_txq_timer(trans, txqs, freeze); } -static inline void iwl_trans_block_txq_ptrs(struct iwl_trans *trans, - bool block) -{ - if (WARN_ON_ONCE(trans->state != IWL_TRANS_FW_ALIVE)) { - IWL_ERR(trans, "%s bad state = %d\n", __func__, trans->state); - return; - } - - if (trans->ops->block_txq_ptrs) - trans->ops->block_txq_ptrs(trans, block); -} - static inline int iwl_trans_wait_tx_queues_empty(struct iwl_trans *trans, u32 txqs) { diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/iwl-vendor-cmd.h backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/iwl-vendor-cmd.h --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/iwl-vendor-cmd.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/iwl-vendor-cmd.h 2023-10-04 04:18:43.000000000 +0800 @@ -115,6 +115,7 @@ * table * @IWL_MVM_VENDOR_CMD_RFIM_GET_TABLE: Retrieve the RFIM table * @IWL_MVM_VENDOR_CMD_RFIM_GET_CAPA: Retrieve RFIM capabilities + * @IWL_MVM_VENDOR_CMD_RFIM_SET_CNVI_MASTER: Set CNVI is master or not */ enum iwl_mvm_vendor_cmd { @@ -170,6 +171,7 @@ IWL_MVM_VENDOR_CMD_SAR_GET_TABLE = 0x34, IWL_MVM_VENDOR_CMD_GEO_SAR_GET_TABLE = 0x35, IWL_MVM_VENDOR_CMD_SGOM_GET_TABLE = 0x36, + IWL_MVM_VENDOR_CMD_RFIM_SET_CNVI_MASTER = 0x37, }; /** @@ -796,6 +798,7 @@ * @IWL_MVM_VENDOR_ATTR_RFIM_CHANNELS: RFIM channels * @IWL_MVM_VENDOR_ATTR_RFIM_FREQ: RFIM frequency (u16) * @IWL_MVM_VENDOR_ATTR_RFIM_INFO: overall RFIM info (nested) + * @IWL_MVM_VENDOR_ATTR_RFIM_CNVI_MASTER: CNVI master configuration (u32) * * @NUM_IWL_MVM_VENDOR_ATTR: number of vendor attributes * @MAX_IWL_MVM_VENDOR_ATTR: highest vendor attribute number @@ -911,6 +914,7 @@ IWL_MVM_VENDOR_ATTR_GEO_SAR_TABLE = 0x76, IWL_MVM_VENDOR_ATTR_GEO_SAR_VER = 0x77, IWL_MVM_VENDOR_ATTR_SGOM_TABLE = 0x78, + IWL_MVM_VENDOR_ATTR_RFIM_CNVI_MASTER = 0x79, NUM_IWL_MVM_VENDOR_ATTR, MAX_IWL_MVM_VENDOR_ATTR = NUM_IWL_MVM_VENDOR_ATTR - 1, diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mei/iwl-mei.h backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mei/iwl-mei.h --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mei/iwl-mei.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mei/iwl-mei.h 2023-10-04 04:18:43.000000000 +0800 @@ -1,6 +1,6 @@ /* SPDX-License-Identifier: GPL-2.0-only */ /* - * Copyright (C) 2021 - 2022 Intel Corporation + * Copyright (C) 2021-2023 Intel Corporation */ #ifndef __iwl_mei_h__ @@ -493,7 +493,7 @@ static inline int iwl_mei_register(void *priv, const struct iwl_mei_ops *ops) -{ return 0; } +{ return -EOPNOTSUPP; } static inline void iwl_mei_start_unregister(void) {} diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/constants.h backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/constants.h --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/constants.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/constants.h 2023-10-04 04:18:43.000000000 +0800 @@ -123,6 +123,7 @@ #define IWL_MVM_MEI_REPORT_RFKILL false #define IWL_MVM_MIN_BEACON_INTERVAL_TU 16 #define IWL_MVM_ADAPTIVE_DWELL_NUM_APS_OVERRIDE 0 +#define IWL_MVM_AUTO_EML_ENABLE true #else /* CPTCFG_IWLWIFI_SUPPORT_DEBUG_OVERRIDES */ #define IWL_MVM_DEFAULT_PS_TX_DATA_TIMEOUT (mvm->trans->dbg_cfg.MVM_DEFAULT_PS_TX_DATA_TIMEOUT) #define IWL_MVM_DEFAULT_PS_RX_DATA_TIMEOUT (mvm->trans->dbg_cfg.MVM_DEFAULT_PS_RX_DATA_TIMEOUT) @@ -240,6 +241,7 @@ #define IWL_MVM_MEI_REPORT_RFKILL (mvm->trans->dbg_cfg.MVM_MEI_REPORT_RFKILL) #define IWL_MVM_MIN_BEACON_INTERVAL_TU (mvm->trans->dbg_cfg.MVM_MIN_BEACON_INTERVAL_TU) #define IWL_MVM_ADAPTIVE_DWELL_NUM_APS_OVERRIDE (mvm->trans->dbg_cfg.MVM_ADAPTIVE_DWELL_NUM_APS_OVERRIDE) +#define IWL_MVM_AUTO_EML_ENABLE (mvm->trans->dbg_cfg.MVM_AUTO_EML_ENABLE) #endif /* CPTCFG_IWLWIFI_SUPPORT_DEBUG_OVERRIDES */ diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/d3.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/d3.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/d3.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/d3.c 2023-10-04 04:18:43.000000000 +0800 @@ -818,7 +818,7 @@ if (ret) IWL_ERR(mvm, "Failed to send quota: %d\n", ret); - if (iwl_mvm_is_lar_supported(mvm) && iwl_mvm_init_fw_regd(mvm)) + if (iwl_mvm_is_lar_supported(mvm) && iwl_mvm_init_fw_regd(mvm, false)) IWL_ERR(mvm, "Failed to initialize D3 LAR information\n"); return 0; @@ -2031,6 +2031,16 @@ if (IS_ERR(key_config)) return false; ieee80211_set_key_rx_seq(key_config, 0, &seq); + + if (key_config->keyidx == 4 || key_config->keyidx == 5) { + struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif); + int link_id = vif->active_links ? __ffs(vif->active_links) : 0; + struct iwl_mvm_vif_link_info *mvm_link = + mvmvif->link[link_id]; + + mvm_link->igtk = key_config; + } + return true; } @@ -2988,16 +2998,14 @@ (void *)pkt->data; struct iwl_wowlan_info_notif_v2 *notif_v2; - notif_v2 = kmemdup(notif_v1, - offsetofend(struct iwl_wowlan_info_notif_v2, - received_beacons), - GFP_ATOMIC); + notif_v2 = kmemdup(notif_v1, sizeof(*notif_v2), GFP_ATOMIC); if (!notif_v2) return false; notif_v2->tid_tear_down = notif_v1->tid_tear_down; notif_v2->station_id = notif_v1->station_id; + memset_after(notif_v2, 0, station_id); iwl_mvm_parse_wowlan_info_notif_v2(mvm, notif_v2, d3_data->status, len); diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/debugfs.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/debugfs.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/debugfs.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/debugfs.c 2023-10-04 04:18:43.000000000 +0800 @@ -124,8 +124,18 @@ size_t count, loff_t *ppos) { int ret; + bool force; - if (!iwl_mvm_is_ctdp_supported(mvm)) + if (!kstrtobool(buf, &force)) + IWL_DEBUG_INFO(mvm, + "force start is %d [0=disabled, 1=enabled]\n", + force); + + /* we allow skipping cap support check and force stop ctdp + * statistics collection and with guerantee that it is + * safe to use. + */ + if (!force && !iwl_mvm_is_ctdp_supported(mvm)) return -EOPNOTSUPP; if (!iwl_mvm_firmware_running(mvm) || @@ -139,6 +149,36 @@ return ret ?: count; } +static ssize_t iwl_dbgfs_start_ctdp_write(struct iwl_mvm *mvm, + char *buf, size_t count, + loff_t *ppos) +{ + int ret; + bool force; + + if (!kstrtobool(buf, &force)) + IWL_DEBUG_INFO(mvm, + "force start is %d [0=disabled, 1=enabled]\n", + force); + + /* we allow skipping cap support check and force enable ctdp + * for statistics collection and with guerantee that it is + * safe to use. + */ + if (!force && !iwl_mvm_is_ctdp_supported(mvm)) + return -EOPNOTSUPP; + + if (!iwl_mvm_firmware_running(mvm) || + mvm->fwrt.cur_fw_img != IWL_UCODE_REGULAR) + return -EIO; + + mutex_lock(&mvm->mutex); + ret = iwl_mvm_ctdp_command(mvm, CTDP_CMD_OPERATION_START, 0); + mutex_unlock(&mvm->mutex); + + return ret ?: count; +} + static ssize_t iwl_dbgfs_force_ctkill_write(struct iwl_mvm *mvm, char *buf, size_t count, loff_t *ppos) { @@ -691,7 +731,8 @@ char buf[32]; int pos; - pos = scnprintf(buf, sizeof(buf), "current %d ", link_sta->agg.max_amsdu_len); + pos = scnprintf(buf, sizeof(buf), "current %d ", + link_sta->agg.max_amsdu_len); pos += scnprintf(buf + pos, sizeof(buf) - pos, "stored %d\n", mvm_link_sta->orig_amsdu_len); @@ -1159,6 +1200,13 @@ char *buf; int ret; size_t bufsz; + u8 cmd_ver = iwl_fw_lookup_cmd_ver(mvm->fw, + WIDE_ID(SYSTEM_GROUP, + SYSTEM_STATISTICS_CMD), + IWL_FW_CMD_VER_UNKNOWN); + + if (cmd_ver != IWL_FW_CMD_VER_UNKNOWN) + return -EOPNOTSUPP; if (iwl_mvm_has_new_rx_stats_api(mvm)) bufsz = ((sizeof(struct mvm_statistics_rx) / @@ -1338,6 +1386,101 @@ } #undef PRINT_STAT_LE32 +static ssize_t iwl_dbgfs_fw_system_stats_read(struct file *file, + char __user *user_buf, + size_t count, loff_t *ppos) +{ + char *buff, *pos, *endpos; + int ret; + size_t bufsz; + int i; + struct iwl_mvm_vif *mvmvif; + struct ieee80211_vif *vif; + struct iwl_mvm *mvm = file->private_data; + u8 cmd_ver = iwl_fw_lookup_cmd_ver(mvm->fw, + WIDE_ID(SYSTEM_GROUP, + SYSTEM_STATISTICS_CMD), + IWL_FW_CMD_VER_UNKNOWN); + + /* in case of a wrong cmd version, allocate buffer only for error msg */ + bufsz = (cmd_ver == 1) ? 4096 : 64; + + buff = kzalloc(bufsz, GFP_KERNEL); + if (!buff) + return -ENOMEM; + + pos = buff; + endpos = pos + bufsz; + + if (cmd_ver != 1) { + pos += scnprintf(pos, endpos - pos, + "System stats not supported:%d\n", cmd_ver); + goto send_out; + } + + mutex_lock(&mvm->mutex); + if (iwl_mvm_firmware_running(mvm)) + iwl_mvm_request_statistics(mvm, false); + + for (i = 0; i < NUM_MAC_INDEX_DRIVER; i++) { + vif = iwl_mvm_rcu_dereference_vif_id(mvm, i, false); + if (!vif) + continue; + + if (vif->type == NL80211_IFTYPE_STATION) + break; + } + + if (i == NUM_MAC_INDEX_DRIVER || !vif) { + pos += scnprintf(pos, endpos - pos, "vif is NULL\n"); + goto release_send_out; + } + + mvmvif = iwl_mvm_vif_from_mac80211(vif); + if (!mvmvif) { + pos += scnprintf(pos, endpos - pos, "mvmvif is NULL\n"); + goto release_send_out; + } + + for_each_mvm_vif_valid_link(mvmvif, i) { + struct iwl_mvm_vif_link_info *link_info = mvmvif->link[i]; + + pos += scnprintf(pos, endpos - pos, + "link_id %d", i); + pos += scnprintf(pos, endpos - pos, + " num_beacons %d", + link_info->beacon_stats.num_beacons); + pos += scnprintf(pos, endpos - pos, + " accu_num_beacons %d", + link_info->beacon_stats.accu_num_beacons); + pos += scnprintf(pos, endpos - pos, + " avg_signal %d\n", + link_info->beacon_stats.avg_signal); + } + + pos += scnprintf(pos, endpos - pos, + "radio_stats.rx_time %lld\n", + mvm->radio_stats.rx_time); + pos += scnprintf(pos, endpos - pos, + "radio_stats.tx_time %lld\n", + mvm->radio_stats.tx_time); + pos += scnprintf(pos, endpos - pos, + "accu_radio_stats.rx_time %lld\n", + mvm->accu_radio_stats.rx_time); + pos += scnprintf(pos, endpos - pos, + "accu_radio_stats.tx_time %lld\n", + mvm->accu_radio_stats.tx_time); + +release_send_out: + mutex_unlock(&mvm->mutex); + +send_out: + ret = simple_read_from_buffer(user_buf, count, ppos, buff, pos - buff); + kfree(buff); + + return ret; +} + static ssize_t iwl_dbgfs_frame_stats_read(struct iwl_mvm *mvm, char __user *user_buf, size_t count, loff_t *ppos, @@ -1767,6 +1910,20 @@ return count; } +static ssize_t iwl_dbgfs_fw_dbg_clear_write(struct iwl_mvm *mvm, + char *buf, size_t count, + loff_t *ppos) +{ + if (mvm->trans->trans_cfg->device_family < IWL_DEVICE_FAMILY_9000) + return -EOPNOTSUPP; + + mutex_lock(&mvm->mutex); + iwl_fw_dbg_clear_monitor_buf(&mvm->fwrt); + mutex_unlock(&mvm->mutex); + + return count; +} + static ssize_t iwl_dbgfs_dbg_time_point_write(struct iwl_mvm *mvm, char *buf, size_t count, loff_t *ppos) @@ -2429,7 +2586,7 @@ /* value zero triggers re-sending the default table to the device */ if (!op_id) { mutex_lock(&mvm->mutex); - ret = iwl_rfi_send_config_cmd(mvm, NULL); + ret = iwl_rfi_send_config_cmd(mvm, NULL, false, false); mutex_unlock(&mvm->mutex); } else { ret = -EOPNOTSUPP; /* in the future a new table will be added */ @@ -2491,6 +2648,7 @@ #endif MVM_DEBUGFS_READ_FILE_OPS(ctdp_budget); MVM_DEBUGFS_WRITE_FILE_OPS(stop_ctdp, 8); +MVM_DEBUGFS_WRITE_FILE_OPS(start_ctdp, 8); MVM_DEBUGFS_WRITE_FILE_OPS(force_ctkill, 8); MVM_DEBUGFS_WRITE_FILE_OPS(tx_flush, 16); MVM_DEBUGFS_WRITE_FILE_OPS(sta_drain, 8); @@ -2505,6 +2663,7 @@ MVM_DEBUGFS_READ_WRITE_FILE_OPS(disable_power_off, 64); MVM_DEBUGFS_READ_FILE_OPS(fw_rx_stats); MVM_DEBUGFS_READ_FILE_OPS(drv_rx_stats); +MVM_DEBUGFS_READ_FILE_OPS(fw_system_stats); MVM_DEBUGFS_READ_FILE_OPS(fw_ver); MVM_DEBUGFS_READ_FILE_OPS(phy_integration_ver); MVM_DEBUGFS_READ_FILE_OPS(tas_get_status); @@ -2515,6 +2674,7 @@ MVM_DEBUGFS_READ_WRITE_FILE_OPS(scan_ant_rxchain, 8); MVM_DEBUGFS_READ_WRITE_FILE_OPS(fw_dbg_conf, 8); MVM_DEBUGFS_WRITE_FILE_OPS(fw_dbg_collect, 64); +MVM_DEBUGFS_WRITE_FILE_OPS(fw_dbg_clear, 64); MVM_DEBUGFS_WRITE_FILE_OPS(dbg_time_point, 64); MVM_DEBUGFS_WRITE_FILE_OPS(indirection_tbl, (IWL_RSS_INDIRECTION_TABLE_SIZE * 2)); @@ -2729,6 +2889,7 @@ MVM_DEBUGFS_ADD_FILE(nic_temp, mvm->debugfs_dir, 0400); MVM_DEBUGFS_ADD_FILE(ctdp_budget, mvm->debugfs_dir, 0400); MVM_DEBUGFS_ADD_FILE(stop_ctdp, mvm->debugfs_dir, 0200); + MVM_DEBUGFS_ADD_FILE(start_ctdp, mvm->debugfs_dir, 0200); MVM_DEBUGFS_ADD_FILE(force_ctkill, mvm->debugfs_dir, 0200); MVM_DEBUGFS_ADD_FILE(stations, mvm->debugfs_dir, 0400); MVM_DEBUGFS_ADD_FILE(bt_notif, mvm->debugfs_dir, 0400); @@ -2737,6 +2898,7 @@ MVM_DEBUGFS_ADD_FILE(fw_ver, mvm->debugfs_dir, 0400); MVM_DEBUGFS_ADD_FILE(fw_rx_stats, mvm->debugfs_dir, 0400); MVM_DEBUGFS_ADD_FILE(drv_rx_stats, mvm->debugfs_dir, 0400); + MVM_DEBUGFS_ADD_FILE(fw_system_stats, mvm->debugfs_dir, 0400); MVM_DEBUGFS_ADD_FILE(fw_restart, mvm->debugfs_dir, 0200); MVM_DEBUGFS_ADD_FILE(fw_nmi, mvm->debugfs_dir, 0200); MVM_DEBUGFS_ADD_FILE(bt_tx_prio, mvm->debugfs_dir, 0200); @@ -2745,6 +2907,7 @@ MVM_DEBUGFS_ADD_FILE(prph_reg, mvm->debugfs_dir, 0600); MVM_DEBUGFS_ADD_FILE(fw_dbg_conf, mvm->debugfs_dir, 0600); MVM_DEBUGFS_ADD_FILE(fw_dbg_collect, mvm->debugfs_dir, 0200); + MVM_DEBUGFS_ADD_FILE(fw_dbg_clear, mvm->debugfs_dir, 0200); MVM_DEBUGFS_ADD_FILE(dbg_time_point, mvm->debugfs_dir, 0200); MVM_DEBUGFS_ADD_FILE(send_echo_cmd, mvm->debugfs_dir, 0200); MVM_DEBUGFS_ADD_FILE(indirection_tbl, mvm->debugfs_dir, 0200); diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/debugfs.h backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/debugfs.h --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/debugfs.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/debugfs.h 2023-10-04 04:18:43.000000000 +0800 @@ -1,5 +1,6 @@ /* SPDX-License-Identifier: GPL-2.0 OR BSD-3-Clause */ /* + * Copyright (C) 2023 Intel Corporation * Copyright (C) 2012-2014 Intel Corporation * Copyright (C) 2013-2014 Intel Mobile Communications GmbH */ diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/debugfs-vif.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/debugfs-vif.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/debugfs-vif.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/debugfs-vif.c 2023-10-04 04:18:43.000000000 +0800 @@ -772,29 +772,29 @@ return ret ?: count; } -static ssize_t iwl_dbgfs_eht_puncturing_read(struct file *file, - char __user *user_buf, - size_t count, loff_t *ppos) +static ssize_t iwl_dbgfs_link_eht_puncturing_read(struct file *file, + char __user *user_buf, + size_t count, loff_t *ppos) { - struct ieee80211_vif *vif = file->private_data; + struct ieee80211_bss_conf *link = file->private_data; char buf[8]; int len; len = scnprintf(buf, sizeof(buf), "0x%04x\n", - vif->bss_conf.eht_puncturing); + link->eht_puncturing); return simple_read_from_buffer(user_buf, count, ppos, buf, len); } -static ssize_t iwl_dbgfs_eht_puncturing_write(struct ieee80211_vif *vif, char *buf, - size_t count, loff_t *ppos) +static +ssize_t iwl_dbgfs_link_eht_puncturing_write(struct ieee80211_bss_conf *link, + char *buf, size_t count, + loff_t *ppos) { - struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif); - struct iwl_mvm *mvm = mvmvif->mvm; - struct ieee80211_sta *sta; - struct iwl_mvm_sta *mvmsta; + struct ieee80211_vif *vif = link->vif; + struct iwl_mvm *mvm = iwl_mvm_vif_from_mac80211(vif)->mvm; u16 puncturing; - int ret, i; + int ret; if (!iwl_mvm_firmware_running(mvm)) return -EIO; @@ -810,26 +810,16 @@ * MVM is not supposed to modify the BSS info, * but softAP doesn't use this field anyway. */ - vif->bss_conf.eht_puncturing = puncturing; + link->eht_puncturing = puncturing; mutex_lock(&mvm->mutex); - for (i = 0; i < mvm->fw->ucode_capa.num_stations; i++) { - sta = rcu_dereference_protected(mvm->fw_id_to_mac_id[i], - lockdep_is_held(&mvm->mutex)); - - if (IS_ERR_OR_NULL(sta)) - continue; - - mvmsta = iwl_mvm_sta_from_mac80211(sta); - if (mvmsta->vif != vif) - continue; - - iwl_mvm_cfg_he_sta(mvm, vif, mvmsta->deflink.sta_id); - } + /* All links are always active in ap mode */ + ret = iwl_mvm_link_changed(mvm, vif, link, + LINK_CONTEXT_MODIFY_EHT_PARAMS, true); mutex_unlock(&mvm->mutex); - return count; + return ret ?: count; } static ssize_t iwl_dbgfs_max_tx_op_write(struct ieee80211_vif *vif, char *buf, @@ -888,22 +878,13 @@ MVM_DEBUGFS_READ_WRITE_FILE_OPS(quota_min, 32); MVM_DEBUGFS_READ_FILE_OPS(os_device_timediff); MVM_DEBUGFS_WRITE_FILE_OPS(twt_setup, 256); -MVM_DEBUGFS_READ_WRITE_FILE_OPS(eht_puncturing, 16); MVM_DEBUGFS_READ_WRITE_FILE_OPS(max_tx_op, 10); - -void iwl_mvm_vif_dbgfs_register(struct iwl_mvm *mvm, struct ieee80211_vif *vif) +void iwl_mvm_vif_add_debugfs(struct ieee80211_hw *hw, struct ieee80211_vif *vif) { + struct iwl_mvm *mvm = IWL_MAC80211_GET_MVM(hw); struct dentry *dbgfs_dir = vif->debugfs_dir; struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif); - char buf[100]; - - /* - * Check if debugfs directory already exist before creating it. - * This may happen when, for example, resetting hw or suspend-resume - */ - if (!dbgfs_dir || mvmvif->dbgfs_dir) - return; mvmvif->dbgfs_dir = debugfs_create_dir("iwlmvm", dbgfs_dir); if (IS_ERR_OR_NULL(mvmvif->dbgfs_dir)) { @@ -926,13 +907,24 @@ MVM_DEBUGFS_ADD_FILE_VIF(quota_min, mvmvif->dbgfs_dir, 0600); MVM_DEBUGFS_ADD_FILE_VIF(os_device_timediff, mvmvif->dbgfs_dir, 0400); MVM_DEBUGFS_ADD_FILE_VIF(twt_setup, mvmvif->dbgfs_dir, 0200); - MVM_DEBUGFS_ADD_FILE_VIF(eht_puncturing, mvmvif->dbgfs_dir, 0600); MVM_DEBUGFS_ADD_FILE_VIF(max_tx_op, mvmvif->dbgfs_dir, 0600); if (vif->type == NL80211_IFTYPE_STATION && !vif->p2p && mvmvif == mvm->bf_allowed_vif) MVM_DEBUGFS_ADD_FILE_VIF(bf_params, mvmvif->dbgfs_dir, 0600); +} + +void iwl_mvm_vif_dbgfs_add_link(struct iwl_mvm *mvm, struct ieee80211_vif *vif) +{ + struct dentry *dbgfs_dir = vif->debugfs_dir; + struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif); + char buf[100]; + + /* this will happen in monitor mode */ + if (!dbgfs_dir) + return; + /* * Create symlink for convenience pointing to interface specific * debugfs entries for the driver. For example, under @@ -940,21 +932,65 @@ * find * netdev:wlan0 -> ../../../ieee80211/phy0/netdev:wlan0/iwlmvm/ */ - snprintf(buf, 100, "../../../%pd3/%pd", - dbgfs_dir, - mvmvif->dbgfs_dir); + snprintf(buf, 100, "../../../%pd3/iwlmvm", dbgfs_dir); mvmvif->dbgfs_slink = debugfs_create_symlink(dbgfs_dir->d_name.name, mvm->debugfs_dir, buf); } -void iwl_mvm_vif_dbgfs_clean(struct iwl_mvm *mvm, struct ieee80211_vif *vif) +void iwl_mvm_vif_dbgfs_rm_link(struct iwl_mvm *mvm, struct ieee80211_vif *vif) { struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif); debugfs_remove(mvmvif->dbgfs_slink); mvmvif->dbgfs_slink = NULL; +} + +#define MVM_DEBUGFS_WRITE_LINK_FILE_OPS(name, bufsz) \ + _MVM_DEBUGFS_WRITE_FILE_OPS(link_##name, bufsz, \ + struct ieee80211_bss_conf) +#define MVM_DEBUGFS_READ_WRITE_LINK_FILE_OPS(name, bufsz) \ + _MVM_DEBUGFS_READ_WRITE_FILE_OPS(link_##name, bufsz, \ + struct ieee80211_bss_conf) +#define MVM_DEBUGFS_ADD_LINK_FILE(name, parent, mode) \ + debugfs_create_file(#name, mode, parent, link_conf, \ + &iwl_dbgfs_link_##name##_ops) + +MVM_DEBUGFS_READ_WRITE_LINK_FILE_OPS(eht_puncturing, 16); + +static void iwl_mvm_debugfs_add_link_files(struct ieee80211_vif *vif, + struct ieee80211_bss_conf *link_conf, + struct dentry *mvm_dir) +{ + if (vif->type == NL80211_IFTYPE_AP) + MVM_DEBUGFS_ADD_LINK_FILE(eht_puncturing, mvm_dir, 0600); +} + +void iwl_mvm_link_add_debugfs(struct ieee80211_hw *hw, + struct ieee80211_vif *vif, + struct ieee80211_bss_conf *link_conf, + struct dentry *dir) +{ + struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif); + struct iwl_mvm *mvm = mvmvif->mvm; + unsigned int link_id = link_conf->link_id; + struct iwl_mvm_vif_link_info *link_info = mvmvif->link[link_id]; + struct dentry *mvm_dir; + + if (WARN_ON(!link_info) || !dir) + return; + + if (dir == vif->debugfs_dir) { + WARN_ON(!mvmvif->dbgfs_dir); + mvm_dir = mvmvif->dbgfs_dir; + } else { + mvm_dir = debugfs_create_dir("iwlmvm", dir); + if (IS_ERR_OR_NULL(mvm_dir)) { + IWL_ERR(mvm, "Failed to create debugfs directory under %pd\n", + dir); + return; + } + } - debugfs_remove_recursive(mvmvif->dbgfs_dir); - mvmvif->dbgfs_dir = NULL; + iwl_mvm_debugfs_add_link_files(vif, link_conf, mvm_dir); } diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/fw.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/fw.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/fw.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/fw.c 2023-10-04 04:18:43.000000000 +0800 @@ -15,6 +15,7 @@ #include "iwl-prph.h" #include "fw/acpi.h" #include "fw/pnvm.h" +#include "fw/uefi.h" #include "mvm.h" #include "fw/dbg.h" @@ -27,12 +28,15 @@ #endif #include "time-sync.h" -#define MVM_UCODE_ALIVE_TIMEOUT (HZ * CPTCFG_IWL_TIMEOUT_FACTOR) +#define MVM_UCODE_ALIVE_TIMEOUT (2 * HZ * CPTCFG_IWL_TIMEOUT_FACTOR) #define MVM_UCODE_CALIB_TIMEOUT (2 * HZ * CPTCFG_IWL_TIMEOUT_FACTOR) #define IWL_TAS_US_MCC 0x5553 #define IWL_TAS_CANADA_MCC 0x4341 +#define IWL_UATS_VLP_AP_SUPPORTED BIT(29) +#define IWL_UATS_AFC_AP_SUPPORTED BIT(30) + struct iwl_mvm_alive_data { bool valid; u32 scd_base_addr; @@ -509,6 +513,52 @@ } #if defined(CONFIG_ACPI) && defined(CONFIG_EFI) +static void iwl_mvm_uats_init(struct iwl_mvm *mvm) +{ + u8 cmd_ver; + int ret; + struct iwl_host_cmd cmd = { + .id = WIDE_ID(REGULATORY_AND_NVM_GROUP, + UATS_TABLE_CMD), + .flags = 0, + .data[0] = &mvm->fwrt.uats_table, + .len[0] = sizeof(mvm->fwrt.uats_table), + .dataflags[0] = IWL_HCMD_DFL_NOCOPY, + }; + + if (!(mvm->trans->trans_cfg->device_family >= + IWL_DEVICE_FAMILY_AX210)) { + IWL_DEBUG_RADIO(mvm, "UATS feature is not supported\n"); + return; + } + + if (!mvm->fwrt.uats_enabled) { + IWL_DEBUG_RADIO(mvm, "UATS feature is disabled\n"); + return; + } + + cmd_ver = iwl_fw_lookup_cmd_ver(mvm->fw, cmd.id, + IWL_FW_CMD_VER_UNKNOWN); + if (cmd_ver != 1) { + IWL_DEBUG_RADIO(mvm, + "UATS_TABLE_CMD ver %d not supported\n", + cmd_ver); + return; + } + + ret = iwl_uefi_get_uats_table(mvm->trans, &mvm->fwrt); + if (ret < 0) { + IWL_ERR(mvm, "failed to read UATS table (%d)\n", ret); + return; + } + + ret = iwl_mvm_send_cmd(mvm, &cmd); + if (ret < 0) + IWL_ERR(mvm, "failed to send UATS_TABLE_CMD (%d)\n", ret); + else + IWL_DEBUG_RADIO(mvm, "UATS_TABLE_CMD sent to FW\n"); +} + static int iwl_mvm_sgom_init(struct iwl_mvm *mvm) { u8 cmd_ver; @@ -548,6 +598,10 @@ { return 0; } + +static void iwl_mvm_uats_init(struct iwl_mvm *mvm) +{ +} #endif static int iwl_send_phy_cfg_cmd(struct iwl_mvm *mvm) @@ -694,7 +748,7 @@ if (mvm->trans->trans_cfg->device_family == IWL_DEVICE_FAMILY_AX210) { sb_cfg = iwl_read_umac_prph(mvm->trans, SB_MODIFY_CFG_FLAG); /* if needed, we'll reset this on our way out later */ - mvm->pldr_sync = !(sb_cfg & SB_CFG_RESIDES_IN_OTP_MASK); + mvm->pldr_sync = sb_cfg == SB_CFG_RESIDES_IN_ROM; if (mvm->pldr_sync && iwl_mei_pldr_req()) return -EBUSY; } @@ -793,7 +847,7 @@ mvm->rfkill_safe_init_done = true; - iwl_rfi_send_config_cmd(mvm, NULL); + iwl_rfi_send_config_cmd(mvm, NULL, false, true); return 0; error: @@ -921,7 +975,7 @@ mvm->nvm_data->bands[0].n_channels = 1; mvm->nvm_data->bands[0].n_bitrates = 1; mvm->nvm_data->bands[0].bitrates = - (void *)((u8 *)mvm->nvm_data->channels + 1); + (void *)(mvm->nvm_data->channels + 1); mvm->nvm_data->bands[0].bitrates->hw_value = 10; } @@ -1214,6 +1268,12 @@ DMI_MATCH(DMI_SYS_VENDOR, "ASUSTeK COMPUTER INC."), }, }, + { .ident = "GOOGLE-HP", + .matches = { + DMI_MATCH(DMI_SYS_VENDOR, "Google"), + DMI_MATCH(DMI_BOARD_VENDOR, "HP"), + }, + }, { .ident = "MSI", .matches = { DMI_MATCH(DMI_SYS_VENDOR, "Micro-Star International Co., Ltd."), @@ -1350,8 +1410,9 @@ { u8 value; - int ret = iwl_acpi_get_dsm_u8(mvm->fwrt.dev, 0, DSM_RFI_DDR_FUNC_ENABLE, - &iwl_rfi_guid, &value); + int ret = iwl_acpi_get_dsm_u8(mvm->fwrt.dev, 0, + DSM_INTERNAL_FUNC_RFI_DDR_ENABLE, + &iwl_internal_guid, &value); if (ret < 0) { IWL_DEBUG_RADIO(mvm, "Failed to get DSM RFI DDR, ret=%d\n", ret); @@ -1376,7 +1437,10 @@ { int ret; u32 value; - struct iwl_lari_config_change_cmd_v6 cmd = {}; + struct iwl_lari_config_change_cmd_v7 cmd = {}; + u8 cmd_ver = iwl_fw_lookup_cmd_ver(mvm->fw, + WIDE_ID(REGULATORY_AND_NVM_GROUP, + LARI_CONFIG_CHANGE), 1); cmd.config_bitmap = iwl_acpi_get_lari_config_bitmap(&mvm->fwrt); @@ -1394,8 +1458,11 @@ ret = iwl_acpi_get_dsm_u32(mvm->fwrt.dev, 0, DSM_FUNC_ACTIVATE_CHANNEL, &iwl_guid, &value); - if (!ret) + if (!ret) { + if (cmd_ver < 8) + value &= ~ACTIVATE_5G2_IN_WW_MASK; cmd.chan_state_active_bitmap = cpu_to_le32(value); + } ret = iwl_acpi_get_dsm_u32(mvm->fwrt.dev, 0, DSM_FUNC_ENABLE_6E, @@ -1409,18 +1476,26 @@ if (!ret) cmd.force_disable_channels_bitmap = cpu_to_le32(value); + ret = iwl_acpi_get_dsm_u32(mvm->fwrt.dev, 0, + DSM_FUNC_ENERGY_DETECTION_THRESHOLD, + &iwl_guid, &value); + if (!ret) + cmd.edt_bitmap = cpu_to_le32(value); + if (cmd.config_bitmap || cmd.oem_uhb_allow_bitmap || cmd.oem_11ax_allow_bitmap || cmd.oem_unii4_allow_bitmap || cmd.chan_state_active_bitmap || - cmd.force_disable_channels_bitmap) { + cmd.force_disable_channels_bitmap || + cmd.edt_bitmap) { size_t cmd_size; - u8 cmd_ver = iwl_fw_lookup_cmd_ver(mvm->fw, - WIDE_ID(REGULATORY_AND_NVM_GROUP, - LARI_CONFIG_CHANGE), - 1); + switch (cmd_ver) { + case 8: + case 7: + cmd_size = sizeof(struct iwl_lari_config_change_cmd_v7); + break; case 6: cmd_size = sizeof(struct iwl_lari_config_change_cmd_v6); break; @@ -1454,6 +1529,9 @@ "sending LARI_CONFIG_CHANGE, oem_uhb_allow_bitmap=0x%x, force_disable_channels_bitmap=0x%x\n", le32_to_cpu(cmd.oem_uhb_allow_bitmap), le32_to_cpu(cmd.force_disable_channels_bitmap)); + IWL_DEBUG_RADIO(mvm, + "sending LARI_CONFIG_CHANGE, edt_bitmap=0x%x\n", + le32_to_cpu(cmd.edt_bitmap)); ret = iwl_mvm_send_cmd_pdu(mvm, WIDE_ID(REGULATORY_AND_NVM_GROUP, LARI_CONFIG_CHANGE), @@ -1463,6 +1541,10 @@ "Failed to send LARI_CONFIG_CHANGE (%d)\n", ret); } + + if (le32_to_cpu(cmd.oem_uhb_allow_bitmap) & IWL_UATS_VLP_AP_SUPPORTED || + le32_to_cpu(cmd.oem_uhb_allow_bitmap) & IWL_UATS_AFC_AP_SUPPORTED) + mvm->fwrt.uats_enabled = TRUE; } void iwl_mvm_get_acpi_tables(struct iwl_mvm *mvm) @@ -1698,8 +1780,6 @@ int iwl_mvm_up(struct iwl_mvm *mvm) { int ret, i; - struct ieee80211_channel *chan; - struct cfg80211_chan_def chandef; struct ieee80211_supported_band *sband = NULL; lockdep_assert_held(&mvm->mutex); @@ -1828,21 +1908,6 @@ goto error; } - chan = &sband->channels[0]; - - cfg80211_chandef_create(&chandef, chan, NL80211_CHAN_NO_HT); - for (i = 0; i < NUM_PHY_CTX; i++) { - /* - * The channel used here isn't relevant as it's - * going to be overwritten in the other flows. - * For now use the first channel we have. - */ - ret = iwl_mvm_phy_ctxt_add(mvm, &mvm->phy_ctxts[i], - &chandef, 1, 1); - if (ret) - goto error; - } - if (iwl_mvm_is_tt_in_fw(mvm)) { /* in order to give the responsibility of ct-kill and * TX backoff to FW we need to send empty temperature reporting @@ -1953,6 +2018,7 @@ iwl_mvm_tas_init(mvm); iwl_mvm_leds_sync(mvm); + iwl_mvm_uats_init(mvm); #ifdef CPTCFG_IWLWIFI_SUPPORT_DEBUG_OVERRIDES iwl_mvm_send_system_features_control(mvm); diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/link.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/link.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/link.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/link.c 2023-10-04 04:18:43.000000000 +0800 @@ -53,7 +53,6 @@ unsigned int link_id = link_conf->link_id; struct iwl_mvm_vif_link_info *link_info = mvmvif->link[link_id]; struct iwl_link_config_cmd cmd = {}; - struct iwl_mvm_phy_ctxt *phyctxt; if (WARN_ON_ONCE(!link_info)) return -EINVAL; @@ -77,12 +76,8 @@ cmd.link_id = cpu_to_le32(link_info->fw_link_id); cmd.mac_id = cpu_to_le32(mvmvif->id); cmd.spec_link_id = link_conf->link_id; - /* P2P-Device already has a valid PHY context during add */ - phyctxt = link_info->phy_ctxt; - if (phyctxt) - cmd.phy_id = cpu_to_le32(phyctxt->id); - else - cmd.phy_id = cpu_to_le32(FW_CTXT_INVALID); + WARN_ON_ONCE(link_info->phy_ctxt); + cmd.phy_id = cpu_to_le32(FW_CTXT_INVALID); memcpy(cmd.local_link_addr, link_conf->addr, ETH_ALEN); @@ -194,11 +189,14 @@ flags_mask |= LINK_FLG_MU_EDCA_CW; } - if (link_conf->eht_puncturing && !iwlwifi_mod_params.disable_11be) - cmd.puncture_mask = cpu_to_le16(link_conf->eht_puncturing); - else - /* This flag can be set only if the MAC has eht support */ - changes &= ~LINK_CONTEXT_MODIFY_EHT_PARAMS; + if (changes & LINK_CONTEXT_MODIFY_EHT_PARAMS) { + if (iwlwifi_mod_params.disable_11be || + !link_conf->eht_support) + changes &= ~LINK_CONTEXT_MODIFY_EHT_PARAMS; + else + cmd.puncture_mask = + cpu_to_le16(link_conf->eht_puncturing); + } cmd.bss_color = link_conf->he_bss_color.color; @@ -244,15 +242,18 @@ struct iwl_link_config_cmd cmd = {}; int ret; + /* mac80211 thought we have the link, but it was never configured */ if (WARN_ON(!link_info || link_info->fw_link_id >= ARRAY_SIZE(mvm->link_id_to_link_conf))) - return -EINVAL; + return 0; - RCU_INIT_POINTER(mvm->link_id_to_link_conf[link_info->fw_link_id], NULL); + RCU_INIT_POINTER(mvm->link_id_to_link_conf[link_info->fw_link_id], + NULL); cmd.link_id = cpu_to_le32(link_info->fw_link_id); iwl_mvm_release_fw_link_id(mvm, link_info->fw_link_id); link_info->fw_link_id = IWL_MVM_FW_LINK_ID_INVALID; cmd.spec_link_id = link_conf->link_id; + cmd.phy_id = cpu_to_le32(FW_CTXT_INVALID); ret = iwl_mvm_link_cmd_send(mvm, &cmd, FW_CTXT_ACTION_REMOVE); diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/mac80211.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/mac80211.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/mac80211.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/mac80211.c 2023-10-04 04:18:43.000000000 +0800 @@ -225,7 +225,7 @@ MCC_SOURCE_OLD_FW, changed); } -int iwl_mvm_init_fw_regd(struct iwl_mvm *mvm) +int iwl_mvm_init_fw_regd(struct iwl_mvm *mvm, bool force_regd_sync) { enum iwl_mcc_source used_src; struct ieee80211_regdomain *regd; @@ -252,8 +252,10 @@ if (IS_ERR_OR_NULL(regd)) return -EIO; - /* update cfg80211 if the regdomain was changed */ - if (changed) + /* update cfg80211 if the regdomain was changed or the caller explicitly + * asked to update regdomain + */ + if (changed || force_regd_sync) ret = regulatory_set_wiphy_regd_sync(mvm->hw->wiphy, regd); else ret = 0; @@ -384,8 +386,9 @@ #endif /* Set this early since we need to have it for the check below */ - if (mvm->mld_api_is_used && !iwlwifi_mod_params.disable_11ax && - mvm->trans->trans_cfg->device_family >= IWL_DEVICE_FAMILY_BZ) + if (mvm->mld_api_is_used && mvm->nvm_data->sku_cap_11be_enable && + !iwlwifi_mod_params.disable_11ax && + !iwlwifi_mod_params.disable_11be) hw->wiphy->flags |= WIPHY_FLAG_SUPPORTS_MLO; /* @@ -422,7 +425,9 @@ ieee80211_hw_set(hw, HAS_RATE_CONTROL); } - if (iwl_mvm_has_new_rx_api(mvm)) + /* We want to use the mac80211's reorder buffer for 9000 */ + if (iwl_mvm_has_new_rx_api(mvm) && + mvm->trans->trans_cfg->device_family > IWL_DEVICE_FAMILY_9000) ieee80211_hw_set(hw, SUPPORTS_REORDERING_BUFFER); if (fw_has_capa(&mvm->fw->ucode_capa, @@ -561,6 +566,10 @@ hw->wiphy->regulatory_flags |= REGULATORY_CUSTOM_REG | REGULATORY_DISABLE_BEACON_HINTS; + if (mvm->trans->trans_cfg->device_family >= IWL_DEVICE_FAMILY_AX210) + wiphy_ext_feature_set(hw->wiphy, + NL80211_EXT_FEATURE_DFS_CONCURRENT); + hw->wiphy->flags |= WIPHY_FLAG_AP_UAPSD; hw->wiphy->flags |= WIPHY_FLAG_HAS_CHANNEL_SWITCH; hw->wiphy->flags |= WIPHY_FLAG_SPLIT_SCAN_6GHZ; @@ -1648,6 +1657,7 @@ struct iwl_mvm *mvm = IWL_MAC80211_GET_MVM(hw); struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif); int ret; + int i; mutex_lock(&mvm->mutex); @@ -1664,8 +1674,9 @@ /* make sure that beacon statistics don't go backwards with FW reset */ if (test_bit(IWL_MVM_STATUS_IN_HW_RESTART, &mvm->status)) - mvmvif->deflink.beacon_stats.accu_num_beacons += - mvmvif->deflink.beacon_stats.num_beacons; + for_each_mvm_vif_valid_link(mvmvif, i) + mvmvif->link[i]->beacon_stats.accu_num_beacons += + mvmvif->link[i]->beacon_stats.num_beacons; /* Allocate resources for the MAC context, and add it to the fw */ ret = iwl_mvm_mac_ctxt_init(mvm, vif); @@ -1693,7 +1704,7 @@ */ if (vif->type == NL80211_IFTYPE_AP || vif->type == NL80211_IFTYPE_ADHOC) { - iwl_mvm_vif_dbgfs_register(mvm, vif); + iwl_mvm_vif_dbgfs_add_link(mvm, vif); ret = 0; goto out; } @@ -1720,32 +1731,8 @@ IEEE80211_VIF_SUPPORTS_CQM_RSSI; } - /* - * P2P_DEVICE interface does not have a channel context assigned to it, - * so a dedicated PHY context is allocated to it and the corresponding - * MAC context is bound to it at this stage. - */ - if (vif->type == NL80211_IFTYPE_P2P_DEVICE) { - - mvmvif->deflink.phy_ctxt = iwl_mvm_get_free_phy_ctxt(mvm); - if (!mvmvif->deflink.phy_ctxt) { - ret = -ENOSPC; - goto out_free_bf; - } - - iwl_mvm_phy_ctxt_ref(mvm, mvmvif->deflink.phy_ctxt); - ret = iwl_mvm_binding_add_vif(mvm, vif); - if (ret) - goto out_unref_phy; - - ret = iwl_mvm_add_p2p_bcast_sta(mvm, vif); - if (ret) - goto out_unbind; - - /* Save a pointer to p2p device vif, so it can later be used to - * update the p2p device MAC when a GO is started/stopped */ + if (vif->type == NL80211_IFTYPE_P2P_DEVICE) mvm->p2p_device_vif = vif; - } iwl_mvm_tcm_add_vif(mvm, vif); INIT_DELAYED_WORK(&mvmvif->csa_work, @@ -1757,7 +1744,7 @@ iwl_mvm_chandef_get_primary_80(&vif->bss_conf.chandef); } - iwl_mvm_vif_dbgfs_register(mvm, vif); + iwl_mvm_vif_dbgfs_add_link(mvm, vif); if (!test_bit(IWL_MVM_STATUS_IN_HW_RESTART, &mvm->status) && vif->type == NL80211_IFTYPE_STATION && !vif->p2p && @@ -1774,16 +1761,6 @@ goto out_unlock; - out_unbind: - iwl_mvm_binding_remove_vif(mvm, vif); - out_unref_phy: - iwl_mvm_phy_ctxt_unref(mvm, mvmvif->deflink.phy_ctxt); - out_free_bf: - if (mvm->bf_allowed_vif == mvmvif) { - mvm->bf_allowed_vif = NULL; - vif->driver_flags &= ~(IEEE80211_VIF_BEACON_FILTER | - IEEE80211_VIF_SUPPORTS_CQM_RSSI); - } out_remove_mac: mvmvif->deflink.phy_ctxt = NULL; iwl_mvm_mac_ctxt_remove(mvm, vif); @@ -1854,7 +1831,7 @@ if (vif->bss_conf.ftm_responder) memset(&mvm->ftm_resp_stats, 0, sizeof(mvm->ftm_resp_stats)); - iwl_mvm_vif_dbgfs_clean(mvm, vif); + iwl_mvm_vif_dbgfs_rm_link(mvm, vif); /* * For AP/GO interface, the tear down of the resources allocated to the @@ -1889,12 +1866,17 @@ if (iwl_mvm_mac_remove_interface_common(hw, vif)) goto out; + /* Before the interface removal, mac80211 would cancel the ROC, and the + * ROC worker would be scheduled if needed. The worker would be flushed + * in iwl_mvm_prepare_mac_removal() and thus at this point there is no + * binding etc. so nothing needs to be done here. + */ if (vif->type == NL80211_IFTYPE_P2P_DEVICE) { + if (mvmvif->deflink.phy_ctxt) { + iwl_mvm_phy_ctxt_unref(mvm, mvmvif->deflink.phy_ctxt); + mvmvif->deflink.phy_ctxt = NULL; + } mvm->p2p_device_vif = NULL; - iwl_mvm_rm_p2p_bcast_sta(mvm, vif); - iwl_mvm_binding_remove_vif(mvm, vif); - iwl_mvm_phy_ctxt_unref(mvm, mvmvif->deflink.phy_ctxt); - mvmvif->deflink.phy_ctxt = NULL; } iwl_mvm_mac_ctxt_remove(mvm, vif); @@ -2684,7 +2666,7 @@ } void iwl_mvm_protect_assoc(struct iwl_mvm *mvm, struct ieee80211_vif *vif, - u32 duration_override) + u32 duration_override, unsigned int link_id) { u32 duration = IWL_MVM_TE_SESSION_PROTECTION_MAX_TIME_MS; u32 min_duration = IWL_MVM_TE_SESSION_PROTECTION_MIN_TIME_MS; @@ -2704,7 +2686,8 @@ if (fw_has_capa(&mvm->fw->ucode_capa, IWL_UCODE_TLV_CAPA_SESSION_PROT_CMD)) iwl_mvm_schedule_session_protection(mvm, vif, 900, - min_duration, false); + min_duration, false, + link_id); else iwl_mvm_protect_session(mvm, vif, duration, min_duration, 500, false); @@ -2800,6 +2783,7 @@ { struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif); int ret; + int i; bool send_he_cmd = false; /* @@ -2860,8 +2844,9 @@ /* clear statistics to get clean beacon counter */ iwl_mvm_request_statistics(mvm, true); - memset(&mvmvif->deflink.beacon_stats, 0, - sizeof(mvmvif->deflink.beacon_stats)); + for_each_mvm_vif_valid_link(mvmvif, i) + memset(&mvmvif->link[i]->beacon_stats, 0, + sizeof(mvmvif->link[i]->beacon_stats)); /* add quota for this interface */ ret = iwl_mvm_update_quotas(mvm, true, NULL); @@ -2908,7 +2893,7 @@ * time could be small without us having heard * a beacon yet. */ - iwl_mvm_protect_assoc(mvm, vif, 0); + iwl_mvm_protect_assoc(mvm, vif, 0, 0); } iwl_mvm_sf_update(mvm, vif, false); @@ -3275,22 +3260,6 @@ struct ieee80211_bss_conf *bss_conf, u64 changes) { - static const struct iwl_mvm_bss_info_changed_ops callbacks = { - .bss_info_changed_sta = iwl_mvm_bss_info_changed_station, - .bss_info_changed_ap_ibss = iwl_mvm_bss_info_changed_ap_ibss, - }; - - iwl_mvm_bss_info_changed_common(hw, vif, bss_conf, &callbacks, - changes); -} - -void -iwl_mvm_bss_info_changed_common(struct ieee80211_hw *hw, - struct ieee80211_vif *vif, - struct ieee80211_bss_conf *bss_conf, - const struct iwl_mvm_bss_info_changed_ops *callbacks, - u64 changes) -{ struct iwl_mvm *mvm = IWL_MAC80211_GET_MVM(hw); mutex_lock(&mvm->mutex); @@ -3300,12 +3269,11 @@ switch (vif->type) { case NL80211_IFTYPE_STATION: - callbacks->bss_info_changed_sta(mvm, vif, bss_conf, changes); + iwl_mvm_bss_info_changed_station(mvm, vif, bss_conf, changes); break; case NL80211_IFTYPE_AP: case NL80211_IFTYPE_ADHOC: - callbacks->bss_info_changed_ap_ibss(mvm, vif, bss_conf, - changes); + iwl_mvm_bss_info_changed_ap_ibss(mvm, vif, bss_conf, changes); break; case NL80211_IFTYPE_MONITOR: if (changes & BSS_CHANGED_MU_GROUPS) @@ -4027,12 +3995,25 @@ callbacks->mac_ctxt_changed(mvm, vif, false); iwl_mvm_mei_host_associated(mvm, vif, mvm_sta); + + /* when client is authorized (AP station marked as such), + * try to enable more links + */ + if (vif->type == NL80211_IFTYPE_STATION && + !test_bit(IWL_MVM_STATUS_IN_HW_RESTART, &mvm->status)) + iwl_mvm_mld_select_links(mvm, vif, false); } mvm_sta->authorized = true; iwl_mvm_rs_rate_init_all_links(mvm, vif, sta); + /* MFP is set by default before the station is authorized. + * Clear it here in case it's not used. + */ + if (!sta->mfp) + return callbacks->update_sta(mvm, vif, sta); + return 0; } @@ -4266,7 +4247,7 @@ struct iwl_mvm *mvm = IWL_MAC80211_GET_MVM(hw); mutex_lock(&mvm->mutex); - iwl_mvm_protect_assoc(mvm, vif, info->duration); + iwl_mvm_protect_assoc(mvm, vif, info->duration, info->link_id); mutex_unlock(&mvm->mutex); } @@ -4646,6 +4627,39 @@ #define AUX_ROC_MAX_DELAY MSEC_TO_TU(600) #define AUX_ROC_SAFETY_BUFFER MSEC_TO_TU(20) #define AUX_ROC_MIN_SAFETY_BUFFER MSEC_TO_TU(10) + +static void iwl_mvm_roc_duration_and_delay(struct ieee80211_vif *vif, + u32 duration_ms, + u32 *duration_tu, + u32 *delay) +{ + u32 dtim_interval = vif->bss_conf.dtim_period * + vif->bss_conf.beacon_int; + + *delay = AUX_ROC_MIN_DELAY; + *duration_tu = MSEC_TO_TU(duration_ms); + + /* + * If we are associated we want the delay time to be at least one + * dtim interval so that the FW can wait until after the DTIM and + * then start the time event, this will potentially allow us to + * remain off-channel for the max duration. + * Since we want to use almost a whole dtim interval we would also + * like the delay to be for 2-3 dtim intervals, in case there are + * other time events with higher priority. + */ + if (vif->cfg.assoc) { + *delay = min_t(u32, dtim_interval * 3, AUX_ROC_MAX_DELAY); + /* We cannot remain off-channel longer than the DTIM interval */ + if (dtim_interval <= *duration_tu) { + *duration_tu = dtim_interval - AUX_ROC_SAFETY_BUFFER; + if (*duration_tu <= AUX_ROC_MIN_DURATION) + *duration_tu = dtim_interval - + AUX_ROC_MIN_SAFETY_BUFFER; + } + } +} + static int iwl_mvm_send_aux_roc_cmd(struct iwl_mvm *mvm, struct ieee80211_channel *channel, struct ieee80211_vif *vif, @@ -4656,8 +4670,6 @@ struct iwl_mvm_time_event_data *te_data = &mvmvif->hs_time_event_data; static const u16 time_event_response[] = { HOT_SPOT_CMD }; struct iwl_notification_wait wait_time_event; - u32 dtim_interval = vif->bss_conf.dtim_period * - vif->bss_conf.beacon_int; u32 req_dur, delay; struct iwl_hs20_roc_req aux_roc_req = { .action = cpu_to_le32(FW_CTXT_ACTION_ADD), @@ -4678,29 +4690,7 @@ /* Set the time and duration */ tail->apply_time = cpu_to_le32(iwl_mvm_get_systime(mvm)); - delay = AUX_ROC_MIN_DELAY; - req_dur = MSEC_TO_TU(duration); - - /* - * If we are associated we want the delay time to be at least one - * dtim interval so that the FW can wait until after the DTIM and - * then start the time event, this will potentially allow us to - * remain off-channel for the max duration. - * Since we want to use almost a whole dtim interval we would also - * like the delay to be for 2-3 dtim intervals, in case there are - * other time events with higher priority. - */ - if (vif->cfg.assoc) { - delay = min_t(u32, dtim_interval * 3, AUX_ROC_MAX_DELAY); - /* We cannot remain off-channel longer than the DTIM interval */ - if (dtim_interval <= req_dur) { - req_dur = dtim_interval - AUX_ROC_SAFETY_BUFFER; - if (req_dur <= AUX_ROC_MIN_DURATION) - req_dur = dtim_interval - - AUX_ROC_MIN_SAFETY_BUFFER; - } - } - + iwl_mvm_roc_duration_and_delay(vif, duration, &req_dur, &delay); tail->duration = cpu_to_le32(req_dur); tail->apply_time_max_delay = cpu_to_le32(delay); @@ -4708,8 +4698,8 @@ "ROC: Requesting to remain on channel %u for %ums\n", channel->hw_value, req_dur); IWL_DEBUG_TE(mvm, - "\t(requested = %ums, max_delay = %ums, dtim_interval = %ums)\n", - duration, delay, dtim_interval); + "\t(requested = %ums, max_delay = %ums)\n", + duration, delay); /* Set the node address */ memcpy(tail->node_addr, vif->addr, ETH_ALEN); @@ -4767,6 +4757,48 @@ return res; } +static int iwl_mvm_roc_add_cmd(struct iwl_mvm *mvm, + struct ieee80211_channel *channel, + struct ieee80211_vif *vif, + int duration, u32 activity) +{ + int res; + u32 duration_tu, delay; + struct iwl_roc_req roc_req = { + .action = cpu_to_le32(FW_CTXT_ACTION_ADD), + .activity = cpu_to_le32(activity), + .sta_id = cpu_to_le32(mvm->aux_sta.sta_id), + }; + + lockdep_assert_held(&mvm->mutex); + + /* Set the channel info data */ + iwl_mvm_set_chan_info(mvm, &roc_req.channel_info, + channel->hw_value, + iwl_mvm_phy_band_from_nl80211(channel->band), + IWL_PHY_CHANNEL_MODE20, 0); + + iwl_mvm_roc_duration_and_delay(vif, duration, &duration_tu, + &delay); + roc_req.duration = cpu_to_le32(duration_tu); + roc_req.max_delay = cpu_to_le32(delay); + + IWL_DEBUG_TE(mvm, + "\t(requested = %ums, max_delay = %ums)\n", + duration, delay); + IWL_DEBUG_TE(mvm, + "Requesting to remain on channel %u for %utu\n", + channel->hw_value, duration_tu); + + /* Set the node address */ + memcpy(roc_req.node_addr, vif->addr, ETH_ALEN); + + res = iwl_mvm_send_cmd_pdu(mvm, WIDE_ID(MAC_CONF_GROUP, ROC_CMD), + 0, sizeof(roc_req), &roc_req); + + return res; +} + static int iwl_mvm_add_aux_sta_for_hs20(struct iwl_mvm *mvm, u32 lmac_id) { int ret = 0; @@ -4787,31 +4819,20 @@ return ret; } -static int iwl_mvm_roc_switch_binding(struct iwl_mvm *mvm, - struct ieee80211_vif *vif, - struct iwl_mvm_phy_ctxt *new_phy_ctxt) +static int iwl_mvm_roc_link(struct iwl_mvm *mvm, struct ieee80211_vif *vif) { - struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif); - int ret = 0; + int ret; lockdep_assert_held(&mvm->mutex); - /* - * Unbind the P2P_DEVICE from the current PHY context, - * and if the PHY context is not used remove it. - */ - ret = iwl_mvm_binding_remove_vif(mvm, vif); - if (WARN(ret, "Failed unbinding P2P_DEVICE\n")) + ret = iwl_mvm_binding_add_vif(mvm, vif); + if (WARN(ret, "Failed binding P2P_DEVICE\n")) return ret; - iwl_mvm_phy_ctxt_unref(mvm, mvmvif->deflink.phy_ctxt); - - /* Bind the P2P_DEVICE to the current PHY Context */ - mvmvif->deflink.phy_ctxt = new_phy_ctxt; - - ret = iwl_mvm_binding_add_vif(mvm, vif); - WARN(ret, "Failed binding P2P_DEVICE\n"); - return ret; + /* The station and queue allocation must be done only after the binding + * is done, as otherwise the FW might incorrectly configure its state. + */ + return iwl_mvm_add_p2p_bcast_sta(mvm, vif); } static int iwl_mvm_roc(struct ieee80211_hw *hw, @@ -4822,12 +4843,81 @@ { static const struct iwl_mvm_roc_ops ops = { .add_aux_sta_for_hs20 = iwl_mvm_add_aux_sta_for_hs20, - .switch_phy_ctxt = iwl_mvm_roc_switch_binding, + .link = iwl_mvm_roc_link, }; return iwl_mvm_roc_common(hw, vif, channel, duration, type, &ops); } +static int iwl_mvm_roc_station(struct iwl_mvm *mvm, + struct ieee80211_channel *channel, + struct ieee80211_vif *vif, + int duration) +{ + int ret; + u32 cmd_id = WIDE_ID(MAC_CONF_GROUP, ROC_CMD); + u8 fw_ver = iwl_fw_lookup_cmd_ver(mvm->fw, cmd_id, + IWL_FW_CMD_VER_UNKNOWN); + + if (fw_ver == IWL_FW_CMD_VER_UNKNOWN) { + ret = iwl_mvm_send_aux_roc_cmd(mvm, channel, vif, duration); + } else if (fw_ver == 3) { + ret = iwl_mvm_roc_add_cmd(mvm, channel, vif, duration, + ROC_ACTIVITY_HOTSPOT); + } else { + ret = -EOPNOTSUPP; + IWL_ERR(mvm, "ROC command version %d mismatch!\n", fw_ver); + } + + return ret; +} + +static int iwl_mvm_p2p_find_phy_ctxt(struct iwl_mvm *mvm, + struct ieee80211_vif *vif, + struct ieee80211_channel *channel) +{ + struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif); + struct cfg80211_chan_def chandef; + int i; + + lockdep_assert_held(&mvm->mutex); + + if (mvmvif->deflink.phy_ctxt && + channel == mvmvif->deflink.phy_ctxt->channel) + return 0; + + /* Try using a PHY context that is already in use */ + for (i = 0; i < NUM_PHY_CTX; i++) { + struct iwl_mvm_phy_ctxt *phy_ctxt = &mvm->phy_ctxts[i]; + + if (!phy_ctxt->ref || mvmvif->deflink.phy_ctxt == phy_ctxt) + continue; + + if (channel == phy_ctxt->channel) { + if (mvmvif->deflink.phy_ctxt) + iwl_mvm_phy_ctxt_unref(mvm, + mvmvif->deflink.phy_ctxt); + + mvmvif->deflink.phy_ctxt = phy_ctxt; + iwl_mvm_phy_ctxt_ref(mvm, mvmvif->deflink.phy_ctxt); + return 0; + } + } + + /* We already have a phy_ctxt, but it's not on the right channel */ + if (mvmvif->deflink.phy_ctxt) + iwl_mvm_phy_ctxt_unref(mvm, mvmvif->deflink.phy_ctxt); + + mvmvif->deflink.phy_ctxt = iwl_mvm_get_free_phy_ctxt(mvm); + if (!mvmvif->deflink.phy_ctxt) + return -ENOSPC; + + cfg80211_chandef_create(&chandef, channel, NL80211_CHAN_NO_HT); + + return iwl_mvm_phy_ctxt_add(mvm, mvmvif->deflink.phy_ctxt, + &chandef, 1, 1); +} + /* Execute the common part for MLD and non-MLD modes */ int iwl_mvm_roc_common(struct ieee80211_hw *hw, struct ieee80211_vif *vif, struct ieee80211_channel *channel, int duration, @@ -4835,12 +4925,8 @@ const struct iwl_mvm_roc_ops *ops) { struct iwl_mvm *mvm = IWL_MAC80211_GET_MVM(hw); - struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif); - struct cfg80211_chan_def chandef; - struct iwl_mvm_phy_ctxt *phy_ctxt; - bool band_change_removal; - int ret, i; u32 lmac_id; + int ret; IWL_DEBUG_MAC80211(mvm, "enter (%d, %d, %d)\n", channel->hw_value, duration, type); @@ -4860,89 +4946,27 @@ /* Use aux roc framework (HS20) */ ret = ops->add_aux_sta_for_hs20(mvm, lmac_id); if (!ret) - ret = iwl_mvm_send_aux_roc_cmd(mvm, channel, - vif, duration); + ret = iwl_mvm_roc_station(mvm, channel, vif, duration); goto out_unlock; case NL80211_IFTYPE_P2P_DEVICE: /* handle below */ break; default: - IWL_ERR(mvm, "vif isn't P2P_DEVICE: %d\n", vif->type); + IWL_ERR(mvm, "ROC: Invalid vif type=%u\n", vif->type); ret = -EINVAL; goto out_unlock; } - for (i = 0; i < NUM_PHY_CTX; i++) { - phy_ctxt = &mvm->phy_ctxts[i]; - if (phy_ctxt->ref == 0 || mvmvif->deflink.phy_ctxt == phy_ctxt) - continue; - - if (phy_ctxt->ref && channel == phy_ctxt->channel) { - ret = ops->switch_phy_ctxt(mvm, vif, phy_ctxt); - if (ret) - goto out_unlock; - iwl_mvm_phy_ctxt_ref(mvm, mvmvif->deflink.phy_ctxt); - goto schedule_time_event; - } - } - - /* Need to update the PHY context only if the ROC channel changed */ - if (channel == mvmvif->deflink.phy_ctxt->channel) - goto schedule_time_event; - - cfg80211_chandef_create(&chandef, channel, NL80211_CHAN_NO_HT); - - /* - * Check if the remain-on-channel is on a different band and that - * requires context removal, see iwl_mvm_phy_ctxt_changed(). If - * so, we'll need to release and then re-configure here, since we - * must not remove a PHY context that's part of a binding. - */ - band_change_removal = - fw_has_capa(&mvm->fw->ucode_capa, - IWL_UCODE_TLV_CAPA_BINDING_CDB_SUPPORT) && - mvmvif->deflink.phy_ctxt->channel->band != chandef.chan->band; - - if (mvmvif->deflink.phy_ctxt->ref == 1 && !band_change_removal) { - /* - * Change the PHY context configuration as it is currently - * referenced only by the P2P Device MAC (and we can modify it) - */ - ret = iwl_mvm_phy_ctxt_changed(mvm, mvmvif->deflink.phy_ctxt, - &chandef, 1, 1); - if (ret) - goto out_unlock; - } else { - /* - * The PHY context is shared with other MACs (or we're trying to - * switch bands), so remove the P2P Device from the binding, - * allocate an new PHY context and create a new binding. - */ - phy_ctxt = iwl_mvm_get_free_phy_ctxt(mvm); - if (!phy_ctxt) { - ret = -ENOSPC; - goto out_unlock; - } - - ret = iwl_mvm_phy_ctxt_changed(mvm, phy_ctxt, &chandef, - 1, 1); - if (ret) { - IWL_ERR(mvm, "Failed to change PHY context\n"); - goto out_unlock; - } - - ret = ops->switch_phy_ctxt(mvm, vif, phy_ctxt); - if (ret) - goto out_unlock; + ret = iwl_mvm_p2p_find_phy_ctxt(mvm, vif, channel); + if (ret) + goto out_unlock; - iwl_mvm_phy_ctxt_ref(mvm, mvmvif->deflink.phy_ctxt); - } + ret = ops->link(mvm, vif); + if (ret) + goto out_unlock; -schedule_time_event: - /* Schedule the time events */ ret = iwl_mvm_start_p2p_roc(mvm, vif, duration, type); - out_unlock: mutex_unlock(&mvm->mutex); IWL_DEBUG_MAC80211(mvm, "leave\n"); @@ -5014,15 +5038,14 @@ goto out; } - ret = iwl_mvm_phy_ctxt_changed(mvm, phy_ctxt, def, - ctx->rx_chains_static, - ctx->rx_chains_dynamic); + ret = iwl_mvm_phy_ctxt_add(mvm, phy_ctxt, def, + ctx->rx_chains_static, + ctx->rx_chains_dynamic); if (ret) { IWL_ERR(mvm, "Failed to add PHY context\n"); goto out; } - iwl_mvm_phy_ctxt_ref(mvm, phy_ctxt); *phy_ctxt_id = phy_ctxt->id; out: @@ -5486,8 +5509,8 @@ return mvm->ibss_manager; } -int iwl_mvm_set_tim(struct ieee80211_hw *hw, struct ieee80211_sta *sta, - bool set) +static int iwl_mvm_set_tim(struct ieee80211_hw *hw, struct ieee80211_sta *sta, + bool set) { struct iwl_mvm *mvm = IWL_MAC80211_GET_MVM(hw); struct iwl_mvm_sta *mvm_sta = iwl_mvm_sta_from_mac80211(sta); @@ -5893,7 +5916,8 @@ } if (drop) { - if (iwl_mvm_flush_sta(mvm, mvmsta, false)) + if (iwl_mvm_flush_sta(mvm, mvmsta->deflink.sta_id, + mvmsta->tfd_queue_msk)) IWL_ERR(mvm, "flush request fail\n"); } else { if (iwl_mvm_has_new_tx_api(mvm)) @@ -5915,22 +5939,21 @@ void iwl_mvm_mac_flush_sta(struct ieee80211_hw *hw, struct ieee80211_vif *vif, struct ieee80211_sta *sta) { + struct iwl_mvm_sta *mvmsta = iwl_mvm_sta_from_mac80211(sta); struct iwl_mvm *mvm = IWL_MAC80211_GET_MVM(hw); - int i; + struct iwl_mvm_link_sta *mvm_link_sta; + struct ieee80211_link_sta *link_sta; + int link_id; mutex_lock(&mvm->mutex); - for (i = 0; i < mvm->fw->ucode_capa.num_stations; i++) { - struct iwl_mvm_sta *mvmsta; - struct ieee80211_sta *tmp; - - tmp = rcu_dereference_protected(mvm->fw_id_to_mac_id[i], - lockdep_is_held(&mvm->mutex)); - if (tmp != sta) + for_each_sta_active_link(vif, sta, link_sta, link_id) { + mvm_link_sta = rcu_dereference_protected(mvmsta->link[link_id], + lockdep_is_held(&mvm->mutex)); + if (!mvm_link_sta) continue; - mvmsta = iwl_mvm_sta_from_mac80211(sta); - - if (iwl_mvm_flush_sta(mvm, mvmsta, false)) + if (iwl_mvm_flush_sta(mvm, mvm_link_sta->sta_id, + mvmsta->tfd_queue_msk)) IWL_ERR(mvm, "flush request fail\n"); } mutex_unlock(&mvm->mutex); @@ -5940,7 +5963,11 @@ struct survey_info *survey) { struct iwl_mvm *mvm = IWL_MAC80211_GET_MVM(hw); - int ret; + int ret = 0; + u8 cmd_ver = iwl_fw_lookup_cmd_ver(mvm->fw, + WIDE_ID(SYSTEM_GROUP, + SYSTEM_STATISTICS_CMD), + IWL_FW_CMD_VER_UNKNOWN); memset(survey, 0, sizeof(*survey)); @@ -5960,13 +5987,8 @@ goto out; } - survey->filled = SURVEY_INFO_TIME | - SURVEY_INFO_TIME_RX | - SURVEY_INFO_TIME_TX | - SURVEY_INFO_TIME_SCAN; - survey->time = mvm->accu_radio_stats.on_time_rf + - mvm->radio_stats.on_time_rf; - do_div(survey->time, USEC_PER_MSEC); + survey->filled = SURVEY_INFO_TIME_RX | + SURVEY_INFO_TIME_TX; survey->time_rx = mvm->accu_radio_stats.rx_time + mvm->radio_stats.rx_time; @@ -5976,11 +5998,20 @@ mvm->radio_stats.tx_time; do_div(survey->time_tx, USEC_PER_MSEC); + /* the new fw api doesn't support the following fields */ + if (cmd_ver != IWL_FW_CMD_VER_UNKNOWN) + goto out; + + survey->filled |= SURVEY_INFO_TIME | + SURVEY_INFO_TIME_SCAN; + survey->time = mvm->accu_radio_stats.on_time_rf + + mvm->radio_stats.on_time_rf; + do_div(survey->time, USEC_PER_MSEC); + survey->time_scan = mvm->accu_radio_stats.on_time_scan + mvm->radio_stats.on_time_scan; do_div(survey->time_scan, USEC_PER_MSEC); - ret = 0; out: mutex_unlock(&mvm->mutex); return ret; @@ -6129,6 +6160,7 @@ struct iwl_mvm *mvm = IWL_MAC80211_GET_MVM(hw); struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif); struct iwl_mvm_sta *mvmsta = iwl_mvm_sta_from_mac80211(sta); + int i; if (mvmsta->deflink.avg_energy) { sinfo->signal_avg = -(s8)mvmsta->deflink.avg_energy; @@ -6157,8 +6189,11 @@ if (iwl_mvm_request_statistics(mvm, false)) goto unlock; - sinfo->rx_beacon = mvmvif->deflink.beacon_stats.num_beacons + - mvmvif->deflink.beacon_stats.accu_num_beacons; + sinfo->rx_beacon = 0; + for_each_mvm_vif_valid_link(mvmvif, i) + sinfo->rx_beacon += mvmvif->link[i]->beacon_stats.num_beacons + + mvmvif->link[i]->beacon_stats.accu_num_beacons; + sinfo->filled |= BIT_ULL(NL80211_STA_INFO_BEACON_RX); if (mvmvif->deflink.beacon_stats.avg_signal) { /* firmware only reports a value after RXing a few beacons */ @@ -6552,6 +6587,7 @@ .can_aggregate_in_amsdu = iwl_mvm_mac_can_aggregate, #ifdef CPTCFG_IWLWIFI_DEBUGFS + .vif_add_debugfs = iwl_mvm_vif_add_debugfs, .link_sta_add_debugfs = iwl_mvm_link_sta_add_debugfs, #endif .set_hw_timestamp = iwl_mvm_set_hw_timestamp, diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/mac-ctxt.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/mac-ctxt.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/mac-ctxt.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/mac-ctxt.c 2023-10-04 04:18:43.000000000 +0800 @@ -291,6 +291,10 @@ INIT_LIST_HEAD(&mvmvif->time_event_data.list); mvmvif->time_event_data.id = TE_MAX; + mvmvif->deflink.bcast_sta.sta_id = IWL_MVM_INVALID_STA; + mvmvif->deflink.mcast_sta.sta_id = IWL_MVM_INVALID_STA; + mvmvif->deflink.ap_sta_id = IWL_MVM_INVALID_STA; + /* No need to allocate data queues to P2P Device MAC and NAN.*/ if (vif->type == NL80211_IFTYPE_P2P_DEVICE || vif->type == NL80211_IFTYPE_NAN) @@ -306,10 +310,6 @@ mvmvif->deflink.cab_queue = IWL_MVM_DQA_GCAST_QUEUE; } - mvmvif->deflink.bcast_sta.sta_id = IWL_MVM_INVALID_STA; - mvmvif->deflink.mcast_sta.sta_id = IWL_MVM_INVALID_STA; - mvmvif->deflink.ap_sta_id = IWL_MVM_INVALID_STA; - for (i = 0; i < NUM_IWL_MVM_SMPS_REQ; i++) mvmvif->deflink.smps_requests[i] = IEEE80211_SMPS_AUTOMATIC; diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/mld-key.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/mld-key.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/mld-key.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/mld-key.c 2023-10-04 04:18:43.000000000 +0800 @@ -97,7 +97,12 @@ if (!sta && vif->type == NL80211_IFTYPE_STATION) sta = mvmvif->ap_sta; - if (!IS_ERR_OR_NULL(sta) && sta->mfp) + /* Set the MFP flag also for an AP interface where the key is an IGTK + * key as in such a case the station would always be NULL + */ + if ((!IS_ERR_OR_NULL(sta) && sta->mfp) || + (vif->type == NL80211_IFTYPE_AP && + (keyconf->keyidx == 4 || keyconf->keyidx == 5))) flags |= IWL_SEC_KEY_FLAG_MFP; return flags; @@ -273,8 +278,7 @@ if (mvm_link) mvm_link->igtk = keyconf; - /* - * We don't really need this, but need it to be not invalid, + /* We don't really need this, but need it to be not invalid, * and if we switch links multiple times it might go to be * invalid when removed. */ diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/mld-mac80211.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/mld-mac80211.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/mld-mac80211.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/mld-mac80211.c 2023-10-04 04:18:43.000000000 +0800 @@ -10,6 +10,7 @@ struct iwl_mvm *mvm = IWL_MAC80211_GET_MVM(hw); struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif); int ret; + int i; mutex_lock(&mvm->mutex); @@ -23,8 +24,9 @@ /* make sure that beacon statistics don't go backwards with FW reset */ if (test_bit(IWL_MVM_STATUS_IN_HW_RESTART, &mvm->status)) - mvmvif->deflink.beacon_stats.accu_num_beacons += - mvmvif->deflink.beacon_stats.num_beacons; + for_each_mvm_vif_valid_link(mvmvif, i) + mvmvif->link[i]->beacon_stats.accu_num_beacons += + mvmvif->link[i]->beacon_stats.num_beacons; /* Allocate resources for the MAC context, and add it to the fw */ ret = iwl_mvm_mac_ctxt_init(mvm, vif); @@ -57,42 +59,15 @@ IEEE80211_VIF_SUPPORTS_CQM_RSSI; } - /* - * P2P_DEVICE interface does not have a channel context assigned to it, - * so a dedicated PHY context is allocated to it and the corresponding - * MAC context is bound to it at this stage. - */ - if (vif->type == NL80211_IFTYPE_P2P_DEVICE) { - mvmvif->deflink.phy_ctxt = iwl_mvm_get_free_phy_ctxt(mvm); - if (!mvmvif->deflink.phy_ctxt) { - ret = -ENOSPC; - goto out_free_bf; - } - - iwl_mvm_phy_ctxt_ref(mvm, mvmvif->deflink.phy_ctxt); - ret = iwl_mvm_add_link(mvm, vif, &vif->bss_conf); - if (ret) - goto out_unref_phy; - - ret = iwl_mvm_link_changed(mvm, vif, &vif->bss_conf, - LINK_CONTEXT_MODIFY_ACTIVE | - LINK_CONTEXT_MODIFY_RATES_INFO, - true); - if (ret) - goto out_remove_link; - - ret = iwl_mvm_mld_add_bcast_sta(mvm, vif, &vif->bss_conf); - if (ret) - goto out_remove_link; + ret = iwl_mvm_add_link(mvm, vif, &vif->bss_conf); + if (ret) + goto out_free_bf; - /* Save a pointer to p2p device vif, so it can later be used to - * update the p2p device MAC when a GO is started/stopped */ + /* Save a pointer to p2p device vif, so it can later be used to + * update the p2p device MAC when a GO is started/stopped + */ + if (vif->type == NL80211_IFTYPE_P2P_DEVICE) mvm->p2p_device_vif = vif; - } else { - ret = iwl_mvm_add_link(mvm, vif, &vif->bss_conf); - if (ret) - goto out_free_bf; - } ret = iwl_mvm_power_update_mac(mvm); if (ret) @@ -107,7 +82,7 @@ ieee80211_hw_set(mvm->hw, RX_INCLUDES_FCS); } - iwl_mvm_vif_dbgfs_register(mvm, vif); + iwl_mvm_vif_dbgfs_add_link(mvm, vif); if (!test_bit(IWL_MVM_STATUS_IN_HW_RESTART, &mvm->status) && vif->type == NL80211_IFTYPE_STATION && !vif->p2p && @@ -125,10 +100,6 @@ goto out_unlock; - out_remove_link: - iwl_mvm_disable_link(mvm, vif, &vif->bss_conf); - out_unref_phy: - iwl_mvm_phy_ctxt_unref(mvm, mvmvif->deflink.phy_ctxt); out_free_bf: if (mvm->bf_allowed_vif == mvmvif) { mvm->bf_allowed_vif = NULL; @@ -136,7 +107,6 @@ IEEE80211_VIF_SUPPORTS_CQM_RSSI); } out_remove_mac: - mvmvif->deflink.phy_ctxt = NULL; mvmvif->link[0] = NULL; iwl_mvm_mld_mac_ctxt_remove(mvm, vif); out_unlock: @@ -183,7 +153,7 @@ if (vif->bss_conf.ftm_responder) memset(&mvm->ftm_resp_stats, 0, sizeof(mvm->ftm_resp_stats)); - iwl_mvm_vif_dbgfs_clean(mvm, vif); + iwl_mvm_vif_dbgfs_rm_link(mvm, vif); /* * For AP/GO interface, the tear down of the resources allocated to the @@ -206,14 +176,18 @@ iwl_mvm_power_update_mac(mvm); + /* Before the interface removal, mac80211 would cancel the ROC, and the + * ROC worker would be scheduled if needed. The worker would be flushed + * in iwl_mvm_prepare_mac_removal() and thus at this point the link is + * not active. So need only to remove the link. + */ if (vif->type == NL80211_IFTYPE_P2P_DEVICE) { + if (mvmvif->deflink.phy_ctxt) { + iwl_mvm_phy_ctxt_unref(mvm, mvmvif->deflink.phy_ctxt); + mvmvif->deflink.phy_ctxt = NULL; + } mvm->p2p_device_vif = NULL; - - /* P2P device uses only one link */ - iwl_mvm_mld_rm_bcast_sta(mvm, vif, &vif->bss_conf); - iwl_mvm_disable_link(mvm, vif, &vif->bss_conf); - iwl_mvm_phy_ctxt_unref(mvm, mvmvif->deflink.phy_ctxt); - mvmvif->deflink.phy_ctxt = NULL; + iwl_mvm_remove_link(mvm, vif, &vif->bss_conf); } else { iwl_mvm_disable_link(mvm, vif, &vif->bss_conf); } @@ -266,8 +240,8 @@ mvmvif->esr_active = true; - /* Disable SMPS overrideing by user */ - vif->driver_flags |= IEEE80211_VIF_DISABLE_SMPS_OVERRIDE; + /* Indicate to mac80211 that EML is enabled */ + vif->driver_flags |= IEEE80211_VIF_EML_ACTIVE; #ifdef CPTCFG_IWLWIFI_DEBUGFS /* Disable RLC overriding by user */ mvm->dbgfs_rx_phyinfo = 0; @@ -428,7 +402,7 @@ mvmvif->esr_active = false; - vif->driver_flags &= ~IEEE80211_VIF_DISABLE_SMPS_OVERRIDE; + vif->driver_flags &= ~IEEE80211_VIF_EML_ACTIVE; iwl_mvm_update_smps_on_active_links(mvm, vif, IWL_MVM_SMPS_REQ_FW, IEEE80211_SMPS_AUTOMATIC); @@ -520,6 +494,11 @@ mutex_lock(&mvm->mutex); __iwl_mvm_mld_unassign_vif_chanctx(mvm, vif, link_conf, ctx, false); + /* in the non-MLD case, remove/re-add the link to clean up FW state */ + if (!ieee80211_vif_is_mld(vif) && !WARN_ON_ONCE(vif->cfg.assoc)) { + iwl_mvm_remove_link(mvm, vif, link_conf); + iwl_mvm_add_link(mvm, vif, link_conf); + } mutex_unlock(&mvm->mutex); } @@ -652,6 +631,126 @@ &callbacks); } +struct iwl_mvm_link_sel_data { + u8 link_id; + enum nl80211_band band; + bool active; +}; + +static bool iwl_mvm_mld_valid_link_pair(struct iwl_mvm_link_sel_data *a, + struct iwl_mvm_link_sel_data *b) +{ + return a->band != b->band; +} + +void iwl_mvm_mld_select_links(struct iwl_mvm *mvm, struct ieee80211_vif *vif, + bool valid_links_changed) +{ + struct iwl_mvm_link_sel_data data[IEEE80211_MLD_MAX_NUM_LINKS]; + unsigned long usable_links = ieee80211_vif_usable_links(vif); + u32 max_active_links = iwl_mvm_max_active_links(mvm, vif); + u16 new_active_links; + u8 link_id, n_data = 0, i, j; + + if (!IWL_MVM_AUTO_EML_ENABLE) + return; + + if (!ieee80211_vif_is_mld(vif) || usable_links == 1) + return; + + /* The logic below is a simple version that doesn't suit more than 2 + * links + */ + WARN_ON_ONCE(max_active_links > 2); + + /* if only a single active link is supported, assume that the one + * selected by higher layer for connection establishment is the best. + */ + if (max_active_links == 1 && !valid_links_changed) + return; + + /* If we are already using the maximal number of active links, don't do + * any change. This can later be optimized to pick a 'better' link pair. + */ + if (hweight16(vif->active_links) == max_active_links) + return; + + rcu_read_lock(); + + for_each_set_bit(link_id, &usable_links, IEEE80211_MLD_MAX_NUM_LINKS) { + struct ieee80211_bss_conf *link_conf = + rcu_dereference(vif->link_conf[link_id]); + + if (WARN_ON_ONCE(!link_conf)) + continue; + + data[n_data].link_id = link_id; + data[n_data].band = link_conf->chandef.chan->band; + data[n_data].active = vif->active_links & BIT(link_id); + n_data++; + } + + rcu_read_unlock(); + + /* this is expected to be the current active link */ + if (n_data == 1) + return; + + new_active_links = 0; + + /* Assume that after association only a single link is active, thus, + * select only the 2nd link + */ + if (!valid_links_changed) { + for (i = 0; i < n_data; i++) { + if (data[i].active) + break; + } + + if (WARN_ON_ONCE(i == n_data)) + return; + + for (j = 0; j < n_data; j++) { + if (i == j) + continue; + + if (iwl_mvm_mld_valid_link_pair(&data[i], &data[j])) + break; + } + + if (j != n_data) + new_active_links = BIT(data[i].link_id) | + BIT(data[j].link_id); + } else { + /* Try to find a valid link pair for EMLSR operation. If a pair + * is not found continue using the current active link. + */ + for (i = 0; i < n_data; i++) { + for (j = 0; j < n_data; j++) { + if (i == j) + continue; + + if (iwl_mvm_mld_valid_link_pair(&data[i], + &data[j])) + break; + } + + /* found a valid pair for EMLSR, use it */ + if (j != n_data) { + new_active_links = BIT(data[i].link_id) | + BIT(data[j].link_id); + break; + } + } + } + + if (WARN_ON(!new_active_links)) + return; + + if (vif->active_links != new_active_links) + ieee80211_set_active_links_async(vif, new_active_links); +} + static void iwl_mvm_mld_link_info_changed_station(struct iwl_mvm *mvm, struct ieee80211_vif *vif, struct ieee80211_bss_conf *link_conf, @@ -681,7 +780,7 @@ } /* Update EHT Puncturing info */ - if (changes & BSS_CHANGED_EHT_PUNCTURING && vif->cfg.assoc && has_eht) + if (changes & BSS_CHANGED_EHT_PUNCTURING && vif->cfg.assoc) link_changes |= LINK_CONTEXT_MODIFY_EHT_PARAMS; if (link_changes) { @@ -695,6 +794,9 @@ if (ret) IWL_ERR(mvm, "failed to update MAC %pM\n", vif->addr); + if (changes & BSS_CHANGED_MLD_VALID_LINKS) + iwl_mvm_mld_select_links(mvm, vif, true); + memcpy(mvmvif->link[link_conf->link_id]->bssid, link_conf->bssid, ETH_ALEN); @@ -789,6 +891,12 @@ if (!test_bit(IWL_MVM_STATUS_IN_HW_RESTART, &mvm->status) && protect) { + /* We are in assoc so only one link is active- + * The association link + */ + unsigned int link_id = + ffs(vif->active_links) - 1; + /* If we're not restarting and still haven't * heard a beacon (dtim period unknown) then * make sure we still have enough minimum time @@ -798,7 +906,7 @@ * time could be small without us having heard * a beacon yet. */ - iwl_mvm_protect_assoc(mvm, vif, 0); + iwl_mvm_protect_assoc(mvm, vif, 0, link_id); } iwl_mvm_sf_update(mvm, vif, false); @@ -1004,37 +1112,29 @@ return 0; } -static int iwl_mvm_link_switch_phy_ctx(struct iwl_mvm *mvm, - struct ieee80211_vif *vif, - struct iwl_mvm_phy_ctxt *new_phy_ctxt) +static int iwl_mvm_mld_roc_link(struct iwl_mvm *mvm, struct ieee80211_vif *vif) { - struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif); - int ret = 0; + int ret; lockdep_assert_held(&mvm->mutex); - /* - * Inorder to change the phy_ctx of a link, the link needs to be - * inactive. Therefore, first deactivate the link, then change its - * phy_ctx, and then activate it again. - */ - ret = iwl_mvm_link_changed(mvm, vif, &vif->bss_conf, - LINK_CONTEXT_MODIFY_ACTIVE, false); - if (WARN(ret, "Failed to deactivate link\n")) + /* The PHY context ID might have changed so need to set it */ + ret = iwl_mvm_link_changed(mvm, vif, &vif->bss_conf, 0, false); + if (WARN(ret, "Failed to set PHY context ID\n")) return ret; - iwl_mvm_phy_ctxt_unref(mvm, mvmvif->deflink.phy_ctxt); - - mvmvif->deflink.phy_ctxt = new_phy_ctxt; + ret = iwl_mvm_link_changed(mvm, vif, &vif->bss_conf, + LINK_CONTEXT_MODIFY_ACTIVE | + LINK_CONTEXT_MODIFY_RATES_INFO, + true); - ret = iwl_mvm_link_changed(mvm, vif, &vif->bss_conf, 0, false); - if (WARN(ret, "Failed to deactivate link\n")) + if (WARN(ret, "Failed linking P2P_DEVICE\n")) return ret; - ret = iwl_mvm_link_changed(mvm, vif, &vif->bss_conf, - LINK_CONTEXT_MODIFY_ACTIVE, true); - WARN(ret, "Failed binding P2P_DEVICE\n"); - return ret; + /* The station and queue allocation must be done only after the linking + * is done, as otherwise the FW might incorrectly configure its state. + */ + return iwl_mvm_mld_add_bcast_sta(mvm, vif, &vif->bss_conf); } static int iwl_mvm_mld_roc(struct ieee80211_hw *hw, struct ieee80211_vif *vif, @@ -1043,7 +1143,7 @@ { static const struct iwl_mvm_roc_ops ops = { .add_aux_sta_for_hs20 = iwl_mvm_mld_add_aux_sta, - .switch_phy_ctxt = iwl_mvm_link_switch_phy_ctx, + .link = iwl_mvm_mld_roc_link, }; return iwl_mvm_roc_common(hw, vif, channel, duration, type, &ops); @@ -1209,8 +1309,6 @@ .tx_last_beacon = iwl_mvm_tx_last_beacon, - .set_tim = iwl_mvm_set_tim, - .channel_switch = iwl_mvm_channel_switch, .pre_channel_switch = iwl_mvm_pre_channel_switch, .post_channel_switch = iwl_mvm_post_channel_switch, @@ -1249,6 +1347,8 @@ .add_nan_func = iwl_mvm_add_nan_func, .del_nan_func = iwl_mvm_del_nan_func, #ifdef CPTCFG_IWLWIFI_DEBUGFS + .vif_add_debugfs = iwl_mvm_vif_add_debugfs, + .link_add_debugfs = iwl_mvm_link_add_debugfs, .link_sta_add_debugfs = iwl_mvm_link_sta_add_debugfs, #endif .set_hw_timestamp = iwl_mvm_set_hw_timestamp, diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/mld-sta.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/mld-sta.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/mld-sta.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/mld-sta.c 2023-10-04 04:18:43.000000000 +0800 @@ -350,7 +350,7 @@ return -EINVAL; if (flush) - iwl_mvm_flush_sta(mvm, int_sta, true); + iwl_mvm_flush_sta(mvm, int_sta->sta_id, int_sta->tfd_queue_msk); iwl_mvm_mld_disable_txq(mvm, BIT(int_sta->sta_id), queuptr, tid); @@ -881,6 +881,9 @@ cmd.sta_id = cpu_to_le32(mvmsta->deflink.sta_id); cmd.disable = cpu_to_le32(disable); + if (WARN_ON(iwl_mvm_has_no_host_disable_tx(mvm))) + return; + ret = iwl_mvm_send_cmd_pdu(mvm, WIDE_ID(MAC_CONF_GROUP, STA_DISABLE_TX_CMD), CMD_ASYNC, sizeof(cmd), &cmd); diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/mvm.h backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/mvm.h --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/mvm.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/mvm.h 2023-10-04 04:18:43.000000000 +0800 @@ -120,6 +120,7 @@ * if the te is in the time event list or not (when id == TE_MAX) */ u32 id; + u8 link_id; }; /* Power management */ @@ -676,18 +677,9 @@ * @queue: queue of this reorder buffer * @last_amsdu: track last ASMDU SN for duplication detection * @last_sub_index: track ASMDU sub frame index for duplication detection - * @reorder_timer: timer for frames are in the reorder buffer. For AMSDU - * it is the time of last received sub-frame - * @removed: prevent timer re-arming * @valid: reordering is valid for this queue * @lock: protect reorder buffer internal state * @mvm: mvm pointer, needed for frame timer context - * @consec_oldsn_drops: consecutive drops due to old SN - * @consec_oldsn_ampdu_gp2: A-MPDU GP2 timestamp to track - * when to apply old SN consecutive drop workaround - * @consec_oldsn_prev_drop: track whether or not an MPDU - * that was single/part of the previous A-MPDU was - * dropped due to old SN */ struct iwl_mvm_reorder_buffer { u16 head_sn; @@ -696,33 +688,21 @@ int queue; u16 last_amsdu; u8 last_sub_index; - struct timer_list reorder_timer; - bool removed; bool valid; spinlock_t lock; struct iwl_mvm *mvm; - unsigned int consec_oldsn_drops; - u32 consec_oldsn_ampdu_gp2; - unsigned int consec_oldsn_prev_drop:1; } ____cacheline_aligned_in_smp; /** - * struct _iwl_mvm_reorder_buf_entry - reorder buffer entry per-queue/per-seqno + * struct iwl_mvm_reorder_buf_entry - reorder buffer entry per-queue/per-seqno * @frames: list of skbs stored - * @reorder_time: time the packet was stored in the reorder buffer */ -struct _iwl_mvm_reorder_buf_entry { - struct sk_buff_head frames; - unsigned long reorder_time; -}; - -/* make this indirection to get the aligned thing */ struct iwl_mvm_reorder_buf_entry { - struct _iwl_mvm_reorder_buf_entry e; + struct sk_buff_head frames; } #ifndef __CHECKER__ /* sparse doesn't like this construct: "bad integer constant expression" */ -__aligned(roundup_pow_of_two(sizeof(struct _iwl_mvm_reorder_buf_entry))) +__aligned(roundup_pow_of_two(sizeof(struct sk_buff_head))) #endif ; @@ -974,6 +954,7 @@ /* the vif that requested the current scan */ struct iwl_mvm_vif *scan_vif; + u8 scan_link_id; /* rx chain antennas set through debugfs for the scan command */ u8 scan_rx_ant; @@ -1262,6 +1243,10 @@ /* Firmware RFI state &enum iwl_rfi_support_reason */ u32 fw_rfi_state; bool pldr_sync; + bool rfi_wlan_master; + bool force_enable_rfi; + bool statistics_clear; + struct iwl_rfi_config_cmd *iwl_prev_rfi_config_cmd; }; /* Extract MVM priv from op_mode and _hw */ @@ -1578,6 +1563,12 @@ IWL_UCODE_TLV_API_QUOTA_LOW_LATENCY); } +static inline bool iwl_mvm_has_no_host_disable_tx(struct iwl_mvm *mvm) +{ + return fw_has_api(&mvm->fw->ucode_capa, + IWL_UCODE_TLV_API_NO_HOST_DISABLE_TX); +} + static inline bool iwl_mvm_has_tlc_offload(const struct iwl_mvm *mvm) { return fw_has_capa(&mvm->fw->ucode_capa, @@ -1721,7 +1712,7 @@ static inline const char *iwl_mvm_get_tx_fail_reason(u32 status) { return ""; } #endif int iwl_mvm_flush_tx_path(struct iwl_mvm *mvm, u32 tfd_msk); -int iwl_mvm_flush_sta(struct iwl_mvm *mvm, void *sta, bool internal); +int iwl_mvm_flush_sta(struct iwl_mvm *mvm, u32 sta_id, u32 tfd_queue_mask); int iwl_mvm_flush_sta_tids(struct iwl_mvm *mvm, u32 sta_id, u16 tids); /* Utils to extract sta related data */ @@ -1752,6 +1743,16 @@ } /* Statistics */ +void iwl_mvm_handle_rx_system_oper_stats(struct iwl_mvm *mvm, + struct iwl_rx_cmd_buffer *rxb); +void iwl_mvm_handle_rx_system_oper_part1_stats(struct iwl_mvm *mvm, + struct iwl_rx_cmd_buffer *rxb); +static inline void +iwl_mvm_handle_rx_system_end_stats_notif(struct iwl_mvm *mvm, + struct iwl_rx_cmd_buffer *rxb) +{ +} + void iwl_mvm_handle_rx_statistics(struct iwl_mvm *mvm, struct iwl_rx_packet *pkt); void iwl_mvm_rx_statistics(struct iwl_mvm *mvm, @@ -1784,7 +1785,7 @@ rx_ant &= mvm->nvm_data->valid_tx_ant; if (mvm->set_rx_ant) - rx_ant &= mvm->set_tx_ant; + rx_ant &= mvm->set_rx_ant; return rx_ant; @@ -1970,36 +1971,6 @@ struct ieee80211_vif *vif); /* BSS Info */ -/** - * struct iwl_mvm_bss_info_changed_ops - callbacks for the bss_info_changed() - * - * Since the only difference between both MLD and - * non-MLD versions of bss_info_changed() is these function calls, - * each version will send its specific function calls to - * %iwl_mvm_bss_info_changed_common(). - * - * @bss_info_changed_sta: pointer to the function that handles changes - * in bss_info in sta mode - * @bss_info_changed_ap_ibss: pointer to the function that handles changes - * in bss_info in ap and ibss modes - */ -struct iwl_mvm_bss_info_changed_ops { - void (*bss_info_changed_sta)(struct iwl_mvm *mvm, - struct ieee80211_vif *vif, - struct ieee80211_bss_conf *bss_conf, - u64 changes); - void (*bss_info_changed_ap_ibss)(struct iwl_mvm *mvm, - struct ieee80211_vif *vif, - struct ieee80211_bss_conf *bss_conf, - u64 changes); -}; - -void -iwl_mvm_bss_info_changed_common(struct ieee80211_hw *hw, - struct ieee80211_vif *vif, - struct ieee80211_bss_conf *bss_conf, - const struct iwl_mvm_bss_info_changed_ops *callbacks, - u64 changes); void iwl_mvm_bss_info_changed_station_common(struct iwl_mvm *mvm, struct ieee80211_vif *vif, struct ieee80211_bss_conf *link_conf, @@ -2019,13 +1990,12 @@ * * @add_aux_sta_for_hs20: pointer to the function that adds an aux sta * for Hot Spot 2.0 - * @switch_phy_ctxt: pointer to the function that switches a vif from one - * phy_ctx to another + * @link: For a P2P Device interface, pointer to a function that links the + * MAC/Link to the PHY context */ struct iwl_mvm_roc_ops { int (*add_aux_sta_for_hs20)(struct iwl_mvm *mvm, u32 lmac_id); - int (*switch_phy_ctxt)(struct iwl_mvm *mvm, struct ieee80211_vif *vif, - struct iwl_mvm_phy_ctxt *new_phy_ctxt); + int (*link)(struct iwl_mvm *mvm, struct ieee80211_vif *vif); }; int iwl_mvm_roc_common(struct ieee80211_hw *hw, struct ieee80211_vif *vif, @@ -2036,7 +2006,7 @@ struct ieee80211_vif *vif); /*Session Protection */ void iwl_mvm_protect_assoc(struct iwl_mvm *mvm, struct ieee80211_vif *vif, - u32 duration_override); + u32 duration_override, unsigned int link_id); /* Quota management */ static inline size_t iwl_mvm_quota_cmd_size(struct iwl_mvm *mvm) @@ -2096,18 +2066,19 @@ /* MVM debugfs */ #ifdef CPTCFG_IWLWIFI_DEBUGFS void iwl_mvm_dbgfs_register(struct iwl_mvm *mvm); -void iwl_mvm_vif_dbgfs_register(struct iwl_mvm *mvm, struct ieee80211_vif *vif); -void iwl_mvm_vif_dbgfs_clean(struct iwl_mvm *mvm, struct ieee80211_vif *vif); +void iwl_mvm_vif_add_debugfs(struct ieee80211_hw *hw, struct ieee80211_vif *vif); +void iwl_mvm_vif_dbgfs_add_link(struct iwl_mvm *mvm, struct ieee80211_vif *vif); +void iwl_mvm_vif_dbgfs_rm_link(struct iwl_mvm *mvm, struct ieee80211_vif *vif); #else static inline void iwl_mvm_dbgfs_register(struct iwl_mvm *mvm) { } static inline void -iwl_mvm_vif_dbgfs_register(struct iwl_mvm *mvm, struct ieee80211_vif *vif) +iwl_mvm_vif_dbgfs_add_link(struct iwl_mvm *mvm, struct ieee80211_vif *vif) { } static inline void -iwl_mvm_vif_dbgfs_clean(struct iwl_mvm *mvm, struct ieee80211_vif *vif) +iwl_mvm_vif_dbgfs_rm_link(struct iwl_mvm *mvm, struct ieee80211_vif *vif) { } #endif /* CPTCFG_IWLWIFI_DEBUGFS */ @@ -2334,7 +2305,7 @@ bool *changed); struct ieee80211_regdomain *iwl_mvm_get_current_regdomain(struct iwl_mvm *mvm, bool *changed); -int iwl_mvm_init_fw_regd(struct iwl_mvm *mvm); +int iwl_mvm_init_fw_regd(struct iwl_mvm *mvm, bool force_regd_sync); void iwl_mvm_update_changed_regdom(struct iwl_mvm *mvm); /* smart fifo */ @@ -2387,7 +2358,8 @@ void iwl_mvm_recalc_tdls_state(struct iwl_mvm *mvm, struct ieee80211_vif *vif, bool sta_added); void iwl_mvm_mac_mgd_protect_tdls_discover(struct ieee80211_hw *hw, - struct ieee80211_vif *vif); + struct ieee80211_vif *vif, + unsigned int link_id); int iwl_mvm_tdls_channel_switch(struct ieee80211_hw *hw, struct ieee80211_vif *vif, struct ieee80211_sta *sta, u8 oper_class, @@ -2414,7 +2386,6 @@ enum iwl_mvm_rxq_notif_type type, bool sync, const void *data, u32 size); -void iwl_mvm_reorder_timer_expired(struct timer_list *t); struct ieee80211_vif *iwl_mvm_get_bss_vif(struct iwl_mvm *mvm); struct ieee80211_vif *iwl_mvm_get_vif_by_macid(struct iwl_mvm *mvm, u32 macid); bool iwl_mvm_is_vif_assoc(struct iwl_mvm *mvm); @@ -2484,6 +2455,10 @@ struct ieee80211_vif *vif, struct ieee80211_link_sta *link_sta, struct dentry *dir); +void iwl_mvm_link_add_debugfs(struct ieee80211_hw *hw, + struct ieee80211_vif *vif, + struct ieee80211_bss_conf *link_conf, + struct dentry *dir); #endif /* new MLD related APIs */ @@ -2513,10 +2488,11 @@ /* 11ax Softap Test Mode */ -bool iwl_rfi_ddr_supported(struct iwl_mvm *mvm); -bool iwl_rfi_dlvr_supported(struct iwl_mvm *mvm); +bool iwl_rfi_ddr_supported(struct iwl_mvm *mvm, bool so_rfi_mode); +bool iwl_rfi_dlvr_supported(struct iwl_mvm *mvm, bool so_rfi_mode); int iwl_rfi_send_config_cmd(struct iwl_mvm *mvm, - struct iwl_rfi_lut_entry *rfi_table); + struct iwl_rfi_lut_entry *rfi_table, + bool is_set_master_cmd, bool force_send_table); struct iwl_rfi_freq_table_resp_cmd *iwl_rfi_get_freq_table(struct iwl_mvm *mvm); void iwl_rfi_support_notif_handler(struct iwl_mvm *mvm, struct iwl_rx_cmd_buffer *rxb); @@ -2779,8 +2755,6 @@ void iwl_mvm_change_chanctx(struct ieee80211_hw *hw, struct ieee80211_chanctx_conf *ctx, u32 changed); int iwl_mvm_tx_last_beacon(struct ieee80211_hw *hw); -int iwl_mvm_set_tim(struct ieee80211_hw *hw, struct ieee80211_sta *sta, - bool set); void iwl_mvm_channel_switch(struct ieee80211_hw *hw, struct ieee80211_vif *vif, struct ieee80211_channel_switch *chsw); int iwl_mvm_pre_channel_switch(struct ieee80211_hw *hw, @@ -2827,4 +2801,6 @@ u8 iwl_mvm_eval_dsm_rfi_dlvr(struct iwl_mvm *mvm); bool iwl_mvm_enable_fils(struct iwl_mvm *mvm, struct ieee80211_chanctx_conf *ctx); +void iwl_mvm_mld_select_links(struct iwl_mvm *mvm, struct ieee80211_vif *vif, + bool valid_links_changed); #endif /* __IWL_MVM_H__ */ diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/nvm.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/nvm.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/nvm.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/nvm.c 2023-10-04 04:18:43.000000000 +0800 @@ -580,7 +580,7 @@ * try to replay the last set MCC to FW. If it doesn't exist, * queue an update to cfg80211 to retrieve the default alpha2 from FW. */ - retval = iwl_mvm_init_fw_regd(mvm); + retval = iwl_mvm_init_fw_regd(mvm, true); if (retval != -ENOENT) return retval; diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/ops.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/ops.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/ops.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/ops.c 2023-10-04 04:18:43.000000000 +0800 @@ -353,6 +353,19 @@ RX_HANDLER_NO_SIZE(STATISTICS_NOTIFICATION, iwl_mvm_rx_statistics, RX_HANDLER_ASYNC_LOCKED), + RX_HANDLER_GRP(STATISTICS_GROUP, STATISTICS_OPER_NOTIF, + iwl_mvm_handle_rx_system_oper_stats, + RX_HANDLER_ASYNC_LOCKED, + struct iwl_system_statistics_notif_oper), + RX_HANDLER_GRP(STATISTICS_GROUP, STATISTICS_OPER_PART1_NOTIF, + iwl_mvm_handle_rx_system_oper_part1_stats, + RX_HANDLER_ASYNC_LOCKED, + struct iwl_system_statistics_part1_notif_oper), + RX_HANDLER_GRP(SYSTEM_GROUP, SYSTEM_STATISTICS_END_NOTIF, + iwl_mvm_handle_rx_system_end_stats_notif, + RX_HANDLER_ASYNC_LOCKED, + struct iwl_system_statistics_end_notif), + RX_HANDLER(BA_WINDOW_STATUS_NOTIFICATION_ID, iwl_mvm_window_status_notif, RX_HANDLER_SYNC, struct iwl_ba_window_status_notif), @@ -468,6 +481,9 @@ WNM_80211V_TIMING_MEASUREMENT_CONFIRM_NOTIFICATION, iwl_mvm_time_sync_msmt_confirm_event, RX_HANDLER_SYNC, struct iwl_time_msmt_cfm_notify), + RX_HANDLER_GRP(MAC_CONF_GROUP, ROC_NOTIF, + iwl_mvm_rx_roc_notif, RX_HANDLER_SYNC, + struct iwl_roc_notif), }; #undef RX_HANDLER #undef RX_HANDLER_GRP @@ -579,6 +595,8 @@ HCMD_NAME(RFI_CONFIG_CMD), HCMD_NAME(RFI_GET_FREQ_TABLE_CMD), HCMD_NAME(SYSTEM_FEATURES_CONTROL_CMD), + HCMD_NAME(SYSTEM_STATISTICS_CMD), + HCMD_NAME(SYSTEM_STATISTICS_END_NOTIF), HCMD_NAME(RFI_SUPPORT_NOTIF), }; @@ -596,6 +614,8 @@ HCMD_NAME(AUX_STA_CMD), HCMD_NAME(STA_REMOVE_CMD), HCMD_NAME(STA_DISABLE_TX_CMD), + HCMD_NAME(ROC_CMD), + HCMD_NAME(ROC_NOTIF), HCMD_NAME(CHANNEL_SWITCH_ERROR_NOTIF), HCMD_NAME(MISSED_VAP_NOTIF), HCMD_NAME(SESSION_PROTECTION_NOTIF), @@ -655,6 +675,14 @@ /* Please keep this array *SORTED* by hex value. * Access is done through binary search */ +static const struct iwl_hcmd_names iwl_mvm_statistics_names[] = { + HCMD_NAME(STATISTICS_OPER_NOTIF), + HCMD_NAME(STATISTICS_OPER_PART1_NOTIF), +}; + +/* Please keep this array *SORTED* by hex value. + * Access is done through binary search + */ static const struct iwl_hcmd_names iwl_mvm_scan_names[] = { HCMD_NAME(OFFLOAD_MATCH_INFO_NOTIF), }; @@ -719,6 +747,7 @@ [PROT_OFFLOAD_GROUP] = HCMD_ARR(iwl_mvm_prot_offload_names), [REGULATORY_AND_NVM_GROUP] = HCMD_ARR(iwl_mvm_regulatory_and_nvm_names), + [STATISTICS_GROUP] = HCMD_ARR(iwl_mvm_statistics_names), }; /* this forward declaration can avoid to export the function */ @@ -1314,6 +1343,7 @@ } mvm->fw_restart = iwlwifi_mod_params.fw_restart ? -1 : 0; + mvm->rfi_wlan_master = true; if (iwl_mvm_has_new_tx_api(mvm)) { /* @@ -1638,6 +1668,9 @@ if (mvm->hw_registered) ieee80211_unregister_hw(mvm->hw); + kfree(mvm->iwl_prev_rfi_config_cmd); + mvm->iwl_prev_rfi_config_cmd = NULL; + kfree(mvm->scan_cmd); kfree(mvm->mcast_filter_cmd); mvm->mcast_filter_cmd = NULL; @@ -1884,18 +1917,6 @@ iwl_mvm_rx_common(mvm, rxb, pkt); } -static void iwl_mvm_async_cb(struct iwl_op_mode *op_mode, - const struct iwl_device_cmd *cmd) -{ - struct iwl_mvm *mvm = IWL_OP_MODE_GET_MVM(op_mode); - - /* - * For now, we only set the CMD_WANT_ASYNC_CALLBACK for ADD_STA - * commands that need to block the Tx queues. - */ - iwl_trans_block_txq_ptrs(mvm->trans, false); -} - static int iwl_mvm_is_static_queue(struct iwl_mvm *mvm, int queue) { return queue == mvm->aux_queue || queue == mvm->probe_queue || @@ -2163,9 +2184,6 @@ { struct iwl_mvm *mvm = IWL_OP_MODE_GET_MVM(op_mode); - if (mvm->pldr_sync) - return; - if (!test_bit(STATUS_TRANS_DEAD, &mvm->trans->status) && !test_and_clear_bit(IWL_MVM_STATUS_SUPPRESS_ERROR_LOG_ONCE, &mvm->status)) @@ -2211,7 +2229,6 @@ #define IWL_MVM_COMMON_OPS \ /* these could be differentiated */ \ - .async_cb = iwl_mvm_async_cb, \ .queue_full = iwl_mvm_stop_sw_queue, \ .queue_not_full = iwl_mvm_wake_sw_queue, \ .hw_rf_kill = iwl_mvm_set_hw_rfkill_state, \ diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/phy-ctxt.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/phy-ctxt.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/phy-ctxt.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/phy-ctxt.c 2023-10-04 04:18:43.000000000 +0800 @@ -258,6 +258,8 @@ struct cfg80211_chan_def *chandef, u8 chains_static, u8 chains_dynamic) { + int ret; + WARN_ON(!test_bit(IWL_MVM_STATUS_IN_HW_RESTART, &mvm->status) && ctxt->ref); lockdep_assert_held(&mvm->mutex); @@ -266,9 +268,16 @@ ctxt->width = chandef->width; ctxt->center_freq1 = chandef->center_freq1; - return iwl_mvm_phy_ctxt_apply(mvm, ctxt, chandef, - chains_static, chains_dynamic, - FW_CTXT_ACTION_ADD); + ret = iwl_mvm_phy_ctxt_apply(mvm, ctxt, chandef, + chains_static, chains_dynamic, + FW_CTXT_ACTION_ADD); + + if (ret) + return ret; + + ctxt->ref++; + + return 0; } /* @@ -278,6 +287,11 @@ void iwl_mvm_phy_ctxt_ref(struct iwl_mvm *mvm, struct iwl_mvm_phy_ctxt *ctxt) { lockdep_assert_held(&mvm->mutex); + + /* If we were taking the first ref, we should have + * called iwl_mvm_phy_ctxt_add. + */ + WARN_ON(!ctxt->ref); ctxt->ref++; } @@ -294,6 +308,9 @@ lockdep_assert_held(&mvm->mutex); + if (WARN_ON_ONCE(!ctxt->ref)) + return -EINVAL; + if (iwl_fw_lookup_cmd_ver(mvm->fw, WIDE_ID(DATA_PATH_GROUP, RLC_CONFIG_CMD), 0) >= 2 && ctxt->channel == chandef->chan && @@ -329,6 +346,7 @@ void iwl_mvm_phy_ctxt_unref(struct iwl_mvm *mvm, struct iwl_mvm_phy_ctxt *ctxt) { + struct cfg80211_chan_def chandef; lockdep_assert_held(&mvm->mutex); if (WARN_ON_ONCE(!ctxt)) @@ -336,41 +354,13 @@ ctxt->ref--; - /* - * Move unused phy's to a default channel. When the phy is moved the, - * fw will cleanup immediate quiet bit if it was previously set, - * otherwise we might not be able to reuse this phy. - */ - if (ctxt->ref == 0) { - struct ieee80211_channel *chan = NULL; - struct cfg80211_chan_def chandef; - struct ieee80211_supported_band *sband; - enum nl80211_band band; - int channel; - - for (band = NL80211_BAND_2GHZ; band < NUM_NL80211_BANDS; band++) { - sband = mvm->hw->wiphy->bands[band]; - - if (!sband) - continue; - - for (channel = 0; channel < sband->n_channels; channel++) - if (!(sband->channels[channel].flags & - IEEE80211_CHAN_DISABLED)) { - chan = &sband->channels[channel]; - break; - } - - if (chan) - break; - } + if (ctxt->ref) + return; - if (WARN_ON(!chan)) - return; + cfg80211_chandef_create(&chandef, ctxt->channel, NL80211_CHAN_NO_HT); - cfg80211_chandef_create(&chandef, chan, NL80211_CHAN_NO_HT); - iwl_mvm_phy_ctxt_changed(mvm, ctxt, &chandef, 1, 1); - } + iwl_mvm_phy_ctxt_apply(mvm, ctxt, &chandef, 1, 1, + FW_CTXT_ACTION_REMOVE); } static void iwl_mvm_binding_iterator(void *_data, u8 *mac, diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/power.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/power.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/power.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/power.c 2023-10-04 04:18:43.000000000 +0800 @@ -674,13 +674,15 @@ return; /* enable PM on bss if bss stand alone */ - if (bss_mvmvif && vifs->bss_active && !vifs->p2p_active && !vifs->ap_active) { + if (bss_mvmvif && vifs->bss_active && !vifs->p2p_active && + !vifs->ap_active) { bss_mvmvif->pm_enabled = true; return; } /* enable PM on p2p if p2p stand alone */ - if (p2p_mvmvif && vifs->p2p_active && !vifs->bss_active && !vifs->ap_active) { + if (p2p_mvmvif && vifs->p2p_active && !vifs->bss_active && + !vifs->ap_active) { p2p_mvmvif->pm_enabled = true; return; } diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/rfi.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/rfi.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/rfi.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/rfi.c 2023-10-04 04:18:43.000000000 +0800 @@ -150,10 +150,24 @@ PHY_BAND_6,}}, }; -bool iwl_rfi_ddr_supported(struct iwl_mvm *mvm) +static inline bool iwl_rfi_enabled_by_mac_type(struct iwl_mvm *mvm, + bool so_rfi_mode) { - u8 dsm_rfi_ddr = iwl_mvm_eval_dsm_rfi_ddr(mvm); u32 mac_type = CSR_HW_REV_TYPE(mvm->trans->hw_rev); + bool enable_rfi = false; + + if ((mac_type != IWL_CFG_ANY && mac_type >= IWL_CFG_MAC_TYPE_MA) || + (mac_type == IWL_CFG_MAC_TYPE_SO && so_rfi_mode)) + enable_rfi = true; + + return enable_rfi; +} + +bool iwl_rfi_ddr_supported(struct iwl_mvm *mvm, bool so_rfi_mode) +{ + u8 dsm_rfi_ddr = iwl_mvm_eval_dsm_rfi_ddr(mvm); + bool rfi_enable_mac_type = iwl_rfi_enabled_by_mac_type(mvm, + so_rfi_mode); bool ddr_capa = fw_has_capa(&mvm->fw->ucode_capa, IWL_UCODE_TLV_CAPA_RFI_DDR_SUPPORT); @@ -162,20 +176,20 @@ ddr_capa ? "yes" : "no", dsm_rfi_ddr == DSM_VALUE_RFI_DDR_ENABLE ? "yes" : "no"); IWL_DEBUG_FW(mvm, - "HW is integrated:%s mac type:%d fw_rfi_state:%d\n", + "HW is integrated:%s rfi_enabled:%s fw_rfi_state:%d\n", mvm->trans->trans_cfg->integrated ? "yes" : "no", - mac_type, mvm->fw_rfi_state); + rfi_enable_mac_type ? "yes" : "no", mvm->fw_rfi_state); return ddr_capa && dsm_rfi_ddr == DSM_VALUE_RFI_DDR_ENABLE && - mac_type >= IWL_CFG_MAC_TYPE_MA && - mvm->trans->trans_cfg->integrated && + rfi_enable_mac_type && mvm->trans->trans_cfg->integrated && mvm->fw_rfi_state == IWL_RFI_PMC_SUPPORTED; } -bool iwl_rfi_dlvr_supported(struct iwl_mvm *mvm) +bool iwl_rfi_dlvr_supported(struct iwl_mvm *mvm, bool so_rfi_mode) { u8 dsm_rfi_dlvr = iwl_mvm_eval_dsm_rfi_dlvr(mvm); - u32 mac_type = CSR_HW_REV_TYPE(mvm->trans->hw_rev); + bool rfi_enable_mac_type = iwl_rfi_enabled_by_mac_type(mvm, + so_rfi_mode); bool dlvr_capa = fw_has_capa(&mvm->fw->ucode_capa, IWL_UCODE_TLV_CAPA_RFI_DLVR_SUPPORT); @@ -183,29 +197,32 @@ "FW has RFI DLVR capability:%s DLVR enabled in BIOS:%s\n", dlvr_capa ? "yes" : "no", dsm_rfi_dlvr == DSM_VALUE_RFI_DLVR_ENABLE ? "yes" : "no"); + IWL_DEBUG_FW(mvm, - "HW is integrated:%s mac type:%d fw_rfi_state:%d\n", + "HW is integrated:%s rfi_enabled:%s fw_rfi_state:%d\n", mvm->trans->trans_cfg->integrated ? "yes" : "no", - mac_type, mvm->fw_rfi_state); + rfi_enable_mac_type ? "yes" : "no", mvm->fw_rfi_state); return dlvr_capa && dsm_rfi_dlvr == DSM_VALUE_RFI_DLVR_ENABLE && - mac_type >= IWL_CFG_MAC_TYPE_MA && - mvm->trans->trans_cfg->integrated && + rfi_enable_mac_type && mvm->trans->trans_cfg->integrated && mvm->fw_rfi_state == IWL_RFI_PMC_SUPPORTED; } int iwl_rfi_send_config_cmd(struct iwl_mvm *mvm, - struct iwl_rfi_lut_entry *rfi_ddr_table) + struct iwl_rfi_lut_entry *rfi_ddr_table, + bool is_set_master_cmd, bool force_send_table) { - int ret; struct iwl_rfi_config_cmd *cmd = NULL; + bool rfi_ddr_support; + bool rfi_dlvr_support; + bool old_force_rfi = mvm->force_enable_rfi; + bool so_rfi_mode; + int ret = 0; struct iwl_host_cmd hcmd = { .id = WIDE_ID(SYSTEM_GROUP, RFI_CONFIG_CMD), .dataflags[0] = IWL_HCMD_DFL_DUP, .len[0] = sizeof(*cmd), }; - bool rfi_ddr_support = iwl_rfi_ddr_supported(mvm); - bool rfi_dlvr_support = iwl_rfi_dlvr_supported(mvm); u8 cmd_ver = iwl_fw_lookup_cmd_ver(mvm->fw, WIDE_ID(SYSTEM_GROUP, RFI_CONFIG_CMD), 0); @@ -213,6 +230,20 @@ if (cmd_ver != 3) return -EOPNOTSUPP; + /* for SO, rfi support is enabled only when vendor + * command explicitly asked us to manage RFI. + * vendor command can change SO enablement mode + */ + if (is_set_master_cmd) { + mvm->force_enable_rfi = mvm->rfi_wlan_master; + so_rfi_mode = old_force_rfi ? true : mvm->force_enable_rfi; + } else { + so_rfi_mode = mvm->force_enable_rfi; + } + + rfi_ddr_support = iwl_rfi_ddr_supported(mvm, so_rfi_mode); + rfi_dlvr_support = iwl_rfi_dlvr_supported(mvm, so_rfi_mode); + if (!rfi_ddr_support && !rfi_dlvr_support) return -EOPNOTSUPP; @@ -223,27 +254,89 @@ lockdep_assert_held(&mvm->mutex); + IWL_DEBUG_FW(mvm, "wlan is %s rfi master\n", + mvm->rfi_wlan_master ? "" : "Not"); + + /* Drop stored rfi_config_cmd buffer when there is change in master */ + if (is_set_master_cmd) { + kfree(mvm->iwl_prev_rfi_config_cmd); + mvm->iwl_prev_rfi_config_cmd = NULL; + } + + /* Zero iwl_rfi_config_cmd is legal for FW API and since it has + * rfi_memory_support equal to 0, it will disable all RFIm operation + * in the FW. + * Not having rfi_ddr_table when wlan driver is not the master means + * user-space requested to stop RFIm. + */ + if (!rfi_ddr_table && !mvm->rfi_wlan_master) { + if (force_send_table || !mvm->iwl_prev_rfi_config_cmd || + memcmp(mvm->iwl_prev_rfi_config_cmd, cmd, sizeof(*cmd))) { + IWL_DEBUG_FW(mvm, "Sending zero DDR superset table\n"); + goto send_empty_cmd; + } else { + IWL_DEBUG_FW(mvm, "Skip RFI_CONFIG_CMD sending\n"); + goto out; + } + } + if (rfi_ddr_support) { cmd->rfi_memory_support = cpu_to_le32(RFI_DDR_SUPPORTED_MSK); - /* in case no table is passed, use the default one */ - if (!rfi_ddr_table) { - memcpy(cmd->table, iwl_rfi_ddr_table, - sizeof(cmd->table)); - } else { + + /* don't send RFI_CONFIG_CMD to FW when DDR table passed by + * caller and previously sent table is same. + */ + if (!force_send_table && rfi_ddr_table && + mvm->iwl_prev_rfi_config_cmd && + !memcmp(rfi_ddr_table, mvm->iwl_prev_rfi_config_cmd->table, + sizeof(mvm->iwl_prev_rfi_config_cmd->table))) { + IWL_DEBUG_FW(mvm, "Skip RFI_CONFIG_CMD sending\n"); + goto out; + /* send RFI_CONFIG_CMD to FW with OEM ddr table */ + } else if (rfi_ddr_table) { + IWL_DEBUG_FW(mvm, "Sending oem DDR superset table\n"); memcpy(cmd->table, rfi_ddr_table, sizeof(cmd->table)); /* notify FW the table is not the default one */ cmd->oem = 1; + /* send previous RFI_CONFIG_CMD once again as FW lost RFI DDR + * table in reset + */ + } else if (mvm->iwl_prev_rfi_config_cmd && force_send_table) { + IWL_DEBUG_FW(mvm, + "Sending buffered %s DDR superset table\n", + mvm->iwl_prev_rfi_config_cmd->oem ? + "oem" : "default"); + memcpy(cmd->table, mvm->iwl_prev_rfi_config_cmd->table, + sizeof(cmd->table)); + cmd->oem = mvm->iwl_prev_rfi_config_cmd->oem; + /* don't send previous RFI_CONFIG_CMD as FW has same table */ + } else if (mvm->iwl_prev_rfi_config_cmd) { + IWL_DEBUG_FW(mvm, "Skip RFI_CONFIG_CMD sending\n"); + goto out; + /* send default ddr table for the first time */ + } else { + IWL_DEBUG_FW(mvm, + "Sending default DDR superset table\n"); + memcpy(cmd->table, iwl_rfi_ddr_table, + sizeof(cmd->table)); } } if (rfi_dlvr_support) cmd->rfi_memory_support |= cpu_to_le32(RFI_DLVR_SUPPORTED_MSK); +send_empty_cmd: ret = iwl_mvm_send_cmd(mvm, &hcmd); - - if (ret) + kfree(mvm->iwl_prev_rfi_config_cmd); + if (ret) { + mvm->iwl_prev_rfi_config_cmd = NULL; IWL_ERR(mvm, "Failed to send RFI config cmd %d\n", ret); + } else { + mvm->iwl_prev_rfi_config_cmd = cmd; + cmd = NULL; + } +out: kfree(cmd); return ret; } @@ -258,7 +351,7 @@ .flags = CMD_WANT_SKB, }; - if (!iwl_rfi_ddr_supported(mvm)) + if (!iwl_rfi_ddr_supported(mvm, mvm->force_enable_rfi)) return ERR_PTR(-EOPNOTSUPP); mutex_lock(&mvm->mutex); diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/rs.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/rs.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/rs.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/rs.c 2023-10-04 04:18:43.000000000 +0800 @@ -2695,7 +2695,7 @@ lq_sta = mvm_sta; - spin_lock(&lq_sta->pers.lock); + spin_lock_bh(&lq_sta->pers.lock); iwl_mvm_hwrate_to_tx_rate_v1(lq_sta->last_rate_n_flags, info->band, &info->control.rates[0]); info->control.rates[0].count = 1; @@ -2710,7 +2710,7 @@ iwl_mvm_hwrate_to_tx_rate_v1(last_ucode_rate, info->band, &txrc->reported_rate); } - spin_unlock(&lq_sta->pers.lock); + spin_unlock_bh(&lq_sta->pers.lock); } static void *rs_drv_alloc_sta(void *mvm_rate, struct ieee80211_sta *sta, @@ -3267,11 +3267,11 @@ /* If it's locked we are in middle of init flow * just wait for next tx status to update the lq_sta data */ - if (!spin_trylock(&mvmsta->deflink.lq_sta.rs_drv.pers.lock)) + if (!spin_trylock_bh(&mvmsta->deflink.lq_sta.rs_drv.pers.lock)) return; __iwl_mvm_rs_tx_status(mvm, sta, tid, info, ndp); - spin_unlock(&mvmsta->deflink.lq_sta.rs_drv.pers.lock); + spin_unlock_bh(&mvmsta->deflink.lq_sta.rs_drv.pers.lock); } #ifdef CPTCFG_MAC80211_DEBUGFS @@ -4120,9 +4120,9 @@ } else { struct iwl_mvm_sta *mvmsta = iwl_mvm_sta_from_mac80211(sta); - spin_lock(&mvmsta->deflink.lq_sta.rs_drv.pers.lock); + spin_lock_bh(&mvmsta->deflink.lq_sta.rs_drv.pers.lock); rs_drv_rate_init(mvm, sta, band); - spin_unlock(&mvmsta->deflink.lq_sta.rs_drv.pers.lock); + spin_unlock_bh(&mvmsta->deflink.lq_sta.rs_drv.pers.lock); } } diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/rx.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/rx.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/rx.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/rx.c 2023-10-04 04:18:43.000000000 +0800 @@ -559,7 +559,7 @@ struct iwl_mvm_stat_data_all_macs { struct iwl_mvm *mvm; __le32 flags; - struct iwl_statistics_ntfy_per_mac *per_mac_stats; + struct iwl_stats_ntfy_per_mac *per_mac; }; static void iwl_mvm_update_vif_sig(struct ieee80211_vif *vif, int sig) @@ -664,7 +664,7 @@ struct ieee80211_vif *vif) { struct iwl_mvm_stat_data_all_macs *data = _data; - struct iwl_statistics_ntfy_per_mac *mac_stats; + struct iwl_stats_ntfy_per_mac *mac_stats; int sig; struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif); u16 vif_id = mvmvif->id; @@ -675,7 +675,7 @@ if (vif->type != NL80211_IFTYPE_STATION) return; - mac_stats = &data->per_mac_stats[vif_id]; + mac_stats = &data->per_mac[vif_id]; mvmvif->deflink.beacon_stats.num_beacons = le32_to_cpu(mac_stats->beacon_counter); @@ -765,7 +765,7 @@ struct iwl_mvm_stat_data_all_macs data = { .mvm = mvm, .flags = stats->flags, - .per_mac_stats = stats->per_mac_stats, + .per_mac = stats->per_mac, }; ieee80211_iterate_active_interfaces(mvm->hw, @@ -835,6 +835,142 @@ } static void +iwl_mvm_stat_iterator_all_links(struct iwl_mvm *mvm, + struct iwl_stats_ntfy_per_link *per_link) +{ + u32 air_time[MAC_INDEX_AUX] = {}; + u32 rx_bytes[MAC_INDEX_AUX] = {}; + int fw_link_id; + + for (fw_link_id = 0; fw_link_id < ARRAY_SIZE(mvm->link_id_to_link_conf); + fw_link_id++) { + struct iwl_stats_ntfy_per_link *link_stats; + struct ieee80211_bss_conf *bss_conf; + struct iwl_mvm_vif *mvmvif; + int link_id; + int sig; + + bss_conf = iwl_mvm_rcu_fw_link_id_to_link_conf(mvm, fw_link_id, + false); + if (!bss_conf) + continue; + + if (bss_conf->vif->type != NL80211_IFTYPE_STATION) + continue; + + link_id = bss_conf->link_id; + if (link_id >= ARRAY_SIZE(mvmvif->link)) + continue; + + mvmvif = iwl_mvm_vif_from_mac80211(bss_conf->vif); + if (!mvmvif || !mvmvif->link[link_id]) + continue; + + link_stats = &per_link[fw_link_id]; + + mvmvif->link[link_id]->beacon_stats.num_beacons = + le32_to_cpu(link_stats->beacon_counter); + + /* we basically just use the u8 to store 8 bits and then treat + * it as a s8 whenever we take it out to a different type. + */ + mvmvif->link[link_id]->beacon_stats.avg_signal = + -le32_to_cpu(link_stats->beacon_average_energy); + + /* make sure that beacon statistics don't go backwards with TCM + * request to clear statistics + */ + if (mvm->statistics_clear) + mvmvif->link[link_id]->beacon_stats.accu_num_beacons += + mvmvif->link[link_id]->beacon_stats.num_beacons; + + sig = -le32_to_cpu(link_stats->beacon_filter_average_energy); + iwl_mvm_update_vif_sig(bss_conf->vif, sig); + + if (WARN_ONCE(mvmvif->id >= MAC_INDEX_AUX, + "invalid mvmvif id: %d", mvmvif->id)) + continue; + + air_time[mvmvif->id] += + le32_to_cpu(per_link[fw_link_id].air_time); + rx_bytes[mvmvif->id] += + le32_to_cpu(per_link[fw_link_id].rx_bytes); + } + + /* Don't update in case the statistics are not cleared, since + * we will end up counting twice the same airtime, once in TCM + * request and once in statistics notification. + */ + if (mvm->statistics_clear) { + __le32 air_time_le[MAC_INDEX_AUX]; + __le32 rx_bytes_le[MAC_INDEX_AUX]; + int vif_id; + + for (vif_id = 0; vif_id < ARRAY_SIZE(air_time_le); vif_id++) { + air_time_le[vif_id] = cpu_to_le32(air_time[vif_id]); + rx_bytes_le[vif_id] = cpu_to_le32(rx_bytes[vif_id]); + } + + iwl_mvm_update_tcm_from_stats(mvm, air_time_le, rx_bytes_le); + } +} + +void iwl_mvm_handle_rx_system_oper_stats(struct iwl_mvm *mvm, + struct iwl_rx_cmd_buffer *rxb) +{ + u8 average_energy[IWL_MVM_STATION_COUNT_MAX]; + struct iwl_rx_packet *pkt = rxb_addr(rxb); + struct iwl_system_statistics_notif_oper *stats; + int i; + u32 notif_ver = iwl_fw_lookup_notif_ver(mvm->fw, STATISTICS_GROUP, + STATISTICS_OPER_NOTIF, 0); + + if (notif_ver != 3) { + IWL_FW_CHECK_FAILED(mvm, + "Oper stats notif ver %d is not supported\n", + notif_ver); + return; + } + + stats = (void *)&pkt->data; + iwl_mvm_stat_iterator_all_links(mvm, stats->per_link); + + for (i = 0; i < ARRAY_SIZE(average_energy); i++) + average_energy[i] = + le32_to_cpu(stats->per_sta[i].average_energy); + + ieee80211_iterate_stations_atomic(mvm->hw, iwl_mvm_stats_energy_iter, + average_energy); +} + +void iwl_mvm_handle_rx_system_oper_part1_stats(struct iwl_mvm *mvm, + struct iwl_rx_cmd_buffer *rxb) +{ + struct iwl_rx_packet *pkt = rxb_addr(rxb); + struct iwl_system_statistics_part1_notif_oper *part1_stats; + int i; + u32 notif_ver = iwl_fw_lookup_notif_ver(mvm->fw, STATISTICS_GROUP, + STATISTICS_OPER_PART1_NOTIF, 0); + + if (notif_ver != 4) { + IWL_FW_CHECK_FAILED(mvm, + "Part1 stats notif ver %d is not supported\n", + notif_ver); + return; + } + + part1_stats = (void *)&pkt->data; + mvm->radio_stats.rx_time = 0; + mvm->radio_stats.tx_time = 0; + for (i = 0; i < ARRAY_SIZE(part1_stats->per_link); i++) { + mvm->radio_stats.rx_time += + le64_to_cpu(part1_stats->per_link[i].rx_time); + mvm->radio_stats.tx_time += + le64_to_cpu(part1_stats->per_link[i].tx_time); + } +} + +static void iwl_mvm_handle_rx_statistics_tlv(struct iwl_mvm *mvm, struct iwl_rx_packet *pkt) { @@ -893,11 +1029,11 @@ for (i = 0; i < ARRAY_SIZE(average_energy); i++) average_energy[i] = - le32_to_cpu(stats->per_sta_stats[i].average_energy); + le32_to_cpu(stats->per_sta[i].average_energy); for (i = 0; i < ARRAY_SIZE(air_time); i++) { - air_time[i] = stats->per_mac_stats[i].air_time; - rx_bytes[i] = stats->per_mac_stats[i].rx_bytes; + air_time[i] = stats->per_mac[i].air_time; + rx_bytes[i] = stats->per_mac[i].rx_bytes; } } @@ -923,6 +1059,13 @@ __le32 *bytes, *air_time, flags; int expected_size; u8 *energy; + u8 cmd_ver = iwl_fw_lookup_cmd_ver(mvm->fw, + WIDE_ID(SYSTEM_GROUP, + SYSTEM_STATISTICS_CMD), + IWL_FW_CMD_VER_UNKNOWN); + + if (cmd_ver != IWL_FW_CMD_VER_UNKNOWN) + return; /* From ver 14 and up we use TLV statistics format */ if (iwl_fw_lookup_notif_ver(mvm->fw, LEGACY_GROUP, diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/rxmq.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/rxmq.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/rxmq.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/rxmq.c 2023-10-04 04:18:43.000000000 +0800 @@ -550,42 +550,12 @@ return false; } -/* - * Returns true if sn2 - buffer_size < sn1 < sn2. - * To be used only in order to compare reorder buffer head with NSSN. - * We fully trust NSSN unless it is behind us due to reorder timeout. - * Reorder timeout can only bring us up to buffer_size SNs ahead of NSSN. - */ -static bool iwl_mvm_is_sn_less(u16 sn1, u16 sn2, u16 buffer_size) -{ - return ieee80211_sn_less(sn1, sn2) && - !ieee80211_sn_less(sn1, sn2 - buffer_size); -} - -static void iwl_mvm_sync_nssn(struct iwl_mvm *mvm, u8 baid, u16 nssn) -{ - struct iwl_mvm_nssn_sync_data notif = { - .baid = baid, - .nssn = nssn, - }; - - iwl_mvm_sync_rx_queues_internal(mvm, IWL_MVM_RXQ_NSSN_SYNC, false, - ¬if, sizeof(notif)); -} - -#define RX_REORDER_BUF_TIMEOUT_MQ (HZ / 10) - -enum iwl_mvm_release_flags { - IWL_MVM_RELEASE_SEND_RSS_SYNC = BIT(0), - IWL_MVM_RELEASE_FROM_RSS_SYNC = BIT(1), -}; - static void iwl_mvm_release_frames(struct iwl_mvm *mvm, struct ieee80211_sta *sta, struct napi_struct *napi, struct iwl_mvm_baid_data *baid_data, struct iwl_mvm_reorder_buffer *reorder_buf, - u16 nssn, u32 flags) + u16 nssn) { struct iwl_mvm_reorder_buf_entry *entries = &baid_data->entries[reorder_buf->queue * @@ -594,31 +564,12 @@ lockdep_assert_held(&reorder_buf->lock); - /* - * We keep the NSSN not too far behind, if we are sync'ing it and it - * is more than 2048 ahead of us, it must be behind us. Discard it. - * This can happen if the queue that hit the 0 / 2048 seqno was lagging - * behind and this queue already processed packets. The next if - * would have caught cases where this queue would have processed less - * than 64 packets, but it may have processed more than 64 packets. - */ - if ((flags & IWL_MVM_RELEASE_FROM_RSS_SYNC) && - ieee80211_sn_less(nssn, ssn)) - goto set_timer; - - /* ignore nssn smaller than head sn - this can happen due to timeout */ - if (iwl_mvm_is_sn_less(nssn, ssn, reorder_buf->buf_size)) - goto set_timer; - - while (iwl_mvm_is_sn_less(ssn, nssn, reorder_buf->buf_size)) { + while (ieee80211_sn_less(ssn, nssn)) { int index = ssn % reorder_buf->buf_size; - struct sk_buff_head *skb_list = &entries[index].e.frames; + struct sk_buff_head *skb_list = &entries[index].frames; struct sk_buff *skb; ssn = ieee80211_sn_inc(ssn); - if ((flags & IWL_MVM_RELEASE_SEND_RSS_SYNC) && - (ssn == 2048 || ssn == 0)) - iwl_mvm_sync_nssn(mvm, baid_data->baid, ssn); /* * Empty the list. Will have more than one frame for A-MSDU. @@ -633,99 +584,6 @@ } } reorder_buf->head_sn = nssn; - -set_timer: - if (reorder_buf->num_stored && !reorder_buf->removed) { - u16 index = reorder_buf->head_sn % reorder_buf->buf_size; - - while (skb_queue_empty(&entries[index].e.frames)) - index = (index + 1) % reorder_buf->buf_size; - /* modify timer to match next frame's expiration time */ - mod_timer(&reorder_buf->reorder_timer, - entries[index].e.reorder_time + 1 + - RX_REORDER_BUF_TIMEOUT_MQ); - } else { - del_timer(&reorder_buf->reorder_timer); - } -} - -void iwl_mvm_reorder_timer_expired(struct timer_list *t) -{ - struct iwl_mvm_reorder_buffer *buf = from_timer(buf, t, reorder_timer); - struct iwl_mvm_baid_data *baid_data = - iwl_mvm_baid_data_from_reorder_buf(buf); - struct iwl_mvm_reorder_buf_entry *entries = - &baid_data->entries[buf->queue * baid_data->entries_per_queue]; - int i; - u16 sn = 0, index = 0; - bool expired = false; - bool cont = false; - - spin_lock(&buf->lock); - - if (!buf->num_stored || buf->removed) { - spin_unlock(&buf->lock); - return; - } - - for (i = 0; i < buf->buf_size ; i++) { - index = (buf->head_sn + i) % buf->buf_size; - - if (skb_queue_empty(&entries[index].e.frames)) { - /* - * If there is a hole and the next frame didn't expire - * we want to break and not advance SN - */ - cont = false; - continue; - } - if (!cont && - !time_after(jiffies, entries[index].e.reorder_time + - RX_REORDER_BUF_TIMEOUT_MQ)) - break; - - expired = true; - /* continue until next hole after this expired frames */ - cont = true; - sn = ieee80211_sn_add(buf->head_sn, i + 1); - } - - if (expired) { - struct ieee80211_sta *sta; - struct iwl_mvm_sta *mvmsta; - u8 sta_id = ffs(baid_data->sta_mask) - 1; - - rcu_read_lock(); - sta = rcu_dereference(buf->mvm->fw_id_to_mac_id[sta_id]); - if (WARN_ON_ONCE(IS_ERR_OR_NULL(sta))) { - rcu_read_unlock(); - goto out; - } - - mvmsta = iwl_mvm_sta_from_mac80211(sta); - - /* SN is set to the last expired frame + 1 */ - IWL_DEBUG_HT(buf->mvm, - "Releasing expired frames for sta %u, sn %d\n", - sta_id, sn); - iwl_mvm_event_frame_timeout_callback(buf->mvm, mvmsta->vif, - sta, baid_data->tid); - iwl_mvm_release_frames(buf->mvm, sta, NULL, baid_data, - buf, sn, IWL_MVM_RELEASE_SEND_RSS_SYNC); - rcu_read_unlock(); - } else { - /* - * If no frame expired and there are stored frames, index is now - * pointing to the first unexpired frame - modify timer - * accordingly to this frame. - */ - mod_timer(&buf->reorder_timer, - entries[index].e.reorder_time + - 1 + RX_REORDER_BUF_TIMEOUT_MQ); - } - -out: - spin_unlock(&buf->lock); } static void iwl_mvm_del_ba(struct iwl_mvm *mvm, int queue, @@ -758,10 +616,8 @@ spin_lock_bh(&reorder_buf->lock); iwl_mvm_release_frames(mvm, sta, NULL, ba_data, reorder_buf, ieee80211_sn_add(reorder_buf->head_sn, - reorder_buf->buf_size), - 0); + reorder_buf->buf_size)); spin_unlock_bh(&reorder_buf->lock); - del_timer_sync(&reorder_buf->reorder_timer); out: rcu_read_unlock(); @@ -769,8 +625,7 @@ static void iwl_mvm_release_frames_from_notif(struct iwl_mvm *mvm, struct napi_struct *napi, - u8 baid, u16 nssn, int queue, - u32 flags) + u8 baid, u16 nssn, int queue) { struct ieee80211_sta *sta; struct iwl_mvm_reorder_buffer *reorder_buf; @@ -788,8 +643,7 @@ ba_data = rcu_dereference(mvm->baid_map[baid]); if (!ba_data) { - WARN(!(flags & IWL_MVM_RELEASE_FROM_RSS_SYNC), - "BAID %d not found in map\n", baid); + WARN(true, "BAID %d not found in map\n", baid); goto out; } @@ -803,22 +657,13 @@ spin_lock_bh(&reorder_buf->lock); iwl_mvm_release_frames(mvm, sta, napi, ba_data, - reorder_buf, nssn, flags); + reorder_buf, nssn); spin_unlock_bh(&reorder_buf->lock); out: rcu_read_unlock(); } -static void iwl_mvm_nssn_sync(struct iwl_mvm *mvm, - struct napi_struct *napi, int queue, - const struct iwl_mvm_nssn_sync_data *data) -{ - iwl_mvm_release_frames_from_notif(mvm, napi, data->baid, - data->nssn, queue, - IWL_MVM_RELEASE_FROM_RSS_SYNC); -} - void iwl_mvm_rx_queue_notif(struct iwl_mvm *mvm, struct napi_struct *napi, struct iwl_rx_cmd_buffer *rxb, int queue) { @@ -853,14 +698,6 @@ break; iwl_mvm_del_ba(mvm, queue, (void *)internal_notif->data); break; - case IWL_MVM_RXQ_NSSN_SYNC: - if (WARN_ONCE(len != sizeof(struct iwl_mvm_nssn_sync_data), - "invalid nssn sync notification size %d (%d)", - len, (int)sizeof(struct iwl_mvm_nssn_sync_data))) - break; - iwl_mvm_nssn_sync(mvm, napi, queue, - (void *)internal_notif->data); - break; default: WARN_ONCE(1, "Invalid identifier %d", internal_notif->type); } @@ -874,55 +711,6 @@ } } -static void iwl_mvm_oldsn_workaround(struct iwl_mvm *mvm, - struct ieee80211_sta *sta, int tid, - struct iwl_mvm_reorder_buffer *buffer, - u32 reorder, u32 gp2, int queue) -{ - struct iwl_mvm_sta *mvmsta = iwl_mvm_sta_from_mac80211(sta); - - if (gp2 != buffer->consec_oldsn_ampdu_gp2) { - /* we have a new (A-)MPDU ... */ - - /* - * reset counter to 0 if we didn't have any oldsn in - * the last A-MPDU (as detected by GP2 being identical) - */ - if (!buffer->consec_oldsn_prev_drop) - buffer->consec_oldsn_drops = 0; - - /* either way, update our tracking state */ - buffer->consec_oldsn_ampdu_gp2 = gp2; - } else if (buffer->consec_oldsn_prev_drop) { - /* - * tracking state didn't change, and we had an old SN - * indication before - do nothing in this case, we - * already noted this one down and are waiting for the - * next A-MPDU (by GP2) - */ - return; - } - - /* return unless this MPDU has old SN */ - if (!(reorder & IWL_RX_MPDU_REORDER_BA_OLD_SN)) - return; - - /* update state */ - buffer->consec_oldsn_prev_drop = 1; - buffer->consec_oldsn_drops++; - - /* if limit is reached, send del BA and reset state */ - if (buffer->consec_oldsn_drops == IWL_MVM_AMPDU_CONSEC_DROPS_DELBA) { - IWL_WARN(mvm, - "reached %d old SN frames from %pM on queue %d, stopping BA session on TID %d\n", - IWL_MVM_AMPDU_CONSEC_DROPS_DELBA, - sta->addr, queue, tid); - ieee80211_stop_rx_ba_session(mvmsta->vif, BIT(tid), sta->addr); - buffer->consec_oldsn_prev_drop = 0; - buffer->consec_oldsn_drops = 0; - } -} - /* * Returns true if the MPDU was buffered\dropped, false if it should be passed * to upper layer. @@ -934,11 +722,9 @@ struct sk_buff *skb, struct iwl_rx_mpdu_desc *desc) { - struct ieee80211_rx_status *rx_status = IEEE80211_SKB_RXCB(skb); struct ieee80211_hdr *hdr = (void *)skb_mac_header(skb); struct iwl_mvm_baid_data *baid_data; struct iwl_mvm_reorder_buffer *buffer; - struct sk_buff *tail; u32 reorder = le32_to_cpu(desc->reorder_data); bool amsdu = desc->mac_flags2 & IWL_RX_MPDU_MFLG2_AMSDU; bool last_subframe = @@ -955,6 +741,9 @@ baid = (reorder & IWL_RX_MPDU_REORDER_BAID_MASK) >> IWL_RX_MPDU_REORDER_BAID_SHIFT; + if (mvm->trans->trans_cfg->device_family == IWL_DEVICE_FAMILY_9000) + return false; + /* * This also covers the case of receiving a Block Ack Request * outside a BA session; we'll pass it to mac80211 and that @@ -991,10 +780,12 @@ sta_mask = iwl_mvm_sta_fw_id_mask(mvm, sta, -1); rcu_read_unlock(); - if (WARN(tid != baid_data->tid || - !(sta_mask & baid_data->sta_mask), - "baid 0x%x is mapped to sta_mask:0x%x tid:%d, but was received for sta_mask:0x%x tid:%d\n", - baid, baid_data->sta_mask, baid_data->tid, sta_mask, tid)) + if (IWL_FW_CHECK(mvm, + tid != baid_data->tid || + !(sta_mask & baid_data->sta_mask), + "baid 0x%x is mapped to sta_mask:0x%x tid:%d, but was received for sta_mask:0x%x tid:%d\n", + baid, baid_data->sta_mask, baid_data->tid, + sta_mask, tid)) return false; nssn = reorder & IWL_RX_MPDU_REORDER_NSSN_MASK; @@ -1014,59 +805,18 @@ buffer->valid = true; } - if (ieee80211_is_back_req(hdr->frame_control)) { - iwl_mvm_release_frames(mvm, sta, napi, baid_data, - buffer, nssn, 0); + /* drop any duplicated packets */ + if (desc->status & cpu_to_le32(IWL_RX_MPDU_STATUS_DUPLICATE)) goto drop; - } - - /* - * If there was a significant jump in the nssn - adjust. - * If the SN is smaller than the NSSN it might need to first go into - * the reorder buffer, in which case we just release up to it and the - * rest of the function will take care of storing it and releasing up to - * the nssn. - * This should not happen. This queue has been lagging and it should - * have been updated by a IWL_MVM_RXQ_NSSN_SYNC notification. Be nice - * and update the other queues. - */ - if (!iwl_mvm_is_sn_less(nssn, buffer->head_sn + buffer->buf_size, - buffer->buf_size) || - !ieee80211_sn_less(sn, buffer->head_sn + buffer->buf_size)) { - u16 min_sn = ieee80211_sn_less(sn, nssn) ? sn : nssn; - - iwl_mvm_release_frames(mvm, sta, napi, baid_data, buffer, - min_sn, IWL_MVM_RELEASE_SEND_RSS_SYNC); - } - - iwl_mvm_oldsn_workaround(mvm, sta, tid, buffer, reorder, - rx_status->device_timestamp, queue); /* drop any oudated packets */ - if (ieee80211_sn_less(sn, buffer->head_sn)) + if (reorder & IWL_RX_MPDU_REORDER_BA_OLD_SN) goto drop; /* release immediately if allowed by nssn and no stored frames */ if (!buffer->num_stored && ieee80211_sn_less(sn, nssn)) { - if (iwl_mvm_is_sn_less(buffer->head_sn, nssn, - buffer->buf_size) && - (!amsdu || last_subframe)) { - /* - * If we crossed the 2048 or 0 SN, notify all the - * queues. This is done in order to avoid having a - * head_sn that lags behind for too long. When that - * happens, we can get to a situation where the head_sn - * is within the interval [nssn - buf_size : nssn] - * which will make us think that the nssn is a packet - * that we already freed because of the reordering - * buffer and we will ignore it. So maintain the - * head_sn somewhat updated across all the queues: - * when it crosses 0 and 2048. - */ - if (sn == 2048 || sn == 0) - iwl_mvm_sync_nssn(mvm, baid, sn); + if (!amsdu || last_subframe) buffer->head_sn = nssn; - } /* No need to update AMSDU last SN - we are moving the head */ spin_unlock_bh(&buffer->lock); return false; @@ -1081,37 +831,18 @@ * while technically there is no hole and we can move forward. */ if (!buffer->num_stored && sn == buffer->head_sn) { - if (!amsdu || last_subframe) { - if (sn == 2048 || sn == 0) - iwl_mvm_sync_nssn(mvm, baid, sn); + if (!amsdu || last_subframe) buffer->head_sn = ieee80211_sn_inc(buffer->head_sn); - } + /* No need to update AMSDU last SN - we are moving the head */ spin_unlock_bh(&buffer->lock); return false; } - index = sn % buffer->buf_size; - - /* - * Check if we already stored this frame - * As AMSDU is either received or not as whole, logic is simple: - * If we have frames in that position in the buffer and the last frame - * originated from AMSDU had a different SN then it is a retransmission. - * If it is the same SN then if the subframe index is incrementing it - * is the same AMSDU - otherwise it is a retransmission. - */ - tail = skb_peek_tail(&entries[index].e.frames); - if (tail && !amsdu) - goto drop; - else if (tail && (sn != buffer->last_amsdu || - buffer->last_sub_index >= sub_frame_idx)) - goto drop; - /* put in reorder buffer */ - __skb_queue_tail(&entries[index].e.frames, skb); + index = sn % buffer->buf_size; + __skb_queue_tail(&entries[index].frames, skb); buffer->num_stored++; - entries[index].e.reorder_time = jiffies; if (amsdu) { buffer->last_amsdu = sn; @@ -1131,8 +862,7 @@ */ if (!amsdu || last_subframe) iwl_mvm_release_frames(mvm, sta, napi, baid_data, - buffer, nssn, - IWL_MVM_RELEASE_SEND_RSS_SYNC); + buffer, nssn); spin_unlock_bh(&buffer->lock); return true; @@ -1505,7 +1235,7 @@ #define IWL_RX_RU_DATA_A1 2 #define IWL_RX_RU_DATA_A2 2 #define IWL_RX_RU_DATA_B1 2 -#define IWL_RX_RU_DATA_B2 3 +#define IWL_RX_RU_DATA_B2 4 #define IWL_RX_RU_DATA_C1 3 #define IWL_RX_RU_DATA_C2 3 #define IWL_RX_RU_DATA_D1 4 @@ -2627,9 +2357,15 @@ if (!iwl_mvm_reorder(mvm, napi, queue, sta, skb, desc) && (likely(!iwl_mvm_time_sync_frame(mvm, skb, hdr->addr2))) && iwl_mvm_is_valid_packet_channel(rx_status, skb) - ) + ) { + if (mvm->trans->trans_cfg->device_family == IWL_DEVICE_FAMILY_9000 && + (desc->mac_flags2 & IWL_RX_MPDU_MFLG2_AMSDU) && + !(desc->amsdu_info & IWL_RX_MPDU_AMSDU_LAST_SUBFRAME)) + rx_status->flag |= RX_FLAG_AMSDU_MORE; + iwl_mvm_pass_packet_to_mac80211(mvm, napi, skb, queue, sta, link_sta); + } out: rcu_read_unlock(); } @@ -2775,7 +2511,7 @@ iwl_mvm_release_frames_from_notif(mvm, napi, release->baid, le16_to_cpu(release->nssn), - queue, 0); + queue); } void iwl_mvm_rx_bar_frame_release(struct iwl_mvm *mvm, struct napi_struct *napi, @@ -2819,7 +2555,7 @@ IWL_DEBUG_DROP(mvm, "Received a BAR, expect packet loss: nssn %d\n", nssn); - iwl_mvm_release_frames_from_notif(mvm, napi, baid, nssn, queue, 0); + iwl_mvm_release_frames_from_notif(mvm, napi, baid, nssn, queue); out: rcu_read_unlock(); } diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/scan.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/scan.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/scan.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/scan.c 2023-10-04 04:18:43.000000000 +0800 @@ -101,6 +101,7 @@ bool scan_6ghz; bool enable_6ghz_passive; bool respect_p2p_go, respect_p2p_go_hb; + s8 tsf_report_link_id; u8 bssid[ETH_ALEN] __aligned(2); }; @@ -2352,21 +2353,15 @@ if (gen_flags & IWL_UMAC_SCAN_GEN_FLAGS_V2_FRAGMENTED_LMAC2) gp->num_of_fragments[SCAN_HB_LMAC_IDX] = IWL_SCAN_NUM_OF_FRAGS; - if (version < 12) { + mvm->scan_link_id = 0; + + if (version < 16) { gp->scan_start_mac_or_link_id = scan_vif->id; } else { - struct iwl_mvm_vif_link_info *link_info; - u8 link_id = 0; - - /* - * Use one of the active link (if any). In the future it would - * be possible that the link ID would be part of the scan - * request coming from upper layers so we would need to use it. - */ - if (vif->active_links) - link_id = ffs(vif->active_links) - 1; + struct iwl_mvm_vif_link_info *link_info = + scan_vif->link[params->tsf_report_link_id]; - link_info = scan_vif->link[link_id]; + mvm->scan_link_id = params->tsf_report_link_id; if (!WARN_ON(!link_info)) gp->scan_start_mac_or_link_id = link_info->fw_link_id; } @@ -2907,6 +2902,14 @@ if (req->duration) params.iter_notif = true; + params.tsf_report_link_id = req->tsf_report_link_id; + if (params.tsf_report_link_id < 0) { + if (vif->active_links) + params.tsf_report_link_id = __ffs(vif->active_links); + else + params.tsf_report_link_id = 0; + } + iwl_mvm_build_scan_probe(mvm, vif, ies, ¶ms); iwl_mvm_scan_6ghz_passive_scan(mvm, ¶ms, vif); @@ -3091,8 +3094,13 @@ .aborted = aborted, .scan_start_tsf = mvm->scan_start, }; + struct iwl_mvm_vif *scan_vif = mvm->scan_vif; + struct iwl_mvm_vif_link_info *link_info = + scan_vif->link[mvm->scan_link_id]; + + if (!WARN_ON(!link_info)) + memcpy(info.tsf_bssid, link_info->bssid, ETH_ALEN); - memcpy(info.tsf_bssid, mvm->scan_vif->deflink.bssid, ETH_ALEN); ieee80211_scan_completed(mvm->hw, &info); mvm->scan_vif = NULL; cancel_delayed_work(&mvm->scan_timeout_dwork); @@ -3335,7 +3343,7 @@ if (!(mvm->scan_status & type)) return 0; - if (iwl_mvm_is_radio_killed(mvm)) { + if (!test_bit(STATUS_DEVICE_ENABLED, &mvm->trans->status)) { ret = 0; goto out; } diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/sta.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/sta.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/sta.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/sta.c 2023-10-04 04:18:43.000000000 +0800 @@ -60,8 +60,7 @@ if (WARN_ON(!link_sta)) return 0; - /* - * Note that we always use only legacy & highest supported PPDUs, so + /* Note that we always use only legacy & highest supported PPDUs, so * of Draft P802.11be D.30 Table 10-12a--Fields used for calculating * the maximum A-MPDU size of various PPDU types in different bands, * we only need to worry about the highest supported PPDU type here. @@ -2058,7 +2057,8 @@ *status = IWL_MVM_QUEUE_FREE; } - if (vif->type == NL80211_IFTYPE_STATION) { + if (vif->type == NL80211_IFTYPE_STATION && + mvm_link->ap_sta_id == sta_id) { /* if associated - we can't remove the AP STA now */ if (vif->cfg.assoc) return true; @@ -2096,7 +2096,8 @@ return ret; /* flush its queues here since we are freeing mvm_sta */ - ret = iwl_mvm_flush_sta(mvm, mvm_sta, false); + ret = iwl_mvm_flush_sta(mvm, mvm_sta->deflink.sta_id, + mvm_sta->tfd_queue_msk); if (ret) return ret; if (iwl_mvm_has_new_tx_api(mvm)) { @@ -2407,7 +2408,8 @@ lockdep_assert_held(&mvm->mutex); - iwl_mvm_flush_sta(mvm, &mvmvif->deflink.bcast_sta, true); + iwl_mvm_flush_sta(mvm, mvmvif->deflink.bcast_sta.sta_id, + mvmvif->deflink.bcast_sta.tfd_queue_msk); switch (vif->type) { case NL80211_IFTYPE_AP: @@ -2663,7 +2665,8 @@ lockdep_assert_held(&mvm->mutex); - iwl_mvm_flush_sta(mvm, &mvmvif->deflink.mcast_sta, true); + iwl_mvm_flush_sta(mvm, mvmvif->deflink.mcast_sta.sta_id, + mvmvif->deflink.mcast_sta.tfd_queue_msk); iwl_mvm_disable_txq(mvm, NULL, mvmvif->deflink.mcast_sta.sta_id, &mvmvif->deflink.cab_queue, 0); @@ -2713,18 +2716,9 @@ WARN_ON(1); for (j = 0; j < reorder_buf->buf_size; j++) - __skb_queue_purge(&entries[j].e.frames); - /* - * Prevent timer re-arm. This prevents a very far fetched case - * where we timed out on the notification. There may be prior - * RX frames pending in the RX queue before the notification - * that might get processed between now and the actual deletion - * and we would re-arm the timer although we are deleting the - * reorder buffer. - */ - reorder_buf->removed = true; + __skb_queue_purge(&entries[j].frames); + spin_unlock_bh(&reorder_buf->lock); - del_timer_sync(&reorder_buf->reorder_timer); } } @@ -2744,15 +2738,12 @@ reorder_buf->num_stored = 0; reorder_buf->head_sn = ssn; reorder_buf->buf_size = buf_size; - /* rx reorder timer */ - timer_setup(&reorder_buf->reorder_timer, - iwl_mvm_reorder_timer_expired, 0); spin_lock_init(&reorder_buf->lock); reorder_buf->mvm = mvm; reorder_buf->queue = i; reorder_buf->valid = false; for (j = 0; j < reorder_buf->buf_size; j++) - __skb_queue_head_init(&entries[j].e.frames); + __skb_queue_head_init(&entries[j].frames); } } @@ -4117,10 +4108,8 @@ } /* block the Tx queues until the FW updated the sleep Tx count */ - iwl_trans_block_txq_ptrs(mvm->trans, true); - ret = iwl_mvm_send_cmd_pdu(mvm, ADD_STA, - CMD_ASYNC | CMD_WANT_ASYNC_CALLBACK, + CMD_ASYNC | CMD_BLOCK_TXQS, iwl_mvm_add_sta_cmd_size(mvm), &cmd); if (ret) IWL_ERR(mvm, "Failed to send ADD_STA command (%d)\n", ret); @@ -4158,7 +4147,8 @@ int ret; if (mvm->mld_api_is_used) { - iwl_mvm_mld_sta_modify_disable_tx(mvm, mvmsta, disable); + if (!iwl_mvm_has_no_host_disable_tx(mvm)) + iwl_mvm_mld_sta_modify_disable_tx(mvm, mvmsta, disable); return; } @@ -4175,7 +4165,8 @@ struct iwl_mvm_sta *mvm_sta = iwl_mvm_sta_from_mac80211(sta); if (mvm->mld_api_is_used) { - iwl_mvm_mld_sta_modify_disable_tx_ap(mvm, sta, disable); + if (!iwl_mvm_has_no_host_disable_tx(mvm)) + iwl_mvm_mld_sta_modify_disable_tx_ap(mvm, sta, disable); return; } @@ -4230,7 +4221,9 @@ int i; if (mvm->mld_api_is_used) { - iwl_mvm_mld_modify_all_sta_disable_tx(mvm, mvmvif, disable); + if (!iwl_mvm_has_no_host_disable_tx(mvm)) + iwl_mvm_mld_modify_all_sta_disable_tx(mvm, mvmvif, + disable); return; } @@ -4344,8 +4337,7 @@ keyconf->flags = IEEE80211_KEY_FLAG_PAIRWISE; if (mld) { - /* - * The MFP flag is set according to the station mfp field. Since + /* The MFP flag is set according to the station mfp field. Since * we don't have a station, set it manually. */ u32 key_flags = diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/sta.h backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/sta.h --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/sta.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/sta.h 2023-10-04 04:18:43.000000000 +0800 @@ -286,12 +286,10 @@ * * @IWL_MVM_RXQ_EMPTY: empty sync notification * @IWL_MVM_RXQ_NOTIF_DEL_BA: notify RSS queues of delBA - * @IWL_MVM_RXQ_NSSN_SYNC: notify all the RSS queues with the new NSSN */ enum iwl_mvm_rxq_notif_type { IWL_MVM_RXQ_EMPTY, IWL_MVM_RXQ_NOTIF_DEL_BA, - IWL_MVM_RXQ_NSSN_SYNC, }; /** @@ -315,11 +313,6 @@ u32 baid; } __packed; -struct iwl_mvm_nssn_sync_data { - u32 baid; - u32 nssn; -} __packed; - /** * struct iwl_mvm_rxq_dup_data - per station per rx queue data * @last_seq: last sequence per tid for duplicate packet detection @@ -371,6 +364,7 @@ * and from Tx response flow, it needs a spinlock. * @tid_data: per tid data + mgmt. Look at %iwl_mvm_tid_data. * @tid_to_baid: a simple map of TID to baid + * @vif: a vif pointer * @reserved_queue: the queue reserved for this STA for DQA purposes * Every STA has is given one reserved queue to allow it to operate. If no * such queue can be guaranteed, the STA addition will fail. diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/tdls.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/tdls.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/tdls.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/tdls.c 2023-10-04 04:18:43.000000000 +0800 @@ -2,7 +2,7 @@ /* * Copyright (C) 2014 Intel Mobile Communications GmbH * Copyright (C) 2017 Intel Deutschland GmbH - * Copyright (C) 2018-2020, 2022 Intel Corporation + * Copyright (C) 2018-2020, 2022-2023 Intel Corporation */ #include #include "mvm.h" @@ -144,7 +144,8 @@ } void iwl_mvm_mac_mgd_protect_tdls_discover(struct ieee80211_hw *hw, - struct ieee80211_vif *vif) + struct ieee80211_vif *vif, + unsigned int link_id) { struct iwl_mvm *mvm = IWL_MAC80211_GET_MVM(hw); u32 duration = 2 * vif->bss_conf.dtim_period * vif->bss_conf.beacon_int; @@ -154,7 +155,7 @@ if (fw_has_capa(&mvm->fw->ucode_capa, IWL_UCODE_TLV_CAPA_SESSION_PROT_CMD)) iwl_mvm_schedule_session_protection(mvm, vif, duration, - duration, true); + duration, true, link_id); else iwl_mvm_protect_session(mvm, vif, duration, duration, 100, true); diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/time-event.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/time-event.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/time-event.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/time-event.c 2023-10-04 04:18:43.000000000 +0800 @@ -42,6 +42,7 @@ te_data->uid = 0; te_data->id = TE_MAX; te_data->vif = NULL; + te_data->link_id = -1; } void iwl_mvm_roc_done_wk(struct work_struct *wk) @@ -78,9 +79,29 @@ */ if (!WARN_ON(!mvm->p2p_device_vif)) { - mvmvif = iwl_mvm_vif_from_mac80211(mvm->p2p_device_vif); - iwl_mvm_flush_sta(mvm, &mvmvif->deflink.bcast_sta, - true); + struct ieee80211_vif *vif = mvm->p2p_device_vif; + + mvmvif = iwl_mvm_vif_from_mac80211(vif); + iwl_mvm_flush_sta(mvm, mvmvif->deflink.bcast_sta.sta_id, + mvmvif->deflink.bcast_sta.tfd_queue_msk); + + if (mvm->mld_api_is_used) { + iwl_mvm_mld_rm_bcast_sta(mvm, vif, + &vif->bss_conf); + + iwl_mvm_link_changed(mvm, vif, &vif->bss_conf, + LINK_CONTEXT_MODIFY_ACTIVE, + false); + } else { + iwl_mvm_rm_p2p_bcast_sta(mvm, vif); + iwl_mvm_binding_remove_vif(mvm, vif); + } + + /* Do not remove the PHY context as removing and adding + * a PHY context has timing overheads. Leaving it + * configured in FW would be useful in case the next ROC + * is with the same channel. + */ } } @@ -93,7 +114,8 @@ */ if (test_and_clear_bit(IWL_MVM_STATUS_ROC_AUX_RUNNING, &mvm->status)) { /* do the same in case of hot spot 2.0 */ - iwl_mvm_flush_sta(mvm, &mvm->aux_sta, true); + iwl_mvm_flush_sta(mvm, mvm->aux_sta.sta_id, + mvm->aux_sta.tfd_queue_msk); if (mvm->mld_api_is_used) { iwl_mvm_mld_rm_aux_sta(mvm); @@ -378,6 +400,22 @@ } } +void iwl_mvm_rx_roc_notif(struct iwl_mvm *mvm, + struct iwl_rx_cmd_buffer *rxb) +{ + struct iwl_rx_packet *pkt = rxb_addr(rxb); + struct iwl_roc_notif *notif = (void *)pkt->data; + + if (le32_to_cpu(notif->success) && le32_to_cpu(notif->started) && + le32_to_cpu(notif->activity) == ROC_ACTIVITY_HOTSPOT) { + set_bit(IWL_MVM_STATUS_ROC_AUX_RUNNING, &mvm->status); + ieee80211_ready_on_channel(mvm->hw); + } else { + iwl_mvm_roc_finished(mvm); + ieee80211_remain_on_channel_expired(mvm->hw); + } +} + /* * Handle A Aux ROC time event */ @@ -651,19 +689,46 @@ } } +/* Determine whether mac or link id should be used, and validate the link id */ +static int iwl_mvm_get_session_prot_id(struct iwl_mvm *mvm, + struct ieee80211_vif *vif, + u32 link_id) +{ + struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif); + int ver = iwl_fw_lookup_cmd_ver(mvm->fw, + WIDE_ID(MAC_CONF_GROUP, + SESSION_PROTECTION_CMD), 1); + + if (ver < 2) + return mvmvif->id; + + if (WARN(link_id < 0 || !mvmvif->link[link_id], + "Invalid link ID for session protection: %u\n", link_id)) + return -EINVAL; + + if (WARN(ieee80211_vif_is_mld(vif) && + !(vif->active_links & BIT(link_id)), + "Session Protection on an inactive link: %u\n", link_id)) + return -EINVAL; + + return mvmvif->link[link_id]->fw_link_id; +} + static void iwl_mvm_cancel_session_protection(struct iwl_mvm *mvm, - struct iwl_mvm_vif *mvmvif, - u32 id) + struct ieee80211_vif *vif, + u32 id, u32 link_id) { + int mac_link_id = iwl_mvm_get_session_prot_id(mvm, vif, link_id); struct iwl_mvm_session_prot_cmd cmd = { - .id_and_color = - cpu_to_le32(FW_CMD_ID_AND_COLOR(mvmvif->id, - mvmvif->color)), + .id_and_color = cpu_to_le32(mac_link_id), .action = cpu_to_le32(FW_CTXT_ACTION_REMOVE), .conf_id = cpu_to_le32(id), }; int ret; + if (mac_link_id < 0) + return; + ret = iwl_mvm_send_cmd_pdu(mvm, WIDE_ID(MAC_CONF_GROUP, SESSION_PROTECTION_CMD), 0, sizeof(cmd), &cmd); @@ -677,10 +742,12 @@ u32 *uid) { u32 id; + struct ieee80211_vif *vif = te_data->vif; struct iwl_mvm_vif *mvmvif; enum nl80211_iftype iftype; + unsigned int link_id; - if (!te_data->vif) + if (!vif) return false; mvmvif = iwl_mvm_vif_from_mac80211(te_data->vif); @@ -695,6 +762,7 @@ /* Save time event uid before clearing its data */ *uid = te_data->uid; id = te_data->id; + link_id = te_data->link_id; /* * The clear_data function handles time events that were already removed @@ -712,7 +780,8 @@ id != HOT_SPOT_CMD) { if (mvmvif && id < SESSION_PROTECT_CONF_MAX_ID) { /* Session protection is still ongoing. Cancel it */ - iwl_mvm_cancel_session_protection(mvm, mvmvif, id); + iwl_mvm_cancel_session_protection(mvm, vif, id, + link_id); if (iftype == NL80211_IFTYPE_P2P_DEVICE) { iwl_mvm_p2p_roc_finished(mvm); } @@ -835,18 +904,41 @@ { struct iwl_rx_packet *pkt = rxb_addr(rxb); struct iwl_mvm_session_prot_notif *notif = (void *)pkt->data; + unsigned int ver = + iwl_fw_lookup_cmd_ver(mvm->fw, + WIDE_ID(MAC_CONF_GROUP, + SESSION_PROTECTION_CMD), 2); + int id = le32_to_cpu(notif->mac_link_id); struct ieee80211_vif *vif; struct iwl_mvm_vif *mvmvif; + unsigned int notif_link_id; rcu_read_lock(); - vif = iwl_mvm_rcu_dereference_vif_id(mvm, le32_to_cpu(notif->mac_id), - true); + + if (ver <= 2) { + vif = iwl_mvm_rcu_dereference_vif_id(mvm, id, true); + } else { + struct ieee80211_bss_conf *link_conf = + iwl_mvm_rcu_fw_link_id_to_link_conf(mvm, id, true); + + if (!link_conf) + goto out_unlock; + + notif_link_id = link_conf->link_id; + vif = link_conf->vif; + } if (!vif) goto out_unlock; mvmvif = iwl_mvm_vif_from_mac80211(vif); + if (WARN(ver > 2 && mvmvif->time_event_data.link_id >= 0 && + mvmvif->time_event_data.link_id != notif_link_id, + "SESION_PROTECTION_NOTIF was received for link %u, while the current time event is on link %u\n", + notif_link_id, mvmvif->time_event_data.link_id)) + goto out_unlock; + /* The vif is not a P2P_DEVICE, maintain its time_event_data */ if (vif->type != NL80211_IFTYPE_P2P_DEVICE) { struct iwl_mvm_time_event_data *te_data = @@ -914,8 +1006,8 @@ if (!le32_to_cpu(notif->status) || !le32_to_cpu(notif->start)) { /* End TE, notify mac80211 */ mvmvif->time_event_data.id = SESSION_PROTECT_CONF_MAX_ID; - ieee80211_remain_on_channel_expired(mvm->hw); iwl_mvm_p2p_roc_finished(mvm); + ieee80211_remain_on_channel_expired(mvm->hw); } else if (le32_to_cpu(notif->start)) { if (WARN_ON(mvmvif->time_event_data.id != le32_to_cpu(notif->conf_id))) @@ -937,8 +1029,7 @@ struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif); struct iwl_mvm_session_prot_cmd cmd = { .id_and_color = - cpu_to_le32(FW_CMD_ID_AND_COLOR(mvmvif->id, - mvmvif->color)), + cpu_to_le32(iwl_mvm_get_session_prot_id(mvm, vif, 0)), .action = cpu_to_le32(FW_CTXT_ACTION_ADD), .duration_tu = cpu_to_le32(MSEC_TO_TU(duration)), }; @@ -948,6 +1039,9 @@ /* The time_event_data.id field is reused to save session * protection's configuration. */ + + mvmvif->time_event_data.link_id = 0; + switch (type) { case IEEE80211_ROC_TYPE_NORMAL: mvmvif->time_event_data.id = @@ -1064,6 +1158,37 @@ __iwl_mvm_remove_time_event(mvm, te_data, &uid); } +static void iwl_mvm_roc_rm_cmd(struct iwl_mvm *mvm, u32 activity) +{ + int ret; + struct iwl_roc_req roc_cmd = { + .action = cpu_to_le32(FW_CTXT_ACTION_REMOVE), + .activity = cpu_to_le32(activity), + }; + + lockdep_assert_held(&mvm->mutex); + ret = iwl_mvm_send_cmd_pdu(mvm, + WIDE_ID(MAC_CONF_GROUP, ROC_CMD), + 0, sizeof(roc_cmd), &roc_cmd); + WARN_ON(ret); +} + +static void iwl_mvm_roc_station_remove(struct iwl_mvm *mvm, + struct iwl_mvm_vif *mvmvif) +{ + u32 cmd_id = WIDE_ID(MAC_CONF_GROUP, ROC_CMD); + u8 fw_ver = iwl_fw_lookup_cmd_ver(mvm->fw, cmd_id, + IWL_FW_CMD_VER_UNKNOWN); + + if (fw_ver == IWL_FW_CMD_VER_UNKNOWN) + iwl_mvm_remove_aux_roc_te(mvm, mvmvif, + &mvmvif->hs_time_event_data); + else if (fw_ver == 3) + iwl_mvm_roc_rm_cmd(mvm, ROC_ACTIVITY_HOTSPOT); + else + IWL_ERR(mvm, "ROC command version %d mismatch!\n", fw_ver); +} + void iwl_mvm_stop_roc(struct iwl_mvm *mvm, struct ieee80211_vif *vif) { struct iwl_mvm_vif *mvmvif; @@ -1074,12 +1199,12 @@ mvmvif = iwl_mvm_vif_from_mac80211(vif); if (vif->type == NL80211_IFTYPE_P2P_DEVICE) { - iwl_mvm_cancel_session_protection(mvm, mvmvif, - mvmvif->time_event_data.id); + iwl_mvm_cancel_session_protection(mvm, vif, + mvmvif->time_event_data.id, + mvmvif->time_event_data.link_id); iwl_mvm_p2p_roc_finished(mvm); } else { - iwl_mvm_remove_aux_roc_te(mvm, mvmvif, - &mvmvif->hs_time_event_data); + iwl_mvm_roc_station_remove(mvm, mvmvif); iwl_mvm_roc_finished(mvm); } @@ -1198,25 +1323,28 @@ void iwl_mvm_schedule_session_protection(struct iwl_mvm *mvm, struct ieee80211_vif *vif, u32 duration, u32 min_duration, - bool wait_for_notif) + bool wait_for_notif, + unsigned int link_id) { struct iwl_mvm_vif *mvmvif = iwl_mvm_vif_from_mac80211(vif); struct iwl_mvm_time_event_data *te_data = &mvmvif->time_event_data; const u16 notif[] = { WIDE_ID(MAC_CONF_GROUP, SESSION_PROTECTION_NOTIF) }; struct iwl_notification_wait wait_notif; + int mac_link_id = iwl_mvm_get_session_prot_id(mvm, vif, link_id); struct iwl_mvm_session_prot_cmd cmd = { - .id_and_color = - cpu_to_le32(FW_CMD_ID_AND_COLOR(mvmvif->id, - mvmvif->color)), + .id_and_color = cpu_to_le32(mac_link_id), .action = cpu_to_le32(FW_CTXT_ACTION_ADD), .conf_id = cpu_to_le32(SESSION_PROTECT_CONF_ASSOC), .duration_tu = cpu_to_le32(MSEC_TO_TU(duration)), }; + if (mac_link_id < 0) + return; + lockdep_assert_held(&mvm->mutex); spin_lock_bh(&mvm->time_event_lock); - if (te_data->running && + if (te_data->running && te_data->link_id == link_id && time_after(te_data->end_jiffies, TU_TO_EXP_TIME(min_duration))) { IWL_DEBUG_TE(mvm, "We have enough time in the current TE: %u\n", jiffies_to_msecs(te_data->end_jiffies - jiffies)); @@ -1233,6 +1361,7 @@ te_data->id = le32_to_cpu(cmd.conf_id); te_data->duration = le32_to_cpu(cmd.duration_tu); te_data->vif = vif; + te_data->link_id = link_id; spin_unlock_bh(&mvm->time_event_lock); IWL_DEBUG_TE(mvm, "Add new session protection, duration %d TU\n", @@ -1242,11 +1371,7 @@ if (iwl_mvm_send_cmd_pdu(mvm, WIDE_ID(MAC_CONF_GROUP, SESSION_PROTECTION_CMD), 0, sizeof(cmd), &cmd)) { - IWL_ERR(mvm, - "Couldn't send the SESSION_PROTECTION_CMD\n"); - spin_lock_bh(&mvm->time_event_lock); - iwl_mvm_te_clear_data(mvm, te_data); - spin_unlock_bh(&mvm->time_event_lock); + goto send_cmd_err; } return; @@ -1259,12 +1384,19 @@ if (iwl_mvm_send_cmd_pdu(mvm, WIDE_ID(MAC_CONF_GROUP, SESSION_PROTECTION_CMD), 0, sizeof(cmd), &cmd)) { - IWL_ERR(mvm, - "Couldn't send the SESSION_PROTECTION_CMD\n"); iwl_remove_notification(&mvm->notif_wait, &wait_notif); + goto send_cmd_err; } else if (iwl_wait_notification(&mvm->notif_wait, &wait_notif, TU_TO_JIFFIES(100))) { IWL_ERR(mvm, "Failed to protect session until session protection\n"); } + return; + +send_cmd_err: + IWL_ERR(mvm, + "Couldn't send the SESSION_PROTECTION_CMD\n"); + spin_lock_bh(&mvm->time_event_lock); + iwl_mvm_te_clear_data(mvm, te_data); + spin_unlock_bh(&mvm->time_event_lock); } diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/time-event.h backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/time-event.h --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/time-event.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/time-event.h 2023-10-04 04:18:43.000000000 +0800 @@ -101,6 +101,14 @@ struct iwl_rx_cmd_buffer *rxb); /** + * iwl_mvm_rx_roc_notif - handles %DISCOVERY_ROC_NTF. + * @mvm: the mvm component + * @rxb: RX buffer + */ +void iwl_mvm_rx_roc_notif(struct iwl_mvm *mvm, + struct iwl_rx_cmd_buffer *rxb); + +/** * iwl_mvm_start_p2p_roc - start remain on channel for p2p device functionality * @mvm: the mvm component * @vif: the virtual interface for which the roc is requested. It is assumed @@ -198,11 +206,13 @@ * @duration: the requested duration of the protection * @min_duration: the minimum duration of the protection * @wait_for_notif: if true, will block until the start of the protection + * @link_id: The link to schedule a session protection for */ void iwl_mvm_schedule_session_protection(struct iwl_mvm *mvm, struct ieee80211_vif *vif, u32 duration, u32 min_duration, - bool wait_for_notif); + bool wait_for_notif, + unsigned int link_id); /** * iwl_mvm_rx_session_protect_notif - handles %SESSION_PROTECTION_NOTIF diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/tt.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/tt.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/tt.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/tt.c 2023-10-04 04:18:43.000000000 +0800 @@ -1,6 +1,6 @@ // SPDX-License-Identifier: GPL-2.0 OR BSD-3-Clause /* - * Copyright (C) 2012-2014, 2019-2022 Intel Corporation + * Copyright (C) 2012-2014, 2019-2023 Intel Corporation * Copyright (C) 2013-2014 Intel Mobile Communications GmbH * Copyright (C) 2015-2016 Intel Deutschland GmbH */ @@ -646,7 +646,6 @@ int trip, int temp) { struct iwl_mvm *mvm = thermal_zone_device_priv(device); - struct iwl_mvm_thermal_device *tzone; int ret; mutex_lock(&mvm->mutex); @@ -662,12 +661,6 @@ goto out; } - tzone = &mvm->tz_device; - if (!tzone) { - ret = -EIO; - goto out; - } - ret = iwl_mvm_send_temp_report_ths_cmd(mvm); out: mutex_unlock(&mvm->mutex); diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/tx.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/tx.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/tx.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/tx.c 2023-10-04 04:18:43.000000000 +0800 @@ -7,6 +7,7 @@ #include #include #include +#include #include #include @@ -1633,7 +1634,7 @@ seq_ctl = le16_to_cpu(tx_resp->seq_ctl); /* we can free until ssn % q.n_bd not inclusive */ - iwl_trans_reclaim(mvm->trans, txq_id, ssn, &skbs); + iwl_trans_reclaim(mvm->trans, txq_id, ssn, &skbs, false); while (!skb_queue_empty(&skbs)) { struct sk_buff *skb = __skb_dequeue(&skbs); @@ -1646,6 +1647,8 @@ iwl_trans_free_tx_cmd(mvm->trans, info->driver_data[1]); memset(&info->status, 0, sizeof(info->status)); + info->flags &= ~(IEEE80211_TX_STAT_ACK | + IEEE80211_TX_STAT_TX_FILTERED); /* inform mac80211 about what happened with the frame */ switch (status & TX_STATUS_MSK) { @@ -1991,7 +1994,7 @@ * block-ack window (we assume that they've been successfully * transmitted ... if not, it's too late anyway). */ - iwl_trans_reclaim(mvm->trans, txq, index, &reclaimed_skbs); + iwl_trans_reclaim(mvm->trans, txq, index, &reclaimed_skbs, is_flush); skb_queue_walk(&reclaimed_skbs, skb) { struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb); @@ -2005,6 +2008,8 @@ */ if (!is_flush) info->flags |= IEEE80211_TX_STAT_ACK; + else + info->flags &= ~IEEE80211_TX_STAT_ACK; } /* @@ -2335,24 +2340,10 @@ return ret; } -int iwl_mvm_flush_sta(struct iwl_mvm *mvm, void *sta, bool internal) +int iwl_mvm_flush_sta(struct iwl_mvm *mvm, u32 sta_id, u32 tfd_queue_mask) { - u32 sta_id, tfd_queue_msk; - - if (internal) { - struct iwl_mvm_int_sta *int_sta = sta; - - sta_id = int_sta->sta_id; - tfd_queue_msk = int_sta->tfd_queue_msk; - } else { - struct iwl_mvm_sta *mvm_sta = sta; - - sta_id = mvm_sta->deflink.sta_id; - tfd_queue_msk = mvm_sta->tfd_queue_msk; - } - if (iwl_mvm_has_new_tx_api(mvm)) return iwl_mvm_flush_sta_tids(mvm, sta_id, 0xffff); - return iwl_mvm_flush_tx_path(mvm, tfd_queue_msk); + return iwl_mvm_flush_tx_path(mvm, tfd_queue_mask); } diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/utils.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/utils.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/utils.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/utils.c 2023-10-04 04:18:43.000000000 +0800 @@ -350,6 +350,60 @@ return true; } +static int iwl_mvm_request_system_statistics(struct iwl_mvm *mvm, bool clear, + u8 cmd_ver) +{ + struct iwl_system_statistics_cmd system_cmd = { + .cfg_mask = clear ? + cpu_to_le32(IWL_STATS_CFG_FLG_ON_DEMAND_NTFY_MSK) : + cpu_to_le32(IWL_STATS_CFG_FLG_RESET_MSK | + IWL_STATS_CFG_FLG_ON_DEMAND_NTFY_MSK), + .type_id_mask = cpu_to_le32(IWL_STATS_NTFY_TYPE_ID_OPER | + IWL_STATS_NTFY_TYPE_ID_OPER_PART1), + }; + struct iwl_host_cmd cmd = { + .id = WIDE_ID(SYSTEM_GROUP, SYSTEM_STATISTICS_CMD), + .len[0] = sizeof(system_cmd), + .data[0] = &system_cmd, + }; + struct iwl_notification_wait stats_wait; + static const u16 stats_complete[] = { + WIDE_ID(SYSTEM_GROUP, SYSTEM_STATISTICS_END_NOTIF), + }; + int ret; + + if (cmd_ver != 1) { + IWL_FW_CHECK_FAILED(mvm, + "Invalid system statistics command version:%d\n", + cmd_ver); + return -EOPNOTSUPP; + } + + iwl_init_notification_wait(&mvm->notif_wait, &stats_wait, + stats_complete, ARRAY_SIZE(stats_complete), + NULL, NULL); + + mvm->statistics_clear = clear; + ret = iwl_mvm_send_cmd(mvm, &cmd); + if (ret) { + iwl_remove_notification(&mvm->notif_wait, &stats_wait); + return ret; + } + + /* 500ms for OPERATIONAL, PART1 and END notification should be enough + * for FW to collect data from all LMACs and send + * STATISTICS_NOTIFICATION to host + */ + ret = iwl_wait_notification(&mvm->notif_wait, &stats_wait, HZ / 2); + if (ret) + return ret; + + if (clear) + iwl_mvm_accu_radio_stats(mvm); + + return ret; +} + int iwl_mvm_request_statistics(struct iwl_mvm *mvm, bool clear) { struct iwl_statistics_cmd scmd = { @@ -361,8 +415,15 @@ .len[0] = sizeof(scmd), .data[0] = &scmd, }; + u8 cmd_ver = iwl_fw_lookup_cmd_ver(mvm->fw, + WIDE_ID(SYSTEM_GROUP, + SYSTEM_STATISTICS_CMD), + IWL_FW_CMD_VER_UNKNOWN); int ret; + if (cmd_ver != IWL_FW_CMD_VER_UNKNOWN) + return iwl_mvm_request_system_statistics(mvm, clear, cmd_ver); + /* From version 15 - STATISTICS_NOTIFICATION, the reply for * STATISTICS_CMD is empty, and the response is with * STATISTICS_NOTIFICATION notification diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/vendor-cmd.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/vendor-cmd.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/mvm/vendor-cmd.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/mvm/vendor-cmd.c 2023-10-04 04:18:43.000000000 +0800 @@ -90,6 +90,7 @@ [IWL_MVM_VENDOR_ATTR_RFIM_FREQ] = { .type = NLA_U32 }, [IWL_MVM_VENDOR_ATTR_RFIM_CHANNELS] = { .type = NLA_U32 }, [IWL_MVM_VENDOR_ATTR_RFIM_BANDS] = { .type = NLA_U32 }, + [IWL_MVM_VENDOR_ATTR_RFIM_CNVI_MASTER] = { .type = NLA_U32 }, [IWL_MVM_VENDOR_ATTR_ROAMING_FORBIDDEN] = { .type = NLA_U8 }, [IWL_MVM_VENDOR_ATTR_AUTH_MODE] = { .type = NLA_U32 }, [IWL_MVM_VENDOR_ATTR_CHANNEL_NUM] = { .type = NLA_U8 }, @@ -421,15 +422,16 @@ return -ENOMEM; if (mvm->trans->trans_cfg->integrated) { - if (iwl_rfi_ddr_supported(mvm)) + if (iwl_rfi_ddr_supported(mvm, mvm->force_enable_rfi)) capa = IWL_MVM_RFI_DDR_CAPA_ALL; else capa = IWL_MVM_RFI_DDR_CAPA_CNVI; } - if (iwl_rfi_dlvr_supported(mvm)) + if (iwl_rfi_dlvr_supported(mvm, mvm->force_enable_rfi)) capa |= IWL_MVM_RFI_DLVR_CAPA; + IWL_DEBUG_FW(mvm, "RFIm capabilities:%04x\n", capa); if (nla_put_u16(skb, IWL_MVM_VENDOR_ATTR_RFIM_CAPA, capa)) { kfree_skb(skb); return -ENOBUFS; @@ -556,7 +558,7 @@ } mutex_lock(&mvm->mutex); - err = iwl_rfi_send_config_cmd(mvm, rfi_ddr_table); + err = iwl_rfi_send_config_cmd(mvm, rfi_ddr_table, false, false); mutex_unlock(&mvm->mutex); if (err) IWL_ERR(mvm, "Failed to send rfi table to FW, error %d\n", err); @@ -567,6 +569,81 @@ return err; } +enum iwl_rfi_cnvi_master_conf { + IWL_MVM_RFI_CNVI_DLVR_NOT_MASTER = BIT(0), + IWL_MVM_RFI_CNVI_DDR_NOT_MASTER = BIT(1), +}; + +#define IWL_MVM_RFI_CNVI_NOT_MASTER (IWL_MVM_RFI_CNVI_DLVR_NOT_MASTER |\ + IWL_MVM_RFI_CNVI_DDR_NOT_MASTER) + +static int iwl_vendor_rfi_set_cnvi_master(struct wiphy *wiphy, + struct wireless_dev *wdev, + const void *data, int data_len) +{ + struct ieee80211_hw *hw = wiphy_to_ieee80211_hw(wiphy); + struct iwl_mvm *mvm = IWL_MAC80211_GET_MVM(hw); + bool old_rfi_wlan_master = mvm->rfi_wlan_master; + struct nlattr **tb; + int err = 0; + u32 rfi_master_conf; + + tb = iwl_mvm_parse_vendor_data(data, data_len); + if (IS_ERR(tb)) + return PTR_ERR(tb); + + if (!tb[IWL_MVM_VENDOR_ATTR_RFIM_CNVI_MASTER]) { + err = -EINVAL; + goto free; + } + + rfi_master_conf = nla_get_u32(tb[IWL_MVM_VENDOR_ATTR_RFIM_CNVI_MASTER]); + IWL_DEBUG_FW(mvm, "rfi cnvi master conf is 0x%08x\n", rfi_master_conf); + rfi_master_conf &= IWL_MVM_RFI_CNVI_NOT_MASTER; + + mutex_lock(&mvm->mutex); + + /* rfi_master_conf can be 0 or 3 only. + * i.e 0 means CNVI is master. 3 means user-space application is master. + * 1 and 2 are invalid configurations, which means there is no way for + * the user space to take partial control. + */ + if (!rfi_master_conf) { + mvm->rfi_wlan_master = true; + } else if (rfi_master_conf == IWL_MVM_RFI_CNVI_NOT_MASTER) { + mvm->rfi_wlan_master = false; + } else { + mutex_unlock(&mvm->mutex); + err = -EINVAL; + goto free; + } + + /* if app sends two consecutive enable/disable then + * driver will not send the same table to the firmware + */ + if (old_rfi_wlan_master != mvm->rfi_wlan_master || + mvm->force_enable_rfi != mvm->rfi_wlan_master) { + /* By-pass sending of RFI_CONFIG command, if user space + * takes control when "fw_rfi_state" is not PMC_SUPPORTED. + */ + if (mvm->fw_rfi_state == IWL_RFI_PMC_SUPPORTED || + mvm->rfi_wlan_master) + err = iwl_rfi_send_config_cmd(mvm, NULL, true, false); + } else { + IWL_ERR(mvm, + "Wlan RFI master configuration is same as old:%d\n", + old_rfi_wlan_master); + } + + if (err) + mvm->rfi_wlan_master = old_rfi_wlan_master; + + mutex_unlock(&mvm->mutex); +free: + kfree(tb); + return err; +} + static int iwl_vendor_set_nic_txpower_limit(struct wiphy *wiphy, struct wireless_dev *wdev, const void *data, int data_len) @@ -1963,6 +2040,17 @@ .policy = iwl_mvm_vendor_attr_policy, .maxattr = MAX_IWL_MVM_VENDOR_ATTR, }, + { + .info = { + .vendor_id = INTEL_OUI, + .subcmd = IWL_MVM_VENDOR_CMD_RFIM_SET_CNVI_MASTER, + }, + .flags = WIPHY_VENDOR_CMD_NEED_WDEV | + WIPHY_VENDOR_CMD_NEED_RUNNING, + .doit = iwl_vendor_rfi_set_cnvi_master, + .policy = iwl_mvm_vendor_attr_policy, + .maxattr = MAX_IWL_MVM_VENDOR_ATTR, + }, { .info = { .vendor_id = INTEL_OUI, diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/pcie/ctxt-info-gen3.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/pcie/ctxt-info-gen3.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/pcie/ctxt-info-gen3.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/pcie/ctxt-info-gen3.c 2023-10-04 04:18:43.000000000 +0800 @@ -306,7 +306,8 @@ } len = len0 + len1; - dram->block = iwl_pcie_ctxt_info_dma_alloc_coherent(trans, len, &dram->physical); + dram->block = iwl_pcie_ctxt_info_dma_alloc_coherent(trans, len, + &dram->physical); if (!dram->block) { IWL_DEBUG_FW(trans, "Failed to allocate PNVM DMA.\n"); return -ENOMEM; diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/pcie/drv.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/pcie/drv.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/pcie/drv.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/pcie/drv.c 2023-10-04 04:18:43.000000000 +0800 @@ -483,6 +483,8 @@ IWL_DEV_INFO(0x2726, 0x1672, iwlax211_2ax_cfg_so_gf_a0, iwl_ax211_killer_1675i_name), IWL_DEV_INFO(0x51F0, 0x1671, iwlax211_2ax_cfg_so_gf_a0, iwl_ax211_killer_1675s_name), IWL_DEV_INFO(0x51F0, 0x1672, iwlax211_2ax_cfg_so_gf_a0, iwl_ax211_killer_1675i_name), + IWL_DEV_INFO(0x51F1, 0x1671, iwlax211_2ax_cfg_so_gf_a0, iwl_ax211_killer_1675s_name), + IWL_DEV_INFO(0x51F1, 0x1672, iwlax211_2ax_cfg_so_gf_a0, iwl_ax211_killer_1675i_name), IWL_DEV_INFO(0x54F0, 0x1671, iwlax211_2ax_cfg_so_gf_a0, iwl_ax211_killer_1675s_name), IWL_DEV_INFO(0x54F0, 0x1672, iwlax211_2ax_cfg_so_gf_a0, iwl_ax211_killer_1675i_name), IWL_DEV_INFO(0x7A70, 0x1671, iwlax211_2ax_cfg_so_gf_a0, iwl_ax211_killer_1675s_name), @@ -820,8 +822,13 @@ _IWL_DEV_INFO(IWL_CFG_ANY, IWL_CFG_ANY, IWL_CFG_MAC_TYPE_GL, IWL_CFG_ANY, IWL_CFG_RF_TYPE_FM, IWL_CFG_ANY, IWL_CFG_ANY, - IWL_CFG_ANY, IWL_CFG_ANY, IWL_CFG_NO_CDB, + IWL_CFG_320, IWL_CFG_ANY, IWL_CFG_NO_CDB, iwl_cfg_gl, iwl_bz_name), + _IWL_DEV_INFO(IWL_CFG_ANY, IWL_CFG_ANY, + IWL_CFG_MAC_TYPE_GL, IWL_CFG_ANY, + IWL_CFG_RF_TYPE_FM, IWL_CFG_ANY, IWL_CFG_ANY, + IWL_CFG_NO_320, IWL_CFG_ANY, IWL_CFG_NO_CDB, + iwl_cfg_gl, iwl_mtp_name), /* SoF with JF2 */ _IWL_DEV_INFO(IWL_CFG_ANY, IWL_CFG_ANY, @@ -933,9 +940,8 @@ /* * Read rf id and cdb info from prph register and store it */ -static int get_crf_id(struct iwl_trans *iwl_trans) +static void get_crf_id(struct iwl_trans *iwl_trans) { - int ret = 0; u32 sd_reg_ver_addr; u32 val = 0; @@ -961,8 +967,6 @@ IWL_INFO(iwl_trans, "Detected crf-id 0x%x, cnv-id 0x%x wfpm id 0x%x\n", iwl_trans->hw_crf_id, iwl_trans->hw_cnv_id, iwl_trans->hw_wfpm_id); - - return ret; } /* @@ -1195,6 +1199,7 @@ if (dev_info) { iwl_trans->cfg = dev_info->cfg; iwl_trans->name = dev_info->name; + iwl_trans->no_160 = dev_info->no_160 == IWL_CFG_NO_160; } #if IS_ENABLED(CPTCFG_IWLMVM) diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/pcie/rx.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/pcie/rx.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/pcie/rx.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/pcie/rx.c 2023-10-04 04:18:43.000000000 +0800 @@ -1349,8 +1349,7 @@ if (len < sizeof(*pkt) || offset > max_len) break; - trace_iwlwifi_dev_rx(trans->dev, trans, pkt, len); - trace_iwlwifi_dev_rx_data(trans->dev, trans, pkt, len); + maybe_trace_iwlwifi_dev_rx(trans, pkt, len); /* Reclaim a command buffer only if this packet is a response * to a (driver-originated) command. diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/pcie/trans.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/pcie/trans.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/pcie/trans.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/pcie/trans.c 2023-10-04 04:18:43.000000000 +0800 @@ -620,7 +620,8 @@ iwl_set_bit(trans, CSR_DBG_LINK_PWR_MGMT_REG, CSR_RESET_LINK_PWR_MGMT_DISABLED); - usleep_range(1000, 2000); + usleep_range(1000 * CPTCFG_IWL_DELAY_FACTOR, + 2000 * CPTCFG_IWL_DELAY_FACTOR); for (iter = 0; iter < 10; iter++) { int t = 0; @@ -1315,6 +1316,7 @@ if (test_and_clear_bit(STATUS_DEVICE_ENABLED, &trans->status)) { IWL_DEBUG_INFO(trans, "DEVICE_ENABLED bit was set and is now cleared\n"); + iwl_pcie_synchronize_irqs(trans); iwl_pcie_rx_napi_sync(trans); iwl_pcie_tx_stop(trans); iwl_pcie_rx_stop(trans); @@ -2156,18 +2158,29 @@ container_of(wk, struct iwl_trans_pcie_removal, work); struct pci_dev *pdev = removal->pdev; static char *prop[] = {"EVENT=INACCESSIBLE", NULL}; - struct pci_bus *bus = pdev->bus; + struct pci_bus *bus; + + pci_lock_rescan_remove(); + + bus = pdev->bus; + /* in this case, something else already removed the device */ + if (!bus) + goto out; dev_err(&pdev->dev, "Device gone - attempting removal\n"); + kobject_uevent_env(&pdev->dev.kobj, KOBJ_CHANGE, prop); - pci_lock_rescan_remove(); - pci_dev_put(pdev); + pci_stop_and_remove_bus_device(pdev); - if (removal->rescan && bus) { + pci_dev_put(pdev); + + if (removal->rescan) { if (bus->parent) bus = bus->parent; pci_rescan_bus(bus); } + +out: pci_unlock_rescan_remove(); kfree(removal); @@ -2182,6 +2195,7 @@ return; IWL_ERR(trans, "Device gone - scheduling removal!\n"); + iwl_pcie_dump_csr(trans); /* * get a module reference to avoid doing this @@ -2418,32 +2432,6 @@ ofs, val); } -static void iwl_trans_pcie_block_txq_ptrs(struct iwl_trans *trans, bool block) -{ - int i; - - for (i = 0; i < trans->trans_cfg->base_params->num_of_queues; i++) { - struct iwl_txq *txq = trans->txqs.txq[i]; - - if (i == trans->txqs.cmd.q_id) - continue; - - spin_lock_bh(&txq->lock); - - if (!block && !(WARN_ON_ONCE(!txq->block))) { - txq->block--; - if (!txq->block) { - iwl_write32(trans, HBUS_TARG_WRPTR, - txq->write_ptr | (i << 8)); - } - } else if (block) { - txq->block++; - } - - spin_unlock_bh(&txq->lock); - } -} - #define IWL_FLUSH_WAIT_MS 2000 static int iwl_trans_pcie_rxq_dma_data(struct iwl_trans *trans, int queue, @@ -3627,7 +3615,6 @@ .wait_tx_queues_empty = iwl_trans_pcie_wait_txqs_empty, .freeze_txq_timer = iwl_trans_txq_freeze_timer, - .block_txq_ptrs = iwl_trans_pcie_block_txq_ptrs, #ifdef CPTCFG_IWLWIFI_DEBUGFS .debugfs_cleanup = iwl_trans_pcie_debugfs_cleanup, #endif @@ -3705,7 +3692,7 @@ init_waitqueue_head(&trans_pcie->imr_waitq); trans_pcie->rba.alloc_wq = alloc_workqueue("rb_allocator", - WQ_HIGHPRI | WQ_UNBOUND, 1); + WQ_HIGHPRI | WQ_UNBOUND, 0); if (!trans_pcie->rba.alloc_wq) { ret = -ENOMEM; goto out_free_trans; diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/pcie/trans-gen2.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/pcie/trans-gen2.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/pcie/trans-gen2.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/pcie/trans-gen2.c 2023-10-04 04:18:43.000000000 +0800 @@ -161,6 +161,7 @@ if (test_and_clear_bit(STATUS_DEVICE_ENABLED, &trans->status)) { IWL_DEBUG_INFO(trans, "DEVICE_ENABLED bit was set and is now cleared\n"); + iwl_pcie_synchronize_irqs(trans); iwl_pcie_rx_napi_sync(trans); iwl_txq_gen2_tx_free(trans); iwl_pcie_rx_stop(trans); diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/pcie/tx.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/pcie/tx.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/pcie/tx.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/pcie/tx.c 2023-10-04 04:18:43.000000000 +0800 @@ -873,6 +873,33 @@ /*************** HOST COMMAND QUEUE FUNCTIONS *****/ +static void iwl_trans_pcie_block_txq_ptrs(struct iwl_trans *trans, bool block) +{ + int i; + + for (i = 0; i < trans->trans_cfg->base_params->num_of_queues; i++) { + struct iwl_txq *txq = trans->txqs.txq[i]; + + if (i == trans->txqs.cmd.q_id) + continue; + + /* we skip the command queue (obviously) so it's OK to nest */ + spin_lock_nested(&txq->lock, 1); + + if (!block && !(WARN_ON_ONCE(!txq->block))) { + txq->block--; + if (!txq->block) { + iwl_write32(trans, HBUS_TARG_WRPTR, + txq->write_ptr | (i << 8)); + } + } else if (block) { + txq->block++; + } + + spin_unlock(&txq->lock); + } +} + /* * iwl_pcie_enqueue_hcmd - enqueue a uCode command * @priv: device private data point @@ -1137,6 +1164,9 @@ goto out; } + if (cmd->flags & CMD_BLOCK_TXQS) + iwl_trans_pcie_block_txq_ptrs(trans, true); + /* Increment and update queue's write index */ txq->write_ptr = iwl_txq_inc_wrap(trans, txq->write_ptr); iwl_pcie_txq_inc_wr_ptr(trans, txq); @@ -1202,8 +1232,8 @@ meta->source->_rx_page_order = trans_pcie->rx_page_order; } - if (meta->flags & CMD_WANT_ASYNC_CALLBACK) - iwl_op_mode_async_cb(trans->op_mode, cmd); + if (meta->flags & CMD_BLOCK_TXQS) + iwl_trans_pcie_block_txq_ptrs(trans, false); iwl_pcie_cmdq_reclaim(trans, txq_id, index); diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/pcie/tx-gen2.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/pcie/tx-gen2.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/pcie/tx-gen2.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/pcie/tx-gen2.c 2023-10-04 04:18:43.000000000 +0800 @@ -1,7 +1,7 @@ // SPDX-License-Identifier: GPL-2.0 OR BSD-3-Clause /* * Copyright (C) 2017 Intel Deutschland GmbH - * Copyright (C) 2018-2020 Intel Corporation + * Copyright (C) 2018-2020, 2023 Intel Corporation */ #include #include @@ -42,6 +42,9 @@ struct iwl_tfh_tfd *tfd; unsigned long flags; + if (WARN_ON(cmd->flags & CMD_BLOCK_TXQS)) + return -EINVAL; + copy_size = sizeof(struct iwl_cmd_header_wide); cmd_size = sizeof(struct iwl_cmd_header_wide); diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/queue/tx.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/queue/tx.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/queue/tx.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/queue/tx.c 2023-10-04 04:18:43.000000000 +0800 @@ -1576,7 +1576,7 @@ /* Frees buffers until index _not_ inclusive */ void iwl_txq_reclaim(struct iwl_trans *trans, int txq_id, int ssn, - struct sk_buff_head *skbs) + struct sk_buff_head *skbs, bool is_flush) { struct iwl_txq *txq = trans->txqs.txq[txq_id]; int tfd_num, read_ptr, last_to_free; @@ -1651,9 +1651,11 @@ if (iwl_txq_space(trans, txq) > txq->low_mark && test_bit(txq_id, trans->txqs.queue_stopped)) { struct sk_buff_head overflow_skbs; + struct sk_buff *skb; __skb_queue_head_init(&overflow_skbs); - skb_queue_splice_init(&txq->overflow_q, &overflow_skbs); + skb_queue_splice_init(&txq->overflow_q, + is_flush ? skbs : &overflow_skbs); /* * We are going to transmit from the overflow queue. @@ -1673,8 +1675,7 @@ */ spin_unlock_bh(&txq->lock); - while (!skb_queue_empty(&overflow_skbs)) { - struct sk_buff *skb = __skb_dequeue(&overflow_skbs); + while ((skb = __skb_dequeue(&overflow_skbs))) { struct iwl_device_tx_cmd *dev_cmd_ptr; dev_cmd_ptr = *(void **)((u8 *)skb->cb + diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/queue/tx.h backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/queue/tx.h --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/queue/tx.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/queue/tx.h 2023-10-04 04:18:43.000000000 +0800 @@ -181,7 +181,7 @@ struct iwl_txq *txq, u16 byte_cnt, int num_tbs); void iwl_txq_reclaim(struct iwl_trans *trans, int txq_id, int ssn, - struct sk_buff_head *skbs); + struct sk_buff_head *skbs, bool is_flush); void iwl_txq_set_q_ptrs(struct iwl_trans *trans, int txq_id, int ptr); void iwl_trans_txq_freeze_timer(struct iwl_trans *trans, unsigned long txqs, bool freeze); diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/xvt/fw-api.h backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/xvt/fw-api.h --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/xvt/fw-api.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/xvt/fw-api.h 2023-10-04 04:18:43.000000000 +0800 @@ -1,6 +1,6 @@ /* SPDX-License-Identifier: GPL-2.0 OR BSD-3-Clause */ /* - * Copyright (C) 2005-2014, 2018 Intel Corporation + * Copyright (C) 2005-2014, 2018, 2023 Intel Corporation * Copyright (C) 2015-2017 Intel Deutschland GmbH */ #ifndef __fw_api_h__ @@ -82,7 +82,7 @@ struct xvt_debug_res { __le32 dw_num; - __le32 data[0]; + __le32 data[]; }; /* DEBUG_XVT_RES_API_S_VER_1 */ #endif /* __fw_api_h__ */ diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/xvt/user-infc.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/xvt/user-infc.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/xvt/user-infc.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/xvt/user-infc.c 2023-10-04 04:18:43.000000000 +0800 @@ -149,9 +149,40 @@ iwl_xvt_user_send_notif(xvt, IWL_XVT_CMD_TX_CMD_RESP, data, size, GFP_ATOMIC); break; + case WIDE_ID(STATISTICS_GROUP, STATISTICS_OPER_NOTIF): + iwl_xvt_user_send_notif(xvt, + IWL_TM_USER_CMD_NOTIF_STATS_OPER, + data, size, GFP_ATOMIC); + break; + case WIDE_ID(STATISTICS_GROUP, STATISTICS_OPER_PART1_NOTIF): + iwl_xvt_user_send_notif(xvt, + IWL_TM_USER_CMD_NOTIF_STATS_OPER_PART1, + data, size, GFP_ATOMIC); + break; + case WIDE_ID(STATISTICS_GROUP, STATISTICS_OPER_PART2_NOTIF): + iwl_xvt_user_send_notif(xvt, + IWL_TM_USER_CMD_NOTIF_STATS_OPER_PART2, + data, size, GFP_ATOMIC); + break; + case WIDE_ID(STATISTICS_GROUP, STATISTICS_OPER_PART3_NOTIF): + iwl_xvt_user_send_notif(xvt, + IWL_TM_USER_CMD_NOTIF_STATS_OPER_PART3, + data, size, GFP_ATOMIC); + break; + case WIDE_ID(STATISTICS_GROUP, STATISTICS_OPER_PART4_NOTIF): + iwl_xvt_user_send_notif(xvt, + IWL_TM_USER_CMD_NOTIF_STATS_OPER_PART4, + data, size, GFP_ATOMIC); + break; + case WIDE_ID(SYSTEM_GROUP, SYSTEM_STATISTICS_END_NOTIF): + iwl_xvt_user_send_notif(xvt, + IWL_TM_USER_CMD_NOTIF_STATS_END, + data, size, GFP_ATOMIC); + break; default: - IWL_DEBUG_INFO(xvt, "xVT mode RX command 0x%x not handled\n", - pkt->hdr.cmd); + IWL_DEBUG_INFO(xvt, + "xVT mode RX group 0x%x command 0x%x not handled\n", + pkt->hdr.group_id, pkt->hdr.cmd); } } diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/xvt/xvt.c backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/xvt/xvt.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/intel/iwlwifi/xvt/xvt.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/intel/iwlwifi/xvt/xvt.c 2023-10-04 04:18:43.000000000 +0800 @@ -1,6 +1,6 @@ // SPDX-License-Identifier: GPL-2.0 OR BSD-3-Clause /* - * Copyright (C) 2005-2014, 2018-2022 Intel Corporation + * Copyright (C) 2005-2014, 2018-2023 Intel Corporation * Copyright (C) 2015-2017 Intel Deutschland GmbH */ #include @@ -354,7 +354,7 @@ static void iwl_xvt_reclaim_and_free(struct iwl_xvt *xvt, struct tx_meta_data *tx_data, - u16 txq_id, u16 ssn) + u16 txq_id, u16 ssn, bool is_flush) { struct sk_buff_head skbs; struct sk_buff *skb; @@ -362,7 +362,7 @@ __skb_queue_head_init(&skbs); - iwl_trans_reclaim(xvt->trans, txq_id, ssn, &skbs); + iwl_trans_reclaim(xvt->trans, txq_id, ssn, &skbs, is_flush); while (!skb_queue_empty(&skbs)) { skb = __skb_dequeue(&skbs); @@ -459,7 +459,8 @@ if (!tx_data) continue; - iwl_xvt_reclaim_and_free(xvt, tx_data, queue_num, read_after); + iwl_xvt_reclaim_and_free(xvt, tx_data, queue_num, + read_after, true); } } } @@ -482,7 +483,7 @@ if (unlikely(status != TX_STATUS_SUCCESS)) IWL_WARN(xvt, "got error TX_RSP status %#x\n", status); - iwl_xvt_reclaim_and_free(xvt, tx_data, txq_id, ssn); + iwl_xvt_reclaim_and_free(xvt, tx_data, txq_id, ssn, false); } static void iwl_xvt_rx_tx_cmd_handler(struct iwl_xvt *xvt, @@ -519,7 +520,7 @@ if (!tx_data) return; - iwl_xvt_reclaim_and_free(xvt, tx_data, queue, tfd_idx); + iwl_xvt_reclaim_and_free(xvt, tx_data, queue, tfd_idx, false); out: IWL_DEBUG_TX_REPLY(xvt, "BA_NOTIFICATION Received from sta_id = %d, flags %x, sent:%d, acked:%d\n", @@ -537,7 +538,7 @@ if (!tx_data) return; - iwl_xvt_reclaim_and_free(xvt, tx_data, scd_flow, scd_ssn); + iwl_xvt_reclaim_and_free(xvt, tx_data, scd_flow, scd_ssn, false); IWL_DEBUG_TX_REPLY(xvt, "ba_notif from %pM, sta_id = %d\n", ba_notif->sta_addr, ba_notif->sta_id); @@ -1127,7 +1128,10 @@ { int ret; u32 value; - struct iwl_lari_config_change_cmd_v6 cmd = {}; + struct iwl_lari_config_change_cmd_v7 cmd = {}; + u8 cmd_ver = iwl_fw_lookup_cmd_ver(xvt->fw, + WIDE_ID(REGULATORY_AND_NVM_GROUP, + LARI_CONFIG_CHANGE), 1); cmd.config_bitmap = iwl_acpi_get_lari_config_bitmap(&xvt->fwrt); @@ -1137,15 +1141,32 @@ if (!ret) cmd.oem_unii4_allow_bitmap = cpu_to_le32(value); + ret = iwl_acpi_get_dsm_u32(xvt->fwrt.dev, 0, + DSM_FUNC_ACTIVATE_CHANNEL, + &iwl_guid, &value); + if (!ret) { + if (cmd_ver < 8) + value &= ~ACTIVATE_5G2_IN_WW_MASK; + cmd.chan_state_active_bitmap = cpu_to_le32(value); + } + + ret = iwl_acpi_get_dsm_u32(xvt->fwrt.dev, 0, + DSM_FUNC_ENERGY_DETECTION_THRESHOLD, + &iwl_guid, &value); + if (!ret) + cmd.edt_bitmap = cpu_to_le32(value); + if (cmd.config_bitmap || cmd.oem_uhb_allow_bitmap || - cmd.oem_unii4_allow_bitmap) { + cmd.oem_unii4_allow_bitmap || + cmd.edt_bitmap) { size_t cmd_size; - u8 cmd_ver = iwl_fw_lookup_cmd_ver(xvt->fw, - WIDE_ID(REGULATORY_AND_NVM_GROUP, - LARI_CONFIG_CHANGE), 1); switch (cmd_ver) { + case 8: + case 7: + cmd_size = sizeof(struct iwl_lari_config_change_cmd_v7); + break; case 6: cmd_size = sizeof(struct iwl_lari_config_change_cmd_v6); break; @@ -1175,6 +1196,9 @@ le32_to_cpu(cmd.oem_unii4_allow_bitmap), le32_to_cpu(cmd.chan_state_active_bitmap), cmd_ver); + IWL_DEBUG_RADIO(xvt, + "sending LARI_CONFIG_CHANGE, edt_bitmap=0x%x\n", + le32_to_cpu(cmd.edt_bitmap)); ret = iwl_xvt_send_cmd_pdu(xvt, WIDE_ID(REGULATORY_AND_NVM_GROUP, diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/legacy/Makefile backport-iwlwifi-dkms-11510/drivers/net/wireless/legacy/Makefile --- backport-iwlwifi-dkms-11289/drivers/net/wireless/legacy/Makefile 1970-01-01 08:00:00.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/legacy/Makefile 2023-10-04 04:18:43.000000000 +0800 @@ -0,0 +1,6 @@ +# 16-bit wireless PCMCIA client drivers +#obj-$(CONFIG_PCMCIA_RAYCS) += ray_cs.o +#obj-$(CONFIG_PCMCIA_WL3501) += wl3501_cs.o +# +#obj-$(CONFIG_USB_NET_RNDIS_WLAN) += rndis_wlan.o + diff -Nru backport-iwlwifi-dkms-11289/drivers/net/wireless/virtual/mac80211_hwsim.c backport-iwlwifi-dkms-11510/drivers/net/wireless/virtual/mac80211_hwsim.c --- backport-iwlwifi-dkms-11289/drivers/net/wireless/virtual/mac80211_hwsim.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/drivers/net/wireless/virtual/mac80211_hwsim.c 2023-10-04 04:18:43.000000000 +0800 @@ -190,10 +190,25 @@ } }; +static const struct ieee80211_regdomain hwsim_world_regdom_custom_04 = { + .n_reg_rules = 6, + .alpha2 = "99", + .reg_rules = { + REG_RULE(2412 - 10, 2462 + 10, 40, 0, 20, 0), + REG_RULE(2484 - 10, 2484 + 10, 40, 0, 20, 0), + REG_RULE(5150 - 10, 5240 + 10, 80, 0, 30, 0), + REG_RULE(5260 - 10, 5320 + 10, 80, 0, 30, + NL80211_RRF_DFS_CONCURRENT | NL80211_RRF_DFS), + REG_RULE(5745 - 10, 5825 + 10, 80, 0, 30, 0), + REG_RULE(5855 - 10, 5925 + 10, 80, 0, 33, 0), + } +}; + static const struct ieee80211_regdomain *hwsim_world_regdom_custom[] = { &hwsim_world_regdom_custom_01, &hwsim_world_regdom_custom_02, &hwsim_world_regdom_custom_03, + &hwsim_world_regdom_custom_04, }; struct hwsim_vif_priv { @@ -2450,6 +2465,14 @@ vp->assoc = vif->cfg.assoc; vp->aid = vif->cfg.aid; } + + if (vif->type == NL80211_IFTYPE_STATION && + changed & BSS_CHANGED_MLD_VALID_LINKS) { + u16 usable_links = ieee80211_vif_usable_links(vif); + + if (vif->active_links != usable_links) + ieee80211_set_active_links_async(vif, usable_links); + } } static void mac80211_hwsim_link_info_changed(struct ieee80211_hw *hw, @@ -5293,6 +5316,10 @@ schedule_timeout_interruptible(1); } + /* TODO: Add param */ + wiphy_ext_feature_set(hw->wiphy, + NL80211_EXT_FEATURE_DFS_CONCURRENT); + if (param->no_vif) ieee80211_hw_set(hw, NO_AUTO_VIF); @@ -5983,12 +6010,11 @@ ret = -ENOMEM; goto out_free; } + param.pmsr_capa = pmsr_capa; + ret = parse_pmsr_capa(info->attrs[HWSIM_ATTR_PMSR_SUPPORT], pmsr_capa, info); - if (ret) { - kfree(pmsr_capa); + if (ret) goto out_free; - } - param.pmsr_capa = pmsr_capa; } ret = mac80211_hwsim_new_radio(info, ¶m); diff -Nru backport-iwlwifi-dkms-11289/include/crypto/backport-public_key.h backport-iwlwifi-dkms-11510/include/crypto/backport-public_key.h --- backport-iwlwifi-dkms-11289/include/crypto/backport-public_key.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/include/crypto/backport-public_key.h 2023-10-04 04:18:43.000000000 +0800 @@ -48,8 +48,6 @@ const char *pkey_algo; const char *hash_algo; const char *encoding; - const void *data; - unsigned int data_size; }; extern void public_key_signature_free(struct public_key_signature *sig); diff -Nru backport-iwlwifi-dkms-11289/include/linux/ieee80211.h backport-iwlwifi-dkms-11510/include/linux/ieee80211.h --- backport-iwlwifi-dkms-11289/include/linux/ieee80211.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/include/linux/ieee80211.h 2023-10-04 04:18:43.000000000 +0800 @@ -4963,7 +4963,7 @@ if (control & IEEE80211_MLE_STA_CONTROL_DTIM_INFO_PRESENT) info_len += 2; if (control & IEEE80211_MLE_STA_CONTROL_COMPLETE_PROFILE && - control & IEEE80211_MLE_STA_CONTROL_NSTR_BITMAP_SIZE) { + control & IEEE80211_MLE_STA_CONTROL_NSTR_LINK_PAIR_PRESENT) { if (control & IEEE80211_MLE_STA_CONTROL_NSTR_BITMAP_SIZE) info_len += 2; else @@ -5002,7 +5002,7 @@ if (control & IEEE80211_MLE_STA_CONTROL_DTIM_INFO_PRESENT) pos += 2; if (control & IEEE80211_MLE_STA_CONTROL_COMPLETE_PROFILE && - control & IEEE80211_MLE_STA_CONTROL_NSTR_BITMAP_SIZE) { + control & IEEE80211_MLE_STA_CONTROL_NSTR_LINK_PAIR_PRESENT) { if (control & IEEE80211_MLE_STA_CONTROL_NSTR_BITMAP_SIZE) pos += 2; else diff -Nru backport-iwlwifi-dkms-11289/include/linux/overflow.h backport-iwlwifi-dkms-11510/include/linux/overflow.h --- backport-iwlwifi-dkms-11289/include/linux/overflow.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/include/linux/overflow.h 2023-10-04 04:18:43.000000000 +0800 @@ -286,7 +286,7 @@ * @member: Name of the array member. * @count: Number of elements in the array. * - * Calculates size of memory needed for structure @p followed by an + * Calculates size of memory needed for structure of @p followed by an * array of @count number of @member elements. * * Return: number of bytes needed or SIZE_MAX on overflow. @@ -296,4 +296,20 @@ sizeof(*(p)) + flex_array_size(p, member, count), \ size_add(sizeof(*(p)), flex_array_size(p, member, count))) +/** + * struct_size_t() - Calculate size of structure with trailing flexible array + * @type: structure type name. + * @member: Name of the array member. + * @count: Number of elements in the array. + * + * Calculates size of memory needed for structure @type followed by an + * array of @count number of @member elements. Prefer using struct_size() + * when possible instead, to keep calculations associated with a specific + * instance variable of type @type. + * + * Return: number of bytes needed or SIZE_MAX on overflow. + */ +#define struct_size_t(type, member, count) \ + struct_size((type *)NULL, member, count) + #endif /* __LINUX_OVERFLOW_H */ diff -Nru backport-iwlwifi-dkms-11289/include/linux/pci_ids.h backport-iwlwifi-dkms-11510/include/linux/pci_ids.h --- backport-iwlwifi-dkms-11289/include/linux/pci_ids.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/include/linux/pci_ids.h 2023-10-04 04:18:43.000000000 +0800 @@ -2,7 +2,7 @@ /* * PCI Class, Vendor and Device IDs * - * Please keep sorted. + * Please keep sorted by numeric Vendor ID and Device ID. * * Do not add new entries to this file unless the definitions * are shared between multiple drivers. @@ -151,6 +151,9 @@ #define PCI_CLASS_SP_DPIO 0x1100 #define PCI_CLASS_SP_OTHER 0x1180 +#define PCI_BASE_CLASS_ACCELERATOR 0x12 +#define PCI_CLASS_ACCELERATOR_PROCESSING 0x1200 + #define PCI_CLASS_OTHERS 0xff /* Vendors and devices. Sort key: vendor first, device next. */ @@ -158,6 +161,11 @@ #define PCI_VENDOR_ID_LOONGSON 0x0014 +#define PCI_DEVICE_ID_LOONGSON_HDA 0x7a07 +#define PCI_DEVICE_ID_LOONGSON_HDMI 0x7a37 + +#define PCI_VENDOR_ID_SOLIDIGM 0x025e + #define PCI_VENDOR_ID_TTTECH 0x0357 #define PCI_DEVICE_ID_TTTECH_MC322 0x000a @@ -567,6 +575,8 @@ #define PCI_DEVICE_ID_AMD_19H_M50H_DF_F3 0x166d #define PCI_DEVICE_ID_AMD_19H_M60H_DF_F3 0x14e3 #define PCI_DEVICE_ID_AMD_19H_M70H_DF_F3 0x14f3 +#define PCI_DEVICE_ID_AMD_19H_M78H_DF_F3 0x12fb +#define PCI_DEVICE_ID_AMD_MI200_DF_F3 0x14d3 #define PCI_DEVICE_ID_AMD_CNB17H_F3 0x1703 #define PCI_DEVICE_ID_AMD_LANCE 0x2000 #define PCI_DEVICE_ID_AMD_LANCE_HOME 0x2001 diff -Nru backport-iwlwifi-dkms-11289/include/net/cfg80211.h backport-iwlwifi-dkms-11510/include/net/cfg80211.h --- backport-iwlwifi-dkms-11289/include/net/cfg80211.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/include/net/cfg80211.h 2023-10-04 04:18:43.000000000 +0800 @@ -120,6 +120,7 @@ * This may be due to the driver or due to regulatory bandwidth * restrictions. * @IEEE80211_CHAN_NO_EHT: EHT operation is not permitted on this channel. + * @IEEE80211_CHAN_DFS_CONCURRENT: See %NL80211_RRF_DFS_CONCURRENT */ enum ieee80211_channel_flags { IEEE80211_CHAN_DISABLED = 1<<0, @@ -143,6 +144,7 @@ IEEE80211_CHAN_16MHZ = 1<<18, IEEE80211_CHAN_NO_320MHZ = 1<<19, IEEE80211_CHAN_NO_EHT = 1<<20, + IEEE80211_CHAN_DFS_CONCURRENT = 1<<21, }; #define IEEE80211_CHAN_NO_HT40 \ @@ -1760,6 +1762,7 @@ * @RATE_INFO_FLAGS_EDMG: 60GHz MCS in EDMG mode * @RATE_INFO_FLAGS_EXTENDED_SC_DMG: 60GHz extended SC MCS * @RATE_INFO_FLAGS_EHT_MCS: EHT MCS information + * @RATE_INFO_FLAGS_S1G_MCS: MCS field filled with S1G MCS */ enum rate_info_flags { RATE_INFO_FLAGS_MCS = BIT(0), @@ -1770,6 +1773,7 @@ RATE_INFO_FLAGS_EDMG = BIT(5), RATE_INFO_FLAGS_EXTENDED_SC_DMG = BIT(6), RATE_INFO_FLAGS_EHT_MCS = BIT(7), + RATE_INFO_FLAGS_S1G_MCS = BIT(8), }; /** @@ -1786,6 +1790,11 @@ * @RATE_INFO_BW_HE_RU: bandwidth determined by HE RU allocation * @RATE_INFO_BW_320: 320 MHz bandwidth * @RATE_INFO_BW_EHT_RU: bandwidth determined by EHT RU allocation + * @RATE_INFO_BW_1: 1 MHz bandwidth + * @RATE_INFO_BW_2: 2 MHz bandwidth + * @RATE_INFO_BW_4: 4 MHz bandwidth + * @RATE_INFO_BW_8: 8 MHz bandwidth + * @RATE_INFO_BW_16: 16 MHz bandwidth */ enum rate_info_bw { RATE_INFO_BW_20 = 0, @@ -1797,6 +1806,11 @@ RATE_INFO_BW_HE_RU, RATE_INFO_BW_320, RATE_INFO_BW_EHT_RU, + RATE_INFO_BW_1, + RATE_INFO_BW_2, + RATE_INFO_BW_4, + RATE_INFO_BW_8, + RATE_INFO_BW_16, }; /** @@ -1805,8 +1819,8 @@ * Information about a receiving or transmitting bitrate * * @flags: bitflag of flags from &enum rate_info_flags - * @mcs: mcs index if struct describes an HT/VHT/HE rate * @legacy: bitrate in 100kbit/s for 802.11abg + * @mcs: mcs index if struct describes an HT/VHT/HE/EHT/S1G rate * @nss: number of streams (VHT & HE only) * @bw: bandwidth (from &enum rate_info_bw) * @he_gi: HE guard interval (from &enum nl80211_he_gi) @@ -1819,9 +1833,9 @@ * only valid if bw is %RATE_INFO_BW_EHT_RU) */ struct rate_info { - u8 flags; - u8 mcs; + u16 flags; u16 legacy; + u8 mcs; u8 nss; u8 bw; u8 he_gi; @@ -2556,6 +2570,8 @@ * @n_6ghz_params: number of 6 GHz params * @scan_6ghz_params: 6 GHz params * @bssid: BSSID to scan for (most commonly, the wildcard BSSID) + * @tsf_report_link_id: for MLO, indicates the link ID of the BSS that should be + * used for TSF reporting. Can be set to -1 to indicate no preference. */ struct cfg80211_scan_request { struct cfg80211_ssid *ssids; @@ -2585,6 +2601,7 @@ bool scan_6ghz; u32 n_6ghz_params; struct cfg80211_scan_6ghz_params *scan_6ghz_params; + s8 tsf_report_link_id; /* keep last */ struct ieee80211_channel *channels[]; @@ -2610,7 +2627,7 @@ * or no match (RSSI only) * @rssi_thold: don't report scan results below this threshold (in s32 dBm) * @per_band_rssi_thold: Minimum rssi threshold for each band to be applied - * for filtering out scan results received. Drivers advertize this support + * for filtering out scan results received. Drivers advertise this support * of band specific rssi based filtering through the feature capability * %NL80211_EXT_FEATURE_SCHED_SCAN_BAND_SPECIFIC_RSSI_THOLD. These band * specific rssi thresholds take precedence over rssi_thold, if specified. @@ -2768,6 +2785,13 @@ * the BSS that requested the scan in which the beacon/probe was received. * @chains: bitmask for filled values in @chain_signal. * @chain_signal: per-chain signal strength of last received BSS in dBm. + * @restrict_use: restrict usage, if not set, assume @use_for is + * %NL80211_BSS_USE_FOR_NORMAL. + * @use_for: bitmap of possible usage for this BSS, see + * &enum nl80211_bss_use_for + * @cannot_use_reasons: the reasons (bitmap) for not being able to connect, + * if @restrict_use is set and @use_for is zero (empty); may be 0 for + * unspecified reasons; see &enum nl80211_bss_cannot_use_reasons * @drv_data: Data to be passed through to @inform_bss */ struct cfg80211_inform_bss { @@ -2780,6 +2804,9 @@ u8 chains; s8 chain_signal[IEEE80211_MAX_CHAINS]; + u8 restrict_use:1, use_for:7; + u8 cannot_use_reasons; + void *drv_data; }; @@ -2832,6 +2859,11 @@ * @chain_signal: per-chain signal strength of last received BSS in dBm. * @bssid_index: index in the multiple BSS set * @max_bssid_indicator: max number of members in the BSS set + * @use_for: bitmap of possible usage for this BSS, see + * &enum nl80211_bss_use_for + * @cannot_use_reasons: the reasons (bitmap) for not being able to connect, + * if @restrict_use is set and @use_for is zero (empty); may be 0 for + * unspecified reasons; see &enum nl80211_bss_cannot_use_reasons * @priv: private area for driver use, has at least wiphy->bss_priv_size bytes */ struct cfg80211_bss { @@ -2858,6 +2890,9 @@ u8 bssid_index; u8 max_bssid_indicator; + u8 use_for; + u8 cannot_use_reasons; + u8 priv[] __aligned(sizeof(void *)); }; @@ -2935,12 +2970,15 @@ * @elems_len: length of the elements * @disabled: If set this link should be included during association etc. but it * should not be used until enabled by the AP MLD. + * @error: per-link error code, must be <= 0. If there is an error, then the + * operation as a whole must fail. */ struct cfg80211_assoc_link { struct cfg80211_bss *bss; const u8 *elems; size_t elems_len; bool disabled; + int error; }; /** @@ -4861,6 +4899,8 @@ * @WIPHY_FLAG_SUPPORTS_EXT_KCK_32: The device supports 32-byte KCK keys. * @WIPHY_FLAG_NOTIFY_REGDOM_BY_DRIVER: The device could handle reg notify for * NL80211_REGDOM_SET_BY_DRIVER. + * @WIPHY_FLAG_SUPPORTS_NSTR_NONPRIMARY: support connection to non-primary link + * of an NSTR mobile AP MLD. */ enum wiphy_flags { WIPHY_FLAG_SUPPORTS_EXT_KEK_KCK = BIT(0), @@ -4874,7 +4914,7 @@ WIPHY_FLAG_IBSS_RSN = BIT(8), WIPHY_FLAG_MESH_AUTH = BIT(10), WIPHY_FLAG_SUPPORTS_EXT_KCK_32 = BIT(11), - /* use hole at 12 */ + WIPHY_FLAG_SUPPORTS_NSTR_NONPRIMARY = BIT(12), WIPHY_FLAG_SUPPORTS_FW_ROAM = BIT(13), WIPHY_FLAG_AP_UAPSD = BIT(14), WIPHY_FLAG_SUPPORTS_TDLS = BIT(15), @@ -5985,8 +6025,6 @@ * @mgmt_registrations: list of registrations for management frames * @mgmt_registrations_need_update: mgmt registrations were updated, * need to propagate the update to the driver - * @mtx: mutex used to lock data in this struct, may be used by drivers - * and some API functions require it held * @beacon_interval: beacon interval used on this device for transmitting * beacons, 0 when not valid * @address: The address for this device, valid only if @netdev is %NULL @@ -6032,8 +6070,6 @@ struct list_head mgmt_registrations; u8 mgmt_registrations_need_update:1; - struct mutex mtx; - bool use_4addr, is_running, registered, registering; u8 address[ETH_ALEN] __aligned(sizeof(u16)); @@ -6753,7 +6789,7 @@ * * @elem: the element to defragment * @ies: elements where @elem is contained - * @ies_len: length of @ies + * @ieslen: length of @ies * @data: buffer to store element data * @data_len: length of @data * @frag_id: the element ID of fragments @@ -7156,6 +7192,25 @@ } /** + * __cfg80211_get_bss - get a BSS reference + * @wiphy: the wiphy this BSS struct belongs to + * @channel: the channel to search on (or %NULL) + * @bssid: the desired BSSID (or %NULL) + * @ssid: the desired SSID (or %NULL) + * @ssid_len: length of the SSID (or 0) + * @bss_type: type of BSS, see &enum ieee80211_bss_type + * @privacy: privacy filter, see &enum ieee80211_privacy + * @use_for: indicates which use is intended + */ +struct cfg80211_bss *__cfg80211_get_bss(struct wiphy *wiphy, + struct ieee80211_channel *channel, + const u8 *bssid, + const u8 *ssid, size_t ssid_len, + enum ieee80211_bss_type bss_type, + enum ieee80211_privacy privacy, + u32 use_for); + +/** * cfg80211_get_bss - get a BSS reference * @wiphy: the wiphy this BSS struct belongs to * @channel: the channel to search on (or %NULL) @@ -7164,13 +7219,20 @@ * @ssid_len: length of the SSID (or 0) * @bss_type: type of BSS, see &enum ieee80211_bss_type * @privacy: privacy filter, see &enum ieee80211_privacy + * + * This version implies regular usage, %NL80211_BSS_USE_FOR_NORMAL. */ -struct cfg80211_bss *cfg80211_get_bss(struct wiphy *wiphy, - struct ieee80211_channel *channel, - const u8 *bssid, - const u8 *ssid, size_t ssid_len, - enum ieee80211_bss_type bss_type, - enum ieee80211_privacy privacy); +static inline struct cfg80211_bss * +cfg80211_get_bss(struct wiphy *wiphy, struct ieee80211_channel *channel, + const u8 *bssid, const u8 *ssid, size_t ssid_len, + enum ieee80211_bss_type bss_type, + enum ieee80211_privacy privacy) +{ + return __cfg80211_get_bss(wiphy, channel, bssid, ssid, ssid_len, + bss_type, privacy, + NL80211_BSS_USE_FOR_NORMAL); +} + static inline struct cfg80211_bss * cfg80211_get_ibss(struct wiphy *wiphy, struct ieee80211_channel *channel, @@ -8432,20 +8494,6 @@ void cfg80211_cqm_beacon_loss_notify(struct net_device *dev, gfp_t gfp); /** - * cfg80211_cqm_links_state_change_notify - inform CQM of change in AP MLD - * links - * - * @vif: &struct ieee80211_vif pointer from the add_interface callback. - * @removed_links: bitmap of links on which connection was removed due to links - * being removed by the AP MLD. - * - * Caller must acquire wdev_lock, therefore must only be called from sleepable - * driver context! - */ -void cfg80211_cqm_links_state_change_notify(struct net_device *dev, - u16 removed_links); - -/** * __cfg80211_radar_event - radar detection event * @wiphy: the wiphy * @chandef: chandef for the current channel @@ -8650,7 +8698,7 @@ * @link_id: the link ID for MLO, must be 0 for non-MLO * @punct_bitmap: the new puncturing bitmap * - * Caller must acquire wdev_lock, therefore must only be called from sleepable + * Caller must hold wiphy mutex, therefore must only be called from sleepable * driver context! */ void cfg80211_ch_switch_notify(struct net_device *dev, @@ -9303,4 +9351,28 @@ bool cfg80211_valid_disable_subchannel_bitmap(u16 *bitmap, const struct cfg80211_chan_def *chandef); +/** + * cfg80211_links_removed - Notify about removed STA MLD setup links. + * @dev: network device. + * @link_mask: BIT mask of removed STA MLD setup link IDs. + * + * Inform cfg80211 and the userspace about removed STA MLD setup links due to + * AP MLD removing the corresponding affiliated APs with Multi-Link + * reconfiguration. Note that it's not valid to remove all links, in this + * case disconnect instead. + * Also note that the wdev mutex must be held. + */ + +void cfg80211_links_removed(struct net_device *dev, u16 link_mask); + +/** + * cfg80211_schedule_channels_check - schedule regulatory check if needed + * @netdev: the device to check + * + * In case the device supports NO_IR or DFS relaxations, schedule regulatory + * channels check, as previous concurrent operation conditions may not + * hold anymore. + */ +void cfg80211_schedule_channels_check(struct net_device *netdev); + #endif /* __NET_CFG80211_H */ diff -Nru backport-iwlwifi-dkms-11289/include/net/codel.h backport-iwlwifi-dkms-11510/include/net/codel.h --- backport-iwlwifi-dkms-11289/include/net/codel.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/include/net/codel.h 2023-10-04 04:18:43.000000000 +0800 @@ -145,8 +145,8 @@ * @maxpacket: largest packet we've seen so far * @drop_count: temp count of dropped packets in dequeue() * @drop_len: bytes of dropped packets in dequeue() - * ecn_mark: number of packets we ECN marked instead of dropping - * ce_mark: number of packets CE marked because sojourn time was above ce_threshold + * @ecn_mark: number of packets we ECN marked instead of dropping + * @ce_mark: number of packets CE marked because sojourn time was above ce_threshold */ struct codel_stats { u32 maxpacket; diff -Nru backport-iwlwifi-dkms-11289/include/net/mac80211.h backport-iwlwifi-dkms-11510/include/net/mac80211.h --- backport-iwlwifi-dkms-11289/include/net/mac80211.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/include/net/mac80211.h 2023-10-04 04:18:43.000000000 +0800 @@ -341,6 +341,7 @@ * @BSS_CHANGED_UNSOL_BCAST_PROBE_RESP: Unsolicited broadcast probe response * status changed. * @BSS_CHANGED_EHT_PUNCTURING: The channel puncturing bitmap changed. + * @BSS_CHANGED_MLD_VALID_LINKS: MLD valid links status changed. */ enum ieee80211_bss_change { BSS_CHANGED_ASSOC = 1<<0, @@ -376,6 +377,7 @@ BSS_CHANGED_FILS_DISCOVERY = 1<<30, BSS_CHANGED_UNSOL_BCAST_PROBE_RESP = 1<<31, BSS_CHANGED_EHT_PUNCTURING = BIT_ULL(32), + BSS_CHANGED_MLD_VALID_LINKS = BIT_ULL(33), /* when adding here, make sure to change ieee80211_reconfig */ }; @@ -643,9 +645,7 @@ * @pwr_reduction: power constraint of BSS. * @eht_support: does this BSS support EHT * @eht_puncturing: bitmap to indicate which channels are punctured in this BSS - * @csa_active: marks whether a channel switch is going on. Internally it is - * write-protected by sdata_lock and local->mtx so holding either is fine - * for read access. + * @csa_active: marks whether a channel switch is going on. * @csa_punct_bitmap: new puncturing bitmap for channel switch * @mu_mimo_owner: indicates interface owns MU-MIMO capability * @chanctx_conf: The channel context this interface is assigned to, or %NULL @@ -653,9 +653,7 @@ * path needing to access it; even though the netdev carrier will always * be off when it is %NULL there can still be races and packets could be * processed after it switches back to %NULL. - * @color_change_active: marks whether a color change is ongoing. Internally it is - * write-protected by sdata_lock and local->mtx so holding either is fine - * for read access. + * @color_change_active: marks whether a color change is ongoing. * @color_change_color: the bss color that will be used after the change. * @ht_ldpc: in AP mode, indicates interface has HT LDPC capability. * @vht_ldpc: in AP mode, indicates interface has VHT LDPC capability. @@ -1115,7 +1113,9 @@ * not valid if the interface is an MLD since we won't know which * link the frame will be transmitted on * @hw_queue: HW queue to put the frame on, skb_get_queue_mapping() gives the AC - * @ack_frame_id: internal frame ID for TX status, used internally + * @status_data: internal data for TX status handling, assigned privately, + * see also &enum ieee80211_status_data for the internal documentation + * @status_data_idr: indicates status data is IDR allocated ID for ack frame * @tx_time_est: TX time estimate in units of 4us, used internally * @control: union part for control data * @control.rates: TX rates array to try @@ -1155,10 +1155,11 @@ /* common information */ u32 flags; u32 band:3, - ack_frame_id:13, + status_data_idr:1, + status_data:13, hw_queue:4, tx_time_est:10; - /* 2 free bits */ + /* 1 free bit */ union { struct { @@ -1768,8 +1769,8 @@ * @IEEE80211_VIF_GET_NOA_UPDATE: request to handle NOA attributes * and send P2P_PS notification to the driver if NOA changed, even * this is not pure P2P vif. - * @IEEE80211_VIF_DISABLE_SMPS_OVERRIDE: disable user configuration of - * SMPS mode via debugfs. + * @IEEE80211_VIF_EML_ACTIVE: The driver indicates that EML operation is + * enabled for the interface. * @IEEE80211_VIF_DISABLE_EML: disable EML in EHT */ enum ieee80211_vif_flags { @@ -1777,7 +1778,7 @@ IEEE80211_VIF_SUPPORTS_CQM_RSSI = BIT(1), IEEE80211_VIF_SUPPORTS_UAPSD = BIT(2), IEEE80211_VIF_GET_NOA_UPDATE = BIT(3), - IEEE80211_VIF_DISABLE_SMPS_OVERRIDE = BIT(4), + IEEE80211_VIF_EML_ACTIVE = BIT(4), IEEE80211_VIF_DISABLE_EML = BIT(5), }; @@ -1983,22 +1984,18 @@ */ struct wireless_dev *ieee80211_vif_to_wdev(struct ieee80211_vif *vif); -/** - * lockdep_vif_mutex_held - for lockdep checks on link poiners - * @vif: the interface to check - */ -static inline bool lockdep_vif_mutex_held(struct ieee80211_vif *vif) +static inline bool lockdep_vif_wiphy_mutex_held(struct ieee80211_vif *vif) { - return lockdep_is_held(&ieee80211_vif_to_wdev(vif)->mtx); + return lockdep_is_held(&ieee80211_vif_to_wdev(vif)->wiphy->mtx); } #define link_conf_dereference_protected(vif, link_id) \ rcu_dereference_protected((vif)->link_conf[link_id], \ - lockdep_vif_mutex_held(vif)) + lockdep_vif_wiphy_mutex_held(vif)) #define link_conf_dereference_check(vif, link_id) \ rcu_dereference_check((vif)->link_conf[link_id], \ - lockdep_vif_mutex_held(vif)) + lockdep_vif_wiphy_mutex_held(vif)) /** * enum ieee80211_key_flags - key flags @@ -3646,11 +3643,14 @@ * @success: whether the frame exchange was successful, only * used with the mgd_complete_tx() method, and then only * valid for auth and (re)assoc. + * @link_id: the link id on which the frame will be TX'ed. + * Only used with the mgd_prepare_tx() method. */ struct ieee80211_prep_tx_info { u16 duration; u16 subtype; u8 success:1; + int link_id; }; /** @@ -3874,20 +3874,24 @@ * the station. See @sta_pre_rcu_remove if needed. * This callback can sleep. * + * @vif_add_debugfs: Drivers can use this callback to add a debugfs vif + * directory with its files. This callback should be within a + * CONFIG_MAC80211_DEBUGFS conditional. This callback can sleep. + * * @link_add_debugfs: Drivers can use this callback to add debugfs files * when a link is added to a mac80211 vif. This callback should be within - * a CPTCFG_MAC80211_DEBUGFS conditional. This callback can sleep. + * a CONFIG_MAC80211_DEBUGFS conditional. This callback can sleep. * For non-MLO the callback will be called once for the default bss_conf * with the vif's directory rather than a separate subdirectory. * * @sta_add_debugfs: Drivers can use this callback to add debugfs files * when a station is added to mac80211's station list. This callback - * should be within a CPTCFG_MAC80211_DEBUGFS conditional. This + * should be within a CONFIG_MAC80211_DEBUGFS conditional. This * callback can sleep. * * @link_sta_add_debugfs: Drivers can use this callback to add debugfs files * when a link is added to a mac80211 station. This callback - * should be within a CPTCFG_MAC80211_DEBUGFS conditional. This + * should be within a CONFIG_MAC80211_DEBUGFS conditional. This * callback can sleep. * For non-MLO the callback will be called once for the deflink with the * station's directory rather than a separate subdirectory. @@ -4369,6 +4373,8 @@ int (*sta_remove)(struct ieee80211_hw *hw, struct ieee80211_vif *vif, struct ieee80211_sta *sta); #ifdef CPTCFG_MAC80211_DEBUGFS + void (*vif_add_debugfs)(struct ieee80211_hw *hw, + struct ieee80211_vif *vif); void (*link_add_debugfs)(struct ieee80211_hw *hw, struct ieee80211_vif *vif, struct ieee80211_bss_conf *link_conf, @@ -4517,7 +4523,8 @@ struct ieee80211_prep_tx_info *info); void (*mgd_protect_tdls_discover)(struct ieee80211_hw *hw, - struct ieee80211_vif *vif); + struct ieee80211_vif *vif, + unsigned int link_id); int (*add_chanctx)(struct ieee80211_hw *hw, struct ieee80211_chanctx_conf *ctx); diff -Nru backport-iwlwifi-dkms-11289/include/net/regulatory.h backport-iwlwifi-dkms-11510/include/net/regulatory.h --- backport-iwlwifi-dkms-11289/include/net/regulatory.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/include/net/regulatory.h 2023-10-04 04:18:43.000000000 +0800 @@ -143,17 +143,6 @@ * otherwise initiating radiation is not allowed. This will enable the * relaxations enabled under the CFG80211_REG_RELAX_NO_IR configuration * option - * @REGULATORY_IGNORE_STALE_KICKOFF: the regulatory core will _not_ make sure - * all interfaces on this wiphy reside on allowed channels. If this flag - * is not set, upon a regdomain change, the interfaces are given a grace - * period (currently 60 seconds) to disconnect or move to an allowed - * channel. Interfaces on forbidden channels are forcibly disconnected. - * Currently these types of interfaces are supported for enforcement: - * NL80211_IFTYPE_ADHOC, NL80211_IFTYPE_STATION, NL80211_IFTYPE_AP, - * NL80211_IFTYPE_AP_VLAN, NL80211_IFTYPE_MONITOR, - * NL80211_IFTYPE_P2P_CLIENT, NL80211_IFTYPE_P2P_GO, - * NL80211_IFTYPE_P2P_DEVICE. The flag will be set by default if a device - * includes any modes unsupported for enforcement checking. * @REGULATORY_WIPHY_SELF_MANAGED: for devices that employ wiphy-specific * regdom management. These devices will ignore all regdom changes not * originating from their own wiphy. @@ -180,7 +169,7 @@ REGULATORY_COUNTRY_IE_FOLLOW_POWER = BIT(3), REGULATORY_COUNTRY_IE_IGNORE = BIT(4), REGULATORY_ENABLE_RELAX_NO_IR = BIT(5), - REGULATORY_IGNORE_STALE_KICKOFF = BIT(6), + /* reuse bit 6 next time */ REGULATORY_WIPHY_SELF_MANAGED = BIT(7), }; diff -Nru backport-iwlwifi-dkms-11289/include/uapi/linux/nl80211.h backport-iwlwifi-dkms-11510/include/uapi/linux/nl80211.h --- backport-iwlwifi-dkms-11289/include/uapi/linux/nl80211.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/include/uapi/linux/nl80211.h 2023-10-04 04:18:43.000000000 +0800 @@ -1309,6 +1309,11 @@ * The number of peers that HW timestamping can be enabled for concurrently * is indicated by %NL80211_ATTR_MAX_HW_TIMESTAMP_PEERS. * + * @NL80211_CMD_LINKS_REMOVED: Notify userspace about the removal of STA MLD + * setup links due to AP MLD removing the corresponding affiliated APs with + * Multi-Link reconfiguration. %NL80211_ATTR_MLO_LINKS is used to provide + * information about the removed STA MLD setup links. + * * @NL80211_CMD_MAX: highest used command number * @__NL80211_CMD_AFTER_LAST: internal use */ @@ -1556,12 +1561,14 @@ NL80211_CMD_ADD_LINK, NL80211_CMD_REMOVE_LINK, - NL80211_CMD_SET_HW_TIMESTAMP, - NL80211_CMD_ADD_LINK_STA, NL80211_CMD_MODIFY_LINK_STA, NL80211_CMD_REMOVE_LINK_STA, + NL80211_CMD_SET_HW_TIMESTAMP, + + NL80211_CMD_LINKS_REMOVED, + /* let this always be before all commands we haven't upstreamed yet */ __NL80211_CMD_NONUPSTREAM_START, @@ -2756,19 +2763,6 @@ * @NL80211_ATTR_MLD_ADDR: An MLD address, used with various commands such as * authenticate/associate. * - * @NL80211_ATTR_TX_HW_TIMESTAMP: Hardware timestamp for TX operation in - * nanoseconds (u64). This is the device clock timestamp so it will - * probably reset when the device is stopped or the firmware is reset. - * When used with %NL80211_CMD_FRAME_TX_STATUS, indicates the frame TX - * timestamp. When used with %NL80211_CMD_FRAME RX notification, indicates - * the ack TX timestamp. - * @NL80211_ATTR_RX_HW_TIMESTAMP: Hardware timestamp for RX operation in - * nanoseconds (u64). This is the device clock timestamp so it will - * probably reset when the device is stopped or the firmware is reset. - * When used with %NL80211_CMD_FRAME_TX_STATUS, indicates the ack RX - * timestamp. When used with %NL80211_CMD_FRAME RX notification, indicates - * the incoming frame RX timestamp. - * * @NL80211_ATTR_MLO_SUPPORT: Flag attribute to indicate user space supports MLO * connection. Used with %NL80211_CMD_CONNECT. If this attribute is not * included in NL80211_CMD_CONNECT drivers must not perform MLO connection. @@ -2783,9 +2777,18 @@ * @NL80211_ATTR_EML_CAPABILITY: EML Capability information (u16) * @NL80211_ATTR_MLD_CAPA_AND_OPS: MLD Capabilities and Operations (u16) * - * @NL80211_ATTR_MLO_LINK_DISABLED: Flag attribute indicating that the link is - * disabled. - * + * @NL80211_ATTR_TX_HW_TIMESTAMP: Hardware timestamp for TX operation in + * nanoseconds (u64). This is the device clock timestamp so it will + * probably reset when the device is stopped or the firmware is reset. + * When used with %NL80211_CMD_FRAME_TX_STATUS, indicates the frame TX + * timestamp. When used with %NL80211_CMD_FRAME RX notification, indicates + * the ack TX timestamp. + * @NL80211_ATTR_RX_HW_TIMESTAMP: Hardware timestamp for RX operation in + * nanoseconds (u64). This is the device clock timestamp so it will + * probably reset when the device is stopped or the firmware is reset. + * When used with %NL80211_CMD_FRAME_TX_STATUS, indicates the ack RX + * timestamp. When used with %NL80211_CMD_FRAME RX notification, indicates + * the incoming frame RX timestamp. * @NL80211_ATTR_TD_BITMAP: Transition Disable bitmap, for subsequent * (re)associations. * @@ -2812,6 +2815,13 @@ * index. If the userspace includes more RNR elements than number of * MBSSID elements then these will be added in every EMA beacon. * + * @NL80211_ATTR_MLO_LINK_DISABLED: Flag attribute indicating that the link is + * disabled. + * + * @NL80211_ATTR_BSS_DUMP_INCLUDE_USE_DATA: Include BSS usage data, i.e. + * include BSSes that can only be used in restricted scenarios and/or + * cannot be used at all. + * * @NUM_NL80211_ATTR: total number of nl80211_attrs available * @NL80211_ATTR_MAX: highest attribute number currently defined * @__NL80211_ATTR_AFTER_LAST: internal use @@ -3326,16 +3336,10 @@ NL80211_ATTR_DISABLE_EHT, - NL80211_ATTR_TX_HW_TIMESTAMP, - NL80211_ATTR_RX_HW_TIMESTAMP, - NL80211_ATTR_MLO_LINKS, NL80211_ATTR_MLO_LINK_ID, NL80211_ATTR_MLD_ADDR, - NL80211_ATTR_MAX_HW_TIMESTAMP_PEERS, - NL80211_ATTR_HW_TIMESTAMP_ENABLED, - NL80211_ATTR_MLO_SUPPORT, NL80211_ATTR_MAX_NUM_AKM_SUITES, @@ -3343,14 +3347,21 @@ NL80211_ATTR_EML_CAPABILITY, NL80211_ATTR_MLD_CAPA_AND_OPS, - NL80211_ATTR_MLO_LINK_DISABLED, - + NL80211_ATTR_TX_HW_TIMESTAMP, + NL80211_ATTR_RX_HW_TIMESTAMP, NL80211_ATTR_TD_BITMAP, NL80211_ATTR_PUNCT_BITMAP, + NL80211_ATTR_MAX_HW_TIMESTAMP_PEERS, + NL80211_ATTR_HW_TIMESTAMP_ENABLED, + NL80211_ATTR_EMA_RNR_ELEMS, + NL80211_ATTR_MLO_LINK_DISABLED, + + NL80211_ATTR_BSS_DUMP_INCLUDE_USE_DATA, + /* add attributes here, update the policy in nl80211.c */ __NL80211_ATTR_AFTER_LAST, @@ -3677,6 +3688,13 @@ * (u8, see &enum nl80211_eht_gi) * @NL80211_RATE_INFO_EHT_RU_ALLOC: EHT RU allocation, if not present then * non-OFDMA was used (u8, see &enum nl80211_eht_ru_alloc) + * @NL80211_RATE_INFO_S1G_MCS: S1G MCS index (u8, 0-10) + * @NL80211_RATE_INFO_S1G_NSS: S1G NSS value (u8, 1-4) + * @NL80211_RATE_INFO_1_MHZ_WIDTH: 1 MHz S1G rate + * @NL80211_RATE_INFO_2_MHZ_WIDTH: 2 MHz S1G rate + * @NL80211_RATE_INFO_4_MHZ_WIDTH: 4 MHz S1G rate + * @NL80211_RATE_INFO_8_MHZ_WIDTH: 8 MHz S1G rate + * @NL80211_RATE_INFO_16_MHZ_WIDTH: 16 MHz S1G rate * @__NL80211_RATE_INFO_AFTER_LAST: internal use */ enum nl80211_rate_info { @@ -3703,6 +3721,13 @@ NL80211_RATE_INFO_EHT_NSS, NL80211_RATE_INFO_EHT_GI, NL80211_RATE_INFO_EHT_RU_ALLOC, + NL80211_RATE_INFO_S1G_MCS, + NL80211_RATE_INFO_S1G_NSS, + NL80211_RATE_INFO_1_MHZ_WIDTH, + NL80211_RATE_INFO_2_MHZ_WIDTH, + NL80211_RATE_INFO_4_MHZ_WIDTH, + NL80211_RATE_INFO_8_MHZ_WIDTH, + NL80211_RATE_INFO_16_MHZ_WIDTH, /* keep last */ __NL80211_RATE_INFO_AFTER_LAST, @@ -4197,6 +4222,10 @@ * as the primary or any of the secondary channels isn't possible * @NL80211_FREQUENCY_ATTR_NO_EHT: EHT operation is not allowed on this channel * in current regulatory domain. + * @NL80211_FREQUENCY_ATTR_DFS_CONCURRENT: Operation on this channel is + * allowed for peer-to-peer or adhoc communication under the control + * of a DFS master which operates on the same channel (FCC-594280 D01 + * Section B.3). Should be used together with %NL80211_RRF_DFS only. * @NL80211_FREQUENCY_ATTR_MAX: highest frequency attribute number * currently defined * @__NL80211_FREQUENCY_ATTR_AFTER_LAST: internal use @@ -4235,6 +4264,7 @@ NL80211_FREQUENCY_ATTR_16MHZ, NL80211_FREQUENCY_ATTR_NO_320MHZ, NL80211_FREQUENCY_ATTR_NO_EHT, + NL80211_FREQUENCY_ATTR_DFS_CONCURRENT, /* keep last */ __NL80211_FREQUENCY_ATTR_AFTER_LAST, @@ -4435,6 +4465,10 @@ * @NL80211_RRF_NO_HE: HE operation not allowed * @NL80211_RRF_NO_320MHZ: 320MHz operation not allowed * @NL80211_RRF_NO_EHT: EHT operation not allowed + * @NL80211_RRF_DFS_CONCURRENT: Operation on this channel is allowed for + peer-to-peer or adhoc communication under the control of a DFS master + which operates on the same channel (FCC-594280 D01 Section B.3). + Should be used together with %NL80211_RRF_DFS only. */ enum nl80211_reg_rule_flags { NL80211_RRF_NO_OFDM = 1<<0, @@ -4455,6 +4489,7 @@ NL80211_RRF_NO_HE = 1<<17, NL80211_RRF_NO_320MHZ = 1<<18, NL80211_RRF_NO_EHT = 1<<19, + NL80211_RRF_DFS_CONCURRENT = 1<<20, }; #define NL80211_RRF_PASSIVE_SCAN NL80211_RRF_NO_IR @@ -4992,6 +5027,30 @@ }; /** + * enum nl80211_bss_use_for - bitmap indicating possible BSS use + * @NL80211_BSS_USE_FOR_NORMAL: Use this BSS for normal "connection", + * including IBSS/MBSS depending on the type. + * @NL80211_BSS_USE_FOR_MLD_LINK: This BSS can be used as a link in an + * MLO connection. Note that for an MLO connection, all links including + * the assoc link must have this flag set, and the assoc link must + * additionally have %NL80211_BSS_USE_FOR_NORMAL set. + */ +enum nl80211_bss_use_for { + NL80211_BSS_USE_FOR_NORMAL = 1 << 0, + NL80211_BSS_USE_FOR_MLD_LINK = 1 << 1, +}; + +/** + * enum nl80211_bss_cannot_use_reasons - reason(s) connection to a + * BSS isn't possible + * @NL80211_BSS_CANNOT_USE_NSTR_NONPRIMARY: NSTR nonprimary links aren't + * supported by the device, and this BSS entry represents one. + */ +enum nl80211_bss_cannot_use_reasons { + NL80211_BSS_CANNOT_USE_NSTR_NONPRIMARY = 1 << 0, +}; + +/** * enum nl80211_bss - netlink attributes for a BSS * * @__NL80211_BSS_INVALID: invalid @@ -5043,6 +5102,14 @@ * @NL80211_BSS_FREQUENCY_OFFSET: frequency offset in KHz * @NL80211_BSS_MLO_LINK_ID: MLO link ID of the BSS (u8). * @NL80211_BSS_MLD_ADDR: MLD address of this BSS if connected to it. + * @NL80211_BSS_USE_FOR: u32 bitmap attribute indicating what the BSS can be + * used for, see &enum nl80211_bss_use_for. + * @NL80211_BSS_CANNOT_USE_REASONS: Indicates the reason that this BSS cannot + * be used for all or some of the possible uses by the device reporting it, + * even though its presence was detected. + * This is a u64 attribute containing a bitmap of values from + * &enum nl80211_cannot_use_reasons, note that the attribute may be missing + * if no reasons are specified. * @__NL80211_BSS_AFTER_LAST: internal * @NL80211_BSS_MAX: highest BSS attribute */ @@ -5070,6 +5137,8 @@ NL80211_BSS_FREQUENCY_OFFSET, NL80211_BSS_MLO_LINK_ID, NL80211_BSS_MLD_ADDR, + NL80211_BSS_USE_FOR, + NL80211_BSS_CANNOT_USE_REASONS, /* keep last */ __NL80211_BSS_AFTER_LAST, @@ -5343,8 +5412,6 @@ * loss event * @NL80211_ATTR_CQM_RSSI_LEVEL: the RSSI value in dBm that triggered the * RSSI threshold event. - * @NL80211_ATTR_CQM_REMOVED_LINKS: bitmap of links on which connection was - * removed due to links being removed by the AP MLD. * @__NL80211_ATTR_CQM_AFTER_LAST: internal * @NL80211_ATTR_CQM_MAX: highest key attribute */ @@ -5359,7 +5426,6 @@ NL80211_ATTR_CQM_TXE_INTVL, NL80211_ATTR_CQM_BEACON_LOSS_EVENT, NL80211_ATTR_CQM_RSSI_LEVEL, - NL80211_ATTR_CQM_REMOVED_LINKS, /* keep last */ __NL80211_ATTR_CQM_AFTER_LAST, @@ -6208,9 +6274,11 @@ * the BSS that the interface that requested the scan is connected to * (if available). * @NL80211_EXT_FEATURE_BSS_PARENT_TSF: Per BSS, this driver reports the - * time the last beacon/probe was received. The time is the TSF of the - * BSS that the interface that requested the scan is connected to - * (if available). + * time the last beacon/probe was received. For a non MLO connection, the + * time is the TSF of the BSS that the interface that requested the scan is + * connected to (if available). For an MLO connection, the time is the TSF + * of the BSS corresponding with link ID specified in the scan request (if + * specified). * @NL80211_EXT_FEATURE_SET_SCAN_DWELL: This driver supports configuration of * channel dwell time. * @NL80211_EXT_FEATURE_BEACON_RATE_LEGACY: Driver supports beacon rate @@ -6386,7 +6454,11 @@ * @NL80211_EXT_FEATURE_AUTH_AND_DEAUTH_RANDOM_TA: Device supports randomized TA * in authentication and deauthentication frames sent to unassociated peer * using @NL80211_CMD_FRAME. - * + * @NL80211_EXT_FEATURE_DFS_CONCURRENT: The device supports peer-to-peer or + * ad hoc operation on DFS channels under the control of a concurrent + * DFS master on the same channel as described in FCC-594280 D01 + * (Section B.3). This, for example, allows P2P GO and P2P clients to + * operate on DFS channels as long as there's a concurrent BSS connection. * @NUM_NL80211_EXT_FEATURES: number of extended features. * @MAX_NL80211_EXT_FEATURES: highest extended feature index. */ @@ -6458,6 +6530,7 @@ NL80211_EXT_FEATURE_PUNCT, NL80211_EXT_FEATURE_SECURE_NAN, NL80211_EXT_FEATURE_AUTH_AND_DEAUTH_RANDOM_TA, + NL80211_EXT_FEATURE_DFS_CONCURRENT, /* add new features before the definition below */ NUM_NL80211_EXT_FEATURES, diff -Nru backport-iwlwifi-dkms-11289/include/uapi/linux/pci_regs.h backport-iwlwifi-dkms-11510/include/uapi/linux/pci_regs.h --- backport-iwlwifi-dkms-11289/include/uapi/linux/pci_regs.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/include/uapi/linux/pci_regs.h 2023-10-04 04:18:43.000000000 +0800 @@ -738,6 +738,7 @@ #define PCI_EXT_CAP_ID_DVSEC 0x23 /* Designated Vendor-Specific */ #define PCI_EXT_CAP_ID_DLF 0x25 /* Data Link Feature */ #define PCI_EXT_CAP_ID_PL_16GT 0x26 /* Physical Layer 16.0 GT/s */ +#define PCI_EXT_CAP_ID_PL_32GT 0x2A /* Physical Layer 32.0 GT/s */ #define PCI_EXT_CAP_ID_DOE 0x2E /* Data Object Exchange */ #define PCI_EXT_CAP_ID_MAX PCI_EXT_CAP_ID_DOE diff -Nru backport-iwlwifi-dkms-11289/MAINTAINERS backport-iwlwifi-dkms-11510/MAINTAINERS --- backport-iwlwifi-dkms-11289/MAINTAINERS 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/MAINTAINERS 2023-10-04 04:18:43.000000000 +0800 @@ -1,81 +1,5 @@ -List of maintainers and how to submit kernel changes -==================================================== - -Please try to follow the guidelines below. This will make things -easier on the maintainers. Not all of these guidelines matter for every -trivial patch so apply some common sense. - -Tips for patch submitters -------------------------- - -1. Always *test* your changes, however small, on at least 4 or - 5 people, preferably many more. - -2. Try to release a few ALPHA test versions to the net. Announce - them onto the kernel channel and await results. This is especially - important for device drivers, because often that's the only way - you will find things like the fact version 3 firmware needs - a magic fix you didn't know about, or some clown changed the - chips on a board and not its name. (Don't laugh! Look at the - SMC etherpower for that.) - -3. Make sure your changes compile correctly in multiple - configurations. In particular check that changes work both as a - module and built into the kernel. - -4. When you are happy with a change make it generally available for - testing and await feedback. - -5. Make a patch available to the relevant maintainer in the list. Use - ``diff -u`` to make the patch easy to merge. Be prepared to get your - changes sent back with seemingly silly requests about formatting - and variable names. These aren't as silly as they seem. One - job the maintainers (and especially Linus) do is to keep things - looking the same. Sometimes this means that the clever hack in - your driver to get around a problem actually needs to become a - generalized kernel feature ready for next time. - - PLEASE check your patch with the automated style checker - (scripts/checkpatch.pl) to catch trivial style violations. - See Documentation/process/coding-style.rst for guidance here. - - PLEASE CC: the maintainers and mailing lists that are generated - by ``scripts/get_maintainer.pl.`` The results returned by the - script will be best if you have git installed and are making - your changes in a branch derived from Linus' latest git tree. - See Documentation/process/submitting-patches.rst for details. - - PLEASE try to include any credit lines you want added with the - patch. It avoids people being missed off by mistake and makes - it easier to know who wants adding and who doesn't. - - PLEASE document known bugs. If it doesn't work for everything - or does something very odd once a month document it. - - PLEASE remember that submissions must be made under the terms - of the Linux Foundation certificate of contribution and should - include a Signed-off-by: line. The current version of this - "Developer's Certificate of Origin" (DCO) is listed in the file - Documentation/process/submitting-patches.rst. - -6. Make sure you have the right to send any changes you make. If you - do changes at work you may find your employer owns the patch - not you. - -7. When sending security related changes or reports to a maintainer - please Cc: security@kernel.org, especially if the maintainer - does not respond. Please keep in mind that the security team is - a small set of people who can be efficient only when working on - verified bugs. Please only Cc: this list when you have identified - that the bug would present a short-term risk to other users if it - were publicly disclosed. For example, reports of address leaks do - not represent an immediate threat and are better handled publicly, - and ideally, should come with a patch proposal. Please do not send - automated reports to this list either. Such bugs will be handled - better and faster in the usual public places. See - Documentation/process/security-bugs.rst for details. - -8. Happy hacking. +List of maintainers +=================== Descriptions of section entries and preferred order --------------------------------------------------- @@ -273,8 +197,8 @@ L: linux-api@vger.kernel.org F: include/linux/syscalls.h F: kernel/sys_ni.c -X: include/uapi/ X: arch/*/include/uapi/ +X: include/uapi/ ABIT UGURU 1,2 HARDWARE MONITOR DRIVER M: Hans de Goede @@ -406,11 +330,12 @@ S: Maintained F: drivers/acpi/arm64 -ACPI SERIAL MULTI INSTANTIATE DRIVER -M: Hans de Goede -L: platform-driver-x86@vger.kernel.org +ACPI FOR RISC-V (ACPI/riscv) +M: Sunil V L +L: linux-acpi@vger.kernel.org +L: linux-riscv@lists.infradead.org S: Maintained -F: drivers/platform/x86/serial-multi-instantiate.c +F: drivers/acpi/riscv/ ACPI PCC(Platform Communication Channel) MAILBOX DRIVER M: Sudeep Holla @@ -430,6 +355,12 @@ T: git git://git.kernel.org/pub/scm/linux/kernel/git/rafael/linux-pm F: drivers/acpi/pmic/ +ACPI SERIAL MULTI INSTANTIATE DRIVER +M: Hans de Goede +L: platform-driver-x86@vger.kernel.org +S: Maintained +F: drivers/platform/x86/serial-multi-instantiate.c + ACPI THERMAL DRIVER M: Rafael J. Wysocki R: Zhang Rui @@ -449,6 +380,8 @@ ACPI WMI DRIVER L: platform-driver-x86@vger.kernel.org S: Orphan +F: Documentation/driver-api/wmi.rst +F: Documentation/wmi/ F: drivers/platform/x86/wmi.c F: include/uapi/linux/wmi.h @@ -823,6 +756,13 @@ S: Maintained F: drivers/crypto/allwinner/ +ALLWINNER DMIC DRIVERS +M: Ban Tao +L: alsa-devel@alsa-project.org (moderated for non-subscribers) +S: Maintained +F: Documentation/devicetree/bindings/sound/allwinner,sun50i-h6-dmic.yaml +F: sound/soc/sunxi/sun50i-dmic.c + ALLWINNER HARDWARE SPINLOCK SUPPORT M: Wilken Gottwalt S: Maintained @@ -844,13 +784,6 @@ S: Maintained F: drivers/staging/media/sunxi/cedrus/ -ALLWINNER DMIC DRIVERS -M: Ban Tao -L: alsa-devel@alsa-project.org (moderated for non-subscribers) -S: Maintained -F: Documentation/devicetree/bindings/sound/allwinner,sun50i-h6-dmic.yaml -F: sound/soc/sunxi/sun50i-dmic.c - ALPHA PORT M: Richard Henderson M: Ivan Kokshaysky @@ -909,13 +842,6 @@ S: Maintained F: drivers/net/ethernet/altera/ -ALTERA TSE PCS -M: Maxime Chevallier -L: netdev@vger.kernel.org -S: Supported -F: drivers/net/pcs/pcs-altera-tse.c -F: include/linux/pcs-altera-tse.h - ALTERA UART/JTAG UART SERIAL DRIVERS M: Tobias Klauser L: linux-serial@vger.kernel.org @@ -956,7 +882,8 @@ F: drivers/net/ethernet/amazon/ AMAZON RDMA EFA DRIVER -M: Gal Pressman +M: Michael Margolin +R: Gal Pressman R: Yossi Leybovich L: linux-rdma@vger.kernel.org S: Supported @@ -1026,6 +953,16 @@ F: drivers/crypto/geode* F: drivers/video/fbdev/geode/ +AMD HSMP DRIVER +M: Naveen Krishna Chatradhi +R: Carlos Bilbao +L: platform-driver-x86@vger.kernel.org +S: Maintained +F: Documentation/arch/x86/amd_hsmp.rst +F: arch/x86/include/asm/amd_hsmp.h +F: arch/x86/include/uapi/asm/amd_hsmp.h +F: drivers/platform/x86/amd/hsmp.c + AMD IOMMU (AMD-VI) M: Joerg Roedel R: Suravee Suthikulpanit @@ -1049,6 +986,13 @@ F: include/uapi/linux/kfd_ioctl.h F: include/uapi/linux/kfd_sysfs.h +AMD MP2 I2C DRIVER +M: Elie Morisse +M: Shyam Sundar S K +L: linux-i2c@vger.kernel.org +S: Maintained +F: drivers/i2c/busses/i2c-amd-mp2* + AMD PDS CORE DRIVER M: Shannon Nelson M: Brett Creeley @@ -1058,18 +1002,6 @@ F: drivers/net/ethernet/amd/pds_core/ F: include/linux/pds/ -AMD SPI DRIVER -M: Sanjay R Mehta -S: Maintained -F: drivers/spi/spi-amd.c - -AMD MP2 I2C DRIVER -M: Elie Morisse -M: Shyam Sundar S K -L: linux-i2c@vger.kernel.org -S: Maintained -F: drivers/i2c/busses/i2c-amd-mp2* - AMD PMC DRIVER M: Shyam Sundar S K L: platform-driver-x86@vger.kernel.org @@ -1083,16 +1015,6 @@ F: Documentation/ABI/testing/sysfs-amd-pmf F: drivers/platform/x86/amd/pmf/ -AMD HSMP DRIVER -M: Naveen Krishna Chatradhi -R: Carlos Bilbao -L: platform-driver-x86@vger.kernel.org -S: Maintained -F: Documentation/arch/x86/amd_hsmp.rst -F: arch/x86/include/asm/amd_hsmp.h -F: arch/x86/include/uapi/asm/amd_hsmp.h -F: drivers/platform/x86/amd/hsmp.c - AMD POWERPLAY AND SWSMU M: Evan Quan L: amd-gfx@lists.freedesktop.org @@ -1121,13 +1043,6 @@ S: Supported F: arch/arm64/boot/dts/amd/ -AMD XGBE DRIVER -M: "Shyam Sundar S K" -L: netdev@vger.kernel.org -S: Supported -F: arch/arm64/boot/dts/amd/amd-seattle-xgbe*.dtsi -F: drivers/net/ethernet/amd/xgbe/ - AMD SENSOR FUSION HUB DRIVER M: Basavaraj Natikar L: linux-input@vger.kernel.org @@ -1135,6 +1050,18 @@ F: Documentation/hid/amd-sfh* F: drivers/hid/amd-sfh-hid/ +AMD SPI DRIVER +M: Sanjay R Mehta +S: Maintained +F: drivers/spi/spi-amd.c + +AMD XGBE DRIVER +M: "Shyam Sundar S K" +L: netdev@vger.kernel.org +S: Supported +F: arch/arm64/boot/dts/amd/amd-seattle-xgbe*.dtsi +F: drivers/net/ethernet/amd/xgbe/ + AMLOGIC DDR PMU DRIVER M: Jiucheng Xu L: linux-amlogic@lists.infradead.org @@ -1169,6 +1096,14 @@ T: git git://git.kernel.org/pub/scm/linux/kernel/git/netdev/net-next.git F: drivers/net/amt.c +ANALOG DEVICES INC AD3552R DRIVER +M: Nuno Sá +L: linux-iio@vger.kernel.org +S: Supported +W: https://ez.analog.com/linux-software-drivers +F: Documentation/devicetree/bindings/iio/dac/adi,ad3552r.yaml +F: drivers/iio/dac/ad3552r.c + ANALOG DEVICES INC AD4130 DRIVER M: Cosmin Tanislav L: linux-iio@vger.kernel.org @@ -1194,14 +1129,6 @@ F: Documentation/devicetree/bindings/iio/adc/adi,ad7292.yaml F: drivers/iio/adc/ad7292.c -ANALOG DEVICES INC AD3552R DRIVER -M: Nuno Sá -L: linux-iio@vger.kernel.org -S: Supported -W: https://ez.analog.com/linux-software-drivers -F: Documentation/devicetree/bindings/iio/dac/adi,ad3552r.yaml -F: drivers/iio/dac/ad3552r.c - ANALOG DEVICES INC AD7293 DRIVER M: Antoniu Miclaus L: linux-iio@vger.kernel.org @@ -1210,23 +1137,6 @@ F: Documentation/devicetree/bindings/iio/dac/adi,ad7293.yaml F: drivers/iio/dac/ad7293.c -ANALOG DEVICES INC AD7768-1 DRIVER -M: Michael Hennerich -L: linux-iio@vger.kernel.org -S: Supported -W: https://ez.analog.com/linux-software-drivers -F: Documentation/devicetree/bindings/iio/adc/adi,ad7768-1.yaml -F: drivers/iio/adc/ad7768-1.c - -ANALOG DEVICES INC AD7780 DRIVER -M: Michael Hennerich -M: Renato Lui Geh -L: linux-iio@vger.kernel.org -S: Supported -W: https://ez.analog.com/linux-software-drivers -F: Documentation/devicetree/bindings/iio/adc/adi,ad7780.yaml -F: drivers/iio/adc/ad7780.c - ANALOG DEVICES INC AD74115 DRIVER M: Cosmin Tanislav L: linux-iio@vger.kernel.org @@ -1244,6 +1154,23 @@ F: drivers/iio/addac/ad74413r.c F: include/dt-bindings/iio/addac/adi,ad74413r.h +ANALOG DEVICES INC AD7768-1 DRIVER +M: Michael Hennerich +L: linux-iio@vger.kernel.org +S: Supported +W: https://ez.analog.com/linux-software-drivers +F: Documentation/devicetree/bindings/iio/adc/adi,ad7768-1.yaml +F: drivers/iio/adc/ad7768-1.c + +ANALOG DEVICES INC AD7780 DRIVER +M: Michael Hennerich +M: Renato Lui Geh +L: linux-iio@vger.kernel.org +S: Supported +W: https://ez.analog.com/linux-software-drivers +F: Documentation/devicetree/bindings/iio/adc/adi,ad7780.yaml +F: drivers/iio/adc/ad7780.c + ANALOG DEVICES INC ADA4250 DRIVER M: Antoniu Miclaus L: linux-iio@vger.kernel.org @@ -1294,10 +1221,10 @@ ANALOG DEVICES INC ADIS16475 DRIVER M: Nuno Sa L: linux-iio@vger.kernel.org -W: https://ez.analog.com/linux-software-drivers S: Supported -F: drivers/iio/imu/adis16475.c +W: https://ez.analog.com/linux-software-drivers F: Documentation/devicetree/bindings/iio/imu/adi,adis16475.yaml +F: drivers/iio/imu/adis16475.c ANALOG DEVICES INC ADM1177 DRIVER M: Michael Hennerich @@ -1315,21 +1242,21 @@ F: Documentation/devicetree/bindings/iio/frequency/adi,admv1013.yaml F: drivers/iio/frequency/admv1013.c -ANALOG DEVICES INC ADMV8818 DRIVER +ANALOG DEVICES INC ADMV1014 DRIVER M: Antoniu Miclaus L: linux-iio@vger.kernel.org S: Supported W: https://ez.analog.com/linux-software-drivers -F: Documentation/devicetree/bindings/iio/filter/adi,admv8818.yaml -F: drivers/iio/filter/admv8818.c +F: Documentation/devicetree/bindings/iio/frequency/adi,admv1014.yaml +F: drivers/iio/frequency/admv1014.c -ANALOG DEVICES INC ADMV1014 DRIVER +ANALOG DEVICES INC ADMV8818 DRIVER M: Antoniu Miclaus L: linux-iio@vger.kernel.org S: Supported W: https://ez.analog.com/linux-software-drivers -F: Documentation/devicetree/bindings/iio/frequency/adi,admv1014.yaml -F: drivers/iio/frequency/admv1014.c +F: Documentation/devicetree/bindings/iio/filter/adi,admv8818.yaml +F: drivers/iio/filter/admv8818.c ANALOG DEVICES INC ADP5061 DRIVER M: Michael Hennerich @@ -1351,8 +1278,8 @@ L: linux-media@vger.kernel.org S: Supported W: https://ez.analog.com/linux-software-drivers -F: drivers/media/i2c/adv7180.c F: Documentation/devicetree/bindings/media/i2c/adv7180.yaml +F: drivers/media/i2c/adv7180.c ANALOG DEVICES INC ADV748X DRIVER M: Kieran Bingham @@ -1371,8 +1298,8 @@ M: Hans Verkuil L: linux-media@vger.kernel.org S: Maintained -F: drivers/media/i2c/adv7604* F: Documentation/devicetree/bindings/media/i2c/adv7604.yaml +F: drivers/media/i2c/adv7604* ANALOG DEVICES INC ADV7842 DRIVER M: Hans Verkuil @@ -1384,8 +1311,8 @@ M: Nishant Malpani L: linux-iio@vger.kernel.org S: Supported -F: drivers/iio/gyro/adxrs290.c F: Documentation/devicetree/bindings/iio/gyroscope/adi,adxrs290.yaml +F: drivers/iio/gyro/adxrs290.c ANALOG DEVICES INC ASOC CODEC DRIVERS M: Lars-Peter Clausen @@ -1600,7 +1527,7 @@ ARASAN NAND CONTROLLER DRIVER M: Miquel Raynal -M: Naga Sureshkumar Relli +R: Michal Simek L: linux-mtd@lists.infradead.org S: Maintained F: Documentation/devicetree/bindings/mtd/arasan,nand-controller.yaml @@ -1625,6 +1552,18 @@ F: drivers/net/arcnet/ F: include/uapi/linux/if_arcnet.h +ARM AND ARM64 SoC SUB-ARCHITECTURES (COMMON PARTS) +M: Arnd Bergmann +M: Olof Johansson +M: soc@kernel.org +L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) +S: Maintained +C: irc://irc.libera.chat/armlinux +T: git git://git.kernel.org/pub/scm/linux/kernel/git/soc/soc.git +F: Documentation/process/maintainer-soc.rst +F: arch/arm/boot/dts/Makefile +F: arch/arm64/boot/dts/Makefile + ARM ARCHITECTED TIMER DRIVER M: Mark Rutland M: Marc Zyngier @@ -1653,9 +1592,9 @@ F: Documentation/devicetree/bindings/i2c/arm,i2c-versatile.yaml F: Documentation/devicetree/bindings/interrupt-controller/arm,versatile-fpga-irq.txt F: Documentation/devicetree/bindings/mtd/mtd-physmap.yaml -F: arch/arm/boot/dts/arm-realview-* -F: arch/arm/boot/dts/integrator* -F: arch/arm/boot/dts/versatile* +F: arch/arm/boot/dts/arm/arm-realview-* +F: arch/arm/boot/dts/arm/integrator* +F: arch/arm/boot/dts/arm/versatile* F: arch/arm/mach-versatile/ F: drivers/bus/arm-integrator-lm.c F: drivers/clk/versatile/ @@ -1666,10 +1605,7 @@ F: drivers/soc/versatile/ ARM KOMEDA DRM-KMS DRIVER -M: James (Qian) Wang M: Liviu Dudau -M: Mihail Atanassov -L: Mali DP Maintainers S: Supported T: git git://anongit.freedesktop.org/drm/drm-misc F: Documentation/devicetree/bindings/display/arm,komeda.yaml @@ -1690,8 +1626,6 @@ ARM MALI-DP DRM DRIVER M: Liviu Dudau -M: Brian Starkey -L: Mali DP Maintainers S: Supported T: git git://anongit.freedesktop.org/drm/drm-misc F: Documentation/devicetree/bindings/display/arm,malidp.yaml @@ -1738,22 +1672,6 @@ F: drivers/amba/ F: include/linux/amba/bus.h -ARM PRIMECELL PL35X NAND CONTROLLER DRIVER -M: Miquel Raynal -M: Naga Sureshkumar Relli -L: linux-mtd@lists.infradead.org -S: Maintained -F: Documentation/devicetree/bindings/mtd/arm,pl353-nand-r2p1.yaml -F: drivers/mtd/nand/raw/pl35x-nand-controller.c - -ARM PRIMECELL PL35X SMC DRIVER -M: Miquel Raynal -M: Naga Sureshkumar Relli -L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) -S: Maintained -F: Documentation/devicetree/bindings/memory-controllers/arm,pl35x-smc.yaml -F: drivers/memory/pl353-smc.c - ARM PRIMECELL CLCD PL110 DRIVER M: Russell King S: Odd Fixes @@ -1771,6 +1689,22 @@ F: drivers/mmc/host/mmci.* F: include/linux/amba/mmci.h +ARM PRIMECELL PL35X NAND CONTROLLER DRIVER +M: Miquel Raynal +R: Michal Simek +L: linux-mtd@lists.infradead.org +S: Maintained +F: Documentation/devicetree/bindings/mtd/arm,pl353-nand-r2p1.yaml +F: drivers/mtd/nand/raw/pl35x-nand-controller.c + +ARM PRIMECELL PL35X SMC DRIVER +M: Miquel Raynal +R: Michal Simek +L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) +S: Maintained +F: Documentation/devicetree/bindings/memory-controllers/arm,pl35x-smc.yaml +F: drivers/memory/pl353-smc.c + ARM PRIMECELL SSP PL022 SPI DRIVER M: Linus Walleij L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) @@ -1807,17 +1741,6 @@ F: drivers/iommu/arm/ F: drivers/iommu/io-pgtable-arm* -ARM AND ARM64 SoC SUB-ARCHITECTURES (COMMON PARTS) -M: Arnd Bergmann -M: Olof Johansson -M: soc@kernel.org -L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) -S: Maintained -C: irc://irc.libera.chat/armlinux -T: git git://git.kernel.org/pub/scm/linux/kernel/git/soc/soc.git -F: arch/arm/boot/dts/Makefile -F: arch/arm64/boot/dts/Makefile - ARM SUB-ARCHITECTURES L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) S: Maintained @@ -1842,7 +1765,7 @@ F: Documentation/devicetree/bindings/pinctrl/actions,* F: Documentation/devicetree/bindings/power/actions,owl-sps.txt F: Documentation/devicetree/bindings/timer/actions,owl-timer.txt -F: arch/arm/boot/dts/owl-* +F: arch/arm/boot/dts/actions/ F: arch/arm/mach-actions/ F: arch/arm64/boot/dts/actions/ F: drivers/clk/actions/ @@ -1869,9 +1792,9 @@ M: Jernej Skrabec M: Samuel Holland L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) +L: linux-sunxi@lists.linux.dev S: Maintained T: git git://git.kernel.org/pub/scm/linux/kernel/git/sunxi/linux.git -L: linux-sunxi@lists.linux.dev F: arch/arm/mach-sunxi/ F: arch/arm64/boot/dts/allwinner/ F: drivers/clk/sunxi-ng/ @@ -1888,6 +1811,7 @@ S: Maintained F: Documentation/devicetree/bindings/clock/amlogic* F: drivers/clk/meson/ +F: include/dt-bindings/clock/amlogic,a1* F: include/dt-bindings/clock/gxbb* F: include/dt-bindings/clock/meson* @@ -1915,10 +1839,12 @@ L: linux-amlogic@lists.infradead.org S: Maintained W: http://linux-meson.com/ -F: arch/arm/boot/dts/meson* +F: Documentation/devicetree/bindings/phy/amlogic* +F: arch/arm/boot/dts/amlogic/ F: arch/arm/mach-meson/ F: arch/arm64/boot/dts/amlogic/ F: drivers/mmc/host/meson* +F: drivers/phy/amlogic/ F: drivers/pinctrl/meson/ F: drivers/rtc/rtc-meson* F: drivers/soc/amlogic/ @@ -1929,11 +1855,22 @@ M: Antoine Tenart L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) S: Maintained -F: arch/arm/boot/dts/alpine* +F: arch/arm/boot/dts/amazon/ F: arch/arm/mach-alpine/ F: arch/arm64/boot/dts/amazon/ F: drivers/*/*alpine* +ARM/APPLE MACHINE SOUND DRIVERS +M: Martin PoviÅ¡er +L: asahi@lists.linux.dev +L: alsa-devel@alsa-project.org (moderated for non-subscribers) +S: Maintained +F: Documentation/devicetree/bindings/sound/adi,ssm3515.yaml +F: Documentation/devicetree/bindings/sound/apple,* +F: sound/soc/apple/* +F: sound/soc/codecs/cs42l83-i2c.c +F: sound/soc/codecs/ssm3515.c + ARM/APPLE MACHINE SUPPORT M: Hector Martin M: Sven Peter @@ -1961,7 +1898,7 @@ F: Documentation/devicetree/bindings/pci/apple,pcie.yaml F: Documentation/devicetree/bindings/pinctrl/apple,pinctrl.yaml F: Documentation/devicetree/bindings/power/apple* -F: Documentation/devicetree/bindings/pwm/pwm-apple.yaml +F: Documentation/devicetree/bindings/pwm/apple,s5l-fpwm.yaml F: Documentation/devicetree/bindings/watchdog/apple,wdt.yaml F: arch/arm64/boot/dts/apple/ F: drivers/bluetooth/hci_bcm4377.c @@ -1985,22 +1922,13 @@ F: include/linux/apple-mailbox.h F: include/linux/soc/apple/* -ARM/APPLE MACHINE SOUND DRIVERS -M: Martin PoviÅ¡er -L: asahi@lists.linux.dev -L: alsa-devel@alsa-project.org (moderated for non-subscribers) -S: Maintained -F: Documentation/devicetree/bindings/sound/apple,* -F: sound/soc/apple/* -F: sound/soc/codecs/cs42l83-i2c.c - ARM/ARTPEC MACHINE SUPPORT M: Jesper Nilsson M: Lars Persson L: linux-arm-kernel@axis.com S: Maintained F: Documentation/devicetree/bindings/pinctrl/axis,artpec6-pinctrl.txt -F: arch/arm/boot/dts/artpec6* +F: arch/arm/boot/dts/axis/ F: arch/arm/mach-artpec F: drivers/clk/axis F: drivers/crypto/axis @@ -2028,7 +1956,7 @@ Q: https://patchwork.ozlabs.org/project/linux-aspeed/list/ T: git git://git.kernel.org/pub/scm/linux/kernel/git/joel/aspeed.git F: Documentation/devicetree/bindings/arm/aspeed/ -F: arch/arm/boot/dts/aspeed-* +F: arch/arm/boot/dts/aspeed/ F: arch/arm/mach-aspeed/ N: aspeed @@ -2047,8 +1975,7 @@ M: Andre Przywara L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) S: Maintained -F: arch/arm/boot/dts/ecx-*.dts* -F: arch/arm/boot/dts/highbank.dts +F: arch/arm/boot/dts/calxeda/ F: arch/arm/mach-highbank/ ARM/CAVIUM THUNDER NETWORK DRIVER @@ -2096,12 +2023,13 @@ M: Baruch Siach L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) S: Maintained -F: arch/arm/boot/dts/cx92755* +F: arch/arm/boot/dts/cnxt/ N: digicolor ARM/CORESIGHT FRAMEWORK AND DRIVERS M: Suzuki K Poulose R: Mike Leach +R: James Clark R: Leo Yan L: coresight@lists.linaro.org (moderated for non-subscribers) L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) @@ -2109,19 +2037,19 @@ T: git git://git.kernel.org/pub/scm/linux/kernel/git/coresight/linux.git F: Documentation/ABI/testing/sysfs-bus-coresight-devices-* F: Documentation/devicetree/bindings/arm/arm,coresight-*.yaml -F: Documentation/devicetree/bindings/arm/qcom,coresight-*.yaml F: Documentation/devicetree/bindings/arm/arm,embedded-trace-extension.yaml F: Documentation/devicetree/bindings/arm/arm,trace-buffer-extension.yaml +F: Documentation/devicetree/bindings/arm/qcom,coresight-*.yaml F: Documentation/trace/coresight/* F: drivers/hwtracing/coresight/* F: include/dt-bindings/arm/coresight-cti-dt.h F: include/linux/coresight* F: samples/coresight/* -F: tools/perf/tests/shell/coresight/* F: tools/perf/arch/arm/util/auxtrace.c F: tools/perf/arch/arm/util/cs-etm.c F: tools/perf/arch/arm/util/cs-etm.h F: tools/perf/arch/arm/util/pmu.c +F: tools/perf/tests/shell/coresight/* F: tools/perf/util/cs-etm-decoder/* F: tools/perf/util/cs-etm.* @@ -2135,7 +2063,7 @@ F: Documentation/devicetree/bindings/net/cortina,gemini-ethernet.yaml F: Documentation/devicetree/bindings/pinctrl/cortina,gemini-pinctrl.txt F: Documentation/devicetree/bindings/rtc/faraday,ftrtc010.yaml -F: arch/arm/boot/dts/gemini* +F: arch/arm/boot/dts/gemini/ F: arch/arm/mach-gemini/ F: drivers/crypto/gemini/ F: drivers/net/ethernet/cortina/ @@ -2156,9 +2084,9 @@ F: Documentation/devicetree/bindings/watchdog/armada-37xx-wdt.txt F: drivers/bus/moxtet.c F: drivers/firmware/turris-mox-rwtm.c +F: drivers/gpio/gpio-moxtet.c F: drivers/leds/leds-turris-omnia.c F: drivers/mailbox/armada-37xx-rwtm-mailbox.c -F: drivers/gpio/gpio-moxtet.c F: drivers/watchdog/armada_37xx_wdt.c F: include/dt-bindings/bus/moxtet.h F: include/linux/armada-37xx-rwtm-mailbox.h @@ -2188,10 +2116,11 @@ L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) S: Maintained T: git git://git.kernel.org/pub/scm/linux/kernel/git/shawnguo/linux.git -X: drivers/media/i2c/ -F: arch/arm64/boot/dts/freescale/ +F: arch/arm/boot/dts/nxp/imx/ +F: arch/arm/boot/dts/nxp/mxs/ X: arch/arm64/boot/dts/freescale/fsl-* X: arch/arm64/boot/dts/freescale/qoriq-* +X: drivers/media/i2c/ N: imx N: mxs @@ -2201,7 +2130,7 @@ L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) S: Maintained T: git git://git.kernel.org/pub/scm/linux/kernel/git/shawnguo/linux.git -F: arch/arm/boot/dts/ls1021a* +F: arch/arm/boot/dts/nxp/ls/ F: arch/arm64/boot/dts/freescale/fsl-* F: arch/arm64/boot/dts/freescale/qoriq-* @@ -2213,7 +2142,7 @@ L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) S: Maintained T: git git://git.kernel.org/pub/scm/linux/kernel/git/shawnguo/linux.git -F: arch/arm/boot/dts/vf* +F: arch/arm/boot/dts/nxp/vf/ F: arch/arm/mach-imx/*vf610* ARM/GUMSTIX MACHINE SUPPORT @@ -2227,9 +2156,7 @@ S: Supported W: http://www.hisilicon.com T: git https://github.com/hisilicon/linux-hisi.git -F: arch/arm/boot/dts/hi3* -F: arch/arm/boot/dts/hip* -F: arch/arm/boot/dts/hisi* +F: arch/arm/boot/dts/hisilicon/ F: arch/arm/mach-hisi/ F: arch/arm64/boot/dts/hisilicon/ @@ -2245,14 +2172,13 @@ M: Jean-Marie Verdun M: Nick Hawkins S: Maintained -F: Documentation/hwmon/gxp-fan-ctrl.rst F: Documentation/devicetree/bindings/arm/hpe,gxp.yaml F: Documentation/devicetree/bindings/hwmon/hpe,gxp-fan-ctrl.yaml F: Documentation/devicetree/bindings/i2c/hpe,gxp-i2c.yaml F: Documentation/devicetree/bindings/spi/hpe,gxp-spifi.yaml F: Documentation/devicetree/bindings/timer/hpe,gxp-timer.yaml -F: arch/arm/boot/dts/hpe-bmc* -F: arch/arm/boot/dts/hpe-gxp* +F: Documentation/hwmon/gxp-fan-ctrl.rst +F: arch/arm/boot/dts/hpe/ F: arch/arm/mach-hpe/ F: drivers/clocksource/timer-gxp.c F: drivers/hwmon/gxp-fan-ctrl.c @@ -2266,7 +2192,7 @@ L: linux-omap@vger.kernel.org L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) S: Maintained -F: arch/arm/boot/dts/omap3-igep* +F: arch/arm/boot/dts/ti/omap/omap3-igep* ARM/INTEL IXP4XX ARM ARCHITECTURE M: Linus Walleij @@ -2275,11 +2201,11 @@ L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) S: Maintained F: Documentation/devicetree/bindings/arm/intel-ixp4xx.yaml -F: Documentation/devicetree/bindings/memory-controllers/intel,ixp4xx-expansion* F: Documentation/devicetree/bindings/gpio/intel,ixp4xx-gpio.txt F: Documentation/devicetree/bindings/interrupt-controller/intel,ixp4xx-interrupt.yaml +F: Documentation/devicetree/bindings/memory-controllers/intel,ixp4xx-expansion* F: Documentation/devicetree/bindings/timer/intel,ixp4xx-timer.yaml -F: arch/arm/boot/dts/intel-ixp* +F: arch/arm/boot/dts/intel/ixp/ F: arch/arm/mach-ixp4xx/ F: drivers/bus/intel-ixp4xx-eb.c F: drivers/clocksource/timer-ixp4xx.c @@ -2311,7 +2237,7 @@ L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) S: Maintained F: Documentation/devicetree/bindings/i2c/i2c-lpc2k.txt -F: arch/arm/boot/dts/lpc43* +F: arch/arm/boot/dts/nxp/lpc/lpc43* F: drivers/i2c/busses/i2c-lpc2k.c F: drivers/memory/pl172.c F: drivers/mtd/spi-nor/controllers/nxp-spifi.c @@ -2324,7 +2250,7 @@ S: Maintained T: git git://github.com/vzapolskiy/linux-lpc32xx.git F: Documentation/devicetree/bindings/i2c/i2c-pnx.txt -F: arch/arm/boot/dts/lpc32* +F: arch/arm/boot/dts/nxp/lpc/lpc32* F: arch/arm/mach-lpc32xx/ F: drivers/i2c/busses/i2c-pnx.c F: drivers/net/ethernet/nxp/lpc_eth.c @@ -2342,8 +2268,8 @@ F: Documentation/devicetree/bindings/arm/marvell/marvell,dove.txt F: Documentation/devicetree/bindings/arm/marvell/marvell,orion5x.txt F: Documentation/devicetree/bindings/soc/dove/ -F: arch/arm/boot/dts/dove* -F: arch/arm/boot/dts/orion5x* +F: arch/arm/boot/dts/marvell/dove* +F: arch/arm/boot/dts/marvell/orion5x* F: arch/arm/mach-dove/ F: arch/arm/mach-mv78xx0/ F: arch/arm/mach-orion5x/ @@ -2358,12 +2284,13 @@ S: Maintained T: git git://git.kernel.org/pub/scm/linux/kernel/git/gclement/mvebu.git F: Documentation/devicetree/bindings/arm/marvell/ -F: arch/arm/boot/dts/armada* -F: arch/arm/boot/dts/kirkwood* +F: arch/arm/boot/dts/marvell/armada* +F: arch/arm/boot/dts/marvell/kirkwood* F: arch/arm/configs/mvebu_*_defconfig F: arch/arm/mach-mvebu/ F: arch/arm64/boot/dts/marvell/armada* F: arch/arm64/boot/dts/marvell/cn913* +F: drivers/clk/mvebu/ F: drivers/cpufreq/armada-37xx-cpufreq.c F: drivers/cpufreq/armada-8k-cpufreq.c F: drivers/cpufreq/mvebu-cpufreq.c @@ -2393,10 +2320,7 @@ S: Maintained W: https://mtk.wiki.kernel.org/ C: irc://irc.libera.chat/linux-mediatek -F: arch/arm/boot/dts/mt2* -F: arch/arm/boot/dts/mt6* -F: arch/arm/boot/dts/mt7* -F: arch/arm/boot/dts/mt8* +F: arch/arm/boot/dts/mediatek/ F: arch/arm/mach-mediatek/ F: arch/arm64/boot/dts/mediatek/ F: drivers/soc/mediatek/ @@ -2412,18 +2336,25 @@ F: Documentation/devicetree/bindings/phy/mediatek,* F: drivers/phy/mediatek/ +ARM/MICROCHIP (ARM64) SoC support +M: Conor Dooley +M: Nicolas Ferre +M: Claudiu Beznea +L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) +S: Supported +T: git https://git.kernel.org/pub/scm/linux/kernel/git/at91/linux.git +F: arch/arm64/boot/dts/microchip/ + ARM/Microchip (AT91) SoC support M: Nicolas Ferre M: Alexandre Belloni -M: Claudiu Beznea +M: Claudiu Beznea L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) S: Supported W: http://www.linux4sam.org T: git git://git.kernel.org/pub/scm/linux/kernel/git/at91/linux.git -F: arch/arm/boot/dts/at91*.dts -F: arch/arm/boot/dts/at91*.dtsi -F: arch/arm/boot/dts/sama*.dts -F: arch/arm/boot/dts/sama*.dtsi +F: arch/arm/boot/dts/microchip/at91* +F: arch/arm/boot/dts/microchip/sama* F: arch/arm/include/debug/at91.S F: arch/arm/mach-at91/ F: drivers/memory/atmel* @@ -2441,25 +2372,17 @@ M: UNGLinuxDriver@microchip.com L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) S: Supported -T: git git://github.com/microchip-ung/linux-upstream.git -F: arch/arm64/boot/dts/microchip/ +F: arch/arm64/boot/dts/microchip/sparx* F: drivers/net/ethernet/microchip/vcap/ F: drivers/pinctrl/pinctrl-microchip-sgpio.c N: sparx5 -Microchip Timer Counter Block (TCB) Capture Driver -M: Kamel Bouhara -L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) -L: linux-iio@vger.kernel.org -S: Maintained -F: drivers/counter/microchip-tcb-capture.c - ARM/MILBEAUT ARCHITECTURE M: Taichi Sugaya M: Takao Orito L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) S: Maintained -F: arch/arm/boot/dts/milbeaut* +F: arch/arm/boot/dts/socionext/milbeaut* F: arch/arm/mach-milbeaut/ N: milbeaut @@ -2473,7 +2396,7 @@ F: Documentation/devicetree/bindings/arm/mstar/* F: Documentation/devicetree/bindings/clock/mstar,msc313-mpll.yaml F: Documentation/devicetree/bindings/gpio/mstar,msc313-gpio.yaml -F: arch/arm/boot/dts/mstar-* +F: arch/arm/boot/dts/sigmastar/ F: arch/arm/mach-mstar/ F: drivers/clk/mstar/ F: drivers/clocksource/timer-msc313e.c @@ -2492,7 +2415,7 @@ F: Documentation/devicetree/bindings/arm/ux500.yaml F: Documentation/devicetree/bindings/arm/ux500/ F: Documentation/devicetree/bindings/i2c/st,nomadik-i2c.yaml -F: arch/arm/boot/dts/ste-* +F: arch/arm/boot/dts/st/ste-* F: arch/arm/mach-nomadik/ F: arch/arm/mach-ux500/ F: drivers/clk/clk-nomadik.c @@ -2509,6 +2432,18 @@ F: drivers/rtc/rtc-pl031.c F: drivers/soc/ux500/ +ARM/NUVOTON MA35 ARCHITECTURE +M: Jacky Huang +M: Shan-Chun Hung +L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) +S: Supported +F: Documentation/devicetree/bindings/*/*/*ma35* +F: Documentation/devicetree/bindings/*/*ma35* +F: arch/arm64/boot/dts/nuvoton/*ma35* +F: drivers/*/*/*ma35* +F: drivers/*/*ma35* +K: ma35d1 + ARM/NUVOTON NPCM ARCHITECTURE M: Avi Fishman M: Tomer Maimon @@ -2520,13 +2455,12 @@ S: Supported F: Documentation/devicetree/bindings/*/*/*npcm* F: Documentation/devicetree/bindings/*/*npcm* -F: Documentation/devicetree/bindings/arm/npcm/* F: Documentation/devicetree/bindings/rtc/nuvoton,nct3018y.yaml -F: arch/arm/boot/dts/nuvoton-npcm* +F: arch/arm/boot/dts/nuvoton/nuvoton-npcm* F: arch/arm/mach-npcm/ F: arch/arm64/boot/dts/nuvoton/ -F: drivers/*/*npcm* F: drivers/*/*/*npcm* +F: drivers/*/*npcm* F: drivers/rtc/rtc-nct3018y.c F: include/dt-bindings/clock/nuvoton,npcm7xx-clock.h F: include/dt-bindings/clock/nuvoton,npcm845-clk.h @@ -2537,7 +2471,7 @@ S: Maintained W: https://github.com/neuschaefer/wpcm450/wiki F: Documentation/devicetree/bindings/*/*wpcm* -F: arch/arm/boot/dts/nuvoton-wpcm450* +F: arch/arm/boot/dts/nuvoton/nuvoton-wpcm450* F: arch/arm/configs/wpcm450_defconfig F: arch/arm/mach-npcm/wpcm450.c F: drivers/*/*/*wpcm* @@ -2569,23 +2503,28 @@ F: drivers/power/reset/oxnas-restart.c N: oxnas +ARM/QUALCOMM CHROMEBOOK SUPPORT +R: cros-qcom-dts-watchers@chromium.org +F: arch/arm64/boot/dts/qcom/sc7180* +F: arch/arm64/boot/dts/qcom/sc7280* +F: arch/arm64/boot/dts/qcom/sdm845-cheza* + ARM/QUALCOMM SUPPORT M: Andy Gross M: Bjorn Andersson -R: Konrad Dybcio +M: Konrad Dybcio L: linux-arm-msm@vger.kernel.org S: Maintained T: git git://git.kernel.org/pub/scm/linux/kernel/git/qcom/linux.git F: Documentation/devicetree/bindings/*/qcom* F: Documentation/devicetree/bindings/soc/qcom/ -F: arch/arm/boot/dts/qcom-*.dts -F: arch/arm/boot/dts/qcom-*.dtsi +F: arch/arm/boot/dts/qcom/ F: arch/arm/configs/qcom_defconfig F: arch/arm/mach-qcom/ F: arch/arm64/boot/dts/qcom/ +F: drivers/*/*/pm8???-* F: drivers/*/*/qcom* F: drivers/*/*/qcom/ -F: drivers/*/pm8???-* F: drivers/*/qcom* F: drivers/*/qcom/ F: drivers/bluetooth/btqcomsmd.c @@ -2602,22 +2541,16 @@ F: drivers/phy/qualcomm/ F: drivers/power/*/msm* F: drivers/reset/reset-qcom-* -F: drivers/ufs/host/ufs-qcom* F: drivers/spi/spi-geni-qcom.c F: drivers/spi/spi-qcom-qspi.c F: drivers/spi/spi-qup.c F: drivers/tty/serial/msm_serial.c +F: drivers/ufs/host/ufs-qcom* F: drivers/usb/dwc3/dwc3-qcom.c F: include/dt-bindings/*/qcom* F: include/linux/*/qcom* F: include/linux/soc/qcom/ -ARM/QUALCOMM CHROMEBOOK SUPPORT -R: cros-qcom-dts-watchers@chromium.org -F: arch/arm64/boot/dts/qcom/sc7180* -F: arch/arm64/boot/dts/qcom/sc7280* -F: arch/arm64/boot/dts/qcom/sdm845-cheza* - ARM/RDA MICRO ARCHITECTURE M: Manivannan Sadhasivam L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) @@ -2628,7 +2561,7 @@ F: Documentation/devicetree/bindings/interrupt-controller/rda,8810pl-intc.yaml F: Documentation/devicetree/bindings/serial/rda,8810pl-uart.yaml F: Documentation/devicetree/bindings/timer/rda,8810pl-timer.yaml -F: arch/arm/boot/dts/rda8810pl-* +F: arch/arm/boot/dts/unisoc/ F: drivers/clocksource/timer-rda.c F: drivers/gpio/gpio-rda.c F: drivers/irqchip/irq-rda-intc.c @@ -2640,7 +2573,7 @@ L: linux-realtek-soc@lists.infradead.org (moderated for non-subscribers) S: Maintained F: Documentation/devicetree/bindings/arm/realtek.yaml -F: arch/arm/boot/dts/rtd* +F: arch/arm/boot/dts/realtek/ F: arch/arm/mach-realtek/ F: arch/arm64/boot/dts/realtek/ @@ -2654,13 +2587,7 @@ T: git git://git.kernel.org/pub/scm/linux/kernel/git/geert/renesas-devel.git next F: Documentation/devicetree/bindings/hwinfo/renesas,prr.yaml F: Documentation/devicetree/bindings/soc/renesas/ -F: arch/arm/boot/dts/emev2* -F: arch/arm/boot/dts/gr-peach* -F: arch/arm/boot/dts/iwg20d-q7* -F: arch/arm/boot/dts/r7s* -F: arch/arm/boot/dts/r8a* -F: arch/arm/boot/dts/r9a* -F: arch/arm/boot/dts/sh* +F: arch/arm/boot/dts/renesas/ F: arch/arm/configs/shmobile_defconfig F: arch/arm/include/debug/renesas-scif.S F: arch/arm/mach-shmobile/ @@ -2693,8 +2620,7 @@ F: Documentation/devicetree/bindings/i2c/i2c-rk3x.yaml F: Documentation/devicetree/bindings/mmc/rockchip-dw-mshc.yaml F: Documentation/devicetree/bindings/spi/spi-rockchip.yaml -F: arch/arm/boot/dts/rk3* -F: arch/arm/boot/dts/rv11* +F: arch/arm/boot/dts/rockchip/ F: arch/arm/mach-rockchip/ F: drivers/*/*/*rockchip* F: drivers/*/*rockchip* @@ -2709,18 +2635,16 @@ L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) L: linux-samsung-soc@vger.kernel.org S: Maintained -C: irc://irc.libera.chat/linux-exynos Q: https://patchwork.kernel.org/project/linux-samsung-soc/list/ B: mailto:linux-samsung-soc@vger.kernel.org +C: irc://irc.libera.chat/linux-exynos T: git git://git.kernel.org/pub/scm/linux/kernel/git/krzk/linux.git -F: Documentation/arm/samsung/ +F: Documentation/arch/arm/samsung/ F: Documentation/devicetree/bindings/arm/samsung/ F: Documentation/devicetree/bindings/hwinfo/samsung,* F: Documentation/devicetree/bindings/power/pd-samsung.yaml F: Documentation/devicetree/bindings/soc/samsung/ -F: arch/arm/boot/dts/exynos* -F: arch/arm/boot/dts/s3c* -F: arch/arm/boot/dts/s5p* +F: arch/arm/boot/dts/samsung/ F: arch/arm/mach-exynos*/ F: arch/arm/mach-s3c/ F: arch/arm/mach-s5p*/ @@ -2780,7 +2704,7 @@ S: Maintained W: http://www.rocketboards.org T: git git://git.kernel.org/pub/scm/linux/kernel/git/dinguyen/linux.git -F: arch/arm/boot/dts/socfpga* +F: arch/arm/boot/dts/intel/socfpga/ F: arch/arm/configs/socfpga_defconfig F: arch/arm/mach-socfpga/ F: arch/arm64/boot/dts/altera/ @@ -2811,9 +2735,9 @@ L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) S: Maintained W: http://www.stlinux.com -F: Documentation/devicetree/bindings/spi/st,ssc-spi.yaml F: Documentation/devicetree/bindings/i2c/st,sti-i2c.yaml -F: arch/arm/boot/dts/sti* +F: Documentation/devicetree/bindings/spi/st,ssc-spi.yaml +F: arch/arm/boot/dts/st/sti* F: arch/arm/mach-sti/ F: drivers/ata/ahci_st.c F: drivers/char/hw_random/st-rng.c @@ -2846,8 +2770,9 @@ L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) S: Maintained T: git git://git.kernel.org/pub/scm/linux/kernel/git/atorgue/stm32.git stm32-next -F: arch/arm/boot/dts/stm32* +F: arch/arm/boot/dts/st/stm32* F: arch/arm/mach-stm32/ +F: arch/arm64/boot/dts/st/ F: drivers/clocksource/armv7m_systick.c N: stm32 N: stm @@ -2861,7 +2786,7 @@ F: Documentation/devicetree/bindings/clock/sunplus,sp7021-clkc.yaml F: Documentation/devicetree/bindings/interrupt-controller/sunplus,sp7021-intc.yaml F: Documentation/devicetree/bindings/reset/sunplus,reset.yaml -F: arch/arm/boot/dts/sunplus-sp7021*.dts* +F: arch/arm/boot/dts/sunplus/ F: arch/arm/configs/sp7021_*defconfig F: arch/arm/mach-sunplus/ F: drivers/clk/clk-sp7021.c @@ -2875,7 +2800,7 @@ M: Sebastian Hesselbarth L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) S: Maintained -F: arch/arm/boot/dts/berlin* +F: arch/arm/boot/dts/synaptics/ F: arch/arm/mach-berlin/ F: arch/arm64/boot/dts/synaptics/ @@ -2917,7 +2842,7 @@ L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) S: Maintained T: git git://git.kernel.org/pub/scm/linux/kernel/git/ti/linux.git -F: arch/arm/boot/dts/keystone-* +F: arch/arm/boot/dts/ti/keystone/ F: arch/arm/mach-keystone/ ARM/TEXAS INSTRUMENT KEYSTONE CLOCK FRAMEWORK @@ -2949,7 +2874,6 @@ F: Documentation/devicetree/bindings/hwinfo/ti,k3-socinfo.yaml F: arch/arm64/boot/dts/ti/Makefile F: arch/arm64/boot/dts/ti/k3-* -F: include/dt-bindings/pinctrl/k3.h ARM/TOSHIBA VISCONTI ARCHITECTURE M: Nobuhiro Iwamatsu @@ -2959,15 +2883,15 @@ F: Documentation/devicetree/bindings/arm/toshiba.yaml F: Documentation/devicetree/bindings/clock/toshiba,tmpv770x-pipllct.yaml F: Documentation/devicetree/bindings/clock/toshiba,tmpv770x-pismu.yaml -F: Documentation/devicetree/bindings/net/toshiba,visconti-dwmac.yaml F: Documentation/devicetree/bindings/gpio/toshiba,gpio-visconti.yaml +F: Documentation/devicetree/bindings/net/toshiba,visconti-dwmac.yaml F: Documentation/devicetree/bindings/pci/toshiba,visconti-pcie.yaml F: Documentation/devicetree/bindings/pinctrl/toshiba,visconti-pinctrl.yaml F: Documentation/devicetree/bindings/watchdog/toshiba,visconti-wdt.yaml F: arch/arm64/boot/dts/toshiba/ F: drivers/clk/visconti/ -F: drivers/net/ethernet/stmicro/stmmac/dwmac-visconti.c F: drivers/gpio/gpio-visconti.c +F: drivers/net/ethernet/stmicro/stmmac/dwmac-visconti.c F: drivers/pci/controller/dwc/pcie-visconti.c F: drivers/pinctrl/visconti/ F: drivers/watchdog/visconti_wdt.c @@ -2982,7 +2906,7 @@ F: Documentation/devicetree/bindings/gpio/socionext,uniphier-gpio.yaml F: Documentation/devicetree/bindings/pinctrl/socionext,uniphier-pinctrl.yaml F: Documentation/devicetree/bindings/soc/socionext/socionext,uniphier*.yaml -F: arch/arm/boot/dts/uniphier* +F: arch/arm/boot/dts/socionext/uniphier* F: arch/arm/include/asm/hardware/cache-uniphier.h F: arch/arm/mach-uniphier/ F: arch/arm/mm/cache-uniphier.c @@ -3007,7 +2931,7 @@ S: Maintained F: */*/*/vexpress* F: */*/vexpress* -F: arch/arm/boot/dts/vexpress* +F: arch/arm/boot/dts/arm/vexpress* F: arch/arm/mach-versatile/ F: arch/arm64/boot/dts/arm/ F: drivers/clk/versatile/clk-vexpress-osc.c @@ -3065,7 +2989,7 @@ L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) S: Maintained T: git git://git.kernel.org/pub/scm/linux/kernel/git/arm64/linux.git -F: Documentation/arm64/ +F: Documentation/arch/arm64/ F: arch/arm64/ F: tools/testing/selftests/arm64/ X: arch/arm64/boot/dts/ @@ -3112,6 +3036,13 @@ F: Documentation/devicetree/bindings/net/asix,ax88796c.yaml F: drivers/net/ethernet/asix/ax88796c_* +ASPEED CRYPTO DRIVER +M: Neal Liu +L: linux-aspeed@lists.ozlabs.org (moderated for non-subscribers) +S: Maintained +F: Documentation/devicetree/bindings/crypto/aspeed,* +F: drivers/crypto/aspeed/ + ASPEED PECI CONTROLLER M: Iwona Winiarska L: linux-aspeed@lists.ozlabs.org (moderated for non-subscribers) @@ -3156,6 +3087,13 @@ F: Documentation/devicetree/bindings/spi/aspeed,ast2600-fmc.yaml F: drivers/spi/spi-aspeed-smc.c +ASPEED USB UDC DRIVER +M: Neal Liu +L: linux-aspeed@lists.ozlabs.org (moderated for non-subscribers) +S: Maintained +F: Documentation/devicetree/bindings/usb/aspeed,ast2600-udc.yaml +F: drivers/usb/gadget/udc/aspeed_udc.c + ASPEED VIDEO ENGINE DRIVER M: Eddie James L: linux-media@vger.kernel.org @@ -3164,19 +3102,11 @@ F: Documentation/devicetree/bindings/media/aspeed-video.txt F: drivers/media/platform/aspeed/ -ASPEED USB UDC DRIVER -M: Neal Liu -L: linux-aspeed@lists.ozlabs.org (moderated for non-subscribers) -S: Maintained -F: Documentation/devicetree/bindings/usb/aspeed,ast2600-udc.yaml -F: drivers/usb/gadget/udc/aspeed_udc.c - -ASPEED CRYPTO DRIVER -M: Neal Liu -L: linux-aspeed@lists.ozlabs.org (moderated for non-subscribers) +ASUS EC HARDWARE MONITOR DRIVER +M: Eugene Shalygin +L: linux-hwmon@vger.kernel.org S: Maintained -F: Documentation/devicetree/bindings/crypto/aspeed,* -F: drivers/crypto/aspeed/ +F: drivers/hwmon/asus-ec-sensors.c ASUS NOTEBOOKS AND EEEPC ACPI/WMI EXTRAS DRIVERS M: Corentin Chary @@ -3194,6 +3124,12 @@ T: git git://git.kernel.org/pub/scm/linux/kernel/git/pdx86/platform-drivers-x86.git F: drivers/platform/x86/asus-tf103c-dock.c +ASUS WIRELESS RADIO CONTROL DRIVER +M: João Paulo Rechi Vita +L: platform-driver-x86@vger.kernel.org +S: Maintained +F: drivers/platform/x86/asus-wireless.c + ASUS WMI HARDWARE MONITOR DRIVER M: Ed Brindley M: Denis Pauk @@ -3201,18 +3137,6 @@ S: Maintained F: drivers/hwmon/asus_wmi_sensors.c -ASUS EC HARDWARE MONITOR DRIVER -M: Eugene Shalygin -L: linux-hwmon@vger.kernel.org -S: Maintained -F: drivers/hwmon/asus-ec-sensors.c - -ASUS WIRELESS RADIO CONTROL DRIVER -M: João Paulo Rechi Vita -L: platform-driver-x86@vger.kernel.org -S: Maintained -F: drivers/platform/x86/asus-wireless.c - ASYMMETRIC KEYS M: David Howells L: keyrings@vger.kernel.org @@ -3326,7 +3250,7 @@ ATMEL MACB ETHERNET DRIVER M: Nicolas Ferre -M: Claudiu Beznea +M: Claudiu Beznea S: Supported F: drivers/net/ethernet/cadence/ @@ -3338,9 +3262,8 @@ F: drivers/input/touchscreen/atmel_mxt_ts.c ATMEL WIRELESS DRIVER -M: Simon Kelley L: linux-wireless@vger.kernel.org -S: Maintained +S: Orphan W: http://www.thekelleys.org.uk/atmel W: http://atmelwlandriver.sourceforge.net/ F: drivers/net/wireless/atmel/atmel* @@ -3352,10 +3275,10 @@ R: Mark Rutland L: linux-kernel@vger.kernel.org S: Maintained +F: Documentation/atomic_*.txt F: arch/*/include/asm/atomic*.h F: include/*/atomic*.h F: include/linux/refcount.h -F: Documentation/atomic_*.txt F: scripts/atomic/ ATTO EXPRESSSAS SAS/SATA RAID SCSI DRIVER @@ -3387,6 +3310,16 @@ F: kernel/audit* F: lib/*audit.c +AUXILIARY BUS DRIVER +M: Greg Kroah-Hartman +R: Dave Ertman +R: Ira Weiny +S: Supported +T: git git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/driver-core.git +F: Documentation/driver-api/auxiliary_bus.rst +F: drivers/base/auxiliary.c +F: include/linux/auxiliary_bus.h + AUXILIARY DISPLAY DRIVERS M: Miguel Ojeda S: Maintained @@ -3414,10 +3347,10 @@ M: Peter Rosin L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) S: Maintained -F: arch/arm/boot/dts/at91-linea.dtsi -F: arch/arm/boot/dts/at91-natte.dtsi -F: arch/arm/boot/dts/at91-nattis-2-natte-2.dts -F: arch/arm/boot/dts/at91-tse850-3.dts +F: arch/arm/boot/dts/microchip/at91-linea.dtsi +F: arch/arm/boot/dts/microchip/at91-natte.dtsi +F: arch/arm/boot/dts/microchip/at91-nattis-2-natte-2.dts +F: arch/arm/boot/dts/microchip/at91-tse850-3.dts AXENTIA ASOC DRIVERS M: Peter Rosin @@ -3460,7 +3393,7 @@ B43 WIRELESS DRIVER L: linux-wireless@vger.kernel.org L: b43-dev@lists.infradead.org -S: Odd Fixes +S: Orphan W: https://wireless.wiki.kernel.org/en/users/Drivers/b43 F: drivers/net/wireless/broadcom/b43/ @@ -3548,7 +3481,7 @@ F: fs/befs/ BFQ I/O SCHEDULER -M: Paolo Valente +M: Paolo Valente M: Jens Axboe L: linux-block@vger.kernel.org S: Maintained @@ -3567,18 +3500,24 @@ R: Andy Shevchenko R: Rasmus Villemoes S: Maintained +F: include/linux/bitfield.h F: include/linux/bitmap.h +F: include/linux/bits.h F: include/linux/cpumask.h F: include/linux/find.h F: include/linux/nodemask.h +F: include/vdso/bits.h F: lib/bitmap.c F: lib/cpumask.c F: lib/cpumask_kunit.c F: lib/find_bit.c F: lib/find_bit_benchmark.c F: lib/test_bitmap.c +F: tools/include/linux/bitfield.h F: tools/include/linux/bitmap.h +F: tools/include/linux/bits.h F: tools/include/linux/find.h +F: tools/include/vdso/bits.h F: tools/lib/bitmap.c F: tools/lib/find_bit.c @@ -3616,6 +3555,7 @@ W: http://www.bluez.org/ T: git git://git.kernel.org/pub/scm/linux/kernel/git/bluetooth/bluetooth.git T: git git://git.kernel.org/pub/scm/linux/kernel/git/bluetooth/bluetooth-next.git +F: Documentation/devicetree/bindings/net/bluetooth/ F: drivers/bluetooth/ BLUETOOTH SUBSYSTEM @@ -3649,50 +3589,6 @@ F: Documentation/devicetree/bindings/iio/accel/bosch,bma400.yaml F: drivers/iio/accel/bma400* -BPF [GENERAL] (Safe Dynamic Programs and Tools) -M: Alexei Starovoitov -M: Daniel Borkmann -M: Andrii Nakryiko -R: Martin KaFai Lau -R: Song Liu -R: Yonghong Song -R: John Fastabend -R: KP Singh -R: Stanislav Fomichev -R: Hao Luo -R: Jiri Olsa -L: bpf@vger.kernel.org -S: Supported -W: https://bpf.io/ -Q: https://patchwork.kernel.org/project/netdevbpf/list/?delegate=121173 -T: git git://git.kernel.org/pub/scm/linux/kernel/git/bpf/bpf.git -T: git git://git.kernel.org/pub/scm/linux/kernel/git/bpf/bpf-next.git -F: Documentation/bpf/ -F: Documentation/networking/filter.rst -F: Documentation/userspace-api/ebpf/ -F: arch/*/net/* -F: include/linux/bpf* -F: include/linux/btf* -F: include/linux/filter.h -F: include/trace/events/xdp.h -F: include/uapi/linux/bpf* -F: include/uapi/linux/btf* -F: include/uapi/linux/filter.h -F: kernel/bpf/ -F: kernel/trace/bpf_trace.c -F: lib/test_bpf.c -F: net/bpf/ -F: net/core/filter.c -F: net/sched/act_bpf.c -F: net/sched/cls_bpf.c -F: samples/bpf/ -F: scripts/bpf_doc.py -F: scripts/pahole-flags.sh -F: scripts/pahole-version.sh -F: tools/bpf/ -F: tools/lib/bpf/ -F: tools/testing/selftests/bpf/ - BPF JIT for ARM M: Shubham Bansal L: bpf@vger.kernel.org @@ -3771,79 +3667,79 @@ F: arch/x86/net/ X: arch/x86/net/bpf_jit_comp32.c +BPF [BTF] +M: Martin KaFai Lau +L: bpf@vger.kernel.org +S: Maintained +F: include/linux/btf* +F: kernel/bpf/btf.c + BPF [CORE] M: Alexei Starovoitov M: Daniel Borkmann R: John Fastabend L: bpf@vger.kernel.org S: Maintained -F: kernel/bpf/verifier.c -F: kernel/bpf/tnum.c -F: kernel/bpf/core.c -F: kernel/bpf/syscall.c -F: kernel/bpf/dispatcher.c -F: kernel/bpf/trampoline.c F: include/linux/bpf* F: include/linux/filter.h F: include/linux/tnum.h +F: kernel/bpf/core.c +F: kernel/bpf/dispatcher.c +F: kernel/bpf/syscall.c +F: kernel/bpf/tnum.c +F: kernel/bpf/trampoline.c +F: kernel/bpf/verifier.c -BPF [BTF] -M: Martin KaFai Lau -L: bpf@vger.kernel.org -S: Maintained -F: kernel/bpf/btf.c -F: include/linux/btf* - -BPF [TRACING] -M: Song Liu -R: Jiri Olsa +BPF [DOCUMENTATION] (Related to Standardization) +R: David Vernet L: bpf@vger.kernel.org +L: bpf@ietf.org S: Maintained -F: kernel/trace/bpf_trace.c -F: kernel/bpf/stackmap.c +F: Documentation/bpf/instruction-set.rst -BPF [NETWORKING] (tc BPF, sock_addr) -M: Martin KaFai Lau +BPF [GENERAL] (Safe Dynamic Programs and Tools) +M: Alexei Starovoitov M: Daniel Borkmann +M: Andrii Nakryiko +R: Martin KaFai Lau +R: Song Liu +R: Yonghong Song R: John Fastabend +R: KP Singh +R: Stanislav Fomichev +R: Hao Luo +R: Jiri Olsa L: bpf@vger.kernel.org -L: netdev@vger.kernel.org -S: Maintained +S: Supported +W: https://bpf.io/ +Q: https://patchwork.kernel.org/project/netdevbpf/list/?delegate=121173 +T: git git://git.kernel.org/pub/scm/linux/kernel/git/bpf/bpf.git +T: git git://git.kernel.org/pub/scm/linux/kernel/git/bpf/bpf-next.git +F: Documentation/bpf/ +F: Documentation/networking/filter.rst +F: Documentation/userspace-api/ebpf/ +F: arch/*/net/* +F: include/linux/bpf* +F: include/linux/btf* +F: include/linux/filter.h +F: include/trace/events/xdp.h +F: include/uapi/linux/bpf* +F: include/uapi/linux/btf* +F: include/uapi/linux/filter.h +F: kernel/bpf/ +F: kernel/trace/bpf_trace.c +F: lib/test_bpf.c +F: net/bpf/ F: net/core/filter.c F: net/sched/act_bpf.c F: net/sched/cls_bpf.c - -BPF [NETWORKING] (struct_ops, reuseport) -M: Martin KaFai Lau -L: bpf@vger.kernel.org -L: netdev@vger.kernel.org -S: Maintained -F: kernel/bpf/bpf_struct* - -BPF [SECURITY & LSM] (Security Audit and Enforcement using BPF) -M: KP Singh -R: Florent Revest -R: Brendan Jackman -L: bpf@vger.kernel.org -S: Maintained -F: Documentation/bpf/prog_lsm.rst -F: include/linux/bpf_lsm.h -F: kernel/bpf/bpf_lsm.c -F: security/bpf/ - -BPF [STORAGE & CGROUPS] -M: Martin KaFai Lau -L: bpf@vger.kernel.org -S: Maintained -F: kernel/bpf/cgroup.c -F: kernel/bpf/*storage.c -F: kernel/bpf/bpf_lru* - -BPF [RINGBUF] -M: Andrii Nakryiko -L: bpf@vger.kernel.org -S: Maintained -F: kernel/bpf/ringbuf.c +F: samples/bpf/ +F: scripts/bpf_doc.py +F: scripts/pahole-flags.sh +F: scripts/pahole-version.sh +F: tools/bpf/ +F: tools/lib/bpf/ +F: tools/testing/selftests/bpf/ BPF [ITERATOR] M: Yonghong Song @@ -3870,12 +3766,45 @@ S: Maintained F: tools/lib/bpf/ -BPF [TOOLING] (bpftool) -M: Quentin Monnet +BPF [MISC] L: bpf@vger.kernel.org +S: Odd Fixes +K: (?:\b|_)bpf(?:\b|_) + +BPF [NETWORKING] (struct_ops, reuseport) +M: Martin KaFai Lau +L: bpf@vger.kernel.org +L: netdev@vger.kernel.org S: Maintained -F: kernel/bpf/disasm.* -F: tools/bpf/bpftool/ +F: kernel/bpf/bpf_struct* + +BPF [NETWORKING] (tc BPF, sock_addr) +M: Martin KaFai Lau +M: Daniel Borkmann +R: John Fastabend +L: bpf@vger.kernel.org +L: netdev@vger.kernel.org +S: Maintained +F: net/core/filter.c +F: net/sched/act_bpf.c +F: net/sched/cls_bpf.c + +BPF [RINGBUF] +M: Andrii Nakryiko +L: bpf@vger.kernel.org +S: Maintained +F: kernel/bpf/ringbuf.c + +BPF [SECURITY & LSM] (Security Audit and Enforcement using BPF) +M: KP Singh +R: Florent Revest +R: Brendan Jackman +L: bpf@vger.kernel.org +S: Maintained +F: Documentation/bpf/prog_lsm.rst +F: include/linux/bpf_lsm.h +F: kernel/bpf/bpf_lsm.c +F: security/bpf/ BPF [SELFTESTS] (Test Runners & Infrastructure) M: Andrii Nakryiko @@ -3884,17 +3813,28 @@ S: Maintained F: tools/testing/selftests/bpf/ -BPF [DOCUMENTATION] (Related to Standardization) -R: David Vernet +BPF [STORAGE & CGROUPS] +M: Martin KaFai Lau L: bpf@vger.kernel.org -L: bpf@ietf.org S: Maintained -F: Documentation/bpf/instruction-set.rst +F: kernel/bpf/*storage.c +F: kernel/bpf/bpf_lru* +F: kernel/bpf/cgroup.c -BPF [MISC] +BPF [TOOLING] (bpftool) +M: Quentin Monnet L: bpf@vger.kernel.org -S: Odd Fixes -K: (?:\b|_)bpf(?:\b|_) +S: Maintained +F: kernel/bpf/disasm.* +F: tools/bpf/bpftool/ + +BPF [TRACING] +M: Song Liu +R: Jiri Olsa +L: bpf@vger.kernel.org +S: Maintained +F: kernel/bpf/stackmap.c +F: kernel/trace/bpf_trace.c BROADCOM B44 10/100 ETHERNET DRIVER M: Michael Chan @@ -3903,7 +3843,7 @@ F: drivers/net/ethernet/broadcom/b44.* BROADCOM B53/SF2 ETHERNET SWITCH DRIVER -M: Florian Fainelli +M: Florian Fainelli L: netdev@vger.kernel.org L: openwrt-devel@lists.openwrt.org (subscribers-only) S: Supported @@ -3913,36 +3853,8 @@ F: include/linux/dsa/brcm.h F: include/linux/platform_data/b53.h -BROADCOM BCMBCA ARM ARCHITECTURE -M: William Zhang -M: Anand Gore -M: Kursad Oney -M: Florian Fainelli -M: RafaÅ‚ MiÅ‚ecki -R: Broadcom internal kernel review list -L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) -S: Maintained -T: git https://github.com/broadcom/stblinux.git -F: Documentation/devicetree/bindings/arm/bcm/brcm,bcmbca.yaml -F: arch/arm64/boot/dts/broadcom/bcmbca/* -N: bcmbca -N: bcm[9]?47622 -N: bcm[9]?4912 -N: bcm[9]?63138 -N: bcm[9]?63146 -N: bcm[9]?63148 -N: bcm[9]?63158 -N: bcm[9]?63178 -N: bcm[9]?6756 -N: bcm[9]?6813 -N: bcm[9]?6846 -N: bcm[9]?6855 -N: bcm[9]?6856 -N: bcm[9]?6858 -N: bcm[9]?6878 - BROADCOM BCM2711/BCM2835 ARM ARCHITECTURE -M: Florian Fainelli +M: Florian Fainelli R: Broadcom internal kernel review list L: linux-rpi-kernel@lists.infradead.org (moderated for non-subscribers) L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) @@ -3956,7 +3868,7 @@ N: raspberrypi BROADCOM BCM281XX/BCM11XXX/BCM216XX ARM ARCHITECTURE -M: Florian Fainelli +M: Florian Fainelli M: Ray Jui M: Scott Branden R: Broadcom internal kernel review list @@ -3995,25 +3907,26 @@ F: drivers/pinctrl/bcm/pinctrl-bcm4908.c BROADCOM BCM5301X ARM ARCHITECTURE -M: Florian Fainelli +M: Florian Fainelli M: Hauke Mehrtens M: RafaÅ‚ MiÅ‚ecki R: Broadcom internal kernel review list L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) S: Maintained -F: arch/arm/boot/dts/bcm470* -F: arch/arm/boot/dts/bcm5301* -F: arch/arm/boot/dts/bcm953012* +F: arch/arm/boot/dts/broadcom/bcm-ns.dtsi +F: arch/arm/boot/dts/broadcom/bcm470* +F: arch/arm/boot/dts/broadcom/bcm5301* +F: arch/arm/boot/dts/broadcom/bcm953012* F: arch/arm/mach-bcm/bcm_5301x.c BROADCOM BCM53573 ARM ARCHITECTURE -M: Florian Fainelli +M: Florian Fainelli M: RafaÅ‚ MiÅ‚ecki R: Broadcom internal kernel review list L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) S: Maintained -F: arch/arm/boot/dts/bcm47189* -F: arch/arm/boot/dts/bcm53573* +F: arch/arm/boot/dts/broadcom/bcm47189* +F: arch/arm/boot/dts/broadcom/bcm53573* BROADCOM BCM63XX/BCM33XX UDC DRIVER M: Kevin Cernekee @@ -4022,13 +3935,13 @@ F: drivers/usb/gadget/udc/bcm63xx_udc.* BROADCOM BCM7XXX ARM ARCHITECTURE -M: Florian Fainelli +M: Florian Fainelli R: Broadcom internal kernel review list L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) S: Maintained T: git https://github.com/broadcom/stblinux.git F: Documentation/devicetree/bindings/pci/brcm,stb-pcie.yaml -F: arch/arm/boot/dts/bcm7*.dts* +F: arch/arm/boot/dts/broadcom/bcm7*.dts* F: arch/arm/include/asm/hardware/cache-b15-rac.h F: arch/arm/mach-bcm/*brcmstb* F: arch/arm/mm/cache-b15-rac.c @@ -4038,11 +3951,39 @@ N: bcm7038 N: bcm7120 +BROADCOM BCMBCA ARM ARCHITECTURE +M: William Zhang +M: Anand Gore +M: Kursad Oney +M: Florian Fainelli +M: RafaÅ‚ MiÅ‚ecki +R: Broadcom internal kernel review list +L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) +S: Maintained +T: git https://github.com/broadcom/stblinux.git +F: Documentation/devicetree/bindings/arm/bcm/brcm,bcmbca.yaml +F: arch/arm64/boot/dts/broadcom/bcmbca/* +N: bcmbca +N: bcm[9]?47622 +N: bcm[9]?4912 +N: bcm[9]?63138 +N: bcm[9]?63146 +N: bcm[9]?63148 +N: bcm[9]?63158 +N: bcm[9]?63178 +N: bcm[9]?6756 +N: bcm[9]?6813 +N: bcm[9]?6846 +N: bcm[9]?6855 +N: bcm[9]?6856 +N: bcm[9]?6858 +N: bcm[9]?6878 + BROADCOM BDC DRIVER -M: Justin Chen +M: Justin Chen M: Al Cooper -L: linux-usb@vger.kernel.org R: Broadcom internal kernel review list +L: linux-usb@vger.kernel.org S: Maintained F: Documentation/devicetree/bindings/usb/brcm,bdc.yaml F: drivers/usb/gadget/udc/bdc/ @@ -4055,7 +3996,7 @@ F: drivers/cpufreq/bmips-cpufreq.c BROADCOM BMIPS MIPS ARCHITECTURE -M: Florian Fainelli +M: Florian Fainelli R: Broadcom internal kernel review list L: linux-mips@vger.kernel.org S: Maintained @@ -4064,10 +4005,10 @@ F: arch/mips/boot/dts/brcm/bcm*.dts* F: arch/mips/include/asm/mach-bmips/* F: arch/mips/kernel/*bmips* -F: drivers/soc/bcm/bcm63xx F: drivers/irqchip/irq-bcm63* F: drivers/irqchip/irq-bcm7* F: drivers/irqchip/irq-brcmstb* +F: drivers/soc/bcm/bcm63xx F: include/linux/bcm963xx_nvram.h F: include/linux/bcm963xx_tag.h @@ -4123,14 +4064,14 @@ BROADCOM BRCMSTB GPIO DRIVER M: Doug Berger -M: Florian Fainelli +M: Florian Fainelli R: Broadcom internal kernel review list S: Supported F: Documentation/devicetree/bindings/gpio/brcm,brcmstb-gpio.yaml F: drivers/gpio/gpio-brcmstb.c BROADCOM BRCMSTB I2C DRIVER -M: Kamal Dasu +M: Kamal Dasu R: Broadcom internal kernel review list L: linux-i2c@vger.kernel.org S: Supported @@ -4146,7 +4087,7 @@ F: drivers/tty/serial/8250/8250_bcm7271.c BROADCOM BRCMSTB USB EHCI DRIVER -M: Justin Chen +M: Justin Chen M: Al Cooper R: Broadcom internal kernel review list L: linux-usb@vger.kernel.org @@ -4163,7 +4104,7 @@ F: drivers/usb/misc/brcmstb-usb-pinmap.c BROADCOM BRCMSTB USB2 and USB3 PHY DRIVER -M: Justin Chen +M: Justin Chen M: Al Cooper R: Broadcom internal kernel review list L: linux-kernel@vger.kernel.org @@ -4181,8 +4122,15 @@ F: drivers/spi/spi-bcm63xx-hsspi.c F: drivers/spi/spi-bcmbca-hsspi.c +BROADCOM BCM6348/BCM6358 SPI controller DRIVER +M: Jonas Gorski +L: linux-spi@vger.kernel.org +S: Odd Fixes +F: Documentation/devicetree/bindings/spi/spi-bcm63xx.txt +F: drivers/spi/spi-bcm63xx.c + BROADCOM ETHERNET PHY DRIVERS -M: Florian Fainelli +M: Florian Fainelli R: Broadcom internal kernel review list L: netdev@vger.kernel.org S: Supported @@ -4193,7 +4141,7 @@ BROADCOM GENET ETHERNET DRIVER M: Doug Berger -M: Florian Fainelli +M: Florian Fainelli R: Broadcom internal kernel review list L: netdev@vger.kernel.org S: Supported @@ -4277,7 +4225,7 @@ BROADCOM PMB (POWER MANAGEMENT BUS) DRIVER M: RafaÅ‚ MiÅ‚ecki -M: Florian Fainelli +M: Florian Fainelli R: Broadcom internal kernel review list L: linux-pm@vger.kernel.org S: Maintained @@ -4293,7 +4241,7 @@ F: include/linux/bcma/ BROADCOM SPI DRIVER -M: Kamal Dasu +M: Kamal Dasu R: Broadcom internal kernel review list S: Maintained F: Documentation/devicetree/bindings/spi/brcm,spi-bcm-qspi.yaml @@ -4327,7 +4275,7 @@ BROADCOM STB NAND FLASH DRIVER M: Brian Norris -M: Kamal Dasu +M: Kamal Dasu R: Broadcom internal kernel review list L: linux-mtd@lists.infradead.org S: Maintained @@ -4337,7 +4285,7 @@ BROADCOM STB PCIE DRIVER M: Jim Quinlan M: Nicolas Saenz Julienne -M: Florian Fainelli +M: Florian Fainelli R: Broadcom internal kernel review list L: linux-pci@vger.kernel.org S: Maintained @@ -4345,13 +4293,13 @@ F: drivers/pci/controller/pcie-brcmstb.c BROADCOM SYSTEMPORT ETHERNET DRIVER -M: Florian Fainelli +M: Florian Fainelli R: Broadcom internal kernel review list L: netdev@vger.kernel.org S: Supported +F: Documentation/devicetree/bindings/net/brcm,systemport.yaml F: drivers/net/ethernet/broadcom/bcmsysport.* F: drivers/net/ethernet/broadcom/unimac.h -F: Documentation/devicetree/bindings/net/brcm,systemport.yaml BROADCOM TG3 GIGABIT ETHERNET DRIVER M: Siva Reddy Kallam @@ -4483,29 +4431,6 @@ F: Documentation/devicetree/bindings/net/ieee802154/ca8210.txt F: drivers/net/ieee802154/ca8210.c -CANAAN/KENDRYTE K210 SOC FPIOA DRIVER -M: Damien Le Moal -L: linux-riscv@lists.infradead.org -L: linux-gpio@vger.kernel.org (pinctrl driver) -F: Documentation/devicetree/bindings/pinctrl/canaan,k210-fpioa.yaml -F: drivers/pinctrl/pinctrl-k210.c - -CANAAN/KENDRYTE K210 SOC RESET CONTROLLER DRIVER -M: Damien Le Moal -L: linux-kernel@vger.kernel.org -L: linux-riscv@lists.infradead.org -S: Maintained -F: Documentation/devicetree/bindings/reset/canaan,k210-rst.yaml -F: drivers/reset/reset-k210.c - -CANAAN/KENDRYTE K210 SOC SYSTEM CONTROLLER DRIVER -M: Damien Le Moal -L: linux-riscv@lists.infradead.org -S: Maintained -F: Documentation/devicetree/bindings/mfd/canaan,k210-sysctl.yaml -F: drivers/soc/canaan/ -F: include/soc/canaan/ - CACHEFILES: FS-CACHE BACKEND FOR CACHING ON MOUNTED FILESYSTEMS M: David Howells L: linux-cachefs@redhat.com (moderated for non-subscribers) @@ -4513,6 +4438,13 @@ F: Documentation/filesystems/caching/cachefiles.rst F: fs/cachefiles/ +CACHESTAT: PAGE CACHE STATS FOR A FILE +M: Nhat Pham +M: Johannes Weiner +L: linux-mm@kvack.org +S: Maintained +F: tools/testing/selftests/cachestat/test_cachestat.c + CADENCE MIPI-CSI2 BRIDGES M: Maxime Ripard L: linux-media@vger.kernel.org @@ -4530,7 +4462,6 @@ M: Peter Chen M: Pawel Laszczak R: Roger Quadros -R: Aswath Govindraju L: linux-usb@vger.kernel.org S: Maintained T: git git://git.kernel.org/pub/scm/linux/kernel/git/peter.chen/usb.git @@ -4538,6 +4469,12 @@ F: drivers/usb/cdns3/ X: drivers/usb/cdns3/cdnsp* +CADENCE USBHS DRIVER +M: Pawel Laszczak +L: linux-usb@vger.kernel.org +S: Maintained +F: drivers/usb/gadget/udc/cdns2 + CADENCE USBSSP DRD IP DRIVER M: Pawel Laszczak L: linux-usb@vger.kernel.org @@ -4627,6 +4564,29 @@ F: include/uapi/linux/can/j1939.h F: net/can/j1939/ +CANAAN/KENDRYTE K210 SOC FPIOA DRIVER +M: Damien Le Moal +L: linux-riscv@lists.infradead.org +L: linux-gpio@vger.kernel.org (pinctrl driver) +F: Documentation/devicetree/bindings/pinctrl/canaan,k210-fpioa.yaml +F: drivers/pinctrl/pinctrl-k210.c + +CANAAN/KENDRYTE K210 SOC RESET CONTROLLER DRIVER +M: Damien Le Moal +L: linux-kernel@vger.kernel.org +L: linux-riscv@lists.infradead.org +S: Maintained +F: Documentation/devicetree/bindings/reset/canaan,k210-rst.yaml +F: drivers/reset/reset-k210.c + +CANAAN/KENDRYTE K210 SOC SYSTEM CONTROLLER DRIVER +M: Damien Le Moal +L: linux-riscv@lists.infradead.org +S: Maintained +F: Documentation/devicetree/bindings/mfd/canaan,k210-sysctl.yaml +F: drivers/soc/canaan/ +F: include/soc/canaan/ + CAPABILITIES M: Serge Hallyn L: linux-security-module@vger.kernel.org @@ -4686,8 +4646,8 @@ CBS/ETF/TAPRIO QDISCS M: Vinicius Costa Gomes -S: Maintained L: netdev@vger.kernel.org +S: Maintained F: net/sched/sch_cbs.c F: net/sched/sch_etf.c F: net/sched/sch_taprio.c @@ -4710,10 +4670,10 @@ M: Hadar Gat L: linux-crypto@vger.kernel.org S: Supported +W: https://developer.arm.com/products/system-ip/trustzone-cryptocell/cryptocell-700-family +F: Documentation/devicetree/bindings/rng/arm-cctrng.yaml F: drivers/char/hw_random/cctrng.c F: drivers/char/hw_random/cctrng.h -F: Documentation/devicetree/bindings/rng/arm-cctrng.yaml -W: https://developer.arm.com/products/system-ip/trustzone-cryptocell/cryptocell-700-family CEC FRAMEWORK M: Hans Verkuil @@ -4873,13 +4833,6 @@ F: Documentation/devicetree/bindings/sound/google,cros-ec-codec.yaml F: sound/soc/codecs/cros_ec_codec.* -CHROMEOS EC UART DRIVER -M: Bhanu Prakash Maiya -R: Benson Leung -R: Tzung-Bi Shih -S: Maintained -F: drivers/platform/chrome/cros_ec_uart.c - CHROMEOS EC SUBDRIVERS M: Benson Leung R: Guenter Roeck @@ -4889,13 +4842,12 @@ N: cros_ec N: cros-ec -CHROMEOS EC USB TYPE-C DRIVER -M: Prashant Malani -L: chrome-platform@lists.linux.dev +CHROMEOS EC UART DRIVER +M: Bhanu Prakash Maiya +R: Benson Leung +R: Tzung-Bi Shih S: Maintained -F: drivers/platform/chrome/cros_ec_typec.* -F: drivers/platform/chrome/cros_typec_switch.c -F: drivers/platform/chrome/cros_typec_vdm.* +F: drivers/platform/chrome/cros_ec_uart.c CHROMEOS EC USB PD NOTIFY DRIVER M: Prashant Malani @@ -4904,6 +4856,14 @@ F: drivers/platform/chrome/cros_usbpd_notify.c F: include/linux/platform_data/cros_usbpd_notify.h +CHROMEOS EC USB TYPE-C DRIVER +M: Prashant Malani +L: chrome-platform@lists.linux.dev +S: Maintained +F: drivers/platform/chrome/cros_ec_typec.* +F: drivers/platform/chrome/cros_typec_switch.c +F: drivers/platform/chrome/cros_typec_vdm.* + CHROMEOS HPS DRIVER M: Dan Callaghan R: Sami Kyöstilä @@ -4921,7 +4881,6 @@ CIRRUS LOGIC AUDIO CODEC DRIVERS M: James Schulman M: David Rhodes -M: Lucas Tanure M: Richard Fitzgerald L: alsa-devel@alsa-project.org (moderated for non-subscribers) L: patches@opensource.cirrus.com @@ -5021,6 +4980,18 @@ S: Supported F: drivers/infiniband/hw/usnic/ +CLANG CONTROL FLOW INTEGRITY SUPPORT +M: Sami Tolvanen +M: Kees Cook +R: Nathan Chancellor +R: Nick Desaulniers +L: llvm@lists.linux.dev +S: Supported +B: https://github.com/ClangBuiltLinux/linux/issues +T: git git://git.kernel.org/pub/scm/linux/kernel/git/kees/linux.git for-next/hardening +F: include/linux/cfi.h +F: kernel/cfi.c + CLANG-FORMAT FILE M: Miguel Ojeda S: Maintained @@ -5041,18 +5012,6 @@ F: scripts/clang-tools/ K: \b(?i:clang|llvm)\b -CLANG CONTROL FLOW INTEGRITY SUPPORT -M: Sami Tolvanen -M: Kees Cook -R: Nathan Chancellor -R: Nick Desaulniers -L: llvm@lists.linux.dev -S: Supported -B: https://github.com/ClangBuiltLinux/linux/issues -T: git git://git.kernel.org/pub/scm/linux/kernel/git/kees/linux.git for-next/hardening -F: include/linux/cfi.h -F: kernel/cfi.c - CLK API M: Russell King L: linux-clk@vger.kernel.org @@ -5143,7 +5102,7 @@ COMMON INTERNET FILE SYSTEM CLIENT (CIFS and SMB3) M: Steve French -R: Paulo Alcantara (DFS, global name space) +R: Paulo Alcantara (DFS, global name space) R: Ronnie Sahlberg (directory leases, sparse files) R: Shyam Prasad N (multichannel) R: Tom Talpey (RDMA, smbdirect) @@ -5153,8 +5112,8 @@ W: https://wiki.samba.org/index.php/LinuxCIFS T: git git://git.samba.org/sfrench/cifs-2.6.git F: Documentation/admin-guide/cifs/ -F: fs/cifs/ -F: fs/smbfs_common/ +F: fs/smb/client/ +F: fs/smb/common/ F: include/uapi/linux/cifs COMPACTPCI HOTPLUG CORE @@ -5188,16 +5147,25 @@ F: include/linux/compiler_attributes.h COMPUTE EXPRESS LINK (CXL) +M: Davidlohr Bueso +M: Jonathan Cameron +M: Dave Jiang M: Alison Schofield M: Vishal Verma M: Ira Weiny -M: Ben Widawsky M: Dan Williams L: linux-cxl@vger.kernel.org S: Maintained F: drivers/cxl/ F: include/uapi/linux/cxl_mem.h +COMPUTE EXPRESS LINK PMU (CPMU) +M: Jonathan Cameron +L: linux-cxl@vger.kernel.org +S: Maintained +F: Documentation/admin-guide/perf/cxl.rst +F: drivers/perf/cxl_pmu.c + CONEXANT ACCESSRUNNER USB DRIVER L: accessrunner-general@lists.sourceforge.net S: Orphan @@ -5223,8 +5191,8 @@ M: Frederic Weisbecker M: "Paul E. McKenney" S: Maintained -F: kernel/context_tracking.c F: include/linux/context_tracking* +F: kernel/context_tracking.c CONTROL GROUP (CGROUP) M: Tejun Heo @@ -5348,6 +5316,18 @@ F: kernel/sched/cpufreq*.c F: tools/testing/selftests/cpufreq/ +CPU HOTPLUG +M: Thomas Gleixner +M: Peter Zijlstra +L: linux-kernel@vger.kernel.org +S: Maintained +T: git git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip.git smp/core +F: include/linux/cpu.h +F: include/linux/cpuhotplug.h +F: include/linux/smpboot.h +F: kernel/cpu.c +F: kernel/smpboot.* + CPU IDLE TIME MANAGEMENT FRAMEWORK M: "Rafael J. Wysocki" M: Daniel Lezcano @@ -5385,8 +5365,8 @@ CPUIDLE DRIVER - ARM EXYNOS M: Daniel Lezcano -R: Krzysztof Kozlowski M: Kukjin Kim +R: Krzysztof Kozlowski L: linux-pm@vger.kernel.org L: linux-samsung-soc@vger.kernel.org S: Supported @@ -5407,8 +5387,8 @@ L: linux-pm@vger.kernel.org L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) S: Supported -F: drivers/cpuidle/cpuidle-psci.h F: drivers/cpuidle/cpuidle-psci-domain.c +F: drivers/cpuidle/cpuidle-psci.h CPUIDLE DRIVER - DT IDLE PM DOMAIN M: Ulf Hansson @@ -5481,8 +5461,7 @@ F: drivers/net/can/ctucanfd/ CW1200 WLAN driver -M: Solomon Peachy -S: Maintained +S: Orphan F: drivers/net/wireless/st/cw1200/ CX18 VIDEO4LINUX DRIVER @@ -5552,19 +5531,19 @@ W: http://www.chelsio.com F: drivers/crypto/chelsio -CXGB4 INLINE CRYPTO DRIVER -M: Ayush Sawal +CXGB4 ETHERNET DRIVER (CXGB4) +M: Raju Rangoju L: netdev@vger.kernel.org S: Supported W: http://www.chelsio.com -F: drivers/net/ethernet/chelsio/inline_crypto/ +F: drivers/net/ethernet/chelsio/cxgb4/ -CXGB4 ETHERNET DRIVER (CXGB4) -M: Raju Rangoju +CXGB4 INLINE CRYPTO DRIVER +M: Ayush Sawal L: netdev@vger.kernel.org S: Supported W: http://www.chelsio.com -F: drivers/net/ethernet/chelsio/cxgb4/ +F: drivers/net/ethernet/chelsio/inline_crypto/ CXGB4 ISCSI DRIVER (CXGB4I) M: Varun Prakash @@ -5621,16 +5600,6 @@ S: Orphan F: drivers/net/wan/pc300* -CYPRESS_FIRMWARE MEDIA DRIVER -M: Antti Palosaari -L: linux-media@vger.kernel.org -S: Maintained -W: https://linuxtv.org -W: http://palosaari.fi/linux/ -Q: http://patchwork.linuxtv.org/project/linux-media/list/ -T: git git://linuxtv.org/anttip/media_tree.git -F: drivers/media/common/cypress_firmware* - CYPRESS CY8C95X0 PINCTRL DRIVER M: Patrick Rudolph L: linux-gpio@vger.kernel.org @@ -5650,6 +5619,16 @@ F: Documentation/devicetree/bindings/input/cypress-sf.yaml F: drivers/input/keyboard/cypress-sf.c +CYPRESS_FIRMWARE MEDIA DRIVER +M: Antti Palosaari +L: linux-media@vger.kernel.org +S: Maintained +W: https://linuxtv.org +W: http://palosaari.fi/linux/ +Q: http://patchwork.linuxtv.org/project/linux-media/list/ +T: git git://linuxtv.org/anttip/media_tree.git +F: drivers/media/common/cypress_firmware* + CYTTSP TOUCHSCREEN DRIVER M: Linus Walleij L: linux-input@vger.kernel.org @@ -5716,10 +5695,7 @@ M: Oliver Neukum M: Ali Akcaagac M: Jamie Lenehan -L: dc395x@twibble.org S: Maintained -W: http://twibble.org/dist/dc395x/ -W: http://lists.twibble.org/mailman/listinfo/dc395x/ F: Documentation/scsi/dc395x.rst F: drivers/scsi/dc395x.* @@ -5732,6 +5708,14 @@ F: include/uapi/linux/dccp.h F: net/dccp/ +DEBUGOBJECTS: +M: Thomas Gleixner +L: linux-kernel@vger.kernel.org +S: Maintained +T: git git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip.git core/debugobjects +F: include/linux/debugobjects.h +F: lib/debugobjects.c + DECSTATION PLATFORM SUPPORT M: "Maciej W. Rozycki" L: linux-mips@vger.kernel.org @@ -5816,25 +5800,25 @@ F: Documentation/driver-api/dcdbas.rst F: drivers/platform/x86/dell/dcdbas.* -DELL WMI DESCRIPTOR DRIVER -L: Dell.Client.Kernel@dell.com -S: Maintained -F: drivers/platform/x86/dell/dell-wmi-descriptor.c - DELL WMI DDV DRIVER M: Armin Wolf S: Maintained F: Documentation/ABI/testing/debugfs-dell-wmi-ddv F: Documentation/ABI/testing/sysfs-platform-dell-wmi-ddv +F: Documentation/wmi/devices/dell-wmi-ddv.rst F: drivers/platform/x86/dell/dell-wmi-ddv.c -DELL WMI SYSMAN DRIVER -M: Prasanth Ksr +DELL WMI DESCRIPTOR DRIVER +L: Dell.Client.Kernel@dell.com +S: Maintained +F: drivers/platform/x86/dell/dell-wmi-descriptor.c + +DELL WMI HARDWARE PRIVACY SUPPORT +M: Perry Yuan L: Dell.Client.Kernel@dell.com L: platform-driver-x86@vger.kernel.org S: Maintained -F: Documentation/ABI/testing/sysfs-class-firmware-attributes -F: drivers/platform/x86/dell/dell-wmi-sysman/ +F: drivers/platform/x86/dell/dell-wmi-privacy.c DELL WMI NOTIFICATIONS DRIVER M: Matthew Garrett @@ -5842,20 +5826,13 @@ S: Maintained F: drivers/platform/x86/dell/dell-wmi-base.c -DELL WMI HARDWARE PRIVACY SUPPORT -M: Perry Yuan +DELL WMI SYSMAN DRIVER +M: Prasanth Ksr L: Dell.Client.Kernel@dell.com L: platform-driver-x86@vger.kernel.org S: Maintained -F: drivers/platform/x86/dell/dell-wmi-privacy.c - -DELTA ST MEDIA DRIVER -M: Hugues Fruchet -L: linux-media@vger.kernel.org -S: Supported -W: https://linuxtv.org -T: git git://linuxtv.org/media_tree.git -F: drivers/media/platform/st/sti/delta +F: Documentation/ABI/testing/sysfs-class-firmware-attributes +F: drivers/platform/x86/dell/dell-wmi-sysman/ DELTA AHE-50DC FAN CONTROL MODULE DRIVER M: Zev Weiss @@ -5879,25 +5856,28 @@ F: drivers/gpio/gpio-tn48m.c F: include/dt-bindings/reset/delta,tn48m-reset.h +DELTA ST MEDIA DRIVER +M: Hugues Fruchet +L: linux-media@vger.kernel.org +S: Supported +W: https://linuxtv.org +T: git git://linuxtv.org/media_tree.git +F: drivers/media/platform/st/sti/delta + DENALI NAND DRIVER L: linux-mtd@lists.infradead.org S: Orphan F: drivers/mtd/nand/raw/denali* DESIGNWARE EDMA CORE IP DRIVER -M: Gustavo Pimentel +M: Manivannan Sadhasivam +R: Gustavo Pimentel +R: Serge Semin L: dmaengine@vger.kernel.org S: Maintained F: drivers/dma/dw-edma/ F: include/linux/dma/edma.h -DESIGNWARE XDATA IP DRIVER -M: Gustavo Pimentel -L: linux-pci@vger.kernel.org -S: Maintained -F: Documentation/misc-devices/dw-xdata-pcie.rst -F: drivers/misc/dw-xdata-pcie.c - DESIGNWARE USB2 DRD IP DRIVER M: Minas Harutyunyan L: linux-usb@vger.kernel.org @@ -5911,6 +5891,13 @@ S: Maintained F: drivers/usb/dwc3/ +DESIGNWARE XDATA IP DRIVER +M: Gustavo Pimentel +L: linux-pci@vger.kernel.org +S: Maintained +F: Documentation/misc-devices/dw-xdata-pcie.rst +F: drivers/misc/dw-xdata-pcie.c + DEVANTECH SRF ULTRASONIC RANGER IIO DRIVER M: Andreas Klinger L: linux-iio@vger.kernel.org @@ -6002,15 +5989,15 @@ M: Christoph Niedermaier L: kernel@dh-electronics.com S: Maintained -F: arch/arm/boot/dts/imx6*-dhcom-* -F: arch/arm/boot/dts/imx6*-dhcor-* +F: arch/arm/boot/dts/nxp/imx/imx6*-dhcom-* +F: arch/arm/boot/dts/nxp/imx/imx6*-dhcor-* DH ELECTRONICS STM32MP1 DHCOM/DHCOR BOARD SUPPORT M: Marek Vasut L: kernel@dh-electronics.com S: Maintained -F: arch/arm/boot/dts/stm32mp1*-dhcom-* -F: arch/arm/boot/dts/stm32mp1*-dhcor-* +F: arch/arm/boot/dts/st/stm32mp1*-dhcom-* +F: arch/arm/boot/dts/st/stm32mp1*-dhcor-* DIALOG SEMICONDUCTOR DRIVERS M: Support Opensource @@ -6019,9 +6006,9 @@ F: Documentation/devicetree/bindings/input/da90??-onkey.txt F: Documentation/devicetree/bindings/input/dlg,da72??.txt F: Documentation/devicetree/bindings/mfd/da90*.txt -F: Documentation/devicetree/bindings/mfd/da90*.yaml -F: Documentation/devicetree/bindings/regulator/dlg,da9*.yaml +F: Documentation/devicetree/bindings/mfd/dlg,da90*.yaml F: Documentation/devicetree/bindings/regulator/da92*.txt +F: Documentation/devicetree/bindings/regulator/dlg,da9*.yaml F: Documentation/devicetree/bindings/regulator/slg51000.txt F: Documentation/devicetree/bindings/sound/da[79]*.txt F: Documentation/devicetree/bindings/thermal/da90??-thermal.txt @@ -6140,6 +6127,12 @@ F: include/linux/dmaengine.h F: include/linux/of_dma.h +DMA MAPPING BENCHMARK +M: Xiang Chen +L: iommu@lists.linux.dev +F: kernel/dma/map_benchmark.c +F: tools/testing/selftests/dma/ + DMA MAPPING HELPERS M: Christoph Hellwig M: Marek Szyprowski @@ -6150,17 +6143,11 @@ T: git git://git.infradead.org/users/hch/dma-mapping.git F: include/asm-generic/dma-mapping.h F: include/linux/dma-direct.h -F: include/linux/dma-mapping.h F: include/linux/dma-map-ops.h +F: include/linux/dma-mapping.h F: include/linux/swiotlb.h F: kernel/dma/ -DMA MAPPING BENCHMARK -M: Xiang Chen -L: iommu@lists.linux.dev -F: kernel/dma/map_benchmark.c -F: tools/testing/selftests/dma/ - DMA-BUF HEAPS FRAMEWORK M: Sumit Semwal R: Benjamin Gaignard @@ -6218,10 +6205,17 @@ X: Documentation/driver-api/media/ X: Documentation/firmware-guide/acpi/ X: Documentation/i2c/ +X: Documentation/netlink/ X: Documentation/power/ X: Documentation/spi/ X: Documentation/userspace-api/media/ +DOCUMENTATION PROCESS +M: Jonathan Corbet +L: workflows@vger.kernel.org +S: Maintained +F: Documentation/process/ + DOCUMENTATION REPORTING ISSUES M: Thorsten Leemhuis L: linux-doc@vger.kernel.org @@ -6350,6 +6344,25 @@ F: drivers/soc/ti/smartreflex.c F: include/linux/power/smartreflex.h +DRM ACCEL DRIVERS FOR INTEL VPU +M: Jacek Lawrynowicz +M: Stanislaw Gruszka +L: dri-devel@lists.freedesktop.org +S: Supported +T: git git://anongit.freedesktop.org/drm/drm-misc +F: drivers/accel/ivpu/ +F: include/uapi/drm/ivpu_accel.h + +DRM COMPUTE ACCELERATORS DRIVERS AND FRAMEWORK +M: Oded Gabbay +L: dri-devel@lists.freedesktop.org +S: Maintained +C: irc://irc.oftc.net/dri-devel +T: git https://git.kernel.org/pub/scm/linux/kernel/git/ogabbay/accel.git +F: Documentation/accel/ +F: drivers/accel/ +F: include/drm/drm_accel.h + DRM DRIVER FOR ALLWINNER DE2 AND DE3 ENGINE M: Maxime Ripard M: Chen-Yu Tsai @@ -6432,6 +6445,21 @@ F: Documentation/devicetree/bindings/display/panel/feiyang,fy07024di26a30d.yaml F: drivers/gpu/drm/panel/panel-feiyang-fy07024di26a30d.c +DRM DRIVER FOR FIRMWARE FRAMEBUFFERS +M: Thomas Zimmermann +M: Javier Martinez Canillas +L: dri-devel@lists.freedesktop.org +S: Maintained +T: git git://anongit.freedesktop.org/drm/drm-misc +F: drivers/gpu/drm/drm_aperture.c +F: drivers/gpu/drm/tiny/ofdrm.c +F: drivers/gpu/drm/tiny/simpledrm.c +F: drivers/video/aperture.c +F: drivers/video/nomodeset.c +F: include/drm/drm_aperture.h +F: include/linux/aperture.h +F: include/video/nomodeset.h + DRM DRIVER FOR GENERIC EDP PANELS R: Douglas Anderson F: Documentation/devicetree/bindings/display/panel/panel-edp.yaml @@ -6466,6 +6494,14 @@ F: Documentation/devicetree/bindings/display/himax,hx8357d.txt F: drivers/gpu/drm/tiny/hx8357d.c +DRM DRIVER FOR HYPERV SYNTHETIC VIDEO DEVICE +M: Deepak Rawat +L: linux-hyperv@vger.kernel.org +L: dri-devel@lists.freedesktop.org +S: Maintained +T: git git://anongit.freedesktop.org/drm/drm-misc +F: drivers/gpu/drm/hyperv + DRM DRIVER FOR ILITEK ILI9225 PANELS M: David Lechner S: Maintained @@ -6495,11 +6531,11 @@ DRM DRIVER FOR LVDS PANELS M: Laurent Pinchart L: dri-devel@lists.freedesktop.org -T: git git://anongit.freedesktop.org/drm/drm-misc S: Maintained -F: drivers/gpu/drm/panel/panel-lvds.c +T: git git://anongit.freedesktop.org/drm/drm-misc F: Documentation/devicetree/bindings/display/lvds.yaml F: Documentation/devicetree/bindings/display/panel/panel-lvds.yaml +F: drivers/gpu/drm/panel/panel-lvds.c DRM DRIVER FOR MANTIX MLAF057WE51 PANELS M: Guido Günther @@ -6536,6 +6572,7 @@ M: Abhinav Kumar M: Dmitry Baryshkov R: Sean Paul +R: Marijn Suijten L: linux-arm-msm@vger.kernel.org L: dri-devel@lists.freedesktop.org L: freedreno@lists.freedesktop.org @@ -6608,13 +6645,6 @@ F: Documentation/devicetree/bindings/display/repaper.txt F: drivers/gpu/drm/tiny/repaper.c -DRM DRIVER FOR SOLOMON SSD130X OLED DISPLAYS -M: Javier Martinez Canillas -S: Maintained -T: git git://anongit.freedesktop.org/drm/drm-misc -F: Documentation/devicetree/bindings/display/solomon,ssd1307fb.yaml -F: drivers/gpu/drm/solomon/ssd130x* - DRM DRIVER FOR QEMU'S CIRRUS DEVICE M: Dave Airlie M: Gerd Hoffmann @@ -6663,28 +6693,11 @@ F: Documentation/devicetree/bindings/display/panel/samsung,s6d27a1.yaml F: drivers/gpu/drm/panel/panel-samsung-s6d27a1.c -DRM DRIVER FOR SITRONIX ST7703 PANELS -M: Guido Günther -R: Purism Kernel Team -R: Ondrej Jirman +DRM DRIVER FOR SAMSUNG S6D7AA0 PANELS +M: Artur Weber S: Maintained -F: Documentation/devicetree/bindings/display/panel/rocktech,jh057n00900.yaml -F: drivers/gpu/drm/panel/panel-sitronix-st7703.c - -DRM DRIVER FOR FIRMWARE FRAMEBUFFERS -M: Thomas Zimmermann -M: Javier Martinez Canillas -L: dri-devel@lists.freedesktop.org -S: Maintained -T: git git://anongit.freedesktop.org/drm/drm-misc -F: drivers/gpu/drm/drm_aperture.c -F: drivers/gpu/drm/tiny/ofdrm.c -F: drivers/gpu/drm/tiny/simpledrm.c -F: drivers/video/aperture.c -F: drivers/video/nomodeset.c -F: include/drm/drm_aperture.h -F: include/linux/aperture.h -F: include/video/nomodeset.h +F: Documentation/devicetree/bindings/display/panel/samsung,s6d7aa0.yaml +F: drivers/gpu/drm/panel/panel-samsung-s6d7aa0.c DRM DRIVER FOR SITRONIX ST7586 PANELS M: David Lechner @@ -6699,6 +6712,14 @@ F: Documentation/devicetree/bindings/display/panel/sitronix,st7701.yaml F: drivers/gpu/drm/panel/panel-sitronix-st7701.c +DRM DRIVER FOR SITRONIX ST7703 PANELS +M: Guido Günther +R: Purism Kernel Team +R: Ondrej Jirman +S: Maintained +F: Documentation/devicetree/bindings/display/panel/rocktech,jh057n00900.yaml +F: drivers/gpu/drm/panel/panel-sitronix-st7703.c + DRM DRIVER FOR SITRONIX ST7735R PANELS M: David Lechner S: Maintained @@ -6706,6 +6727,13 @@ F: Documentation/devicetree/bindings/display/sitronix,st7735r.yaml F: drivers/gpu/drm/tiny/st7735r.c +DRM DRIVER FOR SOLOMON SSD130X OLED DISPLAYS +M: Javier Martinez Canillas +S: Maintained +T: git git://anongit.freedesktop.org/drm/drm-misc +F: Documentation/devicetree/bindings/display/solomon,ssd1307fb.yaml +F: drivers/gpu/drm/solomon/ssd130x* + DRM DRIVER FOR ST-ERICSSON MCDE M: Linus Walleij S: Maintained @@ -6743,6 +6771,7 @@ DRM DRIVER FOR VIRTUAL KERNEL MODESETTING (VKMS) M: Rodrigo Siqueira M: Melissa Wen +M: Maíra Canal R: Haneen Mohammed R: Daniel Vetter L: dri-devel@lists.freedesktop.org @@ -6804,25 +6833,6 @@ F: include/linux/vga* F: include/uapi/drm/drm* -DRM COMPUTE ACCELERATORS DRIVERS AND FRAMEWORK -M: Oded Gabbay -L: dri-devel@lists.freedesktop.org -S: Maintained -C: irc://irc.oftc.net/dri-devel -T: git https://git.kernel.org/pub/scm/linux/kernel/git/ogabbay/accel.git -F: Documentation/accel/ -F: drivers/accel/ -F: include/drm/drm_accel.h - -DRM ACCEL DRIVERS FOR INTEL VPU -M: Jacek Lawrynowicz -M: Stanislaw Gruszka -L: dri-devel@lists.freedesktop.org -S: Supported -T: git git://anongit.freedesktop.org/drm/drm-misc -F: drivers/accel/ivpu/ -F: include/uapi/drm/ivpu_accel.h - DRM DRIVERS FOR ALLWINNER A10 M: Maxime Ripard M: Chen-Yu Tsai @@ -6864,6 +6874,7 @@ T: git git://anongit.freedesktop.org/drm/drm-misc F: Documentation/devicetree/bindings/display/bridge/ F: drivers/gpu/drm/bridge/ +F: drivers/gpu/drm/drm_bridge.c F: include/drm/drm_bridge.h DRM DRIVERS FOR EXYNOS @@ -6926,14 +6937,6 @@ F: Documentation/devicetree/bindings/display/hisilicon/ F: drivers/gpu/drm/hisilicon/ -DRM DRIVER FOR HYPERV SYNTHETIC VIDEO DEVICE -M: Deepak Rawat -L: linux-hyperv@vger.kernel.org -L: dri-devel@lists.freedesktop.org -S: Maintained -T: git git://anongit.freedesktop.org/drm/drm-misc -F: drivers/gpu/drm/hyperv - DRM DRIVERS FOR LIMA M: Qiang Yu L: dri-devel@lists.freedesktop.org @@ -6980,8 +6983,7 @@ F: Documentation/devicetree/bindings/display/bridge/renesas,dw-hdmi.yaml F: Documentation/devicetree/bindings/display/bridge/renesas,lvds.yaml F: Documentation/devicetree/bindings/display/renesas,du.yaml -F: drivers/gpu/drm/rcar-du/ -F: drivers/gpu/drm/shmobile/ +F: drivers/gpu/drm/renesas/ F: include/linux/platform_data/shmob_drm.h DRM DRIVERS FOR ROCKCHIP @@ -7077,7 +7079,6 @@ F: drivers/gpu/drm/xen/ DRM DRIVERS FOR XILINX -M: Hyun Kwon M: Laurent Pinchart L: dri-devel@lists.freedesktop.org S: Maintained @@ -7085,6 +7086,14 @@ F: Documentation/devicetree/bindings/display/xlnx/ F: drivers/gpu/drm/xlnx/ +DRM GPU SCHEDULER +M: Luben Tuikov +L: dri-devel@lists.freedesktop.org +S: Maintained +T: git git://anongit.freedesktop.org/drm/drm-misc +F: drivers/gpu/drm/scheduler/ +F: include/drm/gpu_scheduler.h + DRM PANEL DRIVERS M: Neil Armstrong R: Sam Ravnborg @@ -7113,14 +7122,6 @@ F: drivers/gpu/drm/ttm/ F: include/drm/ttm/ -DRM GPU SCHEDULER -M: Luben Tuikov -L: dri-devel@lists.freedesktop.org -S: Maintained -T: git git://anongit.freedesktop.org/drm/drm-misc -F: drivers/gpu/drm/scheduler/ -F: include/drm/gpu_scheduler.h - DSBR100 USB FM RADIO DRIVER M: Alexey Klimov L: linux-media@vger.kernel.org @@ -7248,10 +7249,10 @@ DYNAMIC DEBUG M: Jason Baron +M: Jim Cromie S: Maintained F: include/linux/dynamic_debug.h F: lib/dynamic_debug.c -M: Jim Cromie F: lib/test_dynamic_debug.c DYNAMIC INTERRUPT MODERATION @@ -7261,6 +7262,15 @@ F: include/linux/dim.h F: lib/dim/ +DYNAMIC THERMAL POWER MANAGEMENT (DTPM) +M: Daniel Lezcano +L: linux-pm@vger.kernel.org +S: Supported +B: https://bugzilla.kernel.org +T: git git://git.kernel.org/pub/scm/linux/kernel/git/rafael/linux-pm +F: drivers/powercap/dtpm* +F: include/linux/dtpm.h + DZ DECSTATION DZ11 SERIAL DRIVER M: "Maciej W. Rozycki" S: Maintained @@ -7468,6 +7478,14 @@ S: Maintained F: drivers/edac/mpc85xx_edac.[ch] +EDAC-NPCM +M: Marvin Lin +M: Stanley Chu +L: linux-edac@vger.kernel.org +S: Maintained +F: Documentation/devicetree/bindings/memory-controllers/nuvoton,npcm-memory-controller.yaml +F: drivers/edac/npcm_edac.c + EDAC-PASEMI M: Egor Martovetsky L: linux-edac@vger.kernel.org @@ -7599,22 +7617,22 @@ F: drivers/infiniband/hw/ocrdma/ F: include/uapi/rdma/ocrdma-abi.h -EMULEX/BROADCOM LPFC FC/FCOE SCSI DRIVER +EMULEX/BROADCOM EFCT FC/FCOE SCSI TARGET DRIVER M: James Smart -M: Dick Kennedy +M: Ram Vegesna L: linux-scsi@vger.kernel.org +L: target-devel@vger.kernel.org S: Supported W: http://www.broadcom.com -F: drivers/scsi/lpfc/ +F: drivers/scsi/elx/ -EMULEX/BROADCOM EFCT FC/FCOE SCSI TARGET DRIVER +EMULEX/BROADCOM LPFC FC/FCOE SCSI DRIVER M: James Smart -M: Ram Vegesna +M: Dick Kennedy L: linux-scsi@vger.kernel.org -L: target-devel@vger.kernel.org S: Supported W: http://www.broadcom.com -F: drivers/scsi/elx/ +F: drivers/scsi/lpfc/ ENE CB710 FLASH CARD READER DRIVER M: MichaÅ‚ MirosÅ‚aw @@ -7707,8 +7725,8 @@ F: drivers/net/pcs/ F: drivers/net/phy/ F: include/dt-bindings/net/qca-ar803x.h -F: include/linux/linkmode.h F: include/linux/*mdio*.h +F: include/linux/linkmode.h F: include/linux/mdio/*.h F: include/linux/mii.h F: include/linux/of_net.h @@ -7771,8 +7789,8 @@ L: linux-integrity@vger.kernel.org S: Supported T: git git://git.kernel.org/pub/scm/linux/kernel/git/zohar/linux-integrity.git -F: security/integrity/evm/ F: security/integrity/ +F: security/integrity/evm/ EXTENSIBLE FIRMWARE INTERFACE (EFI) M: Ard Biesheuvel @@ -7803,8 +7821,8 @@ M: Masami Hiramatsu L: linux-kernel@vger.kernel.org L: linux-trace-kernel@vger.kernel.org -Q: https://patchwork.kernel.org/project/linux-trace-kernel/list/ S: Maintained +Q: https://patchwork.kernel.org/project/linux-trace-kernel/list/ T: git git://git.kernel.org/pub/scm/linux/kernel/git/trace/linux-trace.git F: Documentation/admin-guide/bootconfig.rst F: fs/proc/bootconfig.c @@ -7964,6 +7982,12 @@ F: drivers/hwmon/f75375s.c F: include/linux/f75375s.h +FINTEK F81604 USB to 2xCANBUS DEVICE DRIVER +M: Ji-Ze Hong (Peter Hong) +L: linux-can@vger.kernel.org +S: Maintained +F: drivers/net/can/usb/f81604.c + FIREWIRE AUDIO DRIVERS and IEC 61883-1/6 PACKET STREAMING ENGINE M: Clemens Ladisch M: Takashi Sakamoto @@ -8059,6 +8083,7 @@ F: include/linux/fortify-string.h F: lib/fortify_kunit.c F: lib/memcpy_kunit.c +F: lib/strcat_kunit.c F: lib/strscpy_kunit.c F: lib/test_fortify/* F: scripts/test_fortify.sh @@ -8091,21 +8116,6 @@ F: drivers/fpga/ F: include/linux/fpga/ -INTEL MAX10 BMC SECURE UPDATES -M: Russ Weight -L: linux-fpga@vger.kernel.org -S: Maintained -F: Documentation/ABI/testing/sysfs-driver-intel-m10-bmc-sec-update -F: drivers/fpga/intel-m10-bmc-sec-update.c - -MICROCHIP POLARFIRE FPGA DRIVERS -M: Conor Dooley -R: Ivan Bornyakov -L: linux-fpga@vger.kernel.org -S: Supported -F: Documentation/devicetree/bindings/fpga/microchip,mpf-spi-fpga-mgr.yaml -F: drivers/fpga/microchip-spi.c - FPU EMULATOR M: Bill Metzenthen S: Maintained @@ -8114,9 +8124,9 @@ FRAMEBUFFER CORE M: Daniel Vetter -F: drivers/video/fbdev/core/ S: Odd Fixes T: git git://anongit.freedesktop.org/drm/drm-misc +F: drivers/video/fbdev/core/ FRAMEBUFFER LAYER M: Helge Deller @@ -8171,6 +8181,7 @@ FREESCALE ENETC ETHERNET DRIVERS M: Claudiu Manoil +M: Vladimir Oltean L: netdev@vger.kernel.org S: Maintained F: drivers/net/ethernet/freescale/enetc/ @@ -8493,15 +8504,15 @@ R: Mark Rutland L: linux-kernel@vger.kernel.org L: linux-trace-kernel@vger.kernel.org -Q: https://patchwork.kernel.org/project/linux-trace-kernel/list/ S: Maintained +Q: https://patchwork.kernel.org/project/linux-trace-kernel/list/ T: git git://git.kernel.org/pub/scm/linux/kernel/git/trace/linux-trace.git F: Documentation/trace/ftrace* -F: kernel/trace/ftrace* -F: kernel/trace/fgraph.c F: arch/*/*/*/*ftrace* F: arch/*/*/*ftrace* F: include/*/ftrace.h +F: kernel/trace/fgraph.c +F: kernel/trace/ftrace* F: samples/ftrace FUNGIBLE ETHERNET DRIVERS @@ -8542,10 +8553,10 @@ M: Tim Harvey S: Maintained F: Documentation/devicetree/bindings/mfd/gateworks-gsc.yaml -F: drivers/mfd/gateworks-gsc.c -F: include/linux/mfd/gsc.h F: Documentation/hwmon/gsc-hwmon.rst F: drivers/hwmon/gsc-hwmon.c +F: drivers/mfd/gateworks-gsc.c +F: include/linux/mfd/gsc.h F: include/linux/platform_data/gsc_hwmon.h GCC PLUGINS @@ -8669,12 +8680,18 @@ F: drivers/input/touchscreen/resistive-adc-touch.c GENERIC STRING LIBRARY +M: Kees Cook R: Andy Shevchenko -S: Maintained +L: linux-hardening@vger.kernel.org +S: Supported +T: git git://git.kernel.org/pub/scm/linux/kernel/git/kees/linux.git for-next/hardening +F: include/linux/string.h +F: include/linux/string_choices.h +F: include/linux/string_helpers.h F: lib/string.c F: lib/string_helpers.c -F: lib/test_string.c F: lib/test-string_helpers.c +F: lib/test_string.c GENERIC UIO DRIVER FOR PCI DEVICES M: "Michael S. Tsirkin" @@ -8795,10 +8812,12 @@ S: Maintained F: drivers/gpio/gpio-regmap.c F: include/linux/gpio/regmap.h +K: (devm_)?gpio_regmap_(un)?register GPIO SUBSYSTEM M: Linus Walleij M: Bartosz Golaszewski +R: Andy Shevchenko L: linux-gpio@vger.kernel.org S: Maintained T: git git://git.kernel.org/pub/scm/linux/kernel/git/brgl/linux.git @@ -9157,18 +9176,11 @@ S: Maintained F: drivers/hid/hid-logitech-* -HID++ LOGITECH DRIVERS -R: Filipe Laíns -R: Bastien Nocera +HID NVIDIA SHIELD DRIVER +M: Rahul Rameshbabu L: linux-input@vger.kernel.org S: Maintained -F: drivers/hid/hid-logitech-hidpp.c - -HID PLAYSTATION DRIVER -M: Roderick Colenbrander -L: linux-input@vger.kernel.org -S: Supported -F: drivers/hid/hid-playstation.c +F: drivers/hid/hid-nvidia-shield.c HID PHOENIX RC FLIGHT CONTROLLER M: Marcus Folkesson @@ -9176,6 +9188,12 @@ S: Maintained F: drivers/hid/hid-pxrc.c +HID PLAYSTATION DRIVER +M: Roderick Colenbrander +L: linux-input@vger.kernel.org +S: Supported +F: drivers/hid/hid-playstation.c + HID SENSOR HUB DRIVERS M: Jiri Kosina M: Jonathan Cameron @@ -9202,6 +9220,13 @@ F: drivers/hid/wacom.h F: drivers/hid/wacom_* +HID++ LOGITECH DRIVERS +R: Filipe Laíns +R: Bastien Nocera +L: linux-input@vger.kernel.org +S: Maintained +F: drivers/hid/hid-logitech-hidpp.c + HIGH-RESOLUTION TIMERS, CLOCKEVENTS M: Thomas Gleixner L: linux-kernel@vger.kernel.org @@ -9226,6 +9251,12 @@ F: Documentation/scsi/hptiop.rst F: drivers/scsi/hptiop.c +HIKEY960 ONBOARD USB GPIO HUB DRIVER +M: John Stultz +L: linux-kernel@vger.kernel.org +S: Maintained +F: drivers/misc/hisi_hikey_usb.c + HIMAX HX83112B TOUCHSCREEN SUPPORT M: Job Noorman L: linux-input@vger.kernel.org @@ -9274,6 +9305,12 @@ F: drivers/crypto/hisilicon/hpre/hpre_crypto.c F: drivers/crypto/hisilicon/hpre/hpre_main.c +HISILICON HNS3 PMU DRIVER +M: Guangbin Huang +S: Supported +F: Documentation/admin-guide/perf/hns3-pmu.rst +F: drivers/perf/hisilicon/hns3_pmu.c + HISILICON I2C CONTROLLER DRIVER M: Yicong Yang L: linux-i2c@vger.kernel.org @@ -9306,12 +9343,6 @@ F: Documentation/devicetree/bindings/net/hisilicon*.txt F: drivers/net/ethernet/hisilicon/ -HIKEY960 ONBOARD USB GPIO HUB DRIVER -M: John Stultz -L: linux-kernel@vger.kernel.org -S: Maintained -F: drivers/misc/hisi_hikey_usb.c - HISILICON PMU DRIVER M: Shaokun Zhang M: Jonathan Cameron @@ -9321,12 +9352,6 @@ F: Documentation/admin-guide/perf/hisi-pmu.rst F: drivers/perf/hisilicon -HISILICON HNS3 PMU DRIVER -M: Guangbin Huang -S: Supported -F: Documentation/admin-guide/perf/hns3-pmu.rst -F: drivers/perf/hisilicon/hns3_pmu.c - HISILICON PTT DRIVER M: Yicong Yang M: Jonathan Cameron @@ -9350,17 +9375,8 @@ F: drivers/crypto/hisilicon/sgl.c F: include/linux/hisi_acc_qm.h -HISILICON ZIP Controller DRIVER -M: Yang Shen -M: Zhou Wang -L: linux-crypto@vger.kernel.org -S: Maintained -F: Documentation/ABI/testing/debugfs-hisi-zip -F: drivers/crypto/hisilicon/zip/ - HISILICON ROCE DRIVER -M: Haoyue Xu -M: Wenpeng Liang +M: Junxian Huang L: linux-rdma@vger.kernel.org S: Maintained F: Documentation/devicetree/bindings/infiniband/hisilicon-hns-roce.txt @@ -9416,6 +9432,14 @@ W: http://www.hisilicon.com F: drivers/spi/spi-hisi-sfc-v3xx.c +HISILICON ZIP Controller DRIVER +M: Yang Shen +M: Zhou Wang +L: linux-crypto@vger.kernel.org +S: Maintained +F: Documentation/ABI/testing/debugfs-hisi-zip +F: drivers/crypto/hisilicon/zip/ + HMM - Heterogeneous Memory Management M: Jérôme Glisse L: linux-mm@kvack.org @@ -9426,6 +9450,13 @@ F: mm/hmm* F: tools/testing/selftests/mm/*hmm* +HONEYWELL MPRLS0025PA PRESSURE SENSOR SERIES IIO DRIVER +M: Andreas Klinger +L: linux-iio@vger.kernel.org +S: Maintained +F: Documentation/devicetree/bindings/iio/pressure/honeywell,mprls0025pa.yaml +F: drivers/iio/pressure/mprls0025pa.c + HOST AP DRIVER M: Jouni Malinen L: linux-wireless@vger.kernel.org @@ -9438,6 +9469,13 @@ S: Orphan F: drivers/platform/x86/hp/tc1100-wmi.c +HP WMI HARDWARE MONITOR DRIVER +M: James Seo +L: linux-hwmon@vger.kernel.org +S: Maintained +F: Documentation/hwmon/hp-wmi-sensors.rst +F: drivers/hwmon/hp-wmi-sensors.c + HPET: High Precision Event Timers driver M: Clemens Ladisch S: Maintained @@ -9492,9 +9530,9 @@ HTE SUBSYSTEM M: Dipen Patel L: timestamp@lists.linux.dev -T: git git://git.kernel.org/pub/scm/linux/kernel/git/pateldipen1984/linux.git -Q: https://patchwork.kernel.org/project/timestamp/list/ S: Maintained +Q: https://patchwork.kernel.org/project/timestamp/list/ +T: git git://git.kernel.org/pub/scm/linux/kernel/git/pateldipen1984/linux.git F: Documentation/devicetree/bindings/timestamp/ F: Documentation/driver-api/hte/ F: drivers/hte/ @@ -9589,8 +9627,8 @@ F: Documentation/ABI/stable/sysfs-bus-vmbus F: Documentation/ABI/testing/debugfs-hyperv F: Documentation/devicetree/bindings/bus/microsoft,vmbus.yaml -F: Documentation/virt/hyperv F: Documentation/networking/device_drivers/ethernet/microsoft/netvsc.rst +F: Documentation/virt/hyperv F: arch/arm64/hyperv F: arch/arm64/include/asm/hyperv-tlfs.h F: arch/arm64/include/asm/mshyperv.h @@ -9622,6 +9660,7 @@ HYPERBUS SUPPORT M: Vignesh Raghavendra +R: Tudor Ambarus L: linux-mtd@lists.infradead.org S: Supported Q: http://patchwork.ozlabs.org/project/linux-mtd/list/ @@ -9695,8 +9734,9 @@ F: include/uapi/linux/i2c.h I2C SUBSYSTEM HOST DRIVERS +M: Andi Shyti L: linux-i2c@vger.kernel.org -S: Odd Fixes +S: Maintained W: https://i2c.wiki.kernel.org/ Q: https://patchwork.ozlabs.org/project/linux-i2c/list/ T: git git://git.kernel.org/pub/scm/linux/kernel/git/wsa/linux.git @@ -9772,6 +9812,12 @@ S: Maintained F: drivers/i2c/i2c-stub.c +I3C DRIVER FOR ASPEED AST2600 +M: Jeremy Kerr +S: Maintained +F: Documentation/devicetree/bindings/i3c/aspeed,ast2600-i3c.yaml +F: drivers/i3c/master/ast2600-i3c-master.c + I3C DRIVER FOR CADENCE I3C MASTER IP M: PrzemysÅ‚aw Gaj S: Maintained @@ -9783,12 +9829,6 @@ F: Documentation/devicetree/bindings/i3c/snps,dw-i3c-master.yaml F: drivers/i3c/master/dw* -I3C DRIVER FOR ASPEED AST2600 -M: Jeremy Kerr -S: Maintained -F: Documentation/devicetree/bindings/i3c/aspeed,ast2600-i3c.yaml -F: drivers/i3c/master/ast2600-i3c-master.c - I3C SUBSYSTEM M: Alexandre Belloni L: linux-i3c@lists.infradead.org (moderated for non-subscribers) @@ -9867,6 +9907,11 @@ S: Supported F: drivers/net/ethernet/ibm/ibmvnic.* +IBM Power VFIO Support +M: Timothy Pearson +S: Supported +F: drivers/vfio/vfio_iommu_spapr_tce.c + IBM Power Virtual Ethernet Device Driver M: Nick Child L: netdev@vger.kernel.org @@ -9912,11 +9957,6 @@ F: drivers/crypto/vmx/ppc-xlate.pl F: drivers/crypto/vmx/vmx.c -IBM Power VFIO Support -M: Timothy Pearson -S: Supported -F: drivers/vfio/vfio_iommu_spapr_tce.c - IBM ServeRAID RAID DRIVER S: Orphan F: drivers/scsi/ips.* @@ -9970,8 +10010,9 @@ L: linux-wpan@vger.kernel.org S: Maintained W: https://linux-wpan.org/ -T: git git://git.kernel.org/pub/scm/linux/kernel/git/sschmidt/wpan.git -T: git git://git.kernel.org/pub/scm/linux/kernel/git/sschmidt/wpan-next.git +Q: https://patchwork.kernel.org/project/linux-wpan/list/ +T: git git://git.kernel.org/pub/scm/linux/kernel/git/wpan/wpan.git +T: git git://git.kernel.org/pub/scm/linux/kernel/git/wpan/wpan-next.git F: Documentation/networking/ieee802154.rst F: drivers/net/ieee802154/ F: include/linux/ieee802154.h @@ -9984,6 +10025,10 @@ F: net/ieee802154/ F: net/mac802154/ +IFCVF VIRTIO DATA PATH ACCELERATOR +R: Zhu Lingshan +F: drivers/vdpa/ifcvf/ + IFE PROTOCOL M: Yotam Gigi M: Jamal Hadi Salim @@ -10119,7 +10164,7 @@ F: Documentation/process/kernel-docs.rst INDUSTRY PACK SUBSYSTEM (IPACK) -M: Samuel Iglesias Gonsalvez +M: Vaibhav Gupta M: Jens Taprogge M: Greg Kroah-Hartman L: industrypack-devel@lists.sourceforge.net @@ -10248,8 +10293,8 @@ L: linux-integrity@vger.kernel.org S: Supported T: git git://git.kernel.org/pub/scm/linux/kernel/git/zohar/linux-integrity.git -F: security/integrity/ima/ F: security/integrity/ +F: security/integrity/ima/ INTEL 810/815 FRAMEBUFFER DRIVER M: Antonino Daplas @@ -10257,6 +10302,13 @@ S: Maintained F: drivers/video/fbdev/i810/ +INTEL 8254 COUNTER DRIVER +M: William Breathitt Gray +L: linux-iio@vger.kernel.org +S: Maintained +F: drivers/counter/i8254.c +F: include/linux/i8254.h + INTEL 8255 GPIO DRIVER M: William Breathitt Gray L: linux-gpio@vger.kernel.org @@ -10339,9 +10391,8 @@ M: Tony Nguyen L: intel-wired-lan@lists.osuosl.org (moderated for non-subscribers) S: Supported -W: http://www.intel.com/support/feedback.htm -W: http://e1000.sourceforge.net/ -Q: http://patchwork.ozlabs.org/project/intel-wired-lan/list/ +W: https://www.intel.com/content/www/us/en/support.html +Q: https://patchwork.ozlabs.org/project/intel-wired-lan/list/ T: git git://git.kernel.org/pub/scm/linux/kernel/git/tnguy/net-queue.git T: git git://git.kernel.org/pub/scm/linux/kernel/git/tnguy/next-queue.git F: Documentation/networking/device_drivers/ethernet/intel/ @@ -10403,14 +10454,6 @@ Q: https://patchwork.kernel.org/project/linux-dmaengine/list/ F: drivers/dma/ioat* -INTEL IDXD DRIVER -M: Fenghua Yu -M: Dave Jiang -L: dmaengine@vger.kernel.org -S: Supported -F: drivers/dma/idxd/* -F: include/uapi/linux/idxd.h - INTEL IDLE DRIVER M: Jacob Pan M: Len Brown @@ -10420,6 +10463,14 @@ T: git git://git.kernel.org/pub/scm/linux/kernel/git/lenb/linux.git F: drivers/idle/intel_idle.c +INTEL IDXD DRIVER +M: Fenghua Yu +M: Dave Jiang +L: dmaengine@vger.kernel.org +S: Supported +F: drivers/dma/idxd/* +F: include/uapi/linux/idxd.h + INTEL IN FIELD SCAN (IFS) DEVICE M: Jithu Joseph R: Ashok Raj @@ -10463,21 +10514,21 @@ S: Maintained F: Documentation/admin-guide/media/ipu3.rst F: Documentation/admin-guide/media/ipu3_rcb.svg -F: Documentation/userspace-api/media/v4l/pixfmt-meta-intel-ipu3.rst +F: Documentation/userspace-api/media/v4l/metafmt-intel-ipu3.rst F: drivers/staging/media/ipu3/ -INTEL IXP4XX CRYPTO SUPPORT -M: Corentin Labbe -L: linux-crypto@vger.kernel.org -S: Maintained -F: drivers/crypto/intel/ixp4xx/ixp4xx_crypto.c - INTEL ISHTP ECLITE DRIVER M: Sumesh K Naduvalath L: platform-driver-x86@vger.kernel.org S: Supported F: drivers/platform/x86/intel/ishtp_eclite.c +INTEL IXP4XX CRYPTO SUPPORT +M: Corentin Labbe +L: linux-crypto@vger.kernel.org +S: Maintained +F: drivers/crypto/intel/ixp4xx/ixp4xx_crypto.c + INTEL IXP4XX QMGR, NPE, ETHERNET and HSS SUPPORT M: Krzysztof Halasa S: Maintained @@ -10556,6 +10607,13 @@ F: drivers/mfd/intel-m10-bmc* F: include/linux/mfd/intel-m10-bmc.h +INTEL MAX10 BMC SECURE UPDATES +M: Russ Weight +L: linux-fpga@vger.kernel.org +S: Maintained +F: Documentation/ABI/testing/sysfs-driver-intel-m10-bmc-sec-update +F: drivers/fpga/intel-m10-bmc-sec-update.c + INTEL P-Unit IPC DRIVER M: Zha Qipeng L: platform-driver-x86@vger.kernel.org @@ -10603,6 +10661,13 @@ S: Supported F: drivers/cpufreq/intel_pstate.c +INTEL PTP DFL ToD DRIVER +M: Tianfei Zhang +L: linux-fpga@vger.kernel.org +L: netdev@vger.kernel.org +S: Maintained +F: drivers/ptp/ptp_dfl_tod.c + INTEL QUADRATURE ENCODER PERIPHERAL DRIVER M: Jarkko Nikula L: linux-iio@vger.kernel.org @@ -10621,6 +10686,21 @@ F: tools/arch/x86/intel_sdsi/ F: tools/testing/selftests/drivers/sdsi/ +INTEL SGX +M: Jarkko Sakkinen +R: Dave Hansen +L: linux-sgx@vger.kernel.org +S: Supported +Q: https://patchwork.kernel.org/project/intel-sgx/list/ +T: git git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip.git x86/sgx +F: Documentation/arch/x86/sgx.rst +F: arch/x86/entry/vdso/vsgx.S +F: arch/x86/include/asm/sgx.h +F: arch/x86/include/uapi/asm/sgx.h +F: arch/x86/kernel/cpu/sgx/* +F: tools/testing/selftests/sgx/* +K: \bSGX_ + INTEL SKYLAKE INT3472 ACPI DEVICE DRIVER M: Daniel Scally S: Maintained @@ -10638,13 +10718,13 @@ M: Dinh Nguyen L: linux-kernel@vger.kernel.org S: Maintained +T: git git://git.kernel.org/pub/scm/linux/kernel/git/dinguyen/linux.git F: Documentation/ABI/testing/sysfs-devices-platform-stratix10-rsu F: Documentation/devicetree/bindings/firmware/intel,stratix10-svc.txt F: drivers/firmware/stratix10-rsu.c F: drivers/firmware/stratix10-svc.c F: include/linux/firmware/intel/stratix10-smc.h F: include/linux/firmware/intel/stratix10-svc-client.h -T: git git://git.kernel.org/pub/scm/linux/kernel/git/dinguyen/linux.git INTEL TELEMETRY DRIVER M: Rajneesh Bhardwaj @@ -10729,21 +10809,6 @@ F: arch/x86/kernel/tboot.c F: include/linux/tboot.h -INTEL SGX -M: Jarkko Sakkinen -R: Dave Hansen -L: linux-sgx@vger.kernel.org -S: Supported -Q: https://patchwork.kernel.org/project/intel-sgx/list/ -T: git git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip.git x86/sgx -F: Documentation/arch/x86/sgx.rst -F: arch/x86/entry/vdso/vsgx.S -F: arch/x86/include/asm/sgx.h -F: arch/x86/include/uapi/asm/sgx.h -F: arch/x86/kernel/cpu/sgx/* -F: tools/testing/selftests/sgx/* -K: \bSGX_ - INTERCONNECT API M: Georgi Djakov L: linux-pm@vger.kernel.org @@ -10793,7 +10858,6 @@ F: drivers/net/ethernet/sgi/ioc3-eth.c IOMAP FILESYSTEM LIBRARY -M: Christoph Hellwig M: Darrick J. Wong L: linux-xfs@vger.kernel.org L: linux-fsdevel@vger.kernel.org @@ -10812,18 +10876,6 @@ F: drivers/iommu/iova.c F: include/linux/iova.h -IOMMUFD -M: Jason Gunthorpe -M: Kevin Tian -L: iommu@lists.linux.dev -S: Maintained -T: git git://git.kernel.org/pub/scm/linux/kernel/git/jgg/iommufd.git -F: Documentation/userspace-api/iommufd.rst -F: drivers/iommu/iommufd/ -F: include/linux/iommufd.h -F: include/uapi/linux/iommufd.h -F: tools/testing/selftests/iommu/ - IOMMU SUBSYSTEM M: Joerg Roedel M: Will Deacon @@ -10839,6 +10891,18 @@ F: include/linux/of_iommu.h F: include/uapi/linux/iommu.h +IOMMUFD +M: Jason Gunthorpe +M: Kevin Tian +L: iommu@lists.linux.dev +S: Maintained +T: git git://git.kernel.org/pub/scm/linux/kernel/git/jgg/iommufd.git +F: Documentation/userspace-api/iommufd.rst +F: drivers/iommu/iommufd/ +F: include/linux/iommufd.h +F: include/uapi/linux/iommufd.h +F: tools/testing/selftests/iommu/ + IOSYS-MAP HELPERS M: Thomas Zimmermann L: dri-devel@lists.freedesktop.org @@ -10853,11 +10917,11 @@ S: Maintained T: git git://git.kernel.dk/linux-block T: git git://git.kernel.dk/liburing -F: io_uring/ F: include/linux/io_uring.h F: include/linux/io_uring_types.h F: include/trace/events/io_uring.h F: include/uapi/linux/io_uring.h +F: io_uring/ F: tools/io_uring/ IPMI SUBSYSTEM @@ -10866,8 +10930,8 @@ S: Supported W: http://openipmi.sourceforge.net/ T: git https://github.com/cminyard/linux-ipmi.git for-next -F: Documentation/driver-api/ipmi.rst F: Documentation/devicetree/bindings/ipmi/ +F: Documentation/driver-api/ipmi.rst F: drivers/char/ipmi/ F: include/linux/ipmi* F: include/uapi/linux/ipmi* @@ -10919,8 +10983,8 @@ L: linux-kernel@vger.kernel.org S: Maintained T: git git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip.git irq/core -F: kernel/irq/ F: include/linux/group_cpus.h +F: kernel/irq/ F: lib/group_cpus.c IRQCHIP DRIVERS @@ -11254,10 +11318,15 @@ KERNEL NFSD, SUNRPC, AND LOCKD SERVERS M: Chuck Lever M: Jeff Layton +R: Neil Brown +R: Olga Kornievskaia +R: Dai Ngo +R: Tom Talpey L: linux-nfs@vger.kernel.org S: Supported W: http://nfs.sourceforge.net/ T: git git://git.kernel.org/pub/scm/linux/kernel/git/cel/linux.git +F: Documentation/filesystems/nfs/ F: fs/exportfs/ F: fs/lockd/ F: fs/nfs_common/ @@ -11273,7 +11342,6 @@ F: include/uapi/linux/nfsd/ F: include/uapi/linux/sunrpc/ F: net/sunrpc/ -F: Documentation/filesystems/nfs/ KERNEL REGRESSIONS M: Thorsten Leemhuis @@ -11300,9 +11368,9 @@ L: linux-cifs@vger.kernel.org S: Maintained T: git git://git.samba.org/ksmbd.git -F: Documentation/filesystems/cifs/ksmbd.rst -F: fs/ksmbd/ -F: fs/smbfs_common/ +F: Documentation/filesystems/smb/ksmbd.rst +F: fs/smb/common/ +F: fs/smb/server/ KERNEL UNIT TESTING FRAMEWORK (KUnit) M: Brendan Higgins @@ -11311,6 +11379,8 @@ L: kunit-dev@googlegroups.com S: Maintained W: https://google.github.io/kunit-docs/third_party/kernel/docs/ +T: git git://git.kernel.org/pub/scm/linux/kernel/git/shuah/linux-kselftest.git kunit +T: git git://git.kernel.org/pub/scm/linux/kernel/git/shuah/linux-kselftest.git kunit-fixes F: Documentation/dev-tools/kunit/ F: include/kunit/ F: lib/kunit/ @@ -11359,7 +11429,6 @@ KERNEL VIRTUAL MACHINE FOR MIPS (KVM/mips) M: Huacai Chen -M: Aleksandar Markovic L: linux-mips@vger.kernel.org L: kvm@vger.kernel.org S: Maintained @@ -11369,7 +11438,13 @@ F: arch/mips/kvm/ KERNEL VIRTUAL MACHINE FOR POWERPC (KVM/powerpc) +M: Michael Ellerman +R: Nicholas Piggin L: linuxppc-dev@lists.ozlabs.org +L: kvm@vger.kernel.org +S: Maintained (Book3S 64-bit HV) +S: Odd fixes (Book3S 64-bit PR) +S: Orphan (Book3E and 32-bit) T: git git://git.kernel.org/pub/scm/linux/kernel/git/powerpc/linux.git topic/ppc-kvm F: arch/powerpc/include/asm/kvm* F: arch/powerpc/include/uapi/asm/kvm* @@ -11415,6 +11490,7 @@ M: Paolo Bonzini L: kvm@vger.kernel.org S: Supported +P: Documentation/process/maintainer-kvm-x86.rst T: git git://git.kernel.org/pub/scm/virt/kvm/kvm.git F: arch/x86/include/asm/kvm* F: arch/x86/include/asm/svm.h @@ -11425,47 +11501,6 @@ F: arch/x86/kvm/ F: arch/x86/kvm/*/ -KVM PARAVIRT (KVM/paravirt) -M: Paolo Bonzini -R: Wanpeng Li -R: Vitaly Kuznetsov -L: kvm@vger.kernel.org -S: Supported -T: git git://git.kernel.org/pub/scm/virt/kvm/kvm.git -F: arch/x86/kernel/kvm.c -F: arch/x86/kernel/kvmclock.c -F: arch/x86/include/asm/pvclock-abi.h -F: include/linux/kvm_para.h -F: include/uapi/linux/kvm_para.h -F: include/uapi/asm-generic/kvm_para.h -F: include/asm-generic/kvm_para.h -F: arch/um/include/asm/kvm_para.h -F: arch/x86/include/asm/kvm_para.h -F: arch/x86/include/uapi/asm/kvm_para.h - -KVM X86 HYPER-V (KVM/hyper-v) -M: Vitaly Kuznetsov -M: Sean Christopherson -M: Paolo Bonzini -L: kvm@vger.kernel.org -S: Supported -T: git git://git.kernel.org/pub/scm/virt/kvm/kvm.git -F: arch/x86/kvm/hyperv.* -F: arch/x86/kvm/kvm_onhyperv.* -F: arch/x86/kvm/svm/hyperv.* -F: arch/x86/kvm/svm/svm_onhyperv.* -F: arch/x86/kvm/vmx/hyperv.* - -KVM X86 Xen (KVM/Xen) -M: David Woodhouse -M: Paul Durrant -M: Sean Christopherson -M: Paolo Bonzini -L: kvm@vger.kernel.org -S: Supported -T: git git://git.kernel.org/pub/scm/virt/kvm/kvm.git -F: arch/x86/kvm/xen.* - KERNFS M: Greg Kroah-Hartman M: Tejun Heo @@ -11504,14 +11539,6 @@ F: include/keys/trusted_tpm.h F: security/keys/trusted-keys/ -KEYS-TRUSTED-TEE -M: Sumit Garg -L: linux-integrity@vger.kernel.org -L: keyrings@vger.kernel.org -S: Supported -F: include/keys/trusted_tee.h -F: security/keys/trusted-keys/trusted_tee.c - KEYS-TRUSTED-CAAM M: Ahmad Fatoum R: Pengutronix Kernel Team @@ -11521,6 +11548,14 @@ F: include/keys/trusted_caam.h F: security/keys/trusted-keys/trusted_caam.c +KEYS-TRUSTED-TEE +M: Sumit Garg +L: linux-integrity@vger.kernel.org +L: keyrings@vger.kernel.org +S: Supported +F: include/keys/trusted_tee.h +F: security/keys/trusted-keys/trusted_tee.c + KEYS/KEYRINGS M: David Howells M: Jarkko Sakkinen @@ -11583,8 +11618,8 @@ S: Maintained F: Documentation/devicetree/bindings/mfd/khadas,mcu.yaml F: drivers/mfd/khadas-mcu.c -F: include/linux/mfd/khadas-mcu.h F: drivers/thermal/khadas_mcu_fan.c +F: include/linux/mfd/khadas-mcu.h KIONIX/ROHM KX022A ACCELEROMETER M: Matti Vaittinen @@ -11621,8 +11656,8 @@ M: Masami Hiramatsu L: linux-kernel@vger.kernel.org L: linux-trace-kernel@vger.kernel.org -Q: https://patchwork.kernel.org/project/linux-trace-kernel/list/ S: Maintained +Q: https://patchwork.kernel.org/project/linux-trace-kernel/list/ T: git git://git.kernel.org/pub/scm/linux/kernel/git/trace/linux-trace.git F: Documentation/trace/kprobes.rst F: include/asm-generic/kprobes.h @@ -11656,6 +11691,47 @@ F: Documentation/devicetree/bindings/leds/backlight/kinetic,ktz8866.yaml F: drivers/video/backlight/ktz8866.c +KVM PARAVIRT (KVM/paravirt) +M: Paolo Bonzini +R: Wanpeng Li +R: Vitaly Kuznetsov +L: kvm@vger.kernel.org +S: Supported +T: git git://git.kernel.org/pub/scm/virt/kvm/kvm.git +F: arch/um/include/asm/kvm_para.h +F: arch/x86/include/asm/kvm_para.h +F: arch/x86/include/asm/pvclock-abi.h +F: arch/x86/include/uapi/asm/kvm_para.h +F: arch/x86/kernel/kvm.c +F: arch/x86/kernel/kvmclock.c +F: include/asm-generic/kvm_para.h +F: include/linux/kvm_para.h +F: include/uapi/asm-generic/kvm_para.h +F: include/uapi/linux/kvm_para.h + +KVM X86 HYPER-V (KVM/hyper-v) +M: Vitaly Kuznetsov +M: Sean Christopherson +M: Paolo Bonzini +L: kvm@vger.kernel.org +S: Supported +T: git git://git.kernel.org/pub/scm/virt/kvm/kvm.git +F: arch/x86/kvm/hyperv.* +F: arch/x86/kvm/kvm_onhyperv.* +F: arch/x86/kvm/svm/hyperv.* +F: arch/x86/kvm/svm/svm_onhyperv.* +F: arch/x86/kvm/vmx/hyperv.* + +KVM X86 Xen (KVM/Xen) +M: David Woodhouse +M: Paul Durrant +M: Sean Christopherson +M: Paolo Bonzini +L: kvm@vger.kernel.org +S: Supported +T: git git://git.kernel.org/pub/scm/virt/kvm/kvm.git +F: arch/x86/kvm/xen.* + L3MDEV M: David Ahern L: netdev@vger.kernel.org @@ -11731,7 +11807,7 @@ R: David Lechner S: Maintained F: Documentation/devicetree/bindings/power/supply/lego,ev3-battery.yaml -F: arch/arm/boot/dts/da850-lego-ev3.dts +F: arch/arm/boot/dts/ti/davinci/da850-lego-ev3.dts F: drivers/power/supply/lego_ev3_battery.c LEGO USB Tower driver @@ -11897,16 +11973,17 @@ LINEAR RANGES HELPERS M: Mark Brown R: Matti Vaittinen +F: include/linux/linear_range.h F: lib/linear_ranges.c F: lib/test_linear_ranges.c -F: include/linux/linear_range.h LINUX FOR POWER MACINTOSH -M: Benjamin Herrenschmidt L: linuxppc-dev@lists.ozlabs.org -S: Odd Fixes +S: Orphan F: arch/powerpc/platforms/powermac/ F: drivers/macintosh/ +X: drivers/macintosh/adb-iop.c +X: drivers/macintosh/via-macii.c LINUX FOR POWERPC (32-BIT AND 64-BIT) M: Michael Ellerman @@ -12004,6 +12081,13 @@ F: Documentation/memory-barriers.txt F: tools/memory-model/ +LINUX-NEXT TREE +M: Stephen Rothwell +L: linux-next@vger.kernel.org +S: Supported +B: mailto:linux-next@vger.kernel.org and the appropriate development tree +T: git git://git.kernel.org/pub/scm/linux/kernel/git/next/linux-next.git/ + LIS3LV02D ACCELEROMETER DRIVER M: Eric Piel S: Maintained @@ -12026,11 +12110,11 @@ S: Maintained F: Documentation/devicetree/bindings/*/litex,*.yaml F: arch/openrisc/boot/dts/or1klitex.dts -F: include/linux/litex.h -F: drivers/tty/serial/liteuart.c -F: drivers/soc/litex/* -F: drivers/net/ethernet/litex/* F: drivers/mmc/host/litex_mmc.c +F: drivers/net/ethernet/litex/* +F: drivers/soc/litex/* +F: drivers/tty/serial/liteuart.c +F: include/linux/litex.h N: litex LIVE PATCHING @@ -12159,10 +12243,17 @@ L: loongarch@lists.linux.dev S: Maintained T: git git://git.kernel.org/pub/scm/linux/kernel/git/chenhuacai/linux-loongson.git -F: arch/loongarch/ -F: drivers/*/*loongarch* F: Documentation/loongarch/ F: Documentation/translations/zh_CN/loongarch/ +F: arch/loongarch/ +F: drivers/*/*loongarch* + +LOONGSON GPIO DRIVER +M: Yinbo Zhu +L: linux-gpio@vger.kernel.org +S: Maintained +F: Documentation/devicetree/bindings/gpio/loongson,ls-gpio.yaml +F: drivers/gpio/gpio-loongson-64bit.c LOONGSON LS2X I2C DRIVER M: Binbin Zhou @@ -12171,6 +12262,14 @@ F: Documentation/devicetree/bindings/i2c/loongson,ls2x-i2c.yaml F: drivers/i2c/busses/i2c-ls2x.c +LOONGSON-2 SOC SERIES CLOCK DRIVER +M: Yinbo Zhu +L: linux-clk@vger.kernel.org +S: Maintained +F: Documentation/devicetree/bindings/clock/loongson,ls2k-clk.yaml +F: drivers/clk/clk-loongson2.c +F: include/dt-bindings/clock/loongson,ls2k-clk.h + LOONGSON-2 SOC SERIES GUTS DRIVER M: Yinbo Zhu L: loongarch@lists.linux.dev @@ -12186,21 +12285,6 @@ F: Documentation/devicetree/bindings/pinctrl/loongson,ls2k-pinctrl.yaml F: drivers/pinctrl/pinctrl-loongson2.c -LOONGSON GPIO DRIVER -M: Yinbo Zhu -L: linux-gpio@vger.kernel.org -S: Maintained -F: Documentation/devicetree/bindings/gpio/loongson,ls-gpio.yaml -F: drivers/gpio/gpio-loongson-64bit.c - -LOONGSON-2 SOC SERIES CLOCK DRIVER -M: Yinbo Zhu -L: linux-clk@vger.kernel.org -S: Maintained -F: Documentation/devicetree/bindings/clock/loongson,ls2k-clk.yaml -F: drivers/clk/clk-loongson2.c -F: include/dt-bindings/clock/loongson,ls2k-clk.h - LSILOGIC MPT FUSION DRIVERS (FC/SAS/SPI) M: Sathya Prakash M: Sreekanth Reddy @@ -12361,20 +12445,26 @@ M: Jassi Brar L: linux-kernel@vger.kernel.org S: Maintained +F: Documentation/devicetree/bindings/mailbox/ F: drivers/mailbox/ +F: include/dt-bindings/mailbox/ F: include/linux/mailbox_client.h F: include/linux/mailbox_controller.h -F: include/dt-bindings/mailbox/ -F: Documentation/devicetree/bindings/mailbox/ MAILBOX ARM MHUv2 M: Viresh Kumar M: Tushar Khandelwal L: linux-kernel@vger.kernel.org S: Maintained +F: Documentation/devicetree/bindings/mailbox/arm,mhuv2.yaml F: drivers/mailbox/arm_mhuv2.c F: include/linux/mailbox/arm_mhuv2_message.h -F: Documentation/devicetree/bindings/mailbox/arm,mhuv2.yaml + +MAN-PAGES: MANUAL PAGES FOR LINUX -- Sections 2, 3, 4, 5, and 7 +M: Michael Kerrisk +L: linux-man@vger.kernel.org +S: Maintained +W: http://www.kernel.org/doc/man-pages MANAGEMENT COMPONENT TRANSPORT PROTOCOL (MCTP) M: Jeremy Kerr @@ -12388,14 +12478,9 @@ F: include/net/netns/mctp.h F: net/mctp/ -MAN-PAGES: MANUAL PAGES FOR LINUX -- Sections 2, 3, 4, 5, and 7 -M: Michael Kerrisk -L: linux-man@vger.kernel.org -S: Maintained -W: http://www.kernel.org/doc/man-pages - MAPLE TREE M: Liam R. Howlett +L: maple-tree@lists.infradead.org L: linux-mm@kvack.org S: Supported F: Documentation/core-api/maple_tree.rst @@ -12425,8 +12510,8 @@ MARVELL ARMADA 3700 PHY DRIVERS M: Miquel Raynal S: Maintained -F: Documentation/devicetree/bindings/phy/phy-mvebu-comphy.txt F: Documentation/devicetree/bindings/phy/marvell,armada-3700-utmi-phy.yaml +F: Documentation/devicetree/bindings/phy/phy-mvebu-comphy.txt F: drivers/phy/marvell/phy-mvebu-a3700-comphy.c F: drivers/phy/marvell/phy-mvebu-a3700-utmi.c @@ -12507,27 +12592,29 @@ F: drivers/net/ethernet/marvell/mvpp2/ MARVELL MWIFIEX WIRELESS DRIVER -M: Amitkumar Karwar -M: Ganapathi Bhat -M: Sharvari Harisangam -M: Xinming Hu +M: Brian Norris L: linux-wireless@vger.kernel.org -S: Maintained +S: Odd Fixes F: drivers/net/wireless/marvell/mwifiex/ MARVELL MWL8K WIRELESS DRIVER -M: Lennert Buytenhek L: linux-wireless@vger.kernel.org -S: Odd Fixes +S: Orphan F: drivers/net/wireless/marvell/mwl8k.c MARVELL NAND CONTROLLER DRIVER M: Miquel Raynal L: linux-mtd@lists.infradead.org S: Maintained -F: Documentation/devicetree/bindings/mtd/marvell-nand.txt F: drivers/mtd/nand/raw/marvell_nand.c +MARVELL OCTEON ENDPOINT DRIVER +M: Veerasenareddy Burru +M: Sathesh Edara +L: netdev@vger.kernel.org +S: Supported +F: drivers/net/ethernet/marvell/octeon_ep + MARVELL OCTEONTX2 PHYSICAL FUNCTION DRIVER M: Sunil Goutham M: Geetha sowjanya @@ -12575,13 +12662,6 @@ F: Documentation/devicetree/bindings/mmc/marvell,xenon-sdhci.yaml F: drivers/mmc/host/sdhci-xenon* -MARVELL OCTEON ENDPOINT DRIVER -M: Veerasenareddy Burru -M: Abhijit Ayarekar -L: netdev@vger.kernel.org -S: Supported -F: drivers/net/ethernet/marvell/octeon_ep - MATROX FRAMEBUFFER DRIVER L: linux-fbdev@vger.kernel.org S: Orphan @@ -12612,6 +12692,15 @@ F: drivers/media/i2c/max2175* F: include/uapi/linux/max2175.h +MAX31827 TEMPERATURE SWITCH DRIVER +M: Daniel Matyas +L: linux-hwmon@vger.kernel.org +S: Supported +W: http://ez.analog.com/community/linux-device-drivers +F: Documentation/devicetree/bindings/hwmon/adi,max31827.yaml +F: Documentation/hwmon/max31827.rst +F: drivers/hwmon/max31827.c + MAX6650 HARDWARE MONITOR AND FAN CONTROLLER DRIVER L: linux-hwmon@vger.kernel.org S: Orphan @@ -12781,12 +12870,6 @@ S: Supported F: drivers/net/phy/mxl-gpy.c -MCBA MICROCHIP CAN BUS ANALYZER TOOL DRIVER -R: Yasushi SHOJI -L: linux-can@vger.kernel.org -S: Maintained -F: drivers/net/can/usb/mcba_usb.c - MCAN MMIO DEVICE DRIVER M: Chandrasekar Ramakrishnan L: linux-can@vger.kernel.org @@ -12796,6 +12879,12 @@ F: drivers/net/can/m_can/m_can.h F: drivers/net/can/m_can/m_can_platform.c +MCBA MICROCHIP CAN BUS ANALYZER TOOL DRIVER +R: Yasushi SHOJI +L: linux-can@vger.kernel.org +S: Maintained +F: drivers/net/can/usb/mcba_usb.c + MCP2221A MICROCHIP USB-HID TO I2C BRIDGE DRIVER M: Rishi Gupta L: linux-i2c@vger.kernel.org @@ -12829,6 +12918,13 @@ F: drivers/net/ieee802154/mcr20a.c F: drivers/net/ieee802154/mcr20a.h +MDIO REGMAP DRIVER +M: Maxime Chevallier +L: netdev@vger.kernel.org +S: Maintained +F: drivers/net/mdio/mdio-regmap.c +F: include/linux/mdio/mdio-regmap.h + MEASUREMENT COMPUTING CIO-DAC IIO DRIVER M: William Breathitt Gray L: linux-iio@vger.kernel.org @@ -13128,6 +13224,15 @@ F: drivers/net/pcs/pcs-mtk-lynxi.c F: include/linux/pcs/pcs-mtk-lynxi.h +MEDIATEK ETHERNET PHY DRIVERS +M: Daniel Golle +M: Qingfang Deng +M: SkyLake Huang +L: netdev@vger.kernel.org +S: Maintained +F: drivers/net/phy/mediatek-ge-soc.c +F: drivers/net/phy/mediatek-ge.c + MEDIATEK I2C CONTROLLER DRIVER M: Qii Wang L: linux-i2c@vger.kernel.org @@ -13189,6 +13294,7 @@ R: Sean Wang L: linux-wireless@vger.kernel.org S: Maintained +T: git https://github.com/nbd168/wireless F: Documentation/devicetree/bindings/net/wireless/mediatek,mt76.yaml F: drivers/net/wireless/mediatek/mt76/ @@ -13204,13 +13310,6 @@ F: Documentation/devicetree/bindings/clock/mediatek,mt7621-sysc.yaml F: drivers/clk/ralink/clk-mt7621.c -MEDIATEK MT7621/28/88 I2C DRIVER -M: Stefan Roese -L: linux-i2c@vger.kernel.org -S: Maintained -F: Documentation/devicetree/bindings/i2c/mediatek,mt7621-i2c.yaml -F: drivers/i2c/busses/i2c-mt7621.c - MEDIATEK MT7621 PCIE CONTROLLER DRIVER M: Sergio Paracuellos S: Maintained @@ -13223,6 +13322,19 @@ F: Documentation/devicetree/bindings/phy/mediatek,mt7621-pci-phy.yaml F: drivers/phy/ralink/phy-mt7621-pci.c +MEDIATEK MT7621/28/88 I2C DRIVER +M: Stefan Roese +L: linux-i2c@vger.kernel.org +S: Maintained +F: Documentation/devicetree/bindings/i2c/mediatek,mt7621-i2c.yaml +F: drivers/i2c/busses/i2c-mt7621.c + +MEDIATEK MTMIPS CLOCK DRIVER +M: Sergio Paracuellos +S: Maintained +F: Documentation/devicetree/bindings/clock/mediatek,mtmips-sysc.yaml +F: drivers/clk/ralink/clk-mtmips.c + MEDIATEK NAND CONTROLLER DRIVER L: linux-mtd@lists.infradead.org S: Orphan @@ -13249,10 +13361,11 @@ F: include/soc/mediatek/smi.h MEDIATEK SWITCH DRIVER -M: Sean Wang +M: Arınç ÃœNAL +M: Daniel Golle M: Landen Chao M: DENG Qingfang -M: Daniel Golle +M: Sean Wang L: netdev@vger.kernel.org S: Maintained F: drivers/net/dsa/mt7530-mdio.c @@ -13482,10 +13595,22 @@ M: Dmitry Osipenko L: linux-pm@vger.kernel.org L: linux-tegra@vger.kernel.org -T: git git://git.kernel.org/pub/scm/linux/kernel/git/chanwoo/linux.git S: Maintained +T: git git://git.kernel.org/pub/scm/linux/kernel/git/chanwoo/linux.git F: drivers/devfreq/tegra30-devfreq.c +MEMORY HOT(UN)PLUG +M: David Hildenbrand +M: Oscar Salvador +L: linux-mm@kvack.org +S: Maintained +F: Documentation/admin-guide/mm/memory-hotplug.rst +F: Documentation/core-api/memory-hotplug.rst +F: drivers/base/memory.c +F: include/linux/memory_hotplug.h +F: mm/memory_hotplug.c +F: tools/testing/selftests/memory-hotplug/ + MEMORY MANAGEMENT M: Andrew Morton L: linux-mm@kvack.org @@ -13504,30 +13629,6 @@ F: tools/mm/ F: tools/testing/selftests/mm/ -VMALLOC -M: Andrew Morton -R: Uladzislau Rezki -R: Christoph Hellwig -R: Lorenzo Stoakes -L: linux-mm@kvack.org -S: Maintained -W: http://www.linux-mm.org -T: git git://git.kernel.org/pub/scm/linux/kernel/git/akpm/mm -F: include/linux/vmalloc.h -F: mm/vmalloc.c - -MEMORY HOT(UN)PLUG -M: David Hildenbrand -M: Oscar Salvador -L: linux-mm@kvack.org -S: Maintained -F: Documentation/admin-guide/mm/memory-hotplug.rst -F: Documentation/core-api/memory-hotplug.rst -F: drivers/base/memory.c -F: include/linux/memory_hotplug.h -F: mm/memory_hotplug.c -F: tools/testing/selftests/memory-hotplug/ - MEMORY TECHNOLOGY DEVICES (MTD) M: Miquel Raynal M: Richard Weinberger @@ -13629,6 +13730,7 @@ F: Documentation/ABI/stable/sysfs-bus-mhi F: Documentation/mhi/ F: drivers/bus/mhi/ +F: drivers/pci/endpoint/functions/pci-epf-mhi.c F: include/linux/mhi.h MICROBLAZE ARCHITECTURE @@ -13638,6 +13740,12 @@ T: git git://git.monstr.eu/linux-2.6-microblaze.git F: arch/microblaze/ +MICROBLAZE TMR INJECT +M: Appana Durga Kedareswara rao +S: Supported +F: Documentation/devicetree/bindings/misc/xlnx,tmr-inject.yaml +F: drivers/misc/xilinx_tmr_inject.c + MICROBLAZE TMR MANAGER M: Appana Durga Kedareswara rao S: Supported @@ -13645,12 +13753,6 @@ F: Documentation/devicetree/bindings/misc/xlnx,tmr-manager.yaml F: drivers/misc/xilinx_tmr_manager.c -MICROBLAZE TMR INJECT -M: Appana Durga Kedareswara rao -S: Supported -F: Documentation/devicetree/bindings/misc/xlnx,tmr-inject.yaml -F: drivers/misc/xilinx_tmr_inject.c - MICROCHIP AT91 DMA DRIVERS M: Ludovic Desroches M: Tudor Ambarus @@ -13685,7 +13787,7 @@ F: drivers/spi/spi-at91-usart.c MICROCHIP AUDIO ASOC DRIVERS -M: Claudiu Beznea +M: Claudiu Beznea L: alsa-devel@alsa-project.org (moderated for non-subscribers) S: Supported F: Documentation/devicetree/bindings/sound/atmel* @@ -13708,9 +13810,10 @@ F: drivers/crypto/atmel-ecc.* MICROCHIP EIC DRIVER -M: Claudiu Beznea +M: Claudiu Beznea L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) S: Supported +F: Documentation/devicetree/bindings/interrupt-controller/microchip,sama7g5-eic.yaml F: drivers/irqchip/irq-mchp-eic.c MICROCHIP I2C DRIVER @@ -13726,10 +13829,10 @@ S: Supported F: Documentation/devicetree/bindings/media/atmel,isc.yaml F: Documentation/devicetree/bindings/media/microchip,xisc.yaml -F: drivers/staging/media/deprecated/atmel/atmel-isc* -F: drivers/staging/media/deprecated/atmel/atmel-sama*-isc* F: drivers/media/platform/microchip/microchip-isc* F: drivers/media/platform/microchip/microchip-sama*-isc* +F: drivers/staging/media/deprecated/atmel/atmel-isc* +F: drivers/staging/media/deprecated/atmel/atmel-sama*-isc* F: include/linux/atmel-isc-media.h MICROCHIP ISI DRIVER @@ -13751,13 +13854,6 @@ F: include/linux/platform_data/microchip-ksz.h F: net/dsa/tag_ksz.c -MICROCHIP LAN87xx/LAN937x T1 PHY DRIVER -M: Arun Ramadoss -R: UNGLinuxDriver@microchip.com -L: netdev@vger.kernel.org -S: Maintained -F: drivers/net/phy/microchip_t1.c - MICROCHIP LAN743X ETHERNET DRIVER M: Bryan Whitehead M: UNGLinuxDriver@microchip.com @@ -13765,6 +13861,13 @@ S: Maintained F: drivers/net/ethernet/microchip/lan743x_* +MICROCHIP LAN87xx/LAN937x T1 PHY DRIVER +M: Arun Ramadoss +R: UNGLinuxDriver@microchip.com +L: netdev@vger.kernel.org +S: Maintained +F: drivers/net/phy/microchip_t1.c + MICROCHIP LAN966X ETHERNET DRIVER M: Horatiu Vultur M: UNGLinuxDriver@microchip.com @@ -13780,7 +13883,7 @@ F: include/video/atmel_lcdc.h MICROCHIP MCP16502 PMIC DRIVER -M: Claudiu Beznea +M: Claudiu Beznea L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) S: Supported F: Documentation/devicetree/bindings/regulator/mcp16502-regulator.txt @@ -13806,6 +13909,14 @@ F: Documentation/devicetree/bindings/mtd/atmel-nand.txt F: drivers/mtd/nand/raw/atmel/* +MICROCHIP OTPC DRIVER +M: Claudiu Beznea +L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) +S: Supported +F: Documentation/devicetree/bindings/nvmem/microchip,sama7g5-otpc.yaml +F: drivers/nvmem/microchip-otpc.c +F: include/dt-bindings/nvmem/microchip,sama7g5-otpc.h + MICROCHIP PCI1XXXX GP DRIVER M: Kumaravel Thiagarajan L: linux-gpio@vger.kernel.org @@ -13814,14 +13925,6 @@ F: drivers/misc/mchp_pci1xxxx/mchp_pci1xxxx_gp.h F: drivers/misc/mchp_pci1xxxx/mchp_pci1xxxx_gpio.c -MICROCHIP OTPC DRIVER -M: Claudiu Beznea -L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) -S: Supported -F: Documentation/devicetree/bindings/nvmem/microchip,sama7g5-otpc.yaml -F: drivers/nvmem/microchip-otpc.c -F: include/dt-bindings/nvmem/microchip,sama7g5-otpc.h - MICROCHIP PCI1XXXX I2C DRIVER M: Tharun Kumar P M: Kumaravel Thiagarajan @@ -13837,8 +13940,16 @@ S: Maintained F: drivers/tty/serial/8250/8250_pci1xxxx.c +MICROCHIP POLARFIRE FPGA DRIVERS +M: Conor Dooley +R: Vladimir Georgiev +L: linux-fpga@vger.kernel.org +S: Supported +F: Documentation/devicetree/bindings/fpga/microchip,mpf-spi-fpga-mgr.yaml +F: drivers/fpga/microchip-spi.c + MICROCHIP PWM DRIVER -M: Claudiu Beznea +M: Claudiu Beznea L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) L: linux-pwm@vger.kernel.org S: Supported @@ -13854,28 +13965,36 @@ F: include/dt-bindings/iio/adc/at91-sama5d2_adc.h MICROCHIP SAMA5D2-COMPATIBLE SHUTDOWN CONTROLLER -M: Claudiu Beznea +M: Claudiu Beznea S: Supported +F: Documentation/devicetree/bindings/power/reset/atmel,sama5d2-shdwc.yaml F: drivers/power/reset/at91-sama5d2_shdwc.c +MICROCHIP SOC DRIVERS +M: Conor Dooley +S: Supported +T: git https://git.kernel.org/pub/scm/linux/kernel/git/conor/linux.git/ +F: drivers/soc/microchip/ + MICROCHIP SPI DRIVER -M: Tudor Ambarus +M: Ryan Wanner S: Supported F: drivers/spi/spi-atmel.* MICROCHIP SSC DRIVER -M: Claudiu Beznea +M: Claudiu Beznea L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) S: Supported F: Documentation/devicetree/bindings/misc/atmel-ssc.txt F: drivers/misc/atmel-ssc.c F: include/linux/atmel-ssc.h -MICROCHIP SOC DRIVERS -M: Conor Dooley -S: Supported -T: git https://git.kernel.org/pub/scm/linux/kernel/git/conor/linux.git/ -F: drivers/soc/microchip/ +Microchip Timer Counter Block (TCB) Capture Driver +M: Kamel Bouhara +L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) +L: linux-iio@vger.kernel.org +S: Maintained +F: drivers/counter/microchip-tcb-capture.c MICROCHIP USB251XB DRIVER M: Richard Leitner @@ -13892,7 +14011,7 @@ MICROCHIP WILC1000 WIFI DRIVER M: Ajay Singh -M: Claudiu Beznea +M: Claudiu Beznea L: linux-wireless@vger.kernel.org S: Supported F: drivers/net/wireless/microchip/wilc1000/ @@ -13992,6 +14111,12 @@ S: Supported F: drivers/platform/surface/surfacepro3_button.c +MICROSOFT SURFACE SYSTEM AGGREGATOR HUB DRIVER +M: Maximilian Luz +L: platform-driver-x86@vger.kernel.org +S: Maintained +F: drivers/platform/surface/surface_aggregator_hub.c + MICROSOFT SURFACE SYSTEM AGGREGATOR SUBSYSTEM M: Maximilian Luz L: platform-driver-x86@vger.kernel.org @@ -14007,12 +14132,6 @@ F: include/linux/surface_aggregator/ F: include/uapi/linux/surface_aggregator/ -MICROSOFT SURFACE SYSTEM AGGREGATOR HUB DRIVER -M: Maximilian Luz -L: platform-driver-x86@vger.kernel.org -S: Maintained -F: drivers/platform/surface/surface_aggregator_hub.c - MICROTEK X6 SCANNER M: Oliver Neukum S: Maintained @@ -14022,12 +14141,12 @@ M: Luka Kovacic M: Luka Perkov S: Maintained -F: arch/arm/boot/dts/armada-xp-crs305-1g-4s-bit.dts -F: arch/arm/boot/dts/armada-xp-crs305-1g-4s.dts -F: arch/arm/boot/dts/armada-xp-crs326-24g-2s-bit.dts -F: arch/arm/boot/dts/armada-xp-crs326-24g-2s.dts -F: arch/arm/boot/dts/armada-xp-crs328-4c-20s-4s-bit.dts -F: arch/arm/boot/dts/armada-xp-crs328-4c-20s-4s.dts +F: arch/arm/boot/dts/marvell/armada-xp-crs305-1g-4s-bit.dts +F: arch/arm/boot/dts/marvell/armada-xp-crs305-1g-4s.dts +F: arch/arm/boot/dts/marvell/armada-xp-crs326-24g-2s-bit.dts +F: arch/arm/boot/dts/marvell/armada-xp-crs326-24g-2s.dts +F: arch/arm/boot/dts/marvell/armada-xp-crs328-4c-20s-4s-bit.dts +F: arch/arm/boot/dts/marvell/armada-xp-crs328-4c-20s-4s.dts MIPI CCS, SMIA AND SMIA++ IMAGE SENSOR DRIVER M: Sakari Ailus @@ -14130,7 +14249,7 @@ L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) S: Odd Fixes T: git git://git.kernel.org/pub/scm/linux/kernel/git/lkundrak/linux-mmp.git -F: arch/arm/boot/dts/mmp* +F: arch/arm/boot/dts/marvell/mmp* F: arch/arm/mach-mmp/ F: include/linux/soc/mmp/ @@ -14178,11 +14297,11 @@ L: linux-kernel@vger.kernel.org S: Maintained T: git git://git.kernel.org/pub/scm/linux/kernel/git/mcgrof/linux.git modules-next -F: include/linux/module.h F: include/linux/kmod.h +F: include/linux/module.h F: kernel/module/ -F: scripts/module* F: lib/test_kmod.c +F: scripts/module* F: tools/testing/selftests/kmod/ MONOLITHIC POWER SYSTEM PMIC DRIVER @@ -14568,6 +14687,7 @@ F: include/linux/netdevice.h F: include/uapi/linux/if_* F: include/uapi/linux/netdevice.h +X: drivers/net/wireless/ NETWORKING DRIVERS (WIRELESS) M: Kalle Valo @@ -14607,6 +14727,7 @@ T: git git://git.kernel.org/pub/scm/linux/kernel/git/netdev/net.git T: git git://git.kernel.org/pub/scm/linux/kernel/git/netdev/net-next.git F: Documentation/core-api/netlink.rst +F: Documentation/netlink/ F: Documentation/networking/ F: Documentation/process/maintainer-netdev.rst F: Documentation/userspace-api/netlink/ @@ -14623,6 +14744,7 @@ F: net/ F: tools/net/ F: tools/testing/selftests/net/ +X: net/bluetooth/ NETWORKING [IPSEC] M: Steffen Klassert @@ -14667,7 +14789,7 @@ M: Paul Moore L: netdev@vger.kernel.org L: linux-security-module@vger.kernel.org -S: Maintained +S: Supported W: https://github.com/netlabel F: Documentation/netlabel/ F: include/net/calipso.h @@ -14703,6 +14825,7 @@ M: Eric Dumazet L: netdev@vger.kernel.org S: Maintained +F: include/linux/net_mm.h F: include/linux/tcp.h F: include/net/tcp.h F: include/trace/events/tcp.h @@ -14771,6 +14894,7 @@ S: Maintained W: http://client.linux-nfs.org T: git git://git.linux-nfs.org/projects/trondmy/linux-nfs.git +F: Documentation/filesystems/nfs/ F: fs/lockd/ F: fs/nfs/ F: fs/nfs_common/ @@ -14780,7 +14904,6 @@ F: include/uapi/linux/nfs* F: include/uapi/linux/sunrpc/ F: net/sunrpc/ -F: Documentation/filesystems/nfs/ NILFS2 FILESYSTEM M: Ryusuke Konishi @@ -14896,7 +15019,7 @@ L: ntb@lists.linux.dev S: Supported W: https://github.com/jonmason/ntb/wiki -T: git git://github.com/jonmason/ntb.git +T: git https://github.com/jonmason/ntb.git F: drivers/net/ntb_netdev.c F: drivers/ntb/ F: drivers/pci/endpoint/functions/pci-epf-*ntb.c @@ -14920,6 +15043,7 @@ NTFS FILESYSTEM M: Anton Altaparmakov +R: Namjae Jeon L: linux-ntfs-dev@lists.sourceforge.net S: Supported W: http://www.tuxera.com/ @@ -14984,12 +15108,6 @@ F: drivers/nvme/target/fabrics-cmd-auth.c F: include/linux/nvme-auth.h -NVM EXPRESS HARDWARE MONITORING SUPPORT -M: Guenter Roeck -L: linux-nvme@lists.infradead.org -S: Supported -F: drivers/nvme/host/hwmon.c - NVM EXPRESS FC TRANSPORT DRIVERS M: James Smart L: linux-nvme@lists.infradead.org @@ -15000,6 +15118,12 @@ F: include/linux/nvme-fc-driver.h F: include/linux/nvme-fc.h +NVM EXPRESS HARDWARE MONITORING SUPPORT +M: Guenter Roeck +L: linux-nvme@lists.infradead.org +S: Supported +F: drivers/nvme/host/hwmon.c + NVM EXPRESS TARGET DRIVER M: Christoph Hellwig M: Sagi Grimberg @@ -15020,6 +15144,13 @@ F: include/linux/nvmem-consumer.h F: include/linux/nvmem-provider.h +NXP BLUETOOTH WIRELESS DRIVERS +M: Amitkumar Karwar +M: Neeraj Kale +S: Maintained +F: Documentation/devicetree/bindings/net/bluetooth/nxp,88w8987-bt.yaml +F: drivers/bluetooth/btnxpuart.c + NXP C45 TJA11XX PHY DRIVER M: Radu Pirea L: netdev@vger.kernel.org @@ -15045,16 +15176,17 @@ F: drivers/iio/gyro/fxas21002c_i2c.c F: drivers/iio/gyro/fxas21002c_spi.c -NXP i.MX CLOCK DRIVERS -M: Abel Vesa -R: Peng Fan -L: linux-clk@vger.kernel.org +NXP i.MX 7D/6SX/6UL/93 AND VF610 ADC DRIVER +M: Haibo Chen +L: linux-iio@vger.kernel.org L: linux-imx@nxp.com S: Maintained -T: git git://git.kernel.org/pub/scm/linux/kernel/git/abelvesa/linux.git clk/imx -F: Documentation/devicetree/bindings/clock/imx* -F: drivers/clk/imx/ -F: include/dt-bindings/clock/imx* +F: Documentation/devicetree/bindings/iio/adc/fsl,imx7d-adc.yaml +F: Documentation/devicetree/bindings/iio/adc/fsl,vf610-adc.yaml +F: Documentation/devicetree/bindings/iio/adc/nxp,imx93-adc.yaml +F: drivers/iio/adc/imx7d_adc.c +F: drivers/iio/adc/imx93_adc.c +F: drivers/iio/adc/vf610_adc.c NXP i.MX 8M ISI DRIVER M: Laurent Pinchart @@ -15063,6 +15195,15 @@ F: Documentation/devicetree/bindings/media/nxp,imx8-isi.yaml F: drivers/media/platform/nxp/imx8-isi/ +NXP i.MX 8MP DW100 V4L2 DRIVER +M: Xavier Roumegue +L: linux-media@vger.kernel.org +S: Maintained +F: Documentation/devicetree/bindings/media/nxp,dw100.yaml +F: Documentation/userspace-api/media/drivers/dw100.rst +F: drivers/media/platform/nxp/dw100/ +F: include/uapi/linux/dw100.h + NXP i.MX 8MQ DCSS DRIVER M: Laurentiu Palcu R: Lucas Stach @@ -15080,17 +15221,24 @@ F: Documentation/devicetree/bindings/iio/adc/nxp,imx8qxp-adc.yaml F: drivers/iio/adc/imx8qxp-adc.c -NXP i.MX 7D/6SX/6UL/93 AND VF610 ADC DRIVER -M: Haibo Chen -L: linux-iio@vger.kernel.org +NXP i.MX 8QXP/8QM JPEG V4L2 DRIVER +M: Mirela Rabulea +R: NXP Linux Team +L: linux-media@vger.kernel.org +S: Maintained +F: Documentation/devicetree/bindings/media/nxp,imx8-jpeg.yaml +F: drivers/media/platform/nxp/imx-jpeg + +NXP i.MX CLOCK DRIVERS +M: Abel Vesa +R: Peng Fan +L: linux-clk@vger.kernel.org L: linux-imx@nxp.com S: Maintained -F: Documentation/devicetree/bindings/iio/adc/fsl,imx7d-adc.yaml -F: Documentation/devicetree/bindings/iio/adc/fsl,vf610-adc.yaml -F: Documentation/devicetree/bindings/iio/adc/nxp,imx93-adc.yaml -F: drivers/iio/adc/imx7d_adc.c -F: drivers/iio/adc/imx93_adc.c -F: drivers/iio/adc/vf610_adc.c +T: git git://git.kernel.org/pub/scm/linux/kernel/git/abelvesa/linux.git clk/imx +F: Documentation/devicetree/bindings/clock/imx* +F: drivers/clk/imx/ +F: include/dt-bindings/clock/imx* NXP PF8100/PF8121A/PF8200 PMIC REGULATOR DEVICE DRIVER M: Jagan Teki @@ -15136,34 +15284,17 @@ F: Documentation/devicetree/bindings/sound/tfa9879.txt F: sound/soc/codecs/tfa9879* -NXP/Goodix TFA989X (TFA1) DRIVER -M: Stephan Gerhold -L: alsa-devel@alsa-project.org (moderated for non-subscribers) -S: Maintained -F: Documentation/devicetree/bindings/sound/nxp,tfa989x.yaml -F: sound/soc/codecs/tfa989x.c - NXP-NCI NFC DRIVER S: Orphan F: Documentation/devicetree/bindings/net/nfc/nxp,nci.yaml F: drivers/nfc/nxp-nci -NXP i.MX 8MP DW100 V4L2 DRIVER -M: Xavier Roumegue -L: linux-media@vger.kernel.org -S: Maintained -F: Documentation/devicetree/bindings/media/nxp,dw100.yaml -F: Documentation/userspace-api/media/drivers/dw100.rst -F: drivers/media/platform/nxp/dw100/ -F: include/uapi/linux/dw100.h - -NXP i.MX 8QXP/8QM JPEG V4L2 DRIVER -M: Mirela Rabulea -R: NXP Linux Team -L: linux-media@vger.kernel.org +NXP/Goodix TFA989X (TFA1) DRIVER +M: Stephan Gerhold +L: alsa-devel@alsa-project.org (moderated for non-subscribers) S: Maintained -F: Documentation/devicetree/bindings/media/nxp,imx8-jpeg.yaml -F: drivers/media/platform/nxp/imx-jpeg +F: Documentation/devicetree/bindings/sound/nxp,tfa989x.yaml +F: sound/soc/codecs/tfa989x.c NZXT-KRAKEN2 HARDWARE MONITORING DRIVER M: Jonas Malaco @@ -15251,19 +15382,13 @@ L: linux-omap@vger.kernel.org L: devicetree@vger.kernel.org S: Maintained -F: arch/arm/boot/dts/*am3* -F: arch/arm/boot/dts/*am4* -F: arch/arm/boot/dts/*am5* -F: arch/arm/boot/dts/*dra7* -F: arch/arm/boot/dts/*omap* -F: arch/arm/boot/dts/logicpd-som-lv* -F: arch/arm/boot/dts/logicpd-torpedo* +F: arch/arm/boot/dts/ti/omap/ OMAP DISPLAY SUBSYSTEM and FRAMEBUFFER SUPPORT (DSS2) L: linux-omap@vger.kernel.org L: linux-fbdev@vger.kernel.org S: Orphan -F: Documentation/arm/omap/dss.rst +F: Documentation/arch/arm/omap/dss.rst F: drivers/video/fbdev/omap2/ OMAP FRAMEBUFFER SUPPORT @@ -15365,7 +15490,7 @@ M: Mark Jackson L: linux-omap@vger.kernel.org S: Maintained -F: arch/arm/boot/dts/am335x-nano.dts +F: arch/arm/boot/dts/ti/omap/am335x-nano.dts OMAP1 SUPPORT M: Aaro Koskinen @@ -15392,6 +15517,7 @@ F: arch/arm/configs/omap2plus_defconfig F: arch/arm/mach-omap2/ F: drivers/bus/ti-sysc.c +F: drivers/gpio/gpio-tps65219.c F: drivers/i2c/busses/i2c-omap.c F: drivers/irqchip/irq-omap-intc.c F: drivers/mfd/*omap*.c @@ -15429,6 +15555,13 @@ S: Maintained F: drivers/media/i2c/og01a1b.c +OMNIVISION OV01A10 SENSOR DRIVER +M: Bingbu Cao +L: linux-media@vger.kernel.org +S: Maintained +T: git git://linuxtv.org/media_tree.git +F: drivers/media/i2c/ov01a10.c + OMNIVISION OV02A10 SENSOR DRIVER M: Dongchun Zhu L: linux-media@vger.kernel.org @@ -15689,8 +15822,8 @@ M: Frank Rowand L: devicetree@vger.kernel.org S: Maintained -C: irc://irc.libera.chat/devicetree W: http://www.devicetree.org/ +C: irc://irc.libera.chat/devicetree T: git git://git.kernel.org/pub/scm/linux/kernel/git/robh/linux.git F: Documentation/ABI/testing/sysfs-firmware-ofw F: drivers/of/ @@ -15706,8 +15839,8 @@ M: Conor Dooley L: devicetree@vger.kernel.org S: Maintained -C: irc://irc.libera.chat/devicetree Q: http://patchwork.ozlabs.org/project/devicetree-bindings/list/ +C: irc://irc.libera.chat/devicetree T: git git://git.kernel.org/pub/scm/linux/kernel/git/robh/linux.git F: Documentation/devicetree/ F: arch/*/boot/dts/ @@ -15720,13 +15853,6 @@ S: Maintained F: drivers/ptp/ptp_ocp.c -INTEL PTP DFL ToD DRIVER -M: Tianfei Zhang -L: linux-fpga@vger.kernel.org -L: netdev@vger.kernel.org -S: Maintained -F: drivers/ptp/ptp_dfl_tod.c - OPENCORES I2C BUS DRIVER M: Peter Korsgaard M: Andrew Lunn @@ -15745,8 +15871,8 @@ S: Maintained W: http://openrisc.io T: git https://github.com/openrisc/linux.git -F: Documentation/devicetree/bindings/openrisc/ F: Documentation/arch/openrisc/ +F: Documentation/devicetree/bindings/openrisc/ F: arch/openrisc/ F: drivers/irqchip/irq-ompic.c F: drivers/irqchip/irq-or1k-* @@ -15784,7 +15910,7 @@ M: Mark Fasheh M: Joel Becker M: Joseph Qi -L: ocfs2-devel@oss.oracle.com (moderated for non-subscribers) +L: ocfs2-devel@lists.linux.dev S: Supported W: http://ocfs2.wiki.kernel.org F: Documentation/filesystems/dlmfs.rst @@ -15819,6 +15945,7 @@ OVERLAY FILESYSTEM M: Miklos Szeredi +M: Amir Goldstein L: linux-unionfs@vger.kernel.org S: Supported T: git git://git.kernel.org/pub/scm/linux/kernel/git/mszeredi/vfs.git @@ -15921,7 +16048,7 @@ PARAVIRT_OPS INTERFACE M: Juergen Gross -M: Srivatsa S. Bhat (VMware) +R: Ajay Kaher R: Alexey Makhalov R: VMware PV-Drivers Reviewers L: virtualization@lists.linux-foundation.org @@ -16062,6 +16189,14 @@ S: Maintained F: drivers/pci/controller/dwc/*layerscape* +PCI DRIVER FOR FU740 +M: Paul Walmsley +M: Greentime Hu +L: linux-pci@vger.kernel.org +S: Maintained +F: Documentation/devicetree/bindings/pci/sifive,fu740-pcie.yaml +F: drivers/pci/controller/dwc/pcie-fu740.c + PCI DRIVER FOR GENERIC OF HOSTS M: Will Deacon L: linux-pci@vger.kernel.org @@ -16082,14 +16217,6 @@ F: Documentation/devicetree/bindings/pci/fsl,imx6q-pcie.yaml F: drivers/pci/controller/dwc/*imx6* -PCI DRIVER FOR FU740 -M: Paul Walmsley -M: Greentime Hu -L: linux-pci@vger.kernel.org -S: Maintained -F: Documentation/devicetree/bindings/pci/sifive,fu740-pcie.yaml -F: drivers/pci/controller/dwc/pcie-fu740.c - PCI DRIVER FOR INTEL IXP4XX M: Linus Walleij S: Maintained @@ -16167,10 +16294,11 @@ PCI DRIVER FOR SYNOPSYS DESIGNWARE M: Jingoo Han M: Gustavo Pimentel +M: Manivannan Sadhasivam L: linux-pci@vger.kernel.org S: Maintained -F: Documentation/devicetree/bindings/pci/snps,dw-pcie.yaml F: Documentation/devicetree/bindings/pci/snps,dw-pcie-ep.yaml +F: Documentation/devicetree/bindings/pci/snps,dw-pcie.yaml F: drivers/pci/controller/dwc/*designware* PCI DRIVER FOR TI DRA7XX/J721E @@ -16190,6 +16318,14 @@ F: Documentation/devicetree/bindings/pci/v3-v360epc-pci.txt F: drivers/pci/controller/pci-v3-semi.c +PCI DRIVER FOR XILINX VERSAL CPM +M: Bharat Kumar Gogada +M: Michal Simek +L: linux-pci@vger.kernel.org +S: Maintained +F: Documentation/devicetree/bindings/pci/xilinx-versal-cpm.yaml +F: drivers/pci/controller/pcie-xilinx-cpm.c + PCI ENDPOINT SUBSYSTEM M: Lorenzo Pieralisi M: Krzysztof WilczyÅ„ski @@ -16227,19 +16363,6 @@ S: Supported F: Documentation/PCI/pci-error-recovery.rst -PCI PEER-TO-PEER DMA (P2PDMA) -M: Bjorn Helgaas -M: Logan Gunthorpe -L: linux-pci@vger.kernel.org -S: Supported -Q: https://patchwork.kernel.org/project/linux-pci/list/ -B: https://bugzilla.kernel.org -C: irc://irc.oftc.net/linux-pci -T: git git://git.kernel.org/pub/scm/linux/kernel/git/pci/pci.git -F: Documentation/driver-api/pci/p2pdma.rst -F: drivers/pci/p2pdma.c -F: include/linux/pci-p2pdma.h - PCI MSI DRIVER FOR ALTERA MSI IP M: Joyce Ooi L: linux-pci@vger.kernel.org @@ -16270,6 +16393,19 @@ F: drivers/pci/pci-bridge-emul.c F: drivers/pci/pci-bridge-emul.h +PCI PEER-TO-PEER DMA (P2PDMA) +M: Bjorn Helgaas +M: Logan Gunthorpe +L: linux-pci@vger.kernel.org +S: Supported +Q: https://patchwork.kernel.org/project/linux-pci/list/ +B: https://bugzilla.kernel.org +C: irc://irc.oftc.net/linux-pci +T: git git://git.kernel.org/pub/scm/linux/kernel/git/pci/pci.git +F: Documentation/driver-api/pci/p2pdma.rst +F: drivers/pci/p2pdma.c +F: include/linux/pci-p2pdma.h + PCI SUBSYSTEM M: Bjorn Helgaas L: linux-pci@vger.kernel.org @@ -16349,7 +16485,7 @@ F: drivers/pci/controller/dwc/pcie-keembay.c PCIE DRIVER FOR INTEL LGM GW SOC -M: Rahul Tanwar +M: Chuanhua Lei L: linux-pci@vger.kernel.org S: Maintained F: Documentation/devicetree/bindings/pci/intel-gw-pcie.yaml @@ -16378,14 +16514,6 @@ S: Maintained F: drivers/pci/controller/dwc/pcie-qcom.c -PCIE ENDPOINT DRIVER FOR QUALCOMM -M: Manivannan Sadhasivam -L: linux-pci@vger.kernel.org -L: linux-arm-msm@vger.kernel.org -S: Maintained -F: Documentation/devicetree/bindings/pci/qcom,pcie-ep.yaml -F: drivers/pci/controller/dwc/pcie-qcom-ep.c - PCIE DRIVER FOR ROCKCHIP M: Shawn Lin L: linux-pci@vger.kernel.org @@ -16407,13 +16535,13 @@ S: Maintained F: drivers/pci/controller/dwc/*spear* -PCI DRIVER FOR XILINX VERSAL CPM -M: Bharat Kumar Gogada -M: Michal Simek +PCIE ENDPOINT DRIVER FOR QUALCOMM +M: Manivannan Sadhasivam L: linux-pci@vger.kernel.org +L: linux-arm-msm@vger.kernel.org S: Maintained -F: Documentation/devicetree/bindings/pci/xilinx-versal-cpm.yaml -F: drivers/pci/controller/pcie-xilinx-cpm.c +F: Documentation/devicetree/bindings/pci/qcom,pcie-ep.yaml +F: drivers/pci/controller/dwc/pcie-qcom-ep.c PCMCIA SUBSYSTEM M: Dominik Brodowski @@ -16437,6 +16565,10 @@ F: crypto/pcrypt.c F: include/crypto/pcrypt.h +PDS DSC VIRTIO DATA PATH ACCELERATOR +R: Shannon Nelson +F: drivers/vdpa/pds/ + PECI HARDWARE MONITORING DRIVERS M: Iwona Winiarska L: linux-hwmon@vger.kernel.org @@ -16664,7 +16796,7 @@ M: Bjorn Andersson L: linux-arm-msm@vger.kernel.org S: Maintained -F: Documentation/devicetree/bindings/pinctrl/qcom,*.txt +F: Documentation/devicetree/bindings/pinctrl/qcom,* F: drivers/pinctrl/qcom/ PIN CONTROLLER - RENESAS @@ -16683,9 +16815,9 @@ L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) L: linux-samsung-soc@vger.kernel.org S: Maintained -C: irc://irc.libera.chat/linux-exynos Q: https://patchwork.kernel.org/project/linux-samsung-soc/list/ B: mailto:linux-samsung-soc@vger.kernel.org +C: irc://irc.libera.chat/linux-exynos T: git git://git.kernel.org/pub/scm/linux/kernel/git/pinctrl/samsung.git F: Documentation/devicetree/bindings/pinctrl/samsung,pinctrl*yaml F: drivers/pinctrl/samsung/ @@ -16747,13 +16879,6 @@ S: Maintained F: drivers/dma/plx_dma.c -PM6764TR DRIVER -M: Charles Hsu -L: linux-hwmon@vger.kernel.org -S: Maintained -F: Documentation/hwmon/pm6764tr.rst -F: drivers/hwmon/pmbus/pm6764tr.c - PM-GRAPH UTILITY M: "Todd E Brandt" L: linux-pm@vger.kernel.org @@ -16763,6 +16888,13 @@ T: git git://github.com/intel/pm-graph F: tools/power/pm-graph +PM6764TR DRIVER +M: Charles Hsu +L: linux-hwmon@vger.kernel.org +S: Maintained +F: Documentation/hwmon/pm6764tr.rst +F: drivers/hwmon/pmbus/pm6764tr.c + PMBUS HARDWARE MONITORING DRIVERS M: Guenter Roeck L: linux-hwmon@vger.kernel.org @@ -16843,15 +16975,6 @@ F: include/linux/powercap.h F: kernel/configs/nopm.config -DYNAMIC THERMAL POWER MANAGEMENT (DTPM) -M: Daniel Lezcano -L: linux-pm@vger.kernel.org -S: Supported -B: https://bugzilla.kernel.org -T: git git://git.kernel.org/pub/scm/linux/kernel/git/rafael/linux-pm -F: drivers/powercap/dtpm* -F: include/linux/dtpm.h - POWER STATE COORDINATION INTERFACE (PSCI) M: Mark Rutland M: Lorenzo Pieralisi @@ -17010,8 +17133,8 @@ L: linux-hardening@vger.kernel.org S: Supported T: git git://git.kernel.org/pub/scm/linux/kernel/git/kees/linux.git for-next/pstore -F: Documentation/admin-guide/ramoops.rst F: Documentation/admin-guide/pstore-blk.rst +F: Documentation/admin-guide/ramoops.rst F: Documentation/devicetree/bindings/reserved-memory/ramoops.yaml F: drivers/acpi/apei/erst.c F: drivers/firmware/efi/efi-pstore.c @@ -17128,7 +17251,7 @@ S: Maintained T: git git://github.com/hzhuang1/linux.git T: git git://github.com/rjarzmik/linux.git -F: arch/arm/boot/dts/pxa* +F: arch/arm/boot/dts/intel/pxa/ F: arch/arm/mach-pxa/ F: drivers/dma/pxa* F: drivers/pcmcia/pxa2xx* @@ -17160,12 +17283,13 @@ F: sound/soc/codecs/lpass-wsa-macro.* F: sound/soc/codecs/msm8916-wcd-analog.c F: sound/soc/codecs/msm8916-wcd-digital.c -F: sound/soc/codecs/wcd9335.* -F: sound/soc/codecs/wcd934x.c F: sound/soc/codecs/wcd-clsh-v2.* F: sound/soc/codecs/wcd-mbhc-v2.* +F: sound/soc/codecs/wcd9335.* +F: sound/soc/codecs/wcd934x.c F: sound/soc/codecs/wsa881x.c F: sound/soc/codecs/wsa883x.c +F: sound/soc/codecs/wsa884x.c F: sound/soc/qcom/ QCOM EMBEDDED USB DEBUGGER (EUD) @@ -17320,35 +17444,41 @@ T: git git://linuxtv.org/anttip/media_tree.git F: drivers/media/tuners/qt1010* +QUALCOMM ATH12K WIRELESS DRIVER +M: Kalle Valo +M: Jeff Johnson +L: ath12k@lists.infradead.org +S: Supported +T: git git://git.kernel.org/pub/scm/linux/kernel/git/kvalo/ath.git +F: drivers/net/wireless/ath/ath12k/ + QUALCOMM ATHEROS ATH10K WIRELESS DRIVER M: Kalle Valo +M: Jeff Johnson L: ath10k@lists.infradead.org S: Supported W: https://wireless.wiki.kernel.org/en/users/Drivers/ath10k T: git git://git.kernel.org/pub/scm/linux/kernel/git/kvalo/ath.git -F: drivers/net/wireless/ath/ath10k/ F: Documentation/devicetree/bindings/net/wireless/qcom,ath10k.yaml +F: drivers/net/wireless/ath/ath10k/ QUALCOMM ATHEROS ATH11K WIRELESS DRIVER M: Kalle Valo +M: Jeff Johnson L: ath11k@lists.infradead.org S: Supported +W: https://wireless.wiki.kernel.org/en/users/Drivers/ath11k +B: https://wireless.wiki.kernel.org/en/users/Drivers/ath11k/bugreport T: git git://git.kernel.org/pub/scm/linux/kernel/git/kvalo/ath.git F: Documentation/devicetree/bindings/net/wireless/qcom,ath11k.yaml F: drivers/net/wireless/ath/ath11k/ -QUALCOMM ATH12K WIRELESS DRIVER -M: Kalle Valo -L: ath12k@lists.infradead.org -S: Supported -T: git git://git.kernel.org/pub/scm/linux/kernel/git/kvalo/ath.git -F: drivers/net/wireless/ath/ath12k/ - QUALCOMM ATHEROS ATH9K WIRELESS DRIVER M: Toke Høiland-Jørgensen L: linux-wireless@vger.kernel.org S: Maintained W: https://wireless.wiki.kernel.org/en/users/Drivers/ath9k +T: git git://git.kernel.org/pub/scm/linux/kernel/git/kvalo/ath.git F: Documentation/devicetree/bindings/net/wireless/qca,ath9k.yaml F: drivers/net/wireless/ath/ath9k/ @@ -17381,6 +17511,8 @@ QUALCOMM CLOUD AI (QAIC) DRIVER M: Jeffrey Hugo +R: Carl Vanderlip +R: Pranjal Ramajor Asha Kanojiya L: linux-arm-msm@vger.kernel.org L: dri-devel@lists.freedesktop.org S: Supported @@ -17424,6 +17556,7 @@ M: Vinod Koul R: Bhupesh Sharma L: netdev@vger.kernel.org +L: linux-arm-msm@vger.kernel.org S: Maintained F: Documentation/devicetree/bindings/net/qcom,ethqos.yaml F: drivers/net/ethernet/stmicro/stmmac/dwmac-qcom-ethqos.c @@ -17440,8 +17573,8 @@ QUALCOMM HEXAGON ARCHITECTURE M: Brian Cain L: linux-hexagon@vger.kernel.org -T: git git://git.kernel.org/pub/scm/linux/kernel/git/bcain/linux.git S: Supported +T: git git://git.kernel.org/pub/scm/linux/kernel/git/bcain/linux.git F: arch/hexagon/ QUALCOMM HIDMA DRIVER @@ -17533,9 +17666,18 @@ F: Documentation/devicetree/bindings/thermal/qcom-tsens.yaml F: drivers/thermal/qcom/ +QUALCOMM TYPEC PORT MANAGER DRIVER +M: Bryan O'Donoghue +L: linux-arm-msm@vger.kernel.org +L: linux-usb@vger.kernel.org +S: Maintained +F: Documentation/devicetree/bindings/usb/qcom,pmic-*.yaml +F: drivers/usb/typec/tcpm/qcom/ + QUALCOMM VENUS VIDEO ACCELERATOR DRIVER M: Stanimir Varbanov M: Vikash Garodia +R: Bryan O'Donoghue L: linux-media@vger.kernel.org L: linux-arm-msm@vger.kernel.org S: Maintained @@ -17563,9 +17705,9 @@ M: Pan, Xinhui L: amd-gfx@lists.freedesktop.org S: Supported -T: git https://gitlab.freedesktop.org/agd5f/linux.git B: https://gitlab.freedesktop.org/drm/amd/-/issues C: irc://irc.oftc.net/radeon +T: git https://gitlab.freedesktop.org/agd5f/linux.git F: Documentation/gpu/amdgpu/ F: drivers/gpu/drm/amd/ F: drivers/gpu/drm/radeon/ @@ -17653,8 +17795,8 @@ RANDOM NUMBER DRIVER M: "Theodore Ts'o" M: Jason A. Donenfeld -T: git https://git.kernel.org/pub/scm/linux/kernel/git/crng/random.git S: Maintained +T: git https://git.kernel.org/pub/scm/linux/kernel/git/crng/random.git F: drivers/char/random.c F: drivers/virt/vmgenid.c @@ -17688,8 +17830,8 @@ F: Documentation/driver-api/media/rc-core.rst F: Documentation/userspace-api/media/rc/ F: drivers/media/rc/ -F: include/media/rc-map.h F: include/media/rc-core.h +F: include/media/rc-map.h F: include/uapi/linux/lirc.h RCMM REMOTE CONTROLS DECODER @@ -17778,7 +17920,7 @@ R: Steven Rostedt R: Mathieu Desnoyers R: Lai Jiangshan -R: Zqiang +R: Zqiang L: rcu@vger.kernel.org S: Supported W: http://www.rdrop.com/users/paulmck/RCU/ @@ -17806,6 +17948,14 @@ F: include/uapi/linux/rtc.h F: tools/testing/selftests/rtc/ +Real-time Linux Analysis (RTLA) tools +M: Daniel Bristot de Oliveira +M: Steven Rostedt +L: linux-trace-kernel@vger.kernel.org +S: Maintained +F: Documentation/tools/rtla/ +F: tools/tracing/rtla/ + REALTEK AUDIO CODECS M: Oder Chiou S: Maintained @@ -17835,7 +17985,7 @@ F: drivers/net/wireless/realtek/rtlwifi/ REALTEK WIRELESS DRIVER (rtw88) -M: Yan-Hsuan Chuang +M: Ping-Ke Shih L: linux-wireless@vger.kernel.org S: Maintained F: drivers/net/wireless/realtek/rtw88/ @@ -17929,6 +18079,14 @@ F: Documentation/devicetree/bindings/sound/renesas,idt821034.yaml F: sound/soc/codecs/idt821034.c +RENESAS R-CAR GEN3 & RZ/N1 NAND CONTROLLER DRIVER +M: Miquel Raynal +L: linux-mtd@lists.infradead.org +L: linux-renesas-soc@vger.kernel.org +S: Maintained +F: Documentation/devicetree/bindings/mtd/renesas-nandc.yaml +F: drivers/mtd/nand/raw/renesas-nand-controller.c + RENESAS R-CAR GYROADC DRIVER M: Marek Vasut L: linux-iio@vger.kernel.org @@ -17947,9 +18105,9 @@ RENESAS R-CAR SATA DRIVER R: Sergey Shtylyov -S: Supported L: linux-ide@vger.kernel.org L: linux-renesas-soc@vger.kernel.org +S: Supported F: Documentation/devicetree/bindings/ata/renesas,rcar-sata.yaml F: drivers/ata/sata_rcar.c @@ -17969,12 +18127,6 @@ F: Documentation/devicetree/bindings/i2c/renesas,riic.yaml F: drivers/i2c/busses/i2c-riic.c -RENESAS USB PHY DRIVER -M: Yoshihiro Shimoda -L: linux-renesas-soc@vger.kernel.org -S: Maintained -F: drivers/phy/renesas/phy-rcar-gen3-usb*.c - RENESAS RZ/G2L A/D DRIVER M: Lad Prabhakar L: linux-iio@vger.kernel.org @@ -18020,13 +18172,19 @@ F: Documentation/devicetree/bindings/usb/renesas,rzn1-usbf.yaml F: drivers/usb/gadget/udc/renesas_usbf.c -RENESAS R-CAR GEN3 & RZ/N1 NAND CONTROLLER DRIVER -M: Miquel Raynal -L: linux-mtd@lists.infradead.org +RENESAS RZ/V2M I2C DRIVER +M: Fabrizio Castro +L: linux-i2c@vger.kernel.org +L: linux-renesas-soc@vger.kernel.org +S: Supported +F: Documentation/devicetree/bindings/i2c/renesas,rzv2m.yaml +F: drivers/i2c/busses/i2c-rzv2m.c + +RENESAS USB PHY DRIVER +M: Yoshihiro Shimoda L: linux-renesas-soc@vger.kernel.org S: Maintained -F: Documentation/devicetree/bindings/mtd/renesas-nandc.yaml -F: drivers/mtd/nand/raw/renesas-nand-controller.c +F: drivers/phy/renesas/phy-rcar-gen3-usb*.c RENESAS VERSACLOCK 7 CLOCK DRIVER M: Alex Helms @@ -18034,6 +18192,13 @@ F: Documentation/devicetree/bindings/clock/renesas,versaclock7.yaml F: drivers/clk/clk-versaclock7.c +RENESAS X9250 DIGITAL POTENTIOMETERS DRIVER +M: Herve Codina +L: linux-iio@vger.kernel.org +S: Maintained +F: Documentation/devicetree/bindings/iio/potentiometer/renesas,x9250.yaml +F: drivers/iio/potentiometer/x9250.c + RESET CONTROLLER FRAMEWORK M: Philipp Zabel S: Maintained @@ -18094,15 +18259,6 @@ F: drivers/mtd/nand/raw/r852.c F: drivers/mtd/nand/raw/r852.h -RISC-V PMU DRIVERS -M: Atish Patra -R: Anup Patel -L: linux-riscv@lists.infradead.org -S: Supported -F: drivers/perf/riscv_pmu.c -F: drivers/perf/riscv_pmu_legacy.c -F: drivers/perf/riscv_pmu_sbi.c - RISC-V ARCHITECTURE M: Paul Walmsley M: Palmer Dabbelt @@ -18138,6 +18294,7 @@ F: drivers/i2c/busses/i2c-microchip-corei2c.c F: drivers/mailbox/mailbox-mpfs.c F: drivers/pci/controller/pcie-microchip-host.c +F: drivers/pwm/pwm-microchip-core.c F: drivers/reset/reset-mpfs.c F: drivers/rtc/rtc-mpfs.c F: drivers/soc/microchip/mpfs-sys-controller.c @@ -18154,6 +18311,25 @@ T: git https://git.kernel.org/pub/scm/linux/kernel/git/conor/linux.git/ F: Documentation/devicetree/bindings/riscv/ F: arch/riscv/boot/dts/ +X: arch/riscv/boot/dts/allwinner/ +X: arch/riscv/boot/dts/renesas/ + +RISC-V PMU DRIVERS +M: Atish Patra +R: Anup Patel +L: linux-riscv@lists.infradead.org +S: Supported +F: drivers/perf/riscv_pmu.c +F: drivers/perf/riscv_pmu_legacy.c +F: drivers/perf/riscv_pmu_sbi.c + +RISC-V THEAD SoC SUPPORT +M: Jisheng Zhang +M: Guo Ren +M: Fu Wei +L: linux-riscv@lists.infradead.org +S: Maintained +F: arch/riscv/boot/dts/thead/ RNBD BLOCK DRIVERS M: Md. Haris Iqbal @@ -18191,7 +18367,7 @@ S: Maintained F: Documentation/admin-guide/media/rkisp1.rst F: Documentation/devicetree/bindings/media/rockchip-isp1.yaml -F: Documentation/userspace-api/media/v4l/pixfmt-meta-rkisp1.rst +F: Documentation/userspace-api/media/v4l/metafmt-rkisp1.rst F: drivers/media/platform/rockchip/rkisp1 F: include/uapi/linux/rkisp1-config.h @@ -18236,10 +18412,11 @@ F: Documentation/devicetree/bindings/iio/light/bh1750.yaml F: drivers/iio/light/bh1750.c -ROHM BU27034 AMBIENT LIGHT SENSOR DRIVER +ROHM BU270xx LIGHT SENSOR DRIVERs M: Matti Vaittinen L: linux-iio@vger.kernel.org S: Supported +F: drivers/iio/light/rohm-bu27008.c F: drivers/iio/light/rohm-bu27034.c ROHM MULTIFUNCTION BD9571MWV-M PMIC DEVICE DRIVERS @@ -18333,17 +18510,14 @@ L: linux-wireless@vger.kernel.org S: Orphan W: https://wireless.wiki.kernel.org/ -T: git git://git.kernel.org/pub/scm/linux/kernel/git/linville/wireless-testing.git F: drivers/net/wireless/realtek/rtl818x/rtl8180/ RTL8187 WIRELESS DRIVER -M: Herton Ronaldo Krzesinski -M: Hin-Tak Leung +M: Hin-Tak Leung M: Larry Finger L: linux-wireless@vger.kernel.org S: Maintained W: https://wireless.wiki.kernel.org/ -T: git git://git.kernel.org/pub/scm/linux/kernel/git/linville/wireless-testing.git F: drivers/net/wireless/realtek/rtl818x/rtl8187/ RTL8XXXU WIRELESS DRIVER (rtl8xxxu) @@ -18363,7 +18537,7 @@ RUNTIME VERIFICATION (RV) M: Daniel Bristot de Oliveira M: Steven Rostedt -L: linux-trace-devel@vger.kernel.org +L: linux-trace-kernel@vger.kernel.org S: Maintained F: Documentation/trace/rv/ F: include/linux/rv.h @@ -18459,14 +18633,6 @@ F: include/net/iucv/ F: net/iucv/ -S390 NETWORK DRIVERS -M: Alexandra Winter -M: Wenjia Zhang -L: linux-s390@vger.kernel.org -L: netdev@vger.kernel.org -S: Supported -F: drivers/s390/net/ - S390 MM M: Alexander Gordeev M: Gerald Schaefer @@ -18476,14 +18642,22 @@ F: arch/s390/include/asm/pgtable.h F: arch/s390/mm +S390 NETWORK DRIVERS +M: Alexandra Winter +M: Wenjia Zhang +L: linux-s390@vger.kernel.org +L: netdev@vger.kernel.org +S: Supported +F: drivers/s390/net/ + S390 PCI SUBSYSTEM M: Niklas Schnelle M: Gerald Schaefer L: linux-s390@vger.kernel.org S: Supported +F: Documentation/s390/pci.rst F: arch/s390/pci/ F: drivers/pci/hotplug/s390_pci_hpc.c -F: Documentation/s390/pci.rst S390 SCM DRIVER M: Vineeth Vijayan @@ -18568,10 +18742,9 @@ F: security/safesetid/ SAMSUNG AUDIO (ASoC) DRIVERS -M: Krzysztof Kozlowski M: Sylwester Nawrocki L: alsa-devel@alsa-project.org (moderated for non-subscribers) -S: Supported +S: Maintained B: mailto:linux-samsung-soc@vger.kernel.org F: Documentation/devicetree/bindings/sound/samsung* F: sound/soc/samsung/ @@ -18699,7 +18872,6 @@ F: include/linux/clk/samsung.h SAMSUNG SPI DRIVERS -M: Krzysztof Kozlowski M: Andi Shyti L: linux-spi@vger.kernel.org L: linux-samsung-soc@vger.kernel.org @@ -18740,7 +18912,7 @@ M: Paul Barker R: Marc Murphy S: Supported -F: arch/arm/boot/dts/am335x-sancloud* +F: arch/arm/boot/dts/ti/omap/am335x-sancloud* SC1200 WDT DRIVER M: Zwane Mwaikambo @@ -18767,6 +18939,16 @@ F: include/uapi/linux/sched.h F: kernel/sched/ +SCSI LIBSAS SUBSYSTEM +R: John Garry +R: Jason Yan +L: linux-scsi@vger.kernel.org +S: Supported +F: Documentation/scsi/libsas.rst +F: drivers/scsi/libsas/ +F: include/scsi/libsas.h +F: include/scsi/sas_ata.h + SCSI RDMA PROTOCOL (SRP) INITIATOR M: Bart Van Assche L: linux-rdma@vger.kernel.org @@ -18835,12 +19017,11 @@ F: include/target/ SCTP PROTOCOL -M: Neil Horman M: Marcelo Ricardo Leitner M: Xin Long L: linux-sctp@vger.kernel.org S: Maintained -W: http://lksctp.sourceforge.net +W: https://github.com/sctp/lksctp-tools/wiki F: Documentation/networking/sctp.rst F: include/linux/sctp.h F: include/net/sctp/ @@ -18896,7 +19077,7 @@ K: \bTIF_SECCOMP\b SECURE DIGITAL HOST CONTROLLER INTERFACE (SDHCI) Broadcom BRCMSTB DRIVER -M: Kamal Dasu +M: Kamal Dasu M: Al Cooper R: Broadcom internal kernel review list L: linux-mmc@vger.kernel.org @@ -18916,6 +19097,13 @@ S: Supported F: drivers/mmc/host/sdhci-of-at91.c +SECURE DIGITAL HOST CONTROLLER INTERFACE (SDHCI) NXP i.MX DRIVER +M: Haibo Chen +L: linux-imx@nxp.com +L: linux-mmc@vger.kernel.org +S: Maintained +F: drivers/mmc/host/sdhci-esdhc-imx.c + SECURE DIGITAL HOST CONTROLLER INTERFACE (SDHCI) SAMSUNG DRIVER M: Ben Dooks M: Jaehoon Chung @@ -18935,13 +19123,6 @@ S: Maintained F: drivers/mmc/host/sdhci-omap.c -SECURE DIGITAL HOST CONTROLLER INTERFACE (SDHCI) NXP i.MX DRIVER -M: Haibo Chen -L: linux-imx@nxp.com -L: linux-mmc@vger.kernel.org -S: Maintained -F: drivers/mmc/host/sdhci-esdhc-imx.c - SECURE ENCRYPTING DEVICE (SED) OPAL DRIVER M: Jonathan Derrick L: linux-block@vger.kernel.org @@ -18951,6 +19132,15 @@ F: include/linux/sed* F: include/uapi/linux/sed* +SECURE MONITOR CALL(SMC) CALLING CONVENTION (SMCCC) +M: Mark Rutland +M: Lorenzo Pieralisi +M: Sudeep Holla +L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) +S: Maintained +F: drivers/firmware/smccc/ +F: include/linux/arm-smccc.h + SECURITY CONTACT M: Security Officers S: Supported @@ -19034,13 +19224,6 @@ F: drivers/tty/serdev/ F: include/linux/serdev.h -SERIAL DRIVERS -M: Greg Kroah-Hartman -L: linux-serial@vger.kernel.org -S: Maintained -F: Documentation/devicetree/bindings/serial/ -F: drivers/tty/serial/ - SERIAL IR RECEIVER M: Sean Young L: linux-media@vger.kernel.org @@ -19100,6 +19283,9 @@ M: Karsten Graul M: Wenjia Zhang M: Jan Karcher +R: D. Wythe +R: Tony Lu +R: Wen Gu L: linux-s390@vger.kernel.org S: Supported F: net/smc/ @@ -19400,15 +19586,6 @@ S: Odd Fixes F: drivers/net/ethernet/smsc/smc91x.* -SECURE MONITOR CALL(SMC) CALLING CONVENTION (SMCCC) -M: Mark Rutland -M: Lorenzo Pieralisi -M: Sudeep Holla -L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) -S: Maintained -F: drivers/firmware/smccc/ -F: include/linux/arm-smccc.h - SMM665 HARDWARE MONITOR DRIVER M: Guenter Roeck L: linux-hwmon@vger.kernel.org @@ -19456,6 +19633,10 @@ S: Maintained F: drivers/net/ethernet/smsc/smsc9420.* +SNET DPU VIRTIO DATA PATH ACCELERATOR +R: Alvaro Karsz +F: drivers/vdpa/solidrun/ + SOCIONEXT (SNI) AVE NETWORK DRIVER M: Kunihiko Hayashi L: netdev@vger.kernel.org @@ -19563,15 +19744,15 @@ SOLIDRUN CLEARFOG SUPPORT M: Russell King S: Maintained -F: arch/arm/boot/dts/armada-388-clearfog* -F: arch/arm/boot/dts/armada-38x-solidrun-* +F: arch/arm/boot/dts/marvell/armada-388-clearfog* +F: arch/arm/boot/dts/marvell/armada-38x-solidrun-* SOLIDRUN CUBOX-I/HUMMINGBOARD SUPPORT M: Russell King S: Maintained -F: arch/arm/boot/dts/imx6*-cubox-i* -F: arch/arm/boot/dts/imx6*-hummingboard* -F: arch/arm/boot/dts/imx6*-sr-* +F: arch/arm/boot/dts/nxp/imx/imx6*-cubox-i* +F: arch/arm/boot/dts/nxp/imx/imx6*-hummingboard* +F: arch/arm/boot/dts/nxp/imx/imx6*-sr-* SONIC NETWORK DRIVER M: Thomas Bogendoerfer @@ -19725,6 +19906,13 @@ F: sound/ F: tools/testing/selftests/alsa +SOUND - ALSA SELFTESTS +M: Mark Brown +L: alsa-devel@alsa-project.org (moderated for non-subscribers) +L: linux-kselftest@vger.kernel.org +S: Supported +F: tools/testing/selftests/alsa + SOUND - COMPRESSED AUDIO M: Vinod Koul L: alsa-devel@alsa-project.org (moderated for non-subscribers) @@ -19743,13 +19931,6 @@ F: sound/core/pcm_dmaengine.c F: sound/soc/soc-generic-dmaengine-pcm.c -SOUND - ALSA SELFTESTS -M: Mark Brown -L: alsa-devel@alsa-project.org (moderated for non-subscribers) -L: linux-kselftest@vger.kernel.org -S: Supported -F: tools/testing/selftests/alsa - SOUND - SOC LAYER / DYNAMIC AUDIO POWER MANAGEMENT (ASoC) M: Liam Girdwood M: Mark Brown @@ -19769,8 +19950,8 @@ M: Peter Ujfalusi M: Bard Liao M: Ranjani Sridharan -R: Kai Vehmanen M: Daniel Baluta +R: Kai Vehmanen L: sound-open-firmware@alsa-project.org (moderated for non-subscribers) S: Supported W: https://github.com/thesofproject/linux/ @@ -19832,9 +20013,9 @@ L: linux-sparse@vger.kernel.org S: Maintained W: https://sparse.docs.kernel.org/ -T: git git://git.kernel.org/pub/scm/devel/sparse/sparse.git Q: https://patchwork.kernel.org/project/linux-sparse/list/ B: https://bugzilla.kernel.org/enter_bug.cgi?component=Sparse&product=Tools +T: git git://git.kernel.org/pub/scm/devel/sparse/sparse.git F: include/linux/compiler.h SPEAKUP CONSOLE SPEECH DRIVER @@ -19856,7 +20037,7 @@ L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) S: Maintained W: http://www.st.com/spear -F: arch/arm/boot/dts/spear* +F: arch/arm/boot/dts/st/spear* F: arch/arm/mach-spear/ F: drivers/clk/spear/ F: drivers/pinctrl/spear/ @@ -20069,6 +20250,13 @@ S: Odd Fixes F: drivers/net/ethernet/adaptec/starfire* +STARFIVE CRYPTO DRIVER +M: Jia Jie Ho +M: William Qiu +S: Supported +F: Documentation/devicetree/bindings/crypto/starfive* +F: drivers/crypto/starfive/ + STARFIVE DEVICETREES M: Emil Renner Berthing S: Maintained @@ -20087,6 +20275,12 @@ F: Documentation/devicetree/bindings/mmc/starfive* F: drivers/mmc/host/dw_mmc-starfive.c +STARFIVE JH7110 TDM DRIVER +M: Walker Chen +S: Maintained +F: Documentation/devicetree/bindings/sound/starfive,jh7110-tdm.yaml +F: sound/soc/starfive/jh7110_tdm.c + STARFIVE JH71X0 CLOCK DRIVERS M: Emil Renner Berthing M: Hal Feng @@ -20113,6 +20307,12 @@ F: drivers/reset/starfive/reset-starfive-jh71* F: include/dt-bindings/reset/starfive?jh71*.h +STARFIVE JH71X0 USB DRIVERS +M: Minda Chen +S: Maintained +F: Documentation/devicetree/bindings/usb/starfive,jh7110-usb.yaml +F: drivers/usb/cdns3/cdns3-starfive.c + STARFIVE JH71XX PMU CONTROLLER DRIVER M: Walker Chen S: Supported @@ -20194,7 +20394,6 @@ F: include/linux/*/stm32-*tim* STMMAC ETHERNET DRIVER -M: Giuseppe Cavallaro M: Alexandre Torgue M: Jose Abreu L: netdev@vger.kernel.org @@ -20203,6 +20402,11 @@ F: Documentation/networking/device_drivers/ethernet/stmicro/ F: drivers/net/ethernet/stmicro/stmmac/ +SUN HAPPY MEAL ETHERNET DRIVER +M: Sean Anderson +S: Maintained +F: drivers/net/ethernet/sun/sunhme.* + SUN3/3X M: Sam Creasey S: Maintained @@ -20225,11 +20429,6 @@ S: Maintained F: drivers/net/ethernet/dlink/sundance.c -SUN HAPPY MEAL ETHERNET DRIVER -M: Sean Anderson -S: Maintained -F: drivers/net/ethernet/sun/sunhme.* - SUNPLUS ETHERNET DRIVER M: Wells Lu L: netdev@vger.kernel.org @@ -20251,15 +20450,6 @@ F: Documentation/devicetree/bindings/nvmem/sunplus,sp7021-ocotp.yaml F: drivers/nvmem/sunplus-ocotp.c -SUNPLUS USB2 PHY DRIVER -M: Vincent Shih -L: linux-usb@vger.kernel.org -S: Maintained -F: Documentation/devicetree/bindings/phy/sunplus,sp7021-usb2-phy.yaml -F: drivers/phy/sunplus/Kconfig -F: drivers/phy/sunplus/Makefile -F: drivers/phy/sunplus/phy-sunplus-usb2.c - SUNPLUS PWM DRIVER M: Hammer Hsieh S: Maintained @@ -20286,6 +20476,15 @@ F: Documentation/devicetree/bindings/serial/sunplus,sp7021-uart.yaml F: drivers/tty/serial/sunplus-uart.c +SUNPLUS USB2 PHY DRIVER +M: Vincent Shih +L: linux-usb@vger.kernel.org +S: Maintained +F: Documentation/devicetree/bindings/phy/sunplus,sp7021-usb2-phy.yaml +F: drivers/phy/sunplus/Kconfig +F: drivers/phy/sunplus/Makefile +F: drivers/phy/sunplus/phy-sunplus-usb2.c + SUNPLUS WATCHDOG DRIVER M: Xiantao Hu L: linux-watchdog@vger.kernel.org @@ -20697,6 +20896,14 @@ F: include/uapi/linux/if_team.h F: tools/testing/selftests/drivers/net/team/ +TECHNICAL ADVISORY BOARD PROCESS DOCS +M: "Theodore Ts'o" +M: Greg Kroah-Hartman +L: tech-board-discuss@lists.linux-foundation.org +S: Maintained +F: Documentation/process/contribution-maturity-model.rst +F: Documentation/process/researcher-guidelines.rst + TECHNOLOGIC SYSTEMS TS-5500 PLATFORM SUPPORT M: "Savoir-faire Linux Inc." S: Maintained @@ -20776,6 +20983,14 @@ S: Supported F: drivers/pwm/pwm-tegra.c +TEGRA QUAD SPI DRIVER +M: Thierry Reding +M: Jonathan Hunter +M: Sowjanya Komatineni +L: linux-tegra@vger.kernel.org +S: Maintained +F: drivers/spi/spi-tegra210-quad.c + TEGRA SERIAL DRIVER M: Laxman Dewangan S: Supported @@ -20786,22 +21001,17 @@ S: Supported F: drivers/spi/spi-tegra* -TEGRA QUAD SPI DRIVER -M: Thierry Reding -M: Jonathan Hunter -M: Sowjanya Komatineni -L: linux-tegra@vger.kernel.org -S: Maintained -F: drivers/spi/spi-tegra210-quad.c - TEGRA VIDEO DRIVER M: Thierry Reding M: Jonathan Hunter M: Sowjanya Komatineni +M: Luca Ceresoli L: linux-media@vger.kernel.org L: linux-tegra@vger.kernel.org S: Maintained F: Documentation/devicetree/bindings/display/tegra/nvidia,tegra20-host1x.yaml +F: Documentation/devicetree/bindings/display/tegra/nvidia,tegra20-vi.yaml +F: Documentation/devicetree/bindings/display/tegra/nvidia,tegra20-vip.yaml F: drivers/staging/media/tegra-video/ TEGRA XUSB PADCTL DRIVER @@ -20842,13 +21052,6 @@ F: Documentation/devicetree/bindings/sound/davinci-mcasp-audio.yaml F: sound/soc/ti/ -TEXAS INSTRUMENTS' DAC7612 DAC DRIVER -M: Ricardo Ribalda -L: linux-iio@vger.kernel.org -S: Supported -F: Documentation/devicetree/bindings/iio/dac/ti,dac7612.yaml -F: drivers/iio/dac/ti-dac7612.c - TEXAS INSTRUMENTS DMA DRIVERS M: Peter Ujfalusi L: dmaengine@vger.kernel.org @@ -20857,10 +21060,26 @@ F: Documentation/devicetree/bindings/dma/ti-edma.txt F: Documentation/devicetree/bindings/dma/ti/ F: drivers/dma/ti/ -X: drivers/dma/ti/cppi41.c +F: include/linux/dma/k3-psil.h F: include/linux/dma/k3-udma-glue.h F: include/linux/dma/ti-cppi5.h -F: include/linux/dma/k3-psil.h +X: drivers/dma/ti/cppi41.c + +TEXAS INSTRUMENTS TPS23861 PoE PSE DRIVER +M: Robert Marko +M: Luka Perkov +L: linux-hwmon@vger.kernel.org +S: Maintained +F: Documentation/devicetree/bindings/hwmon/ti,tps23861.yaml +F: Documentation/hwmon/tps23861.rst +F: drivers/hwmon/tps23861.c + +TEXAS INSTRUMENTS' DAC7612 DAC DRIVER +M: Ricardo Ribalda +L: linux-iio@vger.kernel.org +S: Supported +F: Documentation/devicetree/bindings/iio/dac/ti,dac7612.yaml +F: drivers/iio/dac/ti-dac7612.c TEXAS INSTRUMENTS' SYSTEM CONTROL INTERFACE (TISCI) PROTOCOL DRIVER M: Nishanth Menon @@ -20886,15 +21105,6 @@ F: include/linux/soc/ti/ti_sci_inta_msi.h F: include/linux/soc/ti/ti_sci_protocol.h -TEXAS INSTRUMENTS TPS23861 PoE PSE DRIVER -M: Robert Marko -M: Luka Perkov -L: linux-hwmon@vger.kernel.org -S: Maintained -F: Documentation/devicetree/bindings/hwmon/ti,tps23861.yaml -F: Documentation/hwmon/tps23861.rst -F: drivers/hwmon/tps23861.c - TEXAS INSTRUMENTS' TMP117 TEMPERATURE SENSOR DRIVER M: Puranjay Mohan L: linux-iio@vger.kernel.org @@ -21056,7 +21266,7 @@ S: Maintained T: git git://git.kernel.org/pub/scm/linux/kernel/git/brgl/linux.git F: Documentation/devicetree/bindings/i2c/i2c-davinci.txt -F: arch/arm/boot/dts/da850* +F: arch/arm/boot/dts/ti/davinci/ F: arch/arm/mach-davinci/ F: drivers/i2c/busses/i2c-davinci.c @@ -21371,8 +21581,8 @@ M: Masami Hiramatsu L: linux-kernel@vger.kernel.org L: linux-trace-kernel@vger.kernel.org -Q: https://patchwork.kernel.org/project/linux-trace-kernel/list/ S: Maintained +Q: https://patchwork.kernel.org/project/linux-trace-kernel/list/ T: git git://git.kernel.org/pub/scm/linux/kernel/git/trace/linux-trace.git F: Documentation/trace/* F: fs/tracefs/ @@ -21400,31 +21610,15 @@ M: Steven Rostedt M: Daniel Bristot de Oliveira S: Maintained -F: kernel/trace/trace_osnoise.c +F: Documentation/trace/hwlat_detector.rst +F: Documentation/trace/osnoise-tracer.rst +F: Documentation/trace/timerlat-tracer.rst +F: arch/*/kernel/trace.c F: include/trace/events/osnoise.h F: kernel/trace/trace_hwlat.c F: kernel/trace/trace_irqsoff.c +F: kernel/trace/trace_osnoise.c F: kernel/trace/trace_sched_wakeup.c -F: Documentation/trace/osnoise-tracer.rst -F: Documentation/trace/timerlat-tracer.rst -F: Documentation/trace/hwlat_detector.rst -F: arch/*/kernel/trace.c - -Real-time Linux Analysis (RTLA) tools -M: Daniel Bristot de Oliveira -M: Steven Rostedt -L: linux-trace-devel@vger.kernel.org -S: Maintained -F: Documentation/tools/rtla/ -F: tools/tracing/rtla/ - -TECHNICAL ADVISORY BOARD PROCESS DOCS -M: "Theodore Ts'o" -M: Greg Kroah-Hartman -L: tech-board-discuss@lists.linux-foundation.org -S: Maintained -F: Documentation/process/researcher-guidelines.rst -F: Documentation/process/contribution-maturity-model.rst TRADITIONAL CHINESE DOCUMENTATION M: Hu Haowen @@ -21434,14 +21628,16 @@ T: git git://github.com/srcres258/linux-doc.git doc-zh-tw F: Documentation/translations/zh_TW/ -TTY LAYER +TTY LAYER AND SERIAL DRIVERS M: Greg Kroah-Hartman M: Jiri Slaby +L: linux-kernel@vger.kernel.org +L: linux-serial@vger.kernel.org S: Supported T: git git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/tty.git +F: Documentation/devicetree/bindings/serial/ F: Documentation/driver-api/serial/ F: drivers/tty/ -F: drivers/tty/serial/serial_core.c F: include/linux/selection.h F: include/linux/serial.h F: include/linux/serial_core.h @@ -21470,11 +21666,14 @@ F: drivers/net/ethernet/dec/tulip/ TUN/TAP driver -M: Maxim Krasnyansky +M: Willem de Bruijn +M: Jason Wang S: Maintained W: http://vtun.sourceforge.net/tun F: Documentation/networking/tuntap.rst F: arch/um/os-Linux/drivers/ +F: drivers/net/tap.c +F: drivers/net/tun.c TURBOCHANNEL SUBSYSTEM M: "Maciej W. Rozycki" @@ -21697,9 +21896,8 @@ F: drivers/usb/misc/apple-mfi-fastcharge.c USB AR5523 WIRELESS DRIVER -M: Pontus Fuchs L: linux-wireless@vger.kernel.org -S: Maintained +S: Orphan F: drivers/net/wireless/ath/ar5523/ USB ATTACHED SCSI @@ -21782,8 +21980,8 @@ M: Rui Miguel Silva L: linux-usb@vger.kernel.org S: Maintained -F: drivers/usb/isp1760/* F: Documentation/devicetree/bindings/usb/nxp,isp1760.yaml +F: drivers/usb/isp1760/* USB LAN78XX ETHERNET DRIVER M: Woojung Huh @@ -21854,6 +22052,13 @@ S: Supported F: drivers/usb/class/usblp.c +USB QMI WWAN NETWORK DRIVER +M: Bjørn Mork +L: netdev@vger.kernel.org +S: Maintained +F: Documentation/ABI/testing/sysfs-class-net-qmi +F: drivers/net/usb/qmi_wwan.c + USB RAW GADGET DRIVER R: Andrey Konovalov L: linux-usb@vger.kernel.org @@ -21862,13 +22067,6 @@ F: drivers/usb/gadget/legacy/raw_gadget.c F: include/uapi/linux/usb/raw_gadget.h -USB QMI WWAN NETWORK DRIVER -M: Bjørn Mork -L: netdev@vger.kernel.org -S: Maintained -F: Documentation/ABI/testing/sysfs-class-net-qmi -F: drivers/net/usb/qmi_wwan.c - USB RTL8150 DRIVER M: Petko Manolov L: linux-usb@vger.kernel.org @@ -21912,6 +22110,7 @@ F: include/dt-bindings/usb/ F: include/linux/usb.h F: include/linux/usb/ +F: include/uapi/linux/usb/ USB TYPEC BUS FOR ALTERNATE MODES M: Heikki Krogerus @@ -21975,9 +22174,8 @@ F: include/uapi/linux/usb/g_uvc.h USB WIRELESS RNDIS DRIVER (rndis_wlan) -M: Jussi Kivilinna L: linux-wireless@vger.kernel.org -S: Maintained +S: Orphan F: drivers/net/wireless/legacy/rndis_wlan.c USB XHCI DRIVER @@ -22086,6 +22284,13 @@ F: fs/fat/ F: tools/testing/selftests/filesystems/fat/ +VFIO CDX DRIVER +M: Nipun Gupta +M: Nikhil Agarwal +L: kvm@vger.kernel.org +S: Maintained +F: drivers/vfio/cdx/* + VFIO DRIVER M: Alex Williamson L: kvm@vger.kernel.org @@ -22120,6 +22325,12 @@ F: include/linux/mdev.h F: samples/vfio-mdev/ +VFIO MLX5 PCI DRIVER +M: Yishai Hadas +L: kvm@vger.kernel.org +S: Maintained +F: drivers/vfio/pci/mlx5/ + VFIO PCI DEVICE SPECIFIC DRIVERS R: Jason Gunthorpe R: Yishai Hadas @@ -22136,12 +22347,6 @@ S: Maintained F: drivers/vfio/platform/ -VFIO MLX5 PCI DRIVER -M: Yishai Hadas -L: kvm@vger.kernel.org -S: Maintained -F: drivers/vfio/pci/mlx5/ - VGA_SWITCHEROO R: Lukas Wunner S: Maintained @@ -22151,8 +22356,8 @@ F: include/linux/vga_switcheroo.h VIA RHINE NETWORK DRIVER -S: Maintained M: Kevin Brace +S: Maintained F: drivers/net/ethernet/via/via-rhine.c VIA SD/MMC CARD CONTROLLER DRIVER @@ -22167,7 +22372,6 @@ S: Maintained F: drivers/video/fbdev/via/ F: include/linux/via-core.h -F: include/linux/via-gpio.h F: include/linux/via_i2c.h VIA VELOCITY NETWORK DRIVER @@ -22204,6 +22408,14 @@ F: drivers/media/common/videobuf2/* F: include/media/videobuf2-* +VIDTV VIRTUAL DIGITAL TV DRIVER +M: Daniel W. S. Almeida +L: linux-media@vger.kernel.org +S: Maintained +W: https://linuxtv.org +T: git git://linuxtv.org/media_tree.git +F: drivers/media/test-drivers/vidtv/* + VIMC VIRTUAL MEDIA CONTROLLER DRIVER M: Shuah Khan R: Kieran Bingham @@ -22233,6 +22445,16 @@ F: net/vmw_vsock/virtio_transport.c F: net/vmw_vsock/virtio_transport_common.c +VIRTIO BALLOON +M: "Michael S. Tsirkin" +M: David Hildenbrand +L: virtualization@lists.linux-foundation.org +S: Maintained +F: drivers/virtio/virtio_balloon.c +F: include/linux/balloon_compaction.h +F: include/uapi/linux/virtio_balloon.h +F: mm/balloon_compaction.c + VIRTIO BLOCK AND SCSI DRIVERS M: "Michael S. Tsirkin" M: Jason Wang @@ -22242,7 +22464,6 @@ S: Maintained F: drivers/block/virtio_blk.c F: drivers/scsi/virtio_scsi.c -F: drivers/vhost/scsi.c F: include/uapi/linux/virtio_blk.h F: include/uapi/linux/virtio_scsi.h @@ -22275,30 +22496,6 @@ F: include/uapi/linux/virtio_*.h F: tools/virtio/ -VISL VIRTUAL STATELESS DECODER DRIVER -M: Daniel Almeida -L: linux-media@vger.kernel.org -S: Supported -F: drivers/media/test-drivers/visl - -IFCVF VIRTIO DATA PATH ACCELERATOR -R: Zhu Lingshan -F: drivers/vdpa/ifcvf/ - -SNET DPU VIRTIO DATA PATH ACCELERATOR -R: Alvaro Karsz -F: drivers/vdpa/solidrun/ - -VIRTIO BALLOON -M: "Michael S. Tsirkin" -M: David Hildenbrand -L: virtualization@lists.linux-foundation.org -S: Maintained -F: drivers/virtio/virtio_balloon.c -F: include/uapi/linux/virtio_balloon.h -F: include/linux/balloon_compaction.h -F: mm/balloon_compaction.c - VIRTIO CRYPTO DRIVER M: Gonglei L: virtualization@lists.linux-foundation.org @@ -22359,11 +22556,30 @@ L: netdev@vger.kernel.org S: Maintained T: git git://git.kernel.org/pub/scm/linux/kernel/git/mst/vhost.git -F: kernel/vhost_task.c F: drivers/vhost/ F: include/linux/sched/vhost_task.h F: include/linux/vhost_iotlb.h F: include/uapi/linux/vhost.h +F: kernel/vhost_task.c + +VIRTIO HOST (VHOST-SCSI) +M: "Michael S. Tsirkin" +M: Jason Wang +M: Mike Christie +R: Paolo Bonzini +R: Stefan Hajnoczi +L: virtualization@lists.linux-foundation.org +S: Maintained +F: drivers/vhost/scsi.c + +VIRTIO I2C DRIVER +M: Conghui Chen +M: Viresh Kumar +L: linux-i2c@vger.kernel.org +L: virtualization@lists.linux-foundation.org +S: Maintained +F: drivers/i2c/busses/i2c-virtio.c +F: include/uapi/linux/virtio_i2c.h VIRTIO INPUT DRIVER M: Gerd Hoffmann @@ -22386,6 +22602,13 @@ F: drivers/virtio/virtio_mem.c F: include/uapi/linux/virtio_mem.h +VIRTIO PMEM DRIVER +M: Pankaj Gupta +L: virtualization@lists.linux-foundation.org +S: Maintained +F: drivers/nvdimm/nd_virtio.c +F: drivers/nvdimm/virtio_pmem.c + VIRTIO SOUND DRIVER M: Anton Yakovlev M: "Michael S. Tsirkin" @@ -22395,22 +22618,6 @@ F: include/uapi/linux/virtio_snd.h F: sound/virtio/* -VIRTIO I2C DRIVER -M: Conghui Chen -M: Viresh Kumar -L: linux-i2c@vger.kernel.org -L: virtualization@lists.linux-foundation.org -S: Maintained -F: drivers/i2c/busses/i2c-virtio.c -F: include/uapi/linux/virtio_i2c.h - -VIRTIO PMEM DRIVER -M: Pankaj Gupta -L: virtualization@lists.linux-foundation.org -S: Maintained -F: drivers/nvdimm/virtio_pmem.c -F: drivers/nvdimm/nd_virtio.c - VIRTUAL BOX GUEST DEVICE DRIVER M: Hans de Goede M: Arnd Bergmann @@ -22426,12 +22633,26 @@ S: Maintained F: fs/vboxsf/* +VIRTUAL PCM TEST DRIVER +M: Ivan Orlov +L: alsa-devel@alsa-project.org +S: Maintained +F: Documentation/sound/cards/pcmtest.rst +F: sound/drivers/pcmtest.c +F: tools/testing/selftests/alsa/test-pcmtest-driver.c + VIRTUAL SERIO DEVICE DRIVER M: Stephen Chandler Paul S: Maintained F: drivers/input/serio/userio.c F: include/uapi/linux/userio.h +VISL VIRTUAL STATELESS DECODER DRIVER +M: Daniel Almeida +L: linux-media@vger.kernel.org +S: Supported +F: drivers/media/test-drivers/visl + VIVID VIRTUAL VIDEO DRIVER M: Hans Verkuil L: linux-media@vger.kernel.org @@ -22440,14 +22661,6 @@ T: git git://linuxtv.org/media_tree.git F: drivers/media/test-drivers/vivid/* -VIDTV VIRTUAL DIGITAL TV DRIVER -M: Daniel W. S. Almeida -L: linux-media@vger.kernel.org -S: Maintained -W: https://linuxtv.org -T: git git://linuxtv.org/media_tree.git -F: drivers/media/test-drivers/vidtv/* - VLYNQ BUS M: Florian Fainelli L: openwrt-devel@lists.openwrt.org (subscribers-only) @@ -22455,16 +22668,6 @@ F: drivers/vlynq/vlynq.c F: include/linux/vlynq.h -VME SUBSYSTEM -M: Martyn Welch -M: Manohar Vanga -M: Greg Kroah-Hartman -L: linux-kernel@vger.kernel.org -S: Odd fixes -T: git git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/char-misc.git -F: Documentation/driver-api/vme.rst -F: drivers/staging/vme_user/ - VM SOCKETS (AF_VSOCK) M: Stefano Garzarella L: virtualization@lists.linux-foundation.org @@ -22478,6 +22681,28 @@ F: net/vmw_vsock/ F: tools/testing/vsock/ +VMALLOC +M: Andrew Morton +R: Uladzislau Rezki +R: Christoph Hellwig +R: Lorenzo Stoakes +L: linux-mm@kvack.org +S: Maintained +W: http://www.linux-mm.org +T: git git://git.kernel.org/pub/scm/linux/kernel/git/akpm/mm +F: include/linux/vmalloc.h +F: mm/vmalloc.c + +VME SUBSYSTEM +M: Martyn Welch +M: Manohar Vanga +M: Greg Kroah-Hartman +L: linux-kernel@vger.kernel.org +S: Odd fixes +T: git git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/char-misc.git +F: Documentation/driver-api/vme.rst +F: drivers/staging/vme_user/ + VMWARE BALLOON DRIVER M: Nadav Amit R: VMware PV-Drivers Reviewers @@ -22486,7 +22711,7 @@ F: drivers/misc/vmw_balloon.c VMWARE HYPERVISOR INTERFACE -M: Srivatsa S. Bhat (VMware) +M: Ajay Kaher M: Alexey Makhalov R: VMware PV-Drivers Reviewers L: virtualization@lists.linux-foundation.org @@ -22513,8 +22738,8 @@ F: drivers/scsi/vmw_pvscsi.h VMWARE VIRTUAL PTP CLOCK DRIVER -M: Srivatsa S. Bhat (VMware) M: Deep Shah +R: Ajay Kaher R: Alexey Makhalov R: VMware PV-Drivers Reviewers L: netdev@vger.kernel.org @@ -22659,9 +22884,9 @@ WANGXUN ETHERNET DRIVER M: Jiawen Wu M: Mengyuan Lou -W: https://www.net-swift.com L: netdev@vger.kernel.org S: Maintained +W: https://www.net-swift.com F: Documentation/networking/device_drivers/ethernet/wangxun/* F: drivers/net/ethernet/wangxun/ @@ -22676,8 +22901,8 @@ F: Documentation/watchdog/ F: drivers/watchdog/ F: include/linux/watchdog.h -F: include/uapi/linux/watchdog.h F: include/trace/events/watchdog.h +F: include/uapi/linux/watchdog.h WHISKEYCOVE PMIC GPIO DRIVER M: Kuppuswamy Sathyanarayanan @@ -22734,9 +22959,16 @@ WL3501 WIRELESS PCMCIA CARD DRIVER L: linux-wireless@vger.kernel.org -S: Odd fixes +S: Orphan F: drivers/net/wireless/legacy/wl3501* +WMI BINARY MOF DRIVER +L: platform-drivers-x86@vger.kernel.org +S: Orphan +F: Documentation/ABI/stable/sysfs-platform-wmi-bmof +F: Documentation/wmi/devices/wmi-bmof.rst +F: drivers/platform/x86/wmi-bmof.c + WOLFSON MICROELECTRONICS DRIVERS L: patches@opensource.cirrus.com S: Supported @@ -22834,8 +23066,8 @@ L: linux-kernel@vger.kernel.org S: Maintained T: git git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip.git x86/core -F: Documentation/devicetree/bindings/x86/ F: Documentation/arch/x86/ +F: Documentation/devicetree/bindings/x86/ F: arch/x86/ X86 ENTRY CODE @@ -22966,6 +23198,8 @@ L: netdev@vger.kernel.org L: bpf@vger.kernel.org S: Supported +F: drivers/net/ethernet/*/*/*/*/*xdp* +F: drivers/net/ethernet/*/*/*xdp* F: include/net/xdp.h F: include/net/xdp_priv.h F: include/trace/events/xdp.h @@ -22973,10 +23207,8 @@ F: kernel/bpf/devmap.c F: net/core/xdp.c F: samples/bpf/xdp* -F: tools/testing/selftests/bpf/*xdp* F: tools/testing/selftests/bpf/*/*xdp* -F: drivers/net/ethernet/*/*/*/*/*xdp* -F: drivers/net/ethernet/*/*/*xdp* +F: tools/testing/selftests/bpf/*xdp* K: (?:\b|_)xdp(?:\b|_) XDP SOCKETS (AF_XDP) @@ -22988,11 +23220,11 @@ L: bpf@vger.kernel.org S: Maintained F: Documentation/networking/af_xdp.rst +F: include/net/netns/xdp.h F: include/net/xdp_sock* F: include/net/xsk_buff_pool.h F: include/uapi/linux/if_xdp.h F: include/uapi/linux/xdp_diag.h -F: include/net/netns/xdp.h F: net/xdp/ F: tools/testing/selftests/bpf/*xsk* @@ -23094,11 +23326,11 @@ F: include/xen/swiotlb-xen.h XFS FILESYSTEM -C: irc://irc.oftc.net/xfs M: Darrick J. Wong L: linux-xfs@vger.kernel.org S: Supported W: http://xfs.org/ +C: irc://irc.oftc.net/xfs T: git git://git.kernel.org/pub/scm/fs/xfs/xfs-linux.git F: Documentation/ABI/testing/sysfs-fs-xfs F: Documentation/admin-guide/xfs.rst @@ -23116,8 +23348,9 @@ F: drivers/iio/adc/xilinx-ams.c XILINX AXI ETHERNET DRIVER -M: Radhey Shyam Pandey +M: Radhey Shyam Pandey S: Maintained +F: Documentation/devicetree/bindings/net/xlnx,axi-ethernet.yaml F: drivers/net/ethernet/xilinx/xilinx_axienet* XILINX CAN DRIVER @@ -23128,19 +23361,31 @@ F: Documentation/devicetree/bindings/net/can/xilinx,can.yaml F: drivers/net/can/xilinx_can.c +XILINX EVENT MANAGEMENT DRIVER +M: Abhyuday Godhasara +S: Maintained +F: drivers/soc/xilinx/xlnx_event_manager.c +F: include/linux/firmware/xlnx-event-manager.h + XILINX GPIO DRIVER -M: Shubhrajyoti Datta -R: Srinivas Neeli +M: Shubhrajyoti Datta +R: Srinivas Neeli R: Michal Simek S: Maintained -F: Documentation/devicetree/bindings/gpio/xlnx,gpio-xilinx.yaml F: Documentation/devicetree/bindings/gpio/gpio-zynq.yaml +F: Documentation/devicetree/bindings/gpio/xlnx,gpio-xilinx.yaml F: drivers/gpio/gpio-xilinx.c F: drivers/gpio/gpio-zynq.c +XILINX PWM DRIVER +M: Sean Anderson +S: Maintained +F: drivers/pwm/pwm-xilinx.c +F: include/clocksource/timer-xilinx.h + XILINX SD-FEC IP CORES -M: Derek Kiernan -M: Dragan Cvetic +M: Derek Kiernan +M: Dragan Cvetic S: Maintained F: Documentation/devicetree/bindings/misc/xlnx,sd-fec.txt F: Documentation/misc-devices/xilinx_sdfec.rst @@ -23149,12 +23394,6 @@ F: drivers/misc/xilinx_sdfec.c F: include/uapi/misc/xilinx_sdfec.h -XILINX PWM DRIVER -M: Sean Anderson -S: Maintained -F: drivers/pwm/pwm-xilinx.c -F: include/clocksource/timer-xilinx.h - XILINX UARTLITE SERIAL DRIVER M: Peter Korsgaard L: linux-serial@vger.kernel.org @@ -23162,7 +23401,6 @@ F: drivers/tty/serial/uartlite.c XILINX VIDEO IP CORES -M: Hyun Kwon M: Laurent Pinchart L: linux-media@vger.kernel.org S: Supported @@ -23176,8 +23414,10 @@ R: Shubhrajyoti Datta R: Michal Simek S: Maintained +F: Documentation/devicetree/bindings/watchdog/xlnx,versal-wwdt.yaml F: Documentation/devicetree/bindings/watchdog/xlnx,xps-timebase-wdt.yaml F: drivers/watchdog/of_xilinx_wdt.c +F: drivers/watchdog/xilinx_wwdt.c XILINX XDMA DRIVER M: Lizhi Hou @@ -23191,7 +23431,6 @@ F: include/linux/platform_data/amd_xdma.h XILINX ZYNQMP DPDMA DRIVER -M: Hyun Kwon M: Laurent Pinchart L: dmaengine@vger.kernel.org S: Supported @@ -23207,7 +23446,6 @@ F: drivers/edac/zynqmp_edac.c XILINX ZYNQMP PSGTR PHY DRIVER -M: Anurag Kumar Vulisha M: Laurent Pinchart L: linux-kernel@vger.kernel.org S: Supported @@ -23216,16 +23454,10 @@ F: drivers/phy/xilinx/phy-zynqmp.c XILINX ZYNQMP SHA3 DRIVER -M: Harsha +M: Harsha S: Maintained F: drivers/crypto/xilinx/zynqmp-sha.c -XILINX EVENT MANAGEMENT DRIVER -M: Abhyuday Godhasara -S: Maintained -F: drivers/soc/xilinx/xlnx_event_manager.c -F: include/linux/firmware/xlnx-event-manager.h - XILLYBUS DRIVER M: Eli Billauer L: linux-kernel@vger.kernel.org @@ -23273,6 +23505,13 @@ F: Documentation/input/devices/yealink.rst F: drivers/input/misc/yealink.* +Z3FOLD COMPRESSED PAGE ALLOCATOR +M: Vitaly Wool +R: Miaohe Lin +L: linux-mm@kvack.org +S: Maintained +F: mm/z3fold.c + Z8530 DRIVER FOR AX.25 M: Joerg Reuter L: linux-hams@vger.kernel.org @@ -23290,19 +23529,9 @@ S: Maintained F: mm/zbud.c -Z3FOLD COMPRESSED PAGE ALLOCATOR -M: Vitaly Wool -R: Miaohe Lin -L: linux-mm@kvack.org -S: Maintained -F: mm/z3fold.c - ZD1211RW WIRELESS DRIVER -M: Ulrich Kunitz L: linux-wireless@vger.kernel.org -L: zd1211-devs@lists.sourceforge.net (subscribers-only) -S: Maintained -W: http://zd1211.ath.cx/wiki/DriverRewrite +S: Orphan F: drivers/net/wireless/zydas/zd1211rw/ ZD1301 MEDIA DRIVER @@ -23383,10 +23612,10 @@ S: Maintained B: https://github.com/facebook/zstd/issues T: git https://github.com/terrelln/linux.git +F: crypto/zstd.c F: include/linux/zstd* -F: lib/zstd/ F: lib/decompress_unzstd.c -F: crypto/zstd.c +F: lib/zstd/ N: zstd K: zstd @@ -23398,13 +23627,6 @@ S: Maintained F: mm/zswap.c -NXP BLUETOOTH WIRELESS DRIVERS -M: Amitkumar Karwar -M: Neeraj Kale -S: Maintained -F: Documentation/devicetree/bindings/net/bluetooth/nxp,88w8987-bt.yaml -F: drivers/bluetooth/btnxpuart.c - THE REST M: Linus Torvalds L: linux-kernel@vger.kernel.org diff -Nru backport-iwlwifi-dkms-11289/net/Kconfig backport-iwlwifi-dkms-11510/net/Kconfig --- backport-iwlwifi-dkms-11289/net/Kconfig 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/Kconfig 2023-10-04 04:18:43.000000000 +0800 @@ -324,7 +324,7 @@ config NET_RX_BUSY_POLL bool - default y if !PREEMPT_RT + default y if !PREEMPT_RT || (PREEMPT_RT && !NETCONSOLE) config BQL bool diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/agg-rx.c backport-iwlwifi-dkms-11510/net/mac80211/agg-rx.c --- backport-iwlwifi-dkms-11289/net/mac80211/agg-rx.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/agg-rx.c 2023-10-04 04:18:43.000000000 +0800 @@ -9,7 +9,7 @@ * Copyright 2007, Michael Wu * Copyright 2007-2010, Intel Corporation * Copyright(c) 2015-2017 Intel Deutschland GmbH - * Copyright (C) 2018-2022 Intel Corporation + * Copyright (C) 2018-2023 Intel Corporation */ /** @@ -69,10 +69,10 @@ .ssn = 0, }; - lockdep_assert_held(&sta->ampdu_mlme.mtx); + lockdep_assert_wiphy(sta->local->hw.wiphy); tid_rx = rcu_dereference_protected(sta->ampdu_mlme.tid_rx[tid], - lockdep_is_held(&sta->ampdu_mlme.mtx)); + lockdep_is_held(&sta->local->hw.wiphy->mtx)); if (!test_bit(tid, sta->ampdu_mlme.agg_session_valid)) return; @@ -117,9 +117,9 @@ void __ieee80211_stop_rx_ba_session(struct sta_info *sta, u16 tid, u16 initiator, u16 reason, bool tx) { - mutex_lock(&sta->ampdu_mlme.mtx); + lockdep_assert_wiphy(sta->local->hw.wiphy); + ___ieee80211_stop_rx_ba_session(sta, tid, initiator, reason, tx); - mutex_unlock(&sta->ampdu_mlme.mtx); } void ieee80211_stop_rx_ba_session(struct ieee80211_vif *vif, u16 ba_rx_bitmap, @@ -140,7 +140,7 @@ if (ba_rx_bitmap & BIT(i)) set_bit(i, sta->ampdu_mlme.tid_rx_stop_requested); - ieee80211_queue_work(&sta->local->hw, &sta->ampdu_mlme.work); + wiphy_work_queue(sta->local->hw.wiphy, &sta->ampdu_mlme.work); rcu_read_unlock(); } EXPORT_SYMBOL(ieee80211_stop_rx_ba_session); @@ -166,7 +166,7 @@ sta->sta.addr, tid); set_bit(tid, sta->ampdu_mlme.tid_rx_timer_expired); - ieee80211_queue_work(&sta->local->hw, &sta->ampdu_mlme.work); + wiphy_work_queue(sta->local->hw.wiphy, &sta->ampdu_mlme.work); } static void sta_rx_agg_reorder_timer_expired(struct timer_list *t) @@ -270,6 +270,8 @@ u16 status = WLAN_STATUS_REQUEST_DECLINED; u16 max_buf_size; + lockdep_assert_wiphy(sta->local->hw.wiphy); + if (tid >= IEEE80211_FIRST_TSPEC_TSID) { ht_dbg(sta->sdata, "STA %pM requests BA session on unsupported tid %d\n", @@ -325,9 +327,6 @@ ht_dbg(sta->sdata, "AddBA Req buf_size=%d for %pM\n", buf_size, sta->sta.addr); - /* examine state machine */ - lockdep_assert_held(&sta->ampdu_mlme.mtx); - if (test_bit(tid, sta->ampdu_mlme.agg_session_valid)) { if (sta->ampdu_mlme.tid_rx_token[tid] == dialog_token) { struct tid_ampdu_rx *tid_rx; @@ -451,11 +450,11 @@ bool auto_seq, const struct ieee80211_addba_ext_ie *addbaext) { - mutex_lock(&sta->ampdu_mlme.mtx); + lockdep_assert_wiphy(sta->local->hw.wiphy); + ___ieee80211_start_rx_ba_session(sta, dialog_token, timeout, start_seq_num, ba_policy, tid, buf_size, tx, auto_seq, addbaext); - mutex_unlock(&sta->ampdu_mlme.mtx); } void ieee80211_process_addba_request(struct ieee80211_local *local, @@ -507,7 +506,6 @@ const u8 *addr, unsigned int tid) { struct ieee80211_sub_if_data *sdata = vif_to_sdata(vif); - struct ieee80211_local *local = sdata->local; struct sta_info *sta; rcu_read_lock(); @@ -516,7 +514,7 @@ goto unlock; set_bit(tid, sta->ampdu_mlme.tid_rx_manage_offl); - ieee80211_queue_work(&local->hw, &sta->ampdu_mlme.work); + wiphy_work_queue(sta->local->hw.wiphy, &sta->ampdu_mlme.work); unlock: rcu_read_unlock(); } @@ -526,7 +524,6 @@ const u8 *addr, unsigned int tid) { struct ieee80211_sub_if_data *sdata = vif_to_sdata(vif); - struct ieee80211_local *local = sdata->local; struct sta_info *sta; rcu_read_lock(); @@ -535,7 +532,7 @@ goto unlock; set_bit(tid, sta->ampdu_mlme.tid_rx_timer_expired); - ieee80211_queue_work(&local->hw, &sta->ampdu_mlme.work); + wiphy_work_queue(sta->local->hw.wiphy, &sta->ampdu_mlme.work); unlock: rcu_read_unlock(); diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/agg-tx.c backport-iwlwifi-dkms-11510/net/mac80211/agg-tx.c --- backport-iwlwifi-dkms-11289/net/mac80211/agg-tx.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/agg-tx.c 2023-10-04 04:18:43.000000000 +0800 @@ -142,7 +142,7 @@ void ieee80211_assign_tid_tx(struct sta_info *sta, int tid, struct tid_ampdu_tx *tid_tx) { - lockdep_assert_held(&sta->ampdu_mlme.mtx); + lockdep_assert_wiphy(sta->local->hw.wiphy); lockdep_assert_held(&sta->lock); rcu_assign_pointer(sta->ampdu_mlme.tid_tx[tid], tid_tx); } @@ -213,7 +213,7 @@ struct ieee80211_txq *txq = sta->sta.txq[tid]; struct txq_info *txqi; - lockdep_assert_held(&sta->ampdu_mlme.mtx); + lockdep_assert_wiphy(sta->local->hw.wiphy); if (!txq) return; @@ -271,7 +271,7 @@ { struct tid_ampdu_tx *tid_tx; - lockdep_assert_held(&sta->ampdu_mlme.mtx); + lockdep_assert_wiphy(sta->local->hw.wiphy); lockdep_assert_held(&sta->lock); tid_tx = rcu_dereference_protected_tid_tx(sta, tid); @@ -302,8 +302,8 @@ kfree_rcu(tid_tx, rcu_head); } -int ___ieee80211_stop_tx_ba_session(struct sta_info *sta, u16 tid, - enum ieee80211_agg_stop_reason reason) +int __ieee80211_stop_tx_ba_session(struct sta_info *sta, u16 tid, + enum ieee80211_agg_stop_reason reason) { struct ieee80211_local *local = sta->local; struct tid_ampdu_tx *tid_tx; @@ -317,7 +317,7 @@ }; int ret; - lockdep_assert_held(&sta->ampdu_mlme.mtx); + lockdep_assert_wiphy(sta->local->hw.wiphy); switch (reason) { case AGG_STOP_DECLINED: @@ -471,7 +471,7 @@ test_bit(HT_AGG_STATE_WANT_STOP, &tid_tx->state))) return; - lockdep_assert_held(&sta->ampdu_mlme.mtx); + lockdep_assert_wiphy(sta->local->hw.wiphy); /* activate the timer for the recipient's addBA response */ mod_timer(&tid_tx->addba_resp_timer, jiffies + ADDBA_RESP_INTERVAL); @@ -756,7 +756,7 @@ */ sta->ampdu_mlme.tid_start_tx[tid] = tid_tx; - ieee80211_queue_work(&local->hw, &sta->ampdu_mlme.work); + wiphy_work_queue(local->hw.wiphy, &sta->ampdu_mlme.work); /* this flow continues off the work */ err_unlock_sta: @@ -777,7 +777,7 @@ .ssn = 0, }; - lockdep_assert_held(&sta->ampdu_mlme.mtx); + lockdep_assert_wiphy(sta->local->hw.wiphy); tid_tx = rcu_dereference_protected_tid_tx(sta, tid); params.buf_size = tid_tx->buf_size; @@ -814,7 +814,7 @@ struct ieee80211_sub_if_data *sdata = sta->sdata; struct ieee80211_local *local = sdata->local; - lockdep_assert_held(&sta->ampdu_mlme.mtx); + lockdep_assert_wiphy(sta->local->hw.wiphy); if (WARN_ON(test_and_set_bit(HT_AGG_STATE_DRV_READY, &tid_tx->state))) return; @@ -875,26 +875,12 @@ goto out; set_bit(HT_AGG_STATE_START_CB, &tid_tx->state); - ieee80211_queue_work(&local->hw, &sta->ampdu_mlme.work); + wiphy_work_queue(local->hw.wiphy, &sta->ampdu_mlme.work); out: rcu_read_unlock(); } EXPORT_SYMBOL(ieee80211_start_tx_ba_cb_irqsafe); -int __ieee80211_stop_tx_ba_session(struct sta_info *sta, u16 tid, - enum ieee80211_agg_stop_reason reason) -{ - int ret; - - mutex_lock(&sta->ampdu_mlme.mtx); - - ret = ___ieee80211_stop_tx_ba_session(sta, tid, reason); - - mutex_unlock(&sta->ampdu_mlme.mtx); - - return ret; -} - int ieee80211_stop_tx_ba_session(struct ieee80211_sta *pubsta, u16 tid) { struct sta_info *sta = container_of(pubsta, struct sta_info, sta); @@ -929,7 +915,7 @@ } set_bit(HT_AGG_STATE_WANT_STOP, &tid_tx->state); - ieee80211_queue_work(&local->hw, &sta->ampdu_mlme.work); + wiphy_work_queue(local->hw.wiphy, &sta->ampdu_mlme.work); unlock: spin_unlock_bh(&sta->lock); @@ -989,7 +975,7 @@ goto out; set_bit(HT_AGG_STATE_STOP_CB, &tid_tx->state); - ieee80211_queue_work(&local->hw, &sta->ampdu_mlme.work); + wiphy_work_queue(local->hw.wiphy, &sta->ampdu_mlme.work); out: rcu_read_unlock(); } @@ -1006,6 +992,8 @@ u16 capab, tid, buf_size; bool amsdu; + lockdep_assert_wiphy(sta->local->hw.wiphy); + capab = le16_to_cpu(mgmt->u.action.u.addba_resp.capab); amsdu = capab & IEEE80211_ADDBA_PARAM_AMSDU_MASK; tid = u16_get_bits(capab, IEEE80211_ADDBA_PARAM_TID_MASK); @@ -1016,16 +1004,14 @@ if (!amsdu && txq) set_bit(IEEE80211_TXQ_NO_AMSDU, &to_txq_info(txq)->flags); - mutex_lock(&sta->ampdu_mlme.mtx); - tid_tx = rcu_dereference_protected_tid_tx(sta, tid); if (!tid_tx) - goto out; + return; if (mgmt->u.action.u.addba_resp.dialog_token != tid_tx->dialog_token) { ht_dbg(sta->sdata, "wrong addBA response token, %pM tid %d\n", sta->sta.addr, tid); - goto out; + return; } del_timer_sync(&tid_tx->addba_resp_timer); @@ -1043,7 +1029,7 @@ ht_dbg(sta->sdata, "got addBA resp for %pM tid %d but we already gave up\n", sta->sta.addr, tid); - goto out; + return; } /* @@ -1057,7 +1043,7 @@ if (test_and_set_bit(HT_AGG_STATE_RESPONSE_RECEIVED, &tid_tx->state)) { /* ignore duplicate response */ - goto out; + return; } tid_tx->buf_size = buf_size; @@ -1078,9 +1064,6 @@ } } else { - ___ieee80211_stop_tx_ba_session(sta, tid, AGG_STOP_DECLINED); + __ieee80211_stop_tx_ba_session(sta, tid, AGG_STOP_DECLINED); } - - out: - mutex_unlock(&sta->ampdu_mlme.mtx); } diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/cfg.c backport-iwlwifi-dkms-11510/net/mac80211/cfg.c --- backport-iwlwifi-dkms-11289/net/mac80211/cfg.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/cfg.c 2023-10-04 04:18:43.000000000 +0800 @@ -214,6 +214,8 @@ struct sta_info *sta; int ret; + lockdep_assert_wiphy(local->hw.wiphy); + ret = ieee80211_if_change_type(sdata, type); if (ret) return ret; @@ -235,12 +237,10 @@ if (!ifmgd->associated) return 0; - mutex_lock(&local->sta_mtx); sta = sta_info_get(sdata, sdata->deflink.u.mgd.bssid); if (sta) drv_sta_set_4addr(local, sdata, &sta->sta, params->use_4addr); - mutex_unlock(&local->sta_mtx); if (params->use_4addr) ieee80211_send_4addr_nullfunc(local, sdata); @@ -261,9 +261,9 @@ struct ieee80211_sub_if_data *sdata = IEEE80211_WDEV_TO_SUB_IF(wdev); int ret; - mutex_lock(&sdata->local->chanctx_mtx); + lockdep_assert_wiphy(sdata->local->hw.wiphy); + ret = ieee80211_check_combinations(sdata, NULL, 0, 0); - mutex_unlock(&sdata->local->chanctx_mtx); if (ret < 0) return ret; @@ -283,9 +283,9 @@ struct ieee80211_sub_if_data *sdata = IEEE80211_WDEV_TO_SUB_IF(wdev); int ret; - mutex_lock(&sdata->local->chanctx_mtx); + lockdep_assert_wiphy(sdata->local->hw.wiphy); + ret = ieee80211_check_combinations(sdata, NULL, 0, 0); - mutex_unlock(&sdata->local->chanctx_mtx); if (ret < 0) return ret; @@ -452,13 +452,11 @@ if (sta->ptk_idx == key_idx) return 0; - mutex_lock(&local->key_mtx); - key = key_mtx_dereference(local, sta->ptk[key_idx]); + key = wiphy_dereference(local->hw.wiphy, sta->ptk[key_idx]); if (key && key->conf.flags & IEEE80211_KEY_FLAG_NO_AUTO_TX) ret = ieee80211_set_tx_key(key); - mutex_unlock(&local->key_mtx); return ret; } @@ -472,7 +470,8 @@ struct ieee80211_local *local = sdata->local; struct sta_info *sta = NULL; struct ieee80211_key *key; - int err; + + lockdep_assert_wiphy(local->hw.wiphy); if (!ieee80211_sdata_running(sdata)) return -ENETDOWN; @@ -510,8 +509,6 @@ if (params->mode == NL80211_KEY_NO_TX) key->conf.flags |= IEEE80211_KEY_FLAG_NO_AUTO_TX; - mutex_lock(&local->sta_mtx); - if (mac_addr) { sta = sta_info_get_bss(sdata, mac_addr); /* @@ -526,8 +523,7 @@ */ if (!sta || !test_sta_flag(sta, WLAN_STA_ASSOC)) { ieee80211_key_free_unused(key); - err = -ENOENT; - goto out_unlock; + return -ENOENT; } } @@ -565,12 +561,7 @@ break; } - err = ieee80211_key_link(key, link, sta); - - out_unlock: - mutex_unlock(&local->sta_mtx); - - return err; + return ieee80211_key_link(key, link, sta); } static struct ieee80211_key * @@ -582,8 +573,7 @@ struct ieee80211_key *key; if (link_id >= 0) { - link = rcu_dereference_check(sdata->link[link_id], - lockdep_is_held(&sdata->wdev.mtx)); + link = sdata_dereference(sdata->link[link_id], sdata); if (!link) return NULL; } @@ -598,7 +588,7 @@ if (link_id >= 0) { link_sta = rcu_dereference_check(sta->link[link_id], - lockdep_is_held(&local->sta_mtx)); + lockdep_is_held(&local->hw.wiphy->mtx)); if (!link_sta) return NULL; } else { @@ -606,30 +596,29 @@ } if (pairwise && key_idx < NUM_DEFAULT_KEYS) - return rcu_dereference_check_key_mtx(local, - sta->ptk[key_idx]); + return wiphy_dereference(local->hw.wiphy, + sta->ptk[key_idx]); if (!pairwise && key_idx < NUM_DEFAULT_KEYS + NUM_DEFAULT_MGMT_KEYS + NUM_DEFAULT_BEACON_KEYS) - return rcu_dereference_check_key_mtx(local, - link_sta->gtk[key_idx]); + return wiphy_dereference(local->hw.wiphy, + link_sta->gtk[key_idx]); return NULL; } if (pairwise && key_idx < NUM_DEFAULT_KEYS) - return rcu_dereference_check_key_mtx(local, - sdata->keys[key_idx]); + return wiphy_dereference(local->hw.wiphy, sdata->keys[key_idx]); - key = rcu_dereference_check_key_mtx(local, link->gtk[key_idx]); + key = wiphy_dereference(local->hw.wiphy, link->gtk[key_idx]); if (key) return key; /* or maybe it was a WEP key */ if (key_idx < NUM_DEFAULT_KEYS) - return rcu_dereference_check_key_mtx(local, sdata->keys[key_idx]); + return wiphy_dereference(local->hw.wiphy, sdata->keys[key_idx]); return NULL; } @@ -641,25 +630,16 @@ struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev); struct ieee80211_local *local = sdata->local; struct ieee80211_key *key; - int ret; - mutex_lock(&local->sta_mtx); - mutex_lock(&local->key_mtx); + lockdep_assert_wiphy(local->hw.wiphy); key = ieee80211_lookup_key(sdata, link_id, key_idx, pairwise, mac_addr); - if (!key) { - ret = -ENOENT; - goto out_unlock; - } + if (!key) + return -ENOENT; ieee80211_key_free(key, sdata->vif.type == NL80211_IFTYPE_STATION); - ret = 0; - out_unlock: - mutex_unlock(&local->key_mtx); - mutex_unlock(&local->sta_mtx); - - return ret; + return 0; } static int ieee80211_get_key(struct wiphy *wiphy, struct net_device *dev, @@ -860,7 +840,7 @@ struct sta_info *sta; int ret = -ENOENT; - mutex_lock(&local->sta_mtx); + lockdep_assert_wiphy(local->hw.wiphy); sta = sta_info_get_by_idx(sdata, idx); if (sta) { @@ -869,8 +849,6 @@ sta_set_sinfo(sta, sinfo, true); } - mutex_unlock(&local->sta_mtx); - return ret; } @@ -890,7 +868,7 @@ struct sta_info *sta; int ret = -ENOENT; - mutex_lock(&local->sta_mtx); + lockdep_assert_wiphy(local->hw.wiphy); sta = sta_info_get_bss(sdata, mac); if (sta) { @@ -898,8 +876,6 @@ sta_set_sinfo(sta, sinfo, true); } - mutex_unlock(&local->sta_mtx); - return ret; } @@ -910,6 +886,8 @@ struct ieee80211_sub_if_data *sdata; int ret = 0; + lockdep_assert_wiphy(local->hw.wiphy); + if (cfg80211_chandef_identical(&local->monitor_chandef, chandef)) return 0; @@ -917,22 +895,16 @@ sdata = wiphy_dereference(local->hw.wiphy, local->monitor_sdata); if (sdata) { - sdata_lock(sdata); - mutex_lock(&local->mtx); ieee80211_link_release_channel(&sdata->deflink); ret = ieee80211_link_use_channel(&sdata->deflink, chandef, IEEE80211_CHANCTX_EXCLUSIVE); - mutex_unlock(&local->mtx); - sdata_unlock(sdata); } } else { - mutex_lock(&local->mtx); if (local->open_count == local->monitors) { local->_oper_chandef = *chandef; ieee80211_hw_config(local, 0); } - mutex_unlock(&local->mtx); } if (ret == 0) @@ -1107,12 +1079,13 @@ return offset; } -static int ieee80211_assign_beacon(struct ieee80211_sub_if_data *sdata, - struct ieee80211_link_data *link, - struct cfg80211_beacon_data *params, - const struct ieee80211_csa_settings *csa, - const struct ieee80211_color_change_settings *cca, - u64 *changed) +static int +ieee80211_assign_beacon(struct ieee80211_sub_if_data *sdata, + struct ieee80211_link_data *link, + struct cfg80211_beacon_data *params, + const struct ieee80211_csa_settings *csa, + const struct ieee80211_color_change_settings *cca, + u64 *changed) { struct cfg80211_mbssid_elems *mbssid = NULL; struct cfg80211_rnr_elems *rnr = NULL; @@ -1274,6 +1247,8 @@ struct ieee80211_link_data *link; struct ieee80211_bss_conf *link_conf; + lockdep_assert_wiphy(local->hw.wiphy); + link = sdata_dereference(sdata->link[link_id], sdata); if (!link) return -ENOLINK; @@ -1383,12 +1358,10 @@ return err; } - mutex_lock(&local->mtx); err = ieee80211_link_use_channel(link, ¶ms->chandef, IEEE80211_CHANCTX_SHARED); if (!err) ieee80211_link_copy_chanctx_to_vlans(link, false); - mutex_unlock(&local->mtx); if (err) { link_conf->beacon_int = prev_beacon_int; return err; @@ -1499,9 +1472,7 @@ return 0; error: - mutex_lock(&local->mtx); ieee80211_link_release_channel(link); - mutex_unlock(&local->mtx); return err; } @@ -1516,7 +1487,7 @@ struct ieee80211_bss_conf *link_conf; u64 changed = 0; - sdata_assert_lock(sdata); + lockdep_assert_wiphy(wiphy); link = sdata_dereference(sdata->link[params->link_id], sdata); if (!link) @@ -1575,7 +1546,7 @@ sdata_dereference(sdata->link[link_id], sdata); struct ieee80211_bss_conf *link_conf = link->conf; - sdata_assert_lock(sdata); + lockdep_assert_wiphy(local->hw.wiphy); old_beacon = sdata_dereference(link->u.ap.beacon, sdata); if (!old_beacon) @@ -1588,17 +1559,15 @@ sdata_dereference(link->u.ap.unsol_bcast_probe_resp, sdata); - /* abort any running channel switch */ - mutex_lock(&local->mtx); + /* abort any running channel switch or color change */ link_conf->csa_active = false; + link_conf->color_change_active = false; if (link->csa_block_tx) { ieee80211_wake_vif_queues(local, sdata, IEEE80211_QUEUE_STOP_REASON_CSA); link->csa_block_tx = false; } - mutex_unlock(&local->mtx); - ieee80211_free_next_beacon(link); /* turn off carrier for this interface and dependent VLANs */ @@ -1641,7 +1610,7 @@ if (sdata->wdev.cac_started) { chandef = link_conf->chandef; - cancel_delayed_work_sync(&link->dfs_cac_timer_work); + wiphy_delayed_work_cancel(wiphy, &link->dfs_cac_timer_work); cfg80211_cac_event(sdata->dev, &chandef, NL80211_RADAR_CAC_ABORTED, GFP_KERNEL); @@ -1653,10 +1622,8 @@ local->total_ps_buffered -= skb_queue_len(&sdata->u.ap.ps.bc_buf); ieee80211_purge_tx_queue(&local->hw, &sdata->u.ap.ps.bc_buf); - mutex_lock(&local->mtx); ieee80211_link_copy_chanctx_to_vlans(link, true); ieee80211_link_release_channel(link); - mutex_unlock(&local->mtx); return 0; } @@ -1798,7 +1765,7 @@ sdata_dereference(sdata->link[link_id], sdata); struct link_sta_info *link_sta = rcu_dereference_protected(sta->link[link_id], - lockdep_is_held(&local->sta_mtx)); + lockdep_is_held(&local->hw.wiphy->mtx)); /* * If there are no changes, then accept a link that doesn't exist, @@ -2033,6 +2000,8 @@ struct ieee80211_sub_if_data *sdata; int err; + lockdep_assert_wiphy(local->hw.wiphy); + if (params->vlan) { sdata = IEEE80211_DEV_TO_SUB_IF(params->vlan); @@ -2076,9 +2045,7 @@ * visible yet), sta_apply_parameters (and inner functions) require * the mutex due to other paths. */ - mutex_lock(&local->sta_mtx); err = sta_apply_parameters(local, sta, params); - mutex_unlock(&local->sta_mtx); if (err) { sta_info_free(local, sta); return err; @@ -2121,13 +2088,11 @@ enum cfg80211_station_type statype; int err; - mutex_lock(&local->sta_mtx); + lockdep_assert_wiphy(local->hw.wiphy); sta = sta_info_get_bss(sdata, mac); - if (!sta) { - err = -ENOENT; - goto out_err; - } + if (!sta) + return -ENOENT; switch (sdata->vif.type) { case NL80211_IFTYPE_MESH_POINT: @@ -2157,22 +2122,19 @@ statype = CFG80211_STA_AP_CLIENT_UNASSOC; break; default: - err = -EOPNOTSUPP; - goto out_err; + return -EOPNOTSUPP; } err = cfg80211_check_station_change(wiphy, params, statype); if (err) - goto out_err; + return err; if (params->vlan && params->vlan != sta->sdata->dev) { vlansdata = IEEE80211_DEV_TO_SUB_IF(params->vlan); if (params->vlan->ieee80211_ptr->use_4addr) { - if (vlansdata->u.vlan.sta) { - err = -EBUSY; - goto out_err; - } + if (vlansdata->u.vlan.sta) + return -EBUSY; rcu_assign_pointer(vlansdata->u.vlan.sta, sta); __ieee80211_check_fast_rx_iface(vlansdata); @@ -2198,18 +2160,9 @@ } } - /* we use sta_info_get_bss() so this might be different */ - if (sdata != sta->sdata) { - mutex_lock_nested(&sta->sdata->wdev.mtx, 1); - err = sta_apply_parameters(local, sta, params); - mutex_unlock(&sta->sdata->wdev.mtx); - } else { - err = sta_apply_parameters(local, sta, params); - } + err = sta_apply_parameters(local, sta, params); if (err) - goto out_err; - - mutex_unlock(&local->sta_mtx); + return err; if (sdata->vif.type == NL80211_IFTYPE_STATION && params->sta_flags_mask & BIT(NL80211_STA_FLAG_AUTHORIZED)) { @@ -2218,9 +2171,6 @@ } return 0; -out_err: - mutex_unlock(&local->sta_mtx); - return err; } #ifdef CPTCFG_MAC80211_MESH @@ -2633,6 +2583,8 @@ struct ieee80211_if_mesh *ifmsh = &sdata->u.mesh; int err; + lockdep_assert_wiphy(sdata->local->hw.wiphy); + memcpy(&ifmsh->mshcfg, conf, sizeof(struct mesh_config)); err = copy_mesh_setup(ifmsh, setup); if (err) @@ -2644,10 +2596,8 @@ sdata->deflink.smps_mode = IEEE80211_SMPS_OFF; sdata->deflink.needed_rx_chains = sdata->local->rx_chains; - mutex_lock(&sdata->local->mtx); err = ieee80211_link_use_channel(&sdata->deflink, &setup->chandef, IEEE80211_CHANCTX_SHARED); - mutex_unlock(&sdata->local->mtx); if (err) return err; @@ -2658,11 +2608,11 @@ { struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev); + lockdep_assert_wiphy(sdata->local->hw.wiphy); + ieee80211_stop_mesh(sdata); - mutex_lock(&sdata->local->mtx); ieee80211_link_release_channel(&sdata->deflink); kfree(sdata->u.mesh.ie); - mutex_unlock(&sdata->local->mtx); return 0; } @@ -3020,6 +2970,8 @@ bool update_txp_type = false; bool has_monitor = false; + lockdep_assert_wiphy(local->hw.wiphy); + if (wdev) { sdata = IEEE80211_WDEV_TO_SUB_IF(wdev); @@ -3067,7 +3019,6 @@ break; } - mutex_lock(&local->iflist_mtx); list_for_each_entry(sdata, &local->interfaces, list) { if (sdata->vif.type == NL80211_IFTYPE_MONITOR) { has_monitor = true; @@ -3083,7 +3034,6 @@ continue; ieee80211_recalc_txpower(sdata, update_txp_type); } - mutex_unlock(&local->iflist_mtx); if (has_monitor) { sdata = wiphy_dereference(local->hw.wiphy, @@ -3172,14 +3122,24 @@ struct sta_info *sta; bool tdls_peer_found = false; - lockdep_assert_held(&sdata->wdev.mtx); + lockdep_assert_wiphy(sdata->local->hw.wiphy); if (WARN_ON_ONCE(sdata->vif.type != NL80211_IFTYPE_STATION)) return -EINVAL; + if (ieee80211_vif_is_mld(&sdata->vif) && + !(sdata->vif.active_links & BIT(link->link_id))) + return 0; + old_req = link->u.mgd.req_smps; link->u.mgd.req_smps = smps_mode; + /* The driver indicated that EML is enabled for the interface, which + * implies that SMPS flows towards the AP should be stopped. + */ + if (sdata->vif.driver_flags & IEEE80211_VIF_EML_ACTIVE) + return 0; + if (old_req == smps_mode && smps_mode != IEEE80211_SMPS_AUTOMATIC) return 0; @@ -3193,7 +3153,7 @@ link->conf->chandef.width == NL80211_CHAN_WIDTH_20_NOHT) return 0; - ap = link->u.mgd.bssid; + ap = sdata->vif.cfg.ap_addr; rcu_read_lock(); list_for_each_entry_rcu(sta, &sdata->local->sta_list, list) { @@ -3215,7 +3175,9 @@ /* send SM PS frame to AP */ err = ieee80211_send_smps_action(sdata, smps_mode, - ap, ap); + ap, ap, + ieee80211_vif_is_mld(&sdata->vif) ? + link->link_id : -1); if (err) link->u.mgd.req_smps = old_req; else if (smps_mode != IEEE80211_SMPS_OFF && tdls_peer_found) @@ -3245,7 +3207,6 @@ local->dynamic_ps_forced_timeout = timeout; /* no change, but if automatic follow powersave */ - sdata_lock(sdata); for (link_id = 0; link_id < ARRAY_SIZE(sdata->link); link_id++) { struct ieee80211_link_data *link; @@ -3256,7 +3217,6 @@ __ieee80211_request_smps_mgd(sdata, link, link->u.mgd.req_smps); } - sdata_unlock(sdata); if (ieee80211_hw_check(&local->hw, SUPPORTS_DYNAMIC_PS)) ieee80211_hw_config(local, IEEE80211_CONF_CHANGE_PS); @@ -3402,7 +3362,8 @@ struct ieee80211_local *local = sdata->local; int err; - mutex_lock(&local->mtx); + lockdep_assert_wiphy(local->hw.wiphy); + if (!list_empty(&local->roc_list) || local->scanning) { err = -EBUSY; goto out_unlock; @@ -3417,12 +3378,10 @@ if (err) goto out_unlock; - ieee80211_queue_delayed_work(&sdata->local->hw, - &sdata->deflink.dfs_cac_timer_work, - msecs_to_jiffies(cac_time_ms)); + wiphy_delayed_work_queue(wiphy, &sdata->deflink.dfs_cac_timer_work, + msecs_to_jiffies(cac_time_ms)); out_unlock: - mutex_unlock(&local->mtx); return err; } @@ -3432,20 +3391,21 @@ struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev); struct ieee80211_local *local = sdata->local; - mutex_lock(&local->mtx); + lockdep_assert_wiphy(local->hw.wiphy); + list_for_each_entry(sdata, &local->interfaces, list) { /* it might be waiting for the local->mtx, but then * by the time it gets it, sdata->wdev.cac_started * will no longer be true */ - cancel_delayed_work(&sdata->deflink.dfs_cac_timer_work); + wiphy_delayed_work_cancel(wiphy, + &sdata->deflink.dfs_cac_timer_work); if (sdata->wdev.cac_started) { ieee80211_link_release_channel(&sdata->deflink); sdata->wdev.cac_started = false; } } - mutex_unlock(&local->mtx); } static struct cfg80211_beacon_data * @@ -3577,11 +3537,11 @@ if (iter == sdata || iter->vif.mbssid_tx_vif != vif) continue; - ieee80211_queue_work(&iter->local->hw, - &iter->deflink.csa_finalize_work); + wiphy_work_queue(iter->local->hw.wiphy, + &iter->deflink.csa_finalize_work); } } - ieee80211_queue_work(&local->hw, &sdata->deflink.csa_finalize_work); + wiphy_work_queue(local->hw.wiphy, &sdata->deflink.csa_finalize_work); rcu_read_unlock(); } @@ -3644,9 +3604,7 @@ u64 changed = 0; int err; - sdata_assert_lock(sdata); - lockdep_assert_held(&local->mtx); - lockdep_assert_held(&local->chanctx_mtx); + lockdep_assert_wiphy(local->hw.wiphy); if (sdata->vif.bss_conf.eht_puncturing != sdata->vif.bss_conf.csa_punct_bitmap) { sdata->vif.bss_conf.eht_puncturing = @@ -3713,30 +3671,23 @@ } } -void ieee80211_csa_finalize_work(struct work_struct *work) +void ieee80211_csa_finalize_work(struct wiphy *wiphy, struct wiphy_work *work) { struct ieee80211_link_data *link = container_of(work, struct ieee80211_link_data, csa_finalize_work); struct ieee80211_sub_if_data *sdata = link->sdata; struct ieee80211_local *local = sdata->local; - sdata_lock(sdata); - mutex_lock(&local->mtx); - mutex_lock(&local->chanctx_mtx); + lockdep_assert_wiphy(local->hw.wiphy); /* AP might have been stopped while waiting for the lock. */ if (!link->conf->csa_active) - goto unlock; + return; if (!ieee80211_sdata_running(sdata)) - goto unlock; + return; ieee80211_csa_finalize(link); - -unlock: - mutex_unlock(&local->chanctx_mtx); - mutex_unlock(&local->mtx); - sdata_unlock(sdata); } static int ieee80211_set_csa_beacon(struct ieee80211_sub_if_data *sdata, @@ -3892,8 +3843,7 @@ u64 changed = 0; int err; - sdata_assert_lock(sdata); - lockdep_assert_held(&local->mtx); + lockdep_assert_wiphy(local->hw.wiphy); if (!list_empty(&local->roc_list) || local->scanning) return -EBUSY; @@ -3909,9 +3859,8 @@ if (sdata->vif.bss_conf.csa_active) return -EBUSY; - mutex_lock(&local->chanctx_mtx); conf = rcu_dereference_protected(sdata->vif.bss_conf.chanctx_conf, - lockdep_is_held(&local->chanctx_mtx)); + lockdep_is_held(&local->hw.wiphy->mtx)); if (!conf) { err = -EBUSY; goto out; @@ -3985,7 +3934,6 @@ } out: - mutex_unlock(&local->chanctx_mtx); return err; } @@ -3994,18 +3942,15 @@ { struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev); struct ieee80211_local *local = sdata->local; - int err; - mutex_lock(&local->mtx); - err = __ieee80211_channel_switch(wiphy, dev, params); - mutex_unlock(&local->mtx); + lockdep_assert_wiphy(local->hw.wiphy); - return err; + return __ieee80211_channel_switch(wiphy, dev, params); } u64 ieee80211_mgmt_tx_cookie(struct ieee80211_local *local) { - lockdep_assert_held(&local->mtx); + lockdep_assert_wiphy(local->hw.wiphy); local->roc_cookie_counter++; @@ -4037,7 +3982,8 @@ return -ENOMEM; } - IEEE80211_SKB_CB(skb)->ack_frame_id = id; + IEEE80211_SKB_CB(skb)->status_data_idr = 1; + IEEE80211_SKB_CB(skb)->status_data = id; *cookie = ieee80211_mgmt_tx_cookie(local); IEEE80211_SKB_CB(ack_skb)->ack.cookie = *cookie; @@ -4139,7 +4085,7 @@ int ret; /* the lock is needed to assign the cookie later */ - mutex_lock(&local->mtx); + lockdep_assert_wiphy(local->hw.wiphy); rcu_read_lock(); chanctx_conf = rcu_dereference(sdata->vif.bss_conf.chanctx_conf); @@ -4209,7 +4155,6 @@ ret = 0; unlock: rcu_read_unlock(); - mutex_unlock(&local->mtx); return ret; } @@ -4567,7 +4512,8 @@ { struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev); struct sta_info *sta; - int ret; + + lockdep_assert_wiphy(sdata->local->hw.wiphy); if (!sdata->local->ops->set_tid_config) return -EOPNOTSUPP; @@ -4575,17 +4521,11 @@ if (!tid_conf->peer) return drv_set_tid_config(sdata->local, sdata, NULL, tid_conf); - mutex_lock(&sdata->local->sta_mtx); sta = sta_info_get_bss(sdata, tid_conf->peer); - if (!sta) { - mutex_unlock(&sdata->local->sta_mtx); + if (!sta) return -ENOENT; - } - - ret = drv_set_tid_config(sdata->local, sdata, &sta->sta, tid_conf); - mutex_unlock(&sdata->local->sta_mtx); - return ret; + return drv_set_tid_config(sdata->local, sdata, &sta->sta, tid_conf); } static int ieee80211_reset_tid_config(struct wiphy *wiphy, @@ -4594,7 +4534,8 @@ { struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev); struct sta_info *sta; - int ret; + + lockdep_assert_wiphy(sdata->local->hw.wiphy); if (!sdata->local->ops->reset_tid_config) return -EOPNOTSUPP; @@ -4602,17 +4543,11 @@ if (!peer) return drv_reset_tid_config(sdata->local, sdata, NULL, tids); - mutex_lock(&sdata->local->sta_mtx); sta = sta_info_get_bss(sdata, peer); - if (!sta) { - mutex_unlock(&sdata->local->sta_mtx); + if (!sta) return -ENOENT; - } - - ret = drv_reset_tid_config(sdata->local, sdata, &sta->sta, tids); - mutex_unlock(&sdata->local->sta_mtx); - return ret; + return drv_reset_tid_config(sdata->local, sdata, &sta->sta, tids); } static int ieee80211_set_sar_specs(struct wiphy *wiphy, @@ -4698,6 +4633,8 @@ ieee80211_color_change_bss_config_notify(struct ieee80211_sub_if_data *sdata, u8 color, int enable, u64 changed) { + lockdep_assert_wiphy(sdata->local->hw.wiphy); + sdata->vif.bss_conf.he_bss_color.color = color; sdata->vif.bss_conf.he_bss_color.enabled = enable; changed |= BSS_CHANGED_HE_BSS_COLOR; @@ -4707,7 +4644,6 @@ if (!sdata->vif.bss_conf.nontransmitted && sdata->vif.mbssid_tx_vif) { struct ieee80211_sub_if_data *child; - mutex_lock(&sdata->local->iflist_mtx); list_for_each_entry(child, &sdata->local->interfaces, list) { if (child != sdata && child->vif.mbssid_tx_vif == &sdata->vif) { child->vif.bss_conf.he_bss_color.color = color; @@ -4717,7 +4653,6 @@ BSS_CHANGED_HE_BSS_COLOR); } } - mutex_unlock(&sdata->local->iflist_mtx); } } @@ -4727,8 +4662,7 @@ u64 changed = 0; int err; - sdata_assert_lock(sdata); - lockdep_assert_held(&local->mtx); + lockdep_assert_wiphy(local->hw.wiphy); sdata->vif.bss_conf.color_change_active = false; @@ -4746,28 +4680,24 @@ return 0; } -void ieee80211_color_change_finalize_work(struct work_struct *work) +void ieee80211_color_change_finalize_work(struct wiphy *wiphy, + struct wiphy_work *work) { struct ieee80211_sub_if_data *sdata = container_of(work, struct ieee80211_sub_if_data, deflink.color_change_finalize_work); struct ieee80211_local *local = sdata->local; - sdata_lock(sdata); - mutex_lock(&local->mtx); + lockdep_assert_wiphy(local->hw.wiphy); /* AP might have been stopped while waiting for the lock. */ if (!sdata->vif.bss_conf.color_change_active) - goto unlock; + return; if (!ieee80211_sdata_running(sdata)) - goto unlock; + return; ieee80211_color_change_finalize(sdata); - -unlock: - mutex_unlock(&local->mtx); - sdata_unlock(sdata); } void ieee80211_color_collision_detection_work(struct work_struct *work) @@ -4778,17 +4708,15 @@ color_collision_detect_work); struct ieee80211_sub_if_data *sdata = link->sdata; - sdata_lock(sdata); cfg80211_obss_color_collision_notify(sdata->dev, link->color_bitmap); - sdata_unlock(sdata); } void ieee80211_color_change_finish(struct ieee80211_vif *vif) { struct ieee80211_sub_if_data *sdata = vif_to_sdata(vif); - ieee80211_queue_work(&sdata->local->hw, - &sdata->deflink.color_change_finalize_work); + wiphy_work_queue(sdata->local->hw.wiphy, + &sdata->deflink.color_change_finalize_work); } EXPORT_SYMBOL_GPL(ieee80211_color_change_finish); @@ -4824,13 +4752,11 @@ u64 changed = 0; int err; - sdata_assert_lock(sdata); + lockdep_assert_wiphy(local->hw.wiphy); if (sdata->vif.bss_conf.nontransmitted) return -EINVAL; - mutex_lock(&local->mtx); - /* don't allow another color change if one is already active or if csa * is active */ @@ -4855,7 +4781,6 @@ ieee80211_color_change_finalize(sdata); out: - mutex_unlock(&local->mtx); return err; } @@ -4877,16 +4802,13 @@ unsigned int link_id) { struct ieee80211_sub_if_data *sdata = IEEE80211_WDEV_TO_SUB_IF(wdev); - int res; + + lockdep_assert_wiphy(sdata->local->hw.wiphy); if (wdev->use_4addr) return -EOPNOTSUPP; - mutex_lock(&sdata->local->mtx); - res = ieee80211_vif_set_links(sdata, wdev->valid_links, 0); - mutex_unlock(&sdata->local->mtx); - - return res; + return ieee80211_vif_set_links(sdata, wdev->valid_links, 0); } static void ieee80211_del_intf_link(struct wiphy *wiphy, @@ -4895,9 +4817,9 @@ { struct ieee80211_sub_if_data *sdata = IEEE80211_WDEV_TO_SUB_IF(wdev); - mutex_lock(&sdata->local->mtx); + lockdep_assert_wiphy(sdata->local->hw.wiphy); + ieee80211_vif_set_links(sdata, wdev->valid_links, 0); - mutex_unlock(&sdata->local->mtx); } static int sta_add_link_station(struct ieee80211_local *local, @@ -4937,13 +4859,10 @@ { struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev); struct ieee80211_local *local = wiphy_priv(wiphy); - int ret; - mutex_lock(&sdata->local->sta_mtx); - ret = sta_add_link_station(local, sdata, params); - mutex_unlock(&sdata->local->sta_mtx); + lockdep_assert_wiphy(sdata->local->hw.wiphy); - return ret; + return sta_add_link_station(local, sdata, params); } static int sta_mod_link_station(struct ieee80211_local *local, @@ -4968,13 +4887,10 @@ { struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev); struct ieee80211_local *local = wiphy_priv(wiphy); - int ret; - mutex_lock(&sdata->local->sta_mtx); - ret = sta_mod_link_station(local, sdata, params); - mutex_unlock(&sdata->local->sta_mtx); + lockdep_assert_wiphy(sdata->local->hw.wiphy); - return ret; + return sta_mod_link_station(local, sdata, params); } static int sta_del_link_station(struct ieee80211_sub_if_data *sdata, @@ -5003,13 +4919,10 @@ struct link_station_del_parameters *params) { struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev); - int ret; - mutex_lock(&sdata->local->sta_mtx); - ret = sta_del_link_station(sdata, params); - mutex_unlock(&sdata->local->sta_mtx); + lockdep_assert_wiphy(sdata->local->hw.wiphy); - return ret; + return sta_del_link_station(sdata, params); } static int ieee80211_set_hw_timestamp(struct wiphy *wiphy, diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/chan.c backport-iwlwifi-dkms-11510/net/mac80211/chan.c --- backport-iwlwifi-dkms-11289/net/mac80211/chan.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/chan.c 2023-10-04 04:18:43.000000000 +0800 @@ -18,7 +18,7 @@ struct ieee80211_link_data *link; int num = 0; - lockdep_assert_held(&local->chanctx_mtx); + lockdep_assert_wiphy(local->hw.wiphy); list_for_each_entry(link, &ctx->assigned_links, assigned_chanctx_list) num++; @@ -32,7 +32,7 @@ struct ieee80211_link_data *link; int num = 0; - lockdep_assert_held(&local->chanctx_mtx); + lockdep_assert_wiphy(local->hw.wiphy); list_for_each_entry(link, &ctx->reserved_links, reserved_chanctx_list) num++; @@ -52,7 +52,7 @@ struct ieee80211_chanctx *ctx; int num = 0; - lockdep_assert_held(&local->chanctx_mtx); + lockdep_assert_wiphy(local->hw.wiphy); list_for_each_entry(ctx, &local->chanctx_list, list) num++; @@ -62,7 +62,8 @@ static bool ieee80211_can_create_new_chanctx(struct ieee80211_local *local) { - lockdep_assert_held(&local->chanctx_mtx); + lockdep_assert_wiphy(local->hw.wiphy); + return ieee80211_num_chanctx(local) < ieee80211_max_num_channels(local); } @@ -73,7 +74,7 @@ struct ieee80211_chanctx_conf *conf; conf = rcu_dereference_protected(link->conf->chanctx_conf, - lockdep_is_held(&local->chanctx_mtx)); + lockdep_is_held(&local->hw.wiphy->mtx)); if (!conf) return NULL; @@ -87,7 +88,7 @@ { struct ieee80211_link_data *link; - lockdep_assert_held(&local->chanctx_mtx); + lockdep_assert_wiphy(local->hw.wiphy); list_for_each_entry(link, &ctx->reserved_links, reserved_chanctx_list) { @@ -110,7 +111,7 @@ { struct ieee80211_link_data *link; - lockdep_assert_held(&local->chanctx_mtx); + lockdep_assert_wiphy(local->hw.wiphy); list_for_each_entry(link, &ctx->assigned_links, assigned_chanctx_list) { @@ -136,7 +137,7 @@ struct ieee80211_chanctx *ctx, const struct cfg80211_chan_def *compat) { - lockdep_assert_held(&local->chanctx_mtx); + lockdep_assert_wiphy(local->hw.wiphy); compat = ieee80211_chanctx_reserved_chandef(local, ctx, compat); if (!compat) @@ -154,7 +155,7 @@ struct ieee80211_chanctx *ctx, const struct cfg80211_chan_def *def) { - lockdep_assert_held(&local->chanctx_mtx); + lockdep_assert_wiphy(local->hw.wiphy); if (ieee80211_chanctx_combined_chandef(local, ctx, def)) return true; @@ -173,7 +174,7 @@ { struct ieee80211_chanctx *ctx; - lockdep_assert_held(&local->chanctx_mtx); + lockdep_assert_wiphy(local->hw.wiphy); if (mode == IEEE80211_CHANCTX_EXCLUSIVE) return NULL; @@ -361,7 +362,7 @@ enum nl80211_chan_width max_bw; struct cfg80211_chan_def min_def; - lockdep_assert_held(&local->chanctx_mtx); + lockdep_assert_wiphy(local->hw.wiphy); /* don't optimize non-20MHz based and radar_enabled confs */ if (ctx->conf.def.width == NL80211_CHAN_WIDTH_5 || @@ -537,7 +538,7 @@ { struct ieee80211_chanctx *ctx; - lockdep_assert_held(&local->chanctx_mtx); + lockdep_assert_wiphy(local->hw.wiphy); if (mode == IEEE80211_CHANCTX_EXCLUSIVE) return NULL; @@ -572,7 +573,7 @@ { struct ieee80211_sub_if_data *sdata; - lockdep_assert_held(&local->mtx); + lockdep_assert_wiphy(local->hw.wiphy); rcu_read_lock(); list_for_each_entry_rcu(sdata, &local->interfaces, list) { @@ -602,8 +603,7 @@ struct ieee80211_sub_if_data *sdata; bool required = false; - lockdep_assert_held(&local->chanctx_mtx); - lockdep_assert_held(&local->mtx); + lockdep_assert_wiphy(local->hw.wiphy); rcu_read_lock(); list_for_each_entry_rcu(sdata, &local->interfaces, list) { @@ -641,7 +641,7 @@ { struct ieee80211_chanctx *ctx; - lockdep_assert_held(&local->chanctx_mtx); + lockdep_assert_wiphy(local->hw.wiphy); ctx = kzalloc(sizeof(*ctx) + local->hw.chanctx_data_size, GFP_KERNEL); if (!ctx) @@ -665,8 +665,7 @@ u32 changed; int err; - lockdep_assert_held(&local->mtx); - lockdep_assert_held(&local->chanctx_mtx); + lockdep_assert_wiphy(local->hw.wiphy); if (!local->use_chanctx) local->hw.conf.radar_enabled = ctx->conf.radar_enabled; @@ -698,8 +697,7 @@ struct ieee80211_chanctx *ctx; int err; - lockdep_assert_held(&local->mtx); - lockdep_assert_held(&local->chanctx_mtx); + lockdep_assert_wiphy(local->hw.wiphy); ctx = ieee80211_alloc_chanctx(local, chandef, mode); if (!ctx) @@ -718,7 +716,7 @@ static void ieee80211_del_chanctx(struct ieee80211_local *local, struct ieee80211_chanctx *ctx) { - lockdep_assert_held(&local->chanctx_mtx); + lockdep_assert_wiphy(local->hw.wiphy); if (!local->use_chanctx) { struct cfg80211_chan_def *chandef = &local->_oper_chandef; @@ -753,7 +751,7 @@ static void ieee80211_free_chanctx(struct ieee80211_local *local, struct ieee80211_chanctx *ctx) { - lockdep_assert_held(&local->chanctx_mtx); + lockdep_assert_wiphy(local->hw.wiphy); WARN_ON_ONCE(ieee80211_chanctx_refcount(local, ctx) != 0); @@ -770,7 +768,7 @@ const struct cfg80211_chan_def *compat = NULL; struct sta_info *sta; - lockdep_assert_held(&local->chanctx_mtx); + lockdep_assert_wiphy(local->hw.wiphy); rcu_read_lock(); list_for_each_entry_rcu(sdata, &local->interfaces, list) { @@ -833,9 +831,7 @@ { bool radar_enabled; - lockdep_assert_held(&local->chanctx_mtx); - /* for ieee80211_is_radar_required */ - lockdep_assert_held(&local->mtx); + lockdep_assert_wiphy(local->hw.wiphy); radar_enabled = ieee80211_chanctx_radar_required(local, chanctx); @@ -865,7 +861,7 @@ return -ENOTSUPP; conf = rcu_dereference_protected(link->conf->chanctx_conf, - lockdep_is_held(&local->chanctx_mtx)); + lockdep_is_held(&local->hw.wiphy->mtx)); if (conf) { curr_ctx = container_of(conf, struct ieee80211_chanctx, conf); @@ -920,7 +916,7 @@ struct ieee80211_sub_if_data *sdata; u8 rx_chains_static, rx_chains_dynamic; - lockdep_assert_held(&local->chanctx_mtx); + lockdep_assert_wiphy(local->hw.wiphy); rx_chains_static = 1; rx_chains_dynamic = 1; @@ -1023,7 +1019,7 @@ if (WARN_ON(sdata->vif.type != NL80211_IFTYPE_AP)) return; - lockdep_assert_held(&local->mtx); + lockdep_assert_wiphy(local->hw.wiphy); /* Check that conf exists, even when clearing this function * must be called with the AP's channel context still there @@ -1032,7 +1028,7 @@ * to a channel context that has already been freed. */ conf = rcu_dereference_protected(link_conf->chanctx_conf, - lockdep_is_held(&local->chanctx_mtx)); + lockdep_is_held(&local->hw.wiphy->mtx)); WARN_ON(!conf); if (clear) @@ -1056,11 +1052,9 @@ { struct ieee80211_local *local = link->sdata->local; - mutex_lock(&local->chanctx_mtx); + lockdep_assert_wiphy(local->hw.wiphy); __ieee80211_link_copy_chanctx_to_vlans(link, clear); - - mutex_unlock(&local->chanctx_mtx); } int ieee80211_link_unreserve_chanctx(struct ieee80211_link_data *link) @@ -1068,7 +1062,7 @@ struct ieee80211_sub_if_data *sdata = link->sdata; struct ieee80211_chanctx *ctx = link->reserved_chanctx; - lockdep_assert_held(&sdata->local->chanctx_mtx); + lockdep_assert_wiphy(sdata->local->hw.wiphy); if (WARN_ON(!ctx)) return -EINVAL; @@ -1108,7 +1102,7 @@ struct ieee80211_local *local = sdata->local; struct ieee80211_chanctx *new_ctx, *curr_ctx, *ctx; - lockdep_assert_held(&local->chanctx_mtx); + lockdep_assert_wiphy(local->hw.wiphy); curr_ctx = ieee80211_link_get_chanctx(link); if (curr_ctx && local->use_chanctx && !local->ops->switch_vif_chanctx) @@ -1206,8 +1200,8 @@ case NL80211_IFTYPE_AP: case NL80211_IFTYPE_MESH_POINT: case NL80211_IFTYPE_OCB: - ieee80211_queue_work(&sdata->local->hw, - &link->csa_finalize_work); + wiphy_work_queue(sdata->local->hw.wiphy, + &link->csa_finalize_work); break; case NL80211_IFTYPE_STATION: wiphy_delayed_work_queue(sdata->local->hw.wiphy, @@ -1265,8 +1259,7 @@ u64 changed = 0; int err; - lockdep_assert_held(&local->mtx); - lockdep_assert_held(&local->chanctx_mtx); + lockdep_assert_wiphy(local->hw.wiphy); new_ctx = link->reserved_chanctx; old_ctx = ieee80211_link_get_chanctx(link); @@ -1390,7 +1383,7 @@ struct ieee80211_sub_if_data *sdata = link->sdata; struct ieee80211_chanctx *old_ctx, *new_ctx; - lockdep_assert_held(&sdata->local->chanctx_mtx); + lockdep_assert_wiphy(sdata->local->hw.wiphy); new_ctx = link->reserved_chanctx; old_ctx = ieee80211_link_get_chanctx(link); @@ -1415,8 +1408,7 @@ { const struct cfg80211_chan_def *chandef; - lockdep_assert_held(&local->mtx); - lockdep_assert_held(&local->chanctx_mtx); + lockdep_assert_wiphy(local->hw.wiphy); chandef = ieee80211_chanctx_reserved_chandef(local, new_ctx, NULL); if (WARN_ON(!chandef)) @@ -1437,8 +1429,7 @@ struct ieee80211_chanctx *ctx, *old_ctx; int i, err; - lockdep_assert_held(&local->mtx); - lockdep_assert_held(&local->chanctx_mtx); + lockdep_assert_wiphy(local->hw.wiphy); vif_chsw = kcalloc(n_vifs, sizeof(vif_chsw[0]), GFP_KERNEL); if (!vif_chsw) @@ -1482,8 +1473,7 @@ struct ieee80211_chanctx *ctx; int err; - lockdep_assert_held(&local->mtx); - lockdep_assert_held(&local->chanctx_mtx); + lockdep_assert_wiphy(local->hw.wiphy); list_for_each_entry(ctx, &local->chanctx_list, list) { if (ctx->replace_state != IEEE80211_CHANCTX_REPLACES_OTHER) @@ -1523,8 +1513,7 @@ int err, n_assigned, n_reserved, n_ready; int n_ctx = 0, n_vifs_switch = 0, n_vifs_assign = 0, n_vifs_ctxless = 0; - lockdep_assert_held(&local->mtx); - lockdep_assert_held(&local->chanctx_mtx); + lockdep_assert_wiphy(local->hw.wiphy); /* * If there are 2 independent pairs of channel contexts performing @@ -1783,10 +1772,10 @@ struct ieee80211_chanctx *ctx; bool use_reserved_switch = false; - lockdep_assert_held(&local->chanctx_mtx); + lockdep_assert_wiphy(local->hw.wiphy); conf = rcu_dereference_protected(link_conf->chanctx_conf, - lockdep_is_held(&local->chanctx_mtx)); + lockdep_is_held(&local->hw.wiphy->mtx)); if (!conf) return; @@ -1821,7 +1810,7 @@ u8 radar_detect_width = 0; int ret; - lockdep_assert_held(&local->mtx); + lockdep_assert_wiphy(local->hw.wiphy); if (sdata->vif.active_links && !(sdata->vif.active_links & BIT(link->link_id))) { @@ -1829,8 +1818,6 @@ return 0; } - mutex_lock(&local->chanctx_mtx); - ret = cfg80211_chandef_dfs_required(local->hw.wiphy, chandef, sdata->wdev.iftype); @@ -1872,7 +1859,6 @@ if (ret) link->radar_required = false; - mutex_unlock(&local->chanctx_mtx); return ret; } @@ -1884,8 +1870,7 @@ struct ieee80211_chanctx *old_ctx; int err; - lockdep_assert_held(&local->mtx); - lockdep_assert_held(&local->chanctx_mtx); + lockdep_assert_wiphy(local->hw.wiphy); new_ctx = link->reserved_chanctx; old_ctx = ieee80211_link_get_chanctx(link); @@ -1948,51 +1933,40 @@ struct ieee80211_chanctx_conf *conf; struct ieee80211_chanctx *ctx; const struct cfg80211_chan_def *compat; - int ret; + + lockdep_assert_wiphy(local->hw.wiphy); if (!cfg80211_chandef_usable(sdata->local->hw.wiphy, chandef, IEEE80211_CHAN_DISABLED)) return -EINVAL; - mutex_lock(&local->chanctx_mtx); - if (cfg80211_chandef_identical(chandef, &link_conf->chandef)) { - ret = 0; - goto out; - } + if (cfg80211_chandef_identical(chandef, &link_conf->chandef)) + return 0; if (chandef->width == NL80211_CHAN_WIDTH_20_NOHT || - link_conf->chandef.width == NL80211_CHAN_WIDTH_20_NOHT) { - ret = -EINVAL; - goto out; - } + link_conf->chandef.width == NL80211_CHAN_WIDTH_20_NOHT) + return -EINVAL; conf = rcu_dereference_protected(link_conf->chanctx_conf, - lockdep_is_held(&local->chanctx_mtx)); - if (!conf) { - ret = -EINVAL; - goto out; - } + lockdep_is_held(&local->hw.wiphy->mtx)); + if (!conf) + return -EINVAL; ctx = container_of(conf, struct ieee80211_chanctx, conf); compat = cfg80211_chandef_compatible(&conf->def, chandef); - if (!compat) { - ret = -EINVAL; - goto out; - } + if (!compat) + return -EINVAL; switch (ctx->replace_state) { case IEEE80211_CHANCTX_REPLACE_NONE: - if (!ieee80211_chanctx_reserved_chandef(local, ctx, compat)) { - ret = -EBUSY; - goto out; - } + if (!ieee80211_chanctx_reserved_chandef(local, ctx, compat)) + return -EBUSY; break; case IEEE80211_CHANCTX_WILL_BE_REPLACED: /* TODO: Perhaps the bandwidth change could be treated as a * reservation itself? */ - ret = -EBUSY; - goto out; + return -EBUSY; case IEEE80211_CHANCTX_REPLACES_OTHER: /* channel context that is going to replace another channel * context doesn't really exist and shouldn't be assigned @@ -2006,22 +1980,17 @@ ieee80211_recalc_chanctx_chantype(local, ctx); *changed |= BSS_CHANGED_BANDWIDTH; - ret = 0; - out: - mutex_unlock(&local->chanctx_mtx); - return ret; + return 0; } void ieee80211_link_release_channel(struct ieee80211_link_data *link) { struct ieee80211_sub_if_data *sdata = link->sdata; - mutex_lock(&sdata->local->chanctx_mtx); - if (rcu_access_pointer(link->conf->chanctx_conf)) { - lockdep_assert_held(&sdata->local->mtx); + lockdep_assert_wiphy(sdata->local->hw.wiphy); + + if (rcu_access_pointer(link->conf->chanctx_conf)) __ieee80211_link_release_channel(link); - } - mutex_unlock(&sdata->local->chanctx_mtx); } void ieee80211_link_vlan_copy_chanctx(struct ieee80211_link_data *link) @@ -2034,20 +2003,19 @@ struct ieee80211_sub_if_data *ap; struct ieee80211_chanctx_conf *conf; + lockdep_assert_wiphy(local->hw.wiphy); + if (WARN_ON(sdata->vif.type != NL80211_IFTYPE_AP_VLAN || !sdata->bss)) return; ap = container_of(sdata->bss, struct ieee80211_sub_if_data, u.ap); - mutex_lock(&local->chanctx_mtx); - rcu_read_lock(); ap_conf = rcu_dereference(ap->vif.link_conf[link_id]); conf = rcu_dereference_protected(ap_conf->chanctx_conf, - lockdep_is_held(&local->chanctx_mtx)); + lockdep_is_held(&local->hw.wiphy->mtx)); rcu_assign_pointer(link_conf->chanctx_conf, conf); rcu_read_unlock(); - mutex_unlock(&local->chanctx_mtx); } void ieee80211_iter_chan_contexts_atomic( diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/debugfs.c backport-iwlwifi-dkms-11510/net/mac80211/debugfs.c --- backport-iwlwifi-dkms-11289/net/mac80211/debugfs.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/debugfs.c 2023-10-04 04:18:43.000000000 +0800 @@ -4,7 +4,7 @@ * * Copyright 2007 Johannes Berg * Copyright 2013-2015 Intel Mobile Communications GmbH - * Copyright (C) 2018 - 2019, 2021-2022 Intel Corporation + * Copyright (C) 2018 - 2019, 2021-2023 Intel Corporation */ #include @@ -288,10 +288,10 @@ q_limit_low_old = local->aql_txq_limit_low[ac]; q_limit_high_old = local->aql_txq_limit_high[ac]; + wiphy_lock(local->hw.wiphy); local->aql_txq_limit_low[ac] = q_limit_low; local->aql_txq_limit_high[ac] = q_limit_high; - mutex_lock(&local->sta_mtx); list_for_each_entry(sta, &local->sta_list, list) { /* If a sta has customized queue limits, keep it */ if (sta->airtime[ac].aql_limit_low == q_limit_low_old && @@ -300,7 +300,8 @@ sta->airtime[ac].aql_limit_high = q_limit_high; } } - mutex_unlock(&local->sta_mtx); + wiphy_unlock(local->hw.wiphy); + return count; } @@ -600,9 +601,9 @@ char buf[20]; int res; - rtnl_lock(); + wiphy_lock(local->hw.wiphy); res = drv_get_stats(local, &stats); - rtnl_unlock(); + wiphy_unlock(local->hw.wiphy); if (res) return res; res = printvalue(&stats, buf, sizeof(buf)); diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/debugfs_key.c backport-iwlwifi-dkms-11510/net/mac80211/debugfs_key.c --- backport-iwlwifi-dkms-11289/net/mac80211/debugfs_key.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/debugfs_key.c 2023-10-04 04:18:43.000000000 +0800 @@ -4,7 +4,7 @@ * Copyright (c) 2006 Jiri Benc * Copyright 2007 Johannes Berg * Copyright (C) 2015 Intel Deutschland GmbH - * Copyright (C) 2021-2022 Intel Corporation + * Copyright (C) 2021-2023 Intel Corporation */ #include @@ -378,14 +378,14 @@ if (!sdata->vif.debugfs_dir) return; - lockdep_assert_held(&sdata->local->key_mtx); + lockdep_assert_wiphy(sdata->local->hw.wiphy); debugfs_remove(sdata->debugfs.default_unicast_key); sdata->debugfs.default_unicast_key = NULL; if (sdata->default_unicast_key) { - key = key_mtx_dereference(sdata->local, - sdata->default_unicast_key); + key = wiphy_dereference(sdata->local->hw.wiphy, + sdata->default_unicast_key); sprintf(buf, "../keys/%d", key->debugfs.cnt); sdata->debugfs.default_unicast_key = debugfs_create_symlink("default_unicast_key", @@ -396,8 +396,8 @@ sdata->debugfs.default_multicast_key = NULL; if (sdata->deflink.default_multicast_key) { - key = key_mtx_dereference(sdata->local, - sdata->deflink.default_multicast_key); + key = wiphy_dereference(sdata->local->hw.wiphy, + sdata->deflink.default_multicast_key); sprintf(buf, "../keys/%d", key->debugfs.cnt); sdata->debugfs.default_multicast_key = debugfs_create_symlink("default_multicast_key", @@ -413,8 +413,8 @@ if (!sdata->vif.debugfs_dir) return; - key = key_mtx_dereference(sdata->local, - sdata->deflink.default_mgmt_key); + key = wiphy_dereference(sdata->local->hw.wiphy, + sdata->deflink.default_mgmt_key); if (key) { sprintf(buf, "../keys/%d", key->debugfs.cnt); sdata->debugfs.default_mgmt_key = @@ -442,8 +442,8 @@ if (!sdata->vif.debugfs_dir) return; - key = key_mtx_dereference(sdata->local, - sdata->deflink.default_beacon_key); + key = wiphy_dereference(sdata->local->hw.wiphy, + sdata->deflink.default_beacon_key); if (key) { sprintf(buf, "../keys/%d", key->debugfs.cnt); sdata->debugfs.default_beacon_key = diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/debugfs_netdev.c backport-iwlwifi-dkms-11510/net/mac80211/debugfs_netdev.c --- backport-iwlwifi-dkms-11289/net/mac80211/debugfs_netdev.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/debugfs_netdev.c 2023-10-04 04:18:43.000000000 +0800 @@ -23,18 +23,18 @@ #include "debugfs_netdev.h" #include "driver-ops.h" -static ssize_t ieee80211_if_read( - void *data, +static ssize_t ieee80211_if_read_sdata( + struct ieee80211_sub_if_data *sdata, char __user *userbuf, size_t count, loff_t *ppos, - ssize_t (*format)(const void *, char *, int)) + ssize_t (*format)(const struct ieee80211_sub_if_data *sdata, char *, int)) { char buf[200]; ssize_t ret = -EINVAL; - read_lock(&dev_base_lock); - ret = (*format)(data, buf, sizeof(buf)); - read_unlock(&dev_base_lock); + wiphy_lock(sdata->local->hw.wiphy); + ret = (*format)(sdata, buf, sizeof(buf)); + wiphy_unlock(sdata->local->hw.wiphy); if (ret >= 0) ret = simple_read_from_buffer(userbuf, count, ppos, buf, ret); @@ -42,11 +42,11 @@ return ret; } -static ssize_t ieee80211_if_write( - void *data, +static ssize_t ieee80211_if_write_sdata( + struct ieee80211_sub_if_data *sdata, const char __user *userbuf, size_t count, loff_t *ppos, - ssize_t (*write)(void *, const char *, int)) + ssize_t (*write)(struct ieee80211_sub_if_data *sdata, const char *, int)) { char buf[64]; ssize_t ret; @@ -58,9 +58,51 @@ return -EFAULT; buf[count] = '\0'; - rtnl_lock(); - ret = (*write)(data, buf, count); - rtnl_unlock(); + wiphy_lock(sdata->local->hw.wiphy); + ret = (*write)(sdata, buf, count); + wiphy_unlock(sdata->local->hw.wiphy); + + return ret; +} + +static ssize_t ieee80211_if_read_link( + struct ieee80211_link_data *link, + char __user *userbuf, + size_t count, loff_t *ppos, + ssize_t (*format)(const struct ieee80211_link_data *link, char *, int)) +{ + char buf[200]; + ssize_t ret = -EINVAL; + + wiphy_lock(link->sdata->local->hw.wiphy); + ret = (*format)(link, buf, sizeof(buf)); + wiphy_unlock(link->sdata->local->hw.wiphy); + + if (ret >= 0) + ret = simple_read_from_buffer(userbuf, count, ppos, buf, ret); + + return ret; +} + +static ssize_t ieee80211_if_write_link( + struct ieee80211_link_data *link, + const char __user *userbuf, + size_t count, loff_t *ppos, + ssize_t (*write)(struct ieee80211_link_data *link, const char *, int)) +{ + char buf[64]; + ssize_t ret; + + if (count >= sizeof(buf)) + return -E2BIG; + + if (copy_from_user(buf, userbuf, count)) + return -EFAULT; + buf[count] = '\0'; + + wiphy_lock(link->sdata->local->hw.wiphy); + ret = (*write)(link, buf, count); + wiphy_unlock(link->sdata->local->hw.wiphy); return ret; } @@ -127,41 +169,37 @@ .llseek = generic_file_llseek, \ } -#define _IEEE80211_IF_FILE_R_FN(name, type) \ +#define _IEEE80211_IF_FILE_R_FN(name) \ static ssize_t ieee80211_if_read_##name(struct file *file, \ char __user *userbuf, \ size_t count, loff_t *ppos) \ { \ - ssize_t (*fn)(const void *, char *, int) = (void *) \ - ((ssize_t (*)(const type, char *, int)) \ - ieee80211_if_fmt_##name); \ - return ieee80211_if_read(file->private_data, \ - userbuf, count, ppos, fn); \ + return ieee80211_if_read_sdata(file->private_data, \ + userbuf, count, ppos, \ + ieee80211_if_fmt_##name); \ } -#define _IEEE80211_IF_FILE_W_FN(name, type) \ +#define _IEEE80211_IF_FILE_W_FN(name) \ static ssize_t ieee80211_if_write_##name(struct file *file, \ const char __user *userbuf, \ size_t count, loff_t *ppos) \ { \ - ssize_t (*fn)(void *, const char *, int) = (void *) \ - ((ssize_t (*)(type, const char *, int)) \ - ieee80211_if_parse_##name); \ - return ieee80211_if_write(file->private_data, userbuf, count, \ - ppos, fn); \ + return ieee80211_if_write_sdata(file->private_data, userbuf, \ + count, ppos, \ + ieee80211_if_parse_##name); \ } #define IEEE80211_IF_FILE_R(name) \ - _IEEE80211_IF_FILE_R_FN(name, struct ieee80211_sub_if_data *) \ + _IEEE80211_IF_FILE_R_FN(name) \ _IEEE80211_IF_FILE_OPS(name, ieee80211_if_read_##name, NULL) #define IEEE80211_IF_FILE_W(name) \ - _IEEE80211_IF_FILE_W_FN(name, struct ieee80211_sub_if_data *) \ + _IEEE80211_IF_FILE_W_FN(name) \ _IEEE80211_IF_FILE_OPS(name, NULL, ieee80211_if_write_##name) #define IEEE80211_IF_FILE_RW(name) \ - _IEEE80211_IF_FILE_R_FN(name, struct ieee80211_sub_if_data *) \ - _IEEE80211_IF_FILE_W_FN(name, struct ieee80211_sub_if_data *) \ + _IEEE80211_IF_FILE_R_FN(name) \ + _IEEE80211_IF_FILE_W_FN(name) \ _IEEE80211_IF_FILE_OPS(name, ieee80211_if_read_##name, \ ieee80211_if_write_##name) @@ -169,18 +207,37 @@ IEEE80211_IF_FMT_##format(name, struct ieee80211_sub_if_data, field) \ IEEE80211_IF_FILE_R(name) -/* Same but with a link_ prefix in the ops variable name and different type */ +#define _IEEE80211_IF_LINK_R_FN(name) \ +static ssize_t ieee80211_if_read_##name(struct file *file, \ + char __user *userbuf, \ + size_t count, loff_t *ppos) \ +{ \ + return ieee80211_if_read_link(file->private_data, \ + userbuf, count, ppos, \ + ieee80211_if_fmt_##name); \ +} + +#define _IEEE80211_IF_LINK_W_FN(name) \ +static ssize_t ieee80211_if_write_##name(struct file *file, \ + const char __user *userbuf, \ + size_t count, loff_t *ppos) \ +{ \ + return ieee80211_if_write_link(file->private_data, userbuf, \ + count, ppos, \ + ieee80211_if_parse_##name); \ +} + #define IEEE80211_IF_LINK_FILE_R(name) \ - _IEEE80211_IF_FILE_R_FN(name, struct ieee80211_link_data *) \ + _IEEE80211_IF_LINK_R_FN(name) \ _IEEE80211_IF_FILE_OPS(link_##name, ieee80211_if_read_##name, NULL) #define IEEE80211_IF_LINK_FILE_W(name) \ - _IEEE80211_IF_FILE_W_FN(name) \ + _IEEE80211_IF_LINK_W_FN(name) \ _IEEE80211_IF_FILE_OPS(link_##name, NULL, ieee80211_if_write_##name) #define IEEE80211_IF_LINK_FILE_RW(name) \ - _IEEE80211_IF_FILE_R_FN(name, struct ieee80211_link_data *) \ - _IEEE80211_IF_FILE_W_FN(name, struct ieee80211_link_data *) \ + _IEEE80211_IF_LINK_R_FN(name) \ + _IEEE80211_IF_LINK_W_FN(name) \ _IEEE80211_IF_FILE_OPS(link_##name, ieee80211_if_read_##name, \ ieee80211_if_write_##name) @@ -266,9 +323,11 @@ { struct ieee80211_sub_if_data *sdata = link->sdata; struct ieee80211_local *local = sdata->local; - int err; - if (sdata->vif.driver_flags & IEEE80211_VIF_DISABLE_SMPS_OVERRIDE) + /* The driver indicated that EML is enabled for the interface, thus do + * not allow to override the SMPS state. + */ + if (sdata->vif.driver_flags & IEEE80211_VIF_EML_ACTIVE) return -EOPNOTSUPP; if (!(local->hw.wiphy->features & NL80211_FEATURE_STATIC_SMPS) && @@ -284,11 +343,7 @@ if (sdata->vif.type != NL80211_IFTYPE_STATION) return -EOPNOTSUPP; - sdata_lock(sdata); - err = __ieee80211_request_smps_mgd(link->sdata, link, smps_mode); - sdata_unlock(sdata); - - return err; + return __ieee80211_request_smps_mgd(link->sdata, link, smps_mode); } static const char *smps_modes[IEEE80211_SMPS_NUM_MODES] = { @@ -360,16 +415,13 @@ case NL80211_IFTYPE_STATION: fc |= cpu_to_le16(IEEE80211_FCTL_TODS); /* BSSID SA DA */ - sdata_lock(sdata); if (!sdata->u.mgd.associated) { - sdata_unlock(sdata); dev_kfree_skb(skb); return -ENOTCONN; } memcpy(hdr->addr1, sdata->deflink.u.mgd.bssid, ETH_ALEN); memcpy(hdr->addr2, sdata->vif.addr, ETH_ALEN); memcpy(hdr->addr3, addr, ETH_ALEN); - sdata_unlock(sdata); break; default: dev_kfree_skb(skb); @@ -880,18 +932,20 @@ } } -void ieee80211_debugfs_add_netdev(struct ieee80211_sub_if_data *sdata) +void ieee80211_debugfs_add_netdev(struct ieee80211_sub_if_data *sdata, + bool mld_vif) { char buf[10+IFNAMSIZ]; sprintf(buf, "netdev:%s", sdata->name); sdata->vif.debugfs_dir = debugfs_create_dir(buf, sdata->local->hw.wiphy->debugfsdir); + /* deflink also has this */ + sdata->deflink.debugfs_dir = sdata->vif.debugfs_dir; sdata->debugfs.subdir_stations = debugfs_create_dir("stations", sdata->vif.debugfs_dir); add_files(sdata); - - if (!(sdata->local->hw.wiphy->flags & WIPHY_FLAG_SUPPORTS_MLO)) + if (!mld_vif) add_link_files(&sdata->deflink, sdata->vif.debugfs_dir); } @@ -919,11 +973,21 @@ debugfs_rename(dir->d_parent, dir, dir->d_parent, buf); } +void ieee80211_debugfs_recreate_netdev(struct ieee80211_sub_if_data *sdata, + bool mld_vif) +{ + ieee80211_debugfs_remove_netdev(sdata); + ieee80211_debugfs_add_netdev(sdata, mld_vif); + drv_vif_add_debugfs(sdata->local, sdata); + if (!mld_vif) + ieee80211_link_debugfs_drv_add(&sdata->deflink); +} + void ieee80211_link_debugfs_add(struct ieee80211_link_data *link) { char link_dir_name[10]; - if (WARN_ON(!link->sdata->vif.debugfs_dir)) + if (WARN_ON(!link->sdata->vif.debugfs_dir || link->debugfs_dir)) return; /* For now, this should not be called for non-MLO capable drivers */ @@ -960,7 +1024,8 @@ void ieee80211_link_debugfs_drv_add(struct ieee80211_link_data *link) { - if (WARN_ON(!link->debugfs_dir)) + if (link->sdata->vif.type == NL80211_IFTYPE_MONITOR || + WARN_ON(!link->debugfs_dir)) return; drv_link_add_debugfs(link->sdata->local, link->sdata, diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/debugfs_netdev.h backport-iwlwifi-dkms-11510/net/mac80211/debugfs_netdev.h --- backport-iwlwifi-dkms-11289/net/mac80211/debugfs_netdev.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/debugfs_netdev.h 2023-10-04 04:18:43.000000000 +0800 @@ -1,4 +1,8 @@ /* SPDX-License-Identifier: GPL-2.0 */ +/* + * Portions: + * Copyright (C) 2023 Intel Corporation + */ /* routines exported for debugfs handling */ #ifndef __IEEE80211_DEBUGFS_NETDEV_H @@ -7,9 +11,12 @@ #include "ieee80211_i.h" #ifdef CPTCFG_MAC80211_DEBUGFS -void ieee80211_debugfs_add_netdev(struct ieee80211_sub_if_data *sdata); +void ieee80211_debugfs_add_netdev(struct ieee80211_sub_if_data *sdata, + bool mld_vif); void ieee80211_debugfs_remove_netdev(struct ieee80211_sub_if_data *sdata); void ieee80211_debugfs_rename_netdev(struct ieee80211_sub_if_data *sdata); +void ieee80211_debugfs_recreate_netdev(struct ieee80211_sub_if_data *sdata, + bool mld_vif); void ieee80211_link_debugfs_add(struct ieee80211_link_data *link); void ieee80211_link_debugfs_remove(struct ieee80211_link_data *link); @@ -18,7 +25,7 @@ void ieee80211_link_debugfs_drv_remove(struct ieee80211_link_data *link); #else static inline void ieee80211_debugfs_add_netdev( - struct ieee80211_sub_if_data *sdata) + struct ieee80211_sub_if_data *sdata, bool mld_vif) {} static inline void ieee80211_debugfs_remove_netdev( struct ieee80211_sub_if_data *sdata) @@ -26,7 +33,9 @@ static inline void ieee80211_debugfs_rename_netdev( struct ieee80211_sub_if_data *sdata) {} - +static inline void ieee80211_debugfs_recreate_netdev( + struct ieee80211_sub_if_data *sdata, bool mld_vif) +{} static inline void ieee80211_link_debugfs_add(struct ieee80211_link_data *link) {} static inline void ieee80211_link_debugfs_remove(struct ieee80211_link_data *link) diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/debugfs_sta.c backport-iwlwifi-dkms-11510/net/mac80211/debugfs_sta.c --- backport-iwlwifi-dkms-11289/net/mac80211/debugfs_sta.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/debugfs_sta.c 2023-10-04 04:18:43.000000000 +0800 @@ -5,7 +5,7 @@ * Copyright 2007 Johannes Berg * Copyright 2013-2014 Intel Mobile Communications GmbH * Copyright(c) 2016 Intel Deutschland GmbH - * Copyright (C) 2018 - 2022 Intel Corporation + * Copyright (C) 2018 - 2023 Intel Corporation */ #include @@ -420,6 +420,7 @@ if (ret || tid >= IEEE80211_NUM_TIDS) return -EINVAL; + wiphy_lock(sta->local->hw.wiphy); if (tx) { if (start) ret = ieee80211_start_tx_ba_session(&sta->sta, tid, @@ -431,6 +432,7 @@ 3, true); ret = 0; } + wiphy_unlock(sta->local->hw.wiphy); return ret ?: count; } @@ -1035,6 +1037,190 @@ } LINK_STA_OPS(he_capa); +static ssize_t link_sta_eht_capa_read(struct file *file, char __user *userbuf, + size_t count, loff_t *ppos) +{ + char *buf, *p; + size_t buf_sz = PAGE_SIZE; + struct link_sta_info *link_sta = file->private_data; + struct ieee80211_sta_eht_cap *bec = &link_sta->pub->eht_cap; + struct ieee80211_eht_cap_elem_fixed *fixed = &bec->eht_cap_elem; + struct ieee80211_eht_mcs_nss_supp *nss = &bec->eht_mcs_nss_supp; + u8 *cap; + int i; + ssize_t ret; + static const char *mcs_desc[] = { "0-7", "8-9", "10-11", "12-13"}; + + buf = kmalloc(buf_sz, GFP_KERNEL); + if (!buf) + return -ENOMEM; + p = buf; + + p += scnprintf(p, buf_sz + buf - p, "EHT %ssupported\n", + bec->has_eht ? "" : "not "); + if (!bec->has_eht) + goto out; + + p += scnprintf(p, buf_sz + buf - p, + "MAC-CAP: %#.2x %#.2x\n", + fixed->mac_cap_info[0], fixed->mac_cap_info[1]); + p += scnprintf(p, buf_sz + buf - p, + "PHY-CAP: %#.2x %#.2x %#.2x %#.2x %#.2x %#.2x %#.2x %#.2x %#.2x\n", + fixed->phy_cap_info[0], fixed->phy_cap_info[1], + fixed->phy_cap_info[2], fixed->phy_cap_info[3], + fixed->phy_cap_info[4], fixed->phy_cap_info[5], + fixed->phy_cap_info[6], fixed->phy_cap_info[7], + fixed->phy_cap_info[8]); + +#define PRINT(fmt, ...) \ + p += scnprintf(p, buf_sz + buf - p, "\t\t" fmt "\n", \ + ##__VA_ARGS__) + +#define PFLAG(t, n, a, b) \ + do { \ + if (cap[n] & IEEE80211_EHT_##t##_CAP##n##_##a) \ + PRINT("%s", b); \ + } while (0) + + cap = fixed->mac_cap_info; + PFLAG(MAC, 0, EPCS_PRIO_ACCESS, "EPCS-PRIO-ACCESS"); + PFLAG(MAC, 0, OM_CONTROL, "OM-CONTROL"); + PFLAG(MAC, 0, TRIG_TXOP_SHARING_MODE1, "TRIG-TXOP-SHARING-MODE1"); + PFLAG(MAC, 0, TRIG_TXOP_SHARING_MODE2, "TRIG-TXOP-SHARING-MODE2"); + PFLAG(MAC, 0, RESTRICTED_TWT, "RESTRICTED-TWT"); + PFLAG(MAC, 0, SCS_TRAFFIC_DESC, "SCS-TRAFFIC-DESC"); + switch ((cap[0] & 0xc0) >> 6) { + case IEEE80211_EHT_MAC_CAP0_MAX_MPDU_LEN_3895: + PRINT("MAX-MPDU-LEN: 3985"); + break; + case IEEE80211_EHT_MAC_CAP0_MAX_MPDU_LEN_7991: + PRINT("MAX-MPDU-LEN: 7991"); + break; + case IEEE80211_EHT_MAC_CAP0_MAX_MPDU_LEN_11454: + PRINT("MAX-MPDU-LEN: 11454"); + break; + } + + cap = fixed->phy_cap_info; + PFLAG(PHY, 0, 320MHZ_IN_6GHZ, "320MHZ-IN-6GHZ"); + PFLAG(PHY, 0, 242_TONE_RU_GT20MHZ, "242-TONE-RU-GT20MHZ"); + PFLAG(PHY, 0, NDP_4_EHT_LFT_32_GI, "NDP-4-EHT-LFT-32-GI"); + PFLAG(PHY, 0, PARTIAL_BW_UL_MU_MIMO, "PARTIAL-BW-UL-MU-MIMO"); + PFLAG(PHY, 0, SU_BEAMFORMER, "SU-BEAMFORMER"); + PFLAG(PHY, 0, SU_BEAMFORMEE, "SU-BEAMFORMEE"); + i = cap[0] >> 7; + i |= (cap[1] & 0x3) << 1; + PRINT("BEAMFORMEE-80-NSS: %i", i); + PRINT("BEAMFORMEE-160-NSS: %i", (cap[1] >> 2) & 0x7); + PRINT("BEAMFORMEE-320-NSS: %i", (cap[1] >> 5) & 0x7); + PRINT("SOUNDING-DIM-80-NSS: %i", (cap[2] & 0x7)); + PRINT("SOUNDING-DIM-160-NSS: %i", (cap[2] >> 3) & 0x7); + i = cap[2] >> 6; + i |= (cap[3] & 0x1) << 3; + PRINT("SOUNDING-DIM-320-NSS: %i", i); + + PFLAG(PHY, 3, NG_16_SU_FEEDBACK, "NG-16-SU-FEEDBACK"); + PFLAG(PHY, 3, NG_16_MU_FEEDBACK, "NG-16-MU-FEEDBACK"); + PFLAG(PHY, 3, CODEBOOK_4_2_SU_FDBK, "CODEBOOK-4-2-SU-FDBK"); + PFLAG(PHY, 3, CODEBOOK_7_5_MU_FDBK, "CODEBOOK-7-5-MU-FDBK"); + PFLAG(PHY, 3, TRIG_SU_BF_FDBK, "TRIG-SU-BF-FDBK"); + PFLAG(PHY, 3, TRIG_MU_BF_PART_BW_FDBK, "TRIG-MU-BF-PART-BW-FDBK"); + PFLAG(PHY, 3, TRIG_CQI_FDBK, "TRIG-CQI-FDBK"); + + PFLAG(PHY, 4, PART_BW_DL_MU_MIMO, "PART-BW-DL-MU-MIMO"); + PFLAG(PHY, 4, PSR_SR_SUPP, "PSR-SR-SUPP"); + PFLAG(PHY, 4, POWER_BOOST_FACT_SUPP, "POWER-BOOST-FACT-SUPP"); + PFLAG(PHY, 4, EHT_MU_PPDU_4_EHT_LTF_08_GI, "EHT-MU-PPDU-4-EHT-LTF-08-GI"); + PRINT("MAX_NC: %i", cap[4] >> 4); + + PFLAG(PHY, 5, NON_TRIG_CQI_FEEDBACK, "NON-TRIG-CQI-FEEDBACK"); + PFLAG(PHY, 5, TX_LESS_242_TONE_RU_SUPP, "TX-LESS-242-TONE-RU-SUPP"); + PFLAG(PHY, 5, RX_LESS_242_TONE_RU_SUPP, "RX-LESS-242-TONE-RU-SUPP"); + PFLAG(PHY, 5, PPE_THRESHOLD_PRESENT, "PPE_THRESHOLD_PRESENT"); + switch (cap[5] >> 4 & 0x3) { + case IEEE80211_EHT_PHY_CAP5_COMMON_NOMINAL_PKT_PAD_0US: + PRINT("NOMINAL_PKT_PAD: 0us"); + break; + case IEEE80211_EHT_PHY_CAP5_COMMON_NOMINAL_PKT_PAD_8US: + PRINT("NOMINAL_PKT_PAD: 8us"); + break; + case IEEE80211_EHT_PHY_CAP5_COMMON_NOMINAL_PKT_PAD_16US: + PRINT("NOMINAL_PKT_PAD: 16us"); + break; + case IEEE80211_EHT_PHY_CAP5_COMMON_NOMINAL_PKT_PAD_20US: + PRINT("NOMINAL_PKT_PAD: 20us"); + break; + } + i = cap[5] >> 6; + i |= cap[6] & 0x7; + PRINT("MAX-NUM-SUPP-EHT-LTF: %i", i); + PFLAG(PHY, 5, SUPP_EXTRA_EHT_LTF, "SUPP-EXTRA-EHT-LTF"); + + i = (cap[6] >> 3) & 0xf; + PRINT("MCS15-SUPP-MASK: %i", i); + PFLAG(PHY, 6, EHT_DUP_6GHZ_SUPP, "EHT-DUP-6GHZ-SUPP"); + + PFLAG(PHY, 7, 20MHZ_STA_RX_NDP_WIDER_BW, "20MHZ-STA-RX-NDP-WIDER-BW"); + PFLAG(PHY, 7, NON_OFDMA_UL_MU_MIMO_80MHZ, "NON-OFDMA-UL-MU-MIMO-80MHZ"); + PFLAG(PHY, 7, NON_OFDMA_UL_MU_MIMO_160MHZ, "NON-OFDMA-UL-MU-MIMO-160MHZ"); + PFLAG(PHY, 7, NON_OFDMA_UL_MU_MIMO_320MHZ, "NON-OFDMA-UL-MU-MIMO-320MHZ"); + PFLAG(PHY, 7, MU_BEAMFORMER_80MHZ, "MU-BEAMFORMER-80MHZ"); + PFLAG(PHY, 7, MU_BEAMFORMER_160MHZ, "MU-BEAMFORMER-160MHZ"); + PFLAG(PHY, 7, MU_BEAMFORMER_320MHZ, "MU-BEAMFORMER-320MHZ"); + PFLAG(PHY, 7, TB_SOUNDING_FDBK_RATE_LIMIT, "TB-SOUNDING-FDBK-RATE-LIMIT"); + + PFLAG(PHY, 8, RX_1024QAM_WIDER_BW_DL_OFDMA, "RX-1024QAM-WIDER-BW-DL-OFDMA"); + PFLAG(PHY, 8, RX_4096QAM_WIDER_BW_DL_OFDMA, "RX-4096QAM-WIDER-BW-DL-OFDMA"); + +#undef PFLAG + + PRINT(""); /* newline */ + if (!(link_sta->pub->he_cap.he_cap_elem.phy_cap_info[0] & + IEEE80211_HE_PHY_CAP0_CHANNEL_WIDTH_SET_MASK_ALL)) { + u8 *mcs_vals = (u8 *)(&nss->only_20mhz); + + for (i = 0; i < 4; i++) + PRINT("EHT bw=20 MHz, max NSS for MCS %s: Rx=%u, Tx=%u", + mcs_desc[i], + mcs_vals[i] & 0xf, mcs_vals[i] >> 4); + } else { + u8 *mcs_vals = (u8 *)(&nss->bw._80); + + for (i = 0; i < 3; i++) + PRINT("EHT bw <= 80 MHz, max NSS for MCS %s: Rx=%u, Tx=%u", + mcs_desc[i + 1], + mcs_vals[i] & 0xf, mcs_vals[i] >> 4); + + mcs_vals = (u8 *)(&nss->bw._160); + for (i = 0; i < 3; i++) + PRINT("EHT bw <= 160 MHz, max NSS for MCS %s: Rx=%u, Tx=%u", + mcs_desc[i + 1], + mcs_vals[i] & 0xf, mcs_vals[i] >> 4); + + mcs_vals = (u8 *)(&nss->bw._320); + for (i = 0; i < 3; i++) + PRINT("EHT bw <= 320 MHz, max NSS for MCS %s: Rx=%u, Tx=%u", + mcs_desc[i + 1], + mcs_vals[i] & 0xf, mcs_vals[i] >> 4); + } + + if (cap[5] & IEEE80211_EHT_PHY_CAP5_PPE_THRESHOLD_PRESENT) { + u8 ppe_size = ieee80211_eht_ppe_size(bec->eht_ppe_thres[0], cap); + + p += scnprintf(p, buf_sz + buf - p, "EHT PPE Thresholds: "); + for (i = 0; i < ppe_size; i++) + p += scnprintf(p, buf_sz + buf - p, "0x%02x ", + bec->eht_ppe_thres[i]); + PRINT(""); /* newline */ + } + +out: + ret = simple_read_from_buffer(userbuf, count, ppos, buf, p - buf); + kfree(buf); + return ret; +} +LINK_STA_OPS(eht_capa); + #define DEBUGFS_ADD(name) \ debugfs_create_file(#name, 0400, \ sta->debugfs_dir, sta, &sta_ ##name## _ops) @@ -1128,6 +1314,7 @@ DEBUGFS_ADD(ht_capa); DEBUGFS_ADD(vht_capa); DEBUGFS_ADD(he_capa); + DEBUGFS_ADD(eht_capa); DEBUGFS_ADD_COUNTER(rx_duplicates, rx_stats.num_duplicates); DEBUGFS_ADD_COUNTER(rx_fragments, rx_stats.fragments); diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/driver-ops.c backport-iwlwifi-dkms-11510/net/mac80211/driver-ops.c --- backport-iwlwifi-dkms-11289/net/mac80211/driver-ops.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/driver-ops.c 2023-10-04 04:18:43.000000000 +0800 @@ -15,6 +15,7 @@ int ret; might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); if (WARN_ON(local->started)) return -EALREADY; @@ -35,6 +36,7 @@ void drv_stop(struct ieee80211_local *local) { might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); if (WARN_ON(!local->started)) return; @@ -58,6 +60,7 @@ int ret; might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); if (WARN_ON(sdata->vif.type == NL80211_IFTYPE_AP_VLAN || (sdata->vif.type == NL80211_IFTYPE_MONITOR && @@ -69,10 +72,18 @@ ret = local->ops->add_interface(&local->hw, &sdata->vif); trace_drv_return_int(local, ret); - if (ret == 0) - sdata->flags |= IEEE80211_SDATA_IN_DRIVER; + if (ret) + return ret; - return ret; + sdata->flags |= IEEE80211_SDATA_IN_DRIVER; + + if (!local->in_reconfig) { + drv_vif_add_debugfs(local, sdata); + /* initially vif is not MLD */ + ieee80211_link_debugfs_drv_add(&sdata->deflink); + } + + return 0; } int drv_change_interface(struct ieee80211_local *local, @@ -82,6 +93,7 @@ int ret; might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); if (!check_sdata_in_driver(sdata)) return -EIO; @@ -96,6 +108,7 @@ struct ieee80211_sub_if_data *sdata) { might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); if (!check_sdata_in_driver(sdata)) return; @@ -116,6 +129,7 @@ int ret = 0; might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); sdata = get_bss_sdata(sdata); if (!check_sdata_in_driver(sdata)) @@ -149,6 +163,7 @@ int ret = -EOPNOTSUPP; might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); sdata = get_bss_sdata(sdata); if (!check_sdata_in_driver(sdata)) @@ -190,6 +205,7 @@ int ret = -EOPNOTSUPP; might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); if (!check_sdata_in_driver(sdata)) return -EIO; @@ -223,6 +239,7 @@ u64 ret = -1ULL; might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); if (!check_sdata_in_driver(sdata)) return ret; @@ -239,6 +256,7 @@ u64 tsf) { might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); if (!check_sdata_in_driver(sdata)) return; @@ -254,6 +272,7 @@ s64 offset) { might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); if (!check_sdata_in_driver(sdata)) return; @@ -268,6 +287,7 @@ struct ieee80211_sub_if_data *sdata) { might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); if (!check_sdata_in_driver(sdata)) return; @@ -285,7 +305,9 @@ { int ret = 0; - drv_verify_link_exists(sdata, link_conf); + might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); + if (!check_sdata_in_driver(sdata)) return -EIO; @@ -312,8 +334,8 @@ struct ieee80211_chanctx *ctx) { might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); - drv_verify_link_exists(sdata, link_conf); if (!check_sdata_in_driver(sdata)) return; @@ -340,6 +362,7 @@ int i; might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); if (!local->ops->switch_vif_chanctx) return -EOPNOTSUPP; @@ -392,6 +415,7 @@ int ret = -EOPNOTSUPP; might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); if (!sdata) return -EIO; @@ -416,6 +440,7 @@ int link_id, u64 changed) { might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); if (WARN_ON_ONCE(changed & (BSS_CHANGED_BEACON | BSS_CHANGED_BEACON_ENABLED) && @@ -458,6 +483,7 @@ int ret; might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); sdata = get_bss_sdata(sdata); if (!check_sdata_in_driver(sdata)) @@ -485,6 +511,7 @@ int ret = -EOPNOTSUPP; might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); if (!check_sdata_in_driver(sdata)) return -EIO; @@ -510,10 +537,13 @@ if (ret) return ret; - for_each_set_bit(link_id, &links_to_add, IEEE80211_MLD_MAX_NUM_LINKS) { - link = rcu_access_pointer(sdata->link[link_id]); + if (!local->in_reconfig) { + for_each_set_bit(link_id, &links_to_add, + IEEE80211_MLD_MAX_NUM_LINKS) { + link = rcu_access_pointer(sdata->link[link_id]); - ieee80211_link_debugfs_drv_add(link); + ieee80211_link_debugfs_drv_add(link); + } } return 0; @@ -532,6 +562,7 @@ int ret = -EOPNOTSUPP; might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); if (!check_sdata_in_driver(sdata)) return -EIO; @@ -547,7 +578,7 @@ for_each_set_bit(link_id, &links_to_rem, IEEE80211_MLD_MAX_NUM_LINKS) { link_sta = rcu_dereference_protected(info->link[link_id], - lockdep_is_held(&local->sta_mtx)); + lockdep_is_held(&local->hw.wiphy->mtx)); ieee80211_link_sta_debugfs_drv_remove(link_sta); } @@ -567,7 +598,7 @@ for_each_set_bit(link_id, &links_to_add, IEEE80211_MLD_MAX_NUM_LINKS) { link_sta = rcu_dereference_protected(info->link[link_id], - lockdep_is_held(&local->sta_mtx)); + lockdep_is_held(&local->hw.wiphy->mtx)); ieee80211_link_sta_debugfs_drv_add(link_sta); } diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/driver-ops.h backport-iwlwifi-dkms-11510/net/mac80211/driver-ops.h --- backport-iwlwifi-dkms-11289/net/mac80211/driver-ops.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/driver-ops.h 2023-10-04 04:18:43.000000000 +0800 @@ -40,6 +40,9 @@ static inline void drv_sync_rx_queues(struct ieee80211_local *local, struct sta_info *sta) { + might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); + if (local->ops->sync_rx_queues) { trace_drv_sync_rx_queues(local, sta->sdata, &sta->sta); local->ops->sync_rx_queues(&local->hw); @@ -94,6 +97,7 @@ int ret; might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); trace_drv_suspend(local); ret = local->ops->suspend(&local->hw, wowlan); @@ -106,6 +110,7 @@ int ret; might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); trace_drv_resume(local); ret = local->ops->resume(&local->hw); @@ -117,6 +122,7 @@ bool enabled) { might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); if (!local->ops->set_wakeup) return; @@ -142,6 +148,7 @@ int ret; might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); trace_drv_config(local, changed); ret = local->ops->config(&local->hw, changed); @@ -154,6 +161,7 @@ u64 changed) { might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); if (!check_sdata_in_driver(sdata)) return; @@ -193,6 +201,7 @@ u64 multicast) { might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); trace_drv_configure_filter(local, changed_flags, total_flags, multicast); @@ -207,6 +216,7 @@ unsigned int changed_flags) { might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); trace_drv_config_iface_filter(local, sdata, filter_flags, changed_flags); @@ -263,6 +273,7 @@ int ret; might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); if (!check_sdata_in_driver(sdata)) return -EIO; @@ -277,6 +288,7 @@ struct ieee80211_sub_if_data *sdata) { might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); if (!check_sdata_in_driver(sdata)) return; @@ -295,6 +307,7 @@ int ret; might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); if (!check_sdata_in_driver(sdata)) return -EIO; @@ -312,6 +325,7 @@ int ret; might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); if (!check_sdata_in_driver(sdata)) return -EIO; @@ -328,6 +342,7 @@ const u8 *mac_addr) { might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); trace_drv_sw_scan_start(local, sdata, mac_addr); if (local->ops->sw_scan_start) @@ -339,6 +354,7 @@ struct ieee80211_sub_if_data *sdata) { might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); trace_drv_sw_scan_complete(local, sdata); if (local->ops->sw_scan_complete) @@ -352,6 +368,7 @@ int ret = -EOPNOTSUPP; might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); if (local->ops->get_stats) ret = local->ops->get_stats(&local->hw, stats); @@ -375,6 +392,7 @@ int ret = 0; might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); trace_drv_set_frag_threshold(local, value); if (local->ops->set_frag_threshold) @@ -389,6 +407,7 @@ int ret = 0; might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); trace_drv_set_rts_threshold(local, value); if (local->ops->set_rts_threshold) @@ -402,6 +421,7 @@ { int ret = 0; might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); trace_drv_set_coverage_class(local, value); if (local->ops->set_coverage_class) @@ -435,6 +455,7 @@ int ret = 0; might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); sdata = get_bss_sdata(sdata); if (!check_sdata_in_driver(sdata)) @@ -454,6 +475,7 @@ struct ieee80211_sta *sta) { might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); sdata = get_bss_sdata(sdata); if (!check_sdata_in_driver(sdata)) @@ -467,12 +489,30 @@ } #ifdef CPTCFG_MAC80211_DEBUGFS +static inline void drv_vif_add_debugfs(struct ieee80211_local *local, + struct ieee80211_sub_if_data *sdata) +{ + might_sleep(); + + if (sdata->vif.type == NL80211_IFTYPE_MONITOR || + WARN_ON(!sdata->vif.debugfs_dir)) + return; + + sdata = get_bss_sdata(sdata); + if (!check_sdata_in_driver(sdata)) + return; + + if (local->ops->vif_add_debugfs) + local->ops->vif_add_debugfs(&local->hw, &sdata->vif); +} + static inline void drv_link_add_debugfs(struct ieee80211_local *local, struct ieee80211_sub_if_data *sdata, struct ieee80211_bss_conf *link_conf, struct dentry *dir) { might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); sdata = get_bss_sdata(sdata); if (!check_sdata_in_driver(sdata)) @@ -489,6 +529,7 @@ struct dentry *dir) { might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); sdata = get_bss_sdata(sdata); if (!check_sdata_in_driver(sdata)) @@ -505,6 +546,7 @@ struct dentry *dir) { might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); sdata = get_bss_sdata(sdata); if (!check_sdata_in_driver(sdata)) @@ -514,6 +556,12 @@ local->ops->link_sta_add_debugfs(&local->hw, &sdata->vif, link_sta, dir); } +#else +static inline void drv_vif_add_debugfs(struct ieee80211_local *local, + struct ieee80211_sub_if_data *sdata) +{ + might_sleep(); +} #endif static inline void drv_sta_pre_rcu_remove(struct ieee80211_local *local, @@ -521,6 +569,7 @@ struct sta_info *sta) { might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); sdata = get_bss_sdata(sdata); if (!check_sdata_in_driver(sdata)) @@ -569,6 +618,9 @@ struct ieee80211_sta *sta, struct station_info *sinfo) { + might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); + sdata = get_bss_sdata(sdata); if (!check_sdata_in_driver(sdata)) return; @@ -599,6 +651,7 @@ int ret = 0; /* default unsupported op for less congestion */ might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); trace_drv_tx_last_beacon(local); if (local->ops->tx_last_beacon) @@ -616,6 +669,9 @@ { int ret = -EOPNOTSUPP; + might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); + trace_drv_get_survey(local, idx, survey); if (local->ops->get_survey) @@ -629,6 +685,7 @@ static inline void drv_rfkill_poll(struct ieee80211_local *local) { might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); if (local->ops->rfkill_poll) local->ops->rfkill_poll(&local->hw); @@ -641,6 +698,7 @@ struct ieee80211_vif *vif = sdata ? &sdata->vif : NULL; might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); if (sdata && !check_sdata_in_driver(sdata)) return; @@ -656,6 +714,7 @@ struct sta_info *sta) { might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); if (sdata && !check_sdata_in_driver(sdata)) return; @@ -671,6 +730,7 @@ struct ieee80211_channel_switch *ch_switch) { might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); trace_drv_channel_switch(local, sdata, ch_switch); local->ops->channel_switch(&local->hw, &sdata->vif, ch_switch); @@ -683,6 +743,7 @@ { int ret = -EOPNOTSUPP; might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); if (local->ops->set_antenna) ret = local->ops->set_antenna(&local->hw, tx_ant, rx_ant); trace_drv_set_antenna(local, tx_ant, rx_ant, ret); @@ -694,6 +755,7 @@ { int ret = -EOPNOTSUPP; might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); if (local->ops->get_antenna) ret = local->ops->get_antenna(&local->hw, tx_ant, rx_ant); trace_drv_get_antenna(local, *tx_ant, *rx_ant, ret); @@ -709,6 +771,7 @@ int ret; might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); trace_drv_remain_on_channel(local, sdata, chan, duration, type); ret = local->ops->remain_on_channel(&local->hw, &sdata->vif, @@ -725,6 +788,7 @@ int ret; might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); trace_drv_cancel_remain_on_channel(local, sdata); ret = local->ops->cancel_remain_on_channel(&local->hw, &sdata->vif); @@ -739,6 +803,7 @@ int ret = -ENOTSUPP; might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); trace_drv_set_ringparam(local, tx, rx); if (local->ops->set_ringparam) @@ -752,6 +817,7 @@ u32 *tx, u32 *tx_max, u32 *rx, u32 *rx_max) { might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); trace_drv_get_ringparam(local, tx, tx_max, rx, rx_max); if (local->ops->get_ringparam) @@ -764,6 +830,7 @@ bool ret = false; might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); trace_drv_tx_frames_pending(local); if (local->ops->tx_frames_pending) @@ -780,6 +847,7 @@ int ret = -EOPNOTSUPP; might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); if (!check_sdata_in_driver(sdata)) return -EIO; @@ -797,6 +865,9 @@ struct ieee80211_sub_if_data *sdata, struct cfg80211_gtk_rekey_data *data) { + might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); + if (!check_sdata_in_driver(sdata)) return; @@ -851,11 +922,13 @@ struct ieee80211_prep_tx_info *info) { might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); if (!check_sdata_in_driver(sdata)) return; WARN_ON_ONCE(sdata->vif.type != NL80211_IFTYPE_STATION); + info->link_id = info->link_id < 0 ? 0 : info->link_id; trace_drv_mgd_prepare_tx(local, sdata, info->duration, info->subtype, info->success); if (local->ops->mgd_prepare_tx) @@ -868,6 +941,7 @@ struct ieee80211_prep_tx_info *info) { might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); if (!check_sdata_in_driver(sdata)) return; @@ -882,17 +956,22 @@ static inline void drv_mgd_protect_tdls_discover(struct ieee80211_local *local, - struct ieee80211_sub_if_data *sdata) + struct ieee80211_sub_if_data *sdata, + int link_id) { might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); if (!check_sdata_in_driver(sdata)) return; WARN_ON_ONCE(sdata->vif.type != NL80211_IFTYPE_STATION); + link_id = link_id > 0 ? link_id : 0; + trace_drv_mgd_protect_tdls_discover(local, sdata); if (local->ops->mgd_protect_tdls_discover) - local->ops->mgd_protect_tdls_discover(&local->hw, &sdata->vif); + local->ops->mgd_protect_tdls_discover(&local->hw, &sdata->vif, + link_id); trace_drv_return_void(local); } @@ -902,6 +981,7 @@ int ret = -EOPNOTSUPP; might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); trace_drv_add_chanctx(local, ctx); if (local->ops->add_chanctx) @@ -917,6 +997,7 @@ struct ieee80211_chanctx *ctx) { might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); if (WARN_ON(!ctx->driver_present)) return; @@ -933,6 +1014,7 @@ u32 changed) { might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); trace_drv_change_chanctx(local, ctx, changed); if (local->ops->change_chanctx) { @@ -942,14 +1024,6 @@ trace_drv_return_void(local); } -static inline void drv_verify_link_exists(struct ieee80211_sub_if_data *sdata, - struct ieee80211_bss_conf *link_conf) -{ - /* deflink always exists, so need to check only for other links */ - if (sdata->deflink.conf != link_conf) - sdata_assert_lock(sdata); -} - int drv_assign_vif_chanctx(struct ieee80211_local *local, struct ieee80211_sub_if_data *sdata, struct ieee80211_bss_conf *link_conf, @@ -968,10 +1042,8 @@ { int ret = 0; - /* make sure link_conf is protected */ - drv_verify_link_exists(sdata, link_conf); - might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); if (!check_sdata_in_driver(sdata)) return -EIO; @@ -987,8 +1059,8 @@ struct ieee80211_sub_if_data *sdata, struct ieee80211_bss_conf *link_conf) { - /* make sure link_conf is protected */ - drv_verify_link_exists(sdata, link_conf); + might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); if (!check_sdata_in_driver(sdata)) return; @@ -1004,6 +1076,7 @@ enum ieee80211_reconfig_type reconfig_type) { might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); trace_drv_reconfig_complete(local, reconfig_type); if (local->ops->reconfig_complete) @@ -1016,6 +1089,9 @@ struct ieee80211_sub_if_data *sdata, int key_idx) { + might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); + if (!check_sdata_in_driver(sdata)) return; @@ -1046,6 +1122,9 @@ { struct ieee80211_local *local = sdata->local; + might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); + if (local->ops->channel_switch_beacon) { trace_drv_channel_switch_beacon(local, sdata, chandef); local->ops->channel_switch_beacon(&local->hw, &sdata->vif, @@ -1060,6 +1139,9 @@ struct ieee80211_local *local = sdata->local; int ret = 0; + might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); + if (!check_sdata_in_driver(sdata)) return -EIO; @@ -1078,6 +1160,9 @@ struct ieee80211_local *local = sdata->local; int ret = 0; + might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); + if (!check_sdata_in_driver(sdata)) return -EIO; @@ -1094,6 +1179,9 @@ { struct ieee80211_local *local = sdata->local; + might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); + if (!check_sdata_in_driver(sdata)) return; @@ -1109,6 +1197,9 @@ { struct ieee80211_local *local = sdata->local; + might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); + if (!check_sdata_in_driver(sdata)) return; @@ -1124,6 +1215,7 @@ int ret = 0; might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); if (!check_sdata_in_driver(sdata)) return -EIO; @@ -1138,6 +1230,7 @@ struct ieee80211_sub_if_data *sdata) { might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); if (!check_sdata_in_driver(sdata)) return; @@ -1165,6 +1258,9 @@ { int ret; + might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); + if (!local->ops->get_txpower) return -EOPNOTSUPP; @@ -1184,6 +1280,7 @@ int ret; might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); if (!check_sdata_in_driver(sdata)) return -EIO; @@ -1204,6 +1301,7 @@ struct ieee80211_sta *sta) { might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); if (!check_sdata_in_driver(sdata)) return; @@ -1269,6 +1367,11 @@ { u32 ret = -EOPNOTSUPP; + might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); + if (!check_sdata_in_driver(sdata)) + return -EIO; + if (local->ops->get_ftm_responder_stats) ret = local->ops->get_ftm_responder_stats(&local->hw, &sdata->vif, @@ -1285,6 +1388,7 @@ int ret = -EOPNOTSUPP; might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); if (!check_sdata_in_driver(sdata)) return -EIO; @@ -1304,6 +1408,7 @@ trace_drv_abort_pmsr(local, sdata); might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); if (!check_sdata_in_driver(sdata)) return; @@ -1319,6 +1424,7 @@ int ret; might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); check_sdata_in_driver(sdata); trace_drv_start_nan(local, sdata, conf); @@ -1331,6 +1437,7 @@ struct ieee80211_sub_if_data *sdata) { might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); check_sdata_in_driver(sdata); trace_drv_stop_nan(local, sdata); @@ -1346,6 +1453,7 @@ int ret; might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); check_sdata_in_driver(sdata); if (!local->ops->nan_change_conf) @@ -1366,6 +1474,7 @@ int ret; might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); check_sdata_in_driver(sdata); if (!local->ops->add_nan_func) @@ -1383,6 +1492,7 @@ u8 instance_id) { might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); check_sdata_in_driver(sdata); trace_drv_del_nan_func(local, sdata, instance_id); @@ -1399,6 +1509,7 @@ int ret; might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); ret = local->ops->set_tid_config(&local->hw, &sdata->vif, sta, tid_conf); trace_drv_return_int(local, ret); @@ -1413,6 +1524,7 @@ int ret; might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); ret = local->ops->reset_tid_config(&local->hw, &sdata->vif, sta, tids); trace_drv_return_int(local, ret); @@ -1423,6 +1535,7 @@ struct ieee80211_sub_if_data *sdata) { might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); check_sdata_in_driver(sdata); if (!local->ops->update_vif_offload) @@ -1438,6 +1551,9 @@ struct ieee80211_sta *sta, bool enabled) { sdata = get_bss_sdata(sdata); + + might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); if (!check_sdata_in_driver(sdata)) return; @@ -1453,6 +1569,9 @@ bool enabled) { sdata = get_bss_sdata(sdata); + + might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); if (!check_sdata_in_driver(sdata)) return; @@ -1471,6 +1590,7 @@ struct ieee80211_twt_params *twt_agrt; might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); if (!check_sdata_in_driver(sdata)) return; @@ -1488,6 +1608,7 @@ u8 flowid) { might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); if (!check_sdata_in_driver(sdata)) return; @@ -1528,6 +1649,8 @@ { int ret = -EOPNOTSUPP; + might_sleep(); + sdata = get_bss_sdata(sdata); trace_drv_net_setup_tc(local, sdata, type); if (local->ops->net_setup_tc) diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/drop.h backport-iwlwifi-dkms-11510/net/mac80211/drop.h --- backport-iwlwifi-dkms-11289/net/mac80211/drop.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/drop.h 2023-10-04 04:18:43.000000000 +0800 @@ -18,9 +18,54 @@ /* this line for the trailing \ - add before this */ #define MAC80211_DROP_REASONS_UNUSABLE(R) \ + /* 0x00 == ___RX_DROP_UNUSABLE */ \ R(RX_DROP_U_MIC_FAIL) \ R(RX_DROP_U_REPLAY) \ R(RX_DROP_U_BAD_MMIE) \ + R(RX_DROP_U_DUP) \ + R(RX_DROP_U_SPURIOUS) \ + R(RX_DROP_U_DECRYPT_FAIL) \ + R(RX_DROP_U_NO_KEY_ID) \ + R(RX_DROP_U_BAD_CIPHER) \ + R(RX_DROP_U_OOM) \ + R(RX_DROP_U_NONSEQ_PN) \ + R(RX_DROP_U_BAD_KEY_COLOR) \ + R(RX_DROP_U_BAD_4ADDR) \ + R(RX_DROP_U_BAD_AMSDU) \ + R(RX_DROP_U_BAD_AMSDU_CIPHER) \ + R(RX_DROP_U_INVALID_8023) \ + /* 0x10 */ \ + R(RX_DROP_U_RUNT_ACTION) \ + R(RX_DROP_U_UNPROT_ACTION) \ + R(RX_DROP_U_UNPROT_DUAL) \ + R(RX_DROP_U_UNPROT_UCAST_MGMT) \ + R(RX_DROP_U_UNPROT_MCAST_MGMT) \ + R(RX_DROP_U_UNPROT_BEACON) \ + R(RX_DROP_U_UNPROT_UNICAST_PUB_ACTION) \ + R(RX_DROP_U_UNPROT_ROBUST_ACTION) \ + R(RX_DROP_U_ACTION_UNKNOWN_SRC) \ + R(RX_DROP_U_REJECTED_ACTION_RESPONSE) \ + R(RX_DROP_U_EXPECT_DEFRAG_PROT) \ + R(RX_DROP_U_WEP_DEC_FAIL) \ + R(RX_DROP_U_NO_IV) \ + R(RX_DROP_U_NO_ICV) \ + R(RX_DROP_U_AP_RX_GROUPCAST) \ + R(RX_DROP_U_SHORT_MMIC) \ + /* 0x20 */ \ + R(RX_DROP_U_MMIC_FAIL) \ + R(RX_DROP_U_SHORT_TKIP) \ + R(RX_DROP_U_TKIP_FAIL) \ + R(RX_DROP_U_SHORT_CCMP) \ + R(RX_DROP_U_SHORT_CCMP_MIC) \ + R(RX_DROP_U_SHORT_GCMP) \ + R(RX_DROP_U_SHORT_GCMP_MIC) \ + R(RX_DROP_U_SHORT_CMAC) \ + R(RX_DROP_U_SHORT_CMAC256) \ + R(RX_DROP_U_SHORT_GMAC) \ + R(RX_DROP_U_UNEXPECTED_VLAN_4ADDR) \ + R(RX_DROP_U_UNEXPECTED_STA_4ADDR) \ + R(RX_DROP_U_UNEXPECTED_VLAN_MCAST) \ + R(RX_DROP_U_NOT_PORT_CONTROL) \ /* this line for the trailing \ - add before this */ /* having two enums allows for checking ieee80211_rx_result use with sparse */ @@ -46,11 +91,13 @@ RX_CONTINUE = (__force ieee80211_rx_result)___RX_CONTINUE, RX_QUEUED = (__force ieee80211_rx_result)___RX_QUEUED, RX_DROP_MONITOR = (__force ieee80211_rx_result)___RX_DROP_MONITOR, - RX_DROP_UNUSABLE = (__force ieee80211_rx_result)___RX_DROP_UNUSABLE, #define DEF(x) x = (__force ieee80211_rx_result)___ ## x, MAC80211_DROP_REASONS_MONITOR(DEF) MAC80211_DROP_REASONS_UNUSABLE(DEF) #undef DEF }; +#define RX_RES_IS_UNUSABLE(result) \ + (((__force u32)(result) & SKB_DROP_REASON_SUBSYS_MASK) == ___RX_DROP_UNUSABLE) + #endif /* MAC80211_DROP_H */ diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/ethtool.c backport-iwlwifi-dkms-11510/net/mac80211/ethtool.c --- backport-iwlwifi-dkms-11289/net/mac80211/ethtool.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/ethtool.c 2023-10-04 04:18:43.000000000 +0800 @@ -5,7 +5,7 @@ * Copied from cfg.c - originally * Copyright 2006-2010 Johannes Berg * Copyright 2014 Intel Corporation (Author: Johannes Berg) - * Copyright (C) 2018, 2022 Intel Corporation + * Copyright (C) 2018, 2022-2023 Intel Corporation */ #include #include @@ -110,7 +110,7 @@ * network device. */ - mutex_lock(&local->sta_mtx); + wiphy_lock(local->hw.wiphy); if (sdata->vif.type == NL80211_IFTYPE_STATION) { sta = sta_info_get_bss(sdata, sdata->deflink.u.mgd.bssid); @@ -206,12 +206,13 @@ else data[i++] = -1LL; - mutex_unlock(&local->sta_mtx); - - if (WARN_ON(i != STA_STATS_LEN)) + if (WARN_ON(i != STA_STATS_LEN)) { + wiphy_unlock(local->hw.wiphy); return; + } drv_get_et_stats(sdata, stats, &(data[STA_STATS_LEN])); + wiphy_unlock(local->hw.wiphy); } static void ieee80211_get_strings(struct net_device *dev, u32 sset, u8 *data) diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/ht.c backport-iwlwifi-dkms-11510/net/mac80211/ht.c --- backport-iwlwifi-dkms-11289/net/mac80211/ht.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/ht.c 2023-10-04 04:18:43.000000000 +0800 @@ -316,6 +316,8 @@ { int i; + lockdep_assert_wiphy(sta->local->hw.wiphy); + for (i = 0; i < IEEE80211_NUM_TIDS; i++) { __ieee80211_stop_rx_ba_session(sta, i, WLAN_BACK_RECIPIENT, WLAN_REASON_QSTA_LEAVE_QBSS, @@ -332,9 +334,8 @@ * the BA session, so handle it to properly clean tid_tx data. */ if(reason == AGG_STOP_DESTROY_STA) { - cancel_work_sync(&sta->ampdu_mlme.work); + wiphy_work_cancel(sta->local->hw.wiphy, &sta->ampdu_mlme.work); - mutex_lock(&sta->ampdu_mlme.mtx); for (i = 0; i < IEEE80211_NUM_TIDS; i++) { struct tid_ampdu_tx *tid_tx = rcu_dereference_protected_tid_tx(sta, i); @@ -345,11 +346,10 @@ if (test_and_clear_bit(HT_AGG_STATE_STOP_CB, &tid_tx->state)) ieee80211_stop_tx_ba_cb(sta, i, tid_tx); } - mutex_unlock(&sta->ampdu_mlme.mtx); } } -void ieee80211_ba_session_work(struct work_struct *work) +void ieee80211_ba_session_work(struct wiphy *wiphy, struct wiphy_work *work) { struct sta_info *sta = container_of(work, struct sta_info, ampdu_mlme.work); @@ -357,10 +357,11 @@ bool blocked; int tid; + lockdep_assert_wiphy(sta->local->hw.wiphy); + /* When this flag is set, new sessions should be blocked. */ blocked = test_sta_flag(sta, WLAN_STA_BLOCK_BA); - mutex_lock(&sta->ampdu_mlme.mtx); for (tid = 0; tid < IEEE80211_NUM_TIDS; tid++) { if (test_and_clear_bit(tid, sta->ampdu_mlme.tid_rx_timer_expired)) ___ieee80211_stop_rx_ba_session( @@ -413,9 +414,7 @@ */ synchronize_net(); - mutex_unlock(&sta->ampdu_mlme.mtx); - - ieee80211_queue_work(&sdata->local->hw, work); + wiphy_work_queue(sdata->local->hw.wiphy, work); return; } @@ -447,12 +446,11 @@ test_and_clear_bit(HT_AGG_STATE_START_CB, &tid_tx->state)) ieee80211_start_tx_ba_cb(sta, tid, tid_tx); if (test_and_clear_bit(HT_AGG_STATE_WANT_STOP, &tid_tx->state)) - ___ieee80211_stop_tx_ba_session(sta, tid, - AGG_STOP_LOCAL_REQUEST); + __ieee80211_stop_tx_ba_session(sta, tid, + AGG_STOP_LOCAL_REQUEST); if (test_and_clear_bit(HT_AGG_STATE_STOP_CB, &tid_tx->state)) ieee80211_stop_tx_ba_cb(sta, tid, tid_tx); } - mutex_unlock(&sta->ampdu_mlme.mtx); } void ieee80211_send_delba(struct ieee80211_sub_if_data *sdata, @@ -537,11 +535,13 @@ int ieee80211_send_smps_action(struct ieee80211_sub_if_data *sdata, enum ieee80211_smps_mode smps, const u8 *da, - const u8 *bssid) + const u8 *bssid, int link_id) { struct ieee80211_local *local = sdata->local; struct sk_buff *skb; struct ieee80211_mgmt *action_frame; + struct ieee80211_tx_info *info; + u8 status_link_id = link_id < 0 ? 0 : link_id; /* 27 = header + category + action + smps mode */ skb = dev_alloc_skb(27 + local->hw.extra_tx_headroom); @@ -561,6 +561,7 @@ case IEEE80211_SMPS_AUTOMATIC: case IEEE80211_SMPS_NUM_MODES: WARN_ON(1); + smps = IEEE80211_SMPS_OFF; fallthrough; case IEEE80211_SMPS_OFF: action_frame->u.action.u.ht_smps.smps_control = @@ -577,8 +578,13 @@ } /* we'll do more on status of this frame */ - IEEE80211_SKB_CB(skb)->flags |= IEEE80211_TX_CTL_REQ_TX_STATUS; - ieee80211_tx_skb(sdata, skb); + info = IEEE80211_SKB_CB(skb); + info->flags |= IEEE80211_TX_CTL_REQ_TX_STATUS; + /* we have 12 bits, and need 6: link_id 4, smps 2 */ + info->status_data = IEEE80211_STATUS_TYPE_SMPS | + u16_encode_bits(status_link_id << 2 | smps, + IEEE80211_STATUS_SUBDATA_MASK); + ieee80211_tx_skb_tid(sdata, skb, 7, link_id); return 0; } diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/ibss.c backport-iwlwifi-dkms-11510/net/mac80211/ibss.c --- backport-iwlwifi-dkms-11289/net/mac80211/ibss.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/ibss.c 2023-10-04 04:18:43.000000000 +0800 @@ -235,7 +235,7 @@ bool radar_required; int err; - sdata_assert_lock(sdata); + lockdep_assert_wiphy(local->hw.wiphy); /* Reset own TSF to allow time synchronization work. */ drv_reset_tsf(local, sdata); @@ -299,17 +299,14 @@ radar_required = err; - mutex_lock(&local->mtx); if (ieee80211_link_use_channel(&sdata->deflink, &chandef, ifibss->fixed_channel ? IEEE80211_CHANCTX_SHARED : IEEE80211_CHANCTX_EXCLUSIVE)) { sdata_info(sdata, "Failed to join IBSS, no channel context\n"); - mutex_unlock(&local->mtx); return; } sdata->deflink.radar_required = radar_required; - mutex_unlock(&local->mtx); memcpy(ifibss->bssid, bssid, ETH_ALEN); @@ -367,9 +364,7 @@ sdata->vif.cfg.ssid_len = 0; RCU_INIT_POINTER(ifibss->presp, NULL); kfree_rcu(presp, rcu_head); - mutex_lock(&local->mtx); ieee80211_link_release_channel(&sdata->deflink); - mutex_unlock(&local->mtx); sdata_info(sdata, "Failed to join IBSS, driver failure: %d\n", err); return; @@ -407,7 +402,7 @@ u32 rate_flags; int shift; - sdata_assert_lock(sdata); + lockdep_assert_wiphy(sdata->local->hw.wiphy); if (beacon_int < 10) beacon_int = 10; @@ -488,7 +483,7 @@ u16 capability = WLAN_CAPABILITY_IBSS; u64 tsf; - sdata_assert_lock(sdata); + lockdep_assert_wiphy(sdata->local->hw.wiphy); if (ifibss->privacy) capability |= WLAN_CAPABILITY_PRIVACY; @@ -530,7 +525,7 @@ struct ieee80211_if_ibss *ifibss = &sdata->u.ibss; struct cfg80211_bss *cbss; - sdata_assert_lock(sdata); + lockdep_assert_wiphy(sdata->local->hw.wiphy); /* When not connected/joined, sending CSA doesn't make sense. */ if (ifibss->state != IEEE80211_IBSS_MLME_JOINED) @@ -652,7 +647,7 @@ int active = 0; struct sta_info *sta; - sdata_assert_lock(sdata); + lockdep_assert_wiphy(sdata->local->hw.wiphy); rcu_read_lock(); @@ -678,6 +673,9 @@ struct ieee80211_local *local = sdata->local; struct cfg80211_bss *cbss; struct beacon_data *presp; + struct sta_info *sta; + + lockdep_assert_wiphy(local->hw.wiphy); if (!is_zero_ether_addr(ifibss->bssid)) { cbss = cfg80211_get_bss(local->hw.wiphy, ifibss->chandef.chan, @@ -696,6 +694,18 @@ sta_info_flush(sdata); + spin_lock_bh(&ifibss->incomplete_lock); + while (!list_empty(&ifibss->incomplete_stations)) { + sta = list_first_entry(&ifibss->incomplete_stations, + struct sta_info, list); + list_del(&sta->list); + spin_unlock_bh(&ifibss->incomplete_lock); + + sta_info_free(local, sta); + spin_lock_bh(&ifibss->incomplete_lock); + } + spin_unlock_bh(&ifibss->incomplete_lock); + netif_carrier_off(sdata->dev); sdata->vif.cfg.ibss_joined = false; @@ -713,9 +723,7 @@ ieee80211_bss_info_change_notify(sdata, BSS_CHANGED_BEACON_ENABLED | BSS_CHANGED_IBSS); drv_leave_ibss(local, sdata); - mutex_lock(&local->mtx); ieee80211_link_release_channel(&sdata->deflink); - mutex_unlock(&local->mtx); } static void ieee80211_csa_connection_drop_work(struct wiphy *wiphy, @@ -725,16 +733,12 @@ container_of(work, struct ieee80211_sub_if_data, u.ibss.csa_connection_drop_work); - sdata_lock(sdata); - ieee80211_ibss_disconnect(sdata); synchronize_rcu(); skb_queue_purge(&sdata->skb_queue); /* trigger a scan to find another IBSS network to join */ wiphy_work_queue(sdata->local->hw.wiphy, &sdata->work); - - sdata_unlock(sdata); } static void ieee80211_ibss_csa_mark_radar(struct ieee80211_sub_if_data *sdata) @@ -766,7 +770,7 @@ ieee80211_conn_flags_t conn_flags; u32 vht_cap_info = 0; - sdata_assert_lock(sdata); + lockdep_assert_wiphy(sdata->local->hw.wiphy); conn_flags = IEEE80211_CONN_DISABLE_VHT; @@ -938,7 +942,7 @@ { u16 auth_alg, auth_transaction; - sdata_assert_lock(sdata); + lockdep_assert_wiphy(sdata->local->hw.wiphy); if (len < 24 + 6) return; @@ -1188,8 +1192,22 @@ u32 supp_rates) { struct ieee80211_if_ibss *ifibss = &sdata->u.ibss; + struct ieee80211_local *local = sdata->local; + struct sta_info *sta; struct ieee80211_chanctx_conf *chanctx_conf; - struct sk_buff *skb; + struct ieee80211_supported_band *sband; + enum nl80211_bss_scan_width scan_width; + int band; + + /* + * XXX: Consider removing the least recently used entry and + * allow new one to be added. + */ + if (local->num_sta >= IEEE80211_IBSS_MAX_STA_ENTRIES) { + net_info_ratelimited("%s: No room for a new IBSS STA entry %pM\n", + sdata->name, addr); + return; + } if (ifibss->state == IEEE80211_IBSS_MLME_SEARCH) return; @@ -1203,14 +1221,23 @@ rcu_read_unlock(); return; } - - skb = ieee80211_build_probe_req(sdata, sdata->vif.addr, addr, bssid, - (u32)-1, chanctx_conf->def.chan, - ifibss->ssid, ifibss->ssid_len, NULL, 0, - IEEE80211_PROBE_FLAG_DIRECTED); - if (skb) - ieee80211_tx_skb(sdata, skb); + band = chanctx_conf->def.chan->band; + scan_width = cfg80211_chandef_to_scan_width(&chanctx_conf->def); rcu_read_unlock(); + + sta = sta_info_alloc(sdata, addr, GFP_ATOMIC); + if (!sta) + return; + + /* make sure mandatory rates are always added */ + sband = local->hw.wiphy->bands[band]; + sta->sta.deflink.supp_rates[band] = supp_rates | + ieee80211_mandatory_rates(sband, scan_width); + + spin_lock(&ifibss->incomplete_lock); + list_add(&sta->list, &ifibss->incomplete_stations); + spin_unlock(&ifibss->incomplete_lock); + wiphy_work_queue(local->hw.wiphy, &sdata->work); } static void ieee80211_ibss_sta_expire(struct ieee80211_sub_if_data *sdata) @@ -1221,7 +1248,7 @@ unsigned long exp_time = IEEE80211_IBSS_INACTIVITY_LIMIT; unsigned long exp_rsn = IEEE80211_IBSS_RSN_INACTIVITY_LIMIT; - mutex_lock(&local->sta_mtx); + lockdep_assert_wiphy(local->hw.wiphy); list_for_each_entry_safe(sta, tmp, &local->sta_list, list) { unsigned long last_active = ieee80211_sta_last_active(sta); @@ -1246,8 +1273,6 @@ WARN_ON(__sta_info_destroy(sta)); } } - - mutex_unlock(&local->sta_mtx); } /* @@ -1259,7 +1284,7 @@ struct ieee80211_if_ibss *ifibss = &sdata->u.ibss; enum nl80211_bss_scan_width scan_width; - sdata_assert_lock(sdata); + lockdep_assert_wiphy(sdata->local->hw.wiphy); mod_timer(&ifibss->timer, round_jiffies(jiffies + IEEE80211_IBSS_MERGE_INTERVAL)); @@ -1291,7 +1316,7 @@ u16 capability; int i; - sdata_assert_lock(sdata); + lockdep_assert_wiphy(sdata->local->hw.wiphy); if (ifibss->fixed_bssid) { memcpy(bssid, ifibss->bssid, ETH_ALEN); @@ -1402,7 +1427,7 @@ enum nl80211_bss_scan_width scan_width; int active_ibss; - sdata_assert_lock(sdata); + lockdep_assert_wiphy(sdata->local->hw.wiphy); active_ibss = ieee80211_sta_active_ibss(sdata); ibss_dbg(sdata, "sta_find_ibss (active_ibss=%d)\n", active_ibss); @@ -1496,7 +1521,7 @@ struct beacon_data *presp; u8 *pos, *end; - sdata_assert_lock(sdata); + lockdep_assert_wiphy(sdata->local->hw.wiphy); presp = sdata_dereference(ifibss->presp, sdata); @@ -1592,10 +1617,8 @@ mgmt = (struct ieee80211_mgmt *) skb->data; fc = le16_to_cpu(mgmt->frame_control); - sdata_lock(sdata); - if (!sdata->u.ibss.ssid_len) - goto mgmt_out; /* not ready to merge yet */ + return; /* not ready to merge yet */ switch (fc & IEEE80211_FCTL_STYPE) { case IEEE80211_STYPE_PROBE_REQ: @@ -1635,16 +1658,12 @@ break; } } - - mgmt_out: - sdata_unlock(sdata); } void ieee80211_ibss_work(struct ieee80211_sub_if_data *sdata) { struct ieee80211_if_ibss *ifibss = &sdata->u.ibss; - - sdata_lock(sdata); + struct sta_info *sta; /* * Work could be scheduled after scan or similar @@ -1652,7 +1671,20 @@ * network. */ if (!ifibss->ssid_len) - goto out; + return; + + spin_lock_bh(&ifibss->incomplete_lock); + while (!list_empty(&ifibss->incomplete_stations)) { + sta = list_first_entry(&ifibss->incomplete_stations, + struct sta_info, list); + list_del(&sta->list); + spin_unlock_bh(&ifibss->incomplete_lock); + + ieee80211_ibss_finish_sta(sta); + rcu_read_unlock(); + spin_lock_bh(&ifibss->incomplete_lock); + } + spin_unlock_bh(&ifibss->incomplete_lock); switch (ifibss->state) { case IEEE80211_IBSS_MLME_SEARCH: @@ -1665,9 +1697,6 @@ WARN_ON(1); break; } - - out: - sdata_unlock(sdata); } static void ieee80211_ibss_timer(struct timer_list *t) @@ -1683,6 +1712,8 @@ struct ieee80211_if_ibss *ifibss = &sdata->u.ibss; timer_setup(&ifibss->timer, ieee80211_ibss_timer, 0); + INIT_LIST_HEAD(&ifibss->incomplete_stations); + spin_lock_init(&ifibss->incomplete_lock); wiphy_work_init(&ifibss->csa_connection_drop_work, ieee80211_csa_connection_drop_work); } @@ -1692,7 +1723,8 @@ { struct ieee80211_sub_if_data *sdata; - mutex_lock(&local->iflist_mtx); + lockdep_assert_wiphy(local->hw.wiphy); + list_for_each_entry(sdata, &local->interfaces, list) { if (!ieee80211_sdata_running(sdata)) continue; @@ -1700,7 +1732,6 @@ continue; sdata->u.ibss.last_scan_completed = jiffies; } - mutex_unlock(&local->iflist_mtx); } int ieee80211_ibss_join(struct ieee80211_sub_if_data *sdata, @@ -1715,6 +1746,8 @@ int i; int ret; + lockdep_assert_wiphy(local->hw.wiphy); + if (params->chandef.chan->freq_offset) { /* this may work, but is untested */ return -EOPNOTSUPP; @@ -1735,10 +1768,8 @@ chanmode = (params->channel_fixed && !ret) ? IEEE80211_CHANCTX_SHARED : IEEE80211_CHANCTX_EXCLUSIVE; - mutex_lock(&local->chanctx_mtx); ret = ieee80211_check_combinations(sdata, ¶ms->chandef, chanmode, radar_detect_width); - mutex_unlock(&local->chanctx_mtx); if (ret < 0) return ret; diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/ieee80211_i.h backport-iwlwifi-dkms-11510/net/mac80211/ieee80211_i.h --- backport-iwlwifi-dkms-11289/net/mac80211/ieee80211_i.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/ieee80211_i.h 2023-10-04 04:18:43.000000000 +0800 @@ -85,6 +85,12 @@ #define IEEE80211_MAX_NAN_INSTANCE_ID 255 +enum ieee80211_status_data { + IEEE80211_STATUS_TYPE_MASK = 0x00f, + IEEE80211_STATUS_TYPE_INVALID = 0, + IEEE80211_STATUS_TYPE_SMPS = 1, + IEEE80211_STATUS_SUBDATA_MASK = 0xff0, +}; /* * Keep a station's queues on the active list for deficit accounting purposes @@ -482,7 +488,7 @@ struct timer_list timer; struct timer_list conn_mon_timer; struct timer_list bcn_mon_timer; - struct work_struct monitor_work; + struct wiphy_work monitor_work; struct wiphy_work beacon_connection_loss_work; struct wiphy_work csa_connection_drop_work; @@ -545,7 +551,7 @@ /* TDLS support */ u8 tdls_peer[ETH_ALEN] __aligned(2); - struct delayed_work tdls_peer_del_work; + struct wiphy_delayed_work tdls_peer_del_work; struct sk_buff *orig_teardown_skb; /* The original teardown skb */ struct sk_buff *teardown_skb; /* A copy to send through the AP */ spinlock_t teardown_lock; /* To lock changing teardown_skb */ @@ -559,7 +565,7 @@ * on the BE queue, but there's a lot of VO traffic, we might * get stuck in a downgraded situation and flush takes forever. */ - struct delayed_work tx_tspec_wk; + struct wiphy_delayed_work tx_tspec_wk; /* Information elements from the last transmitted (Re)Association * Request frame. @@ -567,7 +573,7 @@ u8 *assoc_req_ies; size_t assoc_req_ies_len; - struct delayed_work ml_reconf_work; + struct wiphy_delayed_work ml_reconf_work; u16 removed_links; /* TID-to-link mapping support */ @@ -603,6 +609,9 @@ struct ieee80211_ht_cap ht_capa; /* configured ht-cap over-rides */ struct ieee80211_ht_cap ht_capa_mask; /* Valid parts of ht_capa */ + spinlock_t incomplete_lock; + struct list_head incomplete_stations; + enum { IEEE80211_IBSS_MLME_SEARCH, IEEE80211_IBSS_MLME_JOINED, @@ -945,6 +954,9 @@ struct wiphy_delayed_work chswitch_work; struct wiphy_work request_smps_work; + /* used to reconfigure hardware SM PS */ + struct wiphy_work recalc_smps; + bool beacon_crc_valid; u32 beacon_crc; struct ewma_beacon_signal ave_beacon_signal; @@ -989,8 +1001,8 @@ struct ieee80211_sub_if_data *sdata; unsigned int link_id; - struct list_head assigned_chanctx_list; /* protected by chanctx_mtx */ - struct list_head reserved_chanctx_list; /* protected by chanctx_mtx */ + struct list_head assigned_chanctx_list; /* protected by wiphy mutex */ + struct list_head reserved_chanctx_list; /* protected by wiphy mutex */ /* multicast keys only */ struct ieee80211_key __rcu *gtk[NUM_DEFAULT_KEYS + @@ -1000,18 +1012,18 @@ struct ieee80211_key __rcu *default_mgmt_key; struct ieee80211_key __rcu *default_beacon_key; - struct work_struct csa_finalize_work; - bool csa_block_tx; /* write-protected by sdata_lock and local->mtx */ + struct wiphy_work csa_finalize_work; + bool csa_block_tx; bool operating_11g_mode; struct cfg80211_chan_def csa_chandef; - struct work_struct color_change_finalize_work; + struct wiphy_work color_change_finalize_work; struct delayed_work color_collision_detect_work; u64 color_bitmap; - /* context reservation -- protected with chanctx_mtx */ + /* context reservation -- protected with wiphy mutex */ struct ieee80211_chanctx *reserved_chanctx; struct cfg80211_chan_def reserved_chandef; bool reserved_radar_required; @@ -1024,7 +1036,7 @@ int ap_power_level; /* in dBm */ bool radar_required; - struct delayed_work dfs_cac_timer_work; + struct wiphy_delayed_work dfs_cac_timer_work; union { struct ieee80211_link_data_managed mgd; @@ -1051,7 +1063,7 @@ /* count for keys needing tailroom space allocation */ int crypto_tx_tailroom_needed_cnt; int crypto_tx_tailroom_pending_dec; - struct delayed_work dec_tailroom_needed_wk; + struct wiphy_delayed_work dec_tailroom_needed_wk; struct net_device *dev; struct ieee80211_local *local; @@ -1083,9 +1095,6 @@ atomic_t num_tx_queued; struct mac80211_qos_map __rcu *qos_map; - /* used to reconfigure hardware SM PS */ - struct work_struct recalc_smps; - struct wiphy_work work; struct sk_buff_head skb_queue; struct sk_buff_head status_queue; @@ -1125,7 +1134,7 @@ struct ieee80211_link_data __rcu *link[IEEE80211_MLD_MAX_NUM_LINKS]; /* for ieee80211_set_active_links_async() */ - struct work_struct activate_links_work; + struct wiphy_work activate_links_work; u16 desired_active_links; #ifdef CPTCFG_MAC80211_DEBUGFS @@ -1148,28 +1157,8 @@ return container_of(p, struct ieee80211_sub_if_data, vif); } -static inline void sdata_lock(struct ieee80211_sub_if_data *sdata) - __acquires(&sdata->wdev.mtx) -{ - mutex_lock(&sdata->wdev.mtx); - __acquire(&sdata->wdev.mtx); -} - -static inline void sdata_unlock(struct ieee80211_sub_if_data *sdata) - __releases(&sdata->wdev.mtx) -{ - mutex_unlock(&sdata->wdev.mtx); - __release(&sdata->wdev.mtx); -} - #define sdata_dereference(p, sdata) \ - rcu_dereference_protected(p, lockdep_is_held(&sdata->wdev.mtx)) - -static inline void -sdata_assert_lock(struct ieee80211_sub_if_data *sdata) -{ - lockdep_assert_held(&sdata->wdev.mtx); -} + wiphy_dereference(sdata->local->hw.wiphy, p) static inline int ieee80211_chanwidth_get_shift(enum nl80211_chan_width width) @@ -1383,7 +1372,7 @@ spinlock_t filter_lock; /* used for uploading changed mc list */ - struct work_struct reconfig_filter; + struct wiphy_work reconfig_filter; /* aggregated multicast list */ struct netdev_hw_addr_list mc_list; @@ -1427,7 +1416,7 @@ /* wowlan is enabled -- don't reconfig on resume */ bool wowlan; - struct work_struct radar_detected_work; + struct wiphy_work radar_detected_work; /* number of RX chains the hardware has */ u8 rx_chains; @@ -1450,10 +1439,9 @@ /* Station data */ /* - * The mutex only protects the list, hash table and - * counter, reads are done with RCU. + * The list, hash table and counter are protected + * by the wiphy mutex, reads are done with RCU. */ - struct mutex sta_mtx; spinlock_t tim_lock; unsigned long num_sta; struct list_head sta_list; @@ -1482,15 +1470,6 @@ struct list_head mon_list; /* only that are IFF_UP && !cooked */ struct mutex iflist_mtx; - /* - * Key mutex, protects sdata's key_list and sta_info's - * key pointers and ptk_idx (write access, they're RCU.) - */ - struct mutex key_mtx; - - /* mutex for scan and work locking */ - struct mutex mtx; - /* Scanning and BSS list */ unsigned long scanning; struct cfg80211_ssid scan_ssid; @@ -1504,14 +1483,14 @@ int hw_scan_ies_bufsize; struct cfg80211_scan_info scan_info; - struct work_struct sched_scan_stopped_work; + struct wiphy_work sched_scan_stopped_work; struct ieee80211_sub_if_data __rcu *sched_scan_sdata; struct cfg80211_sched_scan_request __rcu *sched_scan_req; u8 scan_addr[ETH_ALEN]; unsigned long leave_oper_channel_time; enum mac80211_scan_state next_scan_state; - struct delayed_work scan_work; + struct wiphy_delayed_work scan_work; struct ieee80211_sub_if_data __rcu *scan_sdata; /* For backward compatibility only -- do not use */ struct cfg80211_chan_def _oper_chandef; @@ -1521,7 +1500,6 @@ /* channel contexts */ struct list_head chanctx_list; - struct mutex chanctx_mtx; #ifdef CPTCFG_MAC80211_LEDS struct led_trigger tx_led, rx_led, assoc_led, radio_led; @@ -1575,8 +1553,8 @@ * interface (and monitors) in PS, this then points there. */ struct ieee80211_sub_if_data *ps_sdata; - struct work_struct dynamic_ps_enable_work; - struct work_struct dynamic_ps_disable_work; + struct wiphy_work dynamic_ps_enable_work; + struct wiphy_work dynamic_ps_disable_work; struct timer_list dynamic_ps_timer; struct notifier_block ifa_notifier; struct notifier_block ifa6_notifier; @@ -1604,9 +1582,9 @@ /* * Remain-on-channel support */ - struct delayed_work roc_work; + struct wiphy_delayed_work roc_work; struct list_head roc_list; - struct work_struct hw_roc_start, hw_roc_done; + struct wiphy_work hw_roc_start, hw_roc_done; unsigned long hw_roc_start_time; u64 roc_cookie_counter; @@ -1955,7 +1933,7 @@ u64 *changed); /* scan/BSS handling */ -void ieee80211_scan_work(struct work_struct *work); +void ieee80211_scan_work(struct wiphy *wiphy, struct wiphy_work *work); int ieee80211_request_ibss_scan(struct ieee80211_sub_if_data *sdata, const u8 *ssid, u8 ssid_len, struct ieee80211_channel **channels, @@ -1988,7 +1966,8 @@ struct cfg80211_sched_scan_request *req); int ieee80211_request_sched_scan_stop(struct ieee80211_local *local); void ieee80211_sched_scan_end(struct ieee80211_local *local); -void ieee80211_sched_scan_stopped_work(struct work_struct *work); +void ieee80211_sched_scan_stopped_work(struct wiphy *wiphy, + struct wiphy_work *work); /* off-channel/mgmt-tx */ void ieee80211_offchannel_stop_vifs(struct ieee80211_local *local); @@ -2008,12 +1987,13 @@ struct wireless_dev *wdev, u64 cookie); /* channel switch handling */ -void ieee80211_csa_finalize_work(struct work_struct *work); +void ieee80211_csa_finalize_work(struct wiphy *wiphy, struct wiphy_work *work); int ieee80211_channel_switch(struct wiphy *wiphy, struct net_device *dev, struct cfg80211_csa_settings *params); /* color change handling */ -void ieee80211_color_change_finalize_work(struct work_struct *work); +void ieee80211_color_change_finalize_work(struct wiphy *wiphy, + struct wiphy_work *work); void ieee80211_color_collision_detection_work(struct work_struct *work); /* interface handling */ @@ -2063,7 +2043,10 @@ void ieee80211_link_stop(struct ieee80211_link_data *link); int ieee80211_vif_set_links(struct ieee80211_sub_if_data *sdata, u16 new_links, u16 dormant_links); -void ieee80211_vif_clear_links(struct ieee80211_sub_if_data *sdata); +static inline void ieee80211_vif_clear_links(struct ieee80211_sub_if_data *sdata) +{ + ieee80211_vif_set_links(sdata, 0, 0); +} /* tx handling */ void ieee80211_clear_tx_pending(struct ieee80211_local *local); @@ -2118,7 +2101,7 @@ u16 initiator, u16 reason_code); int ieee80211_send_smps_action(struct ieee80211_sub_if_data *sdata, enum ieee80211_smps_mode smps, const u8 *da, - const u8 *bssid); + const u8 *bssid, int link_id); bool ieee80211_smps_is_restrictive(enum ieee80211_smps_mode smps_mode_old, enum ieee80211_smps_mode smps_mode_new); @@ -2147,13 +2130,11 @@ int __ieee80211_stop_tx_ba_session(struct sta_info *sta, u16 tid, enum ieee80211_agg_stop_reason reason); -int ___ieee80211_stop_tx_ba_session(struct sta_info *sta, u16 tid, - enum ieee80211_agg_stop_reason reason); void ieee80211_start_tx_ba_cb(struct sta_info *sta, int tid, struct tid_ampdu_tx *tid_tx); void ieee80211_stop_tx_ba_cb(struct sta_info *sta, int tid, struct tid_ampdu_tx *tid_tx); -void ieee80211_ba_session_work(struct work_struct *work); +void ieee80211_ba_session_work(struct wiphy *wiphy, struct wiphy_work *work); void ieee80211_tx_ba_session_handle_start(struct sta_info *sta, int tid); void ieee80211_release_reorder_timeout(struct sta_info *sta, int tid); @@ -2366,8 +2347,10 @@ return ieee802_1d_to_ac[tid & 7]; } -void ieee80211_dynamic_ps_enable_work(struct work_struct *work); -void ieee80211_dynamic_ps_disable_work(struct work_struct *work); +void ieee80211_dynamic_ps_enable_work(struct wiphy *wiphy, + struct wiphy_work *work); +void ieee80211_dynamic_ps_disable_work(struct wiphy *wiphy, + struct wiphy_work *work); void ieee80211_dynamic_ps_timer(struct timer_list *t); void ieee80211_send_nullfunc(struct ieee80211_local *local, struct ieee80211_sub_if_data *sdata, @@ -2451,6 +2434,7 @@ struct txq_info *txq, int tid); void ieee80211_txq_purge(struct ieee80211_local *local, struct txq_info *txqi); +void ieee80211_purge_sta_txqs(struct sta_info *sta); void ieee80211_txq_remove_vlan(struct ieee80211_local *local, struct ieee80211_sub_if_data *sdata); void ieee80211_fill_txq_stats(struct cfg80211_txq_stats *txqstats, @@ -2587,9 +2571,10 @@ bool ieee80211_is_radar_required(struct ieee80211_local *local); void ieee80211_dfs_cac_timer(unsigned long data); -void ieee80211_dfs_cac_timer_work(struct work_struct *work); +void ieee80211_dfs_cac_timer_work(struct wiphy *wiphy, struct wiphy_work *work); void ieee80211_dfs_cac_cancel(struct ieee80211_local *local); -void ieee80211_dfs_radar_detected_work(struct work_struct *work); +void ieee80211_dfs_radar_detected_work(struct wiphy *wiphy, + struct wiphy_work *work); int ieee80211_send_action_csa(struct ieee80211_sub_if_data *sdata, struct cfg80211_csa_settings *csa_settings); @@ -2611,7 +2596,7 @@ const u8 *extra_ies, size_t extra_ies_len); int ieee80211_tdls_oper(struct wiphy *wiphy, struct net_device *dev, const u8 *peer, enum nl80211_tdls_operation oper); -void ieee80211_tdls_peer_del_work(struct work_struct *wk); +void ieee80211_tdls_peer_del_work(struct wiphy *wiphy, struct wiphy_work *wk); int ieee80211_tdls_channel_switch(struct wiphy *wiphy, struct net_device *dev, const u8 *addr, u8 oper_class, struct cfg80211_chan_def *chandef); @@ -2661,7 +2646,12 @@ u8 eht_cap_len, struct link_sta_info *link_sta); -#if IS_ENABLED(CONFIG_KUNIT) -int ieee80211_drop_unencrypted_mgmt(struct ieee80211_rx_data *rx); +#if IS_ENABLED(CPTCFG_MAC80211_KUNIT_TEST) +#define EXPORT_SYMBOL_IF_MAC80211_KUNIT(sym) EXPORT_SYMBOL(sym) +#define VISIBLE_IF_MAC80211_KUNIT +ieee80211_rx_result ieee80211_drop_unencrypted_mgmt(struct ieee80211_rx_data *rx); +#else +#define EXPORT_SYMBOL_IF_MAC80211_KUNIT(sym) +#define VISIBLE_IF_MAC80211_KUNIT static #endif #endif /* IEEE80211_I_H */ diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/iface.c backport-iwlwifi-dkms-11510/net/mac80211/iface.c --- backport-iwlwifi-dkms-11289/net/mac80211/iface.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/iface.c 2023-10-04 04:18:43.000000000 +0800 @@ -34,14 +34,13 @@ * The interface list in each struct ieee80211_local is protected * three-fold: * - * (1) modifications may only be done under the RTNL - * (2) modifications and readers are protected against each other by - * the iflist_mtx. - * (3) modifications are done in an RCU manner so atomic readers + * (1) modifications may only be done under the RTNL *and* wiphy mutex + * *and* iflist_mtx + * (2) modifications are done in an RCU manner so atomic readers * can traverse the list in RCU-safe blocks. * * As a consequence, reads (traversals) of the list can be protected - * by either the RTNL, the iflist_mtx or RCU. + * by either the RTNL, the wiphy mutex, the iflist_mtx or RCU. */ static int num_txqs = 1; @@ -116,7 +115,7 @@ bool working, scanning, active; unsigned int led_trig_start = 0, led_trig_stop = 0; - lockdep_assert_held(&local->mtx); + lockdep_assert_wiphy(local->hw.wiphy); active = force_active || !list_empty(&local->chanctx_list) || @@ -166,6 +165,8 @@ u8 *m; int ret = 0; + lockdep_assert_wiphy(local->hw.wiphy); + if (is_zero_ether_addr(local->hw.wiphy->addr_mask)) return 0; @@ -182,7 +183,6 @@ if (!check_dup) return ret; - mutex_lock(&local->iflist_mtx); list_for_each_entry(iter, &local->interfaces, list) { if (iter == sdata) continue; @@ -201,7 +201,6 @@ break; } } - mutex_unlock(&local->iflist_mtx); return ret; } @@ -213,6 +212,8 @@ struct ieee80211_sub_if_data *scan_sdata; int ret = 0; + lockdep_assert_wiphy(local->hw.wiphy); + /* To be the most flexible here we want to only limit changing the * address if the specific interface is doing offchannel work or * scanning. @@ -220,8 +221,6 @@ if (netif_carrier_ok(sdata->dev)) return -EBUSY; - mutex_lock(&local->mtx); - /* First check no ROC work is happening on this iface */ list_for_each_entry(roc, &local->roc_list, list) { if (roc->sdata != sdata) @@ -236,7 +235,7 @@ /* And if this iface is scanning */ if (local->scanning) { scan_sdata = rcu_dereference_protected(local->scan_sdata, - lockdep_is_held(&local->mtx)); + lockdep_is_held(&local->hw.wiphy->mtx)); if (sdata == scan_sdata) ret = -EBUSY; } @@ -253,13 +252,12 @@ } unlock: - mutex_unlock(&local->mtx); return ret; } -static int ieee80211_change_mac(struct net_device *dev, void *addr) +static int _ieee80211_change_mac(struct ieee80211_sub_if_data *sdata, + void *addr) { - struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev); struct ieee80211_local *local = sdata->local; struct sockaddr *sa = addr; bool check_dup = true; @@ -284,7 +282,7 @@ if (live) drv_remove_interface(local, sdata); - ret = eth_mac_addr(dev, sa); + ret = eth_mac_addr(sdata->dev, sa); if (ret == 0) { memcpy(sdata->vif.addr, sa->sa_data, ETH_ALEN); @@ -300,6 +298,19 @@ return ret; } +static int ieee80211_change_mac(struct net_device *dev, void *addr) +{ + struct ieee80211_sub_if_data *sdata = IEEE80211_DEV_TO_SUB_IF(dev); + struct ieee80211_local *local = sdata->local; + int ret; + + wiphy_lock(local->hw.wiphy); + ret = _ieee80211_change_mac(sdata, addr); + wiphy_unlock(local->hw.wiphy); + + return ret; +} + static inline int identical_mac_addr_allowed(int type1, int type2) { return type1 == NL80211_IFTYPE_MONITOR || @@ -317,9 +328,9 @@ { struct ieee80211_local *local = sdata->local; struct ieee80211_sub_if_data *nsdata; - int ret; ASSERT_RTNL(); + lockdep_assert_wiphy(local->hw.wiphy); /* we hold the RTNL here so can safely walk the list */ list_for_each_entry(nsdata, &local->interfaces, list) { @@ -384,10 +395,7 @@ } } - mutex_lock(&local->chanctx_mtx); - ret = ieee80211_check_combinations(sdata, NULL, 0, 0); - mutex_unlock(&local->chanctx_mtx); - return ret; + return ieee80211_check_combinations(sdata, NULL, 0, 0); } static int ieee80211_check_queues(struct ieee80211_sub_if_data *sdata, @@ -436,12 +444,13 @@ if (!is_valid_ether_addr(dev->dev_addr)) return -EADDRNOTAVAIL; + wiphy_lock(sdata->local->hw.wiphy); err = ieee80211_check_concurrent_iface(sdata, sdata->vif.type); if (err) - return err; + goto out; - wiphy_lock(sdata->local->hw.wiphy); err = ieee80211_do_open(&sdata->wdev, true); +out: wiphy_unlock(sdata->local->hw.wiphy); return err; @@ -459,6 +468,8 @@ bool cancel_scan; struct cfg80211_nan_func *func; + lockdep_assert_wiphy(local->hw.wiphy); + clear_bit(SDATA_STATE_RUNNING, &sdata->state); synchronize_rcu(); /* flush _ieee80211_wake_txqs() */ @@ -522,16 +533,12 @@ } del_timer_sync(&local->dynamic_ps_timer); - cancel_work_sync(&local->dynamic_ps_enable_work); + wiphy_work_cancel(local->hw.wiphy, &local->dynamic_ps_enable_work); - cancel_work_sync(&sdata->recalc_smps); - - sdata_lock(sdata); WARN(ieee80211_vif_is_mld(&sdata->vif), "destroying interface with valid links 0x%04x\n", sdata->vif.valid_links); - mutex_lock(&local->mtx); sdata->vif.bss_conf.csa_active = false; if (sdata->vif.type == NL80211_IFTYPE_STATION) sdata->deflink.u.mgd.csa_waiting_bcn = false; @@ -540,20 +547,17 @@ IEEE80211_QUEUE_STOP_REASON_CSA); sdata->deflink.csa_block_tx = false; } - mutex_unlock(&local->mtx); - sdata_unlock(sdata); - - cancel_work_sync(&sdata->deflink.csa_finalize_work); - cancel_work_sync(&sdata->deflink.color_change_finalize_work); - cancel_delayed_work_sync(&sdata->deflink.dfs_cac_timer_work); + wiphy_work_cancel(local->hw.wiphy, &sdata->deflink.csa_finalize_work); + wiphy_work_cancel(local->hw.wiphy, + &sdata->deflink.color_change_finalize_work); + wiphy_delayed_work_cancel(local->hw.wiphy, + &sdata->deflink.dfs_cac_timer_work); if (sdata->wdev.cac_started) { chandef = sdata->vif.bss_conf.chandef; WARN_ON(local->suspended); - mutex_lock(&local->mtx); ieee80211_link_release_channel(&sdata->deflink); - mutex_unlock(&local->mtx); cfg80211_cac_event(sdata->dev, &chandef, NL80211_RADAR_CAC_ABORTED, GFP_KERNEL); @@ -581,9 +585,7 @@ switch (sdata->vif.type) { case NL80211_IFTYPE_AP_VLAN: - mutex_lock(&local->mtx); list_del(&sdata->u.vlan.list); - mutex_unlock(&local->mtx); RCU_INIT_POINTER(sdata->vif.bss_conf.chanctx_conf, NULL); /* see comment in the default case below */ ieee80211_free_keys(sdata, true); @@ -681,9 +683,7 @@ if (local->monitors == 0) ieee80211_del_virtual_monitor(local); - mutex_lock(&local->mtx); ieee80211_recalc_idle(local); - mutex_unlock(&local->mtx); if (!(sdata->u.mntr.flags & MONITOR_FLAG_ACTIVE)) break; @@ -697,7 +697,7 @@ ieee80211_recalc_ps(local); if (cancel_scan) - flush_delayed_work(&local->scan_work); + wiphy_delayed_work_flush(local->hw.wiphy, &local->scan_work); if (local->open_count == 0) { ieee80211_stop_device(local); @@ -756,9 +756,9 @@ ieee80211_stop_mbssid(sdata); } - cancel_work_sync(&sdata->activate_links_work); - wiphy_lock(sdata->local->hw.wiphy); + wiphy_work_cancel(sdata->local->hw.wiphy, &sdata->activate_links_work); + ieee80211_do_stop(sdata, true); wiphy_unlock(sdata->local->hw.wiphy); @@ -785,7 +785,7 @@ spin_lock_bh(&local->filter_lock); __hw_addr_sync(&local->mc_list, &dev->mc, dev->addr_len); spin_unlock_bh(&local->filter_lock); - ieee80211_queue_work(&local->hw, &local->reconfig_filter); + wiphy_work_queue(local->hw.wiphy, &local->reconfig_filter); } /* @@ -1134,7 +1134,7 @@ if (!ieee80211_hw_check(&local->hw, SUPPORTS_TX_ENCAP_OFFLOAD)) return; - mutex_lock(&local->iflist_mtx); + lockdep_assert_wiphy(local->hw.wiphy); list_for_each_entry(sdata, &local->interfaces, list) { if (!ieee80211_sdata_running(sdata)) @@ -1142,8 +1142,6 @@ ieee80211_recalc_sdata_offload(sdata); } - - mutex_unlock(&local->iflist_mtx); } void ieee80211_adjust_monitor_flags(struct ieee80211_sub_if_data *sdata, @@ -1221,7 +1219,7 @@ snprintf(sdata->name, IFNAMSIZ, "%s-monitor", wiphy_name(local->hw.wiphy)); sdata->wdev.iftype = NL80211_IFTYPE_MONITOR; - mutex_init(&sdata->wdev.mtx); + sdata->wdev.wiphy = local->hw.wiphy; ieee80211_sdata_init(local, sdata); @@ -1246,19 +1244,14 @@ rcu_assign_pointer(local->monitor_sdata, sdata); mutex_unlock(&local->iflist_mtx); - sdata_lock(sdata); - mutex_lock(&local->mtx); ret = ieee80211_link_use_channel(&sdata->deflink, &local->monitor_chandef, IEEE80211_CHANCTX_EXCLUSIVE); - mutex_unlock(&local->mtx); - sdata_unlock(sdata); if (ret) { mutex_lock(&local->iflist_mtx); RCU_INIT_POINTER(local->monitor_sdata, NULL); mutex_unlock(&local->iflist_mtx); synchronize_net(); drv_remove_interface(local, sdata); - mutex_destroy(&sdata->wdev.mtx); kfree(sdata); return ret; } @@ -1294,15 +1287,10 @@ synchronize_net(); - sdata_lock(sdata); - mutex_lock(&local->mtx); ieee80211_link_release_channel(&sdata->deflink); - mutex_unlock(&local->mtx); - sdata_unlock(sdata); drv_remove_interface(local, sdata); - mutex_destroy(&sdata->wdev.mtx); kfree(sdata); } @@ -1320,6 +1308,8 @@ int res; u32 hw_reconf_flags = 0; + lockdep_assert_wiphy(local->hw.wiphy); + switch (sdata->vif.type) { case NL80211_IFTYPE_AP_VLAN: { struct ieee80211_sub_if_data *master; @@ -1327,9 +1317,7 @@ if (!sdata->bss) return -ENOLINK; - mutex_lock(&local->mtx); list_add(&sdata->u.vlan.list, &sdata->bss->vlans); - mutex_unlock(&local->mtx); master = container_of(sdata->bss, struct ieee80211_sub_if_data, u.ap); @@ -1346,10 +1334,8 @@ sizeof(sdata->vif.hw_queue)); sdata->vif.bss_conf.chandef = master->vif.bss_conf.chandef; - mutex_lock(&local->key_mtx); sdata->crypto_tx_tailroom_needed_cnt += master->crypto_tx_tailroom_needed_cnt; - mutex_unlock(&local->key_mtx); break; } @@ -1440,9 +1426,7 @@ ieee80211_adjust_monitor_flags(sdata, 1); ieee80211_configure_filter(local); ieee80211_recalc_offload(local); - mutex_lock(&local->mtx); ieee80211_recalc_idle(local); - mutex_unlock(&local->mtx); netif_carrier_on(dev); break; @@ -1547,11 +1531,8 @@ drv_stop(local); err_del_bss: sdata->bss = NULL; - if (sdata->vif.type == NL80211_IFTYPE_AP_VLAN) { - mutex_lock(&local->mtx); + if (sdata->vif.type == NL80211_IFTYPE_AP_VLAN) list_del(&sdata->u.vlan.list); - mutex_unlock(&local->mtx); - } /* might already be clear but that doesn't matter */ clear_bit(SDATA_STATE_RUNNING, &sdata->state); return res; @@ -1584,12 +1565,13 @@ { struct ieee80211_mgmt *mgmt = (void *)skb->data; + lockdep_assert_wiphy(local->hw.wiphy); + if (ieee80211_is_action(mgmt->frame_control) && mgmt->u.action.category == WLAN_CATEGORY_BACK) { struct sta_info *sta; int len = skb->len; - mutex_lock(&local->sta_mtx); sta = sta_info_get_bss(sdata, mgmt->sa); if (sta) { switch (mgmt->u.action.u.addba_req.action_code) { @@ -1610,7 +1592,6 @@ break; } } - mutex_unlock(&local->sta_mtx); } else if (ieee80211_is_action(mgmt->frame_control) && mgmt->u.action.category == WLAN_CATEGORY_VHT) { switch (mgmt->u.action.u.vht_group_notif.action_code) { @@ -1624,7 +1605,6 @@ band = status->band; opmode = mgmt->u.action.u.vht_opmode_notif.operating_mode; - mutex_lock(&local->sta_mtx); sta = sta_info_get_bss(sdata, mgmt->sa); if (sta) @@ -1632,7 +1612,6 @@ &sta->deflink, opmode, band); - mutex_unlock(&local->sta_mtx); break; } case WLAN_VHT_ACTION_GROUPID_MGMT: @@ -1679,7 +1658,6 @@ * a block-ack session was active. That cannot be * right, so terminate the session. */ - mutex_lock(&local->sta_mtx); sta = sta_info_get_bss(sdata, mgmt->sa); if (sta) { u16 tid = ieee80211_get_tid(hdr); @@ -1689,7 +1667,6 @@ WLAN_REASON_QSTA_REQUIRE_SETUP, true); } - mutex_unlock(&local->sta_mtx); } else switch (sdata->vif.type) { case NL80211_IFTYPE_STATION: ieee80211_sta_rx_queued_mgmt(sdata, skb); @@ -1786,15 +1763,8 @@ } } -static void ieee80211_recalc_smps_work(struct work_struct *work) -{ - struct ieee80211_sub_if_data *sdata = - container_of(work, struct ieee80211_sub_if_data, recalc_smps); - - ieee80211_recalc_smps(sdata, &sdata->deflink); -} - -static void ieee80211_activate_links_work(struct work_struct *work) +static void ieee80211_activate_links_work(struct wiphy *wiphy, + struct wiphy_work *work) { struct ieee80211_sub_if_data *sdata = container_of(work, struct ieee80211_sub_if_data, @@ -1841,8 +1811,8 @@ skb_queue_head_init(&sdata->skb_queue); skb_queue_head_init(&sdata->status_queue); wiphy_work_init(&sdata->work, ieee80211_iface_work); - INIT_WORK(&sdata->recalc_smps, ieee80211_recalc_smps_work); - INIT_WORK(&sdata->activate_links_work, ieee80211_activate_links_work); + wiphy_work_init(&sdata->activate_links_work, + ieee80211_activate_links_work); switch (type) { case NL80211_IFTYPE_P2P_GO: @@ -1901,7 +1871,7 @@ /* need to do this after the switch so vif.type is correct */ ieee80211_link_setup(&sdata->deflink); - ieee80211_debugfs_add_netdev(sdata); + ieee80211_debugfs_add_netdev(sdata, false); } static int ieee80211_runtime_change_iftype(struct ieee80211_sub_if_data *sdata, @@ -2032,6 +2002,8 @@ u8 tmp_addr[ETH_ALEN]; int i; + lockdep_assert_wiphy(local->hw.wiphy); + /* default ... something at least */ memcpy(perm_addr, local->hw.wiphy->perm_addr, ETH_ALEN); @@ -2039,8 +2011,6 @@ local->hw.wiphy->n_addresses <= 1) return; - mutex_lock(&local->iflist_mtx); - switch (type) { case NL80211_IFTYPE_MONITOR: /* doesn't matter */ @@ -2064,7 +2034,7 @@ if (!ieee80211_sdata_running(sdata)) continue; memcpy(perm_addr, sdata->vif.addr, ETH_ALEN); - goto out_unlock; + return; } } fallthrough; @@ -2150,9 +2120,6 @@ break; } - - out_unlock: - mutex_unlock(&local->iflist_mtx); } int ieee80211_if_add(struct ieee80211_local *local, const char *name, @@ -2166,6 +2133,7 @@ int ret, i; ASSERT_RTNL(); + lockdep_assert_wiphy(local->hw.wiphy); if (type == NL80211_IFTYPE_P2P_DEVICE || type == NL80211_IFTYPE_NAN) { struct wireless_dev *wdev; @@ -2253,8 +2221,8 @@ INIT_LIST_HEAD(&sdata->key_list); - INIT_DELAYED_WORK(&sdata->dec_tailroom_needed_wk, - ieee80211_delayed_tailroom_dec); + wiphy_delayed_work_init(&sdata->dec_tailroom_needed_wk, + ieee80211_delayed_tailroom_dec); for (i = 0; i < NUM_NL80211_BANDS; i++) { struct ieee80211_supported_band *sband; @@ -2343,6 +2311,7 @@ void ieee80211_if_remove(struct ieee80211_sub_if_data *sdata) { ASSERT_RTNL(); + lockdep_assert_wiphy(sdata->local->hw.wiphy); mutex_lock(&sdata->local->iflist_mtx); list_del_rcu(&sdata->list); @@ -2388,6 +2357,8 @@ */ cfg80211_shutdown_all_interfaces(local->hw.wiphy); + wiphy_lock(local->hw.wiphy); + WARN(local->open_count, "%s: open count remains %d\n", wiphy_name(local->hw.wiphy), local->open_count); @@ -2397,10 +2368,21 @@ list_splice_init(&local->interfaces, &unreg_list); mutex_unlock(&local->iflist_mtx); - wiphy_lock(local->hw.wiphy); list_for_each_entry_safe(sdata, tmp, &unreg_list, list) { bool netdev = sdata->dev; + /* + * Remove IP addresses explicitly, since the notifier will + * skip the callbacks if wdev->registered is false, since + * we can't acquire the wiphy_lock() again there if already + * inside this locked section. + */ + sdata->vif.cfg.arp_addr_cnt = 0; + if (sdata->vif.type == NL80211_IFTYPE_STATION && + sdata->u.mgd.associated) + ieee80211_vif_cfg_change_notify(sdata, + BSS_CHANGED_ARP_FILTER); + list_del(&sdata->list); cfg80211_unregister_wdev(&sdata->wdev); diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/key.c backport-iwlwifi-dkms-11510/net/mac80211/key.c --- backport-iwlwifi-dkms-11289/net/mac80211/key.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/key.c 2023-10-04 04:18:43.000000000 +0800 @@ -53,11 +53,6 @@ static const u8 bcast_addr[ETH_ALEN] = { 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF }; -static void assert_key_lock(struct ieee80211_local *local) -{ - lockdep_assert_held(&local->key_mtx); -} - static void update_vlan_tailroom_need_count(struct ieee80211_sub_if_data *sdata, int delta) { @@ -67,7 +62,7 @@ return; /* crypto_tx_tailroom_needed_cnt is protected by this */ - assert_key_lock(sdata->local); + lockdep_assert_wiphy(sdata->local->hw.wiphy); rcu_read_lock(); @@ -98,7 +93,7 @@ * http://mid.gmane.org/1308590980.4322.19.camel@jlt3.sipsolutions.net */ - assert_key_lock(sdata->local); + lockdep_assert_wiphy(sdata->local->hw.wiphy); update_vlan_tailroom_need_count(sdata, 1); @@ -114,7 +109,7 @@ static void decrease_tailroom_need_count(struct ieee80211_sub_if_data *sdata, int delta) { - assert_key_lock(sdata->local); + lockdep_assert_wiphy(sdata->local->hw.wiphy); WARN_ON_ONCE(sdata->crypto_tx_tailroom_needed_cnt < delta); @@ -129,6 +124,7 @@ int ret = -EOPNOTSUPP; might_sleep(); + lockdep_assert_wiphy(key->local->hw.wiphy); if (key->flags & KEY_FLAG_TAINTED) { /* If we get here, it's during resume and the key is @@ -151,8 +147,6 @@ if (!key->local->ops->set_key) goto out_unsupported; - assert_key_lock(key->local); - sta = key->sta; /* @@ -242,14 +236,14 @@ if (!key || !key->local->ops->set_key) return; - assert_key_lock(key->local); - if (!(key->flags & KEY_FLAG_UPLOADED_TO_HARDWARE)) return; sta = key->sta; sdata = key->sdata; + lockdep_assert_wiphy(key->local->hw.wiphy); + if (key->conf.link_id >= 0 && sdata->vif.active_links && !(sdata->vif.active_links & BIT(key->conf.link_id))) return; @@ -275,7 +269,7 @@ struct sta_info *sta = key->sta; struct ieee80211_local *local = key->local; - assert_key_lock(local); + lockdep_assert_wiphy(local->hw.wiphy); set_sta_flag(sta, WLAN_STA_USES_ENCRYPTION); @@ -300,7 +294,7 @@ struct sta_info *sta = new->sta; int i; - assert_key_lock(local); + lockdep_assert_wiphy(local->hw.wiphy); if (new->conf.flags & IEEE80211_KEY_FLAG_NO_AUTO_TX) { /* Extended Key ID key install, initial one or rekey */ @@ -317,11 +311,9 @@ * job done for the few ms we need it.) */ set_sta_flag(sta, WLAN_STA_BLOCK_BA); - mutex_lock(&sta->ampdu_mlme.mtx); for (i = 0; i < IEEE80211_NUM_TIDS; i++) - ___ieee80211_stop_tx_ba_session(sta, i, - AGG_STOP_LOCAL_REQUEST); - mutex_unlock(&sta->ampdu_mlme.mtx); + __ieee80211_stop_tx_ba_session(sta, i, + AGG_STOP_LOCAL_REQUEST); } } else if (old) { /* Rekey without Extended Key ID. @@ -358,12 +350,14 @@ struct ieee80211_sub_if_data *sdata = link->sdata; struct ieee80211_key *key = NULL; - assert_key_lock(sdata->local); + lockdep_assert_wiphy(sdata->local->hw.wiphy); if (idx >= 0 && idx < NUM_DEFAULT_KEYS) { - key = key_mtx_dereference(sdata->local, sdata->keys[idx]); + key = wiphy_dereference(sdata->local->hw.wiphy, + sdata->keys[idx]); if (!key) - key = key_mtx_dereference(sdata->local, link->gtk[idx]); + key = wiphy_dereference(sdata->local->hw.wiphy, + link->gtk[idx]); } if (uni) { @@ -382,9 +376,9 @@ void ieee80211_set_default_key(struct ieee80211_link_data *link, int idx, bool uni, bool multi) { - mutex_lock(&link->sdata->local->key_mtx); + lockdep_assert_wiphy(link->sdata->local->hw.wiphy); + __ieee80211_set_default_key(link, idx, uni, multi); - mutex_unlock(&link->sdata->local->key_mtx); } static void @@ -393,11 +387,12 @@ struct ieee80211_sub_if_data *sdata = link->sdata; struct ieee80211_key *key = NULL; - assert_key_lock(sdata->local); + lockdep_assert_wiphy(sdata->local->hw.wiphy); if (idx >= NUM_DEFAULT_KEYS && idx < NUM_DEFAULT_KEYS + NUM_DEFAULT_MGMT_KEYS) - key = key_mtx_dereference(sdata->local, link->gtk[idx]); + key = wiphy_dereference(sdata->local->hw.wiphy, + link->gtk[idx]); rcu_assign_pointer(link->default_mgmt_key, key); @@ -407,9 +402,9 @@ void ieee80211_set_default_mgmt_key(struct ieee80211_link_data *link, int idx) { - mutex_lock(&link->sdata->local->key_mtx); + lockdep_assert_wiphy(link->sdata->local->hw.wiphy); + __ieee80211_set_default_mgmt_key(link, idx); - mutex_unlock(&link->sdata->local->key_mtx); } static void @@ -418,12 +413,13 @@ struct ieee80211_sub_if_data *sdata = link->sdata; struct ieee80211_key *key = NULL; - assert_key_lock(sdata->local); + lockdep_assert_wiphy(sdata->local->hw.wiphy); if (idx >= NUM_DEFAULT_KEYS + NUM_DEFAULT_MGMT_KEYS && idx < NUM_DEFAULT_KEYS + NUM_DEFAULT_MGMT_KEYS + NUM_DEFAULT_BEACON_KEYS) - key = key_mtx_dereference(sdata->local, link->gtk[idx]); + key = wiphy_dereference(sdata->local->hw.wiphy, + link->gtk[idx]); rcu_assign_pointer(link->default_beacon_key, key); @@ -433,9 +429,9 @@ void ieee80211_set_default_beacon_key(struct ieee80211_link_data *link, int idx) { - mutex_lock(&link->sdata->local->key_mtx); + lockdep_assert_wiphy(link->sdata->local->hw.wiphy); + __ieee80211_set_default_beacon_key(link, idx); - mutex_unlock(&link->sdata->local->key_mtx); } static int ieee80211_key_replace(struct ieee80211_sub_if_data *sdata, @@ -452,6 +448,8 @@ bool defunikey, defmultikey, defmgmtkey, defbeaconkey; bool is_wep; + lockdep_assert_wiphy(sdata->local->hw.wiphy); + /* caller must provide at least one old/new */ if (WARN_ON(!new && !old)) return 0; @@ -482,7 +480,7 @@ if (sta) { link_sta = rcu_dereference_protected(sta->link[link_id], - lockdep_is_held(&sta->local->sta_mtx)); + lockdep_is_held(&sta->local->hw.wiphy->mtx)); if (!link_sta) return -ENOLINK; } @@ -510,12 +508,10 @@ ret = ieee80211_key_enable_hw_accel(new); } } else { - if (!new->local->wowlan) { + if (!new->local->wowlan) ret = ieee80211_key_enable_hw_accel(new); - } else { - assert_key_lock(new->local); + else new->flags |= KEY_FLAG_UPLOADED_TO_HARDWARE; - } } if (ret) @@ -541,17 +537,17 @@ ieee80211_check_fast_rx(sta); } else { defunikey = old && - old == key_mtx_dereference(sdata->local, - sdata->default_unicast_key); + old == wiphy_dereference(sdata->local->hw.wiphy, + sdata->default_unicast_key); defmultikey = old && - old == key_mtx_dereference(sdata->local, - link->default_multicast_key); + old == wiphy_dereference(sdata->local->hw.wiphy, + link->default_multicast_key); defmgmtkey = old && - old == key_mtx_dereference(sdata->local, - link->default_mgmt_key); + old == wiphy_dereference(sdata->local->hw.wiphy, + link->default_mgmt_key); defbeaconkey = old && - old == key_mtx_dereference(sdata->local, - link->default_beacon_key); + old == wiphy_dereference(sdata->local->hw.wiphy, + link->default_beacon_key); if (defunikey && !new) __ieee80211_set_default_key(link, -1, true, false); @@ -775,8 +771,9 @@ if (delay_tailroom) { /* see ieee80211_delayed_tailroom_dec */ sdata->crypto_tx_tailroom_pending_dec++; - schedule_delayed_work(&sdata->dec_tailroom_needed_wk, - HZ/2); + wiphy_delayed_work_queue(sdata->local->hw.wiphy, + &sdata->dec_tailroom_needed_wk, + HZ / 2); } else { decrease_tailroom_need_count(sdata, 1); } @@ -854,49 +851,50 @@ * can cause warnings to appear. */ bool delay_tailroom = sdata->vif.type == NL80211_IFTYPE_STATION; - int ret = -EOPNOTSUPP; + int ret; - mutex_lock(&sdata->local->key_mtx); + lockdep_assert_wiphy(sdata->local->hw.wiphy); if (sta && pairwise) { struct ieee80211_key *alt_key; - old_key = key_mtx_dereference(sdata->local, sta->ptk[idx]); - alt_key = key_mtx_dereference(sdata->local, sta->ptk[idx ^ 1]); + old_key = wiphy_dereference(sdata->local->hw.wiphy, + sta->ptk[idx]); + alt_key = wiphy_dereference(sdata->local->hw.wiphy, + sta->ptk[idx ^ 1]); /* The rekey code assumes that the old and new key are using * the same cipher. Enforce the assumption for pairwise keys. */ if ((alt_key && alt_key->conf.cipher != key->conf.cipher) || (old_key && old_key->conf.cipher != key->conf.cipher)) - goto out; + return -EOPNOTSUPP; } else if (sta) { struct link_sta_info *link_sta = &sta->deflink; int link_id = key->conf.link_id; if (link_id >= 0) { link_sta = rcu_dereference_protected(sta->link[link_id], - lockdep_is_held(&sta->local->sta_mtx)); - if (!link_sta) { - ret = -ENOLINK; - goto out; - } + lockdep_is_held(&sta->local->hw.wiphy->mtx)); + if (!link_sta) + return -ENOLINK; } - old_key = key_mtx_dereference(sdata->local, link_sta->gtk[idx]); + old_key = wiphy_dereference(sdata->local->hw.wiphy, + link_sta->gtk[idx]); } else { if (idx < NUM_DEFAULT_KEYS) - old_key = key_mtx_dereference(sdata->local, - sdata->keys[idx]); + old_key = wiphy_dereference(sdata->local->hw.wiphy, + sdata->keys[idx]); if (!old_key) - old_key = key_mtx_dereference(sdata->local, - link->gtk[idx]); + old_key = wiphy_dereference(sdata->local->hw.wiphy, + link->gtk[idx]); } /* Non-pairwise keys must also not switch the cipher on rekey */ if (!pairwise) { if (old_key && old_key->conf.cipher != key->conf.cipher) - goto out; + return -EOPNOTSUPP; } /* @@ -905,8 +903,7 @@ */ if (ieee80211_key_identical(sdata, old_key, key)) { ieee80211_key_free_unused(key); - ret = 0; - goto out; + return 0; } key->local = sdata->local; @@ -930,9 +927,6 @@ ieee80211_key_free(key, delay_tailroom); } - out: - mutex_unlock(&sdata->local->key_mtx); - return ret; } @@ -958,8 +952,6 @@ lockdep_assert_wiphy(sdata->local->hw.wiphy); - mutex_lock(&sdata->local->key_mtx); - sdata->crypto_tx_tailroom_needed_cnt = 0; sdata->crypto_tx_tailroom_pending_dec = 0; @@ -976,8 +968,6 @@ ieee80211_key_enable_hw_accel(key); } } - - mutex_unlock(&sdata->local->key_mtx); } void ieee80211_iter_keys(struct ieee80211_hw *hw, @@ -995,7 +985,6 @@ lockdep_assert_wiphy(hw->wiphy); - mutex_lock(&local->key_mtx); if (vif) { sdata = vif_to_sdata(vif); list_for_each_entry_safe(key, tmp, &sdata->key_list, list) @@ -1010,7 +999,6 @@ key->sta ? &key->sta->sta : NULL, &key->conf, iter_data); } - mutex_unlock(&local->key_mtx); } EXPORT_SYMBOL(ieee80211_iter_keys); @@ -1090,7 +1078,8 @@ struct ieee80211_local *local = sdata->local; struct ieee80211_key *key, *tmp; - mutex_lock(&local->key_mtx); + lockdep_assert_wiphy(local->hw.wiphy); + list_for_each_entry_safe(key, tmp, &sdata->key_list, list) { if (key->conf.link_id != link->link_id) continue; @@ -1099,7 +1088,6 @@ key, NULL); list_add_tail(&key->list, keys); } - mutex_unlock(&local->key_mtx); } void ieee80211_free_key_list(struct ieee80211_local *local, @@ -1107,10 +1095,10 @@ { struct ieee80211_key *key, *tmp; - mutex_lock(&local->key_mtx); + lockdep_assert_wiphy(local->hw.wiphy); + list_for_each_entry_safe(key, tmp, keys, list) __ieee80211_key_destroy(key, false); - mutex_unlock(&local->key_mtx); } void ieee80211_free_keys(struct ieee80211_sub_if_data *sdata, @@ -1122,9 +1110,10 @@ struct ieee80211_key *key, *tmp; LIST_HEAD(keys); - cancel_delayed_work_sync(&sdata->dec_tailroom_needed_wk); + wiphy_delayed_work_cancel(local->hw.wiphy, + &sdata->dec_tailroom_needed_wk); - mutex_lock(&local->key_mtx); + lockdep_assert_wiphy(local->hw.wiphy); ieee80211_free_keys_iface(sdata, &keys); @@ -1157,8 +1146,6 @@ WARN_ON_ONCE(vlan->crypto_tx_tailroom_needed_cnt || vlan->crypto_tx_tailroom_pending_dec); } - - mutex_unlock(&local->key_mtx); } void ieee80211_free_sta_keys(struct ieee80211_local *local, @@ -1167,9 +1154,10 @@ struct ieee80211_key *key; int i; - mutex_lock(&local->key_mtx); + lockdep_assert_wiphy(local->hw.wiphy); + for (i = 0; i < ARRAY_SIZE(sta->deflink.gtk); i++) { - key = key_mtx_dereference(local, sta->deflink.gtk[i]); + key = wiphy_dereference(local->hw.wiphy, sta->deflink.gtk[i]); if (!key) continue; ieee80211_key_replace(key->sdata, NULL, key->sta, @@ -1180,7 +1168,7 @@ } for (i = 0; i < NUM_DEFAULT_KEYS; i++) { - key = key_mtx_dereference(local, sta->ptk[i]); + key = wiphy_dereference(local->hw.wiphy, sta->ptk[i]); if (!key) continue; ieee80211_key_replace(key->sdata, NULL, key->sta, @@ -1189,11 +1177,10 @@ __ieee80211_key_destroy(key, key->sdata->vif.type == NL80211_IFTYPE_STATION); } - - mutex_unlock(&local->key_mtx); } -void ieee80211_delayed_tailroom_dec(struct work_struct *wk) +void ieee80211_delayed_tailroom_dec(struct wiphy *wiphy, + struct wiphy_work *wk) { struct ieee80211_sub_if_data *sdata; @@ -1216,11 +1203,9 @@ * within an ESS this usually won't happen. */ - mutex_lock(&sdata->local->key_mtx); decrease_tailroom_need_count(sdata, sdata->crypto_tx_tailroom_pending_dec); sdata->crypto_tx_tailroom_pending_dec = 0; - mutex_unlock(&sdata->local->key_mtx); } void ieee80211_gtk_rekey_notify(struct ieee80211_vif *vif, const u8 *bssid, @@ -1349,7 +1334,7 @@ key = container_of(keyconf, struct ieee80211_key, conf); - assert_key_lock(key->local); + lockdep_assert_wiphy(key->local->hw.wiphy); /* * if key was uploaded, we assume the driver will/has remove(d) diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/key.h backport-iwlwifi-dkms-11510/net/mac80211/key.h --- backport-iwlwifi-dkms-11289/net/mac80211/key.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/key.h 2023-10-04 04:18:43.000000000 +0800 @@ -2,7 +2,7 @@ /* * Copyright 2002-2004, Instant802 Networks, Inc. * Copyright 2005, Devicescape Software, Inc. - * Copyright (C) 2019, 2022 Intel Corporation + * Copyright (C) 2019, 2022-2023 Intel Corporation */ #ifndef IEEE80211_KEY_H @@ -168,12 +168,7 @@ int ieee80211_key_switch_links(struct ieee80211_sub_if_data *sdata, unsigned long del_links_mask, unsigned long add_links_mask); - -#define key_mtx_dereference(local, ref) \ - rcu_dereference_protected(ref, lockdep_is_held(&((local)->key_mtx))) -#define rcu_dereference_check_key_mtx(local, ref) \ - rcu_dereference_check(ref, lockdep_is_held(&((local)->key_mtx))) - -void ieee80211_delayed_tailroom_dec(struct work_struct *wk); +void ieee80211_delayed_tailroom_dec(struct wiphy *wiphy, + struct wiphy_work *wk); #endif /* IEEE80211_KEY_H */ diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/led.c backport-iwlwifi-dkms-11510/net/mac80211/led.c --- backport-iwlwifi-dkms-11289/net/mac80211/led.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/led.c 2023-10-04 04:18:43.000000000 +0800 @@ -327,7 +327,7 @@ } } - led_trigger_blink(&local->tpt_led, &on, &off); + led_trigger_blink(&local->tpt_led, on, off); } const char * diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/led.h backport-iwlwifi-dkms-11510/net/mac80211/led.h --- backport-iwlwifi-dkms-11289/net/mac80211/led.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/led.h 2023-10-04 04:18:43.000000000 +0800 @@ -13,22 +13,18 @@ static inline void ieee80211_led_rx(struct ieee80211_local *local) { #ifdef CPTCFG_MAC80211_LEDS - unsigned long led_delay = MAC80211_BLINK_DELAY; - if (!atomic_read(&local->rx_led_active)) return; - led_trigger_blink_oneshot(&local->rx_led, &led_delay, &led_delay, 0); + led_trigger_blink_oneshot(&local->rx_led, MAC80211_BLINK_DELAY, MAC80211_BLINK_DELAY, 0); #endif } static inline void ieee80211_led_tx(struct ieee80211_local *local) { #ifdef CPTCFG_MAC80211_LEDS - unsigned long led_delay = MAC80211_BLINK_DELAY; - if (!atomic_read(&local->tx_led_active)) return; - led_trigger_blink_oneshot(&local->tx_led, &led_delay, &led_delay, 0); + led_trigger_blink_oneshot(&local->tx_led, MAC80211_BLINK_DELAY, MAC80211_BLINK_DELAY, 0); #endif } diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/link.c backport-iwlwifi-dkms-11510/net/mac80211/link.c --- backport-iwlwifi-dkms-11289/net/mac80211/link.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/link.c 2023-10-04 04:18:43.000000000 +0800 @@ -37,16 +37,16 @@ link_conf->link_id = link_id; link_conf->vif = &sdata->vif; - INIT_WORK(&link->csa_finalize_work, - ieee80211_csa_finalize_work); - INIT_WORK(&link->color_change_finalize_work, - ieee80211_color_change_finalize_work); + wiphy_work_init(&link->csa_finalize_work, + ieee80211_csa_finalize_work); + wiphy_work_init(&link->color_change_finalize_work, + ieee80211_color_change_finalize_work); INIT_DELAYED_WORK(&link->color_collision_detect_work, ieee80211_color_collision_detection_work); INIT_LIST_HEAD(&link->assigned_chanctx_list); INIT_LIST_HEAD(&link->reserved_chanctx_list); - INIT_DELAYED_WORK(&link->dfs_cac_timer_work, - ieee80211_dfs_cac_timer_work); + wiphy_delayed_work_init(&link->dfs_cac_timer_work, + ieee80211_dfs_cac_timer_work); if (!deflink) { switch (sdata->vif.type) { @@ -191,11 +191,11 @@ struct ieee80211_link_data *old_data[IEEE80211_MLD_MAX_NUM_LINKS]; bool use_deflink = old_links == 0; /* set for error case */ - sdata_assert_lock(sdata); + lockdep_assert_wiphy(sdata->local->hw.wiphy); memset(to_free, 0, sizeof(links)); - if (old_links == new_links) + if (old_links == new_links && dormant_links == sdata->vif.dormant_links) return 0; /* if there were no old links, need to clear the pointers to deflink */ @@ -235,6 +235,9 @@ RCU_INIT_POINTER(sdata->vif.link_conf[link_id], NULL); } + if (!old_links) + ieee80211_debugfs_recreate_netdev(sdata, true); + /* link them into data structures */ for_each_set_bit(link_id, &add, IEEE80211_MLD_MAX_NUM_LINKS) { WARN_ON(!use_deflink && @@ -261,6 +264,8 @@ old_links & old_active, new_links & sdata->vif.active_links, old); + if (!new_links) + ieee80211_debugfs_recreate_netdev(sdata, false); } if (ret) { @@ -303,23 +308,6 @@ return ret; } -void ieee80211_vif_clear_links(struct ieee80211_sub_if_data *sdata) -{ - struct link_container *links[IEEE80211_MLD_MAX_NUM_LINKS]; - - /* - * The locking here is different because when we free links - * in the station case we need to be able to cancel_work_sync() - * something that also takes the lock. - */ - - sdata_lock(sdata); - ieee80211_vif_update_links(sdata, links, 0, 0); - sdata_unlock(sdata); - - ieee80211_free_links(sdata, links); -} - static int _ieee80211_set_active_links(struct ieee80211_sub_if_data *sdata, u16 active_links) { @@ -455,10 +443,8 @@ u16 old_active; int ret; - sdata_lock(sdata); - mutex_lock(&local->sta_mtx); - mutex_lock(&local->mtx); - mutex_lock(&local->key_mtx); + lockdep_assert_wiphy(local->hw.wiphy); + old_active = sdata->vif.active_links; if (old_active & active_links) { /* @@ -474,10 +460,6 @@ /* otherwise switch directly */ ret = _ieee80211_set_active_links(sdata, active_links); } - mutex_unlock(&local->key_mtx); - mutex_unlock(&local->mtx); - mutex_unlock(&local->sta_mtx); - sdata_unlock(sdata); return ret; } @@ -502,6 +484,6 @@ return; sdata->desired_active_links = active_links; - schedule_work(&sdata->activate_links_work); + wiphy_work_queue(sdata->local->hw.wiphy, &sdata->activate_links_work); } EXPORT_SYMBOL_GPL(ieee80211_set_active_links_async); diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/main.c backport-iwlwifi-dkms-11510/net/mac80211/main.c --- backport-iwlwifi-dkms-11289/net/mac80211/main.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/main.c 2023-10-04 04:18:43.000000000 +0800 @@ -84,7 +84,8 @@ local->filter_flags = new_flags & ~(1<<31); } -static void ieee80211_reconfig_filter(struct work_struct *work) +static void ieee80211_reconfig_filter(struct wiphy *wiphy, + struct wiphy_work *work) { struct ieee80211_local *local = container_of(work, struct ieee80211_local, reconfig_filter); @@ -206,7 +207,8 @@ BSS_CHANGED_PS |\ BSS_CHANGED_IBSS |\ BSS_CHANGED_ARP_FILTER |\ - BSS_CHANGED_SSID) + BSS_CHANGED_SSID |\ + BSS_CHANGED_MLD_VALID_LINKS) void ieee80211_bss_info_change_notify(struct ieee80211_sub_if_data *sdata, u64 changed) @@ -335,14 +337,12 @@ struct ieee80211_sub_if_data *sdata; int ret; - /* wait for scan work complete */ flush_workqueue(local->workqueue); - flush_work(&local->sched_scan_stopped_work); - flush_work(&local->radar_detected_work); /* we might do interface manipulations, so need both */ rtnl_lock(); wiphy_lock(local->hw.wiphy); + wiphy_work_flush(local->hw.wiphy, NULL); WARN(test_bit(SCAN_HW_SCANNING, &local->scanning), "%s called with hardware scan in progress\n", __func__); @@ -366,21 +366,19 @@ */ wiphy_work_cancel(local->hw.wiphy, &sdata->u.mgd.csa_connection_drop_work); - if (sdata->vif.bss_conf.csa_active) { - sdata_lock(sdata); + if (sdata->vif.bss_conf.csa_active) ieee80211_sta_connection_lost(sdata, WLAN_REASON_UNSPECIFIED, false); - sdata_unlock(sdata); - } } - flush_delayed_work(&sdata->dec_tailroom_needed_wk); + wiphy_delayed_work_flush(local->hw.wiphy, + &sdata->dec_tailroom_needed_wk); } ieee80211_scan_cancel(local); /* make sure any new ROC will consider local->in_reconfig */ - flush_delayed_work(&local->roc_work); - flush_work(&local->hw_roc_done); + wiphy_delayed_work_flush(local->hw.wiphy, &local->roc_work); + wiphy_work_flush(local->hw.wiphy, &local->hw_roc_done); /* wait for all packet processing to be done */ synchronize_net(); @@ -439,7 +437,7 @@ if (!wdev) return NOTIFY_DONE; - if (wdev->wiphy != local->hw.wiphy) + if (wdev->wiphy != local->hw.wiphy || !wdev->registered) return NOTIFY_DONE; sdata = IEEE80211_DEV_TO_SUB_IF(ndev); @@ -454,7 +452,25 @@ return NOTIFY_DONE; ifmgd = &sdata->u.mgd; - sdata_lock(sdata); + + /* + * The nested here is needed to convince lockdep that this is + * all OK. Yes, we lock the wiphy mutex here while we already + * hold the notifier rwsem, that's the normal case. And yes, + * we also acquire the notifier rwsem again when unregistering + * a netdev while we already hold the wiphy mutex, so it does + * look like a typical ABBA deadlock. + * + * However, both of these things happen with the RTNL held + * already. Therefore, they can't actually happen, since the + * lock orders really are ABC and ACB, which is fine due to + * the RTNL (A). + * + * We still need to prevent recursion, which is accomplished + * by the !wdev->registered check above. + */ + mutex_lock_nested(&local->hw.wiphy->mtx, 1); + __acquire(&local->hw.wiphy->mtx); /* Copy the addresses to the vif config list */ ifa = rtnl_dereference(idev->ifa_list); @@ -471,7 +487,7 @@ if (ifmgd->associated) ieee80211_vif_cfg_change_notify(sdata, BSS_CHANGED_ARP_FILTER); - sdata_unlock(sdata); + wiphy_unlock(local->hw.wiphy); return NOTIFY_OK; } @@ -784,9 +800,6 @@ __hw_addr_init(&local->mc_list); mutex_init(&local->iflist_mtx); - mutex_init(&local->mtx); - - mutex_init(&local->key_mtx); spin_lock_init(&local->filter_lock); spin_lock_init(&local->rx_path_lock); spin_lock_init(&local->queue_stop_reason_lock); @@ -807,26 +820,25 @@ spin_lock_init(&local->handle_wake_tx_queue_lock); INIT_LIST_HEAD(&local->chanctx_list); - mutex_init(&local->chanctx_mtx); - INIT_DELAYED_WORK(&local->scan_work, ieee80211_scan_work); + wiphy_delayed_work_init(&local->scan_work, ieee80211_scan_work); INIT_WORK(&local->restart_work, ieee80211_restart_work); - INIT_WORK(&local->radar_detected_work, - ieee80211_dfs_radar_detected_work); + wiphy_work_init(&local->radar_detected_work, + ieee80211_dfs_radar_detected_work); - INIT_WORK(&local->reconfig_filter, ieee80211_reconfig_filter); + wiphy_work_init(&local->reconfig_filter, ieee80211_reconfig_filter); local->smps_mode = IEEE80211_SMPS_OFF; - INIT_WORK(&local->dynamic_ps_enable_work, - ieee80211_dynamic_ps_enable_work); - INIT_WORK(&local->dynamic_ps_disable_work, - ieee80211_dynamic_ps_disable_work); + wiphy_work_init(&local->dynamic_ps_enable_work, + ieee80211_dynamic_ps_enable_work); + wiphy_work_init(&local->dynamic_ps_disable_work, + ieee80211_dynamic_ps_disable_work); timer_setup(&local->dynamic_ps_timer, ieee80211_dynamic_ps_timer, 0); - INIT_WORK(&local->sched_scan_stopped_work, - ieee80211_sched_scan_stopped_work); + wiphy_work_init(&local->sched_scan_stopped_work, + ieee80211_sched_scan_stopped_work); spin_lock_init(&local->ack_status_lock); idr_init(&local->ack_status_frames); @@ -1484,13 +1496,15 @@ */ ieee80211_remove_interfaces(local); + wiphy_lock(local->hw.wiphy); + wiphy_delayed_work_cancel(local->hw.wiphy, &local->roc_work); + wiphy_work_cancel(local->hw.wiphy, &local->reconfig_filter); + wiphy_work_cancel(local->hw.wiphy, &local->sched_scan_stopped_work); + wiphy_work_cancel(local->hw.wiphy, &local->radar_detected_work); + wiphy_unlock(local->hw.wiphy); rtnl_unlock(); - cancel_delayed_work_sync(&local->roc_work); cancel_work_sync(&local->restart_work); - cancel_work_sync(&local->reconfig_filter); - flush_work(&local->sched_scan_stopped_work); - flush_work(&local->radar_detected_work); ieee80211_clear_tx_pending(local); rate_control_deinitialize(local); @@ -1521,7 +1535,6 @@ enum nl80211_band band; mutex_destroy(&local->iflist_mtx); - mutex_destroy(&local->mtx); if (local->wiphy_ciphers_allocated) { kfree(local->hw.wiphy->cipher_suites); diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/mesh.c backport-iwlwifi-dkms-11510/net/mac80211/mesh.c --- backport-iwlwifi-dkms-11289/net/mac80211/mesh.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/mesh.c 2023-10-04 04:18:43.000000000 +0800 @@ -56,6 +56,8 @@ * * This function checks if the mesh configuration of a mesh point matches the * local mesh configuration, i.e. if both nodes belong to the same mesh network. + * + * Returns: %true if both nodes belong to the same mesh */ bool mesh_matches_local(struct ieee80211_sub_if_data *sdata, struct ieee802_11_elems *ie) @@ -119,6 +121,8 @@ * mesh_peer_accepts_plinks - check if an mp is willing to establish peer links * * @ie: information elements of a management frame from the mesh peer + * + * Returns: %true if the mesh peer is willing to establish peer links */ bool mesh_peer_accepts_plinks(struct ieee802_11_elems *ie) { @@ -858,7 +862,7 @@ * @meshsa: source address in the mesh. Same as TA, as frame is * locally originated. * - * Return the length of the 802.11 (does not include a mesh control header) + * Returns: the length of the 802.11 frame header (excludes mesh control header) */ int ieee80211_fill_mesh_addresses(struct ieee80211_hdr *hdr, __le16 *fc, const u8 *meshda, const u8 *meshsa) @@ -891,7 +895,7 @@ * @addr6: 2nd address in the ae header, which corresponds to addr6 of the * mesh frame * - * Return the header length. + * Returns: the header length */ unsigned int ieee80211_new_mesh_header(struct ieee80211_sub_if_data *sdata, struct ieee80211s_hdr *meshhdr, @@ -1291,7 +1295,7 @@ ieee80211_conn_flags_t conn_flags = 0; u32 vht_cap_info = 0; - sdata_assert_lock(sdata); + lockdep_assert_wiphy(sdata->local->hw.wiphy); sband = ieee80211_get_sband(sdata); if (!sband) @@ -1559,7 +1563,7 @@ struct mesh_csa_settings *tmp_csa_settings; int ret = 0; - lockdep_assert_held(&sdata->wdev.mtx); + lockdep_assert_wiphy(sdata->local->hw.wiphy); tmp_csa_settings = kmalloc(sizeof(*tmp_csa_settings), GFP_ATOMIC); @@ -1691,11 +1695,11 @@ struct ieee80211_mgmt *mgmt; u16 stype; - sdata_lock(sdata); + lockdep_assert_wiphy(sdata->local->hw.wiphy); /* mesh already went down */ if (!sdata->u.mesh.mesh_id_len) - goto out; + return; rx_status = IEEE80211_SKB_RXCB(skb); mgmt = (struct ieee80211_mgmt *) skb->data; @@ -1714,8 +1718,6 @@ ieee80211_mesh_rx_mgmt_action(sdata, mgmt, skb->len, rx_status); break; } -out: - sdata_unlock(sdata); } static void mesh_bss_info_changed(struct ieee80211_sub_if_data *sdata) @@ -1745,11 +1747,11 @@ { struct ieee80211_if_mesh *ifmsh = &sdata->u.mesh; - sdata_lock(sdata); + lockdep_assert_wiphy(sdata->local->hw.wiphy); /* mesh already went down */ if (!sdata->u.mesh.mesh_id_len) - goto out; + return; if (ifmsh->preq_queue_len && time_after(jiffies, @@ -1767,8 +1769,6 @@ if (test_and_clear_bit(MESH_WORK_MBSS_CHANGED, &ifmsh->wrkq_flags)) mesh_bss_info_changed(sdata); -out: - sdata_unlock(sdata); } diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/mesh_hwmp.c backport-iwlwifi-dkms-11510/net/mac80211/mesh_hwmp.c --- backport-iwlwifi-dkms-11289/net/mac80211/mesh_hwmp.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/mesh_hwmp.c 2023-10-04 04:18:43.000000000 +0800 @@ -230,6 +230,8 @@ * Note: This function may be called with driver locks taken that the driver * also acquires in the TX path. To avoid a deadlock we don't transmit the * frame directly but add it to the pending queue instead. + * + * Returns: 0 on success */ int mesh_path_error_tx(struct ieee80211_sub_if_data *sdata, u8 ttl, const u8 *target, u32 target_sn, diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/mesh_pathtbl.c backport-iwlwifi-dkms-11510/net/mac80211/mesh_pathtbl.c --- backport-iwlwifi-dkms-11289/net/mac80211/mesh_pathtbl.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/mesh_pathtbl.c 2023-10-04 04:18:43.000000000 +0800 @@ -1,6 +1,7 @@ // SPDX-License-Identifier: GPL-2.0-only /* * Copyright (c) 2008, 2009 open80211s Ltd. + * Copyright (C) 2023 Intel Corporation * Author: Luis Carlos Cobo */ @@ -173,6 +174,11 @@ /** * mesh_path_move_to_queue - Move or copy frames from one mpath queue to another * + * @gate_mpath: An active mpath the frames will be sent to (i.e. the gate) + * @from_mpath: The failed mpath + * @copy: When true, copy all the frames to the new mpath queue. When false, + * move them. + * * This function is used to transfer or copy frames from an unresolved mpath to * a gate mpath. The function also adds the Address Extension field and * updates the next hop. @@ -181,11 +187,6 @@ * destination addresses are updated. * * The gate mpath must be an active mpath with a valid mpath->next_hop. - * - * @gate_mpath: An active mpath the frames will be sent to (i.e. the gate) - * @from_mpath: The failed mpath - * @copy: When true, copy all the frames to the new mpath queue. When false, - * move them. */ static void mesh_path_move_to_queue(struct mesh_path *gate_mpath, struct mesh_path *from_mpath, @@ -330,6 +331,8 @@ /** * mesh_path_add_gate - add the given mpath to a mesh gate to our path table * @mpath: gate path to add to table + * + * Returns: 0 on success, -EEXIST */ int mesh_path_add_gate(struct mesh_path *mpath) { @@ -388,6 +391,8 @@ /** * mesh_gate_num - number of gates known to this interface * @sdata: subif data + * + * Returns: The number of gates */ int mesh_gate_num(struct ieee80211_sub_if_data *sdata) { @@ -648,7 +653,7 @@ cache = &sdata->u.mesh.tx_cache; spin_lock_bh(&cache->walk_lock); - entry = rhashtable_lookup(&cache->rht, addr, fast_tx_rht_params); + entry = rhashtable_lookup_fast(&cache->rht, addr, fast_tx_rht_params); if (entry) mesh_fast_tx_entry_free(cache, entry); spin_unlock_bh(&cache->walk_lock); @@ -861,10 +866,9 @@ /** * mesh_path_flush_by_iface - Deletes all mesh paths associated with a given iface * - * This function deletes both mesh paths as well as mesh portal paths. - * * @sdata: interface data to match * + * This function deletes both mesh paths as well as mesh portal paths. */ void mesh_path_flush_by_iface(struct ieee80211_sub_if_data *sdata) { @@ -944,6 +948,8 @@ * queue to that gate's queue. If there are more than one gates, the frames * are copied from each gate to the next. After frames are copied, the * mpath queues are emptied onto the transmission queue. + * + * Returns: 0 on success, -EHOSTUNREACH */ int mesh_path_send_to_gates(struct mesh_path *mpath) { diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/mesh_plink.c backport-iwlwifi-dkms-11510/net/mac80211/mesh_plink.c --- backport-iwlwifi-dkms-11289/net/mac80211/mesh_plink.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/mesh_plink.c 2023-10-04 04:18:43.000000000 +0800 @@ -153,6 +153,8 @@ * selected if any non-HT peers are present in our MBSS. 20MHz-protection mode * is selected if all peers in our 20/40MHz MBSS support HT and at least one * HT20 peer is present. Otherwise no-protection mode is selected. + * + * Returns: BSS_CHANGED_HT or 0 for no change */ static u64 mesh_set_ht_prot_mode(struct ieee80211_sub_if_data *sdata) { @@ -362,7 +364,7 @@ * Mesh paths with this peer as next hop should be flushed * by the caller outside of plink_lock. * - * Returns beacon changed flag if the beacon content changed. + * Returns: beacon changed flag if the beacon content changed. * * Locking: the caller must hold sta->mesh->plink_lock */ @@ -390,6 +392,8 @@ * @sta: mesh peer link to deactivate * * All mesh paths with this peer as next hop will be flushed + * + * Returns: beacon changed flag if the beacon content changed. */ u64 mesh_plink_deactivate(struct sta_info *sta) { diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/mesh_ps.c backport-iwlwifi-dkms-11510/net/mac80211/mesh_ps.c --- backport-iwlwifi-dkms-11289/net/mac80211/mesh_ps.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/mesh_ps.c 2023-10-04 04:18:43.000000000 +0800 @@ -15,6 +15,8 @@ /** * mps_qos_null_get - create pre-addressed QoS Null frame for mesh powersave * @sta: the station to get the frame for + * + * Returns: A newly allocated SKB */ static struct sk_buff *mps_qos_null_get(struct sta_info *sta) { @@ -77,6 +79,8 @@ * * sets the non-peer power mode and triggers the driver PS (re-)configuration * Return BSS_CHANGED_BEACON if a beacon update is necessary. + * + * Returns: BSS_CHANGED_BEACON if a beacon update is in order. */ u64 ieee80211_mps_local_status_update(struct ieee80211_sub_if_data *sdata) { @@ -147,7 +151,7 @@ * * @sta: mesh STA * @pm: the power mode to set - * Return BSS_CHANGED_BEACON if a beacon update is in order. + * Returns: BSS_CHANGED_BEACON if a beacon update is in order. */ u64 ieee80211_mps_set_sta_local_pm(struct sta_info *sta, enum nl80211_mesh_power_mode pm) diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/mesh_sync.c backport-iwlwifi-dkms-11510/net/mac80211/mesh_sync.c --- backport-iwlwifi-dkms-11289/net/mac80211/mesh_sync.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/mesh_sync.c 2023-10-04 04:18:43.000000000 +0800 @@ -3,7 +3,7 @@ * Copyright 2011-2012, Pavel Zubarev * Copyright 2011-2012, Marco Porsch * Copyright 2011-2012, cozybit Inc. - * Copyright (C) 2021 Intel Corporation + * Copyright (C) 2021,2023 Intel Corporation */ #include "ieee80211_i.h" @@ -37,6 +37,8 @@ * mesh_peer_tbtt_adjusting - check if an mp is currently adjusting its TBTT * * @cfg: mesh config element from the mesh peer (or %NULL) + * + * Returns: If the mesh peer is currently adjusting its TBTT */ static bool mesh_peer_tbtt_adjusting(const struct ieee80211_meshconf_ie *cfg) { diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/mlme.c backport-iwlwifi-dkms-11510/net/mac80211/mlme.c --- backport-iwlwifi-dkms-11289/net/mac80211/mlme.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/mlme.c 2023-10-04 04:18:43.000000000 +0800 @@ -1,4 +1,3 @@ -// SPDX-License-Identifier: GPL-2.0-only /* * BSS client mode implementation * Copyright 2003-2008, Jouni Malinen @@ -176,7 +175,7 @@ static void run_again(struct ieee80211_sub_if_data *sdata, unsigned long timeout) { - sdata_assert_lock(sdata); + lockdep_assert_wiphy(sdata->local->hw.wiphy); if (!timer_pending(&sdata->u.mgd.timer) || time_before(timeout, sdata->u.mgd.timer.expires)) @@ -595,6 +594,7 @@ return ret; } + cfg80211_schedule_channels_check(sdata->dev); return 0; } @@ -1403,7 +1403,7 @@ assoc_data->ie, assoc_data->ie_len); - sdata_assert_lock(sdata); + lockdep_assert_wiphy(sdata->local->hw.wiphy); size = local->hw.extra_tx_headroom + sizeof(*mgmt) + /* bit too much but doesn't matter */ @@ -1588,6 +1588,7 @@ ifmgd->assoc_req_ies_len = pos - ie_start; + info.link_id = assoc_data->assoc_link_id; drv_mgd_prepare_tx(local, sdata, &info); IEEE80211_SKB_CB(skb)->flags |= IEEE80211_TX_INTFL_DONT_ENCRYPT; @@ -1691,15 +1692,13 @@ if (!ieee80211_sdata_running(sdata)) return; - sdata_lock(sdata); - mutex_lock(&local->mtx); - mutex_lock(&local->chanctx_mtx); + lockdep_assert_wiphy(local->hw.wiphy); if (!ifmgd->associated) - goto out; + return; if (!link->conf->csa_active) - goto out; + return; /* * using reservation isn't immediate as it may be deferred until later @@ -1715,7 +1714,7 @@ * reservations */ if (link->reserved_ready) - goto out; + return; ret = ieee80211_link_use_reserved_context(link); if (ret) { @@ -1724,10 +1723,8 @@ ret); wiphy_work_queue(sdata->local->hw.wiphy, &ifmgd->csa_connection_drop_work); - goto out; } - - goto out; + return; } if (!cfg80211_chandef_identical(&link->conf->chandef, @@ -1736,18 +1733,13 @@ "failed to finalize channel switch, disconnecting\n"); wiphy_work_queue(sdata->local->hw.wiphy, &ifmgd->csa_connection_drop_work); - goto out; + return; } link->u.mgd.csa_waiting_bcn = true; ieee80211_sta_reset_beacon_monitor(sdata); ieee80211_sta_reset_conn_monitor(sdata); - -out: - mutex_unlock(&local->chanctx_mtx); - mutex_unlock(&local->mtx); - sdata_unlock(sdata); } static void ieee80211_chswitch_post_beacon(struct ieee80211_link_data *link) @@ -1757,7 +1749,7 @@ struct ieee80211_if_managed *ifmgd = &sdata->u.mgd; int ret; - sdata_assert_lock(sdata); + lockdep_assert_wiphy(sdata->local->hw.wiphy); WARN_ON(!link->conf->csa_active); @@ -1791,30 +1783,28 @@ void ieee80211_chswitch_done(struct ieee80211_vif *vif, bool success, unsigned int link_id) { - struct ieee80211_link_data *link; struct ieee80211_sub_if_data *sdata = vif_to_sdata(vif); - struct ieee80211_link_data_managed *ifmgd; - trace_api_chswitch_done(sdata, success); + trace_api_chswitch_done(sdata, success, link_id); rcu_read_lock(); - link = rcu_dereference(sdata->link[link_id]); - if (WARN_ON(!link)) { - rcu_read_unlock(); - return; - } - - ifmgd = &link->u.mgd; - if (!success) { sdata_info(sdata, "driver channel switch failed, disconnecting\n"); wiphy_work_queue(sdata->local->hw.wiphy, &sdata->u.mgd.csa_connection_drop_work); } else { + struct ieee80211_link_data *link = + rcu_dereference(sdata->link[link_id]); + + if (WARN_ON(!link)) { + rcu_read_unlock(); + return; + } + wiphy_delayed_work_queue(sdata->local->hw.wiphy, - &ifmgd->chswitch_work, 0); + &link->u.mgd.chswitch_work, 0); } rcu_read_unlock(); @@ -1827,14 +1817,12 @@ struct ieee80211_sub_if_data *sdata = link->sdata; struct ieee80211_local *local = sdata->local; + lockdep_assert_wiphy(local->hw.wiphy); + if (!local->ops->abort_channel_switch) return; - mutex_lock(&local->mtx); - - mutex_lock(&local->chanctx_mtx); ieee80211_link_unreserve_chanctx(link); - mutex_unlock(&local->chanctx_mtx); if (link->csa_block_tx) ieee80211_wake_vif_queues(local, sdata, @@ -1843,8 +1831,6 @@ link->csa_block_tx = false; link->conf->csa_active = false; - mutex_unlock(&local->mtx); - drv_abort_channel_switch(sdata); } @@ -1867,7 +1853,7 @@ unsigned long timeout; int res; - sdata_assert_lock(sdata); + lockdep_assert_wiphy(local->hw.wiphy); if (!cbss) return; @@ -1889,7 +1875,7 @@ } if (res < 0) - goto lock_and_drop_connection; + goto drop_connection; if (beacon && link->conf->csa_active && !link->u.mgd.csa_waiting_bcn) { @@ -1911,7 +1897,7 @@ csa_ie.chandef.chan->center_freq, csa_ie.chandef.width, csa_ie.chandef.center_freq1, csa_ie.chandef.center_freq2); - goto lock_and_drop_connection; + goto drop_connection; } if (!cfg80211_chandef_usable(local->hw.wiphy, &csa_ie.chandef, @@ -1926,7 +1912,7 @@ csa_ie.chandef.width, csa_ie.chandef.center_freq1, csa_ie.chandef.freq1_offset, csa_ie.chandef.center_freq2); - goto lock_and_drop_connection; + goto drop_connection; } if (cfg80211_chandef_identical(&csa_ie.chandef, @@ -1949,10 +1935,8 @@ */ ieee80211_teardown_tdls_peers(sdata); - mutex_lock(&local->mtx); - mutex_lock(&local->chanctx_mtx); conf = rcu_dereference_protected(link->conf->chanctx_conf, - lockdep_is_held(&local->chanctx_mtx)); + lockdep_is_held(&local->hw.wiphy->mtx)); if (!conf) { sdata_info(sdata, "no channel context assigned to vif?, disconnecting\n"); @@ -1982,7 +1966,6 @@ res); goto drop_connection; } - mutex_unlock(&local->chanctx_mtx); link->conf->csa_active = true; link->csa_chandef = csa_ie.chandef; @@ -1993,7 +1976,6 @@ if (link->csa_block_tx) ieee80211_stop_vif_queues(local, sdata, IEEE80211_QUEUE_STOP_REASON_CSA); - mutex_unlock(&local->mtx); cfg80211_ch_switch_started_notify(sdata->dev, &csa_ie.chandef, link->link_id, csa_ie.count, @@ -2012,9 +1994,6 @@ &link->u.mgd.chswitch_work, timeout); return; - lock_and_drop_connection: - mutex_lock(&local->mtx); - mutex_lock(&local->chanctx_mtx); drop_connection: /* * This is just so that the disconnect flow will know that @@ -2028,8 +2007,6 @@ wiphy_work_queue(sdata->local->hw.wiphy, &ifmgd->csa_connection_drop_work); - mutex_unlock(&local->chanctx_mtx); - mutex_unlock(&local->mtx); } static bool @@ -2232,7 +2209,8 @@ conf->flags &= ~IEEE80211_CONF_PS; ieee80211_hw_config(local, IEEE80211_CONF_CHANGE_PS); del_timer_sync(&local->dynamic_ps_timer); - cancel_work_sync(&local->dynamic_ps_enable_work); + wiphy_work_cancel(local->hw.wiphy, + &local->dynamic_ps_enable_work); } } @@ -2329,7 +2307,8 @@ } } -void ieee80211_dynamic_ps_disable_work(struct work_struct *work) +void ieee80211_dynamic_ps_disable_work(struct wiphy *wiphy, + struct wiphy_work *work) { struct ieee80211_local *local = container_of(work, struct ieee80211_local, @@ -2346,7 +2325,8 @@ false); } -void ieee80211_dynamic_ps_enable_work(struct work_struct *work) +void ieee80211_dynamic_ps_enable_work(struct wiphy *wiphy, + struct wiphy_work *work) { struct ieee80211_local *local = container_of(work, struct ieee80211_local, @@ -2419,26 +2399,25 @@ { struct ieee80211_local *local = from_timer(local, t, dynamic_ps_timer); - ieee80211_queue_work(&local->hw, &local->dynamic_ps_enable_work); + wiphy_work_queue(local->hw.wiphy, &local->dynamic_ps_enable_work); } -void ieee80211_dfs_cac_timer_work(struct work_struct *work) +void ieee80211_dfs_cac_timer_work(struct wiphy *wiphy, struct wiphy_work *work) { - struct delayed_work *delayed_work = to_delayed_work(work); struct ieee80211_link_data *link = - container_of(delayed_work, struct ieee80211_link_data, - dfs_cac_timer_work); + container_of(work, struct ieee80211_link_data, + dfs_cac_timer_work.work); struct cfg80211_chan_def chandef = link->conf->chandef; struct ieee80211_sub_if_data *sdata = link->sdata; - mutex_lock(&sdata->local->mtx); + lockdep_assert_wiphy(sdata->local->hw.wiphy); + if (sdata->wdev.cac_started) { ieee80211_link_release_channel(link); cfg80211_cac_event(sdata->dev, &chandef, NL80211_RADAR_CAC_FINISHED, GFP_KERNEL); } - mutex_unlock(&sdata->local->mtx); } static bool @@ -2508,8 +2487,10 @@ ac); tx_tspec->action = TX_TSPEC_ACTION_NONE; ret = true; - schedule_delayed_work(&ifmgd->tx_tspec_wk, - tx_tspec->time_slice_start + HZ - now + 1); + wiphy_delayed_work_queue(local->hw.wiphy, + &ifmgd->tx_tspec_wk, + tx_tspec->time_slice_start + + HZ - now + 1); break; case TX_TSPEC_ACTION_NONE: /* nothing now */ @@ -2527,7 +2508,8 @@ BSS_CHANGED_QOS); } -static void ieee80211_sta_handle_tspec_ac_params_wk(struct work_struct *work) +static void ieee80211_sta_handle_tspec_ac_params_wk(struct wiphy *wiphy, + struct wiphy_work *work) { struct ieee80211_sub_if_data *sdata; @@ -2702,7 +2684,7 @@ static void __ieee80211_stop_poll(struct ieee80211_sub_if_data *sdata) { - lockdep_assert_held(&sdata->local->mtx); + lockdep_assert_wiphy(sdata->local->hw.wiphy); sdata->u.mgd.flags &= ~IEEE80211_STA_CONNECTION_POLL; ieee80211_run_deferred_scan(sdata->local); @@ -2710,9 +2692,9 @@ static void ieee80211_stop_poll(struct ieee80211_sub_if_data *sdata) { - mutex_lock(&sdata->local->mtx); + lockdep_assert_wiphy(sdata->local->hw.wiphy); + __ieee80211_stop_poll(sdata); - mutex_unlock(&sdata->local->mtx); } static u64 ieee80211_handle_bss_capability(struct ieee80211_link_data *link, @@ -2830,6 +2812,8 @@ u64 vif_changed = BSS_CHANGED_ASSOC; unsigned int link_id; + lockdep_assert_wiphy(local->hw.wiphy); + sdata->u.mgd.associated = true; for (link_id = 0; link_id < IEEE80211_MLD_MAX_NUM_LINKS; link_id++) { @@ -2891,9 +2875,7 @@ vif_changed | changed[0]); } - mutex_lock(&local->iflist_mtx); ieee80211_recalc_ps(local); - mutex_unlock(&local->iflist_mtx); /* leave this here to not change ordering in non-MLO cases */ if (!ieee80211_vif_is_mld(&sdata->vif)) @@ -2915,7 +2897,7 @@ .subtype = stype, }; - sdata_assert_lock(sdata); + lockdep_assert_wiphy(local->hw.wiphy); if (WARN_ON_ONCE(tx && !frame_buf)) return; @@ -2966,9 +2948,22 @@ * deauthentication frame by calling mgd_prepare_tx, if the * driver requested so. */ - if (ieee80211_hw_check(&local->hw, DEAUTH_NEED_MGD_TX_PREP) && - !sdata->deflink.u.mgd.have_beacon) { - drv_mgd_prepare_tx(sdata->local, sdata, &info); + if (ieee80211_hw_check(&local->hw, DEAUTH_NEED_MGD_TX_PREP)) { + for (link_id = 0; link_id < ARRAY_SIZE(sdata->link); + link_id++) { + struct ieee80211_link_data *link; + + link = sdata_dereference(sdata->link[link_id], + sdata); + if (!link) + continue; + if (link->u.mgd.have_beacon) + break; + } + if (link_id == IEEE80211_MLD_MAX_NUM_LINKS) { + info.link_id = ffs(sdata->vif.active_links) - 1; + drv_mgd_prepare_tx(sdata->local, sdata, &info); + } } ieee80211_send_deauth_disassoc(sdata, sdata->vif.cfg.ap_addr, @@ -3024,7 +3019,7 @@ sdata->deflink.ap_power_level = IEEE80211_UNSET_POWER_LEVEL; del_timer_sync(&local->dynamic_ps_timer); - cancel_work_sync(&local->dynamic_ps_enable_work); + wiphy_work_cancel(local->hw.wiphy, &local->dynamic_ps_enable_work); /* Disable ARP filtering */ if (sdata->vif.cfg.arp_addr_cnt) @@ -3056,7 +3051,6 @@ ifmgd->flags = 0; sdata->deflink.u.mgd.conn_flags = 0; - mutex_lock(&local->mtx); for (link_id = 0; link_id < ARRAY_SIZE(sdata->link); link_id++) { struct ieee80211_link_data *link; @@ -3075,11 +3069,10 @@ IEEE80211_QUEUE_STOP_REASON_CSA); sdata->deflink.csa_block_tx = false; } - mutex_unlock(&local->mtx); /* existing TX TSPEC sessions no longer exist */ memset(ifmgd->tx_tspec, 0, sizeof(ifmgd->tx_tspec)); - cancel_delayed_work_sync(&ifmgd->tx_tspec_wk); + wiphy_delayed_work_cancel(local->hw.wiphy, &ifmgd->tx_tspec_wk); sdata->vif.bss_conf.pwr_reduction = 0; sdata->vif.bss_conf.tx_pwr_env_num = 0; @@ -3097,18 +3090,17 @@ struct ieee80211_if_managed *ifmgd = &sdata->u.mgd; struct ieee80211_local *local = sdata->local; - mutex_lock(&local->mtx); + lockdep_assert_wiphy(local->hw.wiphy); + if (!(ifmgd->flags & IEEE80211_STA_CONNECTION_POLL)) - goto out; + return; __ieee80211_stop_poll(sdata); - mutex_lock(&local->iflist_mtx); ieee80211_recalc_ps(local); - mutex_unlock(&local->iflist_mtx); if (ieee80211_hw_check(&sdata->local->hw, CONNECTION_MONITOR)) - goto out; + return; /* * We've received a probe response, but are not sure whether @@ -3120,8 +3112,6 @@ mod_timer(&ifmgd->conn_mon_timer, round_jiffies_up(jiffies + IEEE80211_CONNECTION_IDLE_TIME)); -out: - mutex_unlock(&local->mtx); } static void ieee80211_sta_tx_wmm_ac_notify(struct ieee80211_sub_if_data *sdata, @@ -3150,7 +3140,8 @@ if (tx_tspec->downgraded) { tx_tspec->action = TX_TSPEC_ACTION_STOP_DOWNGRADE; - schedule_delayed_work(&ifmgd->tx_tspec_wk, 0); + wiphy_delayed_work_queue(sdata->local->hw.wiphy, + &ifmgd->tx_tspec_wk, 0); } } @@ -3162,7 +3153,8 @@ if (tx_tspec->consumed_tx_time >= tx_tspec->admitted_time) { tx_tspec->downgraded = true; tx_tspec->action = TX_TSPEC_ACTION_DOWNGRADE; - schedule_delayed_work(&ifmgd->tx_tspec_wk, 0); + wiphy_delayed_work_queue(sdata->local->hw.wiphy, + &ifmgd->tx_tspec_wk, 0); } } @@ -3203,6 +3195,8 @@ u8 unicast_limit = max(1, max_probe_tries - 3); struct sta_info *sta; + lockdep_assert_wiphy(sdata->local->hw.wiphy); + if (WARN_ON(ieee80211_vif_is_mld(&sdata->vif))) return; @@ -3224,11 +3218,9 @@ ifmgd->probe_send_count++; if (dst) { - mutex_lock(&sdata->local->sta_mtx); sta = sta_info_get(sdata, dst); if (!WARN_ON(!sta)) ieee80211_check_fast_rx(sta); - mutex_unlock(&sdata->local->sta_mtx); } if (ieee80211_hw_check(&sdata->local->hw, REPORTS_TX_ACK_STATUS)) { @@ -3251,29 +3243,24 @@ struct ieee80211_if_managed *ifmgd = &sdata->u.mgd; bool already = false; + lockdep_assert_wiphy(sdata->local->hw.wiphy); + if (WARN_ON_ONCE(ieee80211_vif_is_mld(&sdata->vif))) return; if (!ieee80211_sdata_running(sdata)) return; - sdata_lock(sdata); - if (!ifmgd->associated) - goto out; - - mutex_lock(&sdata->local->mtx); + return; - if (sdata->local->tmp_channel || sdata->local->scanning) { - mutex_unlock(&sdata->local->mtx); - goto out; - } + if (sdata->local->tmp_channel || sdata->local->scanning) + return; if (sdata->local->suspending) { /* reschedule after resume */ - mutex_unlock(&sdata->local->mtx); ieee80211_reset_ap_probe(sdata); - goto out; + return; } if (beacon) { @@ -3300,19 +3287,13 @@ ifmgd->flags |= IEEE80211_STA_CONNECTION_POLL; - mutex_unlock(&sdata->local->mtx); - if (already) - goto out; + return; - mutex_lock(&sdata->local->iflist_mtx); ieee80211_recalc_ps(sdata->local); - mutex_unlock(&sdata->local->iflist_mtx); ifmgd->probe_send_count = 0; ieee80211_mgd_probe_ap_send(sdata); - out: - sdata_unlock(sdata); } struct sk_buff *ieee80211_ap_probereq_get(struct ieee80211_hw *hw, @@ -3325,12 +3306,12 @@ const struct element *ssid; int ssid_len; + lockdep_assert_wiphy(sdata->local->hw.wiphy); + if (WARN_ON(sdata->vif.type != NL80211_IFTYPE_STATION || ieee80211_vif_is_mld(&sdata->vif))) return NULL; - sdata_assert_lock(sdata); - if (ifmgd->associated) cbss = sdata->deflink.u.mgd.bss; else if (ifmgd->auth_data) @@ -3384,11 +3365,10 @@ u8 frame_buf[IEEE80211_DEAUTH_FRAME_LEN]; bool tx; - sdata_lock(sdata); - if (!ifmgd->associated) { - sdata_unlock(sdata); + lockdep_assert_wiphy(local->hw.wiphy); + + if (!ifmgd->associated) return; - } /* in MLO assume we have a link where we can TX the frame */ tx = ieee80211_vif_is_mld(&sdata->vif) || @@ -3422,7 +3402,6 @@ WLAN_REASON_DEAUTH_LEAVING : WLAN_REASON_DISASSOC_DUE_TO_INACTIVITY, tx, frame_buf); - mutex_lock(&local->mtx); /* the other links will be destroyed */ sdata->vif.bss_conf.csa_active = false; sdata->deflink.u.mgd.csa_waiting_bcn = false; @@ -3431,14 +3410,11 @@ IEEE80211_QUEUE_STOP_REASON_CSA); sdata->deflink.csa_block_tx = false; } - mutex_unlock(&local->mtx); ieee80211_report_disconnect(sdata, frame_buf, sizeof(frame_buf), tx, WLAN_REASON_DISASSOC_DUE_TO_INACTIVITY, ifmgd->reconnect); ifmgd->reconnect = false; - - sdata_unlock(sdata); } static void ieee80211_beacon_connection_loss_work(struct wiphy *wiphy, @@ -3522,7 +3498,7 @@ { struct ieee80211_mgd_auth_data *auth_data = sdata->u.mgd.auth_data; - sdata_assert_lock(sdata); + lockdep_assert_wiphy(sdata->local->hw.wiphy); if (!assoc) { /* @@ -3540,10 +3516,8 @@ BSS_CHANGED_BSSID); sdata->u.mgd.flags = 0; - mutex_lock(&sdata->local->mtx); ieee80211_link_release_channel(&sdata->deflink); ieee80211_vif_set_links(sdata, 0, 0); - mutex_unlock(&sdata->local->mtx); } cfg80211_put_bss(sdata->local->hw.wiphy, auth_data->bss); @@ -3563,7 +3537,7 @@ { struct ieee80211_mgd_assoc_data *assoc_data = sdata->u.mgd.assoc_data; - sdata_assert_lock(sdata); + lockdep_assert_wiphy(sdata->local->hw.wiphy); if (status != ASSOC_SUCCESS) { /* @@ -3599,10 +3573,8 @@ cfg80211_assoc_failure(sdata->dev, &data); } - mutex_lock(&sdata->local->mtx); ieee80211_link_release_channel(&sdata->deflink); ieee80211_vif_set_links(sdata, 0, 0); - mutex_unlock(&sdata->local->mtx); } kfree(assoc_data); @@ -3619,6 +3591,7 @@ u32 tx_flags = 0; struct ieee80211_prep_tx_info info = { .subtype = IEEE80211_STYPE_AUTH, + .link_id = auth_data->link_id, }; pos = mgmt->u.auth.variable; @@ -3644,7 +3617,8 @@ struct ieee80211_if_managed *ifmgd = &sdata->u.mgd; const u8 *ap_addr = ifmgd->auth_data->ap_addr; struct sta_info *sta; - bool result = true; + + lockdep_assert_wiphy(sdata->local->hw.wiphy); sdata_info(sdata, "authenticated\n"); ifmgd->auth_data->done = true; @@ -3653,22 +3627,17 @@ run_again(sdata, ifmgd->auth_data->timeout); /* move station state to auth */ - mutex_lock(&sdata->local->sta_mtx); sta = sta_info_get(sdata, ap_addr); if (!sta) { WARN_ONCE(1, "%s: STA %pM not found", sdata->name, ap_addr); - result = false; - goto out; + return false; } if (sta_info_move_state(sta, IEEE80211_STA_AUTH)) { sdata_info(sdata, "failed moving %pM to auth\n", ap_addr); - result = false; - goto out; + return false; } -out: - mutex_unlock(&sdata->local->sta_mtx); - return result; + return true; } static void ieee80211_rx_mgmt_auth(struct ieee80211_sub_if_data *sdata, @@ -3684,7 +3653,7 @@ .subtype = IEEE80211_STYPE_AUTH, }; - sdata_assert_lock(sdata); + lockdep_assert_wiphy(sdata->local->hw.wiphy); if (len < 24 + 6) return; @@ -3842,7 +3811,7 @@ struct ieee80211_if_managed *ifmgd = &sdata->u.mgd; u16 reason_code = le16_to_cpu(mgmt->u.deauth.reason_code); - sdata_assert_lock(sdata); + lockdep_assert_wiphy(sdata->local->hw.wiphy); if (len < 24 + 2) return; @@ -3886,7 +3855,7 @@ struct ieee80211_if_managed *ifmgd = &sdata->u.mgd; u16 reason_code; - sdata_assert_lock(sdata); + lockdep_assert_wiphy(sdata->local->hw.wiphy); if (len < 24 + 2) return; @@ -4839,6 +4808,7 @@ static int ieee80211_prep_channel(struct ieee80211_sub_if_data *sdata, struct ieee80211_link_data *link, struct cfg80211_bss *cbss, + bool mlo, ieee80211_conn_flags_t *conn_flags) { struct ieee80211_local *local = sdata->local; @@ -4852,6 +4822,7 @@ struct cfg80211_chan_def chandef; bool is_6ghz = cbss->channel->band == NL80211_BAND_6GHZ; bool is_5ghz = cbss->channel->band == NL80211_BAND_5GHZ; + bool supports_mlo = false; struct ieee80211_bss *bss = (void *)cbss->priv; struct ieee80211_elems_parse_params parse_params = { .link_id = -1, @@ -4863,6 +4834,8 @@ u32 i; bool have_80mhz; + lockdep_assert_wiphy(local->hw.wiphy); + rcu_read_lock(); ies = rcu_dereference(cbss->ies); @@ -5003,6 +4976,8 @@ ieee80211_mle_type_ok(eht_ml_elem->data + 1, IEEE80211_ML_CONTROL_TYPE_BASIC, eht_ml_elem->datalen - 1)) { + supports_mlo = true; + sdata->vif.cfg.eml_cap = ieee80211_mle_get_eml_cap(eht_ml_elem->data + 1); sdata->vif.cfg.eml_med_sync_delay = @@ -5058,13 +5033,17 @@ return -EINVAL; } + if (mlo && !supports_mlo) { + sdata_info(sdata, "Rejecting MLO as it is not supported by AP\n"); + return -EINVAL; + } + if (!link) return 0; /* will change later if needed */ link->smps_mode = IEEE80211_SMPS_OFF; - mutex_lock(&local->mtx); /* * If this fails (possibly due to channel context sharing * on incompatible channels, e.g. 80+80 and 160 sharing the @@ -5085,7 +5064,6 @@ IEEE80211_CHANCTX_SHARED); } out: - mutex_unlock(&local->mtx); return ret; } @@ -5137,7 +5115,7 @@ u16 valid_links = 0, dormant_links = 0; int err; - mutex_lock(&sdata->local->sta_mtx); + lockdep_assert_wiphy(sdata->local->hw.wiphy); /* * station info was already allocated and inserted before * the association and should be available to us @@ -5152,9 +5130,10 @@ continue; valid_links |= BIT(link_id); - if (assoc_data->link[link_id].disabled) { + if (assoc_data->link[link_id].disabled) dormant_links |= BIT(link_id); - } else if (link_id != assoc_data->assoc_link_id) { + + if (link_id != assoc_data->assoc_link_id) { err = ieee80211_sta_allocate_link(sta, link_id); if (err) goto out_err; @@ -5169,7 +5148,7 @@ struct ieee80211_link_data *link; struct link_sta_info *link_sta; - if (!cbss || assoc_data->link[link_id].disabled) + if (!cbss) continue; link = sdata_dereference(sdata->link[link_id], sdata); @@ -5185,7 +5164,7 @@ " (assoc)" : ""); link_sta = rcu_dereference_protected(sta->link[link_id], - lockdep_is_held(&local->sta_mtx)); + lockdep_is_held(&local->hw.wiphy->mtx)); if (WARN_ON(!link_sta)) goto out_err; @@ -5208,7 +5187,7 @@ link->conf->dtim_period = link->u.mgd.dtim_period ?: 1; if (link_id != assoc_data->assoc_link_id) { - err = ieee80211_prep_channel(sdata, link, cbss, + err = ieee80211_prep_channel(sdata, link, cbss, true, &link->u.mgd.conn_flags); if (err) { link_info(link, "prep_channel failed\n"); @@ -5272,8 +5251,6 @@ if (sdata->wdev.use_4addr) drv_sta_set_4addr(local, sdata, &sta->sta, true); - mutex_unlock(&sdata->local->sta_mtx); - ieee80211_set_associated(sdata, assoc_data, changed); /* @@ -5293,7 +5270,6 @@ return true; out_err: eth_zero_addr(sdata->vif.cfg.ap_addr); - mutex_unlock(&sdata->local->sta_mtx); return false; } @@ -5325,7 +5301,7 @@ u8 ap_mld_addr[ETH_ALEN] __aligned(2); unsigned int link_id; - sdata_assert_lock(sdata); + lockdep_assert_wiphy(sdata->local->hw.wiphy); if (!assoc_data) return; @@ -5525,7 +5501,7 @@ struct ieee80211_bss *bss; struct ieee80211_channel *channel; - sdata_assert_lock(sdata); + lockdep_assert_wiphy(sdata->local->hw.wiphy); channel = ieee80211_get_channel_khz(local->hw.wiphy, ieee80211_rx_status_to_khz(rx_status)); @@ -5552,7 +5528,7 @@ ifmgd = &sdata->u.mgd; - sdata_assert_lock(sdata); + lockdep_assert_wiphy(sdata->local->hw.wiphy); /* * According to Draft P802.11ax D6.0 clause 26.17.2.3.2: @@ -5754,7 +5730,8 @@ return true; } -static void ieee80211_ml_reconf_work(struct work_struct *work) +static void ieee80211_ml_reconf_work(struct wiphy *wiphy, + struct wiphy_work *work) { struct ieee80211_sub_if_data *sdata = container_of(work, struct ieee80211_sub_if_data, @@ -5787,8 +5764,7 @@ BIT(ffs(new_valid_links & ~sdata->vif.dormant_links) - 1); - ret = ieee80211_set_active_links(&sdata->vif, - new_active_links); + ret = ieee80211_set_active_links(&sdata->vif, new_active_links); if (ret) { sdata_info(sdata, "Failed setting active links\n"); @@ -5803,15 +5779,13 @@ if (ret) sdata_info(sdata, "Failed setting valid links\n"); + ieee80211_vif_cfg_change_notify(sdata, BSS_CHANGED_MLD_VALID_LINKS); + out: - if (!ret) { - sdata_lock(sdata); - cfg80211_cqm_links_state_change_notify(sdata->dev, - sdata->u.mgd.removed_links); - sdata_unlock(sdata); - } else { + if (!ret) + cfg80211_links_removed(sdata->dev, sdata->u.mgd.removed_links); + else __ieee80211_disconnect(sdata); - } sdata->u.mgd.removed_links = 0; } @@ -5883,7 +5857,8 @@ /* In case the removal was cancelled, abort it */ if (sdata->u.mgd.removed_links) { sdata->u.mgd.removed_links = 0; - cancel_delayed_work(&sdata->u.mgd.ml_reconf_work); + wiphy_delayed_work_cancel(sdata->local->hw.wiphy, + &sdata->u.mgd.ml_reconf_work); } return; } @@ -5909,7 +5884,9 @@ } sdata->u.mgd.removed_links = removed_links; - schedule_delayed_work(&sdata->u.mgd.ml_reconf_work, TU_TO_JIFFIES(delay)); + wiphy_delayed_work_queue(sdata->local->hw.wiphy, + &sdata->u.mgd.ml_reconf_work, + TU_TO_JIFFIES(delay)); } static void ieee80211_tid_to_link_map_work(struct wiphy *wiphy, @@ -5919,6 +5896,7 @@ struct ieee80211_sub_if_data *sdata = container_of(work, struct ieee80211_sub_if_data, u.mgd.t2l_map_work.work); + int ret; new_active_links = sdata->u.mgd.t2l_map_info.map & sdata->vif.valid_links; @@ -5929,14 +5907,19 @@ return; } + ieee80211_vif_set_links(sdata, sdata->vif.valid_links, 0); new_active_links = BIT(ffs(new_active_links) - 1); ieee80211_set_active_links(&sdata->vif, new_active_links); - ieee80211_vif_set_links(sdata, sdata->vif.valid_links, - new_dormant_links); - sdata_lock(sdata); + + ret = ieee80211_vif_set_links(sdata, sdata->vif.valid_links, + new_dormant_links); + sdata->u.mgd.t2l_map_info.active = true; sdata->u.mgd.t2l_map_info.switch_time = 0; - sdata_unlock(sdata); + + if (!ret) + ieee80211_vif_cfg_change_notify(sdata, + BSS_CHANGED_MLD_VALID_LINKS); } static u16 ieee80211_get_t2l_map(u8 bm_size, u8 *data) @@ -6028,8 +6011,6 @@ u8 i; int ret; - sdata_assert_lock(sdata); - if (!ieee80211_vif_is_mld(&sdata->vif)) return; @@ -6051,6 +6032,8 @@ sdata_info(sdata, "Failed setting valid/dormant links\n"); return; } + ieee80211_vif_cfg_change_notify(sdata, + BSS_CHANGED_MLD_VALID_LINKS); } memset(&sdata->u.mgd.t2l_map_info, 0, sizeof(sdata->u.mgd.t2l_map_info)); @@ -6122,7 +6105,7 @@ .from_ap = true, }; - sdata_assert_lock(sdata); + lockdep_assert_wiphy(local->hw.wiphy); /* Process beacon from the current BSS */ bssid = ieee80211_get_bssid(hdr, len, sdata->vif.type); @@ -6338,9 +6321,7 @@ changed |= BSS_CHANGED_BEACON_INFO; link->u.mgd.have_beacon = true; - mutex_lock(&local->iflist_mtx); ieee80211_recalc_ps(local); - mutex_unlock(&local->iflist_mtx); ieee80211_recalc_ps_vif(sdata); } @@ -6357,16 +6338,13 @@ le16_to_cpu(mgmt->u.beacon.capab_info), erp_valid, erp_value); - mutex_lock(&local->sta_mtx); sta = sta_info_get(sdata, sdata->vif.cfg.ap_addr); if (WARN_ON(!sta)) { - mutex_unlock(&local->sta_mtx); goto free; } link_sta = rcu_dereference_protected(sta->link[link->link_id], - lockdep_is_held(&local->sta_mtx)); + lockdep_is_held(&local->hw.wiphy->mtx)); if (WARN_ON(!link_sta)) { - mutex_unlock(&local->sta_mtx); goto free; } @@ -6382,7 +6360,6 @@ elems->vht_operation, elems->he_operation, elems->eht_operation, elems->s1g_oper, bssid, &changed)) { - mutex_unlock(&local->sta_mtx); sdata_info(sdata, "failed to follow AP %pM bandwidth change, disconnect\n", bssid); @@ -6400,7 +6377,6 @@ ieee80211_vht_handle_opmode(sdata, link_sta, *elems->opmode_notif, rx_status->band); - mutex_unlock(&local->sta_mtx); changed |= ieee80211_handle_pwr_constr(link, chan, mgmt, elems->country_elem, @@ -6440,17 +6416,17 @@ struct ieee80211_hdr *hdr; u16 fc; + lockdep_assert_wiphy(sdata->local->hw.wiphy); + rx_status = (struct ieee80211_rx_status *) skb->cb; hdr = (struct ieee80211_hdr *) skb->data; fc = le16_to_cpu(hdr->frame_control); - sdata_lock(sdata); switch (fc & IEEE80211_FCTL_STYPE) { case IEEE80211_STYPE_S1G_BEACON: ieee80211_rx_mgmt_beacon(link, hdr, skb->len, rx_status); break; } - sdata_unlock(sdata); } void ieee80211_sta_rx_queued_mgmt(struct ieee80211_sub_if_data *sdata, @@ -6462,17 +6438,17 @@ u16 fc; int ies_len; + lockdep_assert_wiphy(sdata->local->hw.wiphy); + rx_status = (struct ieee80211_rx_status *) skb->cb; mgmt = (struct ieee80211_mgmt *) skb->data; fc = le16_to_cpu(mgmt->frame_control); - sdata_lock(sdata); - if (rx_status->link_valid) { link = sdata_dereference(sdata->link[rx_status->link_id], sdata); if (!link) - goto out; + return; } switch (fc & IEEE80211_FCTL_STYPE) { @@ -6555,8 +6531,6 @@ } break; } -out: - sdata_unlock(sdata); } static void ieee80211_sta_timer(struct timer_list *t) @@ -6591,7 +6565,7 @@ .subtype = IEEE80211_STYPE_AUTH, }; - sdata_assert_lock(sdata); + lockdep_assert_wiphy(sdata->local->hw.wiphy); if (WARN_ON_ONCE(!auth_data)) return -EINVAL; @@ -6614,6 +6588,7 @@ if (auth_data->algorithm == WLAN_AUTH_SAE) info.duration = jiffies_to_msecs(IEEE80211_AUTH_TIMEOUT_SAE); + info.link_id = auth_data->link_id; drv_mgd_prepare_tx(local, sdata, &info); sdata_info(sdata, "send auth to %pM (try %d/%d)\n", @@ -6660,7 +6635,7 @@ struct ieee80211_local *local = sdata->local; int ret; - sdata_assert_lock(sdata); + lockdep_assert_wiphy(sdata->local->hw.wiphy); assoc_data->tries++; if (assoc_data->tries > IEEE80211_ASSOC_MAX_TRIES) { @@ -6716,7 +6691,7 @@ struct ieee80211_local *local = sdata->local; struct ieee80211_if_managed *ifmgd = &sdata->u.mgd; - sdata_lock(sdata); + lockdep_assert_wiphy(sdata->local->hw.wiphy); if (ifmgd->status_received) { __le16 fc = ifmgd->status_fc; @@ -6851,8 +6826,6 @@ WLAN_REASON_DISASSOC_DUE_TO_INACTIVITY, false); } } - - sdata_unlock(sdata); } static void ieee80211_sta_bcn_mon_timer(struct timer_list *t) @@ -6908,10 +6881,11 @@ return; } - ieee80211_queue_work(&local->hw, &ifmgd->monitor_work); + wiphy_work_queue(local->hw.wiphy, &sdata->u.mgd.monitor_work); } -static void ieee80211_sta_monitor_work(struct work_struct *work) +static void ieee80211_sta_monitor_work(struct wiphy *wiphy, + struct wiphy_work *work) { struct ieee80211_sub_if_data *sdata = container_of(work, struct ieee80211_sub_if_data, @@ -6927,8 +6901,8 @@ /* let's probe the connection once */ if (!ieee80211_hw_check(&sdata->local->hw, CONNECTION_MONITOR)) - ieee80211_queue_work(&sdata->local->hw, - &sdata->u.mgd.monitor_work); + wiphy_work_queue(sdata->local->hw.wiphy, + &sdata->u.mgd.monitor_work); } } @@ -6938,7 +6912,7 @@ struct ieee80211_if_managed *ifmgd = &sdata->u.mgd; u8 frame_buf[IEEE80211_DEAUTH_FRAME_LEN]; - sdata_lock(sdata); + lockdep_assert_wiphy(sdata->local->hw.wiphy); if (ifmgd->auth_data || ifmgd->assoc_data) { const u8 *ap_addr = ifmgd->auth_data ? @@ -6990,8 +6964,6 @@ memcpy(bssid, sdata->vif.cfg.ap_addr, ETH_ALEN); ieee80211_mgd_deauth(sdata, &req); } - - sdata_unlock(sdata); } #endif @@ -6999,11 +6971,10 @@ { struct ieee80211_if_managed *ifmgd = &sdata->u.mgd; - sdata_lock(sdata); - if (!ifmgd->associated) { - sdata_unlock(sdata); + lockdep_assert_wiphy(sdata->local->hw.wiphy); + + if (!ifmgd->associated) return; - } if (sdata->flags & IEEE80211_SDATA_DISCONNECT_RESUME) { sdata->flags &= ~IEEE80211_SDATA_DISCONNECT_RESUME; @@ -7011,7 +6982,6 @@ ieee80211_sta_connection_lost(sdata, WLAN_REASON_UNSPECIFIED, true); - sdata_unlock(sdata); return; } @@ -7021,12 +6991,9 @@ ieee80211_sta_connection_lost(sdata, WLAN_REASON_UNSPECIFIED, true); - sdata_unlock(sdata); return; } - sdata_unlock(sdata); - ieee80211_send_nullfunc(sdata->local, sdata, false); } @@ -7037,10 +7004,8 @@ container_of(work, struct ieee80211_link_data, u.mgd.request_smps_work); - sdata_lock(link->sdata); __ieee80211_request_smps_mgd(link->sdata, link, link->u.mgd.driver_smps_mode); - sdata_unlock(link->sdata); } /* interface setup */ @@ -7048,19 +7013,20 @@ { struct ieee80211_if_managed *ifmgd = &sdata->u.mgd; - INIT_WORK(&ifmgd->monitor_work, ieee80211_sta_monitor_work); + wiphy_work_init(&ifmgd->monitor_work, ieee80211_sta_monitor_work); wiphy_work_init(&ifmgd->beacon_connection_loss_work, ieee80211_beacon_connection_loss_work); wiphy_work_init(&ifmgd->csa_connection_drop_work, ieee80211_csa_connection_drop_work); - INIT_DELAYED_WORK(&ifmgd->tdls_peer_del_work, - ieee80211_tdls_peer_del_work); - INIT_DELAYED_WORK(&ifmgd->ml_reconf_work, ieee80211_ml_reconf_work); + wiphy_delayed_work_init(&ifmgd->tdls_peer_del_work, + ieee80211_tdls_peer_del_work); + wiphy_delayed_work_init(&ifmgd->ml_reconf_work, + ieee80211_ml_reconf_work); timer_setup(&ifmgd->timer, ieee80211_sta_timer, 0); timer_setup(&ifmgd->bcn_mon_timer, ieee80211_sta_bcn_mon_timer, 0); timer_setup(&ifmgd->conn_mon_timer, ieee80211_sta_conn_mon_timer, 0); - INIT_DELAYED_WORK(&ifmgd->tx_tspec_wk, - ieee80211_sta_handle_tspec_ac_params_wk); + wiphy_delayed_work_init(&ifmgd->tx_tspec_wk, + ieee80211_sta_handle_tspec_ac_params_wk); wiphy_delayed_work_init(&ifmgd->t2l_map_work, ieee80211_tid_to_link_map_work); @@ -7074,6 +7040,16 @@ ifmgd->orig_teardown_skb = NULL; } +static void ieee80211_recalc_smps_work(struct wiphy *wiphy, + struct wiphy_work *work) +{ + struct ieee80211_link_data *link = + container_of(work, struct ieee80211_link_data, + u.mgd.recalc_smps); + + ieee80211_recalc_smps(link->sdata, link); +} + void ieee80211_mgd_setup_link(struct ieee80211_link_data *link) { struct ieee80211_sub_if_data *sdata = link->sdata; @@ -7086,6 +7062,8 @@ wiphy_work_init(&link->u.mgd.request_smps_work, ieee80211_request_smps_mgd_work); + wiphy_work_init(&link->u.mgd.recalc_smps, + ieee80211_recalc_smps_work); if (local->hw.wiphy->features & NL80211_FEATURE_DYNAMIC_SMPS) link->u.mgd.req_smps = IEEE80211_SMPS_AUTOMATIC; else @@ -7249,7 +7227,7 @@ } if (new_sta || override) { - err = ieee80211_prep_channel(sdata, link, cbss, + err = ieee80211_prep_channel(sdata, link, cbss, mlo, &link->u.mgd.conn_flags); if (err) { if (new_sta) @@ -7307,6 +7285,8 @@ int err; bool cont_auth; + lockdep_assert_wiphy(sdata->local->hw.wiphy); + /* prepare auth data structure */ switch (req->auth_type) { @@ -7348,9 +7328,11 @@ ecsa_elem = ieee80211_bss_get_elem(req->bss, WLAN_EID_EXT_CHANSWITCH_ANN); if ((csa_elem && - csa_elem->datalen == sizeof(struct ieee80211_channel_sw_ie)) || + csa_elem->datalen == sizeof(struct ieee80211_channel_sw_ie) && + ((struct ieee80211_channel_sw_ie *)csa_elem->data)->count != 0) || (ecsa_elem && - ecsa_elem->datalen == sizeof(struct ieee80211_ext_chansw_ie))) { + ecsa_elem->datalen == sizeof(struct ieee80211_ext_chansw_ie) && + ((struct ieee80211_ext_chansw_ie *)ecsa_elem->data)->count != 0)) { rcu_read_unlock(); sdata_info(sdata, "AP is in CSA process, reject auth\n"); return -EINVAL; @@ -7476,9 +7458,7 @@ eth_zero_addr(sdata->deflink.u.mgd.bssid); ieee80211_link_info_change_notify(sdata, &sdata->deflink, BSS_CHANGED_BSSID); - mutex_lock(&sdata->local->mtx); ieee80211_link_release_channel(&sdata->deflink); - mutex_unlock(&sdata->local->mtx); } ifmgd->auth_data = NULL; kfree(auth_data); @@ -7700,9 +7680,11 @@ csa_elem = ieee80211_bss_get_elem(cbss, WLAN_EID_CHANNEL_SWITCH); ecsa_elem = ieee80211_bss_get_elem(cbss, WLAN_EID_EXT_CHANSWITCH_ANN); if ((csa_elem && - csa_elem->datalen == sizeof(struct ieee80211_channel_sw_ie)) || + csa_elem->datalen == sizeof(struct ieee80211_channel_sw_ie) && + ((struct ieee80211_channel_sw_ie *)csa_elem->data)->count != 0) || (ecsa_elem && - ecsa_elem->datalen == sizeof(struct ieee80211_ext_chansw_ie))) { + ecsa_elem->datalen == sizeof(struct ieee80211_ext_chansw_ie) && + ((struct ieee80211_ext_chansw_ie *)ecsa_elem->data)->count != 0)) { sdata_info(sdata, "AP is in CSA process, reject assoc\n"); rcu_read_unlock(); kfree(assoc_data); @@ -7769,7 +7751,10 @@ match = ether_addr_equal(ifmgd->auth_data->ap_addr, assoc_data->ap_addr) && ifmgd->auth_data->link_id == req->link_id; - ieee80211_destroy_auth_data(sdata, match); + + /* Cleanup is delayed if auth_data matches */ + if (!match) + ieee80211_destroy_auth_data(sdata, false); } /* prepare assoc data */ @@ -7950,10 +7935,13 @@ if (i == assoc_data->assoc_link_id) continue; /* only calculate the flags, hence link == NULL */ - err = ieee80211_prep_channel(sdata, NULL, assoc_data->link[i].bss, + err = ieee80211_prep_channel(sdata, NULL, + assoc_data->link[i].bss, true, &assoc_data->link[i].conn_flags); - if (err) + if (err) { + req->links[i].error = err; goto err_clear; + } } /* needed for transmitting the assoc frames properly */ @@ -7991,11 +7979,17 @@ run_again(sdata, assoc_data->timeout); + /* We are associating, clean up auth_data */ + if (ifmgd->auth_data) + ieee80211_destroy_auth_data(sdata, true); + return 0; err_clear: - eth_zero_addr(sdata->deflink.u.mgd.bssid); - ieee80211_link_info_change_notify(sdata, &sdata->deflink, - BSS_CHANGED_BSSID); + if (!ifmgd->auth_data) { + eth_zero_addr(sdata->deflink.u.mgd.bssid); + ieee80211_link_info_change_notify(sdata, &sdata->deflink, + BSS_CHANGED_BSSID); + } ifmgd->assoc_data = NULL; err_free: kfree(assoc_data); @@ -8019,6 +8013,7 @@ req->bssid, req->reason_code, ieee80211_get_reason_code_string(req->reason_code)); + info.link_id = ifmgd->auth_data->link_id; drv_mgd_prepare_tx(sdata->local, sdata, &info); ieee80211_send_deauth_disassoc(sdata, req->bssid, req->bssid, IEEE80211_STYPE_DEAUTH, @@ -8039,6 +8034,7 @@ req->bssid, req->reason_code, ieee80211_get_reason_code_string(req->reason_code)); + info.link_id = ifmgd->assoc_data->assoc_link_id; drv_mgd_prepare_tx(sdata->local, sdata, &info); ieee80211_send_deauth_disassoc(sdata, req->bssid, req->bssid, IEEE80211_STYPE_DEAUTH, @@ -8099,6 +8095,8 @@ { wiphy_work_cancel(link->sdata->local->hw.wiphy, &link->u.mgd.request_smps_work); + wiphy_work_cancel(link->sdata->local->hw.wiphy, + &link->u.mgd.recalc_smps); wiphy_delayed_work_cancel(link->sdata->local->hw.wiphy, &link->u.mgd.chswitch_work); } @@ -8112,16 +8110,18 @@ * they will not do anything but might not have been * cancelled when disconnecting. */ - cancel_work_sync(&ifmgd->monitor_work); + wiphy_work_cancel(sdata->local->hw.wiphy, + &ifmgd->monitor_work); wiphy_work_cancel(sdata->local->hw.wiphy, &ifmgd->beacon_connection_loss_work); wiphy_work_cancel(sdata->local->hw.wiphy, &ifmgd->csa_connection_drop_work); - cancel_delayed_work_sync(&ifmgd->tdls_peer_del_work); - cancel_delayed_work_sync(&ifmgd->ml_reconf_work); + wiphy_delayed_work_cancel(sdata->local->hw.wiphy, + &ifmgd->tdls_peer_del_work); + wiphy_delayed_work_cancel(sdata->local->hw.wiphy, + &ifmgd->ml_reconf_work); wiphy_delayed_work_cancel(sdata->local->hw.wiphy, &ifmgd->t2l_map_work); - sdata_lock(sdata); if (ifmgd->assoc_data) ieee80211_destroy_assoc_data(sdata, ASSOC_TIMEOUT); if (ifmgd->auth_data) @@ -8137,7 +8137,6 @@ ifmgd->assoc_req_ies_len = 0; spin_unlock_bh(&ifmgd->teardown_lock); del_timer_sync(&ifmgd->timer); - sdata_unlock(sdata); } void ieee80211_cqm_rssi_notify(struct ieee80211_vif *vif, diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/ocb.c backport-iwlwifi-dkms-11510/net/mac80211/ocb.c --- backport-iwlwifi-dkms-11289/net/mac80211/ocb.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/ocb.c 2023-10-04 04:18:43.000000000 +0800 @@ -124,11 +124,11 @@ struct ieee80211_if_ocb *ifocb = &sdata->u.ocb; struct sta_info *sta; + lockdep_assert_wiphy(sdata->local->hw.wiphy); + if (ifocb->joined != true) return; - sdata_lock(sdata); - spin_lock_bh(&ifocb->incomplete_lock); while (!list_empty(&ifocb->incomplete_stations)) { sta = list_first_entry(&ifocb->incomplete_stations, @@ -144,8 +144,6 @@ if (test_and_clear_bit(OCB_WORK_HOUSEKEEPING, &ifocb->wrkq_flags)) ieee80211_ocb_housekeeping(sdata); - - sdata_unlock(sdata); } static void ieee80211_ocb_housekeeping_timer(struct timer_list *t) @@ -178,6 +176,8 @@ u64 changed = BSS_CHANGED_OCB | BSS_CHANGED_BSSID; int err; + lockdep_assert_wiphy(sdata->local->hw.wiphy); + if (ifocb->joined == true) return -EINVAL; @@ -185,10 +185,8 @@ sdata->deflink.smps_mode = IEEE80211_SMPS_OFF; sdata->deflink.needed_rx_chains = sdata->local->rx_chains; - mutex_lock(&sdata->local->mtx); err = ieee80211_link_use_channel(&sdata->deflink, &setup->chandef, IEEE80211_CHANCTX_SHARED); - mutex_unlock(&sdata->local->mtx); if (err) return err; @@ -209,6 +207,8 @@ struct ieee80211_local *local = sdata->local; struct sta_info *sta; + lockdep_assert_wiphy(sdata->local->hw.wiphy); + ifocb->joined = false; sta_info_flush(sdata); @@ -228,9 +228,7 @@ clear_bit(SDATA_STATE_OFFCHANNEL, &sdata->state); ieee80211_bss_info_change_notify(sdata, BSS_CHANGED_OCB); - mutex_lock(&sdata->local->mtx); ieee80211_link_release_channel(&sdata->deflink); - mutex_unlock(&sdata->local->mtx); skb_queue_purge(&sdata->skb_queue); diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/offchannel.c backport-iwlwifi-dkms-11510/net/mac80211/offchannel.c --- backport-iwlwifi-dkms-11289/net/mac80211/offchannel.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/offchannel.c 2023-10-04 04:18:43.000000000 +0800 @@ -34,7 +34,7 @@ del_timer_sync(&ifmgd->bcn_mon_timer); del_timer_sync(&ifmgd->conn_mon_timer); - cancel_work_sync(&local->dynamic_ps_enable_work); + wiphy_work_cancel(local->hw.wiphy, &local->dynamic_ps_enable_work); if (local->hw.conf.flags & IEEE80211_CONF_PS) { offchannel_ps_enabled = true; @@ -84,6 +84,8 @@ { struct ieee80211_sub_if_data *sdata; + lockdep_assert_wiphy(local->hw.wiphy); + if (WARN_ON(local->use_chanctx)) return; @@ -101,7 +103,6 @@ false); ieee80211_flush_queues(local, NULL, false); - mutex_lock(&local->iflist_mtx); list_for_each_entry(sdata, &local->interfaces, list) { if (!ieee80211_sdata_running(sdata)) continue; @@ -127,17 +128,17 @@ sdata->u.mgd.associated) ieee80211_offchannel_ps_enable(sdata); } - mutex_unlock(&local->iflist_mtx); } void ieee80211_offchannel_return(struct ieee80211_local *local) { struct ieee80211_sub_if_data *sdata; + lockdep_assert_wiphy(local->hw.wiphy); + if (WARN_ON(local->use_chanctx)) return; - mutex_lock(&local->iflist_mtx); list_for_each_entry(sdata, &local->interfaces, list) { if (sdata->vif.type == NL80211_IFTYPE_P2P_DEVICE) continue; @@ -161,7 +162,6 @@ BSS_CHANGED_BEACON_ENABLED); } } - mutex_unlock(&local->iflist_mtx); ieee80211_wake_queues_by_reason(&local->hw, IEEE80211_MAX_QUEUE_MAP, IEEE80211_QUEUE_STOP_REASON_OFFCHANNEL, @@ -197,7 +197,7 @@ struct ieee80211_roc_work *roc, *tmp; long remaining_dur_min = LONG_MAX; - lockdep_assert_held(&local->mtx); + lockdep_assert_wiphy(local->hw.wiphy); list_for_each_entry_safe(roc, tmp, &local->roc_list, list) { long remaining; @@ -230,7 +230,7 @@ if (dur == LONG_MAX) return false; - mod_delayed_work(local->workqueue, &local->roc_work, dur); + wiphy_delayed_work_queue(local->hw.wiphy, &local->roc_work, dur); return true; } @@ -258,13 +258,13 @@ roc->notified = true; } -static void ieee80211_hw_roc_start(struct work_struct *work) +static void ieee80211_hw_roc_start(struct wiphy *wiphy, struct wiphy_work *work) { struct ieee80211_local *local = container_of(work, struct ieee80211_local, hw_roc_start); struct ieee80211_roc_work *roc; - mutex_lock(&local->mtx); + lockdep_assert_wiphy(local->hw.wiphy); list_for_each_entry(roc, &local->roc_list, list) { if (!roc->started) @@ -273,8 +273,6 @@ roc->hw_begun = true; ieee80211_handle_roc_started(roc, local->hw_roc_start_time); } - - mutex_unlock(&local->mtx); } void ieee80211_ready_on_channel(struct ieee80211_hw *hw) @@ -285,7 +283,7 @@ trace_api_ready_on_channel(local); - ieee80211_queue_work(hw, &local->hw_roc_start); + wiphy_work_queue(hw->wiphy, &local->hw_roc_start); } EXPORT_SYMBOL_GPL(ieee80211_ready_on_channel); @@ -295,7 +293,7 @@ enum ieee80211_roc_type type; u32 min_dur, max_dur; - lockdep_assert_held(&local->mtx); + lockdep_assert_wiphy(local->hw.wiphy); if (WARN_ON(list_empty(&local->roc_list))) return; @@ -338,7 +336,7 @@ tmp->started = true; tmp->abort = true; } - ieee80211_queue_work(&local->hw, &local->hw_roc_done); + wiphy_work_queue(local->hw.wiphy, &local->hw_roc_done); return; } @@ -368,8 +366,8 @@ ieee80211_hw_config(local, 0); } - ieee80211_queue_delayed_work(&local->hw, &local->roc_work, - msecs_to_jiffies(min_dur)); + wiphy_delayed_work_queue(local->hw.wiphy, &local->roc_work, + msecs_to_jiffies(min_dur)); /* tell userspace or send frame(s) */ list_for_each_entry(tmp, &local->roc_list, list) { @@ -386,7 +384,7 @@ { struct ieee80211_roc_work *roc; - lockdep_assert_held(&local->mtx); + lockdep_assert_wiphy(local->hw.wiphy); if (list_empty(&local->roc_list)) { ieee80211_run_deferred_scan(local); @@ -407,8 +405,8 @@ _ieee80211_start_next_roc(local); } else { /* delay it a bit */ - ieee80211_queue_delayed_work(&local->hw, &local->roc_work, - round_jiffies_relative(HZ/2)); + wiphy_delayed_work_queue(local->hw.wiphy, &local->roc_work, + round_jiffies_relative(HZ / 2)); } } @@ -417,7 +415,7 @@ struct ieee80211_roc_work *roc; bool on_channel; - lockdep_assert_held(&local->mtx); + lockdep_assert_wiphy(local->hw.wiphy); if (WARN_ON(local->ops->remain_on_channel)) return; @@ -451,29 +449,27 @@ } } -static void ieee80211_roc_work(struct work_struct *work) +static void ieee80211_roc_work(struct wiphy *wiphy, struct wiphy_work *work) { struct ieee80211_local *local = container_of(work, struct ieee80211_local, roc_work.work); - mutex_lock(&local->mtx); + lockdep_assert_wiphy(local->hw.wiphy); + __ieee80211_roc_work(local); - mutex_unlock(&local->mtx); } -static void ieee80211_hw_roc_done(struct work_struct *work) +static void ieee80211_hw_roc_done(struct wiphy *wiphy, struct wiphy_work *work) { struct ieee80211_local *local = container_of(work, struct ieee80211_local, hw_roc_done); - mutex_lock(&local->mtx); + lockdep_assert_wiphy(local->hw.wiphy); ieee80211_end_finished_rocs(local, jiffies); /* if there's another roc, start it now */ ieee80211_start_next_roc(local); - - mutex_unlock(&local->mtx); } void ieee80211_remain_on_channel_expired(struct ieee80211_hw *hw) @@ -482,7 +478,7 @@ trace_api_remain_on_channel_expired(local); - ieee80211_queue_work(hw, &local->hw_roc_done); + wiphy_work_queue(hw->wiphy, &local->hw_roc_done); } EXPORT_SYMBOL_GPL(ieee80211_remain_on_channel_expired); @@ -537,7 +533,7 @@ bool queued = false, combine_started = true; int ret; - lockdep_assert_held(&local->mtx); + lockdep_assert_wiphy(local->hw.wiphy); if (channel->freq_offset) /* this may work, but is untested */ @@ -586,8 +582,8 @@ /* if not HW assist, just queue & schedule work */ if (!local->ops->remain_on_channel) { list_add_tail(&roc->list, &local->roc_list); - ieee80211_queue_delayed_work(&local->hw, - &local->roc_work, 0); + wiphy_delayed_work_queue(local->hw.wiphy, + &local->roc_work, 0); } else { /* otherwise actually kick it off here * (for error handling) @@ -675,15 +671,12 @@ { struct ieee80211_sub_if_data *sdata = IEEE80211_WDEV_TO_SUB_IF(wdev); struct ieee80211_local *local = sdata->local; - int ret; - mutex_lock(&local->mtx); - ret = ieee80211_start_roc_work(local, sdata, chan, - duration, cookie, NULL, - IEEE80211_ROC_TYPE_NORMAL); - mutex_unlock(&local->mtx); + lockdep_assert_wiphy(local->hw.wiphy); - return ret; + return ieee80211_start_roc_work(local, sdata, chan, + duration, cookie, NULL, + IEEE80211_ROC_TYPE_NORMAL); } static int ieee80211_cancel_roc(struct ieee80211_local *local, @@ -692,12 +685,13 @@ struct ieee80211_roc_work *roc, *tmp, *found = NULL; int ret; + lockdep_assert_wiphy(local->hw.wiphy); + if (!cookie) return -ENOENT; - flush_work(&local->hw_roc_start); + wiphy_work_flush(local->hw.wiphy, &local->hw_roc_start); - mutex_lock(&local->mtx); list_for_each_entry_safe(roc, tmp, &local->roc_list, list) { if (!mgmt_tx && roc->cookie != cookie) continue; @@ -709,7 +703,6 @@ } if (!found) { - mutex_unlock(&local->mtx); return -ENOENT; } @@ -721,10 +714,26 @@ if (local->ops->remain_on_channel) { ret = drv_cancel_remain_on_channel(local, roc->sdata); if (WARN_ON_ONCE(ret)) { - mutex_unlock(&local->mtx); return ret; } + /* + * We could be racing against the notification from the driver: + * + driver is handling the notification on CPU0 + * + user space is cancelling the remain on channel and + * schedules the hw_roc_done worker. + * + * Now hw_roc_done might start to run after the next roc will + * start and mac80211 will think that this second roc has + * ended prematurely. + * Cancel the work to make sure that all the pending workers + * have completed execution. + * Note that this assumes that by the time the driver returns + * from drv_cancel_remain_on_channel, it has completed all + * the processing of related notifications. + */ + wiphy_work_cancel(local->hw.wiphy, &local->hw_roc_done); + /* TODO: * if multiple items were combined here then we really shouldn't * cancel them all - we should wait for as much time as needed @@ -745,11 +754,10 @@ } else { /* go through work struct to return to the operating channel */ found->abort = true; - mod_delayed_work(local->workqueue, &local->roc_work, 0); + wiphy_delayed_work_queue(local->hw.wiphy, &local->roc_work, 0); } out_unlock: - mutex_unlock(&local->mtx); return 0; } @@ -778,6 +786,8 @@ int ret; u8 *data; + lockdep_assert_wiphy(local->hw.wiphy); + if (params->dont_wait_for_ack) flags = IEEE80211_TX_CTL_NO_ACK; else @@ -833,7 +843,6 @@ break; case NL80211_IFTYPE_STATION: case NL80211_IFTYPE_P2P_CLIENT: - sdata_lock(sdata); if (!sdata->u.mgd.associated || (params->offchan && params->wait && local->ops->remain_on_channel && @@ -844,8 +853,6 @@ sta = sta_info_get_bss(sdata, mgmt->da); mlo_sta = sta && sta->sta.mlo; } - - sdata_unlock(sdata); break; case NL80211_IFTYPE_P2P_DEVICE: need_offchan = true; @@ -861,8 +868,6 @@ if (need_offchan && !params->chan) return -EINVAL; - mutex_lock(&local->mtx); - /* Check if the operating channel is the requested channel */ if (!params->chan && mlo_sta) { need_offchan = false; @@ -986,7 +991,6 @@ if (ret) ieee80211_free_txskb(&local->hw, skb); out_unlock: - mutex_unlock(&local->mtx); return ret; } @@ -1000,9 +1004,9 @@ void ieee80211_roc_setup(struct ieee80211_local *local) { - INIT_WORK(&local->hw_roc_start, ieee80211_hw_roc_start); - INIT_WORK(&local->hw_roc_done, ieee80211_hw_roc_done); - INIT_DELAYED_WORK(&local->roc_work, ieee80211_roc_work); + wiphy_work_init(&local->hw_roc_start, ieee80211_hw_roc_start); + wiphy_work_init(&local->hw_roc_done, ieee80211_hw_roc_done); + wiphy_delayed_work_init(&local->roc_work, ieee80211_roc_work); INIT_LIST_HEAD(&local->roc_list); } @@ -1012,7 +1016,8 @@ struct ieee80211_roc_work *roc, *tmp; bool work_to_do = false; - mutex_lock(&local->mtx); + lockdep_assert_wiphy(local->hw.wiphy); + list_for_each_entry_safe(roc, tmp, &local->roc_list, list) { if (sdata && roc->sdata != sdata) continue; @@ -1032,5 +1037,4 @@ } if (work_to_do) __ieee80211_roc_work(local); - mutex_unlock(&local->mtx); } diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/pm.c backport-iwlwifi-dkms-11510/net/mac80211/pm.c --- backport-iwlwifi-dkms-11289/net/mac80211/pm.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/pm.c 2023-10-04 04:18:43.000000000 +0800 @@ -1,7 +1,7 @@ // SPDX-License-Identifier: GPL-2.0 /* * Portions - * Copyright (C) 2020-2021 Intel Corporation + * Copyright (C) 2020-2021, 2023 Intel Corporation */ #include #include @@ -40,13 +40,12 @@ if (ieee80211_hw_check(hw, AMPDU_AGGREGATION) && !(wowlan && wowlan->any)) { - mutex_lock(&local->sta_mtx); + lockdep_assert_wiphy(local->hw.wiphy); list_for_each_entry(sta, &local->sta_list, list) { set_sta_flag(sta, WLAN_STA_BLOCK_BA); ieee80211_sta_tear_down_BA_sessions( sta, AGG_STOP_LOCAL_REQUEST); } - mutex_unlock(&local->sta_mtx); } /* keep sched_scan only in case of 'any' trigger */ @@ -76,7 +75,7 @@ * Note that this particular timer doesn't need to be * restarted at resume. */ - cancel_work_sync(&local->dynamic_ps_enable_work); + wiphy_work_cancel(local->hw.wiphy, &local->dynamic_ps_enable_work); del_timer_sync(&local->dynamic_ps_timer); local->wowlan = wowlan; @@ -119,12 +118,11 @@ local->quiescing = false; local->wowlan = false; if (ieee80211_hw_check(hw, AMPDU_AGGREGATION)) { - mutex_lock(&local->sta_mtx); + lockdep_assert_wiphy(local->hw.wiphy); list_for_each_entry(sta, &local->sta_list, list) { clear_sta_flag(sta, WLAN_STA_BLOCK_BA); } - mutex_unlock(&local->sta_mtx); } ieee80211_wake_queues_by_reason(hw, IEEE80211_MAX_QUEUE_MAP, @@ -161,7 +159,8 @@ break; } - flush_delayed_work(&sdata->dec_tailroom_needed_wk); + wiphy_delayed_work_flush(local->hw.wiphy, + &sdata->dec_tailroom_needed_wk); drv_remove_interface(local, sdata); } diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/rx.c backport-iwlwifi-dkms-11510/net/mac80211/rx.c --- backport-iwlwifi-dkms-11289/net/mac80211/rx.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/rx.c 2023-10-04 04:18:43.000000000 +0800 @@ -1435,7 +1435,7 @@ rx->sta->last_seq_ctrl[rx->seqno_idx] == hdr->seq_ctrl)) { I802_DEBUG_INC(rx->local->dot11FrameDuplicateCount); rx->link_sta->rx_stats.num_duplicates++; - return RX_DROP_UNUSABLE; + return RX_DROP_U_DUP; } else if (!(status->flag & RX_FLAG_AMSDU_MORE)) { rx->sta->last_seq_ctrl[rx->seqno_idx] = hdr->seq_ctrl; } @@ -1489,7 +1489,7 @@ cfg80211_rx_spurious_frame(rx->sdata->dev, hdr->addr2, GFP_ATOMIC)) - return RX_DROP_UNUSABLE; + return RX_DROP_U_SPURIOUS; return RX_DROP_MONITOR; } @@ -1882,7 +1882,7 @@ struct ieee80211_rx_status *status = IEEE80211_SKB_RXCB(skb); struct ieee80211_hdr *hdr = (struct ieee80211_hdr *)skb->data; int keyidx; - ieee80211_rx_result result = RX_DROP_UNUSABLE; + ieee80211_rx_result result = RX_DROP_U_DECRYPT_FAIL; struct ieee80211_key *sta_ptk = NULL; struct ieee80211_key *ptk_idx = NULL; int mmie_keyidx = -1; @@ -1932,7 +1932,7 @@ keyid = ieee80211_get_keyid(rx->skb); if (unlikely(keyid < 0)) - return RX_DROP_UNUSABLE; + return RX_DROP_U_NO_KEY_ID; ptk_idx = rcu_dereference(rx->sta->ptk[keyid]); } @@ -2037,7 +2037,7 @@ keyidx = ieee80211_get_keyid(rx->skb); if (unlikely(keyidx < 0)) - return RX_DROP_UNUSABLE; + return RX_DROP_U_NO_KEY_ID; /* check per-station GTK first, if multicast packet */ if (is_multicast_ether_addr(hdr->addr1) && rx->link_sta) @@ -2103,7 +2103,7 @@ result = ieee80211_crypto_gcmp_decrypt(rx); break; default: - result = RX_DROP_UNUSABLE; + result = RX_DROP_U_BAD_CIPHER; } /* the hdr variable is invalid after the decrypt handlers */ @@ -2111,7 +2111,7 @@ /* either the frame has been decrypted or will be dropped */ status->flag |= RX_FLAG_DECRYPTED; - if (unlikely(ieee80211_is_beacon(fc) && result == RX_DROP_UNUSABLE && + if (unlikely(ieee80211_is_beacon(fc) && RX_RES_IS_UNUSABLE(result) && rx->sdata->dev)) cfg80211_rx_unprot_mlme_mgmt(rx->sdata->dev, skb->data, skb->len); @@ -2248,7 +2248,7 @@ I802_DEBUG_INC(rx->local->rx_handlers_fragments); if (skb_linearize(rx->skb)) - return RX_DROP_UNUSABLE; + return RX_DROP_U_OOM; /* * skb_linearize() might change the skb->data and @@ -2311,11 +2311,11 @@ u8 pn[IEEE80211_CCMP_PN_LEN], *rpn; if (!requires_sequential_pn(rx, fc)) - return RX_DROP_UNUSABLE; + return RX_DROP_U_NONSEQ_PN; /* Prevent mixed key and fragment cache attacks */ if (entry->key_color != rx->key->color) - return RX_DROP_UNUSABLE; + return RX_DROP_U_BAD_KEY_COLOR; memcpy(pn, entry->last_pn, IEEE80211_CCMP_PN_LEN); for (i = IEEE80211_CCMP_PN_LEN - 1; i >= 0; i--) { @@ -2326,7 +2326,7 @@ rpn = rx->ccm_gcm.pn; if (memcmp(pn, rpn, IEEE80211_CCMP_PN_LEN)) - return RX_DROP_UNUSABLE; + return RX_DROP_U_REPLAY; memcpy(entry->last_pn, pn, IEEE80211_CCMP_PN_LEN); } else if (entry->is_protected && (!rx->key || @@ -2337,11 +2337,11 @@ * if for TKIP Michael MIC should protect us, and WEP is a * lost cause anyway. */ - return RX_DROP_UNUSABLE; + return RX_DROP_U_EXPECT_DEFRAG_PROT; } else if (entry->is_protected && rx->key && entry->key_color != rx->key->color && (status->flag & RX_FLAG_DECRYPTED)) { - return RX_DROP_UNUSABLE; + return RX_DROP_U_BAD_KEY_COLOR; } skb_pull(rx->skb, ieee80211_hdrlen(fc)); @@ -2360,7 +2360,7 @@ GFP_ATOMIC))) { I802_DEBUG_INC(rx->local->rx_handlers_drop_defrag); __skb_queue_purge(&entry->skb_list); - return RX_DROP_UNUSABLE; + return RX_DROP_U_OOM; } } while ((skb = __skb_dequeue(&entry->skb_list))) { @@ -2404,7 +2404,7 @@ return 0; } -VISIBLE_IF_KUNIT int +VISIBLE_IF_MAC80211_KUNIT ieee80211_rx_result ieee80211_drop_unencrypted_mgmt(struct ieee80211_rx_data *rx) { struct ieee80211_rx_status *status = IEEE80211_SKB_RXCB(rx->skb); @@ -2416,22 +2416,30 @@ * decrypted them already. */ if (status->flag & RX_FLAG_DECRYPTED) - return 0; + return RX_CONTINUE; /* drop unicast protected dual (that wasn't protected) */ if (ieee80211_is_action(fc) && mgmt->u.action.category == WLAN_CATEGORY_PROTECTED_DUAL_OF_ACTION) - return -EACCES; + return RX_DROP_U_UNPROT_DUAL; if (rx->sta && test_sta_flag(rx->sta, WLAN_STA_MFP)) { if (unlikely(!ieee80211_has_protected(fc) && ieee80211_is_unicast_robust_mgmt_frame(rx->skb))) { if (ieee80211_is_deauth(fc) || - ieee80211_is_disassoc(fc)) + ieee80211_is_disassoc(fc)) { + /* + * Permit unprotected deauth/disassoc frames + * during 4-way-HS (key is installed after HS). + */ + if (!rx->key) + return RX_CONTINUE; + cfg80211_rx_unprot_mlme_mgmt(rx->sdata->dev, rx->skb->data, rx->skb->len); - return -EACCES; + } + return RX_DROP_U_UNPROT_UCAST_MGMT; } /* BIP does not use Protected field, so need to check MMIE */ if (unlikely(ieee80211_is_multicast_robust_mgmt_frame(rx->skb) && @@ -2441,14 +2449,14 @@ cfg80211_rx_unprot_mlme_mgmt(rx->sdata->dev, rx->skb->data, rx->skb->len); - return -EACCES; + return RX_DROP_U_UNPROT_MCAST_MGMT; } if (unlikely(ieee80211_is_beacon(fc) && rx->key && ieee80211_get_mmie_keyidx(rx->skb) < 0)) { cfg80211_rx_unprot_mlme_mgmt(rx->sdata->dev, rx->skb->data, rx->skb->len); - return -EACCES; + return RX_DROP_U_UNPROT_BEACON; } /* * When using MFP, Action frames are not allowed prior to @@ -2456,20 +2464,29 @@ */ if (unlikely(ieee80211_is_action(fc) && !rx->key && ieee80211_is_robust_mgmt_frame(rx->skb))) - return -EACCES; + return RX_DROP_U_UNPROT_ACTION; /* drop unicast public action frames when using MPF */ if (is_unicast_ether_addr(mgmt->da) && ieee80211_is_public_action((void *)rx->skb->data, rx->skb->len)) - return -EACCES; + return RX_DROP_U_UNPROT_UNICAST_PUB_ACTION; } - return 0; + /* + * Drop robust action frames before assoc regardless of MFP state, + * after assoc we also have decided on MFP or not. + */ + if (ieee80211_is_action(fc) && + ieee80211_is_robust_mgmt_frame(rx->skb) && + (!rx->sta || !test_sta_flag(rx->sta, WLAN_STA_ASSOC))) + return RX_DROP_U_UNPROT_ROBUST_ACTION; + + return RX_CONTINUE; } -EXPORT_SYMBOL_IF_KUNIT(ieee80211_drop_unencrypted_mgmt); +EXPORT_SYMBOL_IF_MAC80211_KUNIT(ieee80211_drop_unencrypted_mgmt); -static int +static ieee80211_rx_result __ieee80211_data_to_8023(struct ieee80211_rx_data *rx, bool *port_control) { struct ieee80211_sub_if_data *sdata = rx->sdata; @@ -2481,32 +2498,31 @@ *port_control = false; if (ieee80211_has_a4(hdr->frame_control) && sdata->vif.type == NL80211_IFTYPE_AP_VLAN && !sdata->u.vlan.sta) - return -1; + return RX_DROP_U_UNEXPECTED_VLAN_4ADDR; if (sdata->vif.type == NL80211_IFTYPE_STATION && !!sdata->u.mgd.use_4addr != !!ieee80211_has_a4(hdr->frame_control)) { - if (!sdata->u.mgd.use_4addr) - return -1; + return RX_DROP_U_UNEXPECTED_STA_4ADDR; else if (!ether_addr_equal(hdr->addr1, sdata->vif.addr)) check_port_control = true; } if (is_multicast_ether_addr(hdr->addr1) && sdata->vif.type == NL80211_IFTYPE_AP_VLAN && sdata->u.vlan.sta) - return -1; + return RX_DROP_U_UNEXPECTED_VLAN_MCAST; ret = ieee80211_data_to_8023(rx->skb, sdata->vif.addr, sdata->vif.type); if (ret < 0) - return ret; + return RX_DROP_U_INVALID_8023; ehdr = (struct ethhdr *) rx->skb->data; if (ehdr->h_proto == rx->sdata->control_port_protocol) *port_control = true; else if (check_port_control) - return -1; + return RX_DROP_U_NOT_PORT_CONTROL; - return 0; + return RX_CONTINUE; } bool ieee80211_is_our_addr(struct ieee80211_sub_if_data *sdata, @@ -2901,10 +2917,10 @@ skb = NULL; if (skb_cow_head(fwd_skb, hdrlen - sizeof(struct ethhdr))) - return RX_DROP_UNUSABLE; + return RX_DROP_U_OOM; if (skb_linearize(fwd_skb)) - return RX_DROP_UNUSABLE; + return RX_DROP_U_OOM; } fwd_hdr = skb_push(fwd_skb, hdrlen - sizeof(struct ethhdr)); @@ -3000,7 +3016,7 @@ rx->sdata->vif.addr, rx->sdata->vif.type, data_offset, true)) - return RX_DROP_UNUSABLE; + return RX_DROP_U_BAD_AMSDU; if (rx->sta->amsdu_mesh_control < 0) { s8 valid = -1; @@ -3075,21 +3091,21 @@ switch (rx->sdata->vif.type) { case NL80211_IFTYPE_AP_VLAN: if (!rx->sdata->u.vlan.sta) - return RX_DROP_UNUSABLE; + return RX_DROP_U_BAD_4ADDR; break; case NL80211_IFTYPE_STATION: if (!rx->sdata->u.mgd.use_4addr) - return RX_DROP_UNUSABLE; + return RX_DROP_U_BAD_4ADDR; break; case NL80211_IFTYPE_MESH_POINT: break; default: - return RX_DROP_UNUSABLE; + return RX_DROP_U_BAD_4ADDR; } } if (is_multicast_ether_addr(hdr->addr1) || !rx->sta) - return RX_DROP_UNUSABLE; + return RX_DROP_U_BAD_AMSDU; if (rx->key) { /* @@ -3102,7 +3118,7 @@ case WLAN_CIPHER_SUITE_WEP40: case WLAN_CIPHER_SUITE_WEP104: case WLAN_CIPHER_SUITE_TKIP: - return RX_DROP_UNUSABLE; + return RX_DROP_U_BAD_AMSDU_CIPHER; default: break; } @@ -3121,7 +3137,6 @@ __le16 fc = hdr->frame_control; ieee80211_rx_result res; bool port_control; - int err; if (unlikely(!ieee80211_is_data(hdr->frame_control))) return RX_CONTINUE; @@ -3142,9 +3157,9 @@ return RX_DROP_MONITOR; } - err = __ieee80211_data_to_8023(rx, &port_control); - if (unlikely(err)) - return RX_DROP_UNUSABLE; + res = __ieee80211_data_to_8023(rx, &port_control); + if (unlikely(res != RX_CONTINUE)) + return res; res = ieee80211_rx_mesh_data(rx->sdata, rx->sta, rx->skb); if (res != RX_CONTINUE) @@ -3376,7 +3391,7 @@ /* drop too small action frames */ if (ieee80211_is_action(mgmt->frame_control) && rx->skb->len < IEEE80211_MIN_ACTION_SIZE) - return RX_DROP_UNUSABLE; + return RX_DROP_U_RUNT_ACTION; if (rx->sdata->vif.type == NL80211_IFTYPE_AP && ieee80211_is_beacon(mgmt->frame_control) && @@ -3397,10 +3412,7 @@ rx->flags |= IEEE80211_RX_BEACON_REPORTED; } - if (ieee80211_drop_unencrypted_mgmt(rx)) - return RX_DROP_UNUSABLE; - - return RX_CONTINUE; + return ieee80211_drop_unencrypted_mgmt(rx); } static bool @@ -3470,7 +3482,7 @@ if (!rx->sta && mgmt->u.action.category != WLAN_CATEGORY_PUBLIC && mgmt->u.action.category != WLAN_CATEGORY_SELF_PROTECTED && mgmt->u.action.category != WLAN_CATEGORY_SPECTRUM_MGMT) - return RX_DROP_UNUSABLE; + return RX_DROP_U_ACTION_UNKNOWN_SRC; switch (mgmt->u.action.category) { case WLAN_CATEGORY_HT: @@ -3871,7 +3883,7 @@ /* do not return rejected action frames */ if (mgmt->u.action.category & 0x80) - return RX_DROP_UNUSABLE; + return RX_DROP_U_REJECTED_ACTION_RESPONSE; nskb = skb_copy_expand(rx->skb, local->hw.extra_tx_headroom, 0, GFP_ATOMIC); @@ -4385,8 +4397,19 @@ rate_idx = 0; /* TODO: HT/VHT rates */ else rate_idx = status->rate_idx; - ieee80211_ibss_rx_no_sta(sdata, bssid, hdr->addr2, - BIT(rate_idx)); + /* + * FIXME: We should not need to avoid probe req/resp + * here, but we respond with another probe request and + * that can (briefly) cause traffic amplification. + * + * Ignoring probe responses is here is reasonable anyway + * as the STA will be inserted later. + */ + if (!ieee80211_is_probe_req(hdr->frame_control) && + !ieee80211_is_probe_resp(hdr->frame_control)) + ieee80211_ibss_rx_no_sta(sdata, bssid, + hdr->addr2, + BIT(rate_idx)); } return true; case NL80211_IFTYPE_OCB: @@ -4656,7 +4679,7 @@ struct ieee80211_local *local = sdata->local; struct sta_info *sta; - lockdep_assert_held(&local->sta_mtx); + lockdep_assert_wiphy(local->hw.wiphy); list_for_each_entry(sta, &local->sta_list, list) { if (sdata != sta->sdata && @@ -4670,9 +4693,9 @@ { struct ieee80211_local *local = sdata->local; - mutex_lock(&local->sta_mtx); + lockdep_assert_wiphy(local->hw.wiphy); + __ieee80211_check_fast_rx_iface(sdata); - mutex_unlock(&local->sta_mtx); } static void ieee80211_rx_8023(struct ieee80211_rx_data *rx, @@ -4982,9 +5005,10 @@ hdr = (struct ieee80211_hdr *)rx->skb->data; } - if (unlikely(rx->sta && rx->sta->sta.mlo && - !ieee80211_is_probe_resp(hdr->frame_control) && - is_unicast_ether_addr(hdr->addr1))) { + if (unlikely(rx->sta && rx->sta->sta.mlo) && + is_unicast_ether_addr(hdr->addr1) && + !ieee80211_is_probe_resp(hdr->frame_control) && + !ieee80211_is_beacon(hdr->frame_control)) { /* translate to MLD addresses */ if (ether_addr_equal(link->conf->addr, hdr->addr1)) ether_addr_copy(hdr->addr1, rx->sdata->vif.addr); diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/s1g.c backport-iwlwifi-dkms-11510/net/mac80211/s1g.c --- backport-iwlwifi-dkms-11289/net/mac80211/s1g.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/s1g.c 2023-10-04 04:18:43.000000000 +0800 @@ -2,6 +2,7 @@ /* * S1G handling * Copyright(c) 2020 Adapt-IP + * Copyright (C) 2023 Intel Corporation */ #include #include @@ -153,11 +154,11 @@ struct ieee80211_local *local = sdata->local; struct sta_info *sta; - mutex_lock(&local->sta_mtx); + lockdep_assert_wiphy(local->hw.wiphy); sta = sta_info_get_bss(sdata, mgmt->sa); if (!sta) - goto out; + return; switch (mgmt->u.action.u.s1g.action_code) { case WLAN_S1G_TWT_SETUP: @@ -169,9 +170,6 @@ default: break; } - -out: - mutex_unlock(&local->sta_mtx); } void ieee80211_s1g_status_twt_action(struct ieee80211_sub_if_data *sdata, @@ -181,11 +179,11 @@ struct ieee80211_local *local = sdata->local; struct sta_info *sta; - mutex_lock(&local->sta_mtx); + lockdep_assert_wiphy(local->hw.wiphy); sta = sta_info_get_bss(sdata, mgmt->da); if (!sta) - goto out; + return; switch (mgmt->u.action.u.s1g.action_code) { case WLAN_S1G_TWT_SETUP: @@ -195,7 +193,4 @@ default: break; } - -out: - mutex_unlock(&local->sta_mtx); } diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/scan.c backport-iwlwifi-dkms-11510/net/mac80211/scan.c --- backport-iwlwifi-dkms-11289/net/mac80211/scan.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/scan.c 2023-10-04 04:18:43.000000000 +0800 @@ -200,11 +200,32 @@ if (scan_sdata && scan_sdata->vif.type == NL80211_IFTYPE_STATION && scan_sdata->vif.cfg.assoc && ieee80211_have_rx_timestamp(rx_status)) { - bss_meta.parent_tsf = - ieee80211_calculate_rx_timestamp(local, rx_status, - len + FCS_LEN, 24); - ether_addr_copy(bss_meta.parent_bssid, - scan_sdata->vif.bss_conf.bssid); + struct ieee80211_bss_conf *link_conf = NULL; + + /* for an MLO connection, set the TSF data only in case we have + * an indication on which of the links the frame was received + */ + if (ieee80211_vif_is_mld(&scan_sdata->vif)) { + if (rx_status->link_valid) { + s8 link_id = rx_status->link_id; + + link_conf = + rcu_dereference(scan_sdata->vif.link_conf[link_id]); + } + } else { + link_conf = &scan_sdata->vif.bss_conf; + } + + if (link_conf) { + bss_meta.parent_tsf = + ieee80211_calculate_rx_timestamp(local, + rx_status, + len + FCS_LEN, + 24); + + ether_addr_copy(bss_meta.parent_bssid, + link_conf->bssid); + } } rcu_read_unlock(); @@ -274,8 +295,8 @@ * the beacon/proberesp rx gives us an opportunity to upgrade * to active scan */ - set_bit(SCAN_BEACON_DONE, &local->scanning); - ieee80211_queue_delayed_work(&local->hw, &local->scan_work, 0); + set_bit(SCAN_BEACON_DONE, &local->scanning); + wiphy_delayed_work_queue(local->hw.wiphy, &local->scan_work, 0); } if (ieee80211_is_probe_resp(mgmt->frame_control)) { @@ -344,7 +365,7 @@ u32 flags = 0; req = rcu_dereference_protected(local->scan_req, - lockdep_is_held(&local->mtx)); + lockdep_is_held(&local->hw.wiphy->mtx)); if (test_bit(SCAN_HW_CANCELLED, &local->scanning)) return false; @@ -409,7 +430,7 @@ struct ieee80211_sub_if_data *scan_sdata; struct ieee80211_sub_if_data *sdata; - lockdep_assert_held(&local->mtx); + lockdep_assert_wiphy(local->hw.wiphy); /* * It's ok to abort a not-yet-running scan (that @@ -424,7 +445,7 @@ return; scan_sdata = rcu_dereference_protected(local->scan_sdata, - lockdep_is_held(&local->mtx)); + lockdep_is_held(&local->hw.wiphy->mtx)); if (hw_scan && !aborted && !ieee80211_hw_check(&local->hw, SINGLE_SCAN_ON_ALL_BANDS) && @@ -433,7 +454,7 @@ rc = drv_hw_scan(local, rcu_dereference_protected(local->scan_sdata, - lockdep_is_held(&local->mtx)), + lockdep_is_held(&local->hw.wiphy->mtx)), local->hw_scan_req); if (rc == 0) @@ -450,7 +471,7 @@ local->hw_scan_req = NULL; scan_req = rcu_dereference_protected(local->scan_req, - lockdep_is_held(&local->mtx)); + lockdep_is_held(&local->hw.wiphy->mtx)); RCU_INIT_POINTER(local->scan_req, NULL); RCU_INIT_POINTER(local->scan_sdata, NULL); @@ -505,7 +526,7 @@ memcpy(&local->scan_info, info, sizeof(*info)); - ieee80211_queue_delayed_work(&local->hw, &local->scan_work, 0); + wiphy_delayed_work_queue(local->hw.wiphy, &local->scan_work, 0); } EXPORT_SYMBOL(ieee80211_scan_completed); @@ -545,8 +566,7 @@ /* We need to set power level at maximum rate for scanning. */ ieee80211_hw_config(local, 0); - ieee80211_queue_delayed_work(&local->hw, - &local->scan_work, 0); + wiphy_delayed_work_queue(local->hw.wiphy, &local->scan_work, 0); return 0; } @@ -556,20 +576,18 @@ struct ieee80211_local *local = sdata->local; struct ieee80211_sub_if_data *sdata_iter; + lockdep_assert_wiphy(local->hw.wiphy); + if (!ieee80211_is_radar_required(local)) return true; if (!regulatory_pre_cac_allowed(local->hw.wiphy)) return false; - mutex_lock(&local->iflist_mtx); list_for_each_entry(sdata_iter, &local->interfaces, list) { - if (sdata_iter->wdev.cac_started) { - mutex_unlock(&local->iflist_mtx); + if (sdata_iter->wdev.cac_started) return false; - } } - mutex_unlock(&local->iflist_mtx); return true; } @@ -592,7 +610,7 @@ void ieee80211_run_deferred_scan(struct ieee80211_local *local) { - lockdep_assert_held(&local->mtx); + lockdep_assert_wiphy(local->hw.wiphy); if (!local->scan_req || local->scanning) return; @@ -600,11 +618,11 @@ if (!ieee80211_can_scan(local, rcu_dereference_protected( local->scan_sdata, - lockdep_is_held(&local->mtx)))) + lockdep_is_held(&local->hw.wiphy->mtx)))) return; - ieee80211_queue_delayed_work(&local->hw, &local->scan_work, - round_jiffies_relative(0)); + wiphy_delayed_work_queue(local->hw.wiphy, &local->scan_work, + round_jiffies_relative(0)); } static void ieee80211_send_scan_probe_req(struct ieee80211_sub_if_data *sdata, @@ -644,7 +662,7 @@ u32 flags = 0, tx_flags; scan_req = rcu_dereference_protected(local->scan_req, - lockdep_is_held(&local->mtx)); + lockdep_is_held(&local->hw.wiphy->mtx)); tx_flags = IEEE80211_TX_INTFL_OFFCHAN_TX_OK; if (scan_req->no_cck) @@ -655,7 +673,7 @@ flags |= IEEE80211_PROBE_FLAG_RANDOM_SN; sdata = rcu_dereference_protected(local->scan_sdata, - lockdep_is_held(&local->mtx)); + lockdep_is_held(&local->hw.wiphy->mtx)); for (i = 0; i < scan_req->n_ssids; i++) ieee80211_send_scan_probe_req( @@ -680,11 +698,26 @@ bool hw_scan = local->ops->hw_scan; int rc; - lockdep_assert_held(&local->mtx); + lockdep_assert_wiphy(local->hw.wiphy); if (local->scan_req) return -EBUSY; + /* For an MLO connection, if a link ID was specified, validate that it + * is indeed active. If no link ID was specified, select one of the + * active links. + */ + if (ieee80211_vif_is_mld(&sdata->vif)) { + if (req->tsf_report_link_id >= 0) { + if (!(sdata->vif.active_links & + BIT(req->tsf_report_link_id))) + return -EINVAL; + } else { + req->tsf_report_link_id = + __ffs(sdata->vif.active_links); + } + } + if (!__ieee80211_can_leave_ch(sdata)) return -EBUSY; @@ -733,6 +766,8 @@ local->hw_scan_req->req.duration = req->duration; local->hw_scan_req->req.duration_mandatory = req->duration_mandatory; + local->hw_scan_req->req.tsf_report_link_id = + req->tsf_report_link_id; local->hw_scan_band = 0; local->hw_scan_req->req.n_6ghz_params = req->n_6ghz_params; @@ -794,8 +829,8 @@ } /* Now, just wait a bit and we are all done! */ - ieee80211_queue_delayed_work(&local->hw, &local->scan_work, - next_delay); + wiphy_delayed_work_queue(local->hw.wiphy, &local->scan_work, + next_delay); return 0; } else { /* Do normal software scan */ @@ -860,12 +895,13 @@ enum mac80211_scan_state next_scan_state; struct cfg80211_scan_request *scan_req; + lockdep_assert_wiphy(local->hw.wiphy); + /* * check if at least one STA interface is associated, * check if at least one STA interface has pending tx frames * and grab the lowest used beacon interval */ - mutex_lock(&local->iflist_mtx); list_for_each_entry(sdata, &local->interfaces, list) { if (!ieee80211_sdata_running(sdata)) continue; @@ -881,10 +917,9 @@ } } } - mutex_unlock(&local->iflist_mtx); scan_req = rcu_dereference_protected(local->scan_req, - lockdep_is_held(&local->mtx)); + lockdep_is_held(&local->hw.wiphy->mtx)); next_chan = scan_req->channels[local->scan_channel_idx]; @@ -925,7 +960,7 @@ struct cfg80211_scan_request *scan_req; scan_req = rcu_dereference_protected(local->scan_req, - lockdep_is_held(&local->mtx)); + lockdep_is_held(&local->hw.wiphy->mtx)); skip = 0; chan = scan_req->channels[local->scan_channel_idx]; @@ -1042,7 +1077,7 @@ local->next_scan_state = SCAN_SET_CHANNEL; } -void ieee80211_scan_work(struct work_struct *work) +void ieee80211_scan_work(struct wiphy *wiphy, struct wiphy_work *work) { struct ieee80211_local *local = container_of(work, struct ieee80211_local, scan_work.work); @@ -1051,7 +1086,7 @@ unsigned long next_delay = 0; bool aborted; - mutex_lock(&local->mtx); + lockdep_assert_wiphy(local->hw.wiphy); if (!ieee80211_can_run_worker(local)) { aborted = true; @@ -1059,9 +1094,9 @@ } sdata = rcu_dereference_protected(local->scan_sdata, - lockdep_is_held(&local->mtx)); + lockdep_is_held(&local->hw.wiphy->mtx)); scan_req = rcu_dereference_protected(local->scan_req, - lockdep_is_held(&local->mtx)); + lockdep_is_held(&local->hw.wiphy->mtx)); /* When scanning on-channel, the first-callback means completed. */ if (test_bit(SCAN_ONCHANNEL_SCANNING, &local->scanning)) { @@ -1075,7 +1110,7 @@ } if (!sdata || !scan_req) - goto out; + return; if (!local->scanning) { int rc; @@ -1084,13 +1119,12 @@ RCU_INIT_POINTER(local->scan_sdata, NULL); rc = __ieee80211_start_scan(sdata, scan_req); - if (rc) { - /* need to complete scan in cfg80211 */ - rcu_assign_pointer(local->scan_req, scan_req); - aborted = true; - goto out_complete; - } else - goto out; + if (!rc) + return; + /* need to complete scan in cfg80211 */ + rcu_assign_pointer(local->scan_req, scan_req); + aborted = true; + goto out_complete; } clear_bit(SCAN_BEACON_WAIT, &local->scanning); @@ -1136,25 +1170,20 @@ } } while (next_delay == 0); - ieee80211_queue_delayed_work(&local->hw, &local->scan_work, next_delay); - goto out; + wiphy_delayed_work_queue(local->hw.wiphy, &local->scan_work, + next_delay); + return; out_complete: __ieee80211_scan_completed(&local->hw, aborted); -out: - mutex_unlock(&local->mtx); } int ieee80211_request_scan(struct ieee80211_sub_if_data *sdata, struct cfg80211_scan_request *req) { - int res; + lockdep_assert_wiphy(sdata->local->hw.wiphy); - mutex_lock(&sdata->local->mtx); - res = __ieee80211_start_scan(sdata, req); - mutex_unlock(&sdata->local->mtx); - - return res; + return __ieee80211_start_scan(sdata, req); } int ieee80211_request_ibss_scan(struct ieee80211_sub_if_data *sdata, @@ -1167,7 +1196,7 @@ int ret = -EBUSY, i, n_ch = 0; enum nl80211_band band; - mutex_lock(&local->mtx); + lockdep_assert_wiphy(local->hw.wiphy); /* busy scanning */ if (local->scan_req) @@ -1224,7 +1253,6 @@ ret = __ieee80211_start_scan(sdata, sdata->local->int_scan_req); unlock: - mutex_unlock(&local->mtx); return ret; } @@ -1251,9 +1279,8 @@ * after the scan was completed/aborted. */ - mutex_lock(&local->mtx); if (!local->scan_req) - goto out; + return; /* * We have a scan running and the driver already reported completion, @@ -1263,7 +1290,7 @@ if (test_bit(SCAN_HW_SCANNING, &local->scanning) && test_bit(SCAN_COMPLETED, &local->scanning)) { set_bit(SCAN_HW_CANCELLED, &local->scanning); - goto out; + return; } if (test_bit(SCAN_HW_SCANNING, &local->scanning)) { @@ -1275,21 +1302,14 @@ if (local->ops->cancel_hw_scan) drv_cancel_hw_scan(local, rcu_dereference_protected(local->scan_sdata, - lockdep_is_held(&local->mtx))); - goto out; + lockdep_is_held(&local->hw.wiphy->mtx))); + return; } - /* - * If the work is currently running, it must be blocked on - * the mutex, but we'll set scan_sdata = NULL and it'll - * simply exit once it acquires the mutex. - */ - cancel_delayed_work(&local->scan_work); + wiphy_delayed_work_cancel(local->hw.wiphy, &local->scan_work); /* and clean up */ memset(&local->scan_info, 0, sizeof(local->scan_info)); __ieee80211_scan_completed(&local->hw, true); -out: - mutex_unlock(&local->mtx); } int __ieee80211_request_sched_scan_start(struct ieee80211_sub_if_data *sdata, @@ -1304,9 +1324,9 @@ u8 *ie; u32 flags = 0; - iebufsz = local->scan_ies_len + req->ie_len; + lockdep_assert_wiphy(local->hw.wiphy); - lockdep_assert_held(&local->mtx); + iebufsz = local->scan_ies_len + req->ie_len; if (!local->ops->sched_scan_start) return -ENOTSUPP; @@ -1357,19 +1377,13 @@ struct cfg80211_sched_scan_request *req) { struct ieee80211_local *local = sdata->local; - int ret; - mutex_lock(&local->mtx); + lockdep_assert_wiphy(local->hw.wiphy); - if (rcu_access_pointer(local->sched_scan_sdata)) { - mutex_unlock(&local->mtx); + if (rcu_access_pointer(local->sched_scan_sdata)) return -EBUSY; - } - ret = __ieee80211_request_sched_scan_start(sdata, req); - - mutex_unlock(&local->mtx); - return ret; + return __ieee80211_request_sched_scan_start(sdata, req); } int ieee80211_request_sched_scan_stop(struct ieee80211_local *local) @@ -1377,25 +1391,21 @@ struct ieee80211_sub_if_data *sched_scan_sdata; int ret = -ENOENT; - mutex_lock(&local->mtx); + lockdep_assert_wiphy(local->hw.wiphy); - if (!local->ops->sched_scan_stop) { - ret = -ENOTSUPP; - goto out; - } + if (!local->ops->sched_scan_stop) + return -ENOTSUPP; /* We don't want to restart sched scan anymore. */ RCU_INIT_POINTER(local->sched_scan_req, NULL); sched_scan_sdata = rcu_dereference_protected(local->sched_scan_sdata, - lockdep_is_held(&local->mtx)); + lockdep_is_held(&local->hw.wiphy->mtx)); if (sched_scan_sdata) { ret = drv_sched_scan_stop(local, sched_scan_sdata); if (!ret) RCU_INIT_POINTER(local->sched_scan_sdata, NULL); } -out: - mutex_unlock(&local->mtx); return ret; } @@ -1412,24 +1422,21 @@ void ieee80211_sched_scan_end(struct ieee80211_local *local) { - mutex_lock(&local->mtx); + lockdep_assert_wiphy(local->hw.wiphy); - if (!rcu_access_pointer(local->sched_scan_sdata)) { - mutex_unlock(&local->mtx); + if (!rcu_access_pointer(local->sched_scan_sdata)) return; - } RCU_INIT_POINTER(local->sched_scan_sdata, NULL); /* If sched scan was aborted by the driver. */ RCU_INIT_POINTER(local->sched_scan_req, NULL); - mutex_unlock(&local->mtx); - - cfg80211_sched_scan_stopped(local->hw.wiphy, 0); + cfg80211_sched_scan_stopped_locked(local->hw.wiphy, 0); } -void ieee80211_sched_scan_stopped_work(struct work_struct *work) +void ieee80211_sched_scan_stopped_work(struct wiphy *wiphy, + struct wiphy_work *work) { struct ieee80211_local *local = container_of(work, struct ieee80211_local, @@ -1452,6 +1459,6 @@ if (local->in_reconfig) return; - schedule_work(&local->sched_scan_stopped_work); + wiphy_work_queue(hw->wiphy, &local->sched_scan_stopped_work); } EXPORT_SYMBOL(ieee80211_sched_scan_stopped); diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/sta_info.c backport-iwlwifi-dkms-11510/net/mac80211/sta_info.c --- backport-iwlwifi-dkms-11289/net/mac80211/sta_info.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/sta_info.c 2023-10-04 04:18:43.000000000 +0800 @@ -88,7 +88,6 @@ .max_size = CPTCFG_MAC80211_STA_HASH_MAX_SIZE, }; -/* Caller must hold local->sta_mtx */ static int sta_info_hash_del(struct ieee80211_local *local, struct sta_info *sta) { @@ -99,19 +98,36 @@ static int link_sta_info_hash_add(struct ieee80211_local *local, struct link_sta_info *link_sta) { - lockdep_assert_held(&local->sta_mtx); + lockdep_assert_wiphy(local->hw.wiphy); + return rhltable_insert(&local->link_sta_hash, - &link_sta->link_hash_node, - link_sta_rht_params); + &link_sta->link_hash_node, link_sta_rht_params); } static int link_sta_info_hash_del(struct ieee80211_local *local, struct link_sta_info *link_sta) { - lockdep_assert_held(&local->sta_mtx); + lockdep_assert_wiphy(local->hw.wiphy); + return rhltable_remove(&local->link_sta_hash, - &link_sta->link_hash_node, - link_sta_rht_params); + &link_sta->link_hash_node, link_sta_rht_params); +} + +void ieee80211_purge_sta_txqs(struct sta_info *sta) +{ + struct ieee80211_local *local = sta->sdata->local; + int i; + + for (i = 0; i < ARRAY_SIZE(sta->sta.txq); i++) { + struct txq_info *txqi; + + if (!sta->sta.txq[i]) + continue; + + txqi = to_txq_info(sta->sta.txq[i]); + + ieee80211_txq_purge(local, txqi); + } } static void __cleanup_single_sta(struct sta_info *sta) @@ -140,16 +156,7 @@ atomic_dec(&ps->num_sta_ps); } - for (i = 0; i < ARRAY_SIZE(sta->sta.txq); i++) { - struct txq_info *txqi; - - if (!sta->sta.txq[i]) - continue; - - txqi = to_txq_info(sta->sta.txq[i]); - - ieee80211_txq_purge(local, txqi); - } + ieee80211_purge_sta_txqs(sta); for (ac = 0; ac < IEEE80211_NUM_ACS; ac++) { local->total_ps_buffered -= skb_queue_len(&sta->ps_tx_buf[ac]); @@ -331,7 +338,7 @@ int i = 0; list_for_each_entry_rcu(sta, &local->sta_list, list, - lockdep_is_held(&local->sta_mtx)) { + lockdep_is_held(&local->hw.wiphy->mtx)) { if (sdata != sta->sdata) continue; if (i < idx) { @@ -355,10 +362,9 @@ struct sta_link_alloc *alloc = NULL; struct link_sta_info *link_sta; - link_sta = rcu_access_pointer(sta->link[link_id]); - if (link_sta != &sta->deflink) - lockdep_assert_held(&sta->local->sta_mtx); + lockdep_assert_wiphy(sta->local->hw.wiphy); + link_sta = rcu_access_pointer(sta->link[link_id]); if (WARN_ON(!link_sta)) return; @@ -437,7 +443,6 @@ kfree(sta); } -/* Caller must hold local->sta_mtx */ static int sta_info_hash_add(struct ieee80211_local *local, struct sta_info *sta) { @@ -556,8 +561,7 @@ spin_lock_init(&sta->lock); spin_lock_init(&sta->ps_lock); INIT_WORK(&sta->drv_deliver_wk, sta_deliver_ps_frames); - INIT_WORK(&sta->ampdu_mlme.work, ieee80211_ba_session_work); - mutex_init(&sta->ampdu_mlme.mtx); + wiphy_work_init(&sta->ampdu_mlme.work, ieee80211_ba_session_work); #ifdef CPTCFG_MAC80211_MESH if (ieee80211_vif_is_mesh(&sdata->vif)) { sta->mesh = kzalloc(sizeof(*sta->mesh), gfp); @@ -717,6 +721,8 @@ { struct ieee80211_sub_if_data *sdata = sta->sdata; + lockdep_assert_wiphy(sdata->local->hw.wiphy); + /* * Can't be a WARN_ON because it can be triggered through a race: * something inserts a STA (on one CPU) without holding the RTNL @@ -734,7 +740,6 @@ * for correctness. */ rcu_read_lock(); - lockdep_assert_held(&sdata->local->sta_mtx); if (ieee80211_hw_check(&sdata->local->hw, NEEDS_UNIQUE_STA_ADDR) && ieee80211_find_sta_by_ifaddr(&sdata->local->hw, sta->addr, NULL)) { rcu_read_unlock(); @@ -808,11 +813,6 @@ } } -/* - * should be called with sta_mtx locked - * this function replaces the mutex lock - * with a RCU lock - */ static int sta_info_insert_finish(struct sta_info *sta) __acquires(RCU) { struct ieee80211_local *local = sta->local; @@ -820,7 +820,7 @@ struct station_info *sinfo = NULL; int err = 0; - lockdep_assert_held(&local->sta_mtx); + lockdep_assert_wiphy(local->hw.wiphy); /* check if STA exists already */ if (sta_info_get_bss(sdata, sta->sta.addr)) { @@ -884,7 +884,7 @@ struct link_sta_info *link_sta; link_sta = rcu_dereference_protected(sta->link[i], - lockdep_is_held(&local->sta_mtx)); + lockdep_is_held(&local->hw.wiphy->mtx)); if (!link_sta) continue; @@ -906,7 +906,6 @@ /* move reference to rcu-protected */ rcu_read_lock(); - mutex_unlock(&local->sta_mtx); if (ieee80211_vif_is_mesh(&sdata->vif)) mesh_accept_plinks_update(sdata); @@ -922,7 +921,6 @@ synchronize_net(); out_cleanup: cleanup_single_sta(sta); - mutex_unlock(&local->sta_mtx); kfree(sinfo); rcu_read_lock(); return err; @@ -934,13 +932,11 @@ int err; might_sleep(); - - mutex_lock(&local->sta_mtx); + lockdep_assert_wiphy(local->hw.wiphy); err = sta_info_insert_check(sta); if (err) { sta_info_free(local, sta); - mutex_unlock(&local->sta_mtx); rcu_read_lock(); return err; } @@ -1219,7 +1215,7 @@ local = sta->local; sdata = sta->sdata; - lockdep_assert_held(&local->sta_mtx); + lockdep_assert_wiphy(local->hw.wiphy); /* * Before removing the station from the driver and @@ -1244,7 +1240,7 @@ continue; link_sta = rcu_dereference_protected(sta->link[i], - lockdep_is_held(&local->sta_mtx)); + lockdep_is_held(&local->hw.wiphy->mtx)); link_sta_info_hash_del(local, link_sta); } @@ -1279,6 +1275,8 @@ enum ieee80211_sta_state new_state, bool recalc) { + struct ieee80211_local *local = sta->local; + might_sleep(); if (sta->sta_state == new_state) @@ -1355,6 +1353,24 @@ } else if (sta->sta_state == IEEE80211_STA_AUTHORIZED) { ieee80211_vif_dec_num_mcast(sta->sdata); clear_bit(WLAN_STA_AUTHORIZED, &sta->_flags); + + /* + * If we have encryption offload, flush (station) queues + * (after ensuring concurrent TX completed) so we won't + * transmit anything later unencrypted if/when keys are + * also removed, which might otherwise happen depending + * on how the hardware offload works. + */ + if (local->ops->set_key) { + synchronize_net(); + if (local->ops->flush_sta) + drv_flush_sta(local, sta->sdata, sta); + else + ieee80211_flush_queues(local, + sta->sdata, + false); + } + ieee80211_clear_fast_xmit(sta); ieee80211_clear_fast_rx(sta); } @@ -1399,25 +1415,13 @@ */ might_sleep(); - lockdep_assert_held(&local->sta_mtx); + lockdep_assert_wiphy(local->hw.wiphy); if (sta->sta_state == IEEE80211_STA_AUTHORIZED) { ret = _sta_info_move_state(sta, IEEE80211_STA_ASSOC, recalc); WARN_ON_ONCE(ret); } - /* Flush queues before removing keys, as that might remove them - * from hardware, and then depending on the offload method, any - * frames sitting on hardware queues might be sent out without - * any encryption at all. - */ - if (local->ops->set_key) { - if (local->ops->flush_sta) - drv_flush_sta(local, sta->sdata, sta); - else - ieee80211_flush_queues(local, sta->sdata, false); - } - /* now keys can no longer be reached */ ieee80211_free_sta_keys(local, sta); @@ -1475,28 +1479,22 @@ int sta_info_destroy_addr(struct ieee80211_sub_if_data *sdata, const u8 *addr) { struct sta_info *sta; - int ret; - mutex_lock(&sdata->local->sta_mtx); - sta = sta_info_get(sdata, addr); - ret = __sta_info_destroy(sta); - mutex_unlock(&sdata->local->sta_mtx); + lockdep_assert_wiphy(sdata->local->hw.wiphy); - return ret; + sta = sta_info_get(sdata, addr); + return __sta_info_destroy(sta); } int sta_info_destroy_addr_bss(struct ieee80211_sub_if_data *sdata, const u8 *addr) { struct sta_info *sta; - int ret; - mutex_lock(&sdata->local->sta_mtx); - sta = sta_info_get_bss(sdata, addr); - ret = __sta_info_destroy(sta); - mutex_unlock(&sdata->local->sta_mtx); + lockdep_assert_wiphy(sdata->local->hw.wiphy); - return ret; + sta = sta_info_get_bss(sdata, addr); + return __sta_info_destroy(sta); } static void sta_info_cleanup(struct timer_list *t) @@ -1536,7 +1534,6 @@ } spin_lock_init(&local->tim_lock); - mutex_init(&local->sta_mtx); INIT_LIST_HEAD(&local->sta_list); timer_setup(&local->sta_cleanup, sta_info_cleanup, 0); @@ -1559,11 +1556,11 @@ int ret = 0; might_sleep(); + lockdep_assert_wiphy(local->hw.wiphy); WARN_ON(vlans && sdata->vif.type != NL80211_IFTYPE_AP); WARN_ON(vlans && !sdata->bss); - mutex_lock(&local->sta_mtx); list_for_each_entry_safe(sta, tmp, &local->sta_list, list) { if (sdata == sta->sdata || (vlans && sdata->bss == sta->sdata->bss)) { @@ -1587,7 +1584,6 @@ if (!support_p2p_ps) ieee80211_recalc_p2p_go_ps_allowed(sdata); } - mutex_unlock(&local->sta_mtx); return ret; } @@ -1598,7 +1594,7 @@ struct ieee80211_local *local = sdata->local; struct sta_info *sta, *tmp; - mutex_lock(&local->sta_mtx); + lockdep_assert_wiphy(local->hw.wiphy); list_for_each_entry_safe(sta, tmp, &local->sta_list, list) { unsigned long last_active = ieee80211_sta_last_active(sta); @@ -1617,8 +1613,6 @@ WARN_ON(__sta_info_destroy(sta)); } } - - mutex_unlock(&local->sta_mtx); } struct ieee80211_sta *ieee80211_find_sta_by_ifaddr(struct ieee80211_hw *hw, @@ -2873,7 +2867,7 @@ struct sta_link_alloc *alloc; int ret; - lockdep_assert_held(&sdata->local->sta_mtx); + lockdep_assert_wiphy(sdata->local->hw.wiphy); WARN_ON(!test_sta_flag(sta, WLAN_STA_INSERTED)); @@ -2904,7 +2898,7 @@ void ieee80211_sta_free_link(struct sta_info *sta, unsigned int link_id) { - lockdep_assert_held(&sta->sdata->local->sta_mtx); + lockdep_assert_wiphy(sta->sdata->local->hw.wiphy); WARN_ON(!test_sta_flag(sta, WLAN_STA_INSERTED)); @@ -2920,7 +2914,7 @@ int ret; link_sta = rcu_dereference_protected(sta->link[link_id], - lockdep_is_held(&sdata->local->sta_mtx)); + lockdep_is_held(&sdata->local->hw.wiphy->mtx)); if (WARN_ON(old_links == new_links || !link_sta)) return -EINVAL; @@ -2964,7 +2958,7 @@ struct ieee80211_sub_if_data *sdata = sta->sdata; u16 old_links = sta->sta.valid_links; - lockdep_assert_held(&sdata->local->sta_mtx); + lockdep_assert_wiphy(sdata->local->hw.wiphy); sta->sta.valid_links &= ~BIT(link_id); @@ -3003,7 +2997,7 @@ { struct sta_info *sta = container_of(pubsta, struct sta_info, sta); - return lockdep_is_held(&sta->local->sta_mtx); + return lockdep_is_held(&sta->local->hw.wiphy->mtx); } EXPORT_SYMBOL(lockdep_sta_mutex_held); #endif diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/sta_info.h backport-iwlwifi-dkms-11510/net/mac80211/sta_info.h --- backport-iwlwifi-dkms-11289/net/mac80211/sta_info.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/sta_info.h 2023-10-04 04:18:43.000000000 +0800 @@ -259,9 +259,6 @@ /** * struct sta_ampdu_mlme - STA aggregation information. * - * @mtx: mutex to protect all TX data (except non-NULL assignments - * to tid_tx[idx], which are protected by the sta spinlock) - * tid_start_tx is also protected by sta->lock. * @tid_rx: aggregation info for Rx per TID -- RCU protected * @tid_rx_token: dialog tokens for valid aggregation sessions * @tid_rx_timer_expired: bitmap indicating on which TIDs the @@ -275,13 +272,13 @@ * unexpected aggregation related frames outside a session * @work: work struct for starting/stopping aggregation * @tid_tx: aggregation info for Tx per TID - * @tid_start_tx: sessions where start was requested + * @tid_start_tx: sessions where start was requested, not just protected + * by wiphy mutex but also sta->lock * @last_addba_req_time: timestamp of the last addBA request. * @addba_req_num: number of times addBA request has been sent. * @dialog_token_allocator: dialog token enumerator for each new session; */ struct sta_ampdu_mlme { - struct mutex mtx; /* rx */ struct tid_ampdu_rx __rcu *tid_rx[IEEE80211_NUM_TIDS]; u8 tid_rx_token[IEEE80211_NUM_TIDS]; @@ -291,7 +288,7 @@ unsigned long agg_session_valid[BITS_TO_LONGS(IEEE80211_NUM_TIDS)]; unsigned long unexpected_agg[BITS_TO_LONGS(IEEE80211_NUM_TIDS)]; /* tx */ - struct work_struct work; + struct wiphy_work work; struct tid_ampdu_tx __rcu *tid_tx[IEEE80211_NUM_TIDS]; struct tid_ampdu_tx *tid_start_tx[IEEE80211_NUM_TIDS]; unsigned long last_addba_req_time[IEEE80211_NUM_TIDS]; @@ -793,13 +790,10 @@ void ieee80211_assign_tid_tx(struct sta_info *sta, int tid, struct tid_ampdu_tx *tid_tx); -static inline struct tid_ampdu_tx * -rcu_dereference_protected_tid_tx(struct sta_info *sta, int tid) -{ - return rcu_dereference_protected(sta->ampdu_mlme.tid_tx[tid], - lockdep_is_held(&sta->lock) || - lockdep_is_held(&sta->ampdu_mlme.mtx)); -} +#define rcu_dereference_protected_tid_tx(sta, tid) \ + rcu_dereference_protected((sta)->ampdu_mlme.tid_tx[tid], \ + lockdep_is_held(&(sta)->lock) || \ + lockdep_is_held(&(sta)->local->hw.wiphy->mtx)); /* Maximum number of frames to buffer per power saving station per AC */ #define STA_MAX_TX_BUFFER 64 @@ -824,7 +818,7 @@ struct sta_info *sta_info_get_bss(struct ieee80211_sub_if_data *sdata, const u8 *addr); -/* user must hold sta_mtx or be in RCU critical section */ +/* user must hold wiphy mutex or be in RCU critical section */ struct sta_info *sta_info_get_by_addrs(struct ieee80211_local *local, const u8 *sta_addr, const u8 *vif_addr); diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/status.c backport-iwlwifi-dkms-11510/net/mac80211/status.c --- backport-iwlwifi-dkms-11289/net/mac80211/status.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/status.c 2023-10-04 04:18:43.000000000 +0800 @@ -184,8 +184,6 @@ static void ieee80211_frame_acked(struct sta_info *sta, struct sk_buff *skb) { struct ieee80211_mgmt *mgmt = (void *) skb->data; - struct ieee80211_local *local = sta->local; - struct ieee80211_sub_if_data *sdata = sta->sdata; if (ieee80211_is_data_qos(mgmt->frame_control)) { struct ieee80211_hdr *hdr = (void *) skb->data; @@ -194,39 +192,6 @@ ieee80211_check_pending_bar(sta, hdr->addr1, tid); } - - if (ieee80211_is_action(mgmt->frame_control) && - !ieee80211_has_protected(mgmt->frame_control) && - mgmt->u.action.category == WLAN_CATEGORY_HT && - mgmt->u.action.u.ht_smps.action == WLAN_HT_ACTION_SMPS && - ieee80211_sdata_running(sdata)) { - enum ieee80211_smps_mode smps_mode; - - switch (mgmt->u.action.u.ht_smps.smps_control) { - case WLAN_HT_SMPS_CONTROL_DYNAMIC: - smps_mode = IEEE80211_SMPS_DYNAMIC; - break; - case WLAN_HT_SMPS_CONTROL_STATIC: - smps_mode = IEEE80211_SMPS_STATIC; - break; - case WLAN_HT_SMPS_CONTROL_DISABLED: - default: /* shouldn't happen since we don't send that */ - smps_mode = IEEE80211_SMPS_OFF; - break; - } - - if (sdata->vif.type == NL80211_IFTYPE_STATION) { - /* - * This update looks racy, but isn't -- if we come - * here we've definitely got a station that we're - * talking to, and on a managed interface that can - * only be the AP. And the only other place updating - * this variable in managed mode is before association. - */ - sdata->deflink.smps_mode = smps_mode; - ieee80211_queue_work(&local->hw, &sdata->recalc_smps); - } - } } static void ieee80211_set_bar_pending(struct sta_info *sta, u8 tid, u16 ssn) @@ -633,7 +598,7 @@ unsigned long flags; spin_lock_irqsave(&local->ack_status_lock, flags); - skb = idr_remove(&local->ack_status_frames, info->ack_frame_id); + skb = idr_remove(&local->ack_status_frames, info->status_data); spin_unlock_irqrestore(&local->ack_status_lock, flags); if (!skb) @@ -695,6 +660,42 @@ } } +static void ieee80211_handle_smps_status(struct ieee80211_sub_if_data *sdata, + bool acked, u16 status_data) +{ + u16 sub_data = u16_get_bits(status_data, IEEE80211_STATUS_SUBDATA_MASK); + enum ieee80211_smps_mode smps_mode = sub_data & 3; + int link_id = (sub_data >> 2); + struct ieee80211_link_data *link; + + if (!sdata || !ieee80211_sdata_running(sdata)) + return; + + if (!acked) + return; + + if (sdata->vif.type != NL80211_IFTYPE_STATION) + return; + + if (WARN(link_id >= ARRAY_SIZE(sdata->link), + "bad SMPS status link: %d\n", link_id)) + return; + + link = rcu_dereference(sdata->link[link_id]); + if (!link) + return; + + /* + * This update looks racy, but isn't, the only other place + * updating this variable is in managed mode before assoc, + * and we have to be associated to have a status from the + * action frame TX, since we cannot send it while we're not + * associated yet. + */ + link->smps_mode = smps_mode; + wiphy_work_queue(sdata->local->hw.wiphy, &link->u.mgd.recalc_smps); +} + static void ieee80211_report_used_skb(struct ieee80211_local *local, struct sk_buff *skb, bool dropped, ktime_t ack_hwtstamp) @@ -759,9 +760,24 @@ } rcu_read_unlock(); - } else if (info->ack_frame_id) { + } else if (info->status_data_idr) { ieee80211_report_ack_skb(local, skb, acked, dropped, ack_hwtstamp); + } else if (info->status_data) { + struct ieee80211_sub_if_data *sdata; + + rcu_read_lock(); + + sdata = ieee80211_sdata_from_skb(local, skb); + + switch (u16_get_bits(info->status_data, + IEEE80211_STATUS_TYPE_MASK)) { + case IEEE80211_STATUS_TYPE_SMPS: + ieee80211_handle_smps_status(sdata, acked, + info->status_data); + break; + } + rcu_read_unlock(); } if (!dropped && skb->destructor) { diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/tdls.c backport-iwlwifi-dkms-11510/net/mac80211/tdls.c --- backport-iwlwifi-dkms-11289/net/mac80211/tdls.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/tdls.c 2023-10-04 04:18:43.000000000 +0800 @@ -21,7 +21,7 @@ /* give usermode some time for retries in setting up the TDLS session */ #define TDLS_PEER_SETUP_TIMEOUT (15 * HZ) -void ieee80211_tdls_peer_del_work(struct work_struct *wk) +void ieee80211_tdls_peer_del_work(struct wiphy *wiphy, struct wiphy_work *wk) { struct ieee80211_sub_if_data *sdata; struct ieee80211_local *local; @@ -30,13 +30,13 @@ u.mgd.tdls_peer_del_work.work); local = sdata->local; - mutex_lock(&local->mtx); + lockdep_assert_wiphy(local->hw.wiphy); + if (!is_zero_ether_addr(sdata->u.mgd.tdls_peer)) { tdls_dbg(sdata, "TDLS del peer %pM\n", sdata->u.mgd.tdls_peer); sta_info_destroy_addr(sdata, sdata->u.mgd.tdls_peer); eth_zero_addr(sdata->u.mgd.tdls_peer); } - mutex_unlock(&local->mtx); } static void ieee80211_tdls_add_ext_capab(struct ieee80211_link_data *link, @@ -432,15 +432,11 @@ offset = noffset; } - mutex_lock(&local->sta_mtx); - /* we should have the peer STA if we're already responding */ if (action_code == WLAN_TDLS_SETUP_RESPONSE) { sta = sta_info_get(sdata, peer); - if (WARN_ON_ONCE(!sta)) { - mutex_unlock(&local->sta_mtx); + if (WARN_ON_ONCE(!sta)) return; - } sta->tdls_chandef = link->conf->chandef; } @@ -573,7 +569,8 @@ pos = skb_put(skb, cap_size); he_6ghz_capa = ieee80211_get_he_6ghz_capa_vif(sband, &sdata->vif); - pos = ieee80211_write_he_6ghz_cap(pos, he_6ghz_capa, pos + cap_size); + pos = ieee80211_write_he_6ghz_cap(pos, he_6ghz_capa, + pos + cap_size); } } @@ -609,7 +606,6 @@ pos = skb_put(skb, cap_size); ieee80211_ie_build_eht_cap(pos, he_cap, eht_cap, pos + cap_size, false); } - mutex_unlock(&local->sta_mtx); /* add any remaining IEs */ if (extra_ies_len) { @@ -636,15 +632,11 @@ if (WARN_ON_ONCE(!sband)) return; - mutex_lock(&local->sta_mtx); - sta = sta_info_get(sdata, peer); ap_sta = sta_info_get(sdata, sdata->vif.cfg.ap_addr); - if (WARN_ON_ONCE(!sta || !ap_sta)) { - mutex_unlock(&local->sta_mtx); + if (WARN_ON_ONCE(!sta || !ap_sta)) return; - } sta->tdls_chandef = link->conf->chandef; @@ -713,8 +705,6 @@ &sta->tdls_chandef); } - mutex_unlock(&local->sta_mtx); - /* add any remaining IEs */ if (extra_ies_len) { noffset = extra_ies_len; @@ -944,10 +934,11 @@ static struct sk_buff * ieee80211_tdls_build_mgmt_packet_data(struct ieee80211_sub_if_data *sdata, - const u8 *peer, int link_id, u8 action_code, - u8 dialog_token, u16 status_code, - bool initiator, const u8 *extra_ies, - size_t extra_ies_len, u8 oper_class, + const u8 *peer, int link_id, + u8 action_code, u8 dialog_token, + u16 status_code, bool initiator, + const u8 *extra_ies, size_t extra_ies_len, + u8 oper_class, struct cfg80211_chan_def *chandef) { struct ieee80211_local *local = sdata->local; @@ -956,9 +947,10 @@ struct ieee80211_link_data *link; link_id = link_id >= 0 ? link_id : 0; - link = sdata_dereference(sdata->link[link_id], sdata); + rcu_read_lock(); + link = rcu_dereference(sdata->link[link_id]); if (WARN_ON(!link)) - return NULL; + goto unlock; skb = netdev_alloc_skb(sdata->dev, local->hw.extra_tx_headroom + @@ -985,7 +977,7 @@ extra_ies_len + sizeof(struct ieee80211_tdls_lnkie)); if (!skb) - return NULL; + goto unlock; skb_reserve(skb, local->hw.extra_tx_headroom); @@ -1019,10 +1011,13 @@ ieee80211_tdls_add_ies(link, skb, peer, action_code, status_code, initiator, extra_ies, extra_ies_len, oper_class, chandef); + rcu_read_unlock(); return skb; fail: dev_kfree_skb(skb); +unlock: + rcu_read_unlock(); return NULL; } @@ -1185,7 +1180,7 @@ return -ENOTSUPP; } - mutex_lock(&local->mtx); + lockdep_assert_wiphy(local->hw.wiphy); /* we don't support concurrent TDLS peer setups */ if (!is_zero_ether_addr(sdata->u.mgd.tdls_peer) && @@ -1213,7 +1208,6 @@ ieee80211_flush_queues(local, sdata, false); memcpy(sdata->u.mgd.tdls_peer, peer, ETH_ALEN); - mutex_unlock(&local->mtx); /* we cannot take the mutex while preparing the setup packet */ ret = ieee80211_tdls_prep_mgmt_packet(wiphy, dev, peer, @@ -1223,19 +1217,16 @@ extra_ies, extra_ies_len, 0, NULL); if (ret < 0) { - mutex_lock(&local->mtx); eth_zero_addr(sdata->u.mgd.tdls_peer); - mutex_unlock(&local->mtx); return ret; } - ieee80211_queue_delayed_work(&sdata->local->hw, - &sdata->u.mgd.tdls_peer_del_work, - TDLS_PEER_SETUP_TIMEOUT); + wiphy_delayed_work_queue(sdata->local->hw.wiphy, + &sdata->u.mgd.tdls_peer_del_work, + TDLS_PEER_SETUP_TIMEOUT); return 0; out_unlock: - mutex_unlock(&local->mtx); return ret; } @@ -1288,7 +1279,8 @@ return 0; } -int ieee80211_tdls_mgmt(struct wiphy *wiphy, struct net_device *dev, const u8 *peer, int link_id, +int ieee80211_tdls_mgmt(struct wiphy *wiphy, struct net_device *dev, + const u8 *peer, int link_id, u8 action_code, u8 dialog_token, u16 status_code, u32 peer_capability, bool initiator, const u8 *extra_ies, size_t extra_ies_len) @@ -1326,7 +1318,7 @@ * response frame. It is transmitted directly and not buffered * by the AP. */ - drv_mgd_protect_tdls_discover(sdata->local, sdata); + drv_mgd_protect_tdls_discover(sdata->local, sdata, link_id); fallthrough; case WLAN_TDLS_SETUP_CONFIRM: case WLAN_PUB_ACTION_TDLS_DISCOVER_RES: @@ -1358,9 +1350,10 @@ enum nl80211_chan_width width; struct ieee80211_supported_band *sband; - mutex_lock(&local->chanctx_mtx); + lockdep_assert_wiphy(local->hw.wiphy); + conf = rcu_dereference_protected(sdata->vif.bss_conf.chanctx_conf, - lockdep_is_held(&local->chanctx_mtx)); + lockdep_is_held(&local->hw.wiphy->mtx)); if (conf) { width = conf->def.width; sband = local->hw.wiphy->bands[conf->def.chan->band]; @@ -1388,7 +1381,6 @@ } } - mutex_unlock(&local->chanctx_mtx); } static int iee80211_tdls_have_ht_peers(struct ieee80211_sub_if_data *sdata) @@ -1451,6 +1443,8 @@ struct ieee80211_local *local = sdata->local; int ret; + lockdep_assert_wiphy(local->hw.wiphy); + if (!(wiphy->flags & WIPHY_FLAG_SUPPORTS_TDLS)) return -ENOTSUPP; @@ -1471,35 +1465,26 @@ /* protect possible bss_conf changes and avoid concurrency in * ieee80211_bss_info_change_notify() */ - sdata_lock(sdata); - mutex_lock(&local->mtx); tdls_dbg(sdata, "TDLS oper %d peer %pM\n", oper, peer); switch (oper) { case NL80211_TDLS_ENABLE_LINK: if (sdata->vif.bss_conf.csa_active) { tdls_dbg(sdata, "TDLS: disallow link during CSA\n"); - ret = -EBUSY; - break; + return -EBUSY; } - mutex_lock(&local->sta_mtx); sta = sta_info_get(sdata, peer); - if (!sta) { - mutex_unlock(&local->sta_mtx); - ret = -ENOLINK; - break; - } + if (!sta) + return -ENOLINK; iee80211_tdls_recalc_chanctx(sdata, sta); iee80211_tdls_recalc_ht_protection(sdata, sta); set_sta_flag(sta, WLAN_STA_TDLS_PEER_AUTH); - mutex_unlock(&local->sta_mtx); WARN_ON_ONCE(is_zero_ether_addr(sdata->u.mgd.tdls_peer) || !ether_addr_equal(sdata->u.mgd.tdls_peer, peer)); - ret = 0; break; case NL80211_TDLS_DISABLE_LINK: /* @@ -1518,29 +1503,26 @@ ret = sta_info_destroy_addr(sdata, peer); - mutex_lock(&local->sta_mtx); iee80211_tdls_recalc_ht_protection(sdata, NULL); - mutex_unlock(&local->sta_mtx); iee80211_tdls_recalc_chanctx(sdata, NULL); + if (ret) + return ret; break; default: - ret = -ENOTSUPP; - break; + return -ENOTSUPP; } - if (ret == 0 && ether_addr_equal(sdata->u.mgd.tdls_peer, peer)) { - cancel_delayed_work(&sdata->u.mgd.tdls_peer_del_work); + if (ether_addr_equal(sdata->u.mgd.tdls_peer, peer)) { + wiphy_delayed_work_cancel(sdata->local->hw.wiphy, + &sdata->u.mgd.tdls_peer_del_work); eth_zero_addr(sdata->u.mgd.tdls_peer); } - if (ret == 0) - wiphy_work_queue(sdata->local->hw.wiphy, - &sdata->deflink.u.mgd.request_smps_work); + wiphy_work_queue(sdata->local->hw.wiphy, + &sdata->deflink.u.mgd.request_smps_work); - mutex_unlock(&local->mtx); - sdata_unlock(sdata); - return ret; + return 0; } void ieee80211_tdls_oper_request(struct ieee80211_vif *vif, const u8 *peer, @@ -1673,11 +1655,12 @@ u32 ch_sw_tm_ie; int ret; + lockdep_assert_wiphy(local->hw.wiphy); + if (chandef->chan->freq_offset) /* this may work, but is untested */ return -EOPNOTSUPP; - mutex_lock(&local->sta_mtx); sta = sta_info_get(sdata, addr); if (!sta) { tdls_dbg(sdata, @@ -1707,7 +1690,6 @@ set_sta_flag(sta, WLAN_STA_TDLS_OFF_CHANNEL); out: - mutex_unlock(&local->sta_mtx); dev_kfree_skb_any(skb); return ret; } @@ -1721,26 +1703,24 @@ struct ieee80211_local *local = sdata->local; struct sta_info *sta; - mutex_lock(&local->sta_mtx); + lockdep_assert_wiphy(local->hw.wiphy); + sta = sta_info_get(sdata, addr); if (!sta) { tdls_dbg(sdata, "Invalid TDLS peer %pM for channel switch cancel\n", addr); - goto out; + return; } if (!test_sta_flag(sta, WLAN_STA_TDLS_OFF_CHANNEL)) { tdls_dbg(sdata, "TDLS channel switch not initiated by %pM\n", addr); - goto out; + return; } drv_tdls_cancel_channel_switch(local, sdata, &sta->sta); clear_sta_flag(sta, WLAN_STA_TDLS_OFF_CHANNEL); - -out: - mutex_unlock(&local->sta_mtx); } static struct sk_buff * @@ -1802,6 +1782,8 @@ struct ieee80211_tdls_ch_sw_params params = {}; int ret; + lockdep_assert_wiphy(local->hw.wiphy); + params.action_code = WLAN_TDLS_CHANNEL_SWITCH_RESPONSE; params.timestamp = rx_status->device_timestamp; @@ -1811,7 +1793,6 @@ return -EINVAL; } - mutex_lock(&local->sta_mtx); sta = sta_info_get(sdata, tf->sa); if (!sta || !test_sta_flag(sta, WLAN_STA_TDLS_PEER_AUTH)) { tdls_dbg(sdata, "TDLS chan switch from non-peer sta %pM\n", @@ -1874,7 +1855,6 @@ tf->sa, params.status); out: - mutex_unlock(&local->sta_mtx); dev_kfree_skb_any(params.tmpl_skb); kfree(elems); return ret; @@ -1900,6 +1880,8 @@ struct ieee80211_tdls_ch_sw_params params = {}; int ret = 0; + lockdep_assert_wiphy(local->hw.wiphy); + params.action_code = WLAN_TDLS_CHANNEL_SWITCH_REQUEST; params.timestamp = rx_status->device_timestamp; @@ -1988,7 +1970,6 @@ goto free; } - mutex_lock(&local->sta_mtx); sta = sta_info_get(sdata, tf->sa); if (!sta || !test_sta_flag(sta, WLAN_STA_TDLS_PEER_AUTH)) { tdls_dbg(sdata, "TDLS chan switch from non-peer sta %pM\n", @@ -2035,7 +2016,6 @@ tf->sa, params.chandef->chan->center_freq, params.chandef->width); out: - mutex_unlock(&local->sta_mtx); dev_kfree_skb_any(params.tmpl_skb); free: kfree(elems); diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/tests/mfp.c backport-iwlwifi-dkms-11510/net/mac80211/tests/mfp.c --- backport-iwlwifi-dkms-11289/net/mac80211/tests/mfp.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/tests/mfp.c 2023-10-04 04:18:43.000000000 +0800 @@ -13,116 +13,190 @@ static const struct mfp_test_case { const char *desc; - bool sta, mfp, decrypted, unicast, protected_dual; - int result; -} accept_public_action_cases[] = { + bool sta, mfp, decrypted, unicast, assoc; + u8 category; + u8 stype; + ieee80211_rx_result result; +} accept_mfp_cases[] = { /* regular public action */ { .desc = "public action: accept unicast from unknown peer", + .stype = IEEE80211_STYPE_ACTION, + .category = WLAN_CATEGORY_PUBLIC, .unicast = true, - .result = 0, + .result = RX_CONTINUE, }, { .desc = "public action: accept multicast from unknown peer", + .stype = IEEE80211_STYPE_ACTION, + .category = WLAN_CATEGORY_PUBLIC, .unicast = false, - .result = 0, + .result = RX_CONTINUE, }, { .desc = "public action: accept unicast without MFP", + .stype = IEEE80211_STYPE_ACTION, + .category = WLAN_CATEGORY_PUBLIC, .unicast = true, .sta = true, - .result = 0, + .result = RX_CONTINUE, }, { .desc = "public action: accept multicast without MFP", + .stype = IEEE80211_STYPE_ACTION, + .category = WLAN_CATEGORY_PUBLIC, .unicast = false, .sta = true, - .result = 0, + .result = RX_CONTINUE, }, { .desc = "public action: drop unicast with MFP", + .stype = IEEE80211_STYPE_ACTION, + .category = WLAN_CATEGORY_PUBLIC, .unicast = true, .sta = true, .mfp = true, - .result = -EACCES, + .result = RX_DROP_U_UNPROT_UNICAST_PUB_ACTION, }, { .desc = "public action: accept multicast with MFP", + .stype = IEEE80211_STYPE_ACTION, + .category = WLAN_CATEGORY_PUBLIC, .unicast = false, .sta = true, .mfp = true, - .result = 0, + .result = RX_CONTINUE, }, /* protected dual of public action */ { .desc = "protected dual: drop unicast from unknown peer", - .protected_dual = true, + .stype = IEEE80211_STYPE_ACTION, + .category = WLAN_CATEGORY_PROTECTED_DUAL_OF_ACTION, .unicast = true, - .result = -EACCES, + .result = RX_DROP_U_UNPROT_DUAL, }, { .desc = "protected dual: drop multicast from unknown peer", - .protected_dual = true, + .stype = IEEE80211_STYPE_ACTION, + .category = WLAN_CATEGORY_PROTECTED_DUAL_OF_ACTION, .unicast = false, - .result = -EACCES, + .result = RX_DROP_U_UNPROT_DUAL, }, { .desc = "protected dual: drop unicast without MFP", - .protected_dual = true, + .stype = IEEE80211_STYPE_ACTION, + .category = WLAN_CATEGORY_PROTECTED_DUAL_OF_ACTION, .unicast = true, .sta = true, - .result = -EACCES, + .result = RX_DROP_U_UNPROT_DUAL, }, { .desc = "protected dual: drop multicast without MFP", - .protected_dual = true, + .stype = IEEE80211_STYPE_ACTION, + .category = WLAN_CATEGORY_PROTECTED_DUAL_OF_ACTION, .unicast = false, .sta = true, - .result = -EACCES, + .result = RX_DROP_U_UNPROT_DUAL, }, { .desc = "protected dual: drop undecrypted unicast with MFP", - .protected_dual = true, + .stype = IEEE80211_STYPE_ACTION, + .category = WLAN_CATEGORY_PROTECTED_DUAL_OF_ACTION, .unicast = true, .sta = true, .mfp = true, - .result = -EACCES, + .result = RX_DROP_U_UNPROT_DUAL, }, { .desc = "protected dual: drop undecrypted multicast with MFP", - .protected_dual = true, + .stype = IEEE80211_STYPE_ACTION, + .category = WLAN_CATEGORY_PROTECTED_DUAL_OF_ACTION, .unicast = false, .sta = true, .mfp = true, - .result = -EACCES, + .result = RX_DROP_U_UNPROT_DUAL, }, { .desc = "protected dual: accept unicast with MFP", - .protected_dual = true, + .stype = IEEE80211_STYPE_ACTION, + .category = WLAN_CATEGORY_PROTECTED_DUAL_OF_ACTION, .decrypted = true, .unicast = true, .sta = true, .mfp = true, - .result = 0, + .result = RX_CONTINUE, }, { .desc = "protected dual: accept multicast with MFP", - .protected_dual = true, + .stype = IEEE80211_STYPE_ACTION, + .category = WLAN_CATEGORY_PROTECTED_DUAL_OF_ACTION, .decrypted = true, .unicast = false, .sta = true, .mfp = true, - .result = 0, + .result = RX_CONTINUE, + }, + /* deauth/disassoc before keys are set */ + { + .desc = "deauth: accept unicast with MFP but w/o key", + .stype = IEEE80211_STYPE_DEAUTH, + .sta = true, + .mfp = true, + .unicast = true, + .result = RX_CONTINUE, + }, + { + .desc = "disassoc: accept unicast with MFP but w/o key", + .stype = IEEE80211_STYPE_DEAUTH, + .sta = true, + .mfp = true, + .unicast = true, + .result = RX_CONTINUE, + }, + /* non-public robust action frame ... */ + { + .desc = "BA action: drop unicast before assoc", + .stype = IEEE80211_STYPE_ACTION, + .category = WLAN_CATEGORY_BACK, + .unicast = true, + .sta = true, + .result = RX_DROP_U_UNPROT_ROBUST_ACTION, + }, + { + .desc = "BA action: drop unprotected after assoc", + .stype = IEEE80211_STYPE_ACTION, + .category = WLAN_CATEGORY_BACK, + .unicast = true, + .sta = true, + .mfp = true, + .result = RX_DROP_U_UNPROT_UCAST_MGMT, + }, + { + .desc = "BA action: accept unprotected without MFP", + .stype = IEEE80211_STYPE_ACTION, + .category = WLAN_CATEGORY_BACK, + .unicast = true, + .sta = true, + .assoc = true, + .mfp = false, + .result = RX_CONTINUE, + }, + { + .desc = "BA action: drop unprotected with MFP", + .stype = IEEE80211_STYPE_ACTION, + .category = WLAN_CATEGORY_BACK, + .unicast = true, + .sta = true, + .mfp = true, + .result = RX_DROP_U_UNPROT_UCAST_MGMT, }, }; -KUNIT_ARRAY_PARAM_DESC(accept_public_action, - accept_public_action_cases, - desc); +KUNIT_ARRAY_PARAM_DESC(accept_mfp, accept_mfp_cases, desc); -static void accept_public_action(struct kunit *test) +static void accept_mfp(struct kunit *test) { - static struct sta_info sta = {}; + static struct sta_info sta; const struct mfp_test_case *params = test->param_value; struct ieee80211_rx_data rx = { .sta = params->sta ? &sta : NULL, @@ -130,12 +204,14 @@ struct ieee80211_rx_status *status; struct ieee80211_hdr_3addr hdr = { .frame_control = cpu_to_le16(IEEE80211_FTYPE_MGMT | - IEEE80211_STYPE_ACTION), + params->stype), .addr1 = { 0xff, 0xff, 0xff, 0xff, 0xff, 0xff }, .addr2 = { 0x12, 0x22, 0x33, 0x44, 0x55, 0x66 }, /* A3/BSSID doesn't matter here */ }; + memset(&sta, 0, sizeof(sta)); + if (!params->sta) { KUNIT_ASSERT_FALSE(test, params->mfp); KUNIT_ASSERT_FALSE(test, params->decrypted); @@ -144,6 +220,9 @@ if (params->mfp) set_sta_flag(&sta, WLAN_STA_MFP); + if (params->assoc) + set_bit(WLAN_STA_ASSOC, &sta._flags); + rx.skb = kunit_zalloc_skb(test, 128, GFP_KERNEL); status = IEEE80211_SKB_RXCB(rx.skb); @@ -159,18 +238,26 @@ skb_put_data(rx.skb, &hdr, sizeof(hdr)); - if (params->protected_dual) - skb_put_u8(rx.skb, WLAN_CATEGORY_PROTECTED_DUAL_OF_ACTION); - else - skb_put_u8(rx.skb, WLAN_CATEGORY_PUBLIC); + switch (params->stype) { + case IEEE80211_STYPE_ACTION: + skb_put_u8(rx.skb, params->category); + break; + case IEEE80211_STYPE_DEAUTH: + case IEEE80211_STYPE_DISASSOC: { + __le16 reason = cpu_to_le16(WLAN_REASON_UNSPECIFIED); + + skb_put_data(rx.skb, &reason, sizeof(reason)); + } + break; + } KUNIT_EXPECT_EQ(test, - ieee80211_drop_unencrypted_mgmt(&rx), - params->result); + (__force u32)ieee80211_drop_unencrypted_mgmt(&rx), + (__force u32)params->result); } static struct kunit_case mfp_test_cases[] = { - KUNIT_CASE_PARAM(accept_public_action, accept_public_action_gen_params), + KUNIT_CASE_PARAM(accept_mfp, accept_mfp_gen_params), {} }; diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/trace.h backport-iwlwifi-dkms-11510/net/mac80211/trace.h --- backport-iwlwifi-dkms-11289/net/mac80211/trace.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/trace.h 2023-10-04 04:18:43.000000000 +0800 @@ -17,7 +17,7 @@ #define MAXNAME 32 #define LOCAL_ENTRY __array(char, wiphy_name, 32) -#define LOCAL_ASSIGN strlcpy(__entry->wiphy_name, wiphy_name(local->hw.wiphy), MAXNAME) +#define LOCAL_ASSIGN strscpy(__entry->wiphy_name, wiphy_name(local->hw.wiphy), MAXNAME) #define LOCAL_PR_FMT "%s" #define LOCAL_PR_ARG __entry->wiphy_name @@ -2839,23 +2839,26 @@ ); TRACE_EVENT(api_chswitch_done, - TP_PROTO(struct ieee80211_sub_if_data *sdata, bool success), + TP_PROTO(struct ieee80211_sub_if_data *sdata, bool success, + unsigned int link_id), - TP_ARGS(sdata, success), + TP_ARGS(sdata, success, link_id), TP_STRUCT__entry( VIF_ENTRY __field(bool, success) + __field(unsigned int, link_id) ), TP_fast_assign( VIF_ASSIGN; __entry->success = success; + __entry->link_id = link_id; ), TP_printk( - VIF_PR_FMT " success=%d", - VIF_PR_ARG, __entry->success + VIF_PR_FMT " success=%d link_id=%d", + VIF_PR_ARG, __entry->success, __entry->link_id ) ); diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/tx.c backport-iwlwifi-dkms-11510/net/mac80211/tx.c --- backport-iwlwifi-dkms-11289/net/mac80211/tx.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/tx.c 2023-10-04 04:18:43.000000000 +0800 @@ -26,6 +26,7 @@ #include #include #include +#include #include "ieee80211_i.h" #include "driver-ops.h" @@ -265,8 +266,8 @@ IEEE80211_QUEUE_STOP_REASON_PS, false); ifmgd->flags &= ~IEEE80211_STA_NULLFUNC_ACKED; - ieee80211_queue_work(&local->hw, - &local->dynamic_ps_disable_work); + wiphy_work_queue(local->hw.wiphy, + &local->dynamic_ps_disable_work); } /* Don't restart the timer if we're not disassociated */ @@ -2891,9 +2892,10 @@ goto free; } - if (unlikely(!multicast && ((skb->sk && - skb_shinfo(skb)->tx_flags & SKBTX_WIFI_STATUS) || - ctrl_flags & IEEE80211_TX_CTL_REQ_TX_STATUS))) + if (unlikely(!multicast && + ((skb->sk && + skb_shinfo(skb)->tx_flags & SKBTX_WIFI_STATUS) || + ctrl_flags & IEEE80211_TX_CTL_REQ_TX_STATUS))) info_id = ieee80211_store_ack_skb(local, skb, &info_flags, cookie); @@ -2977,7 +2979,10 @@ memset(info, 0, sizeof(*info)); info->flags = info_flags; - info->ack_frame_id = info_id; + if (info_id) { + info->status_data = info_id; + info->status_data_idr = 1; + } info->band = band; if (likely(!cookie)) { @@ -3830,6 +3835,7 @@ ieee80211_tx_result r; struct ieee80211_vif *vif = txq->vif; int q = vif->hw_queue[txq->ac]; + unsigned long flags; bool q_stopped; WARN_ON_ONCE(softirq_count() == 0); @@ -3838,9 +3844,9 @@ return NULL; begin: - spin_lock(&local->queue_stop_reason_lock); + spin_lock_irqsave(&local->queue_stop_reason_lock, flags); q_stopped = local->queue_stop_reasons[q]; - spin_unlock(&local->queue_stop_reason_lock); + spin_unlock_irqrestore(&local->queue_stop_reason_lock, flags); if (unlikely(q_stopped)) { /* mark for waking later */ @@ -4679,9 +4685,12 @@ } if (unlikely(skb->sk && - skb_shinfo(skb)->tx_flags & SKBTX_WIFI_STATUS)) - info->ack_frame_id = ieee80211_store_ack_skb(local, skb, - &info->flags, NULL); + skb_shinfo(skb)->tx_flags & SKBTX_WIFI_STATUS)) { + info->status_data = ieee80211_store_ack_skb(local, skb, + &info->flags, NULL); + if (info->status_data) + info->status_data_idr = 1; + } dev_sw_netstats_tx_add(dev, skbs, len); sta->deflink.tx_stats.packets[queue] += skbs; @@ -5572,7 +5581,7 @@ { struct ieee80211_ema_beacons *ema_beacons = NULL; - WARN_ON(__ieee80211_beacon_get(hw, vif, NULL, false, link_id, 0, + WARN_ON(__ieee80211_beacon_get(hw, vif, NULL, true, link_id, 0, &ema_beacons)); return ema_beacons; @@ -5961,7 +5970,7 @@ int ret; u32 queues; - lockdep_assert_held(&local->sta_mtx); + lockdep_assert_wiphy(local->hw.wiphy); /* only some cases are supported right now */ switch (sdata->vif.type) { @@ -6022,7 +6031,7 @@ struct sta_info *sta = container_of(pubsta, struct sta_info, sta); struct ieee80211_sub_if_data *sdata = sta->sdata; - lockdep_assert_held(&sdata->local->sta_mtx); + lockdep_assert_wiphy(sdata->local->hw.wiphy); /* only some cases are supported right now */ switch (sdata->vif.type) { @@ -6143,6 +6152,9 @@ u32 flags = 0; int err; + /* mutex lock is only needed for incrementing the cookie counter */ + lockdep_assert_wiphy(local->hw.wiphy); + /* Only accept CONTROL_PORT_PROTOCOL configured in CONNECT/ASSOCIATE * or Pre-Authentication */ @@ -6233,15 +6245,10 @@ rcu_read_unlock(); start_xmit: - /* mutex lock is only needed for incrementing the cookie counter */ - mutex_lock(&local->mtx); - local_bh_disable(); __ieee80211_subif_start_xmit(skb, skb->dev, flags, ctrl_flags, cookie); local_bh_enable(); - mutex_unlock(&local->mtx); - return 0; } diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/util.c backport-iwlwifi-dkms-11510/net/mac80211/util.c --- backport-iwlwifi-dkms-11289/net/mac80211/util.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/util.c 2023-10-04 04:18:43.000000000 +0800 @@ -706,6 +706,19 @@ IEEE80211_QUEUE_STOP_REASON_FLUSH, false); + if (drop) { + struct sta_info *sta; + + /* Purge the queues, so the frames on them won't be + * sent during __ieee80211_wake_queue() + */ + list_for_each_entry(sta, &local->sta_list, list) { + if (sdata != sta->sdata) + continue; + ieee80211_purge_sta_txqs(sta); + } + } + drv_flush(local, sdata, queues, drop); ieee80211_wake_queues_by_reason(&local->hw, queues, @@ -2344,9 +2357,10 @@ ieee80211_led_radio(local, false); ieee80211_mod_tpt_led_trig(local, 0, IEEE80211_TPT_LEDTRIG_FL_RADIO); - cancel_work_sync(&local->reconfig_filter); + wiphy_work_cancel(local->hw.wiphy, &local->reconfig_filter); flush_workqueue(local->workqueue); + wiphy_work_flush(local->hw.wiphy, NULL); drv_stop(local); } @@ -2368,8 +2382,8 @@ */ if (aborted) set_bit(SCAN_ABORTED, &local->scanning); - ieee80211_queue_delayed_work(&local->hw, &local->scan_work, 0); - flush_delayed_work(&local->scan_work); + wiphy_delayed_work_queue(local->hw.wiphy, &local->scan_work, 0); + wiphy_delayed_work_flush(local->hw.wiphy, &local->scan_work); } } @@ -2378,6 +2392,8 @@ struct ieee80211_sub_if_data *sdata; struct ieee80211_chanctx *ctx; + lockdep_assert_wiphy(local->hw.wiphy); + /* * We get here if during resume the device can't be restarted properly. * We might also get here if this happens during HW reset, which is a @@ -2406,10 +2422,8 @@ /* Mark channel contexts as not being in the driver any more to avoid * removing them from the driver during the shutdown process... */ - mutex_lock(&local->chanctx_mtx); list_for_each_entry(ctx, &local->chanctx_list, list) ctx->driver_present = false; - mutex_unlock(&local->chanctx_mtx); } static void ieee80211_assign_chanctx(struct ieee80211_local *local, @@ -2419,17 +2433,17 @@ struct ieee80211_chanctx_conf *conf; struct ieee80211_chanctx *ctx; + lockdep_assert_wiphy(local->hw.wiphy); + if (!local->use_chanctx) return; - mutex_lock(&local->chanctx_mtx); conf = rcu_dereference_protected(link->conf->chanctx_conf, - lockdep_is_held(&local->chanctx_mtx)); + lockdep_is_held(&local->hw.wiphy->mtx)); if (conf) { ctx = container_of(conf, struct ieee80211_chanctx, conf); drv_assign_vif_chanctx(local, sdata, link->conf, ctx); } - mutex_unlock(&local->chanctx_mtx); } static void ieee80211_reconfig_stations(struct ieee80211_sub_if_data *sdata) @@ -2437,8 +2451,9 @@ struct ieee80211_local *local = sdata->local; struct sta_info *sta; + lockdep_assert_wiphy(local->hw.wiphy); + /* add STAs back */ - mutex_lock(&local->sta_mtx); list_for_each_entry(sta, &local->sta_list, list) { enum ieee80211_sta_state state; @@ -2450,7 +2465,6 @@ WARN_ON(drv_sta_state(local, sta->sdata, sta, state, state + 1)); } - mutex_unlock(&local->sta_mtx); } static int ieee80211_reconfig_nan(struct ieee80211_sub_if_data *sdata) @@ -2537,6 +2551,8 @@ bool suspended = local->suspended; bool in_reconfig = false; + lockdep_assert_wiphy(local->hw.wiphy); + /* nothing to do if HW shouldn't run */ if (!local->open_count) goto wake_up; @@ -2652,12 +2668,10 @@ /* add channel contexts */ if (local->use_chanctx) { - mutex_lock(&local->chanctx_mtx); list_for_each_entry(ctx, &local->chanctx_list, list) if (ctx->replace_state != IEEE80211_CHANCTX_REPLACES_OTHER) WARN_ON(drv_add_chanctx(local, ctx)); - mutex_unlock(&local->chanctx_mtx); sdata = wiphy_dereference(local->hw.wiphy, local->monitor_sdata); @@ -2691,7 +2705,6 @@ if (!ieee80211_sdata_running(sdata)) continue; - sdata_lock(sdata); if (ieee80211_vif_is_mld(&sdata->vif)) { struct ieee80211_bss_conf *old[IEEE80211_MLD_MAX_NUM_LINKS] = { [0] = &sdata->vif.bss_conf, @@ -2823,7 +2836,6 @@ case NL80211_IFTYPE_NAN: res = ieee80211_reconfig_nan(sdata); if (res < 0) { - sdata_unlock(sdata); ieee80211_handle_reconfig_failure(local); return res; } @@ -2841,7 +2853,6 @@ WARN_ON(1); break; } - sdata_unlock(sdata); if (active_links) ieee80211_set_active_links(&sdata->vif, active_links); @@ -2871,7 +2882,6 @@ if (!ieee80211_sdata_running(sdata)) continue; - sdata_lock(sdata); switch (sdata->vif.type) { case NL80211_IFTYPE_AP_VLAN: case NL80211_IFTYPE_AP: @@ -2880,7 +2890,6 @@ default: break; } - sdata_unlock(sdata); } /* add back keys */ @@ -2888,11 +2897,10 @@ ieee80211_reenable_keys(sdata); /* Reconfigure sched scan if it was interrupted by FW restart */ - mutex_lock(&local->mtx); sched_scan_sdata = rcu_dereference_protected(local->sched_scan_sdata, - lockdep_is_held(&local->mtx)); + lockdep_is_held(&local->hw.wiphy->mtx)); sched_scan_req = rcu_dereference_protected(local->sched_scan_req, - lockdep_is_held(&local->mtx)); + lockdep_is_held(&local->hw.wiphy->mtx)); if (sched_scan_sdata && sched_scan_req) /* * Sched scan stopped, but we don't want to report it. Instead, @@ -2908,7 +2916,6 @@ RCU_INIT_POINTER(local->sched_scan_req, NULL); sched_scan_stopped = true; } - mutex_unlock(&local->mtx); if (sched_scan_stopped) cfg80211_sched_scan_stopped_locked(local->hw.wiphy, 0); @@ -2929,16 +2936,12 @@ * are active. This is really a workaround though. */ if (ieee80211_hw_check(hw, AMPDU_AGGREGATION)) { - mutex_lock(&local->sta_mtx); - list_for_each_entry(sta, &local->sta_list, list) { if (!local->resuming) ieee80211_sta_tear_down_BA_sessions( sta, AGG_STOP_LOCAL_REQUEST); clear_sta_flag(sta, WLAN_STA_BLOCK_BA); } - - mutex_unlock(&local->sta_mtx); } /* @@ -2954,9 +2957,7 @@ barrier(); /* Restart deferred ROCs */ - mutex_lock(&local->mtx); ieee80211_start_next_roc(local); - mutex_unlock(&local->mtx); /* Requeue all works */ list_for_each_entry(sdata, &local->interfaces, list) @@ -3017,6 +3018,8 @@ sdata = vif_to_sdata(vif); local = sdata->local; + lockdep_assert_wiphy(local->hw.wiphy); + if (WARN_ON(flag & IEEE80211_SDATA_DISCONNECT_RESUME && !local->resuming)) return; @@ -3030,10 +3033,8 @@ sdata->flags |= flag; - mutex_lock(&local->key_mtx); list_for_each_entry(key, &sdata->key_list, list) key->flags |= KEY_FLAG_TAINTED; - mutex_unlock(&local->key_mtx); } void ieee80211_hw_restart_disconnect(struct ieee80211_vif *vif) @@ -3055,10 +3056,10 @@ struct ieee80211_chanctx_conf *chanctx_conf; struct ieee80211_chanctx *chanctx; - mutex_lock(&local->chanctx_mtx); + lockdep_assert_wiphy(local->hw.wiphy); chanctx_conf = rcu_dereference_protected(link->conf->chanctx_conf, - lockdep_is_held(&local->chanctx_mtx)); + lockdep_is_held(&local->hw.wiphy->mtx)); /* * This function can be called from a work, thus it may be possible @@ -3067,12 +3068,10 @@ * So nothing should be done in such case. */ if (!chanctx_conf) - goto unlock; + return; chanctx = container_of(chanctx_conf, struct ieee80211_chanctx, conf); ieee80211_recalc_smps_chanctx(local, chanctx); - unlock: - mutex_unlock(&local->chanctx_mtx); } void ieee80211_recalc_min_chandef(struct ieee80211_sub_if_data *sdata, @@ -3083,7 +3082,7 @@ struct ieee80211_chanctx *chanctx; int i; - mutex_lock(&local->chanctx_mtx); + lockdep_assert_wiphy(local->hw.wiphy); for (i = 0; i < ARRAY_SIZE(sdata->vif.link_conf); i++) { struct ieee80211_bss_conf *bss_conf; @@ -3099,9 +3098,9 @@ } chanctx_conf = rcu_dereference_protected(bss_conf->chanctx_conf, - lockdep_is_held(&local->chanctx_mtx)); + lockdep_is_held(&local->hw.wiphy->mtx)); /* - * Since we hold the chanctx_mtx (checked above) + * Since we hold the wiphy mutex (checked above) * we can take the chanctx_conf pointer out of the * RCU critical section, it cannot go away without * the mutex. Just the way we reached it could - in @@ -3111,14 +3110,12 @@ rcu_read_unlock(); if (!chanctx_conf) - goto unlock; + return; chanctx = container_of(chanctx_conf, struct ieee80211_chanctx, conf); ieee80211_recalc_chanctx_min_def(local, chanctx, NULL); } - unlock: - mutex_unlock(&local->chanctx_mtx); } size_t ieee80211_ie_split_vendor(const u8 *ies, size_t ielen, size_t offset) @@ -3899,10 +3896,8 @@ } eht_cap = ieee80211_get_eht_iftype_cap(sband, iftype); - if (!eht_cap) { - sdata_info(sdata, "Missing iftype sband data/EHT cap"); + if (!eht_cap) eht_oper = NULL; - } he_6ghz_oper = ieee80211_he_6ghz_oper(he_oper); @@ -4372,16 +4367,15 @@ struct ieee80211_sub_if_data *sdata; struct cfg80211_chan_def chandef; - /* for interface list, to avoid linking iflist_mtx and chanctx_mtx */ lockdep_assert_wiphy(local->hw.wiphy); - mutex_lock(&local->mtx); list_for_each_entry(sdata, &local->interfaces, list) { /* it might be waiting for the local->mtx, but then * by the time it gets it, sdata->wdev.cac_started * will no longer be true */ - cancel_delayed_work(&sdata->deflink.dfs_cac_timer_work); + wiphy_delayed_work_cancel(local->hw.wiphy, + &sdata->deflink.dfs_cac_timer_work); if (sdata->wdev.cac_started) { chandef = sdata->vif.bss_conf.chandef; @@ -4392,10 +4386,10 @@ GFP_KERNEL); } } - mutex_unlock(&local->mtx); } -void ieee80211_dfs_radar_detected_work(struct work_struct *work) +void ieee80211_dfs_radar_detected_work(struct wiphy *wiphy, + struct wiphy_work *work) { struct ieee80211_local *local = container_of(work, struct ieee80211_local, radar_detected_work); @@ -4403,7 +4397,8 @@ struct ieee80211_chanctx *ctx; int num_chanctx = 0; - mutex_lock(&local->chanctx_mtx); + lockdep_assert_wiphy(local->hw.wiphy); + list_for_each_entry(ctx, &local->chanctx_list, list) { if (ctx->replace_state == IEEE80211_CHANCTX_REPLACES_OTHER) continue; @@ -4411,11 +4406,8 @@ num_chanctx++; chandef = ctx->conf.def; } - mutex_unlock(&local->chanctx_mtx); - wiphy_lock(local->hw.wiphy); ieee80211_dfs_cac_cancel(local); - wiphy_unlock(local->hw.wiphy); if (num_chanctx > 1) /* XXX: multi-channel is not supported yet */ @@ -4430,7 +4422,7 @@ trace_api_radar_detected(local); - schedule_work(&local->radar_detected_work); + wiphy_work_queue(hw->wiphy, &local->radar_detected_work); } EXPORT_SYMBOL(ieee80211_radar_detected); @@ -4814,7 +4806,7 @@ struct ieee80211_link_data *link; u8 radar_detect = 0; - lockdep_assert_held(&local->chanctx_mtx); + lockdep_assert_wiphy(local->hw.wiphy); if (WARN_ON(ctx->replace_state == IEEE80211_CHANCTX_WILL_BE_REPLACED)) return 0; @@ -4855,7 +4847,7 @@ .radar_detect = radar_detect, }; - lockdep_assert_held(&local->chanctx_mtx); + lockdep_assert_wiphy(local->hw.wiphy); if (WARN_ON(hweight32(radar_detect) > 1)) return -EINVAL; @@ -4945,7 +4937,7 @@ int err; struct iface_combination_params params = {0}; - lockdep_assert_held(&local->chanctx_mtx); + lockdep_assert_wiphy(local->hw.wiphy); list_for_each_entry(ctx, &local->chanctx_list, list) { if (ctx->replace_state == IEEE80211_CHANCTX_WILL_BE_REPLACED) diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/wep.c backport-iwlwifi-dkms-11510/net/mac80211/wep.c --- backport-iwlwifi-dkms-11289/net/mac80211/wep.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/wep.c 2023-10-04 04:18:43.000000000 +0800 @@ -3,6 +3,7 @@ * Software WEP encryption implementation * Copyright 2002, Jouni Malinen * Copyright 2003, Instant802 Networks, Inc. + * Copyright (C) 2023 Intel Corporation */ #include @@ -250,18 +251,18 @@ if (!(status->flag & RX_FLAG_DECRYPTED)) { if (skb_linearize(rx->skb)) - return RX_DROP_UNUSABLE; + return RX_DROP_U_OOM; if (ieee80211_wep_decrypt(rx->local, rx->skb, rx->key)) - return RX_DROP_UNUSABLE; + return RX_DROP_U_WEP_DEC_FAIL; } else if (!(status->flag & RX_FLAG_IV_STRIPPED)) { if (!pskb_may_pull(rx->skb, ieee80211_hdrlen(fc) + IEEE80211_WEP_IV_LEN)) - return RX_DROP_UNUSABLE; + return RX_DROP_U_NO_IV; ieee80211_wep_remove_iv(rx->local, rx->skb, rx->key); /* remove ICV */ if (!(status->flag & RX_FLAG_ICV_STRIPPED) && pskb_trim(rx->skb, rx->skb->len - IEEE80211_WEP_ICV_LEN)) - return RX_DROP_UNUSABLE; + return RX_DROP_U_NO_ICV; } return RX_CONTINUE; diff -Nru backport-iwlwifi-dkms-11289/net/mac80211/wpa.c backport-iwlwifi-dkms-11510/net/mac80211/wpa.c --- backport-iwlwifi-dkms-11289/net/mac80211/wpa.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/mac80211/wpa.c 2023-10-04 04:18:43.000000000 +0800 @@ -3,7 +3,7 @@ * Copyright 2002-2004, Instant802 Networks, Inc. * Copyright 2008, Jouni Malinen * Copyright (C) 2016-2017 Intel Deutschland GmbH - * Copyright (C) 2020-2022 Intel Corporation + * Copyright (C) 2020-2023 Intel Corporation */ #include @@ -142,7 +142,7 @@ * group keys and only the AP is sending real multicast * frames in the BSS. */ - return RX_DROP_UNUSABLE; + return RX_DROP_U_AP_RX_GROUPCAST; } if (status->flag & RX_FLAG_MMIC_ERROR) @@ -150,10 +150,10 @@ hdrlen = ieee80211_hdrlen(hdr->frame_control); if (skb->len < hdrlen + MICHAEL_MIC_LEN) - return RX_DROP_UNUSABLE; + return RX_DROP_U_SHORT_MMIC; if (skb_linearize(rx->skb)) - return RX_DROP_UNUSABLE; + return RX_DROP_U_OOM; hdr = (void *)skb->data; data = skb->data + hdrlen; @@ -188,7 +188,7 @@ NL80211_KEYTYPE_PAIRWISE, rx->key ? rx->key->conf.keyidx : -1, NULL, GFP_ATOMIC); - return RX_DROP_UNUSABLE; + return RX_DROP_U_MMIC_FAIL; } static int tkip_encrypt_skb(struct ieee80211_tx_data *tx, struct sk_buff *skb) @@ -276,11 +276,11 @@ return RX_CONTINUE; if (!rx->sta || skb->len - hdrlen < 12) - return RX_DROP_UNUSABLE; + return RX_DROP_U_SHORT_TKIP; /* it may be possible to optimize this a bit more */ if (skb_linearize(rx->skb)) - return RX_DROP_UNUSABLE; + return RX_DROP_U_OOM; hdr = (void *)skb->data; /* @@ -298,7 +298,7 @@ &rx->tkip.iv32, &rx->tkip.iv16); if (res != TKIP_DECRYPT_OK) - return RX_DROP_UNUSABLE; + return RX_DROP_U_TKIP_FAIL; /* Trim ICV */ if (!(status->flag & RX_FLAG_ICV_STRIPPED)) @@ -523,12 +523,12 @@ if (status->flag & RX_FLAG_DECRYPTED) { if (!pskb_may_pull(rx->skb, hdrlen + IEEE80211_CCMP_HDR_LEN)) - return RX_DROP_UNUSABLE; + return RX_DROP_U_SHORT_CCMP; if (status->flag & RX_FLAG_MIC_STRIPPED) mic_len = 0; } else { if (skb_linearize(rx->skb)) - return RX_DROP_UNUSABLE; + return RX_DROP_U_OOM; } /* reload hdr - skb might have been reallocated */ @@ -536,7 +536,7 @@ data_len = skb->len - hdrlen - IEEE80211_CCMP_HDR_LEN - mic_len; if (!rx->sta || data_len < 0) - return RX_DROP_UNUSABLE; + return RX_DROP_U_SHORT_CCMP; if (!(status->flag & RX_FLAG_PN_VALIDATED)) { int res; @@ -574,7 +574,7 @@ /* Remove CCMP header and MIC */ if (pskb_trim(skb, skb->len - mic_len)) - return RX_DROP_UNUSABLE; + return RX_DROP_U_SHORT_CCMP_MIC; memmove(skb->data + IEEE80211_CCMP_HDR_LEN, skb->data, hdrlen); skb_pull(skb, IEEE80211_CCMP_HDR_LEN); @@ -719,12 +719,12 @@ if (status->flag & RX_FLAG_DECRYPTED) { if (!pskb_may_pull(rx->skb, hdrlen + IEEE80211_GCMP_HDR_LEN)) - return RX_DROP_UNUSABLE; + return RX_DROP_U_SHORT_GCMP; if (status->flag & RX_FLAG_MIC_STRIPPED) mic_len = 0; } else { if (skb_linearize(rx->skb)) - return RX_DROP_UNUSABLE; + return RX_DROP_U_OOM; } /* reload hdr - skb might have been reallocated */ @@ -732,7 +732,7 @@ data_len = skb->len - hdrlen - IEEE80211_GCMP_HDR_LEN - mic_len; if (!rx->sta || data_len < 0) - return RX_DROP_UNUSABLE; + return RX_DROP_U_SHORT_GCMP; if (!(status->flag & RX_FLAG_PN_VALIDATED)) { int res; @@ -771,7 +771,7 @@ /* Remove GCMP header and MIC */ if (pskb_trim(skb, skb->len - mic_len)) - return RX_DROP_UNUSABLE; + return RX_DROP_U_SHORT_GCMP_MIC; memmove(skb->data + IEEE80211_GCMP_HDR_LEN, skb->data, hdrlen); skb_pull(skb, IEEE80211_GCMP_HDR_LEN); @@ -924,7 +924,7 @@ /* management frames are already linear */ if (skb->len < 24 + sizeof(*mmie)) - return RX_DROP_UNUSABLE; + return RX_DROP_U_SHORT_CMAC; mmie = (struct ieee80211_mmie *) (skb->data + skb->len - sizeof(*mmie)); @@ -974,13 +974,13 @@ /* management frames are already linear */ if (skb->len < 24 + sizeof(*mmie)) - return RX_DROP_UNUSABLE; + return RX_DROP_U_SHORT_CMAC256; mmie = (struct ieee80211_mmie_16 *) (skb->data + skb->len - sizeof(*mmie)); if (mmie->element_id != WLAN_EID_MMIE || mmie->length != sizeof(*mmie) - 2) - return RX_DROP_UNUSABLE; /* Invalid MMIE */ + return RX_DROP_U_BAD_MMIE; /* Invalid MMIE */ bip_ipn_swap(ipn, mmie->sequence_number); @@ -1073,7 +1073,7 @@ /* management frames are already linear */ if (skb->len < 24 + sizeof(*mmie)) - return RX_DROP_UNUSABLE; + return RX_DROP_U_SHORT_GMAC; mmie = (struct ieee80211_mmie_16 *) (skb->data + skb->len - sizeof(*mmie)); @@ -1097,7 +1097,7 @@ mic = kmalloc(GMAC_MIC_LEN, GFP_ATOMIC); if (!mic) - return RX_DROP_UNUSABLE; + return RX_DROP_U_OOM; if (ieee80211_aes_gmac(key->u.aes_gmac.tfm, aad, nonce, skb->data + 24, skb->len - 24, mic) < 0 || diff -Nru backport-iwlwifi-dkms-11289/net/wireless/ap.c backport-iwlwifi-dkms-11510/net/wireless/ap.c --- backport-iwlwifi-dkms-11289/net/wireless/ap.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/wireless/ap.c 2023-10-04 04:18:43.000000000 +0800 @@ -1,7 +1,7 @@ // SPDX-License-Identifier: GPL-2.0 /* * Parts of this file are - * Copyright (C) 2022 Intel Corporation + * Copyright (C) 2022-2023 Intel Corporation */ #include #include @@ -18,7 +18,7 @@ struct wireless_dev *wdev = dev->ieee80211_ptr; int err; - ASSERT_WDEV_LOCK(wdev); + lockdep_assert_wiphy(wdev->wiphy); if (!rdev->ops->stop_ap) return -EOPNOTSUPP; @@ -52,9 +52,9 @@ return err; } -int __cfg80211_stop_ap(struct cfg80211_registered_device *rdev, - struct net_device *dev, int link_id, - bool notify) +int cfg80211_stop_ap(struct cfg80211_registered_device *rdev, + struct net_device *dev, int link_id, + bool notify) { unsigned int link; int ret = 0; @@ -72,17 +72,3 @@ return ret; } - -int cfg80211_stop_ap(struct cfg80211_registered_device *rdev, - struct net_device *dev, int link_id, - bool notify) -{ - struct wireless_dev *wdev = dev->ieee80211_ptr; - int err; - - wdev_lock(wdev); - err = __cfg80211_stop_ap(rdev, dev, link_id, notify); - wdev_unlock(wdev); - - return err; -} diff -Nru backport-iwlwifi-dkms-11289/net/wireless/chan.c backport-iwlwifi-dkms-11510/net/wireless/chan.c --- backport-iwlwifi-dkms-11289/net/wireless/chan.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/wireless/chan.c 2023-10-04 04:18:43.000000000 +0800 @@ -514,9 +514,83 @@ return end_freq; } +static bool +cfg80211_dfs_permissive_check_wdev(struct cfg80211_registered_device *rdev, + enum nl80211_iftype iftype, + struct wireless_dev *wdev, + struct ieee80211_channel *chan) +{ + unsigned int link_id; + + for_each_valid_link(wdev, link_id) { + struct ieee80211_channel *other_chan = NULL; + struct cfg80211_chan_def chandef = {}; + int ret; + + /* In order to avoid daisy chaining only allow BSS STA */ + if (wdev->iftype != NL80211_IFTYPE_STATION || + !wdev->links[link_id].client.current_bss) + continue; + + other_chan = + wdev->links[link_id].client.current_bss->pub.channel; + + if (!other_chan) + continue; + + if (chan == other_chan) + return true; + + /* continue if we can't get the channel */ + ret = rdev_get_channel(rdev, wdev, link_id, &chandef); + if (ret) + continue; + + if (cfg80211_is_sub_chan(&chandef, chan, false)) + return true; + } + + return false; +} + +/* + * Check if P2P GO is allowed to operate on a DFS channel + */ +static bool cfg80211_dfs_permissive_chan(struct wiphy *wiphy, + enum nl80211_iftype iftype, + struct ieee80211_channel *chan) +{ + struct wireless_dev *wdev; + struct cfg80211_registered_device *rdev = wiphy_to_rdev(wiphy); + + lockdep_assert_held(&rdev->wiphy.mtx); + + if (!wiphy_ext_feature_isset(&rdev->wiphy, + NL80211_EXT_FEATURE_DFS_CONCURRENT) || + !(chan->flags & IEEE80211_CHAN_DFS_CONCURRENT)) + return false; + + /* only valid for P2P GO */ + if (iftype != NL80211_IFTYPE_P2P_GO) + return false; + + /* + * Allow only if there's a concurrent BSS + */ + list_for_each_entry(wdev, &rdev->wiphy.wdev_list, list) { + bool ret = cfg80211_dfs_permissive_check_wdev(rdev, iftype, + wdev, chan); + if (ret) + return ret; + } + + return false; +} + static int cfg80211_get_chans_dfs_required(struct wiphy *wiphy, u32 center_freq, - u32 bandwidth) + u32 bandwidth, + enum nl80211_iftype iftype) { struct ieee80211_channel *c; u32 freq, start_freq, end_freq; @@ -529,9 +603,11 @@ if (!c) return -EINVAL; - if (c->flags & IEEE80211_CHAN_RADAR) + if (c->flags & IEEE80211_CHAN_RADAR && + !cfg80211_dfs_permissive_chan(wiphy, iftype, c)) return 1; } + return 0; } @@ -557,7 +633,7 @@ ret = cfg80211_get_chans_dfs_required(wiphy, ieee80211_chandef_to_khz(chandef), - width); + width, iftype); if (ret < 0) return ret; else if (ret > 0) @@ -568,7 +644,7 @@ ret = cfg80211_get_chans_dfs_required(wiphy, MHZ_TO_KHZ(chandef->center_freq2), - width); + width, iftype); if (ret < 0) return ret; else if (ret > 0) @@ -713,7 +789,7 @@ { unsigned int link; - ASSERT_WDEV_LOCK(wdev); + lockdep_assert_wiphy(wdev->wiphy); switch (wdev->iftype) { case NL80211_IFTYPE_AP: @@ -782,18 +858,14 @@ { struct wireless_dev *wdev; + lockdep_assert_wiphy(wiphy); + list_for_each_entry(wdev, &wiphy->wdev_list, list) { - wdev_lock(wdev); - if (!cfg80211_beaconing_iface_active(wdev)) { - wdev_unlock(wdev); + if (!cfg80211_beaconing_iface_active(wdev)) continue; - } - if (cfg80211_wdev_on_sub_chan(wdev, chan, false)) { - wdev_unlock(wdev); + if (cfg80211_wdev_on_sub_chan(wdev, chan, false)) return true; - } - wdev_unlock(wdev); } return false; @@ -823,14 +895,18 @@ if (!(chan->flags & IEEE80211_CHAN_RADAR)) return false; - list_for_each_entry(rdev, &cfg80211_rdev_list, list) { + for_each_rdev(rdev) { + bool found; + if (!reg_dfs_domain_same(wiphy, &rdev->wiphy)) continue; - if (cfg80211_is_wiphy_oper_chan(&rdev->wiphy, chan)) - return true; + wiphy_lock(&rdev->wiphy); + found = cfg80211_is_wiphy_oper_chan(&rdev->wiphy, chan) || + cfg80211_offchan_chain_is_active(rdev, chan); + wiphy_unlock(&rdev->wiphy); - if (cfg80211_offchan_chain_is_active(rdev, chan)) + if (found) return true; } @@ -1320,10 +1396,7 @@ list_for_each_entry(wdev, &rdev->wiphy.wdev_list, list) { bool ret; - wdev_lock(wdev); ret = cfg80211_ir_permissive_check_wdev(iftype, wdev, chan); - wdev_unlock(wdev); - if (ret) return ret; } @@ -1337,15 +1410,19 @@ bool check_no_ir) { bool res; - u32 prohibited_flags = IEEE80211_CHAN_DISABLED | - IEEE80211_CHAN_RADAR; + u32 prohibited_flags = IEEE80211_CHAN_DISABLED; + int dfs_required; trace_cfg80211_reg_can_beacon(wiphy, chandef, iftype, check_no_ir); if (check_no_ir) prohibited_flags |= IEEE80211_CHAN_NO_IR; - if (cfg80211_chandef_dfs_required(wiphy, chandef, iftype) > 0 && + dfs_required = cfg80211_chandef_dfs_required(wiphy, chandef, iftype); + if (dfs_required != 0) + prohibited_flags |= IEEE80211_CHAN_RADAR; + + if (dfs_required > 0 && cfg80211_chandef_dfs_available(wiphy, chandef)) { /* We can skip IEEE80211_CHAN_NO_IR if chandef dfs available */ prohibited_flags = IEEE80211_CHAN_DISABLED; @@ -1432,17 +1509,10 @@ struct cfg80211_chan_def *wdev_chandef(struct wireless_dev *wdev, unsigned int link_id) { - /* - * We need to sort out the locking here - in some cases - * where we get here we really just don't care (yet) - * about the valid links, but in others we do. But we - * get here with various driver cases, so we cannot - * easily require the wdev mutex. - */ - if (link_id || wdev->valid_links & BIT(0)) { - ASSERT_WDEV_LOCK(wdev); - WARN_ON(!(wdev->valid_links & BIT(link_id))); - } + lockdep_assert_wiphy(wdev->wiphy); + + WARN_ON(wdev->valid_links && !(wdev->valid_links & BIT(link_id))); + WARN_ON(!wdev->valid_links && link_id > 0); switch (wdev->iftype) { case NL80211_IFTYPE_MESH_POINT: diff -Nru backport-iwlwifi-dkms-11289/net/wireless/core.c backport-iwlwifi-dkms-11510/net/wireless/core.c --- backport-iwlwifi-dkms-11289/net/wireless/core.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/wireless/core.c 2023-10-04 04:18:43.000000000 +0800 @@ -60,7 +60,7 @@ ASSERT_RTNL(); - list_for_each_entry(rdev, &cfg80211_rdev_list, list) { + for_each_rdev(rdev) { if (rdev->wiphy_idx == wiphy_idx) { result = rdev; break; @@ -116,7 +116,7 @@ } /* Ensure another device does not already have this name. */ - list_for_each_entry(rdev2, &cfg80211_rdev_list, list) + for_each_rdev(rdev2) if (strcmp(newname, wiphy_name(&rdev2->wiphy)) == 0) return -EINVAL; @@ -763,22 +763,6 @@ return -EINVAL; } - /* - * if a wiphy has unsupported modes for regulatory channel enforcement, - * opt-out of enforcement checking - */ - if (wiphy->interface_modes & ~(BIT(NL80211_IFTYPE_STATION) | - BIT(NL80211_IFTYPE_P2P_CLIENT) | - BIT(NL80211_IFTYPE_AP) | - BIT(NL80211_IFTYPE_MESH_POINT) | - BIT(NL80211_IFTYPE_P2P_GO) | - BIT(NL80211_IFTYPE_ADHOC) | - BIT(NL80211_IFTYPE_P2P_DEVICE) | - BIT(NL80211_IFTYPE_NAN) | - BIT(NL80211_IFTYPE_AP_VLAN) | - BIT(NL80211_IFTYPE_MONITOR))) - wiphy->regulatory_flags |= REGULATORY_IGNORE_STALE_KICKOFF; - if (WARN_ON((wiphy->regulatory_flags & REGULATORY_WIPHY_SELF_MANAGED) && (wiphy->regulatory_flags & (REGULATORY_CUSTOM_REG | @@ -1299,14 +1283,13 @@ rdev->num_running_monitor_ifaces += num; } -void __cfg80211_leave(struct cfg80211_registered_device *rdev, - struct wireless_dev *wdev) +void cfg80211_leave(struct cfg80211_registered_device *rdev, + struct wireless_dev *wdev) { struct net_device *dev = wdev->netdev; struct cfg80211_sched_scan_request *pos, *tmp; lockdep_assert_held(&rdev->wiphy.mtx); - ASSERT_WDEV_LOCK(wdev); cfg80211_pmsr_wdev_down(wdev); @@ -1314,7 +1297,7 @@ switch (wdev->iftype) { case NL80211_IFTYPE_ADHOC: - __cfg80211_leave_ibss(rdev, dev, true); + cfg80211_leave_ibss(rdev, dev, true); break; case NL80211_IFTYPE_P2P_CLIENT: case NL80211_IFTYPE_STATION: @@ -1334,14 +1317,14 @@ WLAN_REASON_DEAUTH_LEAVING, true); break; case NL80211_IFTYPE_MESH_POINT: - __cfg80211_leave_mesh(rdev, dev); + cfg80211_leave_mesh(rdev, dev); break; case NL80211_IFTYPE_AP: case NL80211_IFTYPE_P2P_GO: - __cfg80211_stop_ap(rdev, dev, -1, true); + cfg80211_stop_ap(rdev, dev, -1, true); break; case NL80211_IFTYPE_OCB: - __cfg80211_leave_ocb(rdev, dev); + cfg80211_leave_ocb(rdev, dev); break; case NL80211_IFTYPE_P2P_DEVICE: case NL80211_IFTYPE_NAN: @@ -1359,14 +1342,6 @@ } } -void cfg80211_leave(struct cfg80211_registered_device *rdev, - struct wireless_dev *wdev) -{ - wdev_lock(wdev); - __cfg80211_leave(rdev, wdev); - wdev_unlock(wdev); -} - void cfg80211_stop_iface(struct wiphy *wiphy, struct wireless_dev *wdev, gfp_t gfp) { @@ -1391,7 +1366,6 @@ void cfg80211_init_wdev(struct wireless_dev *wdev) { - mutex_init(&wdev->mtx); INIT_LIST_HEAD(&wdev->event_list); spin_lock_init(&wdev->event_lock); INIT_LIST_HEAD(&wdev->mgmt_registrations); @@ -1558,7 +1532,6 @@ case NETDEV_UP: wiphy_lock(&rdev->wiphy); cfg80211_update_iface_num(rdev, wdev->iftype, 1); - wdev_lock(wdev); switch (wdev->iftype) { #ifdef CPTCFG_CFG80211_WEXT case NL80211_IFTYPE_ADHOC: @@ -1588,7 +1561,6 @@ default: break; } - wdev_unlock(wdev); rdev->opencount++; /* @@ -1631,7 +1603,7 @@ struct cfg80211_registered_device *rdev; rtnl_lock(); - list_for_each_entry(rdev, &cfg80211_rdev_list, list) { + for_each_rdev(rdev) { if (net_eq(wiphy_net(&rdev->wiphy), net)) WARN_ON(cfg80211_switch_netns(rdev, &init_net)); } diff -Nru backport-iwlwifi-dkms-11289/net/wireless/core.h backport-iwlwifi-dkms-11510/net/wireless/core.h --- backport-iwlwifi-dkms-11289/net/wireless/core.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/wireless/core.h 2023-10-04 04:18:43.000000000 +0800 @@ -161,6 +161,16 @@ extern struct list_head cfg80211_rdev_list; extern int cfg80211_rdev_list_generation; +/* This is constructed like this so it can be used in if/else */ +static inline int for_each_rdev_check_rtnl(void) +{ + ASSERT_RTNL(); + return 0; +} +#define for_each_rdev(rdev) \ + if (for_each_rdev_check_rtnl()) {} else \ + list_for_each_entry(rdev, &cfg80211_rdev_list, list) + struct cfg80211_internal_bss { struct list_head list; struct list_head hidden_list; @@ -226,22 +236,6 @@ void cfg80211_register_wdev(struct cfg80211_registered_device *rdev, struct wireless_dev *wdev); -static inline void wdev_lock(struct wireless_dev *wdev) - __acquires(wdev) -{ - mutex_lock(&wdev->mtx); - __acquire(wdev->mtx); -} - -static inline void wdev_unlock(struct wireless_dev *wdev) - __releases(wdev) -{ - __release(wdev->mtx); - mutex_unlock(&wdev->mtx); -} - -#define ASSERT_WDEV_LOCK(wdev) lockdep_assert_held(&(wdev)->mtx) - static inline bool cfg80211_has_monitors_only(struct cfg80211_registered_device *rdev) { lockdep_assert_held(&rdev->wiphy.mtx); @@ -325,8 +319,6 @@ struct cfg80211_ibss_params *params, struct cfg80211_cached_keys *connkeys); void cfg80211_clear_ibss(struct net_device *dev, bool nowext); -int __cfg80211_leave_ibss(struct cfg80211_registered_device *rdev, - struct net_device *dev, bool nowext); int cfg80211_leave_ibss(struct cfg80211_registered_device *rdev, struct net_device *dev, bool nowext); void __cfg80211_ibss_joined(struct net_device *dev, const u8 *bssid, @@ -341,8 +333,6 @@ struct net_device *dev, struct mesh_setup *setup, const struct mesh_config *conf); -int __cfg80211_leave_mesh(struct cfg80211_registered_device *rdev, - struct net_device *dev); int cfg80211_leave_mesh(struct cfg80211_registered_device *rdev, struct net_device *dev); int cfg80211_set_mesh_channel(struct cfg80211_registered_device *rdev, @@ -350,21 +340,13 @@ struct cfg80211_chan_def *chandef); /* OCB */ -int __cfg80211_join_ocb(struct cfg80211_registered_device *rdev, - struct net_device *dev, - struct ocb_setup *setup); int cfg80211_join_ocb(struct cfg80211_registered_device *rdev, struct net_device *dev, struct ocb_setup *setup); -int __cfg80211_leave_ocb(struct cfg80211_registered_device *rdev, - struct net_device *dev); int cfg80211_leave_ocb(struct cfg80211_registered_device *rdev, struct net_device *dev); /* AP */ -int __cfg80211_stop_ap(struct cfg80211_registered_device *rdev, - struct net_device *dev, int link, - bool notify); int cfg80211_stop_ap(struct cfg80211_registered_device *rdev, struct net_device *dev, int link, bool notify); @@ -471,6 +453,9 @@ extern struct work_struct cfg80211_disconnect_work; +#define NL80211_BSS_USE_FOR_ALL (NL80211_BSS_USE_FOR_NORMAL | \ + NL80211_BSS_USE_FOR_MLD_LINK) + /** * cfg80211_chandef_dfs_usable - checks if chandef is DFS usable * @wiphy: the wiphy to validate against @@ -542,8 +527,6 @@ void cfg80211_update_iface_num(struct cfg80211_registered_device *rdev, enum nl80211_iftype iftype, int num); -void __cfg80211_leave(struct cfg80211_registered_device *rdev, - struct wireless_dev *wdev); void cfg80211_leave(struct cfg80211_registered_device *rdev, struct wireless_dev *wdev); @@ -578,6 +561,7 @@ void cfg80211_remove_links(struct wireless_dev *wdev); int cfg80211_remove_virtual_intf(struct cfg80211_registered_device *rdev, struct wireless_dev *wdev); +void cfg80211_wdev_release_link_bsses(struct wireless_dev *wdev, u16 link_mask); #if IS_ENABLED(CPTCFG_CFG80211_KUNIT_TEST) size_t cfg80211_gen_new_ie(const u8 *ie, size_t ielen, diff -Nru backport-iwlwifi-dkms-11289/net/wireless/ibss.c backport-iwlwifi-dkms-11510/net/wireless/ibss.c --- backport-iwlwifi-dkms-11289/net/wireless/ibss.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/wireless/ibss.c 2023-10-04 04:18:43.000000000 +0800 @@ -3,7 +3,7 @@ * Some IBSS support code for cfg80211. * * Copyright 2009 Johannes Berg - * Copyright (C) 2020-2022 Intel Corporation + * Copyright (C) 2020-2023 Intel Corporation */ #include @@ -93,7 +93,6 @@ int err; lockdep_assert_held(&rdev->wiphy.mtx); - ASSERT_WDEV_LOCK(wdev); if (wdev->u.ibss.ssid_len) return -EALREADY; @@ -151,13 +150,13 @@ return 0; } -static void __cfg80211_clear_ibss(struct net_device *dev, bool nowext) +void cfg80211_clear_ibss(struct net_device *dev, bool nowext) { struct wireless_dev *wdev = dev->ieee80211_ptr; struct cfg80211_registered_device *rdev = wiphy_to_rdev(wdev->wiphy); int i; - ASSERT_WDEV_LOCK(wdev); + lockdep_assert_wiphy(wdev->wiphy); kfree_sensitive(wdev->connect_keys); wdev->connect_keys = NULL; @@ -187,22 +186,13 @@ cfg80211_sched_dfs_chan_update(rdev); } -void cfg80211_clear_ibss(struct net_device *dev, bool nowext) -{ - struct wireless_dev *wdev = dev->ieee80211_ptr; - - wdev_lock(wdev); - __cfg80211_clear_ibss(dev, nowext); - wdev_unlock(wdev); -} - -int __cfg80211_leave_ibss(struct cfg80211_registered_device *rdev, - struct net_device *dev, bool nowext) +int cfg80211_leave_ibss(struct cfg80211_registered_device *rdev, + struct net_device *dev, bool nowext) { struct wireless_dev *wdev = dev->ieee80211_ptr; int err; - ASSERT_WDEV_LOCK(wdev); + lockdep_assert_wiphy(wdev->wiphy); if (!wdev->u.ibss.ssid_len) return -ENOLINK; @@ -213,24 +203,11 @@ return err; wdev->conn_owner_nlportid = 0; - __cfg80211_clear_ibss(dev, nowext); + cfg80211_clear_ibss(dev, nowext); return 0; } -int cfg80211_leave_ibss(struct cfg80211_registered_device *rdev, - struct net_device *dev, bool nowext) -{ - struct wireless_dev *wdev = dev->ieee80211_ptr; - int err; - - wdev_lock(wdev); - err = __cfg80211_leave_ibss(rdev, dev, nowext); - wdev_unlock(wdev); - - return err; -} - #ifdef CPTCFG_CFG80211_WEXT int cfg80211_ibss_wext_join(struct cfg80211_registered_device *rdev, struct wireless_dev *wdev) @@ -239,7 +216,7 @@ enum nl80211_band band; int i, err; - ASSERT_WDEV_LOCK(wdev); + lockdep_assert_wiphy(wdev->wiphy); if (!wdev->wext.ibss.beacon_interval) wdev->wext.ibss.beacon_interval = 100; @@ -336,11 +313,9 @@ if (wdev->wext.ibss.chandef.chan == chan) return 0; - wdev_lock(wdev); err = 0; if (wdev->u.ibss.ssid_len) - err = __cfg80211_leave_ibss(rdev, dev, true); - wdev_unlock(wdev); + err = cfg80211_leave_ibss(rdev, dev, true); if (err) return err; @@ -354,11 +329,7 @@ wdev->wext.ibss.channel_fixed = false; } - wdev_lock(wdev); - err = cfg80211_ibss_wext_join(rdev, wdev); - wdev_unlock(wdev); - - return err; + return cfg80211_ibss_wext_join(rdev, wdev); } int cfg80211_ibss_wext_giwfreq(struct net_device *dev, @@ -372,12 +343,10 @@ if (WARN_ON(wdev->iftype != NL80211_IFTYPE_ADHOC)) return -EINVAL; - wdev_lock(wdev); if (wdev->u.ibss.current_bss) chan = wdev->u.ibss.current_bss->pub.channel; else if (wdev->wext.ibss.chandef.chan) chan = wdev->wext.ibss.chandef.chan; - wdev_unlock(wdev); if (chan) { freq->m = chan->center_freq; @@ -405,11 +374,9 @@ if (!rdev->ops->join_ibss) return -EOPNOTSUPP; - wdev_lock(wdev); err = 0; if (wdev->u.ibss.ssid_len) - err = __cfg80211_leave_ibss(rdev, dev, true); - wdev_unlock(wdev); + err = cfg80211_leave_ibss(rdev, dev, true); if (err) return err; @@ -422,11 +389,7 @@ wdev->wext.ibss.ssid = wdev->u.ibss.ssid; wdev->wext.ibss.ssid_len = len; - wdev_lock(wdev); - err = cfg80211_ibss_wext_join(rdev, wdev); - wdev_unlock(wdev); - - return err; + return cfg80211_ibss_wext_join(rdev, wdev); } int cfg80211_ibss_wext_giwessid(struct net_device *dev, @@ -441,7 +404,6 @@ data->flags = 0; - wdev_lock(wdev); if (wdev->u.ibss.ssid_len) { data->flags = 1; data->length = wdev->u.ibss.ssid_len; @@ -451,7 +413,6 @@ data->length = wdev->wext.ibss.ssid_len; memcpy(ssid, wdev->wext.ibss.ssid, data->length); } - wdev_unlock(wdev); return 0; } @@ -491,11 +452,9 @@ ether_addr_equal(bssid, wdev->wext.ibss.bssid)) return 0; - wdev_lock(wdev); err = 0; if (wdev->u.ibss.ssid_len) - err = __cfg80211_leave_ibss(rdev, dev, true); - wdev_unlock(wdev); + err = cfg80211_leave_ibss(rdev, dev, true); if (err) return err; @@ -506,11 +465,7 @@ } else wdev->wext.ibss.bssid = NULL; - wdev_lock(wdev); - err = cfg80211_ibss_wext_join(rdev, wdev); - wdev_unlock(wdev); - - return err; + return cfg80211_ibss_wext_join(rdev, wdev); } int cfg80211_ibss_wext_giwap(struct net_device *dev, @@ -525,7 +480,6 @@ ap_addr->sa_family = ARPHRD_ETHER; - wdev_lock(wdev); if (wdev->u.ibss.current_bss) memcpy(ap_addr->sa_data, wdev->u.ibss.current_bss->pub.bssid, ETH_ALEN); @@ -534,8 +488,6 @@ else eth_zero_addr(ap_addr->sa_data); - wdev_unlock(wdev); - return 0; } #endif diff -Nru backport-iwlwifi-dkms-11289/net/wireless/mesh.c backport-iwlwifi-dkms-11510/net/wireless/mesh.c --- backport-iwlwifi-dkms-11289/net/wireless/mesh.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/wireless/mesh.c 2023-10-04 04:18:43.000000000 +0800 @@ -1,7 +1,7 @@ // SPDX-License-Identifier: GPL-2.0 /* * Portions - * Copyright (C) 2022 Intel Corporation + * Copyright (C) 2022-2023 Intel Corporation */ #include #include @@ -109,7 +109,7 @@ BUILD_BUG_ON(IEEE80211_MAX_SSID_LEN != IEEE80211_MAX_MESH_ID_LEN); - ASSERT_WDEV_LOCK(wdev); + lockdep_assert_wiphy(wdev->wiphy); if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_MESH_POINT) return -EOPNOTSUPP; @@ -257,13 +257,13 @@ return 0; } -int __cfg80211_leave_mesh(struct cfg80211_registered_device *rdev, - struct net_device *dev) +int cfg80211_leave_mesh(struct cfg80211_registered_device *rdev, + struct net_device *dev) { struct wireless_dev *wdev = dev->ieee80211_ptr; int err; - ASSERT_WDEV_LOCK(wdev); + lockdep_assert_wiphy(wdev->wiphy); if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_MESH_POINT) return -EOPNOTSUPP; @@ -287,16 +287,3 @@ return err; } - -int cfg80211_leave_mesh(struct cfg80211_registered_device *rdev, - struct net_device *dev) -{ - struct wireless_dev *wdev = dev->ieee80211_ptr; - int err; - - wdev_lock(wdev); - err = __cfg80211_leave_mesh(rdev, dev); - wdev_unlock(wdev); - - return err; -} diff -Nru backport-iwlwifi-dkms-11289/net/wireless/mlme.c backport-iwlwifi-dkms-11510/net/wireless/mlme.c --- backport-iwlwifi-dkms-11289/net/wireless/mlme.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/wireless/mlme.c 2023-10-04 04:18:43.000000000 +0800 @@ -4,7 +4,7 @@ * * Copyright (c) 2009, Jouni Malinen * Copyright (c) 2015 Intel Deutschland GmbH - * Copyright (C) 2019-2020, 2022 Intel Corporation + * Copyright (C) 2019-2020, 2022-2023 Intel Corporation */ #include @@ -149,7 +149,7 @@ struct wireless_dev *wdev = dev->ieee80211_ptr; struct ieee80211_mgmt *mgmt = (void *)buf; - ASSERT_WDEV_LOCK(wdev); + lockdep_assert_wiphy(wdev->wiphy); trace_cfg80211_rx_mlme_mgmt(dev, buf, len); @@ -214,7 +214,7 @@ struct wireless_dev *wdev = dev->ieee80211_ptr; struct ieee80211_mgmt *mgmt = (void *)buf; - ASSERT_WDEV_LOCK(wdev); + lockdep_assert_wiphy(wdev->wiphy); trace_cfg80211_tx_mlme_mgmt(dev, buf, len, reconnect); @@ -262,7 +262,7 @@ { struct wireless_dev *wdev = dev->ieee80211_ptr; - ASSERT_WDEV_LOCK(wdev); + lockdep_assert_wiphy(wdev->wiphy); if (!req->bss) return -ENOENT; @@ -326,7 +326,7 @@ struct wireless_dev *wdev = dev->ieee80211_ptr; int err, i, j; - ASSERT_WDEV_LOCK(wdev); + lockdep_assert_wiphy(wdev->wiphy); for (i = 1; i < ARRAY_SIZE(req->links); i++) { if (!req->links[i].bss) @@ -380,7 +380,7 @@ .local_state_change = local_state_change, }; - ASSERT_WDEV_LOCK(wdev); + lockdep_assert_wiphy(wdev->wiphy); if (local_state_change && (!wdev->connected || @@ -410,7 +410,7 @@ }; int err; - ASSERT_WDEV_LOCK(wdev); + lockdep_assert_wiphy(wdev->wiphy); if (!wdev->connected) return -ENOTCONN; @@ -433,7 +433,7 @@ struct wireless_dev *wdev = dev->ieee80211_ptr; u8 bssid[ETH_ALEN]; - ASSERT_WDEV_LOCK(wdev); + lockdep_assert_wiphy(wdev->wiphy); if (!rdev->ops->deauth) return; @@ -713,6 +713,8 @@ const struct ieee80211_mgmt *mgmt; u16 stype; + lockdep_assert_wiphy(&rdev->wiphy); + if (!wdev->wiphy->mgmt_stypes) return -EOPNOTSUPP; @@ -735,8 +737,6 @@ mgmt->u.action.category != WLAN_CATEGORY_PUBLIC) { int err = 0; - wdev_lock(wdev); - switch (wdev->iftype) { case NL80211_IFTYPE_ADHOC: /* @@ -801,7 +801,6 @@ err = -EOPNOTSUPP; break; } - wdev_unlock(wdev); if (err) return err; diff -Nru backport-iwlwifi-dkms-11289/net/wireless/nl80211.c backport-iwlwifi-dkms-11510/net/wireless/nl80211.c --- backport-iwlwifi-dkms-11289/net/wireless/nl80211.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/wireless/nl80211.c 2023-10-04 04:18:43.000000000 +0800 @@ -106,7 +106,7 @@ ASSERT_RTNL(); - list_for_each_entry(rdev, &cfg80211_rdev_list, list) { + for_each_rdev(rdev) { struct wireless_dev *wdev; if (wiphy_net(&rdev->wiphy) != netns) @@ -826,12 +826,14 @@ [NL80211_ATTR_PUNCT_BITMAP] = NLA_POLICY_FULL_RANGE(NLA_U32, &nl80211_punct_bitmap_range), #else + [NL80211_ATTR_PUNCT_BITMAP] = NLA_POLICY_RANGE(NLA_U32, 0, 0xffff), #endif [NL80211_ATTR_MAX_HW_TIMESTAMP_PEERS] = { .type = NLA_U16 }, [NL80211_ATTR_HW_TIMESTAMP_ENABLED] = { .type = NLA_FLAG }, [NL80211_ATTR_EMA_RNR_ELEMS] = { .type = NLA_NESTED }, + [NL80211_ATTR_BSS_DUMP_INCLUDE_USE_DATA] = { .type = NLA_FLAG }, }; /* policy for the key attributes */ @@ -1208,6 +1210,9 @@ if ((chan->flags & IEEE80211_CHAN_NO_EHT) && nla_put_flag(msg, NL80211_FREQUENCY_ATTR_NO_EHT)) goto nla_put_failure; + if ((chan->flags & IEEE80211_CHAN_DFS_CONCURRENT) && + nla_put_flag(msg, NL80211_FREQUENCY_ATTR_DFS_CONCURRENT)) + goto nla_put_failure; } if (nla_put_u32(msg, NL80211_FREQUENCY_ATTR_MAX_TX_POWER, @@ -1558,7 +1563,7 @@ static int nl80211_key_allowed(struct wireless_dev *wdev) { - ASSERT_WDEV_LOCK(wdev); + lockdep_assert_wiphy(wdev->wiphy); switch (wdev->iftype) { case NL80211_IFTYPE_AP: @@ -3094,7 +3099,7 @@ cb->args[0] = (long)state; } - list_for_each_entry(rdev, &cfg80211_rdev_list, list) { + for_each_rdev(rdev) { if (!net_eq(wiphy_net(&rdev->wiphy), sock_net(skb->sk))) continue; if (++idx <= state->start) @@ -3442,13 +3447,8 @@ struct cfg80211_registered_device *rdev = info->user_ptr[0]; int link_id = nl80211_link_id_or_invalid(info->attrs); struct net_device *netdev = info->user_ptr[1]; - int ret; - wdev_lock(netdev->ieee80211_ptr); - ret = __nl80211_set_channel(rdev, netdev, info, link_id); - wdev_unlock(netdev->ieee80211_ptr); - - return ret; + return __nl80211_set_channel(rdev, netdev, info, link_id); } static int nl80211_set_wiphy(struct sk_buff *skb, struct genl_info *info) @@ -3555,7 +3555,6 @@ txq_params.link_id = nl80211_link_id_or_invalid(info->attrs); - wdev_lock(netdev->ieee80211_ptr); if (txq_params.link_id >= 0 && !(netdev->ieee80211_ptr->valid_links & BIT(txq_params.link_id))) @@ -3566,7 +3565,6 @@ else result = rdev_set_txq_params(rdev, netdev, &txq_params); - wdev_unlock(netdev->ieee80211_ptr); if (result) goto out; } @@ -3576,12 +3574,10 @@ int link_id = nl80211_link_id_or_invalid(info->attrs); if (wdev) { - wdev_lock(wdev); result = __nl80211_set_channel( rdev, nl80211_can_set_dev_channel(wdev) ? netdev : NULL, info, link_id); - wdev_unlock(wdev); } else { result = __nl80211_set_channel(rdev, netdev, info, link_id); } @@ -3889,33 +3885,31 @@ goto nla_put_failure; } - wdev_lock(wdev); switch (wdev->iftype) { case NL80211_IFTYPE_AP: case NL80211_IFTYPE_P2P_GO: if (wdev->u.ap.ssid_len && nla_put(msg, NL80211_ATTR_SSID, wdev->u.ap.ssid_len, wdev->u.ap.ssid)) - goto nla_put_failure_locked; + goto nla_put_failure; break; case NL80211_IFTYPE_STATION: case NL80211_IFTYPE_P2P_CLIENT: if (wdev->u.client.ssid_len && nla_put(msg, NL80211_ATTR_SSID, wdev->u.client.ssid_len, wdev->u.client.ssid)) - goto nla_put_failure_locked; + goto nla_put_failure; break; case NL80211_IFTYPE_ADHOC: if (wdev->u.ibss.ssid_len && nla_put(msg, NL80211_ATTR_SSID, wdev->u.ibss.ssid_len, wdev->u.ibss.ssid)) - goto nla_put_failure_locked; + goto nla_put_failure; break; default: /* nothing */ break; } - wdev_unlock(wdev); if (rdev->ops->get_txq_stats) { struct cfg80211_txq_stats txqstats = {}; @@ -3962,8 +3956,6 @@ genlmsg_end(msg, hdr); return 0; - nla_put_failure_locked: - wdev_unlock(wdev); nla_put_failure: genlmsg_cancel(msg, hdr); return -EMSGSIZE; @@ -4004,7 +3996,7 @@ filter_wiphy = cb->args[2] - 1; } - list_for_each_entry(rdev, &cfg80211_rdev_list, list) { + for_each_rdev(rdev) { if (!net_eq(wiphy_net(&rdev->wiphy), sock_net(skb->sk))) continue; if (wp_idx < wp_start) { @@ -4210,7 +4202,6 @@ if (netif_running(dev)) return -EBUSY; - wdev_lock(wdev); BUILD_BUG_ON(IEEE80211_MAX_SSID_LEN != IEEE80211_MAX_MESH_ID_LEN); wdev->u.mesh.id_up_len = @@ -4218,7 +4209,6 @@ memcpy(wdev->u.mesh.id, nla_data(info->attrs[NL80211_ATTR_MESH_ID]), wdev->u.mesh.id_up_len); - wdev_unlock(wdev); } if (info->attrs[NL80211_ATTR_4ADDR]) { @@ -4319,7 +4309,6 @@ case NL80211_IFTYPE_MESH_POINT: if (!info->attrs[NL80211_ATTR_MESH_ID]) break; - wdev_lock(wdev); BUILD_BUG_ON(IEEE80211_MAX_SSID_LEN != IEEE80211_MAX_MESH_ID_LEN); wdev->u.mesh.id_up_len = @@ -4327,7 +4316,6 @@ memcpy(wdev->u.mesh.id, nla_data(info->attrs[NL80211_ATTR_MESH_ID]), wdev->u.mesh.id_up_len); - wdev_unlock(wdev); break; case NL80211_IFTYPE_NAN: case NL80211_IFTYPE_P2P_DEVICE: @@ -4618,79 +4606,67 @@ !(key.p.mode == NL80211_KEY_SET_TX)) return -EINVAL; - wdev_lock(wdev); - if (key.def) { - if (!rdev->ops->set_default_key) { - err = -EOPNOTSUPP; - goto out; - } + if (!rdev->ops->set_default_key) + return -EOPNOTSUPP; err = nl80211_key_allowed(wdev); if (err) - goto out; + return err; err = nl80211_validate_key_link_id(info, wdev, link_id, false); if (err) - goto out; + return err; err = rdev_set_default_key(rdev, dev, link_id, key.idx, key.def_uni, key.def_multi); if (err) - goto out; + return err; #ifdef CPTCFG_CFG80211_WEXT wdev->wext.default_key = key.idx; #endif + return 0; } else if (key.defmgmt) { - if (key.def_uni || !key.def_multi) { - err = -EINVAL; - goto out; - } + if (key.def_uni || !key.def_multi) + return -EINVAL; - if (!rdev->ops->set_default_mgmt_key) { - err = -EOPNOTSUPP; - goto out; - } + if (!rdev->ops->set_default_mgmt_key) + return -EOPNOTSUPP; err = nl80211_key_allowed(wdev); if (err) - goto out; + return err; err = nl80211_validate_key_link_id(info, wdev, link_id, false); if (err) - goto out; + return err; err = rdev_set_default_mgmt_key(rdev, dev, link_id, key.idx); if (err) - goto out; + return err; #ifdef CPTCFG_CFG80211_WEXT wdev->wext.default_mgmt_key = key.idx; #endif + return 0; } else if (key.defbeacon) { - if (key.def_uni || !key.def_multi) { - err = -EINVAL; - goto out; - } + if (key.def_uni || !key.def_multi) + return -EINVAL; - if (!rdev->ops->set_default_beacon_key) { - err = -EOPNOTSUPP; - goto out; - } + if (!rdev->ops->set_default_beacon_key) + return -EOPNOTSUPP; err = nl80211_key_allowed(wdev); if (err) - goto out; + return err; err = nl80211_validate_key_link_id(info, wdev, link_id, false); if (err) - goto out; + return err; - err = rdev_set_default_beacon_key(rdev, dev, link_id, key.idx); - if (err) - goto out; + return rdev_set_default_beacon_key(rdev, dev, link_id, key.idx); } else if (key.p.mode == NL80211_KEY_SET_TX && wiphy_ext_feature_isset(&rdev->wiphy, NL80211_EXT_FEATURE_EXT_KEY_ID)) { @@ -4699,25 +4675,19 @@ if (info->attrs[NL80211_ATTR_MAC]) mac_addr = nla_data(info->attrs[NL80211_ATTR_MAC]); - if (!mac_addr || key.idx < 0 || key.idx > 1) { - err = -EINVAL; - goto out; - } + if (!mac_addr || key.idx < 0 || key.idx > 1) + return -EINVAL; err = nl80211_validate_key_link_id(info, wdev, link_id, true); if (err) - goto out; + return err; - err = rdev_add_key(rdev, dev, link_id, key.idx, - NL80211_KEYTYPE_PAIRWISE, - mac_addr, &key.p); - } else { - err = -EINVAL; + return rdev_add_key(rdev, dev, link_id, key.idx, + NL80211_KEYTYPE_PAIRWISE, + mac_addr, &key.p); } - out: - wdev_unlock(wdev); - return err; + return -EINVAL; } static int nl80211_new_key(struct sk_buff *skb, struct genl_info *info) @@ -4770,7 +4740,6 @@ return -EINVAL; } - wdev_lock(wdev); err = nl80211_key_allowed(wdev); if (err) GENL_SET_ERR_MSG(info, "key not allowed"); @@ -4786,7 +4755,6 @@ if (err) GENL_SET_ERR_MSG(info, "key addition failed"); } - wdev_unlock(wdev); return err; } @@ -4827,7 +4795,6 @@ if (!rdev->ops->del_key) return -EOPNOTSUPP; - wdev_lock(wdev); err = nl80211_key_allowed(wdev); if (key.type == NL80211_KEYTYPE_GROUP && mac_addr && @@ -4851,7 +4818,6 @@ wdev->wext.default_mgmt_key = -1; } #endif - wdev_unlock(wdev); return err; } @@ -5450,8 +5416,11 @@ if (!wiphy->mbssid_max_interfaces) return ERR_PTR(-EINVAL); - nla_for_each_nested(nl_elems, attrs, rem_elems) + nla_for_each_nested(nl_elems, attrs, rem_elems) { + if (num_elems >= 255) + return ERR_PTR(-EINVAL); num_elems++; + } elems = kzalloc(struct_size(elems, elem, num_elems), GFP_KERNEL); if (!elems) @@ -6089,20 +6058,18 @@ goto out; } - wdev_lock(wdev); - if (info->attrs[NL80211_ATTR_TX_RATES]) { err = nl80211_parse_tx_bitrate_mask(info, info->attrs, NL80211_ATTR_TX_RATES, ¶ms->beacon_rate, dev, false, link_id); if (err) - goto out_unlock; + goto out; err = validate_beacon_tx_rate(rdev, params->chandef.chan->band, ¶ms->beacon_rate); if (err) - goto out_unlock; + goto out; } if (info->attrs[NL80211_ATTR_SMPS_MODE]) { @@ -6115,19 +6082,19 @@ if (!(rdev->wiphy.features & NL80211_FEATURE_STATIC_SMPS)) { err = -EINVAL; - goto out_unlock; + goto out; } break; case NL80211_SMPS_DYNAMIC: if (!(rdev->wiphy.features & NL80211_FEATURE_DYNAMIC_SMPS)) { err = -EINVAL; - goto out_unlock; + goto out; } break; default: err = -EINVAL; - goto out_unlock; + goto out; } } else { params->smps_mode = NL80211_SMPS_OFF; @@ -6136,7 +6103,7 @@ params->pbss = nla_get_flag(info->attrs[NL80211_ATTR_PBSS]); if (params->pbss && !rdev->wiphy.bands[NL80211_BAND_60GHZ]) { err = -EOPNOTSUPP; - goto out_unlock; + goto out; } if (info->attrs[NL80211_ATTR_ACL_POLICY]) { @@ -6144,7 +6111,7 @@ if (IS_ERR(params->acl)) { err = PTR_ERR(params->acl); params->acl = NULL; - goto out_unlock; + goto out; } } @@ -6156,7 +6123,7 @@ info->attrs[NL80211_ATTR_HE_OBSS_PD], ¶ms->he_obss_pd); if (err) - goto out_unlock; + goto out; } if (info->attrs[NL80211_ATTR_FILS_DISCOVERY]) { @@ -6164,7 +6131,7 @@ info->attrs[NL80211_ATTR_FILS_DISCOVERY], params); if (err) - goto out_unlock; + goto out; } if (info->attrs[NL80211_ATTR_UNSOL_BCAST_PROBE_RESP]) { @@ -6172,7 +6139,7 @@ rdev, info->attrs[NL80211_ATTR_UNSOL_BCAST_PROBE_RESP], params); if (err) - goto out_unlock; + goto out; } if (info->attrs[NL80211_ATTR_MBSSID_CONFIG]) { @@ -6183,17 +6150,17 @@ params->beacon.mbssid_ies->cnt : 0); if (err) - goto out_unlock; + goto out; } if (!params->mbssid_config.ema && params->beacon.rnr_ies) { err = -EINVAL; - goto out_unlock; + goto out; } err = nl80211_calculate_ap_params(params); if (err) - goto out_unlock; + goto out; if (info->attrs[NL80211_ATTR_AP_SETTINGS_FLAGS]) params->flags = nla_get_u32( @@ -6205,7 +6172,7 @@ info->attrs[NL80211_ATTR_SOCKET_OWNER] && wdev->conn_owner_nlportid != info->snd_portid) { err = -EINVAL; - goto out_unlock; + goto out; } /* FIXME: validate MLO/link-id against driver capabilities */ @@ -6223,8 +6190,6 @@ nl80211_send_ap_started(wdev, link_id); } -out_unlock: - wdev_unlock(wdev); out: kfree(params->acl); kfree(params->beacon.mbssid_ies); @@ -6262,9 +6227,7 @@ if (err) goto out; - wdev_lock(wdev); err = rdev_change_beacon(rdev, dev, ¶ms); - wdev_unlock(wdev); out: kfree(params.mbssid_ies); @@ -6390,12 +6353,27 @@ return false; switch (info->bw) { + case RATE_INFO_BW_1: + rate_flg = NL80211_RATE_INFO_1_MHZ_WIDTH; + break; + case RATE_INFO_BW_2: + rate_flg = NL80211_RATE_INFO_2_MHZ_WIDTH; + break; + case RATE_INFO_BW_4: + rate_flg = NL80211_RATE_INFO_4_MHZ_WIDTH; + break; case RATE_INFO_BW_5: rate_flg = NL80211_RATE_INFO_5_MHZ_WIDTH; break; + case RATE_INFO_BW_8: + rate_flg = NL80211_RATE_INFO_8_MHZ_WIDTH; + break; case RATE_INFO_BW_10: rate_flg = NL80211_RATE_INFO_10_MHZ_WIDTH; break; + case RATE_INFO_BW_16: + rate_flg = NL80211_RATE_INFO_16_MHZ_WIDTH; + break; default: WARN_ON(1); fallthrough; @@ -6454,6 +6432,14 @@ nla_put_u8(msg, NL80211_RATE_INFO_HE_RU_ALLOC, info->he_ru_alloc)) return false; + } else if (info->flags & RATE_INFO_FLAGS_S1G_MCS) { + if (nla_put_u8(msg, NL80211_RATE_INFO_S1G_MCS, info->mcs)) + return false; + if (nla_put_u8(msg, NL80211_RATE_INFO_S1G_NSS, info->nss)) + return false; + if (info->flags & RATE_INFO_FLAGS_SHORT_GI && + nla_put_flag(msg, NL80211_RATE_INFO_SHORT_GI)) + return false; } else if (info->flags & RATE_INFO_FLAGS_EHT_MCS) { if (nla_put_u8(msg, NL80211_RATE_INFO_EHT_MCS, info->mcs)) return false; @@ -7303,9 +7289,7 @@ } /* driver will call cfg80211_check_station_change() */ - wdev_lock(dev->ieee80211_ptr); err = rdev_change_station(rdev, dev, mac_addr, ¶ms); - wdev_unlock(dev->ieee80211_ptr); out_put_vlan: dev_put(params.vlan); @@ -7573,7 +7557,6 @@ /* be aware of params.vlan when changing code here */ - wdev_lock(dev->ieee80211_ptr); if (wdev->valid_links) { if (params.link_sta_params.link_id < 0) { err = -EINVAL; @@ -7591,7 +7574,6 @@ } err = rdev_add_station(rdev, dev, mac_addr, ¶ms); out: - wdev_unlock(dev->ieee80211_ptr); dev_put(params.vlan); return err; } @@ -7601,7 +7583,6 @@ struct cfg80211_registered_device *rdev = info->user_ptr[0]; struct net_device *dev = info->user_ptr[1]; struct station_del_parameters params; - int ret; memset(¶ms, 0, sizeof(params)); @@ -7649,11 +7630,7 @@ params.reason_code = WLAN_REASON_PREV_AUTH_NOT_VALID; } - wdev_lock(dev->ieee80211_ptr); - ret = rdev_del_station(rdev, dev, ¶ms); - wdev_unlock(dev->ieee80211_ptr); - - return ret; + return rdev_del_station(rdev, dev, ¶ms); } static int nl80211_send_mpath(struct sk_buff *msg, u32 portid, u32 seq, @@ -7972,9 +7949,7 @@ { struct cfg80211_registered_device *rdev = info->user_ptr[0]; struct net_device *dev = info->user_ptr[1]; - struct wireless_dev *wdev = dev->ieee80211_ptr; struct bss_parameters params; - int err; memset(¶ms, 0, sizeof(params)); params.link_id = nl80211_link_id_or_invalid(info->attrs); @@ -8037,11 +8012,7 @@ dev->ieee80211_ptr->iftype != NL80211_IFTYPE_P2P_GO) return -EOPNOTSUPP; - wdev_lock(wdev); - err = rdev_change_bss(rdev, dev, ¶ms); - wdev_unlock(wdev); - - return err; + return rdev_change_bss(rdev, dev, ¶ms); } static int nl80211_req_set_reg(struct sk_buff *skb, struct genl_info *info) @@ -8112,13 +8083,11 @@ if (!rdev->ops->get_mesh_config) return -EOPNOTSUPP; - wdev_lock(wdev); /* If not connected, get default parameters */ if (!wdev->u.mesh.id_len) memcpy(&cur_params, &default_mesh_config, sizeof(cur_params)); else err = rdev_get_mesh_config(rdev, dev, &cur_params); - wdev_unlock(wdev); if (err) return err; @@ -8480,7 +8449,7 @@ struct cfg80211_registered_device *rdev = info->user_ptr[0]; struct net_device *dev = info->user_ptr[1]; struct wireless_dev *wdev = dev->ieee80211_ptr; - struct mesh_config cfg; + struct mesh_config cfg = {}; u32 mask; int err; @@ -8494,15 +8463,12 @@ if (err) return err; - wdev_lock(wdev); if (!wdev->u.mesh.id_len) err = -ENOLINK; if (!err) err = rdev_update_mesh_config(rdev, dev, mask, &cfg); - wdev_unlock(wdev); - return err; } @@ -8993,7 +8959,7 @@ unsigned int link_id; bool all_ok = true; - ASSERT_WDEV_LOCK(wdev); + lockdep_assert_wiphy(wdev->wiphy); if (!cfg80211_beaconing_iface_active(wdev)) return true; @@ -9255,7 +9221,6 @@ request->n_channels = i; - wdev_lock(wdev); for (i = 0; i < request->n_channels; i++) { struct ieee80211_channel *chan = request->channels[i]; @@ -9264,12 +9229,10 @@ continue; if (!cfg80211_wdev_on_sub_chan(wdev, chan, true)) { - wdev_unlock(wdev); err = -EBUSY; goto out_free; } } - wdev_unlock(wdev); i = 0; if (n_ssids) { @@ -9353,6 +9316,7 @@ else eth_broadcast_addr(request->bssid); + request->tsf_report_link_id = nl80211_link_id_or_invalid(info->attrs); request->wdev = wdev; request->wiphy = &rdev->wiphy; request->scan_start = jiffies; @@ -10289,9 +10253,7 @@ goto free; } - wdev_lock(wdev); err = rdev_channel_switch(rdev, dev, ¶ms); - wdev_unlock(wdev); free: kfree(params.beacon_after.mbssid_ies); @@ -10314,7 +10276,7 @@ void *hdr; struct nlattr *bss; - ASSERT_WDEV_LOCK(wdev); + lockdep_assert_wiphy(wdev->wiphy); hdr = nl80211hdr_put(msg, NETLINK_CB(cb->skb).portid, seq, flags, NL80211_CMD_NEW_SCAN_RESULTS); @@ -10437,6 +10399,15 @@ break; } + if (nla_put_u32(msg, NL80211_BSS_USE_FOR, res->use_for)) + goto nla_put_failure; + + if (res->cannot_use_reasons && + nla_put_u64_64bit(msg, NL80211_BSS_CANNOT_USE_REASONS, + res->cannot_use_reasons, + NL80211_BSS_PAD)) + goto nla_put_failure; + nla_nest_end(msg, bss); genlmsg_end(msg, hdr); @@ -10454,16 +10425,27 @@ struct cfg80211_registered_device *rdev; struct cfg80211_internal_bss *scan; struct wireless_dev *wdev; + struct nlattr **attrbuf; int start = cb->args[2], idx = 0; + bool dump_include_use_data; int err; - err = nl80211_prepare_wdev_dump(cb, &rdev, &wdev, NULL); - if (err) + attrbuf = kcalloc(NUM_NL80211_ATTR, sizeof(*attrbuf), GFP_KERNEL); + if (!attrbuf) + return -ENOMEM; + + err = nl80211_prepare_wdev_dump(cb, &rdev, &wdev, attrbuf); + if (err) { + kfree(attrbuf); return err; + } /* nl80211_prepare_wdev_dump acquired it in the successful case */ __acquire(&rdev->wiphy.mtx); - wdev_lock(wdev); + dump_include_use_data = + attrbuf[NL80211_ATTR_BSS_DUMP_INCLUDE_USE_DATA]; + kfree(attrbuf); + spin_lock_bh(&rdev->bss_lock); /* @@ -10480,6 +10462,9 @@ list_for_each_entry(scan, &rdev->bss_list, list) { if (++idx <= start) continue; + if (!dump_include_use_data && + !(scan->pub.use_for & NL80211_BSS_USE_FOR_NORMAL)) + continue; if (nl80211_send_bss(skb, cb, cb->nlh->nlmsg_seq, NLM_F_MULTI, rdev, wdev, scan) < 0) { @@ -10489,7 +10474,6 @@ } spin_unlock_bh(&rdev->bss_lock); - wdev_unlock(wdev); cb->args[2] = idx; wiphy_unlock(&rdev->wiphy); @@ -10612,9 +10596,7 @@ } while (1) { - wdev_lock(wdev); res = rdev_dump_survey(rdev, wdev->netdev, survey_idx, &survey); - wdev_unlock(wdev); if (res == -ENOENT) break; if (res) @@ -10787,9 +10769,7 @@ if (!req.bss) return -ENOENT; - wdev_lock(dev->ieee80211_ptr); err = cfg80211_mlme_auth(rdev, dev, &req); - wdev_unlock(dev->ieee80211_ptr); cfg80211_put_bss(&rdev->wiphy, req.bss); @@ -10936,12 +10916,13 @@ static struct cfg80211_bss *nl80211_assoc_bss(struct cfg80211_registered_device *rdev, const u8 *ssid, int ssid_len, - struct nlattr **attrs) + struct nlattr **attrs, + int assoc_link_id, int link_id) { struct ieee80211_channel *chan; struct cfg80211_bss *bss; const u8 *bssid; - u32 freq; + u32 freq, use_for = 0; if (!attrs[NL80211_ATTR_MAC] || !attrs[NL80211_ATTR_WIPHY_FREQ]) return ERR_PTR(-EINVAL); @@ -10956,10 +10937,16 @@ if (!chan) return ERR_PTR(-EINVAL); - bss = cfg80211_get_bss(&rdev->wiphy, chan, bssid, - ssid, ssid_len, - IEEE80211_BSS_TYPE_ESS, - IEEE80211_PRIVACY_ANY); + if (assoc_link_id >= 0) + use_for = NL80211_BSS_USE_FOR_MLD_LINK; + if (assoc_link_id == link_id) + use_for |= NL80211_BSS_USE_FOR_NORMAL; + + bss = __cfg80211_get_bss(&rdev->wiphy, chan, bssid, + ssid, ssid_len, + IEEE80211_BSS_TYPE_ESS, + IEEE80211_PRIVACY_ANY, + use_for); if (!bss) return ERR_PTR(-ENOENT); @@ -10999,8 +10986,9 @@ if (cfg80211_find_ext_elem(WLAN_EID_EXT_NON_INHERITANCE, req.ie, req.ie_len)) { - GENL_SET_ERR_MSG(info, - "non-inheritance makes no sense"); + NL_SET_ERR_MSG_ATTR(genl_info_extack(info), + info->attrs[NL80211_ATTR_IE], + "non-inheritance makes no sense"); return -EINVAL; } } @@ -11125,6 +11113,7 @@ if (!attrs[NL80211_ATTR_MLO_LINK_ID]) { err = -EINVAL; + NL_SET_BAD_ATTR(genl_info_extack(info), link); goto free; } @@ -11132,13 +11121,17 @@ /* cannot use the same link ID again */ if (req.links[link_id].bss) { err = -EINVAL; + NL_SET_BAD_ATTR(genl_info_extack(info), link); goto free; } req.links[link_id].bss = - nl80211_assoc_bss(rdev, ssid, ssid_len, attrs); + nl80211_assoc_bss(rdev, ssid, ssid_len, attrs, + req.link_id, link_id); if (IS_ERR(req.links[link_id].bss)) { err = PTR_ERR(req.links[link_id].bss); req.links[link_id].bss = NULL; + NL_SET_ERR_MSG_ATTR(genl_info_extack(info), + link, "Error fetching BSS for link"); goto free; } @@ -11151,8 +11144,9 @@ if (cfg80211_find_elem(WLAN_EID_FRAGMENT, req.links[link_id].elems, req.links[link_id].elems_len)) { - GENL_SET_ERR_MSG(info, - "cannot deal with fragmentation"); + NL_SET_ERR_MSG_ATTR(genl_info_extack(info), + attrs[NL80211_ATTR_IE], + "cannot deal with fragmentation"); err = -EINVAL; goto free; } @@ -11160,8 +11154,9 @@ if (cfg80211_find_ext_elem(WLAN_EID_EXT_NON_INHERITANCE, req.links[link_id].elems, req.links[link_id].elems_len)) { - GENL_SET_ERR_MSG(info, - "cannot deal with non-inheritance"); + NL_SET_ERR_MSG_ATTR(genl_info_extack(info), + attrs[NL80211_ATTR_IE], + "cannot deal with non-inheritance"); err = -EINVAL; goto free; } @@ -11196,7 +11191,8 @@ if (req.link_id >= 0) return -EINVAL; - req.bss = nl80211_assoc_bss(rdev, ssid, ssid_len, info->attrs); + req.bss = nl80211_assoc_bss(rdev, ssid, ssid_len, info->attrs, + -1, -1); if (IS_ERR(req.bss)) return PTR_ERR(req.bss); ap_addr = req.bss->bssid; @@ -11204,7 +11200,8 @@ err = nl80211_crypto_settings(rdev, info, &req.crypto, 1); if (!err) { - wdev_lock(dev->ieee80211_ptr); + struct nlattr *link; + int rem = 0; err = cfg80211_mlme_assoc(rdev, dev, &req); @@ -11215,7 +11212,33 @@ ap_addr, ETH_ALEN); } - wdev_unlock(dev->ieee80211_ptr); + /* Report error from first problematic link */ + if (info->attrs[NL80211_ATTR_MLO_LINKS]) { + nla_for_each_nested(link, + info->attrs[NL80211_ATTR_MLO_LINKS], + rem) { + struct nlattr *link_id_attr = + nla_find_nested(link, NL80211_ATTR_MLO_LINK_ID); + + if (!link_id_attr) + continue; + + link_id = nla_get_u8(link_id_attr); + + if (link_id == req.link_id) + continue; + + if (!req.links[link_id].error || + WARN_ON(req.links[link_id].error > 0)) + continue; + + WARN_ON(err >= 0); + + NL_SET_BAD_ATTR(genl_info_extack(info), link); + err = req.links[link_id].error; + break; + } + } } free: @@ -11232,7 +11255,7 @@ struct cfg80211_registered_device *rdev = info->user_ptr[0]; struct net_device *dev = info->user_ptr[1]; const u8 *ie = NULL, *bssid; - int ie_len = 0, err; + int ie_len = 0; u16 reason_code; bool local_state_change; @@ -11268,11 +11291,8 @@ local_state_change = !!info->attrs[NL80211_ATTR_LOCAL_STATE_CHANGE]; - wdev_lock(dev->ieee80211_ptr); - err = cfg80211_mlme_deauth(rdev, dev, bssid, ie, ie_len, reason_code, - local_state_change); - wdev_unlock(dev->ieee80211_ptr); - return err; + return cfg80211_mlme_deauth(rdev, dev, bssid, ie, ie_len, reason_code, + local_state_change); } static int nl80211_disassociate(struct sk_buff *skb, struct genl_info *info) @@ -11280,7 +11300,7 @@ struct cfg80211_registered_device *rdev = info->user_ptr[0]; struct net_device *dev = info->user_ptr[1]; const u8 *ie = NULL, *bssid; - int ie_len = 0, err; + int ie_len = 0; u16 reason_code; bool local_state_change; @@ -11316,11 +11336,8 @@ local_state_change = !!info->attrs[NL80211_ATTR_LOCAL_STATE_CHANGE]; - wdev_lock(dev->ieee80211_ptr); - err = cfg80211_mlme_disassoc(rdev, dev, bssid, ie, ie_len, reason_code, - local_state_change); - wdev_unlock(dev->ieee80211_ptr); - return err; + return cfg80211_mlme_disassoc(rdev, dev, bssid, ie, ie_len, reason_code, + local_state_change); } static bool @@ -11498,13 +11515,11 @@ ibss.userspace_handles_dfs = nla_get_flag(info->attrs[NL80211_ATTR_HANDLE_DFS]); - wdev_lock(dev->ieee80211_ptr); err = __cfg80211_join_ibss(rdev, dev, &ibss, connkeys); if (err) kfree_sensitive(connkeys); else if (info->attrs[NL80211_ATTR_SOCKET_OWNER]) dev->ieee80211_ptr->conn_owner_nlportid = info->snd_portid; - wdev_unlock(dev->ieee80211_ptr); return err; } @@ -12037,8 +12052,6 @@ if (nla_get_flag(info->attrs[NL80211_ATTR_MLO_SUPPORT])) connect.flags |= CONNECT_REQ_MLO_SUPPORT; - wdev_lock(dev->ieee80211_ptr); - err = cfg80211_connect(rdev, dev, &connect, connkeys, connect.prev_bssid); if (err) @@ -12053,8 +12066,6 @@ eth_zero_addr(dev->ieee80211_ptr->disconnect_bssid); } - wdev_unlock(dev->ieee80211_ptr); - return err; } @@ -12068,7 +12079,6 @@ bool fils_sk_offload; u32 auth_type; u32 changed = 0; - int ret; if (!rdev->ops->update_connect_params) return -EOPNOTSUPP; @@ -12129,14 +12139,10 @@ changed |= UPDATE_AUTH_TYPE; } - wdev_lock(dev->ieee80211_ptr); if (!wdev->connected) - ret = -ENOLINK; - else - ret = rdev_update_connect_params(rdev, dev, &connect, changed); - wdev_unlock(dev->ieee80211_ptr); + return -ENOLINK; - return ret; + return rdev_update_connect_params(rdev, dev, &connect, changed); } static int nl80211_disconnect(struct sk_buff *skb, struct genl_info *info) @@ -12144,7 +12150,6 @@ struct cfg80211_registered_device *rdev = info->user_ptr[0]; struct net_device *dev = info->user_ptr[1]; u16 reason; - int ret; if (dev->ieee80211_ptr->conn_owner_nlportid && dev->ieee80211_ptr->conn_owner_nlportid != info->snd_portid) @@ -12162,10 +12167,7 @@ dev->ieee80211_ptr->iftype != NL80211_IFTYPE_P2P_CLIENT) return -EOPNOTSUPP; - wdev_lock(dev->ieee80211_ptr); - ret = cfg80211_disconnect(rdev, dev, reason, true); - wdev_unlock(dev->ieee80211_ptr); - return ret; + return cfg80211_disconnect(rdev, dev, reason, true); } static int nl80211_wiphy_netns(struct sk_buff *skb, struct genl_info *info) @@ -12376,7 +12378,6 @@ if (err) return err; - wdev_lock(wdev); if (!cfg80211_off_channel_oper_allowed(wdev, chandef.chan)) { const struct cfg80211_chan_def *oper_chandef, *compat_chandef; @@ -12385,7 +12386,6 @@ if (WARN_ON(!oper_chandef)) { /* cannot happen since we must beacon to get here */ WARN_ON(1); - wdev_unlock(wdev); return -EBUSY; } @@ -12393,12 +12393,9 @@ compat_chandef = cfg80211_chandef_compatible(&chandef, oper_chandef); - if (compat_chandef != &chandef) { - wdev_unlock(wdev); + if (compat_chandef != &chandef) return -EBUSY; - } } - wdev_unlock(wdev); msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL); if (!msg) @@ -12457,23 +12454,18 @@ unsigned int link_id = nl80211_link_id(info->attrs); struct cfg80211_registered_device *rdev = info->user_ptr[0]; struct net_device *dev = info->user_ptr[1]; - struct wireless_dev *wdev = dev->ieee80211_ptr; int err; if (!rdev->ops->set_bitrate_mask) return -EOPNOTSUPP; - wdev_lock(wdev); err = nl80211_parse_tx_bitrate_mask(info, info->attrs, NL80211_ATTR_TX_RATES, &mask, dev, true, link_id); if (err) - goto out; + return err; - err = rdev_set_bitrate_mask(rdev, dev, link_id, NULL, &mask); -out: - wdev_unlock(wdev); - return err; + return rdev_set_bitrate_mask(rdev, dev, link_id, NULL, &mask); } static int nl80211_register_mgmt(struct sk_buff *skb, struct genl_info *info) @@ -12602,12 +12594,9 @@ if (!chandef.chan && params.offchan) return -EINVAL; - wdev_lock(wdev); if (params.offchan && - !cfg80211_off_channel_oper_allowed(wdev, chandef.chan)) { - wdev_unlock(wdev); + !cfg80211_off_channel_oper_allowed(wdev, chandef.chan)) return -EBUSY; - } params.link_id = nl80211_link_id_or_invalid(info->attrs); /* @@ -12616,11 +12605,8 @@ * to the driver. */ if (params.link_id >= 0 && - !(wdev->valid_links & BIT(params.link_id))) { - wdev_unlock(wdev); + !(wdev->valid_links & BIT(params.link_id))) return -EINVAL; - } - wdev_unlock(wdev); params.buf = nla_data(info->attrs[NL80211_ATTR_FRAME]); params.len = nla_len(info->attrs[NL80211_ATTR_FRAME]); @@ -12890,8 +12876,8 @@ struct cfg80211_registered_device *rdev = info->user_ptr[0]; struct net_device *dev = info->user_ptr[1]; struct wireless_dev *wdev = dev->ieee80211_ptr; - int i, err; s32 prev = S32_MIN; + int i; /* Check all values negative and sorted */ for (i = 0; i < n_thresholds; i++) { @@ -12905,9 +12891,7 @@ wdev->iftype != NL80211_IFTYPE_P2P_CLIENT) return -EOPNOTSUPP; - wdev_lock(wdev); cfg80211_cqm_config_free(wdev); - wdev_unlock(wdev); if (n_thresholds <= 1 && rdev->ops->set_cqm_rssi_config) { if (n_thresholds == 0 || thresholds[0] == 0) /* Disabling */ @@ -12924,17 +12908,14 @@ if (n_thresholds == 1 && thresholds[0] == 0) /* Disabling */ n_thresholds = 0; - wdev_lock(wdev); if (n_thresholds) { struct cfg80211_cqm_config *cqm_config; cqm_config = kzalloc(struct_size(cqm_config, rssi_thresholds, n_thresholds), GFP_KERNEL); - if (!cqm_config) { - err = -ENOMEM; - goto unlock; - } + if (!cqm_config) + return -ENOMEM; cqm_config->rssi_hyst = hysteresis; cqm_config->n_rssi_thresholds = n_thresholds; @@ -12945,12 +12926,7 @@ wdev->cqm_config = cqm_config; } - err = cfg80211_cqm_rssi_update(rdev, dev); - -unlock: - wdev_unlock(wdev); - - return err; + return cfg80211_cqm_rssi_update(rdev, dev); } static int nl80211_set_cqm(struct sk_buff *skb, struct genl_info *info) @@ -13132,11 +13108,9 @@ setup.control_port_over_nl80211 = true; } - wdev_lock(dev->ieee80211_ptr); err = __cfg80211_join_mesh(rdev, dev, &setup, &cfg); if (!err && info->attrs[NL80211_ATTR_SOCKET_OWNER]) dev->ieee80211_ptr->conn_owner_nlportid = info->snd_portid; - wdev_unlock(dev->ieee80211_ptr); return err; } @@ -14082,21 +14056,13 @@ if (tb[NL80211_REKEY_DATA_AKM]) rekey_data.akm = nla_get_u32(tb[NL80211_REKEY_DATA_AKM]); - wdev_lock(wdev); - if (!wdev->connected) { - err = -ENOTCONN; - goto out; - } + if (!wdev->connected) + return -ENOTCONN; - if (!rdev->ops->set_rekey_data) { - err = -EOPNOTSUPP; - goto out; - } + if (!rdev->ops->set_rekey_data) + return -EOPNOTSUPP; - err = rdev_set_rekey_data(rdev, dev, &rekey_data); - out: - wdev_unlock(wdev); - return err; + return rdev_set_rekey_data(rdev, dev, &rekey_data); } static int nl80211_register_unexpected_frame(struct sk_buff *skb, @@ -15300,11 +15266,9 @@ memcpy(qos_map->up, pos, IEEE80211_QOS_MAP_LEN_MIN); } - wdev_lock(dev->ieee80211_ptr); ret = nl80211_key_allowed(dev->ieee80211_ptr); if (!ret) ret = rdev_set_qos_map(rdev, dev, qos_map); - wdev_unlock(dev->ieee80211_ptr); kfree(qos_map); return ret; @@ -15318,7 +15282,6 @@ const u8 *peer; u8 tsid, up; u16 admitted_time = 0; - int err; if (!(rdev->wiphy.features & NL80211_FEATURE_SUPPORTS_WMM_ADMISSION)) return -EOPNOTSUPP; @@ -15348,34 +15311,25 @@ return -EINVAL; } - wdev_lock(wdev); switch (wdev->iftype) { case NL80211_IFTYPE_STATION: case NL80211_IFTYPE_P2P_CLIENT: if (wdev->connected) break; - err = -ENOTCONN; - goto out; + return -ENOTCONN; default: - err = -EOPNOTSUPP; - goto out; + return -EOPNOTSUPP; } - err = rdev_add_tx_ts(rdev, dev, tsid, peer, up, admitted_time); - - out: - wdev_unlock(wdev); - return err; + return rdev_add_tx_ts(rdev, dev, tsid, peer, up, admitted_time); } static int nl80211_del_tx_ts(struct sk_buff *skb, struct genl_info *info) { struct cfg80211_registered_device *rdev = info->user_ptr[0]; struct net_device *dev = info->user_ptr[1]; - struct wireless_dev *wdev = dev->ieee80211_ptr; const u8 *peer; u8 tsid; - int err; if (!info->attrs[NL80211_ATTR_TSID] || !info->attrs[NL80211_ATTR_MAC]) return -EINVAL; @@ -15383,11 +15337,7 @@ tsid = nla_get_u8(info->attrs[NL80211_ATTR_TSID]); peer = nla_data(info->attrs[NL80211_ATTR_MAC]); - wdev_lock(wdev); - err = rdev_del_tx_ts(rdev, dev, tsid, peer); - wdev_unlock(wdev); - - return err; + return rdev_del_tx_ts(rdev, dev, tsid, peer); } static int nl80211_tdls_channel_switch(struct sk_buff *skb, @@ -15443,11 +15393,7 @@ addr = nla_data(info->attrs[NL80211_ATTR_MAC]); oper_class = nla_get_u8(info->attrs[NL80211_ATTR_OPER_CLASS]); - wdev_lock(wdev); - err = rdev_tdls_channel_switch(rdev, dev, addr, oper_class, &chandef); - wdev_unlock(wdev); - - return err; + return rdev_tdls_channel_switch(rdev, dev, addr, oper_class, &chandef); } static int nl80211_tdls_cancel_channel_switch(struct sk_buff *skb, @@ -15455,7 +15401,6 @@ { struct cfg80211_registered_device *rdev = info->user_ptr[0]; struct net_device *dev = info->user_ptr[1]; - struct wireless_dev *wdev = dev->ieee80211_ptr; const u8 *addr; if (!rdev->ops->tdls_channel_switch || @@ -15476,9 +15421,7 @@ addr = nla_data(info->attrs[NL80211_ATTR_MAC]); - wdev_lock(wdev); rdev_tdls_cancel_channel_switch(rdev, dev, addr); - wdev_unlock(wdev); return 0; } @@ -15511,7 +15454,6 @@ struct net_device *dev = info->user_ptr[1]; struct wireless_dev *wdev = dev->ieee80211_ptr; struct cfg80211_pmk_conf pmk_conf = {}; - int ret; if (wdev->iftype != NL80211_IFTYPE_STATION && wdev->iftype != NL80211_IFTYPE_P2P_CLIENT) @@ -15524,34 +15466,24 @@ if (!info->attrs[NL80211_ATTR_MAC] || !info->attrs[NL80211_ATTR_PMK]) return -EINVAL; - wdev_lock(wdev); - if (!wdev->connected) { - ret = -ENOTCONN; - goto out; - } + if (!wdev->connected) + return -ENOTCONN; pmk_conf.aa = nla_data(info->attrs[NL80211_ATTR_MAC]); - if (memcmp(pmk_conf.aa, wdev->u.client.connected_addr, ETH_ALEN)) { - ret = -EINVAL; - goto out; - } + if (memcmp(pmk_conf.aa, wdev->u.client.connected_addr, ETH_ALEN)) + return -EINVAL; pmk_conf.pmk = nla_data(info->attrs[NL80211_ATTR_PMK]); pmk_conf.pmk_len = nla_len(info->attrs[NL80211_ATTR_PMK]); if (pmk_conf.pmk_len != WLAN_PMK_LEN && - pmk_conf.pmk_len != WLAN_PMK_LEN_SUITE_B_192) { - ret = -EINVAL; - goto out; - } + pmk_conf.pmk_len != WLAN_PMK_LEN_SUITE_B_192) + return -EINVAL; if (info->attrs[NL80211_ATTR_PMKR0_NAME]) pmk_conf.pmk_r0_name = nla_data(info->attrs[NL80211_ATTR_PMKR0_NAME]); - ret = rdev_set_pmk(rdev, dev, &pmk_conf); -out: - wdev_unlock(wdev); - return ret; + return rdev_set_pmk(rdev, dev, &pmk_conf); } static int nl80211_del_pmk(struct sk_buff *skb, struct genl_info *info) @@ -15560,7 +15492,6 @@ struct net_device *dev = info->user_ptr[1]; struct wireless_dev *wdev = dev->ieee80211_ptr; const u8 *aa; - int ret; if (wdev->iftype != NL80211_IFTYPE_STATION && wdev->iftype != NL80211_IFTYPE_P2P_CLIENT) @@ -15573,12 +15504,8 @@ if (!info->attrs[NL80211_ATTR_MAC]) return -EINVAL; - wdev_lock(wdev); aa = nla_data(info->attrs[NL80211_ATTR_MAC]); - ret = rdev_del_pmk(rdev, dev, aa); - wdev_unlock(wdev); - - return ret; + return rdev_del_pmk(rdev, dev, aa); } static int nl80211_external_auth(struct sk_buff *skb, struct genl_info *info) @@ -15652,8 +15579,6 @@ return -EINVAL; } - wdev_lock(wdev); - switch (wdev->iftype) { case NL80211_IFTYPE_AP: case NL80211_IFTYPE_P2P_GO: @@ -15662,21 +15587,16 @@ case NL80211_IFTYPE_ADHOC: if (wdev->u.ibss.current_bss) break; - err = -ENOTCONN; - goto out; + return -ENOTCONN; case NL80211_IFTYPE_STATION: case NL80211_IFTYPE_P2P_CLIENT: if (wdev->connected) break; - err = -ENOTCONN; - goto out; + return -ENOTCONN; default: - err = -EOPNOTSUPP; - goto out; + return -EOPNOTSUPP; } - wdev_unlock(wdev); - buf = nla_data(info->attrs[NL80211_ATTR_FRAME]); len = nla_len(info->attrs[NL80211_ATTR_FRAME]); dest = nla_data(info->attrs[NL80211_ATTR_MAC]); @@ -15692,9 +15612,6 @@ if (!err && !dont_wait_for_ack) nl_set_extack_cookie_u64(genl_info_extack(info), cookie); return err; - out: - wdev_unlock(wdev); - return err; } static int nl80211_get_ftm_responder_stats(struct sk_buff *skb, @@ -15972,8 +15889,6 @@ if (info->attrs[NL80211_ATTR_MAC]) tid_config->peer = nla_data(info->attrs[NL80211_ATTR_MAC]); - wdev_lock(dev->ieee80211_ptr); - nla_for_each_nested(tid, info->attrs[NL80211_ATTR_TID_CONFIG], rem_conf) { ret = nla_parse_nested(attrs, NL80211_TID_CONFIG_ATTR_MAX, @@ -15995,7 +15910,6 @@ bad_tid_conf: kfree(tid_config); - wdev_unlock(dev->ieee80211_ptr); return ret; } @@ -16092,9 +16006,7 @@ params.counter_offset_presp = offset; } - wdev_lock(wdev); err = rdev_color_change(rdev, dev, ¶ms); - wdev_unlock(wdev); out: kfree(params.beacon_next.mbssid_ies); @@ -16150,7 +16062,6 @@ !is_valid_ether_addr(nla_data(info->attrs[NL80211_ATTR_MAC]))) return -EINVAL; - wdev_lock(wdev); wdev->valid_links |= BIT(link_id); ether_addr_copy(wdev->links[link_id].addr, nla_data(info->attrs[NL80211_ATTR_MAC])); @@ -16160,7 +16071,6 @@ wdev->valid_links &= ~BIT(link_id); eth_zero_addr(wdev->links[link_id].addr); } - wdev_unlock(wdev); return ret; } @@ -16182,9 +16092,7 @@ return -EINVAL; } - wdev_lock(wdev); cfg80211_remove_link(wdev, link_id); - wdev_unlock(wdev); return 0; } @@ -16274,14 +16182,10 @@ if (err) return err; - wdev_lock(dev->ieee80211_ptr); if (add) - err = rdev_add_link_station(rdev, dev, ¶ms); - else - err = rdev_mod_link_station(rdev, dev, ¶ms); - wdev_unlock(dev->ieee80211_ptr); + return rdev_add_link_station(rdev, dev, ¶ms); - return err; + return rdev_mod_link_station(rdev, dev, ¶ms); } static int @@ -16302,7 +16206,6 @@ struct link_station_del_parameters params = {}; struct cfg80211_registered_device *rdev = info->user_ptr[0]; struct net_device *dev = info->user_ptr[1]; - int ret; if (!rdev->ops->del_link_station) return -EOPNOTSUPP; @@ -16314,11 +16217,7 @@ params.mld_mac = nla_data(info->attrs[NL80211_ATTR_MLD_ADDR]); params.link_id = nla_get_u8(info->attrs[NL80211_ATTR_MLO_LINK_ID]); - wdev_lock(dev->ieee80211_ptr); - ret = rdev_del_link_station(rdev, dev, ¶ms); - wdev_unlock(dev->ieee80211_ptr); - - return ret; + return rdev_del_link_station(rdev, dev, ¶ms); } static int nl80211_set_hw_timestamp(struct sk_buff *skb, @@ -18338,6 +18237,76 @@ nlmsg_free(msg); } +void cfg80211_links_removed(struct net_device *dev, u16 link_mask) +{ + struct wireless_dev *wdev = dev->ieee80211_ptr; + struct wiphy *wiphy = wdev->wiphy; + struct cfg80211_registered_device *rdev = wiphy_to_rdev(wiphy); + struct sk_buff *msg; + struct nlattr *links; + void *hdr; + + lockdep_assert_wiphy(wdev->wiphy); + trace_cfg80211_links_removed(dev, link_mask); + + if (WARN_ON(wdev->iftype != NL80211_IFTYPE_STATION && + wdev->iftype != NL80211_IFTYPE_P2P_CLIENT)) + return; + + if (WARN_ON(!wdev->valid_links || !link_mask || + (wdev->valid_links & link_mask) != link_mask || + wdev->valid_links == link_mask)) + return; + + cfg80211_wdev_release_link_bsses(wdev, link_mask); + wdev->valid_links &= ~link_mask; + + msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL); + if (!msg) + return; + + hdr = nl80211hdr_put(msg, 0, 0, 0, NL80211_CMD_LINKS_REMOVED); + if (!hdr) { + nlmsg_free(msg); + return; + } + + if (nla_put_u32(msg, NL80211_ATTR_WIPHY, rdev->wiphy_idx) || + nla_put_u32(msg, NL80211_ATTR_IFINDEX, dev->ifindex)) + goto nla_put_failure; + + links = nla_nest_start(msg, NL80211_ATTR_MLO_LINKS); + if (!links) + goto nla_put_failure; + + while (link_mask) { + struct nlattr *link; + int link_id = __ffs(link_mask); + + link = nla_nest_start(msg, link_id + 1); + if (!link) + goto nla_put_failure; + + if (nla_put_u8(msg, NL80211_ATTR_MLO_LINK_ID, link_id)) + goto nla_put_failure; + + nla_nest_end(msg, link); + link_mask &= ~(1 << link_id); + } + + nla_nest_end(msg, links); + + genlmsg_end(msg, hdr); + + genlmsg_multicast_netns(&nl80211_fam, wiphy_net(&rdev->wiphy), msg, 0, + NL80211_MCGRP_MLME, GFP_KERNEL); + return; + + nla_put_failure: + nlmsg_free(msg); +} +EXPORT_SYMBOL(cfg80211_links_removed); + void nl80211_send_ibss_bssid(struct cfg80211_registered_device *rdev, struct net_device *netdev, const u8 *bssid, gfp_t gfp) @@ -19158,49 +19127,6 @@ } EXPORT_SYMBOL(cfg80211_cqm_beacon_loss_notify); -void cfg80211_cqm_links_state_change_notify(struct net_device *dev, - u16 removed_links) -{ - struct wireless_dev *wdev = dev->ieee80211_ptr; - struct sk_buff *msg; - unsigned long removed = removed_links; - u8 link_id; - - ASSERT_WDEV_LOCK(wdev); - - trace_cfg80211_cqm_links_state_change_notify(dev, removed_links); - - if (!removed_links) - return; - - WARN_ON((wdev->valid_links & removed_links) != removed_links); - wdev->valid_links &= ~removed_links; - - for_each_set_bit(link_id, &removed, IEEE80211_MLD_MAX_NUM_LINKS) { - if (!wdev->links[link_id].client.current_bss) - continue; - - cfg80211_unhold_bss(wdev->links[link_id].client.current_bss); - cfg80211_put_bss(wdev->wiphy, - &wdev->links[link_id].client.current_bss->pub); - wdev->links[link_id].client.current_bss = NULL; - } - - msg = cfg80211_prepare_cqm(dev, NULL, GFP_KERNEL); - if (!msg) - return; - - if (nla_put_u16(msg, NL80211_ATTR_CQM_REMOVED_LINKS, removed_links)) - goto nla_put_failure; - - cfg80211_send_cqm(msg, GFP_KERNEL); - return; - - nla_put_failure: - nlmsg_free(msg); -} -EXPORT_SYMBOL(cfg80211_cqm_links_state_change_notify); - static void nl80211_gtk_rekey_notify(struct cfg80211_registered_device *rdev, struct net_device *netdev, const u8 *bssid, const u8 *replay_ctr, gfp_t gfp) @@ -19374,7 +19300,7 @@ struct wiphy *wiphy = wdev->wiphy; struct cfg80211_registered_device *rdev = wiphy_to_rdev(wiphy); - ASSERT_WDEV_LOCK(wdev); + lockdep_assert_wiphy(wdev->wiphy); WARN_INVALID_LINK_ID(wdev, link_id); trace_cfg80211_ch_switch_notify(dev, chandef, link_id, punct_bitmap); @@ -19402,6 +19328,7 @@ break; } + cfg80211_schedule_channels_check(dev); cfg80211_sched_dfs_chan_update(rdev); nl80211_ch_switch_notify(rdev, dev, link_id, chandef, GFP_KERNEL, @@ -19419,7 +19346,7 @@ struct wiphy *wiphy = wdev->wiphy; struct cfg80211_registered_device *rdev = wiphy_to_rdev(wiphy); - ASSERT_WDEV_LOCK(wdev); + lockdep_assert_wiphy(wdev->wiphy); WARN_INVALID_LINK_ID(wdev, link_id); trace_cfg80211_ch_switch_started_notify(dev, chandef, link_id, @@ -19442,7 +19369,7 @@ struct sk_buff *msg; void *hdr; - ASSERT_WDEV_LOCK(wdev); + lockdep_assert_wiphy(wdev->wiphy); trace_cfg80211_bss_color_notify(dev, cmd, count, color_bitmap); @@ -20159,6 +20086,21 @@ } EXPORT_SYMBOL(cfg80211_update_owe_info_event); +void cfg80211_schedule_channels_check(struct net_device *netdev) +{ + struct wireless_dev *wdev = netdev->ieee80211_ptr; + struct wiphy *wiphy = wdev->wiphy; + + /* Schedule channels check if NO_IR or DFS relaxations are supported */ + if (wdev->iftype == NL80211_IFTYPE_STATION && + (wiphy_ext_feature_isset(wiphy, + NL80211_EXT_FEATURE_DFS_CONCURRENT) || + (IS_ENABLED(CPTCFG_CFG80211_REG_RELAX_NO_IR) && + wiphy->regulatory_flags & REGULATORY_ENABLE_RELAX_NO_IR))) + reg_check_channels(); +} +EXPORT_SYMBOL(cfg80211_schedule_channels_check); + /* initialisation/exit functions */ int __init nl80211_init(void) diff -Nru backport-iwlwifi-dkms-11289/net/wireless/ocb.c backport-iwlwifi-dkms-11510/net/wireless/ocb.c --- backport-iwlwifi-dkms-11289/net/wireless/ocb.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/wireless/ocb.c 2023-10-04 04:18:43.000000000 +0800 @@ -4,7 +4,7 @@ * * Copyright: (c) 2014 Czech Technical University in Prague * (c) 2014 Volkswagen Group Research - * Copyright (C) 2022 Intel Corporation + * Copyright (C) 2022-2023 Intel Corporation * Author: Rostislav Lisovy * Funded by: Volkswagen Group Research */ @@ -15,14 +15,14 @@ #include "core.h" #include "rdev-ops.h" -int __cfg80211_join_ocb(struct cfg80211_registered_device *rdev, - struct net_device *dev, - struct ocb_setup *setup) +int cfg80211_join_ocb(struct cfg80211_registered_device *rdev, + struct net_device *dev, + struct ocb_setup *setup) { struct wireless_dev *wdev = dev->ieee80211_ptr; int err; - ASSERT_WDEV_LOCK(wdev); + lockdep_assert_wiphy(wdev->wiphy); if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_OCB) return -EOPNOTSUPP; @@ -40,27 +40,13 @@ return err; } -int cfg80211_join_ocb(struct cfg80211_registered_device *rdev, - struct net_device *dev, - struct ocb_setup *setup) -{ - struct wireless_dev *wdev = dev->ieee80211_ptr; - int err; - - wdev_lock(wdev); - err = __cfg80211_join_ocb(rdev, dev, setup); - wdev_unlock(wdev); - - return err; -} - -int __cfg80211_leave_ocb(struct cfg80211_registered_device *rdev, - struct net_device *dev) +int cfg80211_leave_ocb(struct cfg80211_registered_device *rdev, + struct net_device *dev) { struct wireless_dev *wdev = dev->ieee80211_ptr; int err; - ASSERT_WDEV_LOCK(wdev); + lockdep_assert_wiphy(wdev->wiphy); if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_OCB) return -EOPNOTSUPP; @@ -74,16 +60,3 @@ return err; } - -int cfg80211_leave_ocb(struct cfg80211_registered_device *rdev, - struct net_device *dev) -{ - struct wireless_dev *wdev = dev->ieee80211_ptr; - int err; - - wdev_lock(wdev); - err = __cfg80211_leave_ocb(rdev, dev); - wdev_unlock(wdev); - - return err; -} diff -Nru backport-iwlwifi-dkms-11289/net/wireless/pmsr.c backport-iwlwifi-dkms-11510/net/wireless/pmsr.c --- backport-iwlwifi-dkms-11289/net/wireless/pmsr.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/wireless/pmsr.c 2023-10-04 04:18:43.000000000 +0800 @@ -602,7 +602,7 @@ struct cfg80211_pmsr_request *req, *tmp; LIST_HEAD(free_list); - lockdep_assert_held(&wdev->mtx); + lockdep_assert_wiphy(wdev->wiphy); spin_lock_bh(&wdev->pmsr_lock); list_for_each_entry_safe(req, tmp, &wdev->pmsr_list, list) { @@ -625,9 +625,7 @@ pmsr_free_wk); wiphy_lock(wdev->wiphy); - wdev_lock(wdev); cfg80211_pmsr_process_abort(wdev); - wdev_unlock(wdev); wiphy_unlock(wdev->wiphy); } diff -Nru backport-iwlwifi-dkms-11289/net/wireless/reg.c backport-iwlwifi-dkms-11510/net/wireless/reg.c --- backport-iwlwifi-dkms-11289/net/wireless/reg.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/wireless/reg.c 2023-10-04 04:18:43.000000000 +0800 @@ -1594,6 +1594,9 @@ channel_flags |= IEEE80211_CHAN_NO_320MHZ; if (rd_flags & NL80211_RRF_NO_EHT) channel_flags |= IEEE80211_CHAN_NO_EHT; + if (rd_flags & NL80211_RRF_DFS_CONCURRENT) + channel_flags |= IEEE80211_CHAN_DFS_CONCURRENT; + return channel_flags; } @@ -2347,19 +2350,18 @@ bool ret; int link; - wdev_lock(wdev); iftype = wdev->iftype; /* make sure the interface is active */ if (!wdev->netdev || !netif_running(wdev->netdev)) - goto wdev_inactive_unlock; + return true; for (link = 0; link < ARRAY_SIZE(wdev->links); link++) { struct ieee80211_channel *chan; if (!wdev->valid_links && link > 0) break; - if (!(wdev->valid_links & BIT(link))) + if (wdev->valid_links && !(wdev->valid_links & BIT(link))) continue; switch (iftype) { case NL80211_IFTYPE_AP: @@ -2398,14 +2400,20 @@ case NL80211_IFTYPE_P2P_DEVICE: /* no enforcement required */ break; + case NL80211_IFTYPE_OCB: + if (!wdev->u.ocb.chandef.chan) + continue; + chandef = wdev->u.ocb.chandef; + break; + case NL80211_IFTYPE_NAN: + /* we have no info, but NAN is also pretty universal */ + continue; default: /* others not implemented for now */ - WARN_ON(1); + WARN_ON_ONCE(1); break; } - wdev_unlock(wdev); - switch (iftype) { case NL80211_IFTYPE_AP: case NL80211_IFTYPE_P2P_GO: @@ -2426,16 +2434,8 @@ default: break; } - - wdev_lock(wdev); } - wdev_unlock(wdev); - - return true; - -wdev_inactive_unlock: - wdev_unlock(wdev); return true; } @@ -2459,14 +2459,12 @@ rtnl_lock(); list_for_each_entry(rdev, &cfg80211_rdev_list, list) - if (!(rdev->wiphy.regulatory_flags & - REGULATORY_IGNORE_STALE_KICKOFF)) - reg_leave_invalid_chans(&rdev->wiphy); + reg_leave_invalid_chans(&rdev->wiphy); rtnl_unlock(); } -static void reg_check_channels(void) +void reg_check_channels(void) { /* * Give usermode a chance to do something nicer (move to another @@ -2514,7 +2512,7 @@ ASSERT_RTNL(); - list_for_each_entry(rdev, &cfg80211_rdev_list, list) { + for_each_rdev(rdev) { wiphy = &rdev->wiphy; wiphy_update_regulatory(wiphy, initiator); } @@ -2996,7 +2994,7 @@ ASSERT_RTNL(); - list_for_each_entry(rdev, &cfg80211_rdev_list, list) { + for_each_rdev(rdev) { if (wiphy == &rdev->wiphy) continue; wiphy_share_dfs_chan_state(wiphy, &rdev->wiphy); @@ -3062,7 +3060,7 @@ struct cfg80211_registered_device *rdev; struct wiphy *wiphy; - list_for_each_entry(rdev, &cfg80211_rdev_list, list) { + for_each_rdev(rdev) { wiphy = &rdev->wiphy; if (wiphy->regulatory_flags & REGULATORY_WIPHY_SELF_MANAGED && request->initiator == NL80211_REGDOM_SET_BY_USER) @@ -3127,7 +3125,7 @@ list_del_init(&pending_beacon->list); /* Applies the beacon hint to current wiphys */ - list_for_each_entry(rdev, &cfg80211_rdev_list, list) + for_each_rdev(rdev) wiphy_update_new_beacon(&rdev->wiphy, pending_beacon); /* Remembers the beacon hint for new wiphys or reg changes */ @@ -3182,7 +3180,7 @@ ASSERT_RTNL(); - list_for_each_entry(rdev, &cfg80211_rdev_list, list) { + for_each_rdev(rdev) { wiphy_lock(&rdev->wiphy); reg_process_self_managed_hint(&rdev->wiphy); wiphy_unlock(&rdev->wiphy); @@ -3522,7 +3520,7 @@ world_alpha2[0] = cfg80211_world_regdom->alpha2[0]; world_alpha2[1] = cfg80211_world_regdom->alpha2[1]; - list_for_each_entry(rdev, &cfg80211_rdev_list, list) { + for_each_rdev(rdev) { if (rdev->wiphy.regulatory_flags & REGULATORY_WIPHY_SELF_MANAGED) continue; if (rdev->wiphy.regulatory_flags & REGULATORY_CUSTOM_REG) @@ -3579,15 +3577,15 @@ struct cfg80211_registered_device *rdev; struct wireless_dev *wdev; - list_for_each_entry(rdev, &cfg80211_rdev_list, list) { + for_each_rdev(rdev) { + wiphy_lock(&rdev->wiphy); list_for_each_entry(wdev, &rdev->wiphy.wdev_list, list) { - wdev_lock(wdev); if (!(wdev->wiphy->regulatory_flags & flag)) { - wdev_unlock(wdev); + wiphy_unlock(&rdev->wiphy); return false; } - wdev_unlock(wdev); } + wiphy_unlock(&rdev->wiphy); } return true; @@ -4249,7 +4247,7 @@ if (WARN_ON(!cfg80211_chandef_valid(chandef))) return; - list_for_each_entry(rdev, &cfg80211_rdev_list, list) { + for_each_rdev(rdev) { if (wiphy == &rdev->wiphy) continue; diff -Nru backport-iwlwifi-dkms-11289/net/wireless/reg.h backport-iwlwifi-dkms-11510/net/wireless/reg.h --- backport-iwlwifi-dkms-11289/net/wireless/reg.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/wireless/reg.h 2023-10-04 04:18:43.000000000 +0800 @@ -181,6 +181,11 @@ */ int reg_reload_regdb(void); +/** + * reg_check_channels - schedule regulatory enforcement + */ +void reg_check_channels(void); + extern const u8 shipped_regdb_certs[]; extern unsigned int shipped_regdb_certs_len; extern const u8 extra_regdb_certs[]; diff -Nru backport-iwlwifi-dkms-11289/net/wireless/scan.c backport-iwlwifi-dkms-11510/net/wireless/scan.c --- backport-iwlwifi-dkms-11289/net/wireless/scan.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/wireless/scan.c 2023-10-04 04:18:43.000000000 +0800 @@ -316,8 +316,7 @@ non_inherit_elem = cfg80211_find_ext_elem(WLAN_EID_EXT_NON_INHERITANCE, subie, subie_len); - /* - * We copy the elements one by one from the parent to the generated + /* We copy the elements one by one from the parent to the generated * elements. * If they are not inherited (included in subie or in the non * inheritance element), then we copy all occurrences the first time @@ -377,8 +376,7 @@ } } - /* - * The above misses elements that are included in subie but not in the + /* The above misses elements that are included in subie but not in the * parent, so do a pass over subie and append those. * Skip the non-tx BSSID caps and non-inheritance element. */ @@ -626,8 +624,7 @@ if (!cfg80211_parse_bss_param(bss_params, entry)) return -EINVAL; - /* - * no information about the short ssid. Consider the entry valid + /* no information about the short ssid. Consider the entry valid * for now. It would later be dropped in case there are explicit * SSIDs that need to be matched */ @@ -662,7 +659,7 @@ ret = cfg80211_calc_short_ssid(ies, &ssid_elem, &s_ssid_tmp); if (ret) - return ret; + return 0; for_each_element_id(elem, WLAN_EID_REDUCED_NEIGHBOR_REPORT, ies->data, ies->len) { @@ -699,8 +696,7 @@ continue; } - /* - * TBTT info must include bss param + BSSID + + /* TBTT info must include bss param + BSSID + * (short SSID or same_ssid bit to be set). * ignore other options, and move to the * next AP info @@ -836,10 +832,47 @@ list_for_each_entry(intbss, &rdev->bss_list, list) { struct cfg80211_bss *res = &intbss->pub; const struct cfg80211_bss_ies *ies; + const struct element *ssid_elem; + struct cfg80211_colocated_ap *entry; + u32 s_ssid_tmp; + int ret; ies = rcu_access_pointer(res->ies); count += cfg80211_parse_colocated_ap(ies, &coloc_ap_list); + + /* In case the scan request specified a specific BSSID + * and the BSS is found and operating on 6GHz band then + * add this AP to the collocated APs list. + * This is relevant for ML probe requests when the lower + * band APs have not been discovered. + */ + if (is_broadcast_ether_addr(rdev_req->bssid) || + !ether_addr_equal(rdev_req->bssid, res->bssid) || + res->channel->band != NL80211_BAND_6GHZ) + continue; + + ret = cfg80211_calc_short_ssid(ies, &ssid_elem, + &s_ssid_tmp); + if (ret) + continue; + + entry = kzalloc(sizeof(*entry) + IEEE80211_MAX_SSID_LEN, + GFP_ATOMIC); + + if (!entry) + continue; + + memcpy(entry->bssid, res->bssid, ETH_ALEN); + entry->short_ssid = s_ssid_tmp; + memcpy(entry->ssid, ssid_elem->data, + ssid_elem->datalen); + entry->ssid_len = ssid_elem->datalen; + entry->short_ssid_valid = true; + entry->center_freq = res->channel->center_freq; + + list_add_tail(&entry->list, &coloc_ap_list); + count++; } spin_unlock_bh(&rdev->bss_lock); } @@ -1504,12 +1537,13 @@ } /* Returned bss is reference counted and must be cleaned up appropriately. */ -struct cfg80211_bss *cfg80211_get_bss(struct wiphy *wiphy, - struct ieee80211_channel *channel, - const u8 *bssid, - const u8 *ssid, size_t ssid_len, - enum ieee80211_bss_type bss_type, - enum ieee80211_privacy privacy) +struct cfg80211_bss *__cfg80211_get_bss(struct wiphy *wiphy, + struct ieee80211_channel *channel, + const u8 *bssid, + const u8 *ssid, size_t ssid_len, + enum ieee80211_bss_type bss_type, + enum ieee80211_privacy privacy, + u32 use_for) { struct cfg80211_registered_device *rdev = wiphy_to_rdev(wiphy); struct cfg80211_internal_bss *bss, *res = NULL; @@ -1534,6 +1568,8 @@ continue; if (!is_valid_ether_addr(bss->pub.bssid)) continue; + if ((bss->pub.use_for & use_for) != use_for) + continue; /* Don't get expired BSS structs */ if (time_after(now, bss->ts + IEEE80211_SCAN_RESULT_EXPIRE) && !atomic_read(&bss->hold)) @@ -1551,7 +1587,7 @@ trace_cfg80211_return_bss(&res->pub); return &res->pub; } -EXPORT_SYMBOL(cfg80211_get_bss); +EXPORT_SYMBOL(__cfg80211_get_bss); static void rb_insert_bss(struct cfg80211_registered_device *rdev, struct cfg80211_internal_bss *bss) @@ -1771,6 +1807,8 @@ ether_addr_copy(known->parent_bssid, new->parent_bssid); known->pub.max_bssid_indicator = new->pub.max_bssid_indicator; known->pub.bssid_index = new->pub.bssid_index; + known->pub.use_for &= new->pub.use_for; + known->pub.cannot_use_reasons = new->pub.cannot_use_reasons; return true; } @@ -2026,6 +2064,9 @@ struct cfg80211_bss *source_bss; u8 max_bssid_indicator; u8 bssid_index; + + u8 use_for; + u64 cannot_use_reasons; }; /* Returned bss is reference counted and must be cleaned up appropriately. */ @@ -2073,6 +2114,8 @@ tmp.ts_boottime = drv_data->boottime_ns; tmp.parent_tsf = drv_data->parent_tsf; ether_addr_copy(tmp.parent_bssid, drv_data->parent_bssid); + tmp.pub.use_for = data->use_for; + tmp.pub.cannot_use_reasons = data->cannot_use_reasons; if (data->bss_source != BSS_SOURCE_DIRECT) { tmp.pub.transmitted_bss = data->source_bss; @@ -2243,6 +2286,8 @@ .beacon_interval = tx_data->beacon_interval, .source_bss = source_bss, .bss_source = BSS_SOURCE_MBSSID, + .use_for = tx_data->use_for, + .cannot_use_reasons = tx_data->cannot_use_reasons, }; const u8 *mbssid_index_ie; const struct element *elem, *sub; @@ -2505,7 +2550,7 @@ return NULL; } -static bool +static u8 cfg80211_tbtt_info_for_mld_ap(const u8 *ie, size_t ielen, u8 mld_id, u8 link_id, const struct ieee80211_neighbor_ap_info **ap_info, const u8 **tbtt_info) @@ -2524,6 +2569,7 @@ u16 params; u8 length, i, count, mld_params_offset; u8 type, lid; + u32 use_for; info = (void *)pos; count = u8_get_bits(info->tbtt_info_hdr, @@ -2533,20 +2579,22 @@ pos += sizeof(*info); if (count * length > end - pos) - return false; + return 0; type = u8_get_bits(info->tbtt_info_hdr, IEEE80211_AP_INFO_TBTT_HDR_TYPE); - /* Only accept full TBTT information. NSTR mobile APs - * use the shortened version, but we ignore them here. - */ if (type == IEEE80211_TBTT_INFO_TYPE_TBTT && length >= offsetofend(struct ieee80211_tbtt_info_ge_11, mld_params)) { mld_params_offset = offsetof(struct ieee80211_tbtt_info_ge_11, mld_params); + use_for = NL80211_BSS_USE_FOR_ALL; + } else if (type == IEEE80211_TBTT_INFO_TYPE_MLD && + length >= sizeof(struct ieee80211_rnr_mld_params)) { + mld_params_offset = 0; + use_for = NL80211_BSS_USE_FOR_MLD_LINK; } else { pos += count * length; continue; @@ -2564,7 +2612,7 @@ *ap_info = info; *tbtt_info = pos; - return true; + return use_for; } pos += length; @@ -2572,7 +2620,7 @@ } } - return false; + return 0; } static void cfg80211_parse_ml_sta_data(struct wiphy *wiphy, @@ -2660,7 +2708,7 @@ const u8 *profile; const u8 *tbtt_info; ssize_t profile_len; - u8 link_id; + u8 link_id, use_for; if (!ieee80211_mle_basic_sta_prof_size_ok((u8 *)mle->sta_prof[i], mle->sta_prof_len[i])) @@ -2702,9 +2750,11 @@ profile_len -= 2; /* Find in RNR to look up channel information */ - if (!cfg80211_tbtt_info_for_mld_ap(tx_data->ie, tx_data->ielen, - mld_id, link_id, - &ap_info, &tbtt_info)) + use_for = cfg80211_tbtt_info_for_mld_ap(tx_data->ie, + tx_data->ielen, + mld_id, link_id, + &ap_info, &tbtt_info); + if (!use_for) continue; /* We could sanity check the BSSID is included */ @@ -2716,6 +2766,14 @@ freq = ieee80211_channel_to_freq_khz(ap_info->channel, band); data.channel = ieee80211_get_channel_khz(wiphy, freq); + if (use_for == NL80211_BSS_USE_FOR_MLD_LINK && + !(wiphy->flags & WIPHY_FLAG_SUPPORTS_NSTR_NONPRIMARY)) { + use_for = 0; + data.cannot_use_reasons = + NL80211_BSS_CANNOT_USE_NSTR_NONPRIMARY; + } + data.use_for = use_for; + /* Generate new elements */ memset(new_ie, 0, IEEE80211_MAX_DATA_LEN); data.ie = new_ie; @@ -2753,6 +2811,10 @@ .beacon_interval = beacon_interval, .ie = ie, .ielen = ielen, + .use_for = data->restrict_use ? + data->use_for : + NL80211_BSS_USE_FOR_ALL, + .cannot_use_reasons = data->cannot_use_reasons, }; struct cfg80211_bss *res; @@ -2885,6 +2947,10 @@ tmp.pub.chains = data->chains; memcpy(tmp.pub.chain_signal, data->chain_signal, IEEE80211_MAX_CHAINS); ether_addr_copy(tmp.parent_bssid, data->parent_bssid); + tmp.pub.use_for = data->restrict_use ? + data->use_for : + NL80211_BSS_USE_FOR_ALL; + tmp.pub.cannot_use_reasons = data->cannot_use_reasons; signal_valid = data->chan == channel; spin_lock_bh(&rdev->bss_lock); @@ -2916,6 +2982,10 @@ .ie = mgmt->u.probe_resp.variable, .ielen = len - offsetof(struct ieee80211_mgmt, u.probe_resp.variable), + .use_for = data->restrict_use ? + data->use_for : + NL80211_BSS_USE_FOR_ALL, + .cannot_use_reasons = data->cannot_use_reasons, }; struct cfg80211_bss *res; diff -Nru backport-iwlwifi-dkms-11289/net/wireless/sme.c backport-iwlwifi-dkms-11510/net/wireless/sme.c --- backport-iwlwifi-dkms-11289/net/wireless/sme.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/wireless/sme.c 2023-10-04 04:18:43.000000000 +0800 @@ -67,7 +67,7 @@ struct cfg80211_scan_request *request; int n_channels, err; - ASSERT_WDEV_LOCK(wdev); + lockdep_assert_wiphy(wdev->wiphy); if (rdev->scan_req || rdev->scan_msg) return -EBUSY; @@ -151,7 +151,7 @@ struct cfg80211_assoc_request req = {}; int err; - ASSERT_WDEV_LOCK(wdev); + lockdep_assert_wiphy(wdev->wiphy); if (!wdev->conn) return 0; @@ -255,16 +255,13 @@ if (!wdev->netdev) continue; - wdev_lock(wdev); - if (!netif_running(wdev->netdev)) { - wdev_unlock(wdev); + if (!netif_running(wdev->netdev)) continue; - } + if (!wdev->conn || - wdev->conn->state == CFG80211_CONN_CONNECTED) { - wdev_unlock(wdev); + wdev->conn->state == CFG80211_CONN_CONNECTED) continue; - } + if (wdev->conn->params.bssid) { memcpy(bssid_buf, wdev->conn->params.bssid, ETH_ALEN); bssid = bssid_buf; @@ -279,7 +276,6 @@ cr.timeout_reason = treason; __cfg80211_connect_result(wdev->netdev, &cr, false); } - wdev_unlock(wdev); } wiphy_unlock(&rdev->wiphy); @@ -300,7 +296,7 @@ struct cfg80211_registered_device *rdev = wiphy_to_rdev(wdev->wiphy); struct cfg80211_bss *bss; - ASSERT_WDEV_LOCK(wdev); + lockdep_assert_wiphy(wdev->wiphy); bss = cfg80211_get_bss(wdev->wiphy, wdev->conn->params.channel, wdev->conn->params.bssid, @@ -317,13 +313,13 @@ return bss; } -static void __cfg80211_sme_scan_done(struct net_device *dev) +void cfg80211_sme_scan_done(struct net_device *dev) { struct wireless_dev *wdev = dev->ieee80211_ptr; struct cfg80211_registered_device *rdev = wiphy_to_rdev(wdev->wiphy); struct cfg80211_bss *bss; - ASSERT_WDEV_LOCK(wdev); + lockdep_assert_wiphy(wdev->wiphy); if (!wdev->conn) return; @@ -339,15 +335,6 @@ schedule_work(&rdev->conn_work); } -void cfg80211_sme_scan_done(struct net_device *dev) -{ - struct wireless_dev *wdev = dev->ieee80211_ptr; - - wdev_lock(wdev); - __cfg80211_sme_scan_done(dev); - wdev_unlock(wdev); -} - void cfg80211_sme_rx_auth(struct wireless_dev *wdev, const u8 *buf, size_t len) { struct wiphy *wiphy = wdev->wiphy; @@ -355,7 +342,7 @@ struct ieee80211_mgmt *mgmt = (struct ieee80211_mgmt *)buf; u16 status_code = le16_to_cpu(mgmt->u.auth.status_code); - ASSERT_WDEV_LOCK(wdev); + lockdep_assert_wiphy(wdev->wiphy); if (!wdev->conn || wdev->conn->state == CFG80211_CONN_CONNECTED) return; @@ -491,6 +478,21 @@ } } +void cfg80211_wdev_release_link_bsses(struct wireless_dev *wdev, u16 link_mask) +{ + unsigned int link; + + for_each_valid_link(wdev, link) { + if (!wdev->links[link].client.current_bss || + !(link_mask & BIT(link))) + continue; + cfg80211_unhold_bss(wdev->links[link].client.current_bss); + cfg80211_put_bss(wdev->wiphy, + &wdev->links[link].client.current_bss->pub); + wdev->links[link].client.current_bss = NULL; + } +} + static int cfg80211_sme_get_conn_ies(struct wireless_dev *wdev, const u8 *ies, size_t ies_len, const u8 **out_ies, size_t *out_ies_len) @@ -687,14 +689,14 @@ * need not issue a disconnect hint and reset any info such * as chan dfs state, etc. */ - list_for_each_entry(rdev, &cfg80211_rdev_list, list) { + for_each_rdev(rdev) { + wiphy_lock(&rdev->wiphy); list_for_each_entry(wdev, &rdev->wiphy.wdev_list, list) { - wdev_lock(wdev); if (wdev->conn || wdev->connected || cfg80211_beaconing_iface_active(wdev)) is_all_idle = false; - wdev_unlock(wdev); } + wiphy_unlock(&rdev->wiphy); } return is_all_idle; @@ -746,7 +748,7 @@ const u8 *connected_addr; bool bss_not_found = false; - ASSERT_WDEV_LOCK(wdev); + lockdep_assert_wiphy(wdev->wiphy); if (WARN_ON(wdev->iftype != NL80211_IFTYPE_STATION && wdev->iftype != NL80211_IFTYPE_P2P_CLIENT)) @@ -1078,7 +1080,7 @@ unsigned int link; const u8 *connected_addr; - ASSERT_WDEV_LOCK(wdev); + lockdep_assert_wiphy(wdev->wiphy); if (WARN_ON(wdev->iftype != NL80211_IFTYPE_STATION && wdev->iftype != NL80211_IFTYPE_P2P_CLIENT)) @@ -1282,7 +1284,7 @@ void __cfg80211_port_authorized(struct wireless_dev *wdev, const u8 *bssid, const u8 *td_bitmap, u8 td_bitmap_len) { - ASSERT_WDEV_LOCK(wdev); + lockdep_assert_wiphy(wdev->wiphy); if (WARN_ON(wdev->iftype != NL80211_IFTYPE_STATION && wdev->iftype != NL80211_IFTYPE_P2P_CLIENT)) @@ -1338,7 +1340,7 @@ union iwreq_data wrqu; #endif - ASSERT_WDEV_LOCK(wdev); + lockdep_assert_wiphy(wdev->wiphy); if (WARN_ON(wdev->iftype != NL80211_IFTYPE_STATION && wdev->iftype != NL80211_IFTYPE_P2P_CLIENT)) @@ -1387,6 +1389,8 @@ #endif schedule_work(&cfg80211_disconnect_work); + + cfg80211_schedule_channels_check(dev); } void cfg80211_disconnected(struct net_device *dev, u16 reason, @@ -1428,7 +1432,7 @@ struct wireless_dev *wdev = dev->ieee80211_ptr; int err; - ASSERT_WDEV_LOCK(wdev); + lockdep_assert_wiphy(wdev->wiphy); /* * If we have an ssid_len, we're trying to connect or are @@ -1534,7 +1538,7 @@ struct wireless_dev *wdev = dev->ieee80211_ptr; int err = 0; - ASSERT_WDEV_LOCK(wdev); + lockdep_assert_wiphy(wdev->wiphy); kfree_sensitive(wdev->connect_keys); wdev->connect_keys = NULL; @@ -1570,19 +1574,18 @@ struct cfg80211_registered_device *rdev = wiphy_to_rdev(wdev->wiphy); wiphy_lock(wdev->wiphy); - wdev_lock(wdev); if (wdev->conn_owner_nlportid) { switch (wdev->iftype) { case NL80211_IFTYPE_ADHOC: - __cfg80211_leave_ibss(rdev, wdev->netdev, false); + cfg80211_leave_ibss(rdev, wdev->netdev, false); break; case NL80211_IFTYPE_AP: case NL80211_IFTYPE_P2P_GO: - __cfg80211_stop_ap(rdev, wdev->netdev, -1, false); + cfg80211_stop_ap(rdev, wdev->netdev, -1, false); break; case NL80211_IFTYPE_MESH_POINT: - __cfg80211_leave_mesh(rdev, wdev->netdev); + cfg80211_leave_mesh(rdev, wdev->netdev); break; case NL80211_IFTYPE_STATION: case NL80211_IFTYPE_P2P_CLIENT: @@ -1607,6 +1610,5 @@ } } - wdev_unlock(wdev); wiphy_unlock(wdev->wiphy); } diff -Nru backport-iwlwifi-dkms-11289/net/wireless/tests/scan.c backport-iwlwifi-dkms-11510/net/wireless/tests/scan.c --- backport-iwlwifi-dkms-11289/net/wireless/tests/scan.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/wireless/tests/scan.c 2023-10-04 04:18:43.000000000 +0800 @@ -234,6 +234,11 @@ size_t len; int i; + KUNIT_ASSERT_NOT_NULL(test, parent); + KUNIT_ASSERT_NOT_NULL(test, child); + KUNIT_ASSERT_NOT_NULL(test, reference); + KUNIT_ASSERT_NOT_NULL(test, out); + for (i = 0; i < ARRAY_SIZE(params->parent_ies); i++) { if (params->parent_ies[i].len != 0) { skb_put_u8(parent, params->parent_ies[i].id); @@ -285,6 +290,9 @@ u8 *out = kunit_kzalloc(test, IEEE80211_MAX_DATA_LEN, GFP_KERNEL); size_t len; + KUNIT_ASSERT_NOT_NULL(test, malformed); + KUNIT_ASSERT_NOT_NULL(test, out); + skb_put_u8(malformed, WLAN_EID_SSID); skb_put_u8(malformed, 3); skb_put(malformed, 3); @@ -496,6 +504,8 @@ .capabilities = cpu_to_le16(0xdead), }; + KUNIT_ASSERT_NOT_NULL(test, input); + w_priv->ops->inform_bss = inform_bss_inc_counter; inform_bss.chan = ieee80211_get_channel_khz(wiphy, MHZ_TO_KHZ(2412)); diff -Nru backport-iwlwifi-dkms-11289/net/wireless/trace.h backport-iwlwifi-dkms-11510/net/wireless/trace.h --- backport-iwlwifi-dkms-11289/net/wireless/trace.h 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/wireless/trace.h 2023-10-04 04:18:43.000000000 +0800 @@ -28,7 +28,7 @@ #define MAXNAME 32 #define WIPHY_ENTRY __array(char, wiphy_name, 32) -#define WIPHY_ASSIGN strlcpy(__entry->wiphy_name, wiphy_name(wiphy), MAXNAME) +#define WIPHY_ASSIGN strscpy(__entry->wiphy_name, wiphy_name(wiphy), MAXNAME) #define WIPHY_PR_FMT "%s" #define WIPHY_PR_ARG __entry->wiphy_name @@ -1339,16 +1339,18 @@ NETDEV_ENTRY MAC_ENTRY(bssid) __field(u16, reason_code) + __field(bool, local_state_change) ), TP_fast_assign( WIPHY_ASSIGN; NETDEV_ASSIGN; MAC_ASSIGN(bssid, req->bssid); __entry->reason_code = req->reason_code; + __entry->local_state_change = req->local_state_change; ), - TP_printk(WIPHY_PR_FMT ", " NETDEV_PR_FMT ", bssid: %pM, reason: %u", + TP_printk(WIPHY_PR_FMT ", " NETDEV_PR_FMT ", bssid: %pM, reason: %u, local_state_change:%d", WIPHY_PR_ARG, NETDEV_PR_ARG, __entry->bssid, - __entry->reason_code) + __entry->reason_code, __entry->local_state_change) ); TRACE_EVENT(rdev_disassoc, @@ -3982,20 +3984,19 @@ __entry->link_id) ); -TRACE_EVENT(cfg80211_cqm_links_state_change_notify, - TP_PROTO(struct net_device *netdev, - u16 removed_links), - TP_ARGS(netdev, removed_links), +TRACE_EVENT(cfg80211_links_removed, + TP_PROTO(struct net_device *netdev, u16 link_mask), + TP_ARGS(netdev, link_mask), TP_STRUCT__entry( NETDEV_ENTRY - __field(u16, removed_links) + __field(u16, link_mask) ), TP_fast_assign( NETDEV_ASSIGN; - __entry->removed_links = removed_links; + __entry->link_mask = link_mask; ), - TP_printk(NETDEV_PR_FMT ", removed_links=0x%x", - NETDEV_PR_ARG, __entry->removed_links) + TP_printk(NETDEV_PR_FMT ", link_mask:%u", NETDEV_PR_ARG, + __entry->link_mask) ); #endif /* !__RDEV_OPS_TRACE || TRACE_HEADER_MULTI_READ */ diff -Nru backport-iwlwifi-dkms-11289/net/wireless/util.c backport-iwlwifi-dkms-11510/net/wireless/util.c --- backport-iwlwifi-dkms-11289/net/wireless/util.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/wireless/util.c 2023-10-04 04:18:43.000000000 +0800 @@ -580,6 +580,8 @@ hdrlen += ETH_ALEN + 2; else if (!pskb_may_pull(skb, hdrlen)) return -EINVAL; + else + payload.eth.h_proto = htons(skb->len - hdrlen); mesh_addr = skb->data + sizeof(payload.eth) + ETH_ALEN; switch (payload.flags & MESH_FLAGS_AE) { @@ -1042,7 +1044,6 @@ list_del(&ev->list); spin_unlock_irqrestore(&wdev->event_lock, flags); - wdev_lock(wdev); switch (ev->type) { case EVENT_CONNECT_RESULT: __cfg80211_connect_result( @@ -1064,7 +1065,7 @@ ev->ij.channel); break; case EVENT_STOPPED: - __cfg80211_leave(wiphy_to_rdev(wdev->wiphy), wdev); + cfg80211_leave(wiphy_to_rdev(wdev->wiphy), wdev); break; case EVENT_PORT_AUTHORIZED: __cfg80211_port_authorized(wdev, ev->pa.bssid, @@ -1072,7 +1073,6 @@ ev->pa.td_bitmap_len); break; } - wdev_unlock(wdev); kfree(ev); @@ -1122,9 +1122,7 @@ return -EBUSY; dev->ieee80211_ptr->use_4addr = false; - wdev_lock(dev->ieee80211_ptr); rdev_set_qos_map(rdev, dev, NULL); - wdev_unlock(dev->ieee80211_ptr); switch (otype) { case NL80211_IFTYPE_AP: @@ -1136,10 +1134,8 @@ break; case NL80211_IFTYPE_STATION: case NL80211_IFTYPE_P2P_CLIENT: - wdev_lock(dev->ieee80211_ptr); cfg80211_disconnect(rdev, dev, WLAN_REASON_DEAUTH_LEAVING, true); - wdev_unlock(dev->ieee80211_ptr); break; case NL80211_IFTYPE_MESH_POINT: /* mesh should be handled? */ @@ -1646,6 +1642,114 @@ return result / 10000; } +static u32 cfg80211_calculate_bitrate_s1g(struct rate_info *rate) +{ + /* For 1, 2, 4, 8 and 16 MHz channels */ + static const u32 base[5][11] = { + { 300000, + 600000, + 900000, + 1200000, + 1800000, + 2400000, + 2700000, + 3000000, + 3600000, + 4000000, + /* MCS 10 supported in 1 MHz only */ + 150000, + }, + { 650000, + 1300000, + 1950000, + 2600000, + 3900000, + 5200000, + 5850000, + 6500000, + 7800000, + /* MCS 9 not valid */ + }, + { 1350000, + 2700000, + 4050000, + 5400000, + 8100000, + 10800000, + 12150000, + 13500000, + 16200000, + 18000000, + }, + { 2925000, + 5850000, + 8775000, + 11700000, + 17550000, + 23400000, + 26325000, + 29250000, + 35100000, + 39000000, + }, + { 8580000, + 11700000, + 17550000, + 23400000, + 35100000, + 46800000, + 52650000, + 58500000, + 70200000, + 78000000, + }, + }; + u32 bitrate; + /* default is 1 MHz index */ + int idx = 0; + + if (rate->mcs >= 11) + goto warn; + + switch (rate->bw) { + case RATE_INFO_BW_16: + idx = 4; + break; + case RATE_INFO_BW_8: + idx = 3; + break; + case RATE_INFO_BW_4: + idx = 2; + break; + case RATE_INFO_BW_2: + idx = 1; + break; + case RATE_INFO_BW_1: + idx = 0; + break; + case RATE_INFO_BW_5: + case RATE_INFO_BW_10: + case RATE_INFO_BW_20: + case RATE_INFO_BW_40: + case RATE_INFO_BW_80: + case RATE_INFO_BW_160: + default: + goto warn; + } + + bitrate = base[idx][rate->mcs]; + bitrate *= rate->nss; + + if (rate->flags & RATE_INFO_FLAGS_SHORT_GI) + bitrate = (bitrate / 9) * 10; + /* do NOT round down here */ + return (bitrate + 50000) / 100000; +warn: + WARN_ONCE(1, "invalid rate bw=%d, mcs=%d, nss=%d\n", + rate->bw, rate->mcs, rate->nss); + return 0; +} + u32 cfg80211_calculate_bitrate(struct rate_info *rate) { if (rate->flags & RATE_INFO_FLAGS_MCS) @@ -1662,6 +1766,8 @@ return cfg80211_calculate_bitrate_he(rate); if (rate->flags & RATE_INFO_FLAGS_EHT_MCS) return cfg80211_calculate_bitrate_eht(rate); + if (rate->flags & RATE_INFO_FLAGS_S1G_MCS) + return cfg80211_calculate_bitrate_s1g(rate); return rate->legacy; } @@ -1899,6 +2005,7 @@ *band = NL80211_BAND_5GHZ; return true; case 131 ... 135: + case 137: *band = NL80211_BAND_6GHZ; return true; case 81: @@ -2564,12 +2671,12 @@ { struct cfg80211_registered_device *rdev = wiphy_to_rdev(wdev->wiphy); - ASSERT_WDEV_LOCK(wdev); + lockdep_assert_wiphy(wdev->wiphy); switch (wdev->iftype) { case NL80211_IFTYPE_AP: case NL80211_IFTYPE_P2P_GO: - __cfg80211_stop_ap(rdev, wdev->netdev, link_id, true); + cfg80211_stop_ap(rdev, wdev->netdev, link_id, true); break; default: /* per-link not relevant */ @@ -2594,12 +2701,10 @@ if (wdev->iftype != NL80211_IFTYPE_AP) return; - wdev_lock(wdev); if (wdev->valid_links) { for_each_valid_link(wdev, link_id) cfg80211_remove_link(wdev, link_id); } - wdev_unlock(wdev); } int cfg80211_remove_virtual_intf(struct cfg80211_registered_device *rdev, diff -Nru backport-iwlwifi-dkms-11289/net/wireless/wext-compat.c backport-iwlwifi-dkms-11510/net/wireless/wext-compat.c --- backport-iwlwifi-dkms-11289/net/wireless/wext-compat.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/wireless/wext-compat.c 2023-10-04 04:18:43.000000000 +0800 @@ -7,7 +7,7 @@ * we directly assign the wireless handlers of wireless interfaces. * * Copyright 2008-2009 Johannes Berg - * Copyright (C) 2019-2022 Intel Corporation + * Copyright (C) 2019-2023 Intel Corporation */ #include @@ -227,7 +227,7 @@ * cfg80211_wext_freq - get wext frequency for non-"auto" * @freq: the wext freq encoding * - * Returns a frequency, or a negative error code, or 0 for auto. + * Returns: a frequency, or a negative error code, or 0 for auto. */ int cfg80211_wext_freq(struct iw_freq *freq) { @@ -415,10 +415,10 @@ } EXPORT_WEXT_HANDLER(cfg80211_wext_giwretry); -static int __cfg80211_set_encryption(struct cfg80211_registered_device *rdev, - struct net_device *dev, bool pairwise, - const u8 *addr, bool remove, bool tx_key, - int idx, struct key_params *params) +static int cfg80211_set_encryption(struct cfg80211_registered_device *rdev, + struct net_device *dev, bool pairwise, + const u8 *addr, bool remove, bool tx_key, + int idx, struct key_params *params) { struct wireless_dev *wdev = dev->ieee80211_ptr; int err, i; @@ -471,7 +471,7 @@ */ if (idx == wdev->wext.default_key && wdev->iftype == NL80211_IFTYPE_ADHOC) { - __cfg80211_leave_ibss(rdev, wdev->netdev, true); + cfg80211_leave_ibss(rdev, wdev->netdev, true); rejoin = true; } @@ -552,7 +552,7 @@ */ if (wdev->iftype == NL80211_IFTYPE_ADHOC && wdev->wext.default_key == -1) { - __cfg80211_leave_ibss(rdev, wdev->netdev, true); + cfg80211_leave_ibss(rdev, wdev->netdev, true); rejoin = true; } err = rdev_set_default_key(rdev, dev, -1, idx, true, @@ -580,21 +580,6 @@ return 0; } -static int cfg80211_set_encryption(struct cfg80211_registered_device *rdev, - struct net_device *dev, bool pairwise, - const u8 *addr, bool remove, bool tx_key, - int idx, struct key_params *params) -{ - int err; - - wdev_lock(dev->ieee80211_ptr); - err = __cfg80211_set_encryption(rdev, dev, pairwise, addr, - remove, tx_key, idx, params); - wdev_unlock(dev->ieee80211_ptr); - - return err; -} - static int cfg80211_wext_siwencode(struct net_device *dev, struct iw_request_info *info, union iwreq_data *wrqu, char *keybuf) @@ -639,7 +624,6 @@ else if (erq->length == 0) { /* No key data - just set the default TX key index */ err = 0; - wdev_lock(wdev); if (wdev->connected || (wdev->iftype == NL80211_IFTYPE_ADHOC && wdev->u.ibss.current_bss)) @@ -647,7 +631,6 @@ true); if (!err) wdev->wext.default_key = idx; - wdev_unlock(wdev); goto out; } @@ -697,12 +680,8 @@ !rdev->ops->set_default_key) return -EOPNOTSUPP; - wdev_lock(wdev); - if (wdev->valid_links) { - wdev_unlock(wdev); + if (wdev->valid_links) return -EOPNOTSUPP; - } - wdev_unlock(wdev); switch (ext->alg) { case IW_ENCODE_ALG_NONE: @@ -1341,13 +1320,11 @@ return -EOPNOTSUPP; err = 0; - wdev_lock(wdev); if (!wdev->valid_links && wdev->links[0].client.current_bss) memcpy(addr, wdev->links[0].client.current_bss->pub.bssid, ETH_ALEN); else err = -EOPNOTSUPP; - wdev_unlock(wdev); if (err) return err; @@ -1387,17 +1364,15 @@ return NULL; /* Grab BSSID of current BSS, if any */ - wdev_lock(wdev); + wiphy_lock(&rdev->wiphy); if (wdev->valid_links || !wdev->links[0].client.current_bss) { - wdev_unlock(wdev); + wiphy_unlock(&rdev->wiphy); return NULL; } memcpy(bssid, wdev->links[0].client.current_bss->pub.bssid, ETH_ALEN); - wdev_unlock(wdev); memset(&sinfo, 0, sizeof(sinfo)); - wiphy_lock(&rdev->wiphy); ret = rdev_get_station(rdev, dev, bssid, &sinfo); wiphy_unlock(&rdev->wiphy); diff -Nru backport-iwlwifi-dkms-11289/net/wireless/wext-core.c backport-iwlwifi-dkms-11510/net/wireless/wext-core.c --- backport-iwlwifi-dkms-11289/net/wireless/wext-core.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/wireless/wext-core.c 2023-10-04 04:18:43.000000000 +0800 @@ -815,6 +815,12 @@ } } + /* Sanity-check to ensure we never end up _allocating_ zero + * bytes of data for extra. + */ + if (extra_size <= 0) + return -EFAULT; + /* kzalloc() ensures NULL-termination for essid_compat. */ extra = kzalloc(extra_size, GFP_KERNEL); if (!extra) diff -Nru backport-iwlwifi-dkms-11289/net/wireless/wext-sme.c backport-iwlwifi-dkms-11510/net/wireless/wext-sme.c --- backport-iwlwifi-dkms-11289/net/wireless/wext-sme.c 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/net/wireless/wext-sme.c 2023-10-04 04:18:43.000000000 +0800 @@ -23,7 +23,7 @@ int err, i; ASSERT_RTNL(); - ASSERT_WDEV_LOCK(wdev); + lockdep_assert_wiphy(wdev->wiphy); if (!netif_running(wdev->netdev)) return 0; @@ -87,15 +87,11 @@ return -EINVAL; } - wdev_lock(wdev); - if (wdev->conn) { bool event = true; - if (wdev->wext.connect.channel == chan) { - err = 0; - goto out; - } + if (wdev->wext.connect.channel == chan) + return 0; /* if SSID set, we'll try right again, avoid event */ if (wdev->wext.connect.ssid_len) @@ -103,14 +99,11 @@ err = cfg80211_disconnect(rdev, dev, WLAN_REASON_DEAUTH_LEAVING, event); if (err) - goto out; + return err; } wdev->wext.connect.channel = chan; - err = cfg80211_mgd_wext_connect(rdev, wdev); - out: - wdev_unlock(wdev); - return err; + return cfg80211_mgd_wext_connect(rdev, wdev); } int cfg80211_mgd_wext_giwfreq(struct net_device *dev, @@ -127,12 +120,10 @@ if (wdev->valid_links) return -EOPNOTSUPP; - wdev_lock(wdev); if (wdev->links[0].client.current_bss) chan = wdev->links[0].client.current_bss->pub.channel; else if (wdev->wext.connect.channel) chan = wdev->wext.connect.channel; - wdev_unlock(wdev); if (chan) { freq->m = chan->center_freq; @@ -164,17 +155,13 @@ if (len > 0 && ssid[len - 1] == '\0') len--; - wdev_lock(wdev); - - err = 0; - if (wdev->conn) { bool event = true; if (wdev->wext.connect.ssid && len && len == wdev->wext.connect.ssid_len && memcmp(wdev->wext.connect.ssid, ssid, len) == 0) - goto out; + return 0; /* if SSID set now, we'll try to connect, avoid event */ if (len) @@ -182,7 +169,7 @@ err = cfg80211_disconnect(rdev, dev, WLAN_REASON_DEAUTH_LEAVING, event); if (err) - goto out; + return err; } wdev->wext.prev_bssid_valid = false; @@ -194,10 +181,7 @@ wdev->wext.connect.crypto.control_port_ethertype = cpu_to_be16(ETH_P_PAE); - err = cfg80211_mgd_wext_connect(rdev, wdev); - out: - wdev_unlock(wdev); - return err; + return cfg80211_mgd_wext_connect(rdev, wdev); } int cfg80211_mgd_wext_giwessid(struct net_device *dev, @@ -216,7 +200,6 @@ data->flags = 0; - wdev_lock(wdev); if (wdev->links[0].client.current_bss) { const struct element *ssid_elem; @@ -238,7 +221,6 @@ data->length = wdev->wext.connect.ssid_len; memcpy(ssid, wdev->wext.connect.ssid, data->length); } - wdev_unlock(wdev); return ret; } @@ -263,23 +245,20 @@ if (is_zero_ether_addr(bssid) || is_broadcast_ether_addr(bssid)) bssid = NULL; - wdev_lock(wdev); - if (wdev->conn) { - err = 0; /* both automatic */ if (!bssid && !wdev->wext.connect.bssid) - goto out; + return 0; /* fixed already - and no change */ if (wdev->wext.connect.bssid && bssid && ether_addr_equal(bssid, wdev->wext.connect.bssid)) - goto out; + return 0; err = cfg80211_disconnect(rdev, dev, WLAN_REASON_DEAUTH_LEAVING, false); if (err) - goto out; + return err; } if (bssid) { @@ -288,10 +267,7 @@ } else wdev->wext.connect.bssid = NULL; - err = cfg80211_mgd_wext_connect(rdev, wdev); - out: - wdev_unlock(wdev); - return err; + return cfg80211_mgd_wext_connect(rdev, wdev); } int cfg80211_mgd_wext_giwap(struct net_device *dev, @@ -306,18 +282,15 @@ ap_addr->sa_family = ARPHRD_ETHER; - wdev_lock(wdev); - if (wdev->valid_links) { - wdev_unlock(wdev); + if (wdev->valid_links) return -EOPNOTSUPP; - } + if (wdev->links[0].client.current_bss) memcpy(ap_addr->sa_data, wdev->links[0].client.current_bss->pub.bssid, ETH_ALEN); else eth_zero_addr(ap_addr->sa_data); - wdev_unlock(wdev); return 0; } @@ -339,7 +312,6 @@ ie = NULL; wiphy_lock(wdev->wiphy); - wdev_lock(wdev); /* no change */ err = 0; @@ -370,7 +342,6 @@ /* userspace better not think we'll reconnect */ err = 0; out: - wdev_unlock(wdev); wiphy_unlock(wdev->wiphy); return err; } @@ -396,7 +367,6 @@ return -EINVAL; wiphy_lock(&rdev->wiphy); - wdev_lock(wdev); switch (mlme->cmd) { case IW_MLME_DEAUTH: case IW_MLME_DISASSOC: @@ -406,7 +376,6 @@ err = -EOPNOTSUPP; break; } - wdev_unlock(wdev); wiphy_unlock(&rdev->wiphy); return err; diff -Nru backport-iwlwifi-dkms-11289/versions backport-iwlwifi-dkms-11510/versions --- backport-iwlwifi-dkms-11289/versions 2023-06-12 15:03:18.000000000 +0800 +++ backport-iwlwifi-dkms-11510/versions 2023-10-04 04:18:43.000000000 +0800 @@ -2,4 +2,4 @@ BACKPORTED_KERNEL_VERSION="(see git)" BACKPORTED_KERNEL_NAME="iwlwifi" BACKPORTS_BUILD_TSTAMP=__DATE__ \" \" __TIME__ -BACKPORTS_GIT_TRACKED="iwlwifi-stack-public:master:11289:646e187e" +BACKPORTS_GIT_TRACKED="iwlwifi-stack-public:master:11510:0106cce5"