All the mail mirrored from lore.kernel.org
 help / color / mirror / Atom feed
* [PATCH 0/6] Add some more cfg80211 and mac80211 kunit tests
@ 2023-12-20 15:19 benjamin
  2023-12-20 15:19 ` [PATCH 1/6] kunit: add parameter generation macro using description from array benjamin
                   ` (6 more replies)
  0 siblings, 7 replies; 19+ messages in thread
From: benjamin @ 2023-12-20 15:19 UTC (permalink / raw
  To: linux-wireless, linux-kselftest, kunit-dev; +Cc: Benjamin Berg

From: Benjamin Berg <benjamin.berg@intel.com>

This patchset adds a couple of helpers for kunit as well as tests for
cfg80211 and mac80211 that use them.

Benjamin Berg (3):
  kunit: add parameter generation macro using description from array
  kunit: add a convenience allocation wrapper for SKBs
  wifi: cfg80211: tests: add some scanning related tests

Johannes Berg (3):
  wifi: mac80211: add kunit tests for public action handling
  wifi: mac80211: kunit: generalize public action test
  wifi: mac80211: kunit: extend MFP tests

 Documentation/dev-tools/kunit/usage.rst |  12 +-
 include/kunit/skbuff.h                  |  56 +++
 include/kunit/test.h                    |  19 +
 net/mac80211/ieee80211_i.h              |  10 +
 net/mac80211/rx.c                       |   4 +-
 net/mac80211/tests/Makefile             |   2 +-
 net/mac80211/tests/mfp.c                | 286 +++++++++++
 net/wireless/core.h                     |  13 +-
 net/wireless/scan.c                     |   9 +-
 net/wireless/tests/Makefile             |   2 +-
 net/wireless/tests/scan.c               | 625 ++++++++++++++++++++++++
 net/wireless/tests/util.c               |  56 +++
 net/wireless/tests/util.h               |  66 +++
 13 files changed, 1145 insertions(+), 15 deletions(-)
 create mode 100644 include/kunit/skbuff.h
 create mode 100644 net/mac80211/tests/mfp.c
 create mode 100644 net/wireless/tests/scan.c
 create mode 100644 net/wireless/tests/util.c
 create mode 100644 net/wireless/tests/util.h

-- 
2.43.0


^ permalink raw reply	[flat|nested] 19+ messages in thread

* [PATCH 1/6] kunit: add parameter generation macro using description from array
  2023-12-20 15:19 [PATCH 0/6] Add some more cfg80211 and mac80211 kunit tests benjamin
@ 2023-12-20 15:19 ` benjamin
  2023-12-22 10:02   ` David Gow
  2023-12-20 15:19 ` [PATCH 2/6] kunit: add a convenience allocation wrapper for SKBs benjamin
                   ` (5 subsequent siblings)
  6 siblings, 1 reply; 19+ messages in thread
From: benjamin @ 2023-12-20 15:19 UTC (permalink / raw
  To: linux-wireless, linux-kselftest, kunit-dev; +Cc: Benjamin Berg

From: Benjamin Berg <benjamin.berg@intel.com>

The existing KUNIT_ARRAY_PARAM macro requires a separate function to
get the description. However, in a lot of cases the description can
just be copied directly from the array. Add a second macro that
avoids having to write a static function just for a single strscpy.

Signed-off-by: Benjamin Berg <benjamin.berg@intel.com>
---
 Documentation/dev-tools/kunit/usage.rst | 12 ++++--------
 include/kunit/test.h                    | 19 +++++++++++++++++++
 2 files changed, 23 insertions(+), 8 deletions(-)

diff --git a/Documentation/dev-tools/kunit/usage.rst b/Documentation/dev-tools/kunit/usage.rst
index c27e1646ecd9..b959e5befcbe 100644
--- a/Documentation/dev-tools/kunit/usage.rst
+++ b/Documentation/dev-tools/kunit/usage.rst
@@ -566,13 +566,9 @@ By reusing the same ``cases`` array from above, we can write the test as a
 		},
 	};
 
-	// Need a helper function to generate a name for each test case.
-	static void case_to_desc(const struct sha1_test_case *t, char *desc)
-	{
-		strcpy(desc, t->str);
-	}
-	// Creates `sha1_gen_params()` to iterate over `cases`.
-	KUNIT_ARRAY_PARAM(sha1, cases, case_to_desc);
+	// Creates `sha1_gen_params()` to iterate over `cases` while using
+	// the struct member `str` for the case description.
+	KUNIT_ARRAY_PARAM_DESC(sha1, cases, str);
 
 	// Looks no different from a normal test.
 	static void sha1_test(struct kunit *test)
@@ -588,7 +584,7 @@ By reusing the same ``cases`` array from above, we can write the test as a
 	}
 
 	// Instead of KUNIT_CASE, we use KUNIT_CASE_PARAM and pass in the
-	// function declared by KUNIT_ARRAY_PARAM.
+	// function declared by KUNIT_ARRAY_PARAM or KUNIT_ARRAY_PARAM_DESC.
 	static struct kunit_case sha1_test_cases[] = {
 		KUNIT_CASE_PARAM(sha1_test, sha1_gen_params),
 		{}
diff --git a/include/kunit/test.h b/include/kunit/test.h
index 20ed9f9275c9..2dfa851e1f88 100644
--- a/include/kunit/test.h
+++ b/include/kunit/test.h
@@ -1514,6 +1514,25 @@ do {									       \
 		return NULL;									\
 	}
 
+/**
+ * KUNIT_ARRAY_PARAM_DESC() - Define test parameter generator from an array.
+ * @name:  prefix for the test parameter generator function.
+ * @array: array of test parameters.
+ * @desc_member: structure member from array element to use as description
+ *
+ * Define function @name_gen_params which uses @array to generate parameters.
+ */
+#define KUNIT_ARRAY_PARAM_DESC(name, array, desc_member)					\
+	static const void *name##_gen_params(const void *prev, char *desc)			\
+	{											\
+		typeof((array)[0]) *__next = prev ? ((typeof(__next)) prev) + 1 : (array);	\
+		if (__next - (array) < ARRAY_SIZE((array))) {					\
+			strscpy(desc, __next->desc_member, KUNIT_PARAM_DESC_SIZE);		\
+			return __next;								\
+		}										\
+		return NULL;									\
+	}
+
 // TODO(dlatypov@google.com): consider eventually migrating users to explicitly
 // include resource.h themselves if they need it.
 #include <kunit/resource.h>
-- 
2.43.0


^ permalink raw reply related	[flat|nested] 19+ messages in thread

* [PATCH 2/6] kunit: add a convenience allocation wrapper for SKBs
  2023-12-20 15:19 [PATCH 0/6] Add some more cfg80211 and mac80211 kunit tests benjamin
  2023-12-20 15:19 ` [PATCH 1/6] kunit: add parameter generation macro using description from array benjamin
@ 2023-12-20 15:19 ` benjamin
  2023-12-22 10:02   ` David Gow
  2023-12-20 15:19 ` [PATCH 3/6] wifi: mac80211: add kunit tests for public action handling benjamin
                   ` (4 subsequent siblings)
  6 siblings, 1 reply; 19+ messages in thread
From: benjamin @ 2023-12-20 15:19 UTC (permalink / raw
  To: linux-wireless, linux-kselftest, kunit-dev; +Cc: Benjamin Berg

From: Benjamin Berg <benjamin.berg@intel.com>

Add a simple convenience helper to allocate and zero fill an SKB for the
use by a kunit test. Also provide a way to free it again in case that
may be desirable.

This simply mirrors the kunit_kmalloc API.

Signed-off-by: Benjamin Berg <benjamin.berg@intel.com>
---
 include/kunit/skbuff.h | 56 ++++++++++++++++++++++++++++++++++++++++++
 1 file changed, 56 insertions(+)
 create mode 100644 include/kunit/skbuff.h

diff --git a/include/kunit/skbuff.h b/include/kunit/skbuff.h
new file mode 100644
index 000000000000..2144d01e556f
--- /dev/null
+++ b/include/kunit/skbuff.h
@@ -0,0 +1,56 @@
+/* SPDX-License-Identifier: GPL-2.0 */
+/*
+ * Base unit test (KUnit) API.
+ *
+ * Copyright (C) 2023 Intel Corporation
+ */
+
+#ifndef _KUNIT_SKBUFF_H
+#define _KUNIT_SKBUFF_H
+
+#include <kunit/resource.h>
+#include <linux/skbuff.h>
+
+static void kunit_action_kfree_skb(void *p)
+{
+	kfree_skb((struct sk_buff *)p);
+}
+
+/**
+ * kunit_zalloc_skb() - Allocate and initialize a resource managed skb.
+ * @test: The test case to which the skb belongs
+ * @len: size to allocate
+ *
+ * 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.
+ *
+ * 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_KERNEL);
+
+	if (!res || skb_pad(res, len))
+		return NULL;
+
+	if (kunit_add_action_or_reset(test, kunit_action_kfree_skb, res))
+		return NULL;
+
+	return res;
+}
+
+/**
+ * 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_kfree_skb, (void *)skb);
+}
+
+#endif /* _KUNIT_SKBUFF_H */
-- 
2.43.0


^ permalink raw reply related	[flat|nested] 19+ messages in thread

* [PATCH 3/6] wifi: mac80211: add kunit tests for public action handling
  2023-12-20 15:19 [PATCH 0/6] Add some more cfg80211 and mac80211 kunit tests benjamin
  2023-12-20 15:19 ` [PATCH 1/6] kunit: add parameter generation macro using description from array benjamin
  2023-12-20 15:19 ` [PATCH 2/6] kunit: add a convenience allocation wrapper for SKBs benjamin
@ 2023-12-20 15:19 ` benjamin
  2023-12-20 15:19 ` [PATCH 4/6] wifi: mac80211: kunit: generalize public action test benjamin
                   ` (3 subsequent siblings)
  6 siblings, 0 replies; 19+ messages in thread
From: benjamin @ 2023-12-20 15:19 UTC (permalink / raw
  To: linux-wireless, linux-kselftest, kunit-dev; +Cc: Johannes Berg, Benjamin Berg

From: Johannes Berg <johannes.berg@intel.com>

Check the logic in ieee80211_drop_unencrypted_mgmt()
according to a list of test cases derived from the
spec.

Signed-off-by: Johannes Berg <johannes.berg@intel.com>
Reviewed-by: Benjamin Berg <benjamin.berg@intel.com>
---
 net/mac80211/ieee80211_i.h  |  10 ++
 net/mac80211/rx.c           |   4 +-
 net/mac80211/tests/Makefile |   2 +-
 net/mac80211/tests/mfp.c    | 184 ++++++++++++++++++++++++++++++++++++
 4 files changed, 198 insertions(+), 2 deletions(-)
 create mode 100644 net/mac80211/tests/mfp.c

diff --git a/net/mac80211/ieee80211_i.h b/net/mac80211/ieee80211_i.h
index 29312f6638a1..71fafcd6a36e 100644
--- a/net/mac80211/ieee80211_i.h
+++ b/net/mac80211/ieee80211_i.h
@@ -2610,4 +2610,14 @@ void ieee80211_check_wbrf_support(struct ieee80211_local *local);
 void ieee80211_add_wbrf(struct ieee80211_local *local, struct cfg80211_chan_def *chandef);
 void ieee80211_remove_wbrf(struct ieee80211_local *local, struct cfg80211_chan_def *chandef);
 
+#if IS_ENABLED(CONFIG_MAC80211_KUNIT_TEST)
+#define EXPORT_SYMBOL_IF_MAC80211_KUNIT(sym) EXPORT_SYMBOL_IF_KUNIT(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 --git a/net/mac80211/rx.c b/net/mac80211/rx.c
index bbfdcb0ade72..d294787feed0 100644
--- a/net/mac80211/rx.c
+++ b/net/mac80211/rx.c
@@ -19,6 +19,7 @@
 #include <linux/export.h>
 #include <linux/kcov.h>
 #include <linux/bitops.h>
+#include <kunit/visibility.h>
 #include <net/mac80211.h>
 #include <net/ieee80211_radiotap.h>
 #include <asm/unaligned.h>
@@ -2405,7 +2406,7 @@ static int ieee80211_drop_unencrypted(struct ieee80211_rx_data *rx, __le16 fc)
 	return 0;
 }
 
-static ieee80211_rx_result
+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);
@@ -2484,6 +2485,7 @@ ieee80211_drop_unencrypted_mgmt(struct ieee80211_rx_data *rx)
 
 	return RX_CONTINUE;
 }
+EXPORT_SYMBOL_IF_MAC80211_KUNIT(ieee80211_drop_unencrypted_mgmt);
 
 static ieee80211_rx_result
 __ieee80211_data_to_8023(struct ieee80211_rx_data *rx, bool *port_control)
diff --git a/net/mac80211/tests/Makefile b/net/mac80211/tests/Makefile
index 4814584f8a14..4fdaf3feaca3 100644
--- a/net/mac80211/tests/Makefile
+++ b/net/mac80211/tests/Makefile
@@ -1,3 +1,3 @@
-mac80211-tests-y += module.o elems.o
+mac80211-tests-y += module.o elems.o mfp.o
 
 obj-$(CONFIG_MAC80211_KUNIT_TEST) += mac80211-tests.o
diff --git a/net/mac80211/tests/mfp.c b/net/mac80211/tests/mfp.c
new file mode 100644
index 000000000000..629a5801c08f
--- /dev/null
+++ b/net/mac80211/tests/mfp.c
@@ -0,0 +1,184 @@
+// SPDX-License-Identifier: GPL-2.0-only
+/*
+ * KUnit tests for management frame acceptance
+ *
+ * Copyright (C) 2023 Intel Corporation
+ */
+#include <kunit/test.h>
+#include <kunit/skbuff.h>
+#include "../ieee80211_i.h"
+#include "../sta_info.h"
+
+MODULE_IMPORT_NS(EXPORTED_FOR_KUNIT_TESTING);
+
+static const struct mfp_test_case {
+	const char *desc;
+	bool sta, mfp, decrypted, unicast, protected_dual;
+	ieee80211_rx_result result;
+} accept_public_action_cases[] = {
+	/* regular public action */
+	{
+		.desc = "public action: accept unicast from unknown peer",
+		.unicast = true,
+		.result = RX_CONTINUE,
+	},
+	{
+		.desc = "public action: accept multicast from unknown peer",
+		.unicast = false,
+		.result = RX_CONTINUE,
+	},
+	{
+		.desc = "public action: accept unicast without MFP",
+		.unicast = true,
+		.sta = true,
+		.result = RX_CONTINUE,
+	},
+	{
+		.desc = "public action: accept multicast without MFP",
+		.unicast = false,
+		.sta = true,
+		.result = RX_CONTINUE,
+	},
+	{
+		.desc = "public action: drop unicast with MFP",
+		.unicast = true,
+		.sta = true,
+		.mfp = true,
+		.result = RX_DROP_U_UNPROT_UNICAST_PUB_ACTION,
+	},
+	{
+		.desc = "public action: accept multicast with MFP",
+		.unicast = false,
+		.sta = true,
+		.mfp = true,
+		.result = RX_CONTINUE,
+	},
+	/* protected dual of public action */
+	{
+		.desc = "protected dual: drop unicast from unknown peer",
+		.protected_dual = true,
+		.unicast = true,
+		.result = RX_DROP_U_UNPROT_DUAL,
+	},
+	{
+		.desc = "protected dual: drop multicast from unknown peer",
+		.protected_dual = true,
+		.unicast = false,
+		.result = RX_DROP_U_UNPROT_DUAL,
+	},
+	{
+		.desc = "protected dual: drop unicast without MFP",
+		.protected_dual = true,
+		.unicast = true,
+		.sta = true,
+		.result = RX_DROP_U_UNPROT_DUAL,
+	},
+	{
+		.desc = "protected dual: drop multicast without MFP",
+		.protected_dual = true,
+		.unicast = false,
+		.sta = true,
+		.result = RX_DROP_U_UNPROT_DUAL,
+	},
+	{
+		.desc = "protected dual: drop undecrypted unicast with MFP",
+		.protected_dual = true,
+		.unicast = true,
+		.sta = true,
+		.mfp = true,
+		.result = RX_DROP_U_UNPROT_DUAL,
+	},
+	{
+		.desc = "protected dual: drop undecrypted multicast with MFP",
+		.protected_dual = true,
+		.unicast = false,
+		.sta = true,
+		.mfp = true,
+		.result = RX_DROP_U_UNPROT_DUAL,
+	},
+	{
+		.desc = "protected dual: accept unicast with MFP",
+		.protected_dual = true,
+		.decrypted = true,
+		.unicast = true,
+		.sta = true,
+		.mfp = true,
+		.result = RX_CONTINUE,
+	},
+	{
+		.desc = "protected dual: accept multicast with MFP",
+		.protected_dual = true,
+		.decrypted = true,
+		.unicast = false,
+		.sta = true,
+		.mfp = true,
+		.result = RX_CONTINUE,
+	},
+};
+
+KUNIT_ARRAY_PARAM_DESC(accept_public_action,
+		       accept_public_action_cases,
+		       desc);
+
+static void accept_public_action(struct kunit *test)
+{
+	static struct sta_info sta = {};
+	const struct mfp_test_case *params = test->param_value;
+	struct ieee80211_rx_data rx = {
+		.sta = params->sta ? &sta : NULL,
+	};
+	struct ieee80211_rx_status *status;
+	struct ieee80211_hdr_3addr hdr = {
+		.frame_control = cpu_to_le16(IEEE80211_FTYPE_MGMT |
+					     IEEE80211_STYPE_ACTION),
+		.addr1 = { 0xff, 0xff, 0xff, 0xff, 0xff, 0xff },
+		.addr2 = { 0x12, 0x22, 0x33, 0x44, 0x55, 0x66 },
+		/* A3/BSSID doesn't matter here */
+	};
+
+	if (!params->sta) {
+		KUNIT_ASSERT_FALSE(test, params->mfp);
+		KUNIT_ASSERT_FALSE(test, params->decrypted);
+	}
+
+	if (params->mfp)
+		set_sta_flag(&sta, WLAN_STA_MFP);
+
+	rx.skb = kunit_zalloc_skb(test, 128, GFP_KERNEL);
+	KUNIT_ASSERT_NOT_NULL(test, rx.skb);
+	status = IEEE80211_SKB_RXCB(rx.skb);
+
+	if (params->decrypted) {
+		status->flag |= RX_FLAG_DECRYPTED;
+		if (params->unicast)
+			hdr.frame_control |=
+				cpu_to_le16(IEEE80211_FCTL_PROTECTED);
+	}
+
+	if (params->unicast)
+		hdr.addr1[0] = 0x02;
+
+	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);
+	skb_put_u8(rx.skb, WLAN_PUB_ACTION_DSE_ENABLEMENT);
+
+	KUNIT_EXPECT_EQ(test,
+			ieee80211_drop_unencrypted_mgmt(&rx),
+			params->result);
+}
+
+static struct kunit_case mfp_test_cases[] = {
+	KUNIT_CASE_PARAM(accept_public_action, accept_public_action_gen_params),
+	{}
+};
+
+static struct kunit_suite mfp = {
+	.name = "mac80211-mfp",
+	.test_cases = mfp_test_cases,
+};
+
+kunit_test_suite(mfp);
-- 
2.43.0


^ permalink raw reply related	[flat|nested] 19+ messages in thread

* [PATCH 4/6] wifi: mac80211: kunit: generalize public action test
  2023-12-20 15:19 [PATCH 0/6] Add some more cfg80211 and mac80211 kunit tests benjamin
                   ` (2 preceding siblings ...)
  2023-12-20 15:19 ` [PATCH 3/6] wifi: mac80211: add kunit tests for public action handling benjamin
@ 2023-12-20 15:19 ` benjamin
  2023-12-20 15:19 ` [PATCH 5/6] wifi: mac80211: kunit: extend MFP tests benjamin
                   ` (2 subsequent siblings)
  6 siblings, 0 replies; 19+ messages in thread
From: benjamin @ 2023-12-20 15:19 UTC (permalink / raw
  To: linux-wireless, linux-kselftest, kunit-dev
  Cc: Johannes Berg, Gregory Greenman

From: Johannes Berg <johannes.berg@intel.com>

Generalize the test to be able to handle arbitrary
action categories and non-action frames, for further
test expansion.

Signed-off-by: Johannes Berg <johannes.berg@intel.com>
Reviewed-by: Gregory Greenman <gregory.greenman@intel.com>
---
 net/mac80211/tests/mfp.c | 78 +++++++++++++++++++++++++++++-----------
 1 file changed, 57 insertions(+), 21 deletions(-)

diff --git a/net/mac80211/tests/mfp.c b/net/mac80211/tests/mfp.c
index 629a5801c08f..6ec31386c0df 100644
--- a/net/mac80211/tests/mfp.c
+++ b/net/mac80211/tests/mfp.c
@@ -13,34 +13,52 @@ MODULE_IMPORT_NS(EXPORTED_FOR_KUNIT_TESTING);
 
 static const struct mfp_test_case {
 	const char *desc;
-	bool sta, mfp, decrypted, unicast, protected_dual;
+	bool sta, mfp, decrypted, unicast;
+	u8 category;
+	u8 stype;
+	u8 action;
 	ieee80211_rx_result result;
-} accept_public_action_cases[] = {
+} accept_mfp_cases[] = {
 	/* regular public action */
 	{
 		.desc = "public action: accept unicast from unknown peer",
+		.stype = IEEE80211_STYPE_ACTION,
+		.category = WLAN_CATEGORY_PUBLIC,
+		.action = WLAN_PUB_ACTION_DSE_ENABLEMENT,
 		.unicast = true,
 		.result = RX_CONTINUE,
 	},
 	{
 		.desc = "public action: accept multicast from unknown peer",
+		.stype = IEEE80211_STYPE_ACTION,
+		.category = WLAN_CATEGORY_PUBLIC,
+		.action = WLAN_PUB_ACTION_DSE_ENABLEMENT,
 		.unicast = false,
 		.result = RX_CONTINUE,
 	},
 	{
 		.desc = "public action: accept unicast without MFP",
+		.stype = IEEE80211_STYPE_ACTION,
+		.category = WLAN_CATEGORY_PUBLIC,
+		.action = WLAN_PUB_ACTION_DSE_ENABLEMENT,
 		.unicast = true,
 		.sta = true,
 		.result = RX_CONTINUE,
 	},
 	{
 		.desc = "public action: accept multicast without MFP",
+		.stype = IEEE80211_STYPE_ACTION,
+		.category = WLAN_CATEGORY_PUBLIC,
+		.action = WLAN_PUB_ACTION_DSE_ENABLEMENT,
 		.unicast = false,
 		.sta = true,
 		.result = RX_CONTINUE,
 	},
 	{
 		.desc = "public action: drop unicast with MFP",
+		.stype = IEEE80211_STYPE_ACTION,
+		.category = WLAN_CATEGORY_PUBLIC,
+		.action = WLAN_PUB_ACTION_DSE_ENABLEMENT,
 		.unicast = true,
 		.sta = true,
 		.mfp = true,
@@ -48,6 +66,9 @@ static const struct mfp_test_case {
 	},
 	{
 		.desc = "public action: accept multicast with MFP",
+		.stype = IEEE80211_STYPE_ACTION,
+		.category = WLAN_CATEGORY_PUBLIC,
+		.action = WLAN_PUB_ACTION_DSE_ENABLEMENT,
 		.unicast = false,
 		.sta = true,
 		.mfp = true,
@@ -56,33 +77,43 @@ static const struct mfp_test_case {
 	/* 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,
+		.action = WLAN_PUB_ACTION_DSE_ENABLEMENT,
 		.unicast = true,
 		.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,
+		.action = WLAN_PUB_ACTION_DSE_ENABLEMENT,
 		.unicast = false,
 		.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,
+		.action = WLAN_PUB_ACTION_DSE_ENABLEMENT,
 		.unicast = true,
 		.sta = true,
 		.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,
+		.action = WLAN_PUB_ACTION_DSE_ENABLEMENT,
 		.unicast = false,
 		.sta = true,
 		.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,
+		.action = WLAN_PUB_ACTION_DSE_ENABLEMENT,
 		.unicast = true,
 		.sta = true,
 		.mfp = true,
@@ -90,7 +121,9 @@ static const struct mfp_test_case {
 	},
 	{
 		.desc = "protected dual: drop undecrypted multicast with MFP",
-		.protected_dual = true,
+		.stype = IEEE80211_STYPE_ACTION,
+		.category = WLAN_CATEGORY_PROTECTED_DUAL_OF_ACTION,
+		.action = WLAN_PUB_ACTION_DSE_ENABLEMENT,
 		.unicast = false,
 		.sta = true,
 		.mfp = true,
@@ -98,7 +131,9 @@ static const struct mfp_test_case {
 	},
 	{
 		.desc = "protected dual: accept unicast with MFP",
-		.protected_dual = true,
+		.stype = IEEE80211_STYPE_ACTION,
+		.category = WLAN_CATEGORY_PROTECTED_DUAL_OF_ACTION,
+		.action = WLAN_PUB_ACTION_DSE_ENABLEMENT,
 		.decrypted = true,
 		.unicast = true,
 		.sta = true,
@@ -107,7 +142,9 @@ static const struct mfp_test_case {
 	},
 	{
 		.desc = "protected dual: accept multicast with MFP",
-		.protected_dual = true,
+		.stype = IEEE80211_STYPE_ACTION,
+		.category = WLAN_CATEGORY_PROTECTED_DUAL_OF_ACTION,
+		.action = WLAN_PUB_ACTION_DSE_ENABLEMENT,
 		.decrypted = true,
 		.unicast = false,
 		.sta = true,
@@ -116,11 +153,9 @@ static const struct mfp_test_case {
 	},
 };
 
-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 = {};
 	const struct mfp_test_case *params = test->param_value;
@@ -130,7 +165,7 @@ static void accept_public_action(struct kunit *test)
 	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 */
@@ -160,11 +195,12 @@ static void accept_public_action(struct kunit *test)
 
 	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);
-	skb_put_u8(rx.skb, WLAN_PUB_ACTION_DSE_ENABLEMENT);
+	switch (params->stype) {
+	case IEEE80211_STYPE_ACTION:
+		skb_put_u8(rx.skb, params->category);
+		skb_put_u8(rx.skb, params->action);
+		break;
+	}
 
 	KUNIT_EXPECT_EQ(test,
 			ieee80211_drop_unencrypted_mgmt(&rx),
@@ -172,7 +208,7 @@ static void accept_public_action(struct kunit *test)
 }
 
 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),
 	{}
 };
 
-- 
2.43.0


^ permalink raw reply related	[flat|nested] 19+ messages in thread

* [PATCH 5/6] wifi: mac80211: kunit: extend MFP tests
  2023-12-20 15:19 [PATCH 0/6] Add some more cfg80211 and mac80211 kunit tests benjamin
                   ` (3 preceding siblings ...)
  2023-12-20 15:19 ` [PATCH 4/6] wifi: mac80211: kunit: generalize public action test benjamin
@ 2023-12-20 15:19 ` benjamin
  2023-12-20 15:19 ` [PATCH 6/6] wifi: cfg80211: tests: add some scanning related tests benjamin
  2023-12-21 19:39 ` [PATCH 0/6] Add some more cfg80211 and mac80211 kunit tests Johannes Berg
  6 siblings, 0 replies; 19+ messages in thread
From: benjamin @ 2023-12-20 15:19 UTC (permalink / raw
  To: linux-wireless, linux-kselftest, kunit-dev
  Cc: Johannes Berg, Gregory Greenman

From: Johannes Berg <johannes.berg@intel.com>

Extend the MFP tests to handle the case of deauth/disassoc
and robust action frames (that are not protected dual of
public action frames).

Signed-off-by: Johannes Berg <johannes.berg@intel.com>
Reviewed-by: Gregory Greenman <gregory.greenman@intel.com>
---
 net/mac80211/tests/mfp.c | 74 +++++++++++++++++++++++++++++++++++++---
 1 file changed, 70 insertions(+), 4 deletions(-)

diff --git a/net/mac80211/tests/mfp.c b/net/mac80211/tests/mfp.c
index 6ec31386c0df..a8dc1601da60 100644
--- a/net/mac80211/tests/mfp.c
+++ b/net/mac80211/tests/mfp.c
@@ -13,7 +13,7 @@ MODULE_IMPORT_NS(EXPORTED_FOR_KUNIT_TESTING);
 
 static const struct mfp_test_case {
 	const char *desc;
-	bool sta, mfp, decrypted, unicast;
+	bool sta, mfp, decrypted, unicast, assoc;
 	u8 category;
 	u8 stype;
 	u8 action;
@@ -151,13 +151,67 @@ static const struct mfp_test_case {
 		.mfp = true,
 		.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_mfp, accept_mfp_cases, desc);
 
 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,
@@ -171,6 +225,8 @@ static void accept_mfp(struct kunit *test)
 		/* 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);
@@ -179,6 +235,9 @@ static void accept_mfp(struct kunit *test)
 	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);
 	KUNIT_ASSERT_NOT_NULL(test, rx.skb);
 	status = IEEE80211_SKB_RXCB(rx.skb);
@@ -200,11 +259,18 @@ static void accept_mfp(struct kunit *test)
 		skb_put_u8(rx.skb, params->category);
 		skb_put_u8(rx.skb, params->action);
 		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[] = {
-- 
2.43.0


^ permalink raw reply related	[flat|nested] 19+ messages in thread

* [PATCH 6/6] wifi: cfg80211: tests: add some scanning related tests
  2023-12-20 15:19 [PATCH 0/6] Add some more cfg80211 and mac80211 kunit tests benjamin
                   ` (4 preceding siblings ...)
  2023-12-20 15:19 ` [PATCH 5/6] wifi: mac80211: kunit: extend MFP tests benjamin
@ 2023-12-20 15:19 ` benjamin
  2023-12-21 19:39 ` [PATCH 0/6] Add some more cfg80211 and mac80211 kunit tests Johannes Berg
  6 siblings, 0 replies; 19+ messages in thread
From: benjamin @ 2023-12-20 15:19 UTC (permalink / raw
  To: linux-wireless, linux-kselftest, kunit-dev; +Cc: Benjamin Berg, Johannes Berg

From: Benjamin Berg <benjamin.berg@intel.com>

This adds some scanning related tests, mainly exercising the ML element
parsing and inheritance.

Signed-off-by: Benjamin Berg <benjamin.berg@intel.com>
Reviewed-by: Johannes Berg <johannes.berg@intel.com>
---
 net/wireless/core.h         |  13 +-
 net/wireless/scan.c         |   9 +-
 net/wireless/tests/Makefile |   2 +-
 net/wireless/tests/scan.c   | 625 ++++++++++++++++++++++++++++++++++++
 net/wireless/tests/util.c   |  56 ++++
 net/wireless/tests/util.h   |  66 ++++
 6 files changed, 766 insertions(+), 5 deletions(-)
 create mode 100644 net/wireless/tests/scan.c
 create mode 100644 net/wireless/tests/util.c
 create mode 100644 net/wireless/tests/util.h

diff --git a/net/wireless/core.h b/net/wireless/core.h
index 1963958263d2..13657a85cf61 100644
--- a/net/wireless/core.h
+++ b/net/wireless/core.h
@@ -3,7 +3,7 @@
  * Wireless configuration interface internals.
  *
  * Copyright 2006-2010	Johannes Berg <johannes@sipsolutions.net>
- * Copyright (C) 2018-2022 Intel Corporation
+ * Copyright (C) 2018-2023 Intel Corporation
  */
 #ifndef __NET_WIRELESS_CORE_H
 #define __NET_WIRELESS_CORE_H
@@ -549,4 +549,15 @@ 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(CONFIG_CFG80211_KUNIT_TEST)
+#define EXPORT_SYMBOL_IF_CFG80211_KUNIT(sym) EXPORT_SYMBOL_IF_KUNIT(sym)
+#define VISIBLE_IF_CFG80211_KUNIT
+size_t cfg80211_gen_new_ie(const u8 *ie, size_t ielen,
+			   const u8 *subie, size_t subie_len,
+			   u8 *new_ie, size_t new_ie_len);
+#else
+#define EXPORT_SYMBOL_IF_CFG80211_KUNIT(sym)
+#define VISIBLE_IF_CFG80211_KUNIT static
+#endif /* IS_ENABLED(CONFIG_CFG80211_KUNIT_TEST) */
+
 #endif /* __NET_WIRELESS_CORE_H */
diff --git a/net/wireless/scan.c b/net/wireless/scan.c
index 3d260c99c348..f6c0421f4d77 100644
--- a/net/wireless/scan.c
+++ b/net/wireless/scan.c
@@ -20,6 +20,7 @@
 #include <net/cfg80211.h>
 #include <net/cfg80211-wext.h>
 #include <net/iw_handler.h>
+#include <kunit/visibility.h>
 #include "core.h"
 #include "nl80211.h"
 #include "wext-compat.h"
@@ -303,9 +304,10 @@ static size_t cfg80211_copy_elem_with_frags(const struct element *elem,
 	return *pos - buf;
 }
 
-static size_t cfg80211_gen_new_ie(const u8 *ie, size_t ielen,
-				  const u8 *subie, size_t subie_len,
-				  u8 *new_ie, size_t new_ie_len)
+VISIBLE_IF_CFG80211_KUNIT size_t
+cfg80211_gen_new_ie(const u8 *ie, size_t ielen,
+		    const u8 *subie, size_t subie_len,
+		    u8 *new_ie, size_t new_ie_len)
 {
 	const struct element *non_inherit_elem, *parent, *sub;
 	u8 *pos = new_ie;
@@ -413,6 +415,7 @@ static size_t cfg80211_gen_new_ie(const u8 *ie, size_t ielen,
 
 	return pos - new_ie;
 }
+EXPORT_SYMBOL_IF_CFG80211_KUNIT(cfg80211_gen_new_ie);
 
 static bool is_bss(struct cfg80211_bss *a, const u8 *bssid,
 		   const u8 *ssid, size_t ssid_len)
diff --git a/net/wireless/tests/Makefile b/net/wireless/tests/Makefile
index fa8e297bbc5e..1f6622fcb758 100644
--- a/net/wireless/tests/Makefile
+++ b/net/wireless/tests/Makefile
@@ -1,3 +1,3 @@
-cfg80211-tests-y += module.o fragmentation.o
+cfg80211-tests-y += module.o fragmentation.o scan.o util.o
 
 obj-$(CONFIG_CFG80211_KUNIT_TEST) += cfg80211-tests.o
diff --git a/net/wireless/tests/scan.c b/net/wireless/tests/scan.c
new file mode 100644
index 000000000000..77854161cd22
--- /dev/null
+++ b/net/wireless/tests/scan.c
@@ -0,0 +1,625 @@
+// SPDX-License-Identifier: GPL-2.0-only
+/*
+ * KUnit tests for inform_bss functions
+ *
+ * Copyright (C) 2023 Intel Corporation
+ */
+#include <linux/ieee80211.h>
+#include <net/cfg80211.h>
+#include <kunit/test.h>
+#include <kunit/skbuff.h>
+#include "../core.h"
+#include "util.h"
+
+/* mac80211 helpers for element building */
+#include "../../mac80211/ieee80211_i.h"
+
+MODULE_IMPORT_NS(EXPORTED_FOR_KUNIT_TESTING);
+
+struct test_elem {
+	u8 id;
+	u8 len;
+	union {
+		u8 data[255];
+		struct {
+			u8 eid;
+			u8 edata[254];
+		};
+	};
+};
+
+static struct gen_new_ie_case {
+	const char *desc;
+	struct test_elem parent_ies[16];
+	struct test_elem child_ies[16];
+	struct test_elem result_ies[16];
+} gen_new_ie_cases[] = {
+	{
+		.desc = "ML not inherited",
+		.parent_ies = {
+			{ .id = WLAN_EID_EXTENSION, .len = 255,
+			  .eid = WLAN_EID_EXT_EHT_MULTI_LINK },
+		},
+		.child_ies = {
+			{ .id = WLAN_EID_SSID, .len = 2 },
+		},
+		.result_ies = {
+			{ .id = WLAN_EID_SSID, .len = 2 },
+		},
+	},
+	{
+		.desc = "fragments are ignored if previous len not 255",
+		.parent_ies = {
+			{ .id = WLAN_EID_REDUCED_NEIGHBOR_REPORT, .len = 254, },
+			{ .id = WLAN_EID_FRAGMENT, .len = 125, },
+		},
+		.child_ies = {
+			{ .id = WLAN_EID_SSID, .len = 2 },
+			{ .id = WLAN_EID_FRAGMENT, .len = 125, },
+		},
+		.result_ies = {
+			{ .id = WLAN_EID_REDUCED_NEIGHBOR_REPORT, .len = 254, },
+			{ .id = WLAN_EID_SSID, .len = 2 },
+		},
+	},
+	{
+		.desc = "fragments inherited",
+		.parent_ies = {
+			{ .id = WLAN_EID_REDUCED_NEIGHBOR_REPORT, .len = 255, },
+			{ .id = WLAN_EID_FRAGMENT, .len = 125, },
+		},
+		.child_ies = {
+			{ .id = WLAN_EID_SSID, .len = 2 },
+		},
+		.result_ies = {
+			{ .id = WLAN_EID_REDUCED_NEIGHBOR_REPORT, .len = 255, },
+			{ .id = WLAN_EID_FRAGMENT, .len = 125, },
+			{ .id = WLAN_EID_SSID, .len = 2 },
+		},
+	},
+	{
+		.desc = "fragments copied",
+		.parent_ies = {
+			{ .id = WLAN_EID_REDUCED_NEIGHBOR_REPORT, .len = 255, },
+			{ .id = WLAN_EID_FRAGMENT, .len = 125, },
+		},
+		.child_ies = {
+			{ .id = WLAN_EID_SSID, .len = 2 },
+		},
+		.result_ies = {
+			{ .id = WLAN_EID_REDUCED_NEIGHBOR_REPORT, .len = 255, },
+			{ .id = WLAN_EID_FRAGMENT, .len = 125, },
+			{ .id = WLAN_EID_SSID, .len = 2 },
+		},
+	},
+	{
+		.desc = "multiple elements inherit",
+		.parent_ies = {
+			{ .id = WLAN_EID_REDUCED_NEIGHBOR_REPORT, .len = 255, },
+			{ .id = WLAN_EID_FRAGMENT, .len = 125, },
+			{ .id = WLAN_EID_REDUCED_NEIGHBOR_REPORT, .len = 123, },
+		},
+		.child_ies = {
+			{ .id = WLAN_EID_SSID, .len = 2 },
+		},
+		.result_ies = {
+			{ .id = WLAN_EID_REDUCED_NEIGHBOR_REPORT, .len = 255, },
+			{ .id = WLAN_EID_FRAGMENT, .len = 125, },
+			{ .id = WLAN_EID_REDUCED_NEIGHBOR_REPORT, .len = 123, },
+			{ .id = WLAN_EID_SSID, .len = 2 },
+		},
+	},
+	{
+		.desc = "one child element overrides",
+		.parent_ies = {
+			{ .id = WLAN_EID_REDUCED_NEIGHBOR_REPORT, .len = 255, },
+			{ .id = WLAN_EID_FRAGMENT, .len = 125, },
+			{ .id = WLAN_EID_REDUCED_NEIGHBOR_REPORT, .len = 123, },
+		},
+		.child_ies = {
+			{ .id = WLAN_EID_REDUCED_NEIGHBOR_REPORT, .len = 127, },
+			{ .id = WLAN_EID_SSID, .len = 2 },
+		},
+		.result_ies = {
+			{ .id = WLAN_EID_REDUCED_NEIGHBOR_REPORT, .len = 127, },
+			{ .id = WLAN_EID_SSID, .len = 2 },
+		},
+	},
+	{
+		.desc = "empty elements from parent",
+		.parent_ies = {
+			{ .id = 0x1, .len = 0, },
+			{ .id = WLAN_EID_EXTENSION, .len = 1, .eid = 0x10 },
+		},
+		.child_ies = {
+		},
+		.result_ies = {
+			{ .id = 0x1, .len = 0, },
+			{ .id = WLAN_EID_EXTENSION, .len = 1, .eid = 0x10 },
+		},
+	},
+	{
+		.desc = "empty elements from child",
+		.parent_ies = {
+		},
+		.child_ies = {
+			{ .id = 0x1, .len = 0, },
+			{ .id = WLAN_EID_EXTENSION, .len = 1, .eid = 0x10 },
+		},
+		.result_ies = {
+			{ .id = 0x1, .len = 0, },
+			{ .id = WLAN_EID_EXTENSION, .len = 1, .eid = 0x10 },
+		},
+	},
+	{
+		.desc = "invalid extended elements ignored",
+		.parent_ies = {
+			{ .id = WLAN_EID_EXTENSION, .len = 0 },
+		},
+		.child_ies = {
+			{ .id = WLAN_EID_EXTENSION, .len = 0 },
+		},
+		.result_ies = {
+		},
+	},
+	{
+		.desc = "multiple extended elements",
+		.parent_ies = {
+			{ .id = WLAN_EID_EXTENSION, .len = 3,
+			  .eid = WLAN_EID_EXT_HE_CAPABILITY },
+			{ .id = WLAN_EID_EXTENSION, .len = 5,
+			  .eid = WLAN_EID_EXT_ASSOC_DELAY_INFO },
+			{ .id = WLAN_EID_EXTENSION, .len = 7,
+			  .eid = WLAN_EID_EXT_HE_OPERATION },
+			{ .id = WLAN_EID_EXTENSION, .len = 11,
+			  .eid = WLAN_EID_EXT_FILS_REQ_PARAMS },
+		},
+		.child_ies = {
+			{ .id = WLAN_EID_SSID, .len = 13 },
+			{ .id = WLAN_EID_EXTENSION, .len = 17,
+			  .eid = WLAN_EID_EXT_HE_CAPABILITY },
+			{ .id = WLAN_EID_EXTENSION, .len = 11,
+			  .eid = WLAN_EID_EXT_FILS_KEY_CONFIRM },
+			{ .id = WLAN_EID_EXTENSION, .len = 19,
+			  .eid = WLAN_EID_EXT_HE_OPERATION },
+		},
+		.result_ies = {
+			{ .id = WLAN_EID_EXTENSION, .len = 17,
+			  .eid = WLAN_EID_EXT_HE_CAPABILITY },
+			{ .id = WLAN_EID_EXTENSION, .len = 5,
+			  .eid = WLAN_EID_EXT_ASSOC_DELAY_INFO },
+			{ .id = WLAN_EID_EXTENSION, .len = 19,
+			  .eid = WLAN_EID_EXT_HE_OPERATION },
+			{ .id = WLAN_EID_EXTENSION, .len = 11,
+			  .eid = WLAN_EID_EXT_FILS_REQ_PARAMS },
+			{ .id = WLAN_EID_SSID, .len = 13 },
+			{ .id = WLAN_EID_EXTENSION, .len = 11,
+			  .eid = WLAN_EID_EXT_FILS_KEY_CONFIRM },
+		},
+	},
+	{
+		.desc = "non-inherit element",
+		.parent_ies = {
+			{ .id = 0x1, .len = 7, },
+			{ .id = 0x2, .len = 11, },
+			{ .id = 0x3, .len = 13, },
+			{ .id = WLAN_EID_EXTENSION, .len = 17, .eid = 0x10 },
+			{ .id = WLAN_EID_EXTENSION, .len = 19, .eid = 0x11 },
+			{ .id = WLAN_EID_EXTENSION, .len = 23, .eid = 0x12 },
+			{ .id = WLAN_EID_EXTENSION, .len = 29, .eid = 0x14 },
+		},
+		.child_ies = {
+			{ .id = WLAN_EID_EXTENSION,
+			  .eid = WLAN_EID_EXT_NON_INHERITANCE,
+			  .len = 10,
+			  .edata = { 0x3, 0x1, 0x2, 0x3,
+				     0x4, 0x10, 0x11, 0x13, 0x14 } },
+			{ .id = WLAN_EID_SSID, .len = 2 },
+		},
+		.result_ies = {
+			{ .id = WLAN_EID_EXTENSION, .len = 23, .eid = 0x12 },
+			{ .id = WLAN_EID_SSID, .len = 2 },
+		},
+	},
+};
+KUNIT_ARRAY_PARAM_DESC(gen_new_ie, gen_new_ie_cases, desc)
+
+static void test_gen_new_ie(struct kunit *test)
+{
+	const struct gen_new_ie_case *params = test->param_value;
+	struct sk_buff *parent = kunit_zalloc_skb(test, 1024, GFP_KERNEL);
+	struct sk_buff *child = kunit_zalloc_skb(test, 1024, GFP_KERNEL);
+	struct sk_buff *reference = kunit_zalloc_skb(test, 1024, GFP_KERNEL);
+	u8 *out = kunit_kzalloc(test, IEEE80211_MAX_DATA_LEN, GFP_KERNEL);
+	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);
+			skb_put_u8(parent, params->parent_ies[i].len);
+			skb_put_data(parent, params->parent_ies[i].data,
+				     params->parent_ies[i].len);
+		}
+
+		if (params->child_ies[i].len != 0) {
+			skb_put_u8(child, params->child_ies[i].id);
+			skb_put_u8(child, params->child_ies[i].len);
+			skb_put_data(child, params->child_ies[i].data,
+				     params->child_ies[i].len);
+		}
+
+		if (params->result_ies[i].len != 0) {
+			skb_put_u8(reference, params->result_ies[i].id);
+			skb_put_u8(reference, params->result_ies[i].len);
+			skb_put_data(reference, params->result_ies[i].data,
+				     params->result_ies[i].len);
+		}
+	}
+
+	len = cfg80211_gen_new_ie(parent->data, parent->len,
+				  child->data, child->len,
+				  out, IEEE80211_MAX_DATA_LEN);
+	KUNIT_EXPECT_EQ(test, len, reference->len);
+	KUNIT_EXPECT_MEMEQ(test, out, reference->data, reference->len);
+	memset(out, 0, IEEE80211_MAX_DATA_LEN);
+
+	/* Exactly enough space */
+	len = cfg80211_gen_new_ie(parent->data, parent->len,
+				  child->data, child->len,
+				  out, reference->len);
+	KUNIT_EXPECT_EQ(test, len, reference->len);
+	KUNIT_EXPECT_MEMEQ(test, out, reference->data, reference->len);
+	memset(out, 0, IEEE80211_MAX_DATA_LEN);
+
+	/* Not enough space (or expected zero length) */
+	len = cfg80211_gen_new_ie(parent->data, parent->len,
+				  child->data, child->len,
+				  out, reference->len - 1);
+	KUNIT_EXPECT_EQ(test, len, 0);
+}
+
+static void test_gen_new_ie_malformed(struct kunit *test)
+{
+	struct sk_buff *malformed = kunit_zalloc_skb(test, 1024, GFP_KERNEL);
+	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);
+	skb_put_u8(malformed, WLAN_EID_REDUCED_NEIGHBOR_REPORT);
+	skb_put_u8(malformed, 10);
+	skb_put(malformed, 9);
+
+	len = cfg80211_gen_new_ie(malformed->data, malformed->len,
+				  out, 0,
+				  out, IEEE80211_MAX_DATA_LEN);
+	KUNIT_EXPECT_EQ(test, len, 5);
+
+	len = cfg80211_gen_new_ie(out, 0,
+				  malformed->data, malformed->len,
+				  out, IEEE80211_MAX_DATA_LEN);
+	KUNIT_EXPECT_EQ(test, len, 5);
+}
+
+struct inform_bss {
+	struct kunit *test;
+
+	int inform_bss_count;
+};
+
+static void inform_bss_inc_counter(struct wiphy *wiphy,
+				   struct cfg80211_bss *bss,
+				   const struct cfg80211_bss_ies *ies,
+				   void *drv_data)
+{
+	struct inform_bss *ctx = t_wiphy_ctx(wiphy);
+
+	ctx->inform_bss_count++;
+
+	rcu_read_lock();
+	KUNIT_EXPECT_PTR_EQ(ctx->test, drv_data, ctx);
+	KUNIT_EXPECT_PTR_EQ(ctx->test, ies, rcu_dereference(bss->ies));
+	rcu_read_unlock();
+}
+
+static void test_inform_bss_ssid_only(struct kunit *test)
+{
+	struct inform_bss ctx = {
+		.test = test,
+	};
+	struct wiphy *wiphy = T_WIPHY(test, ctx);
+	struct t_wiphy_priv *w_priv = wiphy_priv(wiphy);
+	struct cfg80211_inform_bss inform_bss = {
+		.signal = 50,
+		.drv_data = &ctx,
+	};
+	const u8 bssid[ETH_ALEN] = { 0x10, 0x22, 0x33, 0x44, 0x55, 0x66 };
+	u64 tsf = 0x1000000000000000ULL;
+	int beacon_int = 100;
+	u16 capability = 0x1234;
+	static const u8 input[] = {
+		[0] = WLAN_EID_SSID,
+		[1] = 4,
+		[2] = 'T', 'E', 'S', 'T'
+	};
+	struct cfg80211_bss *bss, *other;
+	const struct cfg80211_bss_ies *ies;
+
+	w_priv->ops->inform_bss = inform_bss_inc_counter;
+
+	inform_bss.chan = ieee80211_get_channel_khz(wiphy, MHZ_TO_KHZ(2412));
+	KUNIT_ASSERT_NOT_NULL(test, inform_bss.chan);
+
+	bss = cfg80211_inform_bss_data(wiphy, &inform_bss,
+				       CFG80211_BSS_FTYPE_PRESP, bssid, tsf,
+				       capability, beacon_int,
+				       input, sizeof(input),
+				       GFP_KERNEL);
+	KUNIT_EXPECT_NOT_NULL(test, bss);
+	KUNIT_EXPECT_EQ(test, ctx.inform_bss_count, 1);
+
+	/* Check values in returned bss are correct */
+	KUNIT_EXPECT_EQ(test, bss->signal, inform_bss.signal);
+	KUNIT_EXPECT_EQ(test, bss->beacon_interval, beacon_int);
+	KUNIT_EXPECT_EQ(test, bss->capability, capability);
+	KUNIT_EXPECT_EQ(test, bss->bssid_index, 0);
+	KUNIT_EXPECT_PTR_EQ(test, bss->channel, inform_bss.chan);
+	KUNIT_EXPECT_MEMEQ(test, bssid, bss->bssid, sizeof(bssid));
+
+	/* Check the IEs have the expected value */
+	rcu_read_lock();
+	ies = rcu_dereference(bss->ies);
+	KUNIT_EXPECT_NOT_NULL(test, ies);
+	KUNIT_EXPECT_EQ(test, ies->tsf, tsf);
+	KUNIT_EXPECT_EQ(test, ies->len, sizeof(input));
+	KUNIT_EXPECT_MEMEQ(test, ies->data, input, sizeof(input));
+	rcu_read_unlock();
+
+	/* Check we can look up the BSS - by SSID */
+	other = cfg80211_get_bss(wiphy, NULL, NULL, "TEST", 4,
+				 IEEE80211_BSS_TYPE_ANY,
+				 IEEE80211_PRIVACY_ANY);
+	KUNIT_EXPECT_PTR_EQ(test, bss, other);
+	cfg80211_put_bss(wiphy, other);
+
+	/* Check we can look up the BSS - by BSSID */
+	other = cfg80211_get_bss(wiphy, NULL, bssid, NULL, 0,
+				 IEEE80211_BSS_TYPE_ANY,
+				 IEEE80211_PRIVACY_ANY);
+	KUNIT_EXPECT_PTR_EQ(test, bss, other);
+	cfg80211_put_bss(wiphy, other);
+
+	cfg80211_put_bss(wiphy, bss);
+}
+
+static struct inform_bss_ml_sta_case {
+	const char *desc;
+	int mld_id;
+	bool sta_prof_vendor_elems;
+} inform_bss_ml_sta_cases[] = {
+	{ .desc = "no_mld_id", .mld_id = 0, .sta_prof_vendor_elems = false },
+	{ .desc = "mld_id_eq_1", .mld_id = 1, .sta_prof_vendor_elems = true },
+};
+KUNIT_ARRAY_PARAM_DESC(inform_bss_ml_sta, inform_bss_ml_sta_cases, desc)
+
+static void test_inform_bss_ml_sta(struct kunit *test)
+{
+	const struct inform_bss_ml_sta_case *params = test->param_value;
+	struct inform_bss ctx = {
+		.test = test,
+	};
+	struct wiphy *wiphy = T_WIPHY(test, ctx);
+	struct t_wiphy_priv *w_priv = wiphy_priv(wiphy);
+	struct cfg80211_inform_bss inform_bss = {
+		.signal = 50,
+		.drv_data = &ctx,
+	};
+	struct cfg80211_bss *bss, *link_bss;
+	const struct cfg80211_bss_ies *ies;
+
+	/* sending station */
+	const u8 bssid[ETH_ALEN] = { 0x10, 0x22, 0x33, 0x44, 0x55, 0x66 };
+	u64 tsf = 0x1000000000000000ULL;
+	int beacon_int = 100;
+	u16 capability = 0x1234;
+
+	/* Building the frame *************************************************/
+	struct sk_buff *input = kunit_zalloc_skb(test, 1024, GFP_KERNEL);
+	u8 *len_mle, *len_prof;
+	u8 link_id = 2;
+	struct {
+		struct ieee80211_neighbor_ap_info info;
+		struct ieee80211_tbtt_info_ge_11 ap;
+	} __packed rnr = {
+		.info = {
+			.tbtt_info_hdr = u8_encode_bits(0, IEEE80211_AP_INFO_TBTT_HDR_COUNT),
+			.tbtt_info_len = sizeof(struct ieee80211_tbtt_info_ge_11),
+			.op_class = 81,
+			.channel = 11,
+		},
+		.ap = {
+			.tbtt_offset = 0xff,
+			.bssid = { 0x10, 0x22, 0x33, 0x44, 0x55, 0x67 },
+			.short_ssid = 0, /* unused */
+			.bss_params = 0,
+			.psd_20 = 0,
+			.mld_params.mld_id = params->mld_id,
+			.mld_params.params =
+				le16_encode_bits(link_id,
+						 IEEE80211_RNR_MLD_PARAMS_LINK_ID),
+		}
+	};
+	struct {
+		__le16 control;
+		u8 var_len;
+		u8 mld_mac_addr[ETH_ALEN];
+		u8 link_id_info;
+		u8 params_change_count;
+		__le16 mld_caps_and_ops;
+		u8 mld_id;
+		__le16 ext_mld_caps_and_ops;
+	} __packed mle_basic_common_info = {
+		.control =
+			cpu_to_le16(IEEE80211_ML_CONTROL_TYPE_BASIC |
+				    IEEE80211_MLC_BASIC_PRES_BSS_PARAM_CH_CNT |
+				    IEEE80211_MLC_BASIC_PRES_LINK_ID |
+				    (params->mld_id ? IEEE80211_MLC_BASIC_PRES_MLD_ID : 0) |
+				    IEEE80211_MLC_BASIC_PRES_MLD_CAPA_OP),
+		.mld_id = params->mld_id,
+		.mld_caps_and_ops = cpu_to_le16(0x0102),
+		.ext_mld_caps_and_ops = cpu_to_le16(0x0304),
+		.var_len = sizeof(mle_basic_common_info) - 2 -
+			   (params->mld_id ? 0 : 1),
+		.mld_mac_addr = { 0x10, 0x22, 0x33, 0x44, 0x55, 0x60 },
+	};
+	struct {
+		__le16 control;
+		u8 var_len;
+		u8 bssid[ETH_ALEN];
+		__le16 beacon_int;
+		__le64 tsf_offset;
+		__le16 capabilities; /* already part of payload */
+	} __packed sta_prof = {
+		.control =
+			cpu_to_le16(IEEE80211_MLE_STA_CONTROL_COMPLETE_PROFILE |
+				    IEEE80211_MLE_STA_CONTROL_STA_MAC_ADDR_PRESENT |
+				    IEEE80211_MLE_STA_CONTROL_BEACON_INT_PRESENT |
+				    IEEE80211_MLE_STA_CONTROL_TSF_OFFS_PRESENT |
+				    u16_encode_bits(link_id,
+						    IEEE80211_MLE_STA_CONTROL_LINK_ID)),
+		.var_len = sizeof(sta_prof) - 2 - 2,
+		.bssid = { *rnr.ap.bssid },
+		.beacon_int = cpu_to_le16(101),
+		.tsf_offset = cpu_to_le64(-123ll),
+		.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));
+	KUNIT_ASSERT_NOT_NULL(test, inform_bss.chan);
+
+	skb_put_u8(input, WLAN_EID_SSID);
+	skb_put_u8(input, 4);
+	skb_put_data(input, "TEST", 4);
+
+	skb_put_u8(input, WLAN_EID_REDUCED_NEIGHBOR_REPORT);
+	skb_put_u8(input, sizeof(rnr));
+	skb_put_data(input, &rnr, sizeof(rnr));
+
+	/* build a multi-link element */
+	skb_put_u8(input, WLAN_EID_EXTENSION);
+	len_mle = skb_put(input, 1);
+	skb_put_u8(input, WLAN_EID_EXT_EHT_MULTI_LINK);
+	skb_put_data(input, &mle_basic_common_info, sizeof(mle_basic_common_info));
+	if (!params->mld_id)
+		t_skb_remove_member(input, typeof(mle_basic_common_info), mld_id);
+	/* with a STA profile inside */
+	skb_put_u8(input, IEEE80211_MLE_SUBELEM_PER_STA_PROFILE);
+	len_prof = skb_put(input, 1);
+	skb_put_data(input, &sta_prof, sizeof(sta_prof));
+
+	if (params->sta_prof_vendor_elems) {
+		/* Put two (vendor) element into sta_prof */
+		skb_put_u8(input, WLAN_EID_VENDOR_SPECIFIC);
+		skb_put_u8(input, 160);
+		skb_put(input, 160);
+
+		skb_put_u8(input, WLAN_EID_VENDOR_SPECIFIC);
+		skb_put_u8(input, 165);
+		skb_put(input, 165);
+	}
+
+	/* fragment STA profile */
+	ieee80211_fragment_element(input, len_prof,
+				   IEEE80211_MLE_SUBELEM_FRAGMENT);
+	/* fragment MLE */
+	ieee80211_fragment_element(input, len_mle, WLAN_EID_FRAGMENT);
+
+	/* Put a (vendor) element after the ML element */
+	skb_put_u8(input, WLAN_EID_VENDOR_SPECIFIC);
+	skb_put_u8(input, 155);
+	skb_put(input, 155);
+
+	/* Submit *************************************************************/
+	bss = cfg80211_inform_bss_data(wiphy, &inform_bss,
+				       CFG80211_BSS_FTYPE_PRESP, bssid, tsf,
+				       capability, beacon_int,
+				       input->data, input->len,
+				       GFP_KERNEL);
+	KUNIT_EXPECT_NOT_NULL(test, bss);
+	KUNIT_EXPECT_EQ(test, ctx.inform_bss_count, 2);
+
+	/* Check link_bss *****************************************************/
+	link_bss = cfg80211_get_bss(wiphy, NULL, sta_prof.bssid, NULL, 0,
+				    IEEE80211_BSS_TYPE_ANY,
+				    IEEE80211_PRIVACY_ANY);
+	KUNIT_ASSERT_NOT_NULL(test, link_bss);
+	KUNIT_EXPECT_EQ(test, link_bss->signal, 0);
+	KUNIT_EXPECT_EQ(test, link_bss->beacon_interval,
+			      le16_to_cpu(sta_prof.beacon_int));
+	KUNIT_EXPECT_EQ(test, link_bss->capability,
+			      le16_to_cpu(sta_prof.capabilities));
+	KUNIT_EXPECT_EQ(test, link_bss->bssid_index, 0);
+	KUNIT_EXPECT_PTR_EQ(test, link_bss->channel,
+			    ieee80211_get_channel_khz(wiphy, MHZ_TO_KHZ(2462)));
+
+	rcu_read_lock();
+	ies = rcu_dereference(link_bss->ies);
+	KUNIT_EXPECT_NOT_NULL(test, ies);
+	KUNIT_EXPECT_EQ(test, ies->tsf, tsf + le64_to_cpu(sta_prof.tsf_offset));
+	/* Resulting length should be:
+	 * SSID (inherited) + RNR (inherited) + vendor element(s) +
+	 * MLE common info + MLE header and control
+	 */
+	if (params->sta_prof_vendor_elems)
+		KUNIT_EXPECT_EQ(test, ies->len,
+				6 + 2 + sizeof(rnr) + 2 + 160 + 2 + 165 +
+				mle_basic_common_info.var_len + 5);
+	else
+		KUNIT_EXPECT_EQ(test, ies->len,
+				6 + 2 + sizeof(rnr) + 2 + 155 +
+				mle_basic_common_info.var_len + 5);
+	rcu_read_unlock();
+
+	cfg80211_put_bss(wiphy, bss);
+	cfg80211_put_bss(wiphy, link_bss);
+}
+
+static struct kunit_case gen_new_ie_test_cases[] = {
+	KUNIT_CASE_PARAM(test_gen_new_ie, gen_new_ie_gen_params),
+	KUNIT_CASE(test_gen_new_ie_malformed),
+	{}
+};
+
+static struct kunit_suite gen_new_ie = {
+	.name = "cfg80211-ie-generation",
+	.test_cases = gen_new_ie_test_cases,
+};
+
+kunit_test_suite(gen_new_ie);
+
+static struct kunit_case inform_bss_test_cases[] = {
+	KUNIT_CASE(test_inform_bss_ssid_only),
+	KUNIT_CASE_PARAM(test_inform_bss_ml_sta, inform_bss_ml_sta_gen_params),
+	{}
+};
+
+static struct kunit_suite inform_bss = {
+	.name = "cfg80211-inform-bss",
+	.test_cases = inform_bss_test_cases,
+};
+
+kunit_test_suite(inform_bss);
diff --git a/net/wireless/tests/util.c b/net/wireless/tests/util.c
new file mode 100644
index 000000000000..8abdaeb820ce
--- /dev/null
+++ b/net/wireless/tests/util.c
@@ -0,0 +1,56 @@
+// SPDX-License-Identifier: GPL-2.0-only
+/*
+ * KUnit fixture to have a (configurable) wiphy
+ *
+ * Copyright (C) 2023 Intel Corporation
+ */
+#include <linux/ieee80211.h>
+#include <net/cfg80211.h>
+#include <kunit/test.h>
+#include <kunit/test-bug.h>
+#include "util.h"
+
+int t_wiphy_init(struct kunit_resource *resource, void *ctx)
+{
+	struct kunit *test = kunit_get_current_test();
+	struct cfg80211_ops *ops;
+	struct wiphy *wiphy;
+	struct t_wiphy_priv *priv;
+
+	ops = kzalloc(sizeof(*ops), GFP_KERNEL);
+	KUNIT_ASSERT_NOT_NULL(test, ops);
+
+	wiphy = wiphy_new_nm(ops, sizeof(*priv), "kunit");
+	KUNIT_ASSERT_NOT_NULL(test, wiphy);
+
+	priv = wiphy_priv(wiphy);
+	priv->ctx = ctx;
+	priv->ops = ops;
+
+	/* Initialize channels, feel free to add more here channels/bands */
+	memcpy(priv->channels_2ghz, channels_2ghz, sizeof(channels_2ghz));
+	wiphy->bands[NL80211_BAND_2GHZ] = &priv->band_2ghz;
+	priv->band_2ghz.channels = priv->channels_2ghz;
+	priv->band_2ghz.n_channels = ARRAY_SIZE(channels_2ghz);
+
+	resource->data = wiphy;
+	resource->name = "wiphy";
+
+	return 0;
+}
+
+void t_wiphy_exit(struct kunit_resource *resource)
+{
+	struct t_wiphy_priv *priv;
+	struct cfg80211_ops *ops;
+
+	priv = wiphy_priv(resource->data);
+	ops = priv->ops;
+
+	/* Should we ensure anything about the state here?
+	 * e.g. full destruction or no calls to any ops on destruction?
+	 */
+
+	wiphy_free(resource->data);
+	kfree(ops);
+}
diff --git a/net/wireless/tests/util.h b/net/wireless/tests/util.h
new file mode 100644
index 000000000000..6de712e0d432
--- /dev/null
+++ b/net/wireless/tests/util.h
@@ -0,0 +1,66 @@
+/* SPDX-License-Identifier: GPL-2.0-only */
+/*
+ * Utilities for cfg80211 unit testing
+ *
+ * Copyright (C) 2023 Intel Corporation
+ */
+#ifndef __CFG80211_UTILS_H
+#define __CFG80211_UTILS_H
+
+#define CHAN2G(_freq)  { \
+	.band = NL80211_BAND_2GHZ, \
+	.center_freq = (_freq), \
+	.hw_value = (_freq), \
+}
+
+static const struct ieee80211_channel channels_2ghz[] = {
+	CHAN2G(2412), /* Channel 1 */
+	CHAN2G(2417), /* Channel 2 */
+	CHAN2G(2422), /* Channel 3 */
+	CHAN2G(2427), /* Channel 4 */
+	CHAN2G(2432), /* Channel 5 */
+	CHAN2G(2437), /* Channel 6 */
+	CHAN2G(2442), /* Channel 7 */
+	CHAN2G(2447), /* Channel 8 */
+	CHAN2G(2452), /* Channel 9 */
+	CHAN2G(2457), /* Channel 10 */
+	CHAN2G(2462), /* Channel 11 */
+	CHAN2G(2467), /* Channel 12 */
+	CHAN2G(2472), /* Channel 13 */
+	CHAN2G(2484), /* Channel 14 */
+};
+
+struct t_wiphy_priv {
+	struct kunit *test;
+	struct cfg80211_ops *ops;
+
+	void *ctx;
+
+	struct ieee80211_supported_band band_2ghz;
+	struct ieee80211_channel channels_2ghz[ARRAY_SIZE(channels_2ghz)];
+};
+
+#define T_WIPHY(test, ctx) ({						\
+		struct wiphy *__wiphy =					\
+			kunit_alloc_resource(test, t_wiphy_init,	\
+					     t_wiphy_exit,		\
+					     GFP_KERNEL, &(ctx));	\
+									\
+		KUNIT_ASSERT_NOT_NULL(test, __wiphy);			\
+		__wiphy;						\
+	})
+#define t_wiphy_ctx(wiphy) (((struct t_wiphy_priv *)wiphy_priv(wiphy))->ctx)
+
+int t_wiphy_init(struct kunit_resource *resource, void *data);
+void t_wiphy_exit(struct kunit_resource *resource);
+
+#define t_skb_remove_member(skb, type, member)	do {				\
+		memmove((skb)->data + (skb)->len - sizeof(type) +		\
+			offsetof(type, member),					\
+			(skb)->data + (skb)->len - sizeof(type) +		\
+			offsetofend(type, member),				\
+			offsetofend(type, member));				\
+		skb_trim(skb, (skb)->len - sizeof_field(type, member));		\
+	} while (0)
+
+#endif /* __CFG80211_UTILS_H */
-- 
2.43.0


^ permalink raw reply related	[flat|nested] 19+ messages in thread

* Re: [PATCH 0/6] Add some more cfg80211 and mac80211 kunit tests
  2023-12-20 15:19 [PATCH 0/6] Add some more cfg80211 and mac80211 kunit tests benjamin
                   ` (5 preceding siblings ...)
  2023-12-20 15:19 ` [PATCH 6/6] wifi: cfg80211: tests: add some scanning related tests benjamin
@ 2023-12-21 19:39 ` Johannes Berg
  2023-12-21 20:06   ` Shuah Khan
  6 siblings, 1 reply; 19+ messages in thread
From: Johannes Berg @ 2023-12-21 19:39 UTC (permalink / raw
  To: benjamin, linux-wireless, linux-kselftest, kunit-dev; +Cc: Benjamin Berg

> 
> This patchset adds a couple of helpers for kunit as well as tests for
> cfg80211 and mac80211 that use them.

I can take this through the wireless tree, but then I'd like to have
ACKs from kunit folks for the kunit patches:

>   kunit: add parameter generation macro using description from array
>   kunit: add a convenience allocation wrapper for SKBs
> 

Thanks,
johannes

^ permalink raw reply	[flat|nested] 19+ messages in thread

* Re: [PATCH 0/6] Add some more cfg80211 and mac80211 kunit tests
  2023-12-21 19:39 ` [PATCH 0/6] Add some more cfg80211 and mac80211 kunit tests Johannes Berg
@ 2023-12-21 20:06   ` Shuah Khan
  2023-12-21 20:40     ` Johannes Berg
  0 siblings, 1 reply; 19+ messages in thread
From: Shuah Khan @ 2023-12-21 20:06 UTC (permalink / raw
  To: Johannes Berg, benjamin, linux-wireless, linux-kselftest,
	kunit-dev, David Gow, Brendan Higgins
  Cc: Benjamin Berg, Shuah Khan

On 12/21/23 12:39, Johannes Berg wrote:
>>
>> This patchset adds a couple of helpers for kunit as well as tests for
>> cfg80211 and mac80211 that use them.
> 
> I can take this through the wireless tree, but then I'd like to have
> ACKs from kunit folks for the kunit patches:
> 

We have run into conflicts in the past with the kunit tree. I take the
kunit patches through linux-kselftest tree. I do want to make sure there
are no conflicts. I don't mind taking these through my tree.


>>    kunit: add parameter generation macro using description from array
>>    kunit: add a convenience allocation wrapper for SKBs
>>
> 

Adding David and Brendan to the thread for their review.

thanks,
-- Shuah



^ permalink raw reply	[flat|nested] 19+ messages in thread

* Re: [PATCH 0/6] Add some more cfg80211 and mac80211 kunit tests
  2023-12-21 20:06   ` Shuah Khan
@ 2023-12-21 20:40     ` Johannes Berg
  2023-12-21 21:47       ` Shuah Khan
  0 siblings, 1 reply; 19+ messages in thread
From: Johannes Berg @ 2023-12-21 20:40 UTC (permalink / raw
  To: Shuah Khan, benjamin, linux-wireless, linux-kselftest, kunit-dev,
	David Gow, Brendan Higgins
  Cc: Benjamin Berg

On Thu, 2023-12-21 at 13:06 -0700, Shuah Khan wrote:
> On 12/21/23 12:39, Johannes Berg wrote:
> > > 
> > > This patchset adds a couple of helpers for kunit as well as tests for
> > > cfg80211 and mac80211 that use them.
> > 
> > I can take this through the wireless tree, but then I'd like to have
> > ACKs from kunit folks for the kunit patches:
> > 
> 
> We have run into conflicts in the past with the kunit tree. I take the
> kunit patches through linux-kselftest tree. I do want to make sure there
> are no conflicts. I don't mind taking these through my tree.

OK, fair enough.

If you can still put it into 6.8, then I think you can also take the
wireless tests, assuming they pass (I haven't run them in the posted
version). I don't think we'll have conflicts there, we don't have much
work in wireless that's likely to land for 6.8.

johannes

^ permalink raw reply	[flat|nested] 19+ messages in thread

* Re: [PATCH 0/6] Add some more cfg80211 and mac80211 kunit tests
  2023-12-21 20:40     ` Johannes Berg
@ 2023-12-21 21:47       ` Shuah Khan
  2023-12-22 10:02         ` David Gow
  0 siblings, 1 reply; 19+ messages in thread
From: Shuah Khan @ 2023-12-21 21:47 UTC (permalink / raw
  To: Johannes Berg, benjamin, linux-wireless, linux-kselftest,
	kunit-dev, David Gow, Brendan Higgins
  Cc: Benjamin Berg, Shuah Khan

On 12/21/23 13:40, Johannes Berg wrote:
> On Thu, 2023-12-21 at 13:06 -0700, Shuah Khan wrote:
>> On 12/21/23 12:39, Johannes Berg wrote:
>>>>
>>>> This patchset adds a couple of helpers for kunit as well as tests for
>>>> cfg80211 and mac80211 that use them.
>>>
>>> I can take this through the wireless tree, but then I'd like to have
>>> ACKs from kunit folks for the kunit patches:
>>>
>>
>> We have run into conflicts in the past with the kunit tree. I take the
>> kunit patches through linux-kselftest tree. I do want to make sure there
>> are no conflicts. I don't mind taking these through my tree.
> 
> OK, fair enough.
> 
> If you can still put it into 6.8, then I think you can also take the
> wireless tests, assuming they pass (I haven't run them in the posted
> version). I don't think we'll have conflicts there, we don't have much
> work in wireless that's likely to land for 6.8.
> 

Sounds good.

David, will you be able to look at these patches and let me know if
I can apply for Linux 6.8-rc1.

thanks,
-- Shuah


^ permalink raw reply	[flat|nested] 19+ messages in thread

* Re: [PATCH 1/6] kunit: add parameter generation macro using description from array
  2023-12-20 15:19 ` [PATCH 1/6] kunit: add parameter generation macro using description from array benjamin
@ 2023-12-22 10:02   ` David Gow
  2023-12-22 14:59     ` Benjamin Berg
  0 siblings, 1 reply; 19+ messages in thread
From: David Gow @ 2023-12-22 10:02 UTC (permalink / raw
  To: benjamin; +Cc: linux-wireless, linux-kselftest, kunit-dev, Benjamin Berg

[-- Attachment #1: Type: text/plain, Size: 5104 bytes --]

On Wed, 20 Dec 2023 at 23:20, <benjamin@sipsolutions.net> wrote:
>
> From: Benjamin Berg <benjamin.berg@intel.com>
>
> The existing KUNIT_ARRAY_PARAM macro requires a separate function to
> get the description. However, in a lot of cases the description can
> just be copied directly from the array. Add a second macro that
> avoids having to write a static function just for a single strscpy.
>
> Signed-off-by: Benjamin Berg <benjamin.berg@intel.com>
> ---

I'm generally pretty happy with this, though note the checkpatch warning below.

There was some discussion at plumbers about expanding the
parameterised test APIs, so we may need to adjust the implementation
of this down the line, but I don't think that'll happen for a while,
so don't worry.

With the warnings fixed, this is:

Reviewed-by: David Gow <davidgow@google.com>

I'm okay with this going in via the wireless tree if that's easier;
certainly there are some conflicts with the later patches in this
series and the kunit one.

Cheers,
-- David

>  Documentation/dev-tools/kunit/usage.rst | 12 ++++--------
>  include/kunit/test.h                    | 19 +++++++++++++++++++
>  2 files changed, 23 insertions(+), 8 deletions(-)
>
> diff --git a/Documentation/dev-tools/kunit/usage.rst b/Documentation/dev-tools/kunit/usage.rst
> index c27e1646ecd9..b959e5befcbe 100644
> --- a/Documentation/dev-tools/kunit/usage.rst
> +++ b/Documentation/dev-tools/kunit/usage.rst
> @@ -566,13 +566,9 @@ By reusing the same ``cases`` array from above, we can write the test as a
>                 },
>         };
>
> -       // Need a helper function to generate a name for each test case.
> -       static void case_to_desc(const struct sha1_test_case *t, char *desc)
> -       {
> -               strcpy(desc, t->str);
> -       }
> -       // Creates `sha1_gen_params()` to iterate over `cases`.
> -       KUNIT_ARRAY_PARAM(sha1, cases, case_to_desc);
> +       // Creates `sha1_gen_params()` to iterate over `cases` while using
> +       // the struct member `str` for the case description.
> +       KUNIT_ARRAY_PARAM_DESC(sha1, cases, str);
>
>         // Looks no different from a normal test.
>         static void sha1_test(struct kunit *test)
> @@ -588,7 +584,7 @@ By reusing the same ``cases`` array from above, we can write the test as a
>         }
>
>         // Instead of KUNIT_CASE, we use KUNIT_CASE_PARAM and pass in the
> -       // function declared by KUNIT_ARRAY_PARAM.
> +       // function declared by KUNIT_ARRAY_PARAM or KUNIT_ARRAY_PARAM_DESC.
>         static struct kunit_case sha1_test_cases[] = {
>                 KUNIT_CASE_PARAM(sha1_test, sha1_gen_params),
>                 {}
> diff --git a/include/kunit/test.h b/include/kunit/test.h
> index 20ed9f9275c9..2dfa851e1f88 100644
> --- a/include/kunit/test.h
> +++ b/include/kunit/test.h
> @@ -1514,6 +1514,25 @@ do {                                                                            \
>                 return NULL;                                                                    \
>         }
>
> +/**
> + * KUNIT_ARRAY_PARAM_DESC() - Define test parameter generator from an array.
> + * @name:  prefix for the test parameter generator function.
> + * @array: array of test parameters.
> + * @desc_member: structure member from array element to use as description
> + *
> + * Define function @name_gen_params which uses @array to generate parameters.
> + */
> +#define KUNIT_ARRAY_PARAM_DESC(name, array, desc_member)                                       \
> +       static const void *name##_gen_params(const void *prev, char *desc)                      \
> +       {                                                                                       \
> +               typeof((array)[0]) *__next = prev ? ((typeof(__next)) prev) + 1 : (array);      \

checkpatch is complaining here:
ERROR: need consistent spacing around '*' (ctx:WxV)
#71: FILE: include/kunit/test.h:1528:

+               typeof((array)[0]) *__next = prev ? ((typeof(__next))
prev) + 1 : (array);      \

> +               if (__next - (array) < ARRAY_SIZE((array))) {                                   \
> +                       strscpy(desc, __next->desc_member, KUNIT_PARAM_DESC_SIZE);              \
> +                       return __next;                                                          \
> +               }                                                                               \
> +               return NULL;                                                                    \
> +       }
> +
>  // TODO(dlatypov@google.com): consider eventually migrating users to explicitly
>  // include resource.h themselves if they need it.
>  #include <kunit/resource.h>
> --
> 2.43.0
>
> --
> You received this message because you are subscribed to the Google Groups "KUnit Development" group.
> To unsubscribe from this group and stop receiving emails from it, send an email to kunit-dev+unsubscribe@googlegroups.com.
> To view this discussion on the web visit https://groups.google.com/d/msgid/kunit-dev/20231220151952.415232-2-benjamin%40sipsolutions.net.

[-- Attachment #2: S/MIME Cryptographic Signature --]
[-- Type: application/pkcs7-signature, Size: 4003 bytes --]

^ permalink raw reply	[flat|nested] 19+ messages in thread

* Re: [PATCH 2/6] kunit: add a convenience allocation wrapper for SKBs
  2023-12-20 15:19 ` [PATCH 2/6] kunit: add a convenience allocation wrapper for SKBs benjamin
@ 2023-12-22 10:02   ` David Gow
  0 siblings, 0 replies; 19+ messages in thread
From: David Gow @ 2023-12-22 10:02 UTC (permalink / raw
  To: benjamin; +Cc: linux-wireless, linux-kselftest, kunit-dev, Benjamin Berg

[-- Attachment #1: Type: text/plain, Size: 3315 bytes --]

On Wed, 20 Dec 2023 at 23:20, <benjamin@sipsolutions.net> wrote:
>
> From: Benjamin Berg <benjamin.berg@intel.com>
>
> Add a simple convenience helper to allocate and zero fill an SKB for the
> use by a kunit test. Also provide a way to free it again in case that
> may be desirable.
>
> This simply mirrors the kunit_kmalloc API.
>
> Signed-off-by: Benjamin Berg <benjamin.berg@intel.com>
> ---

I'm happy with this as-is, but do think there's a discussion to be had
about where subsystem-specific KUnit helpers should live. I think,
because this is just a header (and it mirrors the normal
linux/skbuff.h), that having it in include/kunit works well.

If it needed a source file, I'm not 100% sure whether it should be in
net/core/ or lib/kunit.

Regardless, this looks good to me, modulo the small nitpick below.

Reviewed-by: David Gow <davidgow@google.com>

>  include/kunit/skbuff.h | 56 ++++++++++++++++++++++++++++++++++++++++++
>  1 file changed, 56 insertions(+)
>  create mode 100644 include/kunit/skbuff.h
>
> diff --git a/include/kunit/skbuff.h b/include/kunit/skbuff.h
> new file mode 100644
> index 000000000000..2144d01e556f
> --- /dev/null
> +++ b/include/kunit/skbuff.h
> @@ -0,0 +1,56 @@
> +/* SPDX-License-Identifier: GPL-2.0 */
> +/*
> + * Base unit test (KUnit) API.

This probably needs a better description which mentions skbuff, and
that it's for resource management.


> + *
> + * Copyright (C) 2023 Intel Corporation
> + */
> +
> +#ifndef _KUNIT_SKBUFF_H
> +#define _KUNIT_SKBUFF_H
> +
> +#include <kunit/resource.h>
> +#include <linux/skbuff.h>
> +
> +static void kunit_action_kfree_skb(void *p)
> +{
> +       kfree_skb((struct sk_buff *)p);
> +}
> +
> +/**
> + * kunit_zalloc_skb() - Allocate and initialize a resource managed skb.
> + * @test: The test case to which the skb belongs
> + * @len: size to allocate
> + *
> + * 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.
> + *
> + * 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_KERNEL);
> +
> +       if (!res || skb_pad(res, len))
> +               return NULL;
> +
> +       if (kunit_add_action_or_reset(test, kunit_action_kfree_skb, res))
> +               return NULL;
> +
> +       return res;
> +}
> +
> +/**
> + * 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_kfree_skb, (void *)skb);
> +}
> +
> +#endif /* _KUNIT_SKBUFF_H */
> --
> 2.43.0
>
> --
> You received this message because you are subscribed to the Google Groups "KUnit Development" group.
> To unsubscribe from this group and stop receiving emails from it, send an email to kunit-dev+unsubscribe@googlegroups.com.
> To view this discussion on the web visit https://groups.google.com/d/msgid/kunit-dev/20231220151952.415232-3-benjamin%40sipsolutions.net.

[-- Attachment #2: S/MIME Cryptographic Signature --]
[-- Type: application/pkcs7-signature, Size: 4003 bytes --]

^ permalink raw reply	[flat|nested] 19+ messages in thread

* Re: [PATCH 0/6] Add some more cfg80211 and mac80211 kunit tests
  2023-12-21 21:47       ` Shuah Khan
@ 2023-12-22 10:02         ` David Gow
  2023-12-22 10:09           ` Johannes Berg
  0 siblings, 1 reply; 19+ messages in thread
From: David Gow @ 2023-12-22 10:02 UTC (permalink / raw
  To: Shuah Khan
  Cc: Johannes Berg, benjamin, linux-wireless, linux-kselftest,
	kunit-dev, Brendan Higgins, Benjamin Berg

[-- Attachment #1: Type: text/plain, Size: 1979 bytes --]

On Fri, 22 Dec 2023 at 05:47, Shuah Khan <skhan@linuxfoundation.org> wrote:
>
> On 12/21/23 13:40, Johannes Berg wrote:
> > On Thu, 2023-12-21 at 13:06 -0700, Shuah Khan wrote:
> >> On 12/21/23 12:39, Johannes Berg wrote:
> >>>>
> >>>> This patchset adds a couple of helpers for kunit as well as tests for
> >>>> cfg80211 and mac80211 that use them.
> >>>
> >>> I can take this through the wireless tree, but then I'd like to have
> >>> ACKs from kunit folks for the kunit patches:
> >>>
> >>
> >> We have run into conflicts in the past with the kunit tree. I take the
> >> kunit patches through linux-kselftest tree. I do want to make sure there
> >> are no conflicts. I don't mind taking these through my tree.
> >
> > OK, fair enough.
> >
> > If you can still put it into 6.8, then I think you can also take the
> > wireless tests, assuming they pass (I haven't run them in the posted
> > version). I don't think we'll have conflicts there, we don't have much
> > work in wireless that's likely to land for 6.8.
> >
>
> Sounds good.
>
> David, will you be able to look at these patches and let me know if
> I can apply for Linux 6.8-rc1.

The two initial KUnit patches look fine, modulo a couple of minor docs
issues and checkpatch warnings. They apply cleanly, and I doubt
there's much chance of there being a merge conflict for 6.8 -- there
are no other changes to the parameterised test macros, and the skb
stuff is in its own file.

The remaining patches don't apply on top of the kunit branch as-is. I
haven't had a chance to review them properly yet; the initial glance I
had didn't show any serious issues (though I think checkpatch
suggested some things to 'check').

So (once those small issues are finished), I'm okay with the first two
patches going in via either tree. The remaining ones are probably best
done via the wireless tree, as they seem to depend on some existing
patches there, so maybe it makes sense to push everything via
wireless.

Cheers,
-- David

[-- Attachment #2: S/MIME Cryptographic Signature --]
[-- Type: application/pkcs7-signature, Size: 4003 bytes --]

^ permalink raw reply	[flat|nested] 19+ messages in thread

* Re: [PATCH 0/6] Add some more cfg80211 and mac80211 kunit tests
  2023-12-22 10:02         ` David Gow
@ 2023-12-22 10:09           ` Johannes Berg
  2023-12-22 14:12             ` David Gow
  2023-12-22 15:44             ` Shuah Khan
  0 siblings, 2 replies; 19+ messages in thread
From: Johannes Berg @ 2023-12-22 10:09 UTC (permalink / raw
  To: David Gow, Shuah Khan
  Cc: benjamin, linux-wireless, linux-kselftest, kunit-dev,
	Brendan Higgins, Benjamin Berg

Hi,

Thanks for taking a look!

On Fri, 2023-12-22 at 18:02 +0800, David Gow wrote:
> The two initial KUnit patches look fine, modulo a couple of minor docs
> issues and checkpatch warnings. 

I can run checkpatch (even if I can't always take it seriously), but do
you want to comment more specifically wrt. the docs?

> They apply cleanly, and I doubt
> there's much chance of there being a merge conflict for 6.8 -- there
> are no other changes to the parameterised test macros, and the skb
> stuff is in its own file.

Right.

> The remaining patches don't apply on top of the kunit branch as-is.

Oh, OK. That makes some sense though, we've had a number of changes in
the stack this cycle before. I somehow thought the tests were likely
standalone, but apparently not.

> I
> haven't had a chance to review them properly yet; the initial glance I
> had didn't show any serious issues (though I think checkpatch
> suggested some things to 'check').

I can check.

> So (once those small issues are finished), I'm okay with the first two
> patches going in via either tree. The remaining ones are probably best
> done via the wireless tree, as they seem to depend on some existing
> patches there, so maybe it makes sense to push everything via
> wireless.

If not through wireless I doubt we'll get it synchronized for 6.8,
though of course it's also not needed for 6.8 to have the extra unit
tests :)

I'll let Shuah decide.

Thanks!

johannes

^ permalink raw reply	[flat|nested] 19+ messages in thread

* Re: [PATCH 0/6] Add some more cfg80211 and mac80211 kunit tests
  2023-12-22 10:09           ` Johannes Berg
@ 2023-12-22 14:12             ` David Gow
  2023-12-22 15:44             ` Shuah Khan
  1 sibling, 0 replies; 19+ messages in thread
From: David Gow @ 2023-12-22 14:12 UTC (permalink / raw
  To: Johannes Berg
  Cc: Shuah Khan, benjamin, linux-wireless, linux-kselftest, kunit-dev,
	Brendan Higgins, Benjamin Berg

[-- Attachment #1: Type: text/plain, Size: 5885 bytes --]

On Fri, 22 Dec 2023 at 18:09, Johannes Berg <johannes@sipsolutions.net> wrote:
>
> Hi,
>
> Thanks for taking a look!
>
> On Fri, 2023-12-22 at 18:02 +0800, David Gow wrote:
> > The two initial KUnit patches look fine, modulo a couple of minor docs
> > issues and checkpatch warnings.
>
> I can run checkpatch (even if I can't always take it seriously), but do
> you want to comment more specifically wrt. the docs?
>

Sorry, the 'docs' issue was just the initial comment on the
include/linux/skbuff.h file in patch 2, which could have been more
specific to skbuff and resource management.
The actual kerneldoc comments seem fine to me.



> > They apply cleanly, and I doubt
> > there's much chance of there being a merge conflict for 6.8 -- there
> > are no other changes to the parameterised test macros, and the skb
> > stuff is in its own file.
>
> Right.
>
> > The remaining patches don't apply on top of the kunit branch as-is.
>
> Oh, OK. That makes some sense though, we've had a number of changes in
> the stack this cycle before. I somehow thought the tests were likely
> standalone, but apparently not.
>

I managed to get this to apply locally. The only real changes are to
net/mac80211/ieee80211_i.h  so it may be possible to port this across
to the kselftest/kunit branch if you want, but it doesn't apply
cleanly as-is.

Also, there are a couple of cfg80211 failures:
---
KTAP version 1
1..1
   KTAP version 1
   # Subtest: cfg80211-inform-bss
   # module: cfg80211_tests
   1..2
platform regulatory.0: Direct firmware load for regulatory.db failed
with error -2
cfg80211: failed to load regulatory.db
   ok 1 test_inform_bss_ssid_only
       KTAP version 1
       # Subtest: test_inform_bss_ml_sta
   # test_inform_bss_ml_sta: EXPECTATION FAILED at net/wireless/tests/scan.c:592
   Expected ies->len == 6 + 2 + sizeof(rnr) + 2 + 155 +
mle_basic_common_info.var_len + 5, but
       ies->len == 185 (0xb9)
       6 + 2 + sizeof(rnr) + 2 + 155 + mle_basic_common_info.var_len +
5 == 203 (0xcb)
       not ok 1 no_mld_id
   # test_inform_bss_ml_sta: EXPECTATION FAILED at net/wireless/tests/scan.c:588
   Expected ies->len == 6 + 2 + sizeof(rnr) + 2 + 160 + 2 + 165 +
mle_basic_common_info.var_len + 5, but
       ies->len == 357 (0x165)
       6 + 2 + sizeof(rnr) + 2 + 160 + 2 + 165 +
mle_basic_common_info.var_len + 5 == 376 (0x178)
       not ok 2 mld_id_eq_1
   # test_inform_bss_ml_sta: pass:0 fail:2 skip:0 total:2
   not ok 2 test_inform_bss_ml_sta
# cfg80211-inform-bss: pass:1 fail:1 skip:0 total:2
# Totals: pass:1 fail:2 skip:0 total:3
not ok 1 cfg80211-inform-bss
---

If the failures are because of the missing 'regulatory.db' file, would
it make more sense to have that SKIP the tests instead? (And, if you
actually want to check that it loads correctly, have that be its own,
separate test?)

> > I
> > haven't had a chance to review them properly yet; the initial glance I
> > had didn't show any serious issues (though I think checkpatch
> > suggested some things to 'check').
>
> I can check.

Yeah, it mostly looks like really minor style 'suggestions' around
indenting and putting blank lines in, along with a couple of "you're
reusing a value in a macro, double check this" ones.. I'll paste them
below (but warning, they're a bit verbose).

CHECK: Please use a blank line after function/struct/union/enum declarations
#1142: FILE: net/wireless/tests/scan.c:225:
+};
+KUNIT_ARRAY_PARAM_DESC(gen_new_ie, gen_new_ie_cases, desc)

CHECK: Please use a blank line after function/struct/union/enum declarations
#1330: FILE: net/wireless/tests/scan.c:413:
+};
+KUNIT_ARRAY_PARAM_DESC(inform_bss_ml_sta, inform_bss_ml_sta_cases, desc)

CHECK: Alignment should match open parenthesis
#1489: FILE: net/wireless/tests/scan.c:572:
+       KUNIT_EXPECT_EQ(test, link_bss->beacon_interval,
+                             le16_to_cpu(sta_prof.beacon_int));

CHECK: Alignment should match open parenthesis
#1491: FILE: net/wireless/tests/scan.c:574:
+       KUNIT_EXPECT_EQ(test, link_bss->capability,
+                             le16_to_cpu(sta_prof.capabilities));

CHECK: Macro argument reuse '_freq' - possible side-effects?
#1620: FILE: net/wireless/tests/util.h:10:
+#define CHAN2G(_freq)  { \
+       .band = NL80211_BAND_2GHZ, \
+       .center_freq = (_freq), \
+       .hw_value = (_freq), \
+}

CHECK: Macro argument reuse 'test' - possible side-effects?
#1653: FILE: net/wireless/tests/util.h:43:
+#define T_WIPHY(test, ctx) ({                                          \
+               struct wiphy *__wiphy =                                 \
+                       kunit_alloc_resource(test, t_wiphy_init,        \
+                                            t_wiphy_exit,              \
+                                            GFP_KERNEL, &(ctx));       \
+                                                                       \
+               KUNIT_ASSERT_NOT_NULL(test, __wiphy);                   \
+               __wiphy;                                                \
+       })




>
> > So (once those small issues are finished), I'm okay with the first two
> > patches going in via either tree. The remaining ones are probably best
> > done via the wireless tree, as they seem to depend on some existing
> > patches there, so maybe it makes sense to push everything via
> > wireless.
>
> If not through wireless I doubt we'll get it synchronized for 6.8,
> though of course it's also not needed for 6.8 to have the extra unit
> tests :)
>
> I'll let Shuah decide.
>

I think you should be able to rebase on top of the kunit tree if Shuah
prefers that -- it's a reasonably straightforward conflict. But I
think we'd want to make sure that the various issues above are fixed
(and I'd not want the tests to fail out-of-the-box on the kunit.py UML
setup, though having them depend on !UML or 'SKIP' should be fine).

Cheers,
-- David

[-- Attachment #2: S/MIME Cryptographic Signature --]
[-- Type: application/pkcs7-signature, Size: 4003 bytes --]

^ permalink raw reply	[flat|nested] 19+ messages in thread

* Re: [PATCH 1/6] kunit: add parameter generation macro using description from array
  2023-12-22 10:02   ` David Gow
@ 2023-12-22 14:59     ` Benjamin Berg
  2023-12-23  5:09       ` David Gow
  0 siblings, 1 reply; 19+ messages in thread
From: Benjamin Berg @ 2023-12-22 14:59 UTC (permalink / raw
  To: David Gow; +Cc: linux-wireless, linux-kselftest, kunit-dev

On Fri, 2023-12-22 at 18:02 +0800, David Gow wrote:
> On Wed, 20 Dec 2023 at 23:20, <benjamin@sipsolutions.net> wrote:
> > 
> > From: Benjamin Berg <benjamin.berg@intel.com>
> > 
> > The existing KUNIT_ARRAY_PARAM macro requires a separate function
> > to
> > get the description. However, in a lot of cases the description can
> > just be copied directly from the array. Add a second macro that
> > avoids having to write a static function just for a single strscpy.
> > 
> > Signed-off-by: Benjamin Berg <benjamin.berg@intel.com>
> > ---
> 
> I'm generally pretty happy with this, though note the checkpatch
> warning below.
> 
> There was some discussion at plumbers about expanding the
> parameterised test APIs, so we may need to adjust the implementation
> of this down the line, but I don't think that'll happen for a while,
> so don't worry.
> 
> With the warnings fixed, this is:

I think the checkpatch warning is a false positive. It seems to confuse
the * as a multiplication due to typeof() looking like a function call
rather than a variable declaration.

Benjamin

> Reviewed-by: David Gow <davidgow@google.com>
> 
> I'm okay with this going in via the wireless tree if that's easier;
> certainly there are some conflicts with the later patches in this
> series and the kunit one.
> 
> Cheers,
> -- David
> 
> >  Documentation/dev-tools/kunit/usage.rst | 12 ++++--------
> >  include/kunit/test.h                    | 19 +++++++++++++++++++
> >  2 files changed, 23 insertions(+), 8 deletions(-)
> > 
> > diff --git a/Documentation/dev-tools/kunit/usage.rst
> > b/Documentation/dev-tools/kunit/usage.rst
> > index c27e1646ecd9..b959e5befcbe 100644
> > --- a/Documentation/dev-tools/kunit/usage.rst
> > +++ b/Documentation/dev-tools/kunit/usage.rst
> > @@ -566,13 +566,9 @@ By reusing the same ``cases`` array from
> > above, we can write the test as a
> >                 },
> >         };
> > 
> > -       // Need a helper function to generate a name for each test
> > case.
> > -       static void case_to_desc(const struct sha1_test_case *t,
> > char *desc)
> > -       {
> > -               strcpy(desc, t->str);
> > -       }
> > -       // Creates `sha1_gen_params()` to iterate over `cases`.
> > -       KUNIT_ARRAY_PARAM(sha1, cases, case_to_desc);
> > +       // Creates `sha1_gen_params()` to iterate over `cases`
> > while using
> > +       // the struct member `str` for the case description.
> > +       KUNIT_ARRAY_PARAM_DESC(sha1, cases, str);
> > 
> >         // Looks no different from a normal test.
> >         static void sha1_test(struct kunit *test)
> > @@ -588,7 +584,7 @@ By reusing the same ``cases`` array from above,
> > we can write the test as a
> >         }
> > 
> >         // Instead of KUNIT_CASE, we use KUNIT_CASE_PARAM and pass
> > in the
> > -       // function declared by KUNIT_ARRAY_PARAM.
> > +       // function declared by KUNIT_ARRAY_PARAM or
> > KUNIT_ARRAY_PARAM_DESC.
> >         static struct kunit_case sha1_test_cases[] = {
> >                 KUNIT_CASE_PARAM(sha1_test, sha1_gen_params),
> >                 {}
> > diff --git a/include/kunit/test.h b/include/kunit/test.h
> > index 20ed9f9275c9..2dfa851e1f88 100644
> > --- a/include/kunit/test.h
> > +++ b/include/kunit/test.h
> > @@ -1514,6 +1514,25 @@ do
> > {                                                                  
> >           \
> >                 return
> > NULL;                                                              
> >       \
> >         }
> > 
> > +/**
> > + * KUNIT_ARRAY_PARAM_DESC() - Define test parameter generator from
> > an array.
> > + * @name:  prefix for the test parameter generator function.
> > + * @array: array of test parameters.
> > + * @desc_member: structure member from array element to use as
> > description
> > + *
> > + * Define function @name_gen_params which uses @array to generate
> > parameters.
> > + */
> > +#define KUNIT_ARRAY_PARAM_DESC(name, array,
> > desc_member)                                       \
> > +       static const void *name##_gen_params(const void *prev, char
> > *desc)                      \
> > +      
> > {                                                                  
> >                      \
> > +               typeof((array)[0]) *__next = prev ?
> > ((typeof(__next)) prev) + 1 : (array);      \
> 
> checkpatch is complaining here:
> ERROR: need consistent spacing around '*' (ctx:WxV)
> #71: FILE: include/kunit/test.h:1528:
> 
> +               typeof((array)[0]) *__next = prev ? ((typeof(__next))
> prev) + 1 : (array);      \
> 
> > +               if (__next - (array) < ARRAY_SIZE((array)))
> > {                                   \
> > +                       strscpy(desc, __next->desc_member,
> > KUNIT_PARAM_DESC_SIZE);              \
> > +                       return
> > __next;                                                          \
> > +              
> > }                                                                  
> >              \
> > +               return
> > NULL;                                                              
> >       \
> > +       }
> > +
> >  // TODO(dlatypov@google.com): consider eventually migrating users
> > to explicitly
> >  // include resource.h themselves if they need it.
> >  #include <kunit/resource.h>
> > --
> > 2.43.0
> > 
> > --
> > You received this message because you are subscribed to the Google
> > Groups "KUnit Development" group.
> > To unsubscribe from this group and stop receiving emails from it,
> > send an email to kunit-dev+unsubscribe@googlegroups.com.
> > To view this discussion on the web visit
> > https://groups.google.com/d/msgid/kunit-dev/20231220151952.415232-2-benjamin%40sipsolutions.net
> > .


^ permalink raw reply	[flat|nested] 19+ messages in thread

* Re: [PATCH 0/6] Add some more cfg80211 and mac80211 kunit tests
  2023-12-22 10:09           ` Johannes Berg
  2023-12-22 14:12             ` David Gow
@ 2023-12-22 15:44             ` Shuah Khan
  1 sibling, 0 replies; 19+ messages in thread
From: Shuah Khan @ 2023-12-22 15:44 UTC (permalink / raw
  To: Johannes Berg, David Gow
  Cc: benjamin, linux-wireless, linux-kselftest, kunit-dev,
	Brendan Higgins, Benjamin Berg, Shuah Khan

On 12/22/23 03:09, Johannes Berg wrote:
> Hi,
> 
> Thanks for taking a look!
> 
> On Fri, 2023-12-22 at 18:02 +0800, David Gow wrote:
>> The two initial KUnit patches look fine, modulo a couple of minor docs
>> issues and checkpatch warnings.
> 
> I can run checkpatch (even if I can't always take it seriously), but do
> you want to comment more specifically wrt. the docs?
> 
>> They apply cleanly, and I doubt
>> there's much chance of there being a merge conflict for 6.8 -- there
>> are no other changes to the parameterised test macros, and the skb
>> stuff is in its own file.
> 
> Right.
> 
>> The remaining patches don't apply on top of the kunit branch as-is.
> 
> Oh, OK. That makes some sense though, we've had a number of changes in
> the stack this cycle before. I somehow thought the tests were likely
> standalone, but apparently not.
> 
>> I
>> haven't had a chance to review them properly yet; the initial glance I
>> had didn't show any serious issues (though I think checkpatch
>> suggested some things to 'check').
> 
> I can check.
> 
>> So (once those small issues are finished), I'm okay with the first two
>> patches going in via either tree. The remaining ones are probably best
>> done via the wireless tree, as they seem to depend on some existing
>> patches there, so maybe it makes sense to push everything via
>> wireless.
> 
> If not through wireless I doubt we'll get it synchronized for 6.8,
> though of course it's also not needed for 6.8 to have the extra unit
> tests :)
> 
> I'll let Shuah decide.
> 


Thank you David for the reviews.


johannes, Please take these through wireless - makes it easier for all
of us.

Acked-by: Shuah Khan <skhan@linuxfoundation.org>

thanks,
-- Shuah


^ permalink raw reply	[flat|nested] 19+ messages in thread

* Re: [PATCH 1/6] kunit: add parameter generation macro using description from array
  2023-12-22 14:59     ` Benjamin Berg
@ 2023-12-23  5:09       ` David Gow
  0 siblings, 0 replies; 19+ messages in thread
From: David Gow @ 2023-12-23  5:09 UTC (permalink / raw
  To: Benjamin Berg; +Cc: linux-wireless, linux-kselftest, kunit-dev

[-- Attachment #1: Type: text/plain, Size: 1366 bytes --]

On Fri, 22 Dec 2023 at 23:09, Benjamin Berg <benjamin@sipsolutions.net> wrote:
>
> On Fri, 2023-12-22 at 18:02 +0800, David Gow wrote:
> > On Wed, 20 Dec 2023 at 23:20, <benjamin@sipsolutions.net> wrote:
> > >
> > > From: Benjamin Berg <benjamin.berg@intel.com>
> > >
> > > The existing KUNIT_ARRAY_PARAM macro requires a separate function
> > > to
> > > get the description. However, in a lot of cases the description can
> > > just be copied directly from the array. Add a second macro that
> > > avoids having to write a static function just for a single strscpy.
> > >
> > > Signed-off-by: Benjamin Berg <benjamin.berg@intel.com>
> > > ---
> >
> > I'm generally pretty happy with this, though note the checkpatch
> > warning below.
> >
> > There was some discussion at plumbers about expanding the
> > parameterised test APIs, so we may need to adjust the implementation
> > of this down the line, but I don't think that'll happen for a while,
> > so don't worry.
> >
> > With the warnings fixed, this is:
>
> I think the checkpatch warning is a false positive. It seems to confuse
> the * as a multiplication due to typeof() looking like a function call
> rather than a variable declaration.
>
> Benjamin
>

Ah, yeah: this appears to be due to checkpatch not handling nested ()
within a typeof().

Reviewed-by: David Gow <davidgow@google.com>

Cheers,
-- David

[-- Attachment #2: S/MIME Cryptographic Signature --]
[-- Type: application/pkcs7-signature, Size: 4003 bytes --]

^ permalink raw reply	[flat|nested] 19+ messages in thread

end of thread, other threads:[~2023-12-23  5:09 UTC | newest]

Thread overview: 19+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2023-12-20 15:19 [PATCH 0/6] Add some more cfg80211 and mac80211 kunit tests benjamin
2023-12-20 15:19 ` [PATCH 1/6] kunit: add parameter generation macro using description from array benjamin
2023-12-22 10:02   ` David Gow
2023-12-22 14:59     ` Benjamin Berg
2023-12-23  5:09       ` David Gow
2023-12-20 15:19 ` [PATCH 2/6] kunit: add a convenience allocation wrapper for SKBs benjamin
2023-12-22 10:02   ` David Gow
2023-12-20 15:19 ` [PATCH 3/6] wifi: mac80211: add kunit tests for public action handling benjamin
2023-12-20 15:19 ` [PATCH 4/6] wifi: mac80211: kunit: generalize public action test benjamin
2023-12-20 15:19 ` [PATCH 5/6] wifi: mac80211: kunit: extend MFP tests benjamin
2023-12-20 15:19 ` [PATCH 6/6] wifi: cfg80211: tests: add some scanning related tests benjamin
2023-12-21 19:39 ` [PATCH 0/6] Add some more cfg80211 and mac80211 kunit tests Johannes Berg
2023-12-21 20:06   ` Shuah Khan
2023-12-21 20:40     ` Johannes Berg
2023-12-21 21:47       ` Shuah Khan
2023-12-22 10:02         ` David Gow
2023-12-22 10:09           ` Johannes Berg
2023-12-22 14:12             ` David Gow
2023-12-22 15:44             ` Shuah Khan

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.