xref: /linux/net/mac80211/chan.c (revision 957e3facd147510f2cf8780e38606f1d707f0e33)
1 /*
2  * mac80211 - channel management
3  */
4 
5 #include <linux/nl80211.h>
6 #include <linux/export.h>
7 #include <linux/rtnetlink.h>
8 #include <net/cfg80211.h>
9 #include "ieee80211_i.h"
10 #include "driver-ops.h"
11 
12 static int ieee80211_chanctx_num_assigned(struct ieee80211_local *local,
13 					  struct ieee80211_chanctx *ctx)
14 {
15 	struct ieee80211_sub_if_data *sdata;
16 	int num = 0;
17 
18 	lockdep_assert_held(&local->chanctx_mtx);
19 
20 	list_for_each_entry(sdata, &ctx->assigned_vifs, assigned_chanctx_list)
21 		num++;
22 
23 	return num;
24 }
25 
26 static int ieee80211_chanctx_num_reserved(struct ieee80211_local *local,
27 					  struct ieee80211_chanctx *ctx)
28 {
29 	struct ieee80211_sub_if_data *sdata;
30 	int num = 0;
31 
32 	lockdep_assert_held(&local->chanctx_mtx);
33 
34 	list_for_each_entry(sdata, &ctx->reserved_vifs, reserved_chanctx_list)
35 		num++;
36 
37 	return num;
38 }
39 
40 int ieee80211_chanctx_refcount(struct ieee80211_local *local,
41 			       struct ieee80211_chanctx *ctx)
42 {
43 	return ieee80211_chanctx_num_assigned(local, ctx) +
44 	       ieee80211_chanctx_num_reserved(local, ctx);
45 }
46 
47 static int ieee80211_num_chanctx(struct ieee80211_local *local)
48 {
49 	struct ieee80211_chanctx *ctx;
50 	int num = 0;
51 
52 	lockdep_assert_held(&local->chanctx_mtx);
53 
54 	list_for_each_entry(ctx, &local->chanctx_list, list)
55 		num++;
56 
57 	return num;
58 }
59 
60 static bool ieee80211_can_create_new_chanctx(struct ieee80211_local *local)
61 {
62 	lockdep_assert_held(&local->chanctx_mtx);
63 	return ieee80211_num_chanctx(local) < ieee80211_max_num_channels(local);
64 }
65 
66 static struct ieee80211_chanctx *
67 ieee80211_vif_get_chanctx(struct ieee80211_sub_if_data *sdata)
68 {
69 	struct ieee80211_local *local __maybe_unused = sdata->local;
70 	struct ieee80211_chanctx_conf *conf;
71 
72 	conf = rcu_dereference_protected(sdata->vif.chanctx_conf,
73 					 lockdep_is_held(&local->chanctx_mtx));
74 	if (!conf)
75 		return NULL;
76 
77 	return container_of(conf, struct ieee80211_chanctx, conf);
78 }
79 
80 static const struct cfg80211_chan_def *
81 ieee80211_chanctx_reserved_chandef(struct ieee80211_local *local,
82 				   struct ieee80211_chanctx *ctx,
83 				   const struct cfg80211_chan_def *compat)
84 {
85 	struct ieee80211_sub_if_data *sdata;
86 
87 	lockdep_assert_held(&local->chanctx_mtx);
88 
89 	list_for_each_entry(sdata, &ctx->reserved_vifs,
90 			    reserved_chanctx_list) {
91 		if (!compat)
92 			compat = &sdata->reserved_chandef;
93 
94 		compat = cfg80211_chandef_compatible(&sdata->reserved_chandef,
95 						     compat);
96 		if (!compat)
97 			break;
98 	}
99 
100 	return compat;
101 }
102 
103 static const struct cfg80211_chan_def *
104 ieee80211_chanctx_non_reserved_chandef(struct ieee80211_local *local,
105 				       struct ieee80211_chanctx *ctx,
106 				       const struct cfg80211_chan_def *compat)
107 {
108 	struct ieee80211_sub_if_data *sdata;
109 
110 	lockdep_assert_held(&local->chanctx_mtx);
111 
112 	list_for_each_entry(sdata, &ctx->assigned_vifs,
113 			    assigned_chanctx_list) {
114 		if (sdata->reserved_chanctx != NULL)
115 			continue;
116 
117 		if (!compat)
118 			compat = &sdata->vif.bss_conf.chandef;
119 
120 		compat = cfg80211_chandef_compatible(
121 				&sdata->vif.bss_conf.chandef, compat);
122 		if (!compat)
123 			break;
124 	}
125 
126 	return compat;
127 }
128 
129 static const struct cfg80211_chan_def *
130 ieee80211_chanctx_combined_chandef(struct ieee80211_local *local,
131 				   struct ieee80211_chanctx *ctx,
132 				   const struct cfg80211_chan_def *compat)
133 {
134 	lockdep_assert_held(&local->chanctx_mtx);
135 
136 	compat = ieee80211_chanctx_reserved_chandef(local, ctx, compat);
137 	if (!compat)
138 		return NULL;
139 
140 	compat = ieee80211_chanctx_non_reserved_chandef(local, ctx, compat);
141 	if (!compat)
142 		return NULL;
143 
144 	return compat;
145 }
146 
147 static bool
148 ieee80211_chanctx_can_reserve_chandef(struct ieee80211_local *local,
149 				      struct ieee80211_chanctx *ctx,
150 				      const struct cfg80211_chan_def *def)
151 {
152 	lockdep_assert_held(&local->chanctx_mtx);
153 
154 	if (ieee80211_chanctx_combined_chandef(local, ctx, def))
155 		return true;
156 
157 	if (!list_empty(&ctx->reserved_vifs) &&
158 	    ieee80211_chanctx_reserved_chandef(local, ctx, def))
159 		return true;
160 
161 	return false;
162 }
163 
164 static struct ieee80211_chanctx *
165 ieee80211_find_reservation_chanctx(struct ieee80211_local *local,
166 				   const struct cfg80211_chan_def *chandef,
167 				   enum ieee80211_chanctx_mode mode)
168 {
169 	struct ieee80211_chanctx *ctx;
170 
171 	lockdep_assert_held(&local->chanctx_mtx);
172 
173 	if (mode == IEEE80211_CHANCTX_EXCLUSIVE)
174 		return NULL;
175 
176 	list_for_each_entry(ctx, &local->chanctx_list, list) {
177 		if (ctx->replace_state == IEEE80211_CHANCTX_WILL_BE_REPLACED)
178 			continue;
179 
180 		if (ctx->mode == IEEE80211_CHANCTX_EXCLUSIVE)
181 			continue;
182 
183 		if (!ieee80211_chanctx_can_reserve_chandef(local, ctx,
184 							   chandef))
185 			continue;
186 
187 		return ctx;
188 	}
189 
190 	return NULL;
191 }
192 
193 static enum nl80211_chan_width ieee80211_get_sta_bw(struct ieee80211_sta *sta)
194 {
195 	switch (sta->bandwidth) {
196 	case IEEE80211_STA_RX_BW_20:
197 		if (sta->ht_cap.ht_supported)
198 			return NL80211_CHAN_WIDTH_20;
199 		else
200 			return NL80211_CHAN_WIDTH_20_NOHT;
201 	case IEEE80211_STA_RX_BW_40:
202 		return NL80211_CHAN_WIDTH_40;
203 	case IEEE80211_STA_RX_BW_80:
204 		return NL80211_CHAN_WIDTH_80;
205 	case IEEE80211_STA_RX_BW_160:
206 		/*
207 		 * This applied for both 160 and 80+80. since we use
208 		 * the returned value to consider degradation of
209 		 * ctx->conf.min_def, we have to make sure to take
210 		 * the bigger one (NL80211_CHAN_WIDTH_160).
211 		 * Otherwise we might try degrading even when not
212 		 * needed, as the max required sta_bw returned (80+80)
213 		 * might be smaller than the configured bw (160).
214 		 */
215 		return NL80211_CHAN_WIDTH_160;
216 	default:
217 		WARN_ON(1);
218 		return NL80211_CHAN_WIDTH_20;
219 	}
220 }
221 
222 static enum nl80211_chan_width
223 ieee80211_get_max_required_bw(struct ieee80211_sub_if_data *sdata)
224 {
225 	enum nl80211_chan_width max_bw = NL80211_CHAN_WIDTH_20_NOHT;
226 	struct sta_info *sta;
227 
228 	rcu_read_lock();
229 	list_for_each_entry_rcu(sta, &sdata->local->sta_list, list) {
230 		if (sdata != sta->sdata &&
231 		    !(sta->sdata->bss && sta->sdata->bss == sdata->bss))
232 			continue;
233 
234 		if (!sta->uploaded)
235 			continue;
236 
237 		max_bw = max(max_bw, ieee80211_get_sta_bw(&sta->sta));
238 	}
239 	rcu_read_unlock();
240 
241 	return max_bw;
242 }
243 
244 static enum nl80211_chan_width
245 ieee80211_get_chanctx_max_required_bw(struct ieee80211_local *local,
246 				      struct ieee80211_chanctx_conf *conf)
247 {
248 	struct ieee80211_sub_if_data *sdata;
249 	enum nl80211_chan_width max_bw = NL80211_CHAN_WIDTH_20_NOHT;
250 
251 	rcu_read_lock();
252 	list_for_each_entry_rcu(sdata, &local->interfaces, list) {
253 		struct ieee80211_vif *vif = &sdata->vif;
254 		enum nl80211_chan_width width = NL80211_CHAN_WIDTH_20_NOHT;
255 
256 		if (!ieee80211_sdata_running(sdata))
257 			continue;
258 
259 		if (rcu_access_pointer(sdata->vif.chanctx_conf) != conf)
260 			continue;
261 
262 		switch (vif->type) {
263 		case NL80211_IFTYPE_AP:
264 		case NL80211_IFTYPE_AP_VLAN:
265 			width = ieee80211_get_max_required_bw(sdata);
266 			break;
267 		case NL80211_IFTYPE_P2P_DEVICE:
268 			continue;
269 		case NL80211_IFTYPE_STATION:
270 		case NL80211_IFTYPE_ADHOC:
271 		case NL80211_IFTYPE_WDS:
272 		case NL80211_IFTYPE_MESH_POINT:
273 		case NL80211_IFTYPE_OCB:
274 			width = vif->bss_conf.chandef.width;
275 			break;
276 		case NL80211_IFTYPE_UNSPECIFIED:
277 		case NUM_NL80211_IFTYPES:
278 		case NL80211_IFTYPE_MONITOR:
279 		case NL80211_IFTYPE_P2P_CLIENT:
280 		case NL80211_IFTYPE_P2P_GO:
281 			WARN_ON_ONCE(1);
282 		}
283 		max_bw = max(max_bw, width);
284 	}
285 
286 	/* use the configured bandwidth in case of monitor interface */
287 	sdata = rcu_dereference(local->monitor_sdata);
288 	if (sdata && rcu_access_pointer(sdata->vif.chanctx_conf) == conf)
289 		max_bw = max(max_bw, conf->def.width);
290 
291 	rcu_read_unlock();
292 
293 	return max_bw;
294 }
295 
296 /*
297  * recalc the min required chan width of the channel context, which is
298  * the max of min required widths of all the interfaces bound to this
299  * channel context.
300  */
301 void ieee80211_recalc_chanctx_min_def(struct ieee80211_local *local,
302 				      struct ieee80211_chanctx *ctx)
303 {
304 	enum nl80211_chan_width max_bw;
305 	struct cfg80211_chan_def min_def;
306 
307 	lockdep_assert_held(&local->chanctx_mtx);
308 
309 	/* don't optimize 5MHz, 10MHz, and radar_enabled confs */
310 	if (ctx->conf.def.width == NL80211_CHAN_WIDTH_5 ||
311 	    ctx->conf.def.width == NL80211_CHAN_WIDTH_10 ||
312 	    ctx->conf.radar_enabled) {
313 		ctx->conf.min_def = ctx->conf.def;
314 		return;
315 	}
316 
317 	max_bw = ieee80211_get_chanctx_max_required_bw(local, &ctx->conf);
318 
319 	/* downgrade chandef up to max_bw */
320 	min_def = ctx->conf.def;
321 	while (min_def.width > max_bw)
322 		ieee80211_chandef_downgrade(&min_def);
323 
324 	if (cfg80211_chandef_identical(&ctx->conf.min_def, &min_def))
325 		return;
326 
327 	ctx->conf.min_def = min_def;
328 	if (!ctx->driver_present)
329 		return;
330 
331 	drv_change_chanctx(local, ctx, IEEE80211_CHANCTX_CHANGE_MIN_WIDTH);
332 }
333 
334 static void ieee80211_change_chanctx(struct ieee80211_local *local,
335 				     struct ieee80211_chanctx *ctx,
336 				     const struct cfg80211_chan_def *chandef)
337 {
338 	if (cfg80211_chandef_identical(&ctx->conf.def, chandef))
339 		return;
340 
341 	WARN_ON(!cfg80211_chandef_compatible(&ctx->conf.def, chandef));
342 
343 	ctx->conf.def = *chandef;
344 	drv_change_chanctx(local, ctx, IEEE80211_CHANCTX_CHANGE_WIDTH);
345 	ieee80211_recalc_chanctx_min_def(local, ctx);
346 
347 	if (!local->use_chanctx) {
348 		local->_oper_chandef = *chandef;
349 		ieee80211_hw_config(local, 0);
350 	}
351 }
352 
353 static struct ieee80211_chanctx *
354 ieee80211_find_chanctx(struct ieee80211_local *local,
355 		       const struct cfg80211_chan_def *chandef,
356 		       enum ieee80211_chanctx_mode mode)
357 {
358 	struct ieee80211_chanctx *ctx;
359 
360 	lockdep_assert_held(&local->chanctx_mtx);
361 
362 	if (mode == IEEE80211_CHANCTX_EXCLUSIVE)
363 		return NULL;
364 
365 	list_for_each_entry(ctx, &local->chanctx_list, list) {
366 		const struct cfg80211_chan_def *compat;
367 
368 		if (ctx->replace_state != IEEE80211_CHANCTX_REPLACE_NONE)
369 			continue;
370 
371 		if (ctx->mode == IEEE80211_CHANCTX_EXCLUSIVE)
372 			continue;
373 
374 		compat = cfg80211_chandef_compatible(&ctx->conf.def, chandef);
375 		if (!compat)
376 			continue;
377 
378 		compat = ieee80211_chanctx_reserved_chandef(local, ctx,
379 							    compat);
380 		if (!compat)
381 			continue;
382 
383 		ieee80211_change_chanctx(local, ctx, compat);
384 
385 		return ctx;
386 	}
387 
388 	return NULL;
389 }
390 
391 static bool ieee80211_is_radar_required(struct ieee80211_local *local)
392 {
393 	struct ieee80211_sub_if_data *sdata;
394 
395 	lockdep_assert_held(&local->mtx);
396 
397 	rcu_read_lock();
398 	list_for_each_entry_rcu(sdata, &local->interfaces, list) {
399 		if (sdata->radar_required) {
400 			rcu_read_unlock();
401 			return true;
402 		}
403 	}
404 	rcu_read_unlock();
405 
406 	return false;
407 }
408 
409 static struct ieee80211_chanctx *
410 ieee80211_alloc_chanctx(struct ieee80211_local *local,
411 			const struct cfg80211_chan_def *chandef,
412 			enum ieee80211_chanctx_mode mode)
413 {
414 	struct ieee80211_chanctx *ctx;
415 
416 	lockdep_assert_held(&local->chanctx_mtx);
417 
418 	ctx = kzalloc(sizeof(*ctx) + local->hw.chanctx_data_size, GFP_KERNEL);
419 	if (!ctx)
420 		return NULL;
421 
422 	INIT_LIST_HEAD(&ctx->assigned_vifs);
423 	INIT_LIST_HEAD(&ctx->reserved_vifs);
424 	ctx->conf.def = *chandef;
425 	ctx->conf.rx_chains_static = 1;
426 	ctx->conf.rx_chains_dynamic = 1;
427 	ctx->mode = mode;
428 	ctx->conf.radar_enabled = ieee80211_is_radar_required(local);
429 	ieee80211_recalc_chanctx_min_def(local, ctx);
430 
431 	return ctx;
432 }
433 
434 static int ieee80211_add_chanctx(struct ieee80211_local *local,
435 				 struct ieee80211_chanctx *ctx)
436 {
437 	u32 changed;
438 	int err;
439 
440 	lockdep_assert_held(&local->mtx);
441 	lockdep_assert_held(&local->chanctx_mtx);
442 
443 	if (!local->use_chanctx)
444 		local->hw.conf.radar_enabled = ctx->conf.radar_enabled;
445 
446 	/* turn idle off *before* setting channel -- some drivers need that */
447 	changed = ieee80211_idle_off(local);
448 	if (changed)
449 		ieee80211_hw_config(local, changed);
450 
451 	if (!local->use_chanctx) {
452 		local->_oper_chandef = ctx->conf.def;
453 		ieee80211_hw_config(local, IEEE80211_CONF_CHANGE_CHANNEL);
454 	} else {
455 		err = drv_add_chanctx(local, ctx);
456 		if (err) {
457 			ieee80211_recalc_idle(local);
458 			return err;
459 		}
460 	}
461 
462 	return 0;
463 }
464 
465 static struct ieee80211_chanctx *
466 ieee80211_new_chanctx(struct ieee80211_local *local,
467 		      const struct cfg80211_chan_def *chandef,
468 		      enum ieee80211_chanctx_mode mode)
469 {
470 	struct ieee80211_chanctx *ctx;
471 	int err;
472 
473 	lockdep_assert_held(&local->mtx);
474 	lockdep_assert_held(&local->chanctx_mtx);
475 
476 	ctx = ieee80211_alloc_chanctx(local, chandef, mode);
477 	if (!ctx)
478 		return ERR_PTR(-ENOMEM);
479 
480 	err = ieee80211_add_chanctx(local, ctx);
481 	if (err) {
482 		kfree(ctx);
483 		return ERR_PTR(err);
484 	}
485 
486 	list_add_rcu(&ctx->list, &local->chanctx_list);
487 	return ctx;
488 }
489 
490 static void ieee80211_del_chanctx(struct ieee80211_local *local,
491 				  struct ieee80211_chanctx *ctx)
492 {
493 	lockdep_assert_held(&local->chanctx_mtx);
494 
495 	if (!local->use_chanctx) {
496 		struct cfg80211_chan_def *chandef = &local->_oper_chandef;
497 		chandef->width = NL80211_CHAN_WIDTH_20_NOHT;
498 		chandef->center_freq1 = chandef->chan->center_freq;
499 		chandef->center_freq2 = 0;
500 
501 		/* NOTE: Disabling radar is only valid here for
502 		 * single channel context. To be sure, check it ...
503 		 */
504 		WARN_ON(local->hw.conf.radar_enabled &&
505 			!list_empty(&local->chanctx_list));
506 
507 		local->hw.conf.radar_enabled = false;
508 
509 		ieee80211_hw_config(local, IEEE80211_CONF_CHANGE_CHANNEL);
510 	} else {
511 		drv_remove_chanctx(local, ctx);
512 	}
513 
514 	ieee80211_recalc_idle(local);
515 }
516 
517 static void ieee80211_free_chanctx(struct ieee80211_local *local,
518 				   struct ieee80211_chanctx *ctx)
519 {
520 	lockdep_assert_held(&local->chanctx_mtx);
521 
522 	WARN_ON_ONCE(ieee80211_chanctx_refcount(local, ctx) != 0);
523 
524 	list_del_rcu(&ctx->list);
525 	ieee80211_del_chanctx(local, ctx);
526 	kfree_rcu(ctx, rcu_head);
527 }
528 
529 static void ieee80211_recalc_chanctx_chantype(struct ieee80211_local *local,
530 					      struct ieee80211_chanctx *ctx)
531 {
532 	struct ieee80211_chanctx_conf *conf = &ctx->conf;
533 	struct ieee80211_sub_if_data *sdata;
534 	const struct cfg80211_chan_def *compat = NULL;
535 
536 	lockdep_assert_held(&local->chanctx_mtx);
537 
538 	rcu_read_lock();
539 	list_for_each_entry_rcu(sdata, &local->interfaces, list) {
540 
541 		if (!ieee80211_sdata_running(sdata))
542 			continue;
543 		if (rcu_access_pointer(sdata->vif.chanctx_conf) != conf)
544 			continue;
545 		if (sdata->vif.type == NL80211_IFTYPE_AP_VLAN)
546 			continue;
547 
548 		if (!compat)
549 			compat = &sdata->vif.bss_conf.chandef;
550 
551 		compat = cfg80211_chandef_compatible(
552 				&sdata->vif.bss_conf.chandef, compat);
553 		if (WARN_ON_ONCE(!compat))
554 			break;
555 	}
556 	rcu_read_unlock();
557 
558 	if (!compat)
559 		return;
560 
561 	ieee80211_change_chanctx(local, ctx, compat);
562 }
563 
564 static void ieee80211_recalc_radar_chanctx(struct ieee80211_local *local,
565 					   struct ieee80211_chanctx *chanctx)
566 {
567 	bool radar_enabled;
568 
569 	lockdep_assert_held(&local->chanctx_mtx);
570 	/* for setting local->radar_detect_enabled */
571 	lockdep_assert_held(&local->mtx);
572 
573 	radar_enabled = ieee80211_is_radar_required(local);
574 
575 	if (radar_enabled == chanctx->conf.radar_enabled)
576 		return;
577 
578 	chanctx->conf.radar_enabled = radar_enabled;
579 	local->radar_detect_enabled = chanctx->conf.radar_enabled;
580 
581 	if (!local->use_chanctx) {
582 		local->hw.conf.radar_enabled = chanctx->conf.radar_enabled;
583 		ieee80211_hw_config(local, IEEE80211_CONF_CHANGE_CHANNEL);
584 	}
585 
586 	drv_change_chanctx(local, chanctx, IEEE80211_CHANCTX_CHANGE_RADAR);
587 }
588 
589 static int ieee80211_assign_vif_chanctx(struct ieee80211_sub_if_data *sdata,
590 					struct ieee80211_chanctx *new_ctx)
591 {
592 	struct ieee80211_local *local = sdata->local;
593 	struct ieee80211_chanctx_conf *conf;
594 	struct ieee80211_chanctx *curr_ctx = NULL;
595 	int ret = 0;
596 
597 	conf = rcu_dereference_protected(sdata->vif.chanctx_conf,
598 					 lockdep_is_held(&local->chanctx_mtx));
599 
600 	if (conf) {
601 		curr_ctx = container_of(conf, struct ieee80211_chanctx, conf);
602 
603 		drv_unassign_vif_chanctx(local, sdata, curr_ctx);
604 		conf = NULL;
605 		list_del(&sdata->assigned_chanctx_list);
606 	}
607 
608 	if (new_ctx) {
609 		ret = drv_assign_vif_chanctx(local, sdata, new_ctx);
610 		if (ret)
611 			goto out;
612 
613 		conf = &new_ctx->conf;
614 		list_add(&sdata->assigned_chanctx_list,
615 			 &new_ctx->assigned_vifs);
616 	}
617 
618 out:
619 	rcu_assign_pointer(sdata->vif.chanctx_conf, conf);
620 
621 	sdata->vif.bss_conf.idle = !conf;
622 
623 	if (curr_ctx && ieee80211_chanctx_num_assigned(local, curr_ctx) > 0) {
624 		ieee80211_recalc_chanctx_chantype(local, curr_ctx);
625 		ieee80211_recalc_smps_chanctx(local, curr_ctx);
626 		ieee80211_recalc_radar_chanctx(local, curr_ctx);
627 		ieee80211_recalc_chanctx_min_def(local, curr_ctx);
628 	}
629 
630 	if (new_ctx && ieee80211_chanctx_num_assigned(local, new_ctx) > 0) {
631 		ieee80211_recalc_txpower(sdata);
632 		ieee80211_recalc_chanctx_min_def(local, new_ctx);
633 	}
634 
635 	if (sdata->vif.type != NL80211_IFTYPE_P2P_DEVICE &&
636 	    sdata->vif.type != NL80211_IFTYPE_MONITOR)
637 		ieee80211_bss_info_change_notify(sdata,
638 						 BSS_CHANGED_IDLE);
639 
640 	return ret;
641 }
642 
643 void ieee80211_recalc_smps_chanctx(struct ieee80211_local *local,
644 				   struct ieee80211_chanctx *chanctx)
645 {
646 	struct ieee80211_sub_if_data *sdata;
647 	u8 rx_chains_static, rx_chains_dynamic;
648 
649 	lockdep_assert_held(&local->chanctx_mtx);
650 
651 	rx_chains_static = 1;
652 	rx_chains_dynamic = 1;
653 
654 	rcu_read_lock();
655 	list_for_each_entry_rcu(sdata, &local->interfaces, list) {
656 		u8 needed_static, needed_dynamic;
657 
658 		if (!ieee80211_sdata_running(sdata))
659 			continue;
660 
661 		if (rcu_access_pointer(sdata->vif.chanctx_conf) !=
662 						&chanctx->conf)
663 			continue;
664 
665 		switch (sdata->vif.type) {
666 		case NL80211_IFTYPE_P2P_DEVICE:
667 			continue;
668 		case NL80211_IFTYPE_STATION:
669 			if (!sdata->u.mgd.associated)
670 				continue;
671 			break;
672 		case NL80211_IFTYPE_AP_VLAN:
673 			continue;
674 		case NL80211_IFTYPE_AP:
675 		case NL80211_IFTYPE_ADHOC:
676 		case NL80211_IFTYPE_WDS:
677 		case NL80211_IFTYPE_MESH_POINT:
678 		case NL80211_IFTYPE_OCB:
679 			break;
680 		default:
681 			WARN_ON_ONCE(1);
682 		}
683 
684 		switch (sdata->smps_mode) {
685 		default:
686 			WARN_ONCE(1, "Invalid SMPS mode %d\n",
687 				  sdata->smps_mode);
688 			/* fall through */
689 		case IEEE80211_SMPS_OFF:
690 			needed_static = sdata->needed_rx_chains;
691 			needed_dynamic = sdata->needed_rx_chains;
692 			break;
693 		case IEEE80211_SMPS_DYNAMIC:
694 			needed_static = 1;
695 			needed_dynamic = sdata->needed_rx_chains;
696 			break;
697 		case IEEE80211_SMPS_STATIC:
698 			needed_static = 1;
699 			needed_dynamic = 1;
700 			break;
701 		}
702 
703 		rx_chains_static = max(rx_chains_static, needed_static);
704 		rx_chains_dynamic = max(rx_chains_dynamic, needed_dynamic);
705 	}
706 
707 	/* Disable SMPS for the monitor interface */
708 	sdata = rcu_dereference(local->monitor_sdata);
709 	if (sdata &&
710 	    rcu_access_pointer(sdata->vif.chanctx_conf) == &chanctx->conf)
711 		rx_chains_dynamic = rx_chains_static = local->rx_chains;
712 
713 	rcu_read_unlock();
714 
715 	if (!local->use_chanctx) {
716 		if (rx_chains_static > 1)
717 			local->smps_mode = IEEE80211_SMPS_OFF;
718 		else if (rx_chains_dynamic > 1)
719 			local->smps_mode = IEEE80211_SMPS_DYNAMIC;
720 		else
721 			local->smps_mode = IEEE80211_SMPS_STATIC;
722 		ieee80211_hw_config(local, 0);
723 	}
724 
725 	if (rx_chains_static == chanctx->conf.rx_chains_static &&
726 	    rx_chains_dynamic == chanctx->conf.rx_chains_dynamic)
727 		return;
728 
729 	chanctx->conf.rx_chains_static = rx_chains_static;
730 	chanctx->conf.rx_chains_dynamic = rx_chains_dynamic;
731 	drv_change_chanctx(local, chanctx, IEEE80211_CHANCTX_CHANGE_RX_CHAINS);
732 }
733 
734 static void
735 __ieee80211_vif_copy_chanctx_to_vlans(struct ieee80211_sub_if_data *sdata,
736 				      bool clear)
737 {
738 	struct ieee80211_local *local __maybe_unused = sdata->local;
739 	struct ieee80211_sub_if_data *vlan;
740 	struct ieee80211_chanctx_conf *conf;
741 
742 	if (WARN_ON(sdata->vif.type != NL80211_IFTYPE_AP))
743 		return;
744 
745 	lockdep_assert_held(&local->mtx);
746 
747 	/* Check that conf exists, even when clearing this function
748 	 * must be called with the AP's channel context still there
749 	 * as it would otherwise cause VLANs to have an invalid
750 	 * channel context pointer for a while, possibly pointing
751 	 * to a channel context that has already been freed.
752 	 */
753 	conf = rcu_dereference_protected(sdata->vif.chanctx_conf,
754 					 lockdep_is_held(&local->chanctx_mtx));
755 	WARN_ON(!conf);
756 
757 	if (clear)
758 		conf = NULL;
759 
760 	list_for_each_entry(vlan, &sdata->u.ap.vlans, u.vlan.list)
761 		rcu_assign_pointer(vlan->vif.chanctx_conf, conf);
762 }
763 
764 void ieee80211_vif_copy_chanctx_to_vlans(struct ieee80211_sub_if_data *sdata,
765 					 bool clear)
766 {
767 	struct ieee80211_local *local = sdata->local;
768 
769 	mutex_lock(&local->chanctx_mtx);
770 
771 	__ieee80211_vif_copy_chanctx_to_vlans(sdata, clear);
772 
773 	mutex_unlock(&local->chanctx_mtx);
774 }
775 
776 int ieee80211_vif_unreserve_chanctx(struct ieee80211_sub_if_data *sdata)
777 {
778 	struct ieee80211_chanctx *ctx = sdata->reserved_chanctx;
779 
780 	lockdep_assert_held(&sdata->local->chanctx_mtx);
781 
782 	if (WARN_ON(!ctx))
783 		return -EINVAL;
784 
785 	list_del(&sdata->reserved_chanctx_list);
786 	sdata->reserved_chanctx = NULL;
787 
788 	if (ieee80211_chanctx_refcount(sdata->local, ctx) == 0) {
789 		if (ctx->replace_state == IEEE80211_CHANCTX_REPLACES_OTHER) {
790 			if (WARN_ON(!ctx->replace_ctx))
791 				return -EINVAL;
792 
793 			WARN_ON(ctx->replace_ctx->replace_state !=
794 			        IEEE80211_CHANCTX_WILL_BE_REPLACED);
795 			WARN_ON(ctx->replace_ctx->replace_ctx != ctx);
796 
797 			ctx->replace_ctx->replace_ctx = NULL;
798 			ctx->replace_ctx->replace_state =
799 					IEEE80211_CHANCTX_REPLACE_NONE;
800 
801 			list_del_rcu(&ctx->list);
802 			kfree_rcu(ctx, rcu_head);
803 		} else {
804 			ieee80211_free_chanctx(sdata->local, ctx);
805 		}
806 	}
807 
808 	return 0;
809 }
810 
811 int ieee80211_vif_reserve_chanctx(struct ieee80211_sub_if_data *sdata,
812 				  const struct cfg80211_chan_def *chandef,
813 				  enum ieee80211_chanctx_mode mode,
814 				  bool radar_required)
815 {
816 	struct ieee80211_local *local = sdata->local;
817 	struct ieee80211_chanctx *new_ctx, *curr_ctx, *ctx;
818 
819 	lockdep_assert_held(&local->chanctx_mtx);
820 
821 	curr_ctx = ieee80211_vif_get_chanctx(sdata);
822 	if (curr_ctx && local->use_chanctx && !local->ops->switch_vif_chanctx)
823 		return -ENOTSUPP;
824 
825 	new_ctx = ieee80211_find_reservation_chanctx(local, chandef, mode);
826 	if (!new_ctx) {
827 		if (ieee80211_can_create_new_chanctx(local)) {
828 			new_ctx = ieee80211_new_chanctx(local, chandef, mode);
829 			if (IS_ERR(new_ctx))
830 				return PTR_ERR(new_ctx);
831 		} else {
832 			if (!curr_ctx ||
833 			    (curr_ctx->replace_state ==
834 			     IEEE80211_CHANCTX_WILL_BE_REPLACED) ||
835 			    !list_empty(&curr_ctx->reserved_vifs)) {
836 				/*
837 				 * Another vif already requested this context
838 				 * for a reservation. Find another one hoping
839 				 * all vifs assigned to it will also switch
840 				 * soon enough.
841 				 *
842 				 * TODO: This needs a little more work as some
843 				 * cases (more than 2 chanctx capable devices)
844 				 * may fail which could otherwise succeed
845 				 * provided some channel context juggling was
846 				 * performed.
847 				 *
848 				 * Consider ctx1..3, vif1..6, each ctx has 2
849 				 * vifs. vif1 and vif2 from ctx1 request new
850 				 * different chandefs starting 2 in-place
851 				 * reserations with ctx4 and ctx5 replacing
852 				 * ctx1 and ctx2 respectively. Next vif5 and
853 				 * vif6 from ctx3 reserve ctx4. If vif3 and
854 				 * vif4 remain on ctx2 as they are then this
855 				 * fails unless `replace_ctx` from ctx5 is
856 				 * replaced with ctx3.
857 				 */
858 				list_for_each_entry(ctx, &local->chanctx_list,
859 						    list) {
860 					if (ctx->replace_state !=
861 					    IEEE80211_CHANCTX_REPLACE_NONE)
862 						continue;
863 
864 					if (!list_empty(&ctx->reserved_vifs))
865 						continue;
866 
867 					curr_ctx = ctx;
868 					break;
869 				}
870 			}
871 
872 			/*
873 			 * If that's true then all available contexts already
874 			 * have reservations and cannot be used.
875 			 */
876 			if (!curr_ctx ||
877 			    (curr_ctx->replace_state ==
878 			     IEEE80211_CHANCTX_WILL_BE_REPLACED) ||
879 			    !list_empty(&curr_ctx->reserved_vifs))
880 				return -EBUSY;
881 
882 			new_ctx = ieee80211_alloc_chanctx(local, chandef, mode);
883 			if (!new_ctx)
884 				return -ENOMEM;
885 
886 			new_ctx->replace_ctx = curr_ctx;
887 			new_ctx->replace_state =
888 					IEEE80211_CHANCTX_REPLACES_OTHER;
889 
890 			curr_ctx->replace_ctx = new_ctx;
891 			curr_ctx->replace_state =
892 					IEEE80211_CHANCTX_WILL_BE_REPLACED;
893 
894 			list_add_rcu(&new_ctx->list, &local->chanctx_list);
895 		}
896 	}
897 
898 	list_add(&sdata->reserved_chanctx_list, &new_ctx->reserved_vifs);
899 	sdata->reserved_chanctx = new_ctx;
900 	sdata->reserved_chandef = *chandef;
901 	sdata->reserved_radar_required = radar_required;
902 	sdata->reserved_ready = false;
903 
904 	return 0;
905 }
906 
907 static void
908 ieee80211_vif_chanctx_reservation_complete(struct ieee80211_sub_if_data *sdata)
909 {
910 	switch (sdata->vif.type) {
911 	case NL80211_IFTYPE_ADHOC:
912 	case NL80211_IFTYPE_AP:
913 	case NL80211_IFTYPE_MESH_POINT:
914 	case NL80211_IFTYPE_OCB:
915 		ieee80211_queue_work(&sdata->local->hw,
916 				     &sdata->csa_finalize_work);
917 		break;
918 	case NL80211_IFTYPE_STATION:
919 		ieee80211_queue_work(&sdata->local->hw,
920 				     &sdata->u.mgd.chswitch_work);
921 		break;
922 	case NL80211_IFTYPE_UNSPECIFIED:
923 	case NL80211_IFTYPE_AP_VLAN:
924 	case NL80211_IFTYPE_WDS:
925 	case NL80211_IFTYPE_MONITOR:
926 	case NL80211_IFTYPE_P2P_CLIENT:
927 	case NL80211_IFTYPE_P2P_GO:
928 	case NL80211_IFTYPE_P2P_DEVICE:
929 	case NUM_NL80211_IFTYPES:
930 		WARN_ON(1);
931 		break;
932 	}
933 }
934 
935 static void
936 ieee80211_vif_update_chandef(struct ieee80211_sub_if_data *sdata,
937 			     const struct cfg80211_chan_def *chandef)
938 {
939 	struct ieee80211_sub_if_data *vlan;
940 
941 	sdata->vif.bss_conf.chandef = *chandef;
942 
943 	if (sdata->vif.type != NL80211_IFTYPE_AP)
944 		return;
945 
946 	list_for_each_entry(vlan, &sdata->u.ap.vlans, u.vlan.list)
947 		vlan->vif.bss_conf.chandef = *chandef;
948 }
949 
950 static int
951 ieee80211_vif_use_reserved_reassign(struct ieee80211_sub_if_data *sdata)
952 {
953 	struct ieee80211_local *local = sdata->local;
954 	struct ieee80211_vif_chanctx_switch vif_chsw[1] = {};
955 	struct ieee80211_chanctx *old_ctx, *new_ctx;
956 	const struct cfg80211_chan_def *chandef;
957 	u32 changed = 0;
958 	int err;
959 
960 	lockdep_assert_held(&local->mtx);
961 	lockdep_assert_held(&local->chanctx_mtx);
962 
963 	new_ctx = sdata->reserved_chanctx;
964 	old_ctx = ieee80211_vif_get_chanctx(sdata);
965 
966 	if (WARN_ON(!sdata->reserved_ready))
967 		return -EBUSY;
968 
969 	if (WARN_ON(!new_ctx))
970 		return -EINVAL;
971 
972 	if (WARN_ON(!old_ctx))
973 		return -EINVAL;
974 
975 	if (WARN_ON(new_ctx->replace_state ==
976 		    IEEE80211_CHANCTX_REPLACES_OTHER))
977 		return -EINVAL;
978 
979 	chandef = ieee80211_chanctx_non_reserved_chandef(local, new_ctx,
980 				&sdata->reserved_chandef);
981 	if (WARN_ON(!chandef))
982 		return -EINVAL;
983 
984 	vif_chsw[0].vif = &sdata->vif;
985 	vif_chsw[0].old_ctx = &old_ctx->conf;
986 	vif_chsw[0].new_ctx = &new_ctx->conf;
987 
988 	list_del(&sdata->reserved_chanctx_list);
989 	sdata->reserved_chanctx = NULL;
990 
991 	err = drv_switch_vif_chanctx(local, vif_chsw, 1,
992 				     CHANCTX_SWMODE_REASSIGN_VIF);
993 	if (err) {
994 		if (ieee80211_chanctx_refcount(local, new_ctx) == 0)
995 			ieee80211_free_chanctx(local, new_ctx);
996 
997 		goto out;
998 	}
999 
1000 	list_move(&sdata->assigned_chanctx_list, &new_ctx->assigned_vifs);
1001 	rcu_assign_pointer(sdata->vif.chanctx_conf, &new_ctx->conf);
1002 
1003 	if (sdata->vif.type == NL80211_IFTYPE_AP)
1004 		__ieee80211_vif_copy_chanctx_to_vlans(sdata, false);
1005 
1006 	if (ieee80211_chanctx_refcount(local, old_ctx) == 0)
1007 		ieee80211_free_chanctx(local, old_ctx);
1008 
1009 	if (sdata->vif.bss_conf.chandef.width != sdata->reserved_chandef.width)
1010 		changed = BSS_CHANGED_BANDWIDTH;
1011 
1012 	ieee80211_vif_update_chandef(sdata, &sdata->reserved_chandef);
1013 
1014 	if (changed)
1015 		ieee80211_bss_info_change_notify(sdata, changed);
1016 
1017 out:
1018 	ieee80211_vif_chanctx_reservation_complete(sdata);
1019 	return err;
1020 }
1021 
1022 static int
1023 ieee80211_vif_use_reserved_assign(struct ieee80211_sub_if_data *sdata)
1024 {
1025 	struct ieee80211_local *local = sdata->local;
1026 	struct ieee80211_chanctx *old_ctx, *new_ctx;
1027 	const struct cfg80211_chan_def *chandef;
1028 	int err;
1029 
1030 	old_ctx = ieee80211_vif_get_chanctx(sdata);
1031 	new_ctx = sdata->reserved_chanctx;
1032 
1033 	if (WARN_ON(!sdata->reserved_ready))
1034 		return -EINVAL;
1035 
1036 	if (WARN_ON(old_ctx))
1037 		return -EINVAL;
1038 
1039 	if (WARN_ON(!new_ctx))
1040 		return -EINVAL;
1041 
1042 	if (WARN_ON(new_ctx->replace_state ==
1043 		    IEEE80211_CHANCTX_REPLACES_OTHER))
1044 		return -EINVAL;
1045 
1046 	chandef = ieee80211_chanctx_non_reserved_chandef(local, new_ctx,
1047 				&sdata->reserved_chandef);
1048 	if (WARN_ON(!chandef))
1049 		return -EINVAL;
1050 
1051 	list_del(&sdata->reserved_chanctx_list);
1052 	sdata->reserved_chanctx = NULL;
1053 
1054 	err = ieee80211_assign_vif_chanctx(sdata, new_ctx);
1055 	if (err) {
1056 		if (ieee80211_chanctx_refcount(local, new_ctx) == 0)
1057 			ieee80211_free_chanctx(local, new_ctx);
1058 
1059 		goto out;
1060 	}
1061 
1062 out:
1063 	ieee80211_vif_chanctx_reservation_complete(sdata);
1064 	return err;
1065 }
1066 
1067 static bool
1068 ieee80211_vif_has_in_place_reservation(struct ieee80211_sub_if_data *sdata)
1069 {
1070 	struct ieee80211_chanctx *old_ctx, *new_ctx;
1071 
1072 	lockdep_assert_held(&sdata->local->chanctx_mtx);
1073 
1074 	new_ctx = sdata->reserved_chanctx;
1075 	old_ctx = ieee80211_vif_get_chanctx(sdata);
1076 
1077 	if (!old_ctx)
1078 		return false;
1079 
1080 	if (WARN_ON(!new_ctx))
1081 		return false;
1082 
1083 	if (old_ctx->replace_state != IEEE80211_CHANCTX_WILL_BE_REPLACED)
1084 		return false;
1085 
1086 	if (new_ctx->replace_state != IEEE80211_CHANCTX_REPLACES_OTHER)
1087 		return false;
1088 
1089 	return true;
1090 }
1091 
1092 static int ieee80211_chsw_switch_hwconf(struct ieee80211_local *local,
1093 					struct ieee80211_chanctx *new_ctx)
1094 {
1095 	const struct cfg80211_chan_def *chandef;
1096 
1097 	lockdep_assert_held(&local->mtx);
1098 	lockdep_assert_held(&local->chanctx_mtx);
1099 
1100 	chandef = ieee80211_chanctx_reserved_chandef(local, new_ctx, NULL);
1101 	if (WARN_ON(!chandef))
1102 		return -EINVAL;
1103 
1104 	local->hw.conf.radar_enabled = new_ctx->conf.radar_enabled;
1105 	local->_oper_chandef = *chandef;
1106 	ieee80211_hw_config(local, 0);
1107 
1108 	return 0;
1109 }
1110 
1111 static int ieee80211_chsw_switch_vifs(struct ieee80211_local *local,
1112 				      int n_vifs)
1113 {
1114 	struct ieee80211_vif_chanctx_switch *vif_chsw;
1115 	struct ieee80211_sub_if_data *sdata;
1116 	struct ieee80211_chanctx *ctx, *old_ctx;
1117 	int i, err;
1118 
1119 	lockdep_assert_held(&local->mtx);
1120 	lockdep_assert_held(&local->chanctx_mtx);
1121 
1122 	vif_chsw = kzalloc(sizeof(vif_chsw[0]) * n_vifs, GFP_KERNEL);
1123 	if (!vif_chsw)
1124 		return -ENOMEM;
1125 
1126 	i = 0;
1127 	list_for_each_entry(ctx, &local->chanctx_list, list) {
1128 		if (ctx->replace_state != IEEE80211_CHANCTX_REPLACES_OTHER)
1129 			continue;
1130 
1131 		if (WARN_ON(!ctx->replace_ctx)) {
1132 			err = -EINVAL;
1133 			goto out;
1134 		}
1135 
1136 		list_for_each_entry(sdata, &ctx->reserved_vifs,
1137 				    reserved_chanctx_list) {
1138 			if (!ieee80211_vif_has_in_place_reservation(
1139 					sdata))
1140 				continue;
1141 
1142 			old_ctx = ieee80211_vif_get_chanctx(sdata);
1143 			vif_chsw[i].vif = &sdata->vif;
1144 			vif_chsw[i].old_ctx = &old_ctx->conf;
1145 			vif_chsw[i].new_ctx = &ctx->conf;
1146 
1147 			i++;
1148 		}
1149 	}
1150 
1151 	err = drv_switch_vif_chanctx(local, vif_chsw, n_vifs,
1152 				     CHANCTX_SWMODE_SWAP_CONTEXTS);
1153 
1154 out:
1155 	kfree(vif_chsw);
1156 	return err;
1157 }
1158 
1159 static int ieee80211_chsw_switch_ctxs(struct ieee80211_local *local)
1160 {
1161 	struct ieee80211_chanctx *ctx;
1162 	int err;
1163 
1164 	lockdep_assert_held(&local->mtx);
1165 	lockdep_assert_held(&local->chanctx_mtx);
1166 
1167 	list_for_each_entry(ctx, &local->chanctx_list, list) {
1168 		if (ctx->replace_state != IEEE80211_CHANCTX_REPLACES_OTHER)
1169 			continue;
1170 
1171 		if (!list_empty(&ctx->replace_ctx->assigned_vifs))
1172 			continue;
1173 
1174 		ieee80211_del_chanctx(local, ctx->replace_ctx);
1175 		err = ieee80211_add_chanctx(local, ctx);
1176 		if (err)
1177 			goto err;
1178 	}
1179 
1180 	return 0;
1181 
1182 err:
1183 	WARN_ON(ieee80211_add_chanctx(local, ctx));
1184 	list_for_each_entry_continue_reverse(ctx, &local->chanctx_list, list) {
1185 		if (ctx->replace_state != IEEE80211_CHANCTX_REPLACES_OTHER)
1186 			continue;
1187 
1188 		if (!list_empty(&ctx->replace_ctx->assigned_vifs))
1189 			continue;
1190 
1191 		ieee80211_del_chanctx(local, ctx);
1192 		WARN_ON(ieee80211_add_chanctx(local, ctx->replace_ctx));
1193 	}
1194 
1195 	return err;
1196 }
1197 
1198 static int ieee80211_vif_use_reserved_switch(struct ieee80211_local *local)
1199 {
1200 	struct ieee80211_sub_if_data *sdata, *sdata_tmp;
1201 	struct ieee80211_chanctx *ctx, *ctx_tmp, *old_ctx;
1202 	struct ieee80211_chanctx *new_ctx = NULL;
1203 	int i, err, n_assigned, n_reserved, n_ready;
1204 	int n_ctx = 0, n_vifs_switch = 0, n_vifs_assign = 0, n_vifs_ctxless = 0;
1205 
1206 	lockdep_assert_held(&local->mtx);
1207 	lockdep_assert_held(&local->chanctx_mtx);
1208 
1209 	/*
1210 	 * If there are 2 independent pairs of channel contexts performing
1211 	 * cross-switch of their vifs this code will still wait until both are
1212 	 * ready even though it could be possible to switch one before the
1213 	 * other is ready.
1214 	 *
1215 	 * For practical reasons and code simplicity just do a single huge
1216 	 * switch.
1217 	 */
1218 
1219 	/*
1220 	 * Verify if the reservation is still feasible.
1221 	 *  - if it's not then disconnect
1222 	 *  - if it is but not all vifs necessary are ready then defer
1223 	 */
1224 
1225 	list_for_each_entry(ctx, &local->chanctx_list, list) {
1226 		if (ctx->replace_state != IEEE80211_CHANCTX_REPLACES_OTHER)
1227 			continue;
1228 
1229 		if (WARN_ON(!ctx->replace_ctx)) {
1230 			err = -EINVAL;
1231 			goto err;
1232 		}
1233 
1234 		if (!local->use_chanctx)
1235 			new_ctx = ctx;
1236 
1237 		n_ctx++;
1238 
1239 		n_assigned = 0;
1240 		n_reserved = 0;
1241 		n_ready = 0;
1242 
1243 		list_for_each_entry(sdata, &ctx->replace_ctx->assigned_vifs,
1244 				    assigned_chanctx_list) {
1245 			n_assigned++;
1246 			if (sdata->reserved_chanctx) {
1247 				n_reserved++;
1248 				if (sdata->reserved_ready)
1249 					n_ready++;
1250 			}
1251 		}
1252 
1253 		if (n_assigned != n_reserved) {
1254 			if (n_ready == n_reserved) {
1255 				wiphy_info(local->hw.wiphy,
1256 					   "channel context reservation cannot be finalized because some interfaces aren't switching\n");
1257 				err = -EBUSY;
1258 				goto err;
1259 			}
1260 
1261 			return -EAGAIN;
1262 		}
1263 
1264 		ctx->conf.radar_enabled = false;
1265 		list_for_each_entry(sdata, &ctx->reserved_vifs,
1266 				    reserved_chanctx_list) {
1267 			if (ieee80211_vif_has_in_place_reservation(sdata) &&
1268 			    !sdata->reserved_ready)
1269 				return -EAGAIN;
1270 
1271 			old_ctx = ieee80211_vif_get_chanctx(sdata);
1272 			if (old_ctx) {
1273 				if (old_ctx->replace_state ==
1274 				    IEEE80211_CHANCTX_WILL_BE_REPLACED)
1275 					n_vifs_switch++;
1276 				else
1277 					n_vifs_assign++;
1278 			} else {
1279 				n_vifs_ctxless++;
1280 			}
1281 
1282 			if (sdata->reserved_radar_required)
1283 				ctx->conf.radar_enabled = true;
1284 		}
1285 	}
1286 
1287 	if (WARN_ON(n_ctx == 0) ||
1288 	    WARN_ON(n_vifs_switch == 0 &&
1289 		    n_vifs_assign == 0 &&
1290 		    n_vifs_ctxless == 0) ||
1291 	    WARN_ON(n_ctx > 1 && !local->use_chanctx) ||
1292 	    WARN_ON(!new_ctx && !local->use_chanctx)) {
1293 		err = -EINVAL;
1294 		goto err;
1295 	}
1296 
1297 	/*
1298 	 * All necessary vifs are ready. Perform the switch now depending on
1299 	 * reservations and driver capabilities.
1300 	 */
1301 
1302 	if (local->use_chanctx) {
1303 		if (n_vifs_switch > 0) {
1304 			err = ieee80211_chsw_switch_vifs(local, n_vifs_switch);
1305 			if (err)
1306 				goto err;
1307 		}
1308 
1309 		if (n_vifs_assign > 0 || n_vifs_ctxless > 0) {
1310 			err = ieee80211_chsw_switch_ctxs(local);
1311 			if (err)
1312 				goto err;
1313 		}
1314 	} else {
1315 		err = ieee80211_chsw_switch_hwconf(local, new_ctx);
1316 		if (err)
1317 			goto err;
1318 	}
1319 
1320 	/*
1321 	 * Update all structures, values and pointers to point to new channel
1322 	 * context(s).
1323 	 */
1324 
1325 	i = 0;
1326 	list_for_each_entry(ctx, &local->chanctx_list, list) {
1327 		if (ctx->replace_state != IEEE80211_CHANCTX_REPLACES_OTHER)
1328 			continue;
1329 
1330 		if (WARN_ON(!ctx->replace_ctx)) {
1331 			err = -EINVAL;
1332 			goto err;
1333 		}
1334 
1335 		list_for_each_entry(sdata, &ctx->reserved_vifs,
1336 				    reserved_chanctx_list) {
1337 			u32 changed = 0;
1338 
1339 			if (!ieee80211_vif_has_in_place_reservation(sdata))
1340 				continue;
1341 
1342 			rcu_assign_pointer(sdata->vif.chanctx_conf, &ctx->conf);
1343 
1344 			if (sdata->vif.type == NL80211_IFTYPE_AP)
1345 				__ieee80211_vif_copy_chanctx_to_vlans(sdata,
1346 								      false);
1347 
1348 			sdata->radar_required = sdata->reserved_radar_required;
1349 
1350 			if (sdata->vif.bss_conf.chandef.width !=
1351 			    sdata->reserved_chandef.width)
1352 				changed = BSS_CHANGED_BANDWIDTH;
1353 
1354 			ieee80211_vif_update_chandef(sdata, &sdata->reserved_chandef);
1355 			if (changed)
1356 				ieee80211_bss_info_change_notify(sdata,
1357 								 changed);
1358 
1359 			ieee80211_recalc_txpower(sdata);
1360 		}
1361 
1362 		ieee80211_recalc_chanctx_chantype(local, ctx);
1363 		ieee80211_recalc_smps_chanctx(local, ctx);
1364 		ieee80211_recalc_radar_chanctx(local, ctx);
1365 		ieee80211_recalc_chanctx_min_def(local, ctx);
1366 
1367 		list_for_each_entry_safe(sdata, sdata_tmp, &ctx->reserved_vifs,
1368 					 reserved_chanctx_list) {
1369 			if (ieee80211_vif_get_chanctx(sdata) != ctx)
1370 				continue;
1371 
1372 			list_del(&sdata->reserved_chanctx_list);
1373 			list_move(&sdata->assigned_chanctx_list,
1374 				  &ctx->assigned_vifs);
1375 			sdata->reserved_chanctx = NULL;
1376 
1377 			ieee80211_vif_chanctx_reservation_complete(sdata);
1378 		}
1379 
1380 		/*
1381 		 * This context might have been a dependency for an already
1382 		 * ready re-assign reservation interface that was deferred. Do
1383 		 * not propagate error to the caller though. The in-place
1384 		 * reservation for originally requested interface has already
1385 		 * succeeded at this point.
1386 		 */
1387 		list_for_each_entry_safe(sdata, sdata_tmp, &ctx->reserved_vifs,
1388 					 reserved_chanctx_list) {
1389 			if (WARN_ON(ieee80211_vif_has_in_place_reservation(
1390 					sdata)))
1391 				continue;
1392 
1393 			if (WARN_ON(sdata->reserved_chanctx != ctx))
1394 				continue;
1395 
1396 			if (!sdata->reserved_ready)
1397 				continue;
1398 
1399 			if (ieee80211_vif_get_chanctx(sdata))
1400 				err = ieee80211_vif_use_reserved_reassign(
1401 						sdata);
1402 			else
1403 				err = ieee80211_vif_use_reserved_assign(sdata);
1404 
1405 			if (err) {
1406 				sdata_info(sdata,
1407 					   "failed to finalize (re-)assign reservation (err=%d)\n",
1408 					   err);
1409 				ieee80211_vif_unreserve_chanctx(sdata);
1410 				cfg80211_stop_iface(local->hw.wiphy,
1411 						    &sdata->wdev,
1412 						    GFP_KERNEL);
1413 			}
1414 		}
1415 	}
1416 
1417 	/*
1418 	 * Finally free old contexts
1419 	 */
1420 
1421 	list_for_each_entry_safe(ctx, ctx_tmp, &local->chanctx_list, list) {
1422 		if (ctx->replace_state != IEEE80211_CHANCTX_WILL_BE_REPLACED)
1423 			continue;
1424 
1425 		ctx->replace_ctx->replace_ctx = NULL;
1426 		ctx->replace_ctx->replace_state =
1427 				IEEE80211_CHANCTX_REPLACE_NONE;
1428 
1429 		list_del_rcu(&ctx->list);
1430 		kfree_rcu(ctx, rcu_head);
1431 	}
1432 
1433 	return 0;
1434 
1435 err:
1436 	list_for_each_entry(ctx, &local->chanctx_list, list) {
1437 		if (ctx->replace_state != IEEE80211_CHANCTX_REPLACES_OTHER)
1438 			continue;
1439 
1440 		list_for_each_entry_safe(sdata, sdata_tmp, &ctx->reserved_vifs,
1441 					 reserved_chanctx_list) {
1442 			ieee80211_vif_unreserve_chanctx(sdata);
1443 			ieee80211_vif_chanctx_reservation_complete(sdata);
1444 		}
1445 	}
1446 
1447 	return err;
1448 }
1449 
1450 static void __ieee80211_vif_release_channel(struct ieee80211_sub_if_data *sdata)
1451 {
1452 	struct ieee80211_local *local = sdata->local;
1453 	struct ieee80211_chanctx_conf *conf;
1454 	struct ieee80211_chanctx *ctx;
1455 	bool use_reserved_switch = false;
1456 
1457 	lockdep_assert_held(&local->chanctx_mtx);
1458 
1459 	conf = rcu_dereference_protected(sdata->vif.chanctx_conf,
1460 					 lockdep_is_held(&local->chanctx_mtx));
1461 	if (!conf)
1462 		return;
1463 
1464 	ctx = container_of(conf, struct ieee80211_chanctx, conf);
1465 
1466 	if (sdata->reserved_chanctx) {
1467 		if (sdata->reserved_chanctx->replace_state ==
1468 		    IEEE80211_CHANCTX_REPLACES_OTHER &&
1469 		    ieee80211_chanctx_num_reserved(local,
1470 						   sdata->reserved_chanctx) > 1)
1471 			use_reserved_switch = true;
1472 
1473 		ieee80211_vif_unreserve_chanctx(sdata);
1474 	}
1475 
1476 	ieee80211_assign_vif_chanctx(sdata, NULL);
1477 	if (ieee80211_chanctx_refcount(local, ctx) == 0)
1478 		ieee80211_free_chanctx(local, ctx);
1479 
1480 	/* Unreserving may ready an in-place reservation. */
1481 	if (use_reserved_switch)
1482 		ieee80211_vif_use_reserved_switch(local);
1483 }
1484 
1485 int ieee80211_vif_use_channel(struct ieee80211_sub_if_data *sdata,
1486 			      const struct cfg80211_chan_def *chandef,
1487 			      enum ieee80211_chanctx_mode mode)
1488 {
1489 	struct ieee80211_local *local = sdata->local;
1490 	struct ieee80211_chanctx *ctx;
1491 	u8 radar_detect_width = 0;
1492 	int ret;
1493 
1494 	lockdep_assert_held(&local->mtx);
1495 
1496 	WARN_ON(sdata->dev && netif_carrier_ok(sdata->dev));
1497 
1498 	mutex_lock(&local->chanctx_mtx);
1499 
1500 	ret = cfg80211_chandef_dfs_required(local->hw.wiphy,
1501 					    chandef,
1502 					    sdata->wdev.iftype);
1503 	if (ret < 0)
1504 		goto out;
1505 	if (ret > 0)
1506 		radar_detect_width = BIT(chandef->width);
1507 
1508 	sdata->radar_required = ret;
1509 
1510 	ret = ieee80211_check_combinations(sdata, chandef, mode,
1511 					   radar_detect_width);
1512 	if (ret < 0)
1513 		goto out;
1514 
1515 	__ieee80211_vif_release_channel(sdata);
1516 
1517 	ctx = ieee80211_find_chanctx(local, chandef, mode);
1518 	if (!ctx)
1519 		ctx = ieee80211_new_chanctx(local, chandef, mode);
1520 	if (IS_ERR(ctx)) {
1521 		ret = PTR_ERR(ctx);
1522 		goto out;
1523 	}
1524 
1525 	ieee80211_vif_update_chandef(sdata, chandef);
1526 
1527 	ret = ieee80211_assign_vif_chanctx(sdata, ctx);
1528 	if (ret) {
1529 		/* if assign fails refcount stays the same */
1530 		if (ieee80211_chanctx_refcount(local, ctx) == 0)
1531 			ieee80211_free_chanctx(local, ctx);
1532 		goto out;
1533 	}
1534 
1535 	ieee80211_recalc_smps_chanctx(local, ctx);
1536 	ieee80211_recalc_radar_chanctx(local, ctx);
1537  out:
1538 	mutex_unlock(&local->chanctx_mtx);
1539 	return ret;
1540 }
1541 
1542 int ieee80211_vif_use_reserved_context(struct ieee80211_sub_if_data *sdata)
1543 {
1544 	struct ieee80211_local *local = sdata->local;
1545 	struct ieee80211_chanctx *new_ctx;
1546 	struct ieee80211_chanctx *old_ctx;
1547 	int err;
1548 
1549 	lockdep_assert_held(&local->mtx);
1550 	lockdep_assert_held(&local->chanctx_mtx);
1551 
1552 	new_ctx = sdata->reserved_chanctx;
1553 	old_ctx = ieee80211_vif_get_chanctx(sdata);
1554 
1555 	if (WARN_ON(!new_ctx))
1556 		return -EINVAL;
1557 
1558 	if (WARN_ON(new_ctx->replace_state ==
1559 		    IEEE80211_CHANCTX_WILL_BE_REPLACED))
1560 		return -EINVAL;
1561 
1562 	if (WARN_ON(sdata->reserved_ready))
1563 		return -EINVAL;
1564 
1565 	sdata->reserved_ready = true;
1566 
1567 	if (new_ctx->replace_state == IEEE80211_CHANCTX_REPLACE_NONE) {
1568 		if (old_ctx)
1569 			err = ieee80211_vif_use_reserved_reassign(sdata);
1570 		else
1571 			err = ieee80211_vif_use_reserved_assign(sdata);
1572 
1573 		if (err)
1574 			return err;
1575 	}
1576 
1577 	/*
1578 	 * In-place reservation may need to be finalized now either if:
1579 	 *  a) sdata is taking part in the swapping itself and is the last one
1580 	 *  b) sdata has switched with a re-assign reservation to an existing
1581 	 *     context readying in-place switching of old_ctx
1582 	 *
1583 	 * In case of (b) do not propagate the error up because the requested
1584 	 * sdata already switched successfully. Just spill an extra warning.
1585 	 * The ieee80211_vif_use_reserved_switch() already stops all necessary
1586 	 * interfaces upon failure.
1587 	 */
1588 	if ((old_ctx &&
1589 	     old_ctx->replace_state == IEEE80211_CHANCTX_WILL_BE_REPLACED) ||
1590 	    new_ctx->replace_state == IEEE80211_CHANCTX_REPLACES_OTHER) {
1591 		err = ieee80211_vif_use_reserved_switch(local);
1592 		if (err && err != -EAGAIN) {
1593 			if (new_ctx->replace_state ==
1594 			    IEEE80211_CHANCTX_REPLACES_OTHER)
1595 				return err;
1596 
1597 			wiphy_info(local->hw.wiphy,
1598 				   "depending in-place reservation failed (err=%d)\n",
1599 				   err);
1600 		}
1601 	}
1602 
1603 	return 0;
1604 }
1605 
1606 int ieee80211_vif_change_bandwidth(struct ieee80211_sub_if_data *sdata,
1607 				   const struct cfg80211_chan_def *chandef,
1608 				   u32 *changed)
1609 {
1610 	struct ieee80211_local *local = sdata->local;
1611 	struct ieee80211_chanctx_conf *conf;
1612 	struct ieee80211_chanctx *ctx;
1613 	const struct cfg80211_chan_def *compat;
1614 	int ret;
1615 
1616 	if (!cfg80211_chandef_usable(sdata->local->hw.wiphy, chandef,
1617 				     IEEE80211_CHAN_DISABLED))
1618 		return -EINVAL;
1619 
1620 	mutex_lock(&local->chanctx_mtx);
1621 	if (cfg80211_chandef_identical(chandef, &sdata->vif.bss_conf.chandef)) {
1622 		ret = 0;
1623 		goto out;
1624 	}
1625 
1626 	if (chandef->width == NL80211_CHAN_WIDTH_20_NOHT ||
1627 	    sdata->vif.bss_conf.chandef.width == NL80211_CHAN_WIDTH_20_NOHT) {
1628 		ret = -EINVAL;
1629 		goto out;
1630 	}
1631 
1632 	conf = rcu_dereference_protected(sdata->vif.chanctx_conf,
1633 					 lockdep_is_held(&local->chanctx_mtx));
1634 	if (!conf) {
1635 		ret = -EINVAL;
1636 		goto out;
1637 	}
1638 
1639 	ctx = container_of(conf, struct ieee80211_chanctx, conf);
1640 
1641 	compat = cfg80211_chandef_compatible(&conf->def, chandef);
1642 	if (!compat) {
1643 		ret = -EINVAL;
1644 		goto out;
1645 	}
1646 
1647 	switch (ctx->replace_state) {
1648 	case IEEE80211_CHANCTX_REPLACE_NONE:
1649 		if (!ieee80211_chanctx_reserved_chandef(local, ctx, compat)) {
1650 			ret = -EBUSY;
1651 			goto out;
1652 		}
1653 		break;
1654 	case IEEE80211_CHANCTX_WILL_BE_REPLACED:
1655 		/* TODO: Perhaps the bandwidth change could be treated as a
1656 		 * reservation itself? */
1657 		ret = -EBUSY;
1658 		goto out;
1659 	case IEEE80211_CHANCTX_REPLACES_OTHER:
1660 		/* channel context that is going to replace another channel
1661 		 * context doesn't really exist and shouldn't be assigned
1662 		 * anywhere yet */
1663 		WARN_ON(1);
1664 		break;
1665 	}
1666 
1667 	ieee80211_vif_update_chandef(sdata, chandef);
1668 
1669 	ieee80211_recalc_chanctx_chantype(local, ctx);
1670 
1671 	*changed |= BSS_CHANGED_BANDWIDTH;
1672 	ret = 0;
1673  out:
1674 	mutex_unlock(&local->chanctx_mtx);
1675 	return ret;
1676 }
1677 
1678 void ieee80211_vif_release_channel(struct ieee80211_sub_if_data *sdata)
1679 {
1680 	WARN_ON(sdata->dev && netif_carrier_ok(sdata->dev));
1681 
1682 	lockdep_assert_held(&sdata->local->mtx);
1683 
1684 	mutex_lock(&sdata->local->chanctx_mtx);
1685 	__ieee80211_vif_release_channel(sdata);
1686 	mutex_unlock(&sdata->local->chanctx_mtx);
1687 }
1688 
1689 void ieee80211_vif_vlan_copy_chanctx(struct ieee80211_sub_if_data *sdata)
1690 {
1691 	struct ieee80211_local *local = sdata->local;
1692 	struct ieee80211_sub_if_data *ap;
1693 	struct ieee80211_chanctx_conf *conf;
1694 
1695 	if (WARN_ON(sdata->vif.type != NL80211_IFTYPE_AP_VLAN || !sdata->bss))
1696 		return;
1697 
1698 	ap = container_of(sdata->bss, struct ieee80211_sub_if_data, u.ap);
1699 
1700 	mutex_lock(&local->chanctx_mtx);
1701 
1702 	conf = rcu_dereference_protected(ap->vif.chanctx_conf,
1703 					 lockdep_is_held(&local->chanctx_mtx));
1704 	rcu_assign_pointer(sdata->vif.chanctx_conf, conf);
1705 	mutex_unlock(&local->chanctx_mtx);
1706 }
1707 
1708 void ieee80211_iter_chan_contexts_atomic(
1709 	struct ieee80211_hw *hw,
1710 	void (*iter)(struct ieee80211_hw *hw,
1711 		     struct ieee80211_chanctx_conf *chanctx_conf,
1712 		     void *data),
1713 	void *iter_data)
1714 {
1715 	struct ieee80211_local *local = hw_to_local(hw);
1716 	struct ieee80211_chanctx *ctx;
1717 
1718 	rcu_read_lock();
1719 	list_for_each_entry_rcu(ctx, &local->chanctx_list, list)
1720 		if (ctx->driver_present)
1721 			iter(hw, &ctx->conf, iter_data);
1722 	rcu_read_unlock();
1723 }
1724 EXPORT_SYMBOL_GPL(ieee80211_iter_chan_contexts_atomic);
1725