Skip to content

Commit d2601e3

Browse files
nbd168jmberg-intel
authored andcommitted
wifi: mac80211_hwsim: add support for multi-radio wiphy
This registers one wiphy radio per supported band. Number of different channels is set per radio. Signed-off-by: Felix Fietkau <[email protected]> Link: https://patch.msgid.link/3a16838bb7a7d1a072bd7c9d586d17f70fcd8a60.1720514221.git-series.nbd@nbd.name Signed-off-by: Johannes Berg <[email protected]>
1 parent 27d4c03 commit d2601e3

File tree

2 files changed

+67
-11
lines changed

2 files changed

+67
-11
lines changed

drivers/net/wireless/virtual/mac80211_hwsim.c

Lines changed: 63 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -69,6 +69,10 @@ static bool mlo;
6969
module_param(mlo, bool, 0444);
7070
MODULE_PARM_DESC(mlo, "Support MLO");
7171

72+
static bool multi_radio;
73+
module_param(multi_radio, bool, 0444);
74+
MODULE_PARM_DESC(mlo, "Support Multiple Radios per wiphy");
75+
7276
/**
7377
* enum hwsim_regtest - the type of regulatory tests we offer
7478
*
@@ -669,6 +673,10 @@ struct mac80211_hwsim_data {
669673
struct ieee80211_iface_limit if_limits[3];
670674
int n_if_limits;
671675

676+
struct ieee80211_iface_combination if_combination_radio;
677+
struct wiphy_radio_freq_range radio_range[NUM_NL80211_BANDS];
678+
struct wiphy_radio radio[NUM_NL80211_BANDS];
679+
672680
u32 ciphers[ARRAY_SIZE(hwsim_ciphers)];
673681

674682
struct mac_address addresses[2];
@@ -917,6 +925,7 @@ static const struct nla_policy hwsim_genl_policy[HWSIM_ATTR_MAX + 1] = {
917925
[HWSIM_ATTR_MLO_SUPPORT] = { .type = NLA_FLAG },
918926
[HWSIM_ATTR_PMSR_SUPPORT] = NLA_POLICY_NESTED(hwsim_pmsr_capa_policy),
919927
[HWSIM_ATTR_PMSR_RESULT] = NLA_POLICY_NESTED(hwsim_pmsr_peers_result_policy),
928+
[HWSIM_ATTR_MULTI_RADIO] = { .type = NLA_FLAG },
920929
};
921930

922931
#if IS_REACHABLE(CONFIG_VIRTIO)
@@ -4018,6 +4027,7 @@ struct hwsim_new_radio_params {
40184027
bool reg_strict;
40194028
bool p2p_device;
40204029
bool use_chanctx;
4030+
bool multi_radio;
40214031
bool destroy_on_close;
40224032
const char *hwname;
40234033
bool no_vif;
@@ -4094,6 +4104,12 @@ static int append_radio_msg(struct sk_buff *skb, int id,
40944104
return ret;
40954105
}
40964106

4107+
if (param->multi_radio) {
4108+
ret = nla_put_flag(skb, HWSIM_ATTR_MULTI_RADIO);
4109+
if (ret < 0)
4110+
return ret;
4111+
}
4112+
40974113
if (param->hwname) {
40984114
ret = nla_put(skb, HWSIM_ATTR_RADIO_NAME,
40994115
strlen(param->hwname), param->hwname);
@@ -5114,6 +5130,7 @@ static int mac80211_hwsim_new_radio(struct genl_info *info,
51145130
struct net *net;
51155131
int idx, i;
51165132
int n_limits = 0;
5133+
int n_bands = 0;
51175134

51185135
if (WARN_ON(param->channels > 1 && !param->use_chanctx))
51195136
return -EINVAL;
@@ -5217,22 +5234,22 @@ static int mac80211_hwsim_new_radio(struct genl_info *info,
52175234
n_limits++;
52185235
}
52195236

5237+
data->if_combination.radar_detect_widths =
5238+
BIT(NL80211_CHAN_WIDTH_5) |
5239+
BIT(NL80211_CHAN_WIDTH_10) |
5240+
BIT(NL80211_CHAN_WIDTH_20_NOHT) |
5241+
BIT(NL80211_CHAN_WIDTH_20) |
5242+
BIT(NL80211_CHAN_WIDTH_40) |
5243+
BIT(NL80211_CHAN_WIDTH_80) |
5244+
BIT(NL80211_CHAN_WIDTH_160);
5245+
52205246
if (data->use_chanctx) {
52215247
hw->wiphy->max_scan_ssids = 255;
52225248
hw->wiphy->max_scan_ie_len = IEEE80211_MAX_DATA_LEN;
52235249
hw->wiphy->max_remain_on_channel_duration = 1000;
5224-
data->if_combination.radar_detect_widths = 0;
52255250
data->if_combination.num_different_channels = data->channels;
52265251
} else {
52275252
data->if_combination.num_different_channels = 1;
5228-
data->if_combination.radar_detect_widths =
5229-
BIT(NL80211_CHAN_WIDTH_5) |
5230-
BIT(NL80211_CHAN_WIDTH_10) |
5231-
BIT(NL80211_CHAN_WIDTH_20_NOHT) |
5232-
BIT(NL80211_CHAN_WIDTH_20) |
5233-
BIT(NL80211_CHAN_WIDTH_40) |
5234-
BIT(NL80211_CHAN_WIDTH_80) |
5235-
BIT(NL80211_CHAN_WIDTH_160);
52365253
}
52375254

52385255
if (!n_limits) {
@@ -5350,6 +5367,9 @@ static int mac80211_hwsim_new_radio(struct genl_info *info,
53505367

53515368
for (band = NL80211_BAND_2GHZ; band < NUM_NL80211_BANDS; band++) {
53525369
struct ieee80211_supported_band *sband = &data->bands[band];
5370+
struct wiphy_radio_freq_range *radio_range;
5371+
const struct ieee80211_channel *c;
5372+
struct wiphy_radio *radio;
53535373

53545374
sband->band = band;
53555375

@@ -5423,8 +5443,36 @@ static int mac80211_hwsim_new_radio(struct genl_info *info,
54235443
mac80211_hwsim_sband_capab(sband);
54245444

54255445
hw->wiphy->bands[band] = sband;
5446+
5447+
if (!param->multi_radio)
5448+
continue;
5449+
5450+
c = sband->channels;
5451+
radio_range = &data->radio_range[n_bands];
5452+
radio_range->start_freq = ieee80211_channel_to_khz(c) - 10000;
5453+
5454+
c += sband->n_channels - 1;
5455+
radio_range->end_freq = ieee80211_channel_to_khz(c) + 10000;
5456+
5457+
radio = &data->radio[n_bands++];
5458+
radio->freq_range = radio_range;
5459+
radio->n_freq_range = 1;
5460+
radio->iface_combinations = &data->if_combination_radio;
5461+
radio->n_iface_combinations = 1;
54265462
}
54275463

5464+
if (param->multi_radio) {
5465+
hw->wiphy->radio = data->radio;
5466+
hw->wiphy->n_radio = n_bands;
5467+
5468+
memcpy(&data->if_combination_radio, &data->if_combination,
5469+
sizeof(data->if_combination));
5470+
data->if_combination.num_different_channels *= n_bands;
5471+
}
5472+
5473+
if (data->use_chanctx)
5474+
data->if_combination.radar_detect_widths = 0;
5475+
54285476
/* By default all radios belong to the first group */
54295477
data->group = 1;
54305478
mutex_init(&data->mutex);
@@ -6042,6 +6090,9 @@ static int hwsim_new_radio_nl(struct sk_buff *msg, struct genl_info *info)
60426090
else
60436091
param.use_chanctx = (param.channels > 1);
60446092

6093+
if (info->attrs[HWSIM_ATTR_MULTI_RADIO])
6094+
param.multi_radio = true;
6095+
60456096
if (info->attrs[HWSIM_ATTR_REG_HINT_ALPHA2])
60466097
param.reg_alpha2 =
60476098
nla_data(info->attrs[HWSIM_ATTR_REG_HINT_ALPHA2]);
@@ -6122,7 +6173,7 @@ static int hwsim_new_radio_nl(struct sk_buff *msg, struct genl_info *info)
61226173

61236174
param.mlo = info->attrs[HWSIM_ATTR_MLO_SUPPORT];
61246175

6125-
if (param.mlo)
6176+
if (param.mlo || param.multi_radio)
61266177
param.use_chanctx = true;
61276178

61286179
if (info->attrs[HWSIM_ATTR_RADIO_NAME]) {
@@ -6815,7 +6866,8 @@ static int __init init_mac80211_hwsim(void)
68156866

68166867
param.p2p_device = support_p2p_device;
68176868
param.mlo = mlo;
6818-
param.use_chanctx = channels > 1 || mlo;
6869+
param.multi_radio = multi_radio;
6870+
param.use_chanctx = channels > 1 || mlo || multi_radio;
68196871
param.iftypes = HWSIM_IFTYPE_SUPPORT_MASK;
68206872
if (param.p2p_device)
68216873
param.iftypes |= BIT(NL80211_IFTYPE_P2P_DEVICE);

drivers/net/wireless/virtual/mac80211_hwsim.h

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -157,6 +157,9 @@ enum hwsim_commands {
157157
* to provide details about peer measurement request (nl80211_peer_measurement_attrs)
158158
* @HWSIM_ATTR_PMSR_RESULT: nested attributed used with %HWSIM_CMD_REPORT_PMSR
159159
* to provide peer measurement result (nl80211_peer_measurement_attrs)
160+
* @HWSIM_ATTR_MULTI_RADIO: Register multiple wiphy radios (flag).
161+
* Adds one radio for each band. Number of supported channels will be set for
162+
* each radio instead of for the wiphy.
160163
* @__HWSIM_ATTR_MAX: enum limit
161164
*/
162165
enum hwsim_attrs {
@@ -189,6 +192,7 @@ enum hwsim_attrs {
189192
HWSIM_ATTR_PMSR_SUPPORT,
190193
HWSIM_ATTR_PMSR_REQUEST,
191194
HWSIM_ATTR_PMSR_RESULT,
195+
HWSIM_ATTR_MULTI_RADIO,
192196
__HWSIM_ATTR_MAX,
193197
};
194198
#define HWSIM_ATTR_MAX (__HWSIM_ATTR_MAX - 1)

0 commit comments

Comments
 (0)