1/* SPDX-License-Identifier: GPL-2.0 */
2/*
3* Portions of this file
4* Copyright(c) 2016 Intel Deutschland GmbH
5* Copyright (C) 2018 - 2019, 2021 - 2023 Intel Corporation
6*/
7
8#ifndef __MAC80211_DRIVER_OPS
9#define __MAC80211_DRIVER_OPS
10
11#include <net/mac80211.h>
12#include "ieee80211_i.h"
13#include "trace.h"
14
15#define check_sdata_in_driver(sdata)	({					\
16	WARN_ONCE(!sdata->local->reconfig_failure &&				\
17		  !(sdata->flags & IEEE80211_SDATA_IN_DRIVER),			\
18		  "%s: Failed check-sdata-in-driver check, flags: 0x%x\n",	\
19		  sdata->dev ? sdata->dev->name : sdata->name, sdata->flags);	\
20	!!(sdata->flags & IEEE80211_SDATA_IN_DRIVER);				\
21})
22
23static inline struct ieee80211_sub_if_data *
24get_bss_sdata(struct ieee80211_sub_if_data *sdata)
25{
26	if (sdata && sdata->vif.type == NL80211_IFTYPE_AP_VLAN)
27		sdata = container_of(sdata->bss, struct ieee80211_sub_if_data,
28				     u.ap);
29
30	return sdata;
31}
32
33static inline void drv_tx(struct ieee80211_local *local,
34			  struct ieee80211_tx_control *control,
35			  struct sk_buff *skb)
36{
37	local->ops->tx(&local->hw, control, skb);
38}
39
40static inline void drv_sync_rx_queues(struct ieee80211_local *local,
41				      struct sta_info *sta)
42{
43	if (local->ops->sync_rx_queues) {
44		trace_drv_sync_rx_queues(local, sta->sdata, &sta->sta);
45		local->ops->sync_rx_queues(&local->hw);
46		trace_drv_return_void(local);
47	}
48}
49
50static inline void drv_get_et_strings(struct ieee80211_sub_if_data *sdata,
51				      u32 sset, u8 *data)
52{
53	struct ieee80211_local *local = sdata->local;
54	if (local->ops->get_et_strings) {
55		trace_drv_get_et_strings(local, sset);
56		local->ops->get_et_strings(&local->hw, &sdata->vif, sset, data);
57		trace_drv_return_void(local);
58	}
59}
60
61static inline void drv_get_et_stats(struct ieee80211_sub_if_data *sdata,
62				    struct ethtool_stats *stats,
63				    u64 *data)
64{
65	struct ieee80211_local *local = sdata->local;
66	if (local->ops->get_et_stats) {
67		trace_drv_get_et_stats(local);
68		local->ops->get_et_stats(&local->hw, &sdata->vif, stats, data);
69		trace_drv_return_void(local);
70	}
71}
72
73static inline int drv_get_et_sset_count(struct ieee80211_sub_if_data *sdata,
74					int sset)
75{
76	struct ieee80211_local *local = sdata->local;
77	int rv = 0;
78	if (local->ops->get_et_sset_count) {
79		trace_drv_get_et_sset_count(local, sset);
80		rv = local->ops->get_et_sset_count(&local->hw, &sdata->vif,
81						   sset);
82		trace_drv_return_int(local, rv);
83	}
84	return rv;
85}
86
87int drv_start(struct ieee80211_local *local);
88void drv_stop(struct ieee80211_local *local);
89
90#ifdef CONFIG_PM
91static inline int drv_suspend(struct ieee80211_local *local,
92			      struct cfg80211_wowlan *wowlan)
93{
94	int ret;
95
96	might_sleep();
97
98	trace_drv_suspend(local);
99	ret = local->ops->suspend(&local->hw, wowlan);
100	trace_drv_return_int(local, ret);
101	return ret;
102}
103
104static inline int drv_resume(struct ieee80211_local *local)
105{
106	int ret;
107
108	might_sleep();
109
110	trace_drv_resume(local);
111	ret = local->ops->resume(&local->hw);
112	trace_drv_return_int(local, ret);
113	return ret;
114}
115
116static inline void drv_set_wakeup(struct ieee80211_local *local,
117				  bool enabled)
118{
119	might_sleep();
120
121	if (!local->ops->set_wakeup)
122		return;
123
124	trace_drv_set_wakeup(local, enabled);
125	local->ops->set_wakeup(&local->hw, enabled);
126	trace_drv_return_void(local);
127}
128#endif
129
130int drv_add_interface(struct ieee80211_local *local,
131		      struct ieee80211_sub_if_data *sdata);
132
133int drv_change_interface(struct ieee80211_local *local,
134			 struct ieee80211_sub_if_data *sdata,
135			 enum nl80211_iftype type, bool p2p);
136
137void drv_remove_interface(struct ieee80211_local *local,
138			  struct ieee80211_sub_if_data *sdata);
139
140static inline int drv_config(struct ieee80211_local *local, u32 changed)
141{
142	int ret;
143
144	might_sleep();
145
146	trace_drv_config(local, changed);
147	ret = local->ops->config(&local->hw, changed);
148	trace_drv_return_int(local, ret);
149	return ret;
150}
151
152static inline void drv_vif_cfg_changed(struct ieee80211_local *local,
153				       struct ieee80211_sub_if_data *sdata,
154				       u64 changed)
155{
156	might_sleep();
157
158	if (!check_sdata_in_driver(sdata))
159		return;
160
161	trace_drv_vif_cfg_changed(local, sdata, changed);
162	if (local->ops->vif_cfg_changed)
163		local->ops->vif_cfg_changed(&local->hw, &sdata->vif, changed);
164	else if (local->ops->bss_info_changed)
165		local->ops->bss_info_changed(&local->hw, &sdata->vif,
166					     &sdata->vif.bss_conf, changed);
167	trace_drv_return_void(local);
168}
169
170void drv_link_info_changed(struct ieee80211_local *local,
171			   struct ieee80211_sub_if_data *sdata,
172			   struct ieee80211_bss_conf *info,
173			   int link_id, u64 changed);
174
175static inline u64 drv_prepare_multicast(struct ieee80211_local *local,
176					struct netdev_hw_addr_list *mc_list)
177{
178	u64 ret = 0;
179
180	trace_drv_prepare_multicast(local, mc_list->count);
181
182	if (local->ops->prepare_multicast)
183		ret = local->ops->prepare_multicast(&local->hw, mc_list);
184
185	trace_drv_return_u64(local, ret);
186
187	return ret;
188}
189
190static inline void drv_configure_filter(struct ieee80211_local *local,
191					unsigned int changed_flags,
192					unsigned int *total_flags,
193					u64 multicast)
194{
195	might_sleep();
196
197	trace_drv_configure_filter(local, changed_flags, total_flags,
198				   multicast);
199	local->ops->configure_filter(&local->hw, changed_flags, total_flags,
200				     multicast);
201	trace_drv_return_void(local);
202}
203
204static inline void drv_config_iface_filter(struct ieee80211_local *local,
205					   struct ieee80211_sub_if_data *sdata,
206					   unsigned int filter_flags,
207					   unsigned int changed_flags)
208{
209	might_sleep();
210
211	trace_drv_config_iface_filter(local, sdata, filter_flags,
212				      changed_flags);
213	if (local->ops->config_iface_filter)
214		local->ops->config_iface_filter(&local->hw, &sdata->vif,
215						filter_flags,
216						changed_flags);
217	trace_drv_return_void(local);
218}
219
220static inline int drv_set_tim(struct ieee80211_local *local,
221			      struct ieee80211_sta *sta, bool set)
222{
223	int ret = 0;
224	trace_drv_set_tim(local, sta, set);
225	if (local->ops->set_tim)
226		ret = local->ops->set_tim(&local->hw, sta, set);
227	trace_drv_return_int(local, ret);
228	return ret;
229}
230
231int drv_set_key(struct ieee80211_local *local,
232		enum set_key_cmd cmd,
233		struct ieee80211_sub_if_data *sdata,
234		struct ieee80211_sta *sta,
235		struct ieee80211_key_conf *key);
236
237static inline void drv_update_tkip_key(struct ieee80211_local *local,
238				       struct ieee80211_sub_if_data *sdata,
239				       struct ieee80211_key_conf *conf,
240				       struct sta_info *sta, u32 iv32,
241				       u16 *phase1key)
242{
243	struct ieee80211_sta *ista = NULL;
244
245	if (sta)
246		ista = &sta->sta;
247
248	sdata = get_bss_sdata(sdata);
249	if (!check_sdata_in_driver(sdata))
250		return;
251
252	trace_drv_update_tkip_key(local, sdata, conf, ista, iv32);
253	if (local->ops->update_tkip_key)
254		local->ops->update_tkip_key(&local->hw, &sdata->vif, conf,
255					    ista, iv32, phase1key);
256	trace_drv_return_void(local);
257}
258
259static inline int drv_hw_scan(struct ieee80211_local *local,
260			      struct ieee80211_sub_if_data *sdata,
261			      struct ieee80211_scan_request *req)
262{
263	int ret;
264
265	might_sleep();
266
267	if (!check_sdata_in_driver(sdata))
268		return -EIO;
269
270	trace_drv_hw_scan(local, sdata);
271	ret = local->ops->hw_scan(&local->hw, &sdata->vif, req);
272	trace_drv_return_int(local, ret);
273	return ret;
274}
275
276static inline void drv_cancel_hw_scan(struct ieee80211_local *local,
277				      struct ieee80211_sub_if_data *sdata)
278{
279	might_sleep();
280
281	if (!check_sdata_in_driver(sdata))
282		return;
283
284	trace_drv_cancel_hw_scan(local, sdata);
285	local->ops->cancel_hw_scan(&local->hw, &sdata->vif);
286	trace_drv_return_void(local);
287}
288
289static inline int
290drv_sched_scan_start(struct ieee80211_local *local,
291		     struct ieee80211_sub_if_data *sdata,
292		     struct cfg80211_sched_scan_request *req,
293		     struct ieee80211_scan_ies *ies)
294{
295	int ret;
296
297	might_sleep();
298
299	if (!check_sdata_in_driver(sdata))
300		return -EIO;
301
302	trace_drv_sched_scan_start(local, sdata);
303	ret = local->ops->sched_scan_start(&local->hw, &sdata->vif,
304					      req, ies);
305	trace_drv_return_int(local, ret);
306	return ret;
307}
308
309static inline int drv_sched_scan_stop(struct ieee80211_local *local,
310				      struct ieee80211_sub_if_data *sdata)
311{
312	int ret;
313
314	might_sleep();
315
316	if (!check_sdata_in_driver(sdata))
317		return -EIO;
318
319	trace_drv_sched_scan_stop(local, sdata);
320	ret = local->ops->sched_scan_stop(&local->hw, &sdata->vif);
321	trace_drv_return_int(local, ret);
322
323	return ret;
324}
325
326static inline void drv_sw_scan_start(struct ieee80211_local *local,
327				     struct ieee80211_sub_if_data *sdata,
328				     const u8 *mac_addr)
329{
330	might_sleep();
331
332	trace_drv_sw_scan_start(local, sdata, mac_addr);
333	if (local->ops->sw_scan_start)
334		local->ops->sw_scan_start(&local->hw, &sdata->vif, mac_addr);
335	trace_drv_return_void(local);
336}
337
338static inline void drv_sw_scan_complete(struct ieee80211_local *local,
339					struct ieee80211_sub_if_data *sdata)
340{
341	might_sleep();
342
343	trace_drv_sw_scan_complete(local, sdata);
344	if (local->ops->sw_scan_complete)
345		local->ops->sw_scan_complete(&local->hw, &sdata->vif);
346	trace_drv_return_void(local);
347}
348
349static inline int drv_get_stats(struct ieee80211_local *local,
350				struct ieee80211_low_level_stats *stats)
351{
352	int ret = -EOPNOTSUPP;
353
354	might_sleep();
355
356	if (local->ops->get_stats)
357		ret = local->ops->get_stats(&local->hw, stats);
358	trace_drv_get_stats(local, stats, ret);
359
360	return ret;
361}
362
363static inline void drv_get_key_seq(struct ieee80211_local *local,
364				   struct ieee80211_key *key,
365				   struct ieee80211_key_seq *seq)
366{
367	if (local->ops->get_key_seq)
368		local->ops->get_key_seq(&local->hw, &key->conf, seq);
369	trace_drv_get_key_seq(local, &key->conf);
370}
371
372static inline int drv_set_frag_threshold(struct ieee80211_local *local,
373					u32 value)
374{
375	int ret = 0;
376
377	might_sleep();
378
379	trace_drv_set_frag_threshold(local, value);
380	if (local->ops->set_frag_threshold)
381		ret = local->ops->set_frag_threshold(&local->hw, value);
382	trace_drv_return_int(local, ret);
383	return ret;
384}
385
386static inline int drv_set_rts_threshold(struct ieee80211_local *local,
387					u32 value)
388{
389	int ret = 0;
390
391	might_sleep();
392
393	trace_drv_set_rts_threshold(local, value);
394	if (local->ops->set_rts_threshold)
395		ret = local->ops->set_rts_threshold(&local->hw, value);
396	trace_drv_return_int(local, ret);
397	return ret;
398}
399
400static inline int drv_set_coverage_class(struct ieee80211_local *local,
401					 s16 value)
402{
403	int ret = 0;
404	might_sleep();
405
406	trace_drv_set_coverage_class(local, value);
407	if (local->ops->set_coverage_class)
408		local->ops->set_coverage_class(&local->hw, value);
409	else
410		ret = -EOPNOTSUPP;
411
412	trace_drv_return_int(local, ret);
413	return ret;
414}
415
416static inline void drv_sta_notify(struct ieee80211_local *local,
417				  struct ieee80211_sub_if_data *sdata,
418				  enum sta_notify_cmd cmd,
419				  struct ieee80211_sta *sta)
420{
421	sdata = get_bss_sdata(sdata);
422	if (!check_sdata_in_driver(sdata))
423		return;
424
425	trace_drv_sta_notify(local, sdata, cmd, sta);
426	if (local->ops->sta_notify)
427		local->ops->sta_notify(&local->hw, &sdata->vif, cmd, sta);
428	trace_drv_return_void(local);
429}
430
431static inline int drv_sta_add(struct ieee80211_local *local,
432			      struct ieee80211_sub_if_data *sdata,
433			      struct ieee80211_sta *sta)
434{
435	int ret = 0;
436
437	might_sleep();
438
439	sdata = get_bss_sdata(sdata);
440	if (!check_sdata_in_driver(sdata))
441		return -EIO;
442
443	trace_drv_sta_add(local, sdata, sta);
444	if (local->ops->sta_add)
445		ret = local->ops->sta_add(&local->hw, &sdata->vif, sta);
446
447	trace_drv_return_int(local, ret);
448
449	return ret;
450}
451
452static inline void drv_sta_remove(struct ieee80211_local *local,
453				  struct ieee80211_sub_if_data *sdata,
454				  struct ieee80211_sta *sta)
455{
456	might_sleep();
457
458	sdata = get_bss_sdata(sdata);
459	if (!check_sdata_in_driver(sdata))
460		return;
461
462	trace_drv_sta_remove(local, sdata, sta);
463	if (local->ops->sta_remove)
464		local->ops->sta_remove(&local->hw, &sdata->vif, sta);
465
466	trace_drv_return_void(local);
467}
468
469#ifdef CONFIG_MAC80211_DEBUGFS
470static inline void drv_link_add_debugfs(struct ieee80211_local *local,
471					struct ieee80211_sub_if_data *sdata,
472					struct ieee80211_bss_conf *link_conf,
473					struct dentry *dir)
474{
475	might_sleep();
476
477	sdata = get_bss_sdata(sdata);
478	if (!check_sdata_in_driver(sdata))
479		return;
480
481	if (local->ops->link_add_debugfs)
482		local->ops->link_add_debugfs(&local->hw, &sdata->vif,
483					     link_conf, dir);
484}
485
486static inline void drv_sta_add_debugfs(struct ieee80211_local *local,
487				       struct ieee80211_sub_if_data *sdata,
488				       struct ieee80211_sta *sta,
489				       struct dentry *dir)
490{
491	might_sleep();
492
493	sdata = get_bss_sdata(sdata);
494	if (!check_sdata_in_driver(sdata))
495		return;
496
497	if (local->ops->sta_add_debugfs)
498		local->ops->sta_add_debugfs(&local->hw, &sdata->vif,
499					    sta, dir);
500}
501
502static inline void drv_link_sta_add_debugfs(struct ieee80211_local *local,
503					    struct ieee80211_sub_if_data *sdata,
504					    struct ieee80211_link_sta *link_sta,
505					    struct dentry *dir)
506{
507	might_sleep();
508
509	sdata = get_bss_sdata(sdata);
510	if (!check_sdata_in_driver(sdata))
511		return;
512
513	if (local->ops->link_sta_add_debugfs)
514		local->ops->link_sta_add_debugfs(&local->hw, &sdata->vif,
515						 link_sta, dir);
516}
517#endif
518
519static inline void drv_sta_pre_rcu_remove(struct ieee80211_local *local,
520					  struct ieee80211_sub_if_data *sdata,
521					  struct sta_info *sta)
522{
523	might_sleep();
524
525	sdata = get_bss_sdata(sdata);
526	if (!check_sdata_in_driver(sdata))
527		return;
528
529	trace_drv_sta_pre_rcu_remove(local, sdata, &sta->sta);
530	if (local->ops->sta_pre_rcu_remove)
531		local->ops->sta_pre_rcu_remove(&local->hw, &sdata->vif,
532					       &sta->sta);
533	trace_drv_return_void(local);
534}
535
536__must_check
537int drv_sta_state(struct ieee80211_local *local,
538		  struct ieee80211_sub_if_data *sdata,
539		  struct sta_info *sta,
540		  enum ieee80211_sta_state old_state,
541		  enum ieee80211_sta_state new_state);
542
543__must_check
544int drv_sta_set_txpwr(struct ieee80211_local *local,
545		      struct ieee80211_sub_if_data *sdata,
546		      struct sta_info *sta);
547
548void drv_sta_rc_update(struct ieee80211_local *local,
549		       struct ieee80211_sub_if_data *sdata,
550		       struct ieee80211_sta *sta, u32 changed);
551
552static inline void drv_sta_rate_tbl_update(struct ieee80211_local *local,
553					   struct ieee80211_sub_if_data *sdata,
554					   struct ieee80211_sta *sta)
555{
556	sdata = get_bss_sdata(sdata);
557	if (!check_sdata_in_driver(sdata))
558		return;
559
560	trace_drv_sta_rate_tbl_update(local, sdata, sta);
561	if (local->ops->sta_rate_tbl_update)
562		local->ops->sta_rate_tbl_update(&local->hw, &sdata->vif, sta);
563
564	trace_drv_return_void(local);
565}
566
567static inline void drv_sta_statistics(struct ieee80211_local *local,
568				      struct ieee80211_sub_if_data *sdata,
569				      struct ieee80211_sta *sta,
570				      struct station_info *sinfo)
571{
572	sdata = get_bss_sdata(sdata);
573	if (!check_sdata_in_driver(sdata))
574		return;
575
576	trace_drv_sta_statistics(local, sdata, sta);
577	if (local->ops->sta_statistics)
578		local->ops->sta_statistics(&local->hw, &sdata->vif, sta, sinfo);
579	trace_drv_return_void(local);
580}
581
582int drv_conf_tx(struct ieee80211_local *local,
583		struct ieee80211_link_data *link, u16 ac,
584		const struct ieee80211_tx_queue_params *params);
585
586u64 drv_get_tsf(struct ieee80211_local *local,
587		struct ieee80211_sub_if_data *sdata);
588void drv_set_tsf(struct ieee80211_local *local,
589		 struct ieee80211_sub_if_data *sdata,
590		 u64 tsf);
591void drv_offset_tsf(struct ieee80211_local *local,
592		    struct ieee80211_sub_if_data *sdata,
593		    s64 offset);
594void drv_reset_tsf(struct ieee80211_local *local,
595		   struct ieee80211_sub_if_data *sdata);
596
597static inline int drv_tx_last_beacon(struct ieee80211_local *local)
598{
599	int ret = 0; /* default unsupported op for less congestion */
600
601	might_sleep();
602
603	trace_drv_tx_last_beacon(local);
604	if (local->ops->tx_last_beacon)
605		ret = local->ops->tx_last_beacon(&local->hw);
606	trace_drv_return_int(local, ret);
607	return ret;
608}
609
610int drv_ampdu_action(struct ieee80211_local *local,
611		     struct ieee80211_sub_if_data *sdata,
612		     struct ieee80211_ampdu_params *params);
613
614static inline int drv_get_survey(struct ieee80211_local *local, int idx,
615				struct survey_info *survey)
616{
617	int ret = -EOPNOTSUPP;
618
619	trace_drv_get_survey(local, idx, survey);
620
621	if (local->ops->get_survey)
622		ret = local->ops->get_survey(&local->hw, idx, survey);
623
624	trace_drv_return_int(local, ret);
625
626	return ret;
627}
628
629static inline void drv_rfkill_poll(struct ieee80211_local *local)
630{
631	might_sleep();
632
633	if (local->ops->rfkill_poll)
634		local->ops->rfkill_poll(&local->hw);
635}
636
637static inline void drv_flush(struct ieee80211_local *local,
638			     struct ieee80211_sub_if_data *sdata,
639			     u32 queues, bool drop)
640{
641	struct ieee80211_vif *vif;
642
643	might_sleep();
644
645	sdata = get_bss_sdata(sdata);
646	vif = sdata ? &sdata->vif : NULL;
647
648	if (sdata && !check_sdata_in_driver(sdata))
649		return;
650
651	trace_drv_flush(local, queues, drop);
652	if (local->ops->flush)
653		local->ops->flush(&local->hw, vif, queues, drop);
654	trace_drv_return_void(local);
655}
656
657static inline void drv_flush_sta(struct ieee80211_local *local,
658				 struct ieee80211_sub_if_data *sdata,
659				 struct sta_info *sta)
660{
661	might_sleep();
662
663	sdata = get_bss_sdata(sdata);
664
665	if (sdata && !check_sdata_in_driver(sdata))
666		return;
667
668	trace_drv_flush_sta(local, sdata, &sta->sta);
669	if (local->ops->flush_sta)
670		local->ops->flush_sta(&local->hw, &sdata->vif, &sta->sta);
671	trace_drv_return_void(local);
672}
673
674static inline void drv_channel_switch(struct ieee80211_local *local,
675				      struct ieee80211_sub_if_data *sdata,
676				      struct ieee80211_channel_switch *ch_switch)
677{
678	might_sleep();
679
680	trace_drv_channel_switch(local, sdata, ch_switch);
681	local->ops->channel_switch(&local->hw, &sdata->vif, ch_switch);
682	trace_drv_return_void(local);
683}
684
685
686static inline int drv_set_antenna(struct ieee80211_local *local,
687				  u32 tx_ant, u32 rx_ant)
688{
689	int ret = -EOPNOTSUPP;
690	might_sleep();
691	if (local->ops->set_antenna)
692		ret = local->ops->set_antenna(&local->hw, tx_ant, rx_ant);
693	trace_drv_set_antenna(local, tx_ant, rx_ant, ret);
694	return ret;
695}
696
697static inline int drv_get_antenna(struct ieee80211_local *local,
698				  u32 *tx_ant, u32 *rx_ant)
699{
700	int ret = -EOPNOTSUPP;
701	might_sleep();
702	if (local->ops->get_antenna)
703		ret = local->ops->get_antenna(&local->hw, tx_ant, rx_ant);
704	trace_drv_get_antenna(local, *tx_ant, *rx_ant, ret);
705	return ret;
706}
707
708static inline int drv_remain_on_channel(struct ieee80211_local *local,
709					struct ieee80211_sub_if_data *sdata,
710					struct ieee80211_channel *chan,
711					unsigned int duration,
712					enum ieee80211_roc_type type)
713{
714	int ret;
715
716	might_sleep();
717
718	trace_drv_remain_on_channel(local, sdata, chan, duration, type);
719	ret = local->ops->remain_on_channel(&local->hw, &sdata->vif,
720					    chan, duration, type);
721	trace_drv_return_int(local, ret);
722
723	return ret;
724}
725
726static inline int
727drv_cancel_remain_on_channel(struct ieee80211_local *local,
728			     struct ieee80211_sub_if_data *sdata)
729{
730	int ret;
731
732	might_sleep();
733
734	trace_drv_cancel_remain_on_channel(local, sdata);
735	ret = local->ops->cancel_remain_on_channel(&local->hw, &sdata->vif);
736	trace_drv_return_int(local, ret);
737
738	return ret;
739}
740
741static inline int drv_set_ringparam(struct ieee80211_local *local,
742				    u32 tx, u32 rx)
743{
744	int ret = -ENOTSUPP;
745
746	might_sleep();
747
748	trace_drv_set_ringparam(local, tx, rx);
749	if (local->ops->set_ringparam)
750		ret = local->ops->set_ringparam(&local->hw, tx, rx);
751	trace_drv_return_int(local, ret);
752
753	return ret;
754}
755
756static inline void drv_get_ringparam(struct ieee80211_local *local,
757				     u32 *tx, u32 *tx_max, u32 *rx, u32 *rx_max)
758{
759	might_sleep();
760
761	trace_drv_get_ringparam(local, tx, tx_max, rx, rx_max);
762	if (local->ops->get_ringparam)
763		local->ops->get_ringparam(&local->hw, tx, tx_max, rx, rx_max);
764	trace_drv_return_void(local);
765}
766
767static inline bool drv_tx_frames_pending(struct ieee80211_local *local)
768{
769	bool ret = false;
770
771	might_sleep();
772
773	trace_drv_tx_frames_pending(local);
774	if (local->ops->tx_frames_pending)
775		ret = local->ops->tx_frames_pending(&local->hw);
776	trace_drv_return_bool(local, ret);
777
778	return ret;
779}
780
781static inline int drv_set_bitrate_mask(struct ieee80211_local *local,
782				       struct ieee80211_sub_if_data *sdata,
783				       const struct cfg80211_bitrate_mask *mask)
784{
785	int ret = -EOPNOTSUPP;
786
787	might_sleep();
788
789	if (!check_sdata_in_driver(sdata))
790		return -EIO;
791
792	trace_drv_set_bitrate_mask(local, sdata, mask);
793	if (local->ops->set_bitrate_mask)
794		ret = local->ops->set_bitrate_mask(&local->hw,
795						   &sdata->vif, mask);
796	trace_drv_return_int(local, ret);
797
798	return ret;
799}
800
801static inline void drv_set_rekey_data(struct ieee80211_local *local,
802				      struct ieee80211_sub_if_data *sdata,
803				      struct cfg80211_gtk_rekey_data *data)
804{
805	if (!check_sdata_in_driver(sdata))
806		return;
807
808	trace_drv_set_rekey_data(local, sdata, data);
809	if (local->ops->set_rekey_data)
810		local->ops->set_rekey_data(&local->hw, &sdata->vif, data);
811	trace_drv_return_void(local);
812}
813
814static inline void drv_event_callback(struct ieee80211_local *local,
815				      struct ieee80211_sub_if_data *sdata,
816				      const struct ieee80211_event *event)
817{
818	trace_drv_event_callback(local, sdata, event);
819	if (local->ops->event_callback)
820		local->ops->event_callback(&local->hw, &sdata->vif, event);
821	trace_drv_return_void(local);
822}
823
824static inline void
825drv_release_buffered_frames(struct ieee80211_local *local,
826			    struct sta_info *sta, u16 tids, int num_frames,
827			    enum ieee80211_frame_release_type reason,
828			    bool more_data)
829{
830	trace_drv_release_buffered_frames(local, &sta->sta, tids, num_frames,
831					  reason, more_data);
832	if (local->ops->release_buffered_frames)
833		local->ops->release_buffered_frames(&local->hw, &sta->sta, tids,
834						    num_frames, reason,
835						    more_data);
836	trace_drv_return_void(local);
837}
838
839static inline void
840drv_allow_buffered_frames(struct ieee80211_local *local,
841			  struct sta_info *sta, u16 tids, int num_frames,
842			  enum ieee80211_frame_release_type reason,
843			  bool more_data)
844{
845	trace_drv_allow_buffered_frames(local, &sta->sta, tids, num_frames,
846					reason, more_data);
847	if (local->ops->allow_buffered_frames)
848		local->ops->allow_buffered_frames(&local->hw, &sta->sta,
849						  tids, num_frames, reason,
850						  more_data);
851	trace_drv_return_void(local);
852}
853
854static inline void drv_mgd_prepare_tx(struct ieee80211_local *local,
855				      struct ieee80211_sub_if_data *sdata,
856				      struct ieee80211_prep_tx_info *info)
857{
858	might_sleep();
859
860	if (!check_sdata_in_driver(sdata))
861		return;
862	WARN_ON_ONCE(sdata->vif.type != NL80211_IFTYPE_STATION);
863
864	trace_drv_mgd_prepare_tx(local, sdata, info->duration,
865				 info->subtype, info->success);
866	if (local->ops->mgd_prepare_tx)
867		local->ops->mgd_prepare_tx(&local->hw, &sdata->vif, info);
868	trace_drv_return_void(local);
869}
870
871static inline void drv_mgd_complete_tx(struct ieee80211_local *local,
872				       struct ieee80211_sub_if_data *sdata,
873				       struct ieee80211_prep_tx_info *info)
874{
875	might_sleep();
876
877	if (!check_sdata_in_driver(sdata))
878		return;
879	WARN_ON_ONCE(sdata->vif.type != NL80211_IFTYPE_STATION);
880
881	trace_drv_mgd_complete_tx(local, sdata, info->duration,
882				  info->subtype, info->success);
883	if (local->ops->mgd_complete_tx)
884		local->ops->mgd_complete_tx(&local->hw, &sdata->vif, info);
885	trace_drv_return_void(local);
886}
887
888static inline void
889drv_mgd_protect_tdls_discover(struct ieee80211_local *local,
890			      struct ieee80211_sub_if_data *sdata)
891{
892	might_sleep();
893
894	if (!check_sdata_in_driver(sdata))
895		return;
896	WARN_ON_ONCE(sdata->vif.type != NL80211_IFTYPE_STATION);
897
898	trace_drv_mgd_protect_tdls_discover(local, sdata);
899	if (local->ops->mgd_protect_tdls_discover)
900		local->ops->mgd_protect_tdls_discover(&local->hw, &sdata->vif);
901	trace_drv_return_void(local);
902}
903
904static inline int drv_add_chanctx(struct ieee80211_local *local,
905				  struct ieee80211_chanctx *ctx)
906{
907	int ret = -EOPNOTSUPP;
908
909	might_sleep();
910
911	trace_drv_add_chanctx(local, ctx);
912	if (local->ops->add_chanctx)
913		ret = local->ops->add_chanctx(&local->hw, &ctx->conf);
914	trace_drv_return_int(local, ret);
915	if (!ret)
916		ctx->driver_present = true;
917
918	return ret;
919}
920
921static inline void drv_remove_chanctx(struct ieee80211_local *local,
922				      struct ieee80211_chanctx *ctx)
923{
924	might_sleep();
925
926	if (WARN_ON(!ctx->driver_present))
927		return;
928
929	trace_drv_remove_chanctx(local, ctx);
930	if (local->ops->remove_chanctx)
931		local->ops->remove_chanctx(&local->hw, &ctx->conf);
932	trace_drv_return_void(local);
933	ctx->driver_present = false;
934}
935
936static inline void drv_change_chanctx(struct ieee80211_local *local,
937				      struct ieee80211_chanctx *ctx,
938				      u32 changed)
939{
940	might_sleep();
941
942	trace_drv_change_chanctx(local, ctx, changed);
943	if (local->ops->change_chanctx) {
944		WARN_ON_ONCE(!ctx->driver_present);
945		local->ops->change_chanctx(&local->hw, &ctx->conf, changed);
946	}
947	trace_drv_return_void(local);
948}
949
950static inline void drv_verify_link_exists(struct ieee80211_sub_if_data *sdata,
951					  struct ieee80211_bss_conf *link_conf)
952{
953	/* deflink always exists, so need to check only for other links */
954	if (sdata->deflink.conf != link_conf)
955		sdata_assert_lock(sdata);
956}
957
958int drv_assign_vif_chanctx(struct ieee80211_local *local,
959			   struct ieee80211_sub_if_data *sdata,
960			   struct ieee80211_bss_conf *link_conf,
961			   struct ieee80211_chanctx *ctx);
962void drv_unassign_vif_chanctx(struct ieee80211_local *local,
963			      struct ieee80211_sub_if_data *sdata,
964			      struct ieee80211_bss_conf *link_conf,
965			      struct ieee80211_chanctx *ctx);
966int drv_switch_vif_chanctx(struct ieee80211_local *local,
967			   struct ieee80211_vif_chanctx_switch *vifs,
968			   int n_vifs, enum ieee80211_chanctx_switch_mode mode);
969
970static inline int drv_start_ap(struct ieee80211_local *local,
971			       struct ieee80211_sub_if_data *sdata,
972			       struct ieee80211_bss_conf *link_conf)
973{
974	int ret = 0;
975
976	/* make sure link_conf is protected */
977	drv_verify_link_exists(sdata, link_conf);
978
979	might_sleep();
980
981	if (!check_sdata_in_driver(sdata))
982		return -EIO;
983
984	trace_drv_start_ap(local, sdata, link_conf);
985	if (local->ops->start_ap)
986		ret = local->ops->start_ap(&local->hw, &sdata->vif, link_conf);
987	trace_drv_return_int(local, ret);
988	return ret;
989}
990
991static inline void drv_stop_ap(struct ieee80211_local *local,
992			       struct ieee80211_sub_if_data *sdata,
993			       struct ieee80211_bss_conf *link_conf)
994{
995	/* make sure link_conf is protected */
996	drv_verify_link_exists(sdata, link_conf);
997
998	if (!check_sdata_in_driver(sdata))
999		return;
1000
1001	trace_drv_stop_ap(local, sdata, link_conf);
1002	if (local->ops->stop_ap)
1003		local->ops->stop_ap(&local->hw, &sdata->vif, link_conf);
1004	trace_drv_return_void(local);
1005}
1006
1007static inline void
1008drv_reconfig_complete(struct ieee80211_local *local,
1009		      enum ieee80211_reconfig_type reconfig_type)
1010{
1011	might_sleep();
1012
1013	trace_drv_reconfig_complete(local, reconfig_type);
1014	if (local->ops->reconfig_complete)
1015		local->ops->reconfig_complete(&local->hw, reconfig_type);
1016	trace_drv_return_void(local);
1017}
1018
1019static inline void
1020drv_set_default_unicast_key(struct ieee80211_local *local,
1021			    struct ieee80211_sub_if_data *sdata,
1022			    int key_idx)
1023{
1024	if (!check_sdata_in_driver(sdata))
1025		return;
1026
1027	WARN_ON_ONCE(key_idx < -1 || key_idx > 3);
1028
1029	trace_drv_set_default_unicast_key(local, sdata, key_idx);
1030	if (local->ops->set_default_unicast_key)
1031		local->ops->set_default_unicast_key(&local->hw, &sdata->vif,
1032						    key_idx);
1033	trace_drv_return_void(local);
1034}
1035
1036#if IS_ENABLED(CONFIG_IPV6)
1037static inline void drv_ipv6_addr_change(struct ieee80211_local *local,
1038					struct ieee80211_sub_if_data *sdata,
1039					struct inet6_dev *idev)
1040{
1041	trace_drv_ipv6_addr_change(local, sdata);
1042	if (local->ops->ipv6_addr_change)
1043		local->ops->ipv6_addr_change(&local->hw, &sdata->vif, idev);
1044	trace_drv_return_void(local);
1045}
1046#endif
1047
1048static inline void
1049drv_channel_switch_beacon(struct ieee80211_sub_if_data *sdata,
1050			  struct cfg80211_chan_def *chandef)
1051{
1052	struct ieee80211_local *local = sdata->local;
1053
1054	if (local->ops->channel_switch_beacon) {
1055		trace_drv_channel_switch_beacon(local, sdata, chandef);
1056		local->ops->channel_switch_beacon(&local->hw, &sdata->vif,
1057						  chandef);
1058	}
1059}
1060
1061static inline int
1062drv_pre_channel_switch(struct ieee80211_sub_if_data *sdata,
1063		       struct ieee80211_channel_switch *ch_switch)
1064{
1065	struct ieee80211_local *local = sdata->local;
1066	int ret = 0;
1067
1068	if (!check_sdata_in_driver(sdata))
1069		return -EIO;
1070
1071	trace_drv_pre_channel_switch(local, sdata, ch_switch);
1072	if (local->ops->pre_channel_switch)
1073		ret = local->ops->pre_channel_switch(&local->hw, &sdata->vif,
1074						     ch_switch);
1075	trace_drv_return_int(local, ret);
1076	return ret;
1077}
1078
1079static inline int
1080drv_post_channel_switch(struct ieee80211_sub_if_data *sdata)
1081{
1082	struct ieee80211_local *local = sdata->local;
1083	int ret = 0;
1084
1085	if (!check_sdata_in_driver(sdata))
1086		return -EIO;
1087
1088	trace_drv_post_channel_switch(local, sdata);
1089	if (local->ops->post_channel_switch)
1090		ret = local->ops->post_channel_switch(&local->hw, &sdata->vif);
1091	trace_drv_return_int(local, ret);
1092	return ret;
1093}
1094
1095static inline void
1096drv_abort_channel_switch(struct ieee80211_sub_if_data *sdata)
1097{
1098	struct ieee80211_local *local = sdata->local;
1099
1100	if (!check_sdata_in_driver(sdata))
1101		return;
1102
1103	trace_drv_abort_channel_switch(local, sdata);
1104
1105	if (local->ops->abort_channel_switch)
1106		local->ops->abort_channel_switch(&local->hw, &sdata->vif);
1107}
1108
1109static inline void
1110drv_channel_switch_rx_beacon(struct ieee80211_sub_if_data *sdata,
1111			     struct ieee80211_channel_switch *ch_switch)
1112{
1113	struct ieee80211_local *local = sdata->local;
1114
1115	if (!check_sdata_in_driver(sdata))
1116		return;
1117
1118	trace_drv_channel_switch_rx_beacon(local, sdata, ch_switch);
1119	if (local->ops->channel_switch_rx_beacon)
1120		local->ops->channel_switch_rx_beacon(&local->hw, &sdata->vif,
1121						     ch_switch);
1122}
1123
1124static inline int drv_join_ibss(struct ieee80211_local *local,
1125				struct ieee80211_sub_if_data *sdata)
1126{
1127	int ret = 0;
1128
1129	might_sleep();
1130	if (!check_sdata_in_driver(sdata))
1131		return -EIO;
1132
1133	trace_drv_join_ibss(local, sdata, &sdata->vif.bss_conf);
1134	if (local->ops->join_ibss)
1135		ret = local->ops->join_ibss(&local->hw, &sdata->vif);
1136	trace_drv_return_int(local, ret);
1137	return ret;
1138}
1139
1140static inline void drv_leave_ibss(struct ieee80211_local *local,
1141				  struct ieee80211_sub_if_data *sdata)
1142{
1143	might_sleep();
1144	if (!check_sdata_in_driver(sdata))
1145		return;
1146
1147	trace_drv_leave_ibss(local, sdata);
1148	if (local->ops->leave_ibss)
1149		local->ops->leave_ibss(&local->hw, &sdata->vif);
1150	trace_drv_return_void(local);
1151}
1152
1153static inline u32 drv_get_expected_throughput(struct ieee80211_local *local,
1154					      struct sta_info *sta)
1155{
1156	u32 ret = 0;
1157
1158	trace_drv_get_expected_throughput(&sta->sta);
1159	if (local->ops->get_expected_throughput && sta->uploaded)
1160		ret = local->ops->get_expected_throughput(&local->hw, &sta->sta);
1161	trace_drv_return_u32(local, ret);
1162
1163	return ret;
1164}
1165
1166static inline int drv_get_txpower(struct ieee80211_local *local,
1167				  struct ieee80211_sub_if_data *sdata, int *dbm)
1168{
1169	int ret;
1170
1171	if (!local->ops->get_txpower)
1172		return -EOPNOTSUPP;
1173
1174	ret = local->ops->get_txpower(&local->hw, &sdata->vif, dbm);
1175	trace_drv_get_txpower(local, sdata, *dbm, ret);
1176
1177	return ret;
1178}
1179
1180static inline int
1181drv_tdls_channel_switch(struct ieee80211_local *local,
1182			struct ieee80211_sub_if_data *sdata,
1183			struct ieee80211_sta *sta, u8 oper_class,
1184			struct cfg80211_chan_def *chandef,
1185			struct sk_buff *tmpl_skb, u32 ch_sw_tm_ie)
1186{
1187	int ret;
1188
1189	might_sleep();
1190	if (!check_sdata_in_driver(sdata))
1191		return -EIO;
1192
1193	if (!local->ops->tdls_channel_switch)
1194		return -EOPNOTSUPP;
1195
1196	trace_drv_tdls_channel_switch(local, sdata, sta, oper_class, chandef);
1197	ret = local->ops->tdls_channel_switch(&local->hw, &sdata->vif, sta,
1198					      oper_class, chandef, tmpl_skb,
1199					      ch_sw_tm_ie);
1200	trace_drv_return_int(local, ret);
1201	return ret;
1202}
1203
1204static inline void
1205drv_tdls_cancel_channel_switch(struct ieee80211_local *local,
1206			       struct ieee80211_sub_if_data *sdata,
1207			       struct ieee80211_sta *sta)
1208{
1209	might_sleep();
1210	if (!check_sdata_in_driver(sdata))
1211		return;
1212
1213	if (!local->ops->tdls_cancel_channel_switch)
1214		return;
1215
1216	trace_drv_tdls_cancel_channel_switch(local, sdata, sta);
1217	local->ops->tdls_cancel_channel_switch(&local->hw, &sdata->vif, sta);
1218	trace_drv_return_void(local);
1219}
1220
1221static inline void
1222drv_tdls_recv_channel_switch(struct ieee80211_local *local,
1223			     struct ieee80211_sub_if_data *sdata,
1224			     struct ieee80211_tdls_ch_sw_params *params)
1225{
1226	trace_drv_tdls_recv_channel_switch(local, sdata, params);
1227	if (local->ops->tdls_recv_channel_switch)
1228		local->ops->tdls_recv_channel_switch(&local->hw, &sdata->vif,
1229						     params);
1230	trace_drv_return_void(local);
1231}
1232
1233static inline void drv_wake_tx_queue(struct ieee80211_local *local,
1234				     struct txq_info *txq)
1235{
1236	struct ieee80211_sub_if_data *sdata = vif_to_sdata(txq->txq.vif);
1237
1238	/* In reconfig don't transmit now, but mark for waking later */
1239	if (local->in_reconfig) {
1240		set_bit(IEEE80211_TXQ_DIRTY, &txq->flags);
1241		return;
1242	}
1243
1244	if (!check_sdata_in_driver(sdata))
1245		return;
1246
1247	trace_drv_wake_tx_queue(local, sdata, txq);
1248	local->ops->wake_tx_queue(&local->hw, &txq->txq);
1249}
1250
1251static inline void schedule_and_wake_txq(struct ieee80211_local *local,
1252					 struct txq_info *txqi)
1253{
1254	ieee80211_schedule_txq(&local->hw, &txqi->txq);
1255	drv_wake_tx_queue(local, txqi);
1256}
1257
1258static inline int drv_can_aggregate_in_amsdu(struct ieee80211_local *local,
1259					     struct sk_buff *head,
1260					     struct sk_buff *skb)
1261{
1262	if (!local->ops->can_aggregate_in_amsdu)
1263		return true;
1264
1265	return local->ops->can_aggregate_in_amsdu(&local->hw, head, skb);
1266}
1267
1268static inline int
1269drv_get_ftm_responder_stats(struct ieee80211_local *local,
1270			    struct ieee80211_sub_if_data *sdata,
1271			    struct cfg80211_ftm_responder_stats *ftm_stats)
1272{
1273	u32 ret = -EOPNOTSUPP;
1274
1275	if (local->ops->get_ftm_responder_stats)
1276		ret = local->ops->get_ftm_responder_stats(&local->hw,
1277							 &sdata->vif,
1278							 ftm_stats);
1279	trace_drv_get_ftm_responder_stats(local, sdata, ftm_stats);
1280
1281	return ret;
1282}
1283
1284static inline int drv_start_pmsr(struct ieee80211_local *local,
1285				 struct ieee80211_sub_if_data *sdata,
1286				 struct cfg80211_pmsr_request *request)
1287{
1288	int ret = -EOPNOTSUPP;
1289
1290	might_sleep();
1291	if (!check_sdata_in_driver(sdata))
1292		return -EIO;
1293
1294	trace_drv_start_pmsr(local, sdata);
1295
1296	if (local->ops->start_pmsr)
1297		ret = local->ops->start_pmsr(&local->hw, &sdata->vif, request);
1298	trace_drv_return_int(local, ret);
1299
1300	return ret;
1301}
1302
1303static inline void drv_abort_pmsr(struct ieee80211_local *local,
1304				  struct ieee80211_sub_if_data *sdata,
1305				  struct cfg80211_pmsr_request *request)
1306{
1307	trace_drv_abort_pmsr(local, sdata);
1308
1309	might_sleep();
1310	if (!check_sdata_in_driver(sdata))
1311		return;
1312
1313	if (local->ops->abort_pmsr)
1314		local->ops->abort_pmsr(&local->hw, &sdata->vif, request);
1315	trace_drv_return_void(local);
1316}
1317
1318static inline int drv_start_nan(struct ieee80211_local *local,
1319				struct ieee80211_sub_if_data *sdata,
1320				struct cfg80211_nan_conf *conf)
1321{
1322	int ret;
1323
1324	might_sleep();
1325	check_sdata_in_driver(sdata);
1326
1327	trace_drv_start_nan(local, sdata, conf);
1328	ret = local->ops->start_nan(&local->hw, &sdata->vif, conf);
1329	trace_drv_return_int(local, ret);
1330	return ret;
1331}
1332
1333static inline void drv_stop_nan(struct ieee80211_local *local,
1334				struct ieee80211_sub_if_data *sdata)
1335{
1336	might_sleep();
1337	check_sdata_in_driver(sdata);
1338
1339	trace_drv_stop_nan(local, sdata);
1340	local->ops->stop_nan(&local->hw, &sdata->vif);
1341	trace_drv_return_void(local);
1342}
1343
1344static inline int drv_nan_change_conf(struct ieee80211_local *local,
1345				       struct ieee80211_sub_if_data *sdata,
1346				       struct cfg80211_nan_conf *conf,
1347				       u32 changes)
1348{
1349	int ret;
1350
1351	might_sleep();
1352	check_sdata_in_driver(sdata);
1353
1354	if (!local->ops->nan_change_conf)
1355		return -EOPNOTSUPP;
1356
1357	trace_drv_nan_change_conf(local, sdata, conf, changes);
1358	ret = local->ops->nan_change_conf(&local->hw, &sdata->vif, conf,
1359					  changes);
1360	trace_drv_return_int(local, ret);
1361
1362	return ret;
1363}
1364
1365static inline int drv_add_nan_func(struct ieee80211_local *local,
1366				   struct ieee80211_sub_if_data *sdata,
1367				   const struct cfg80211_nan_func *nan_func)
1368{
1369	int ret;
1370
1371	might_sleep();
1372	check_sdata_in_driver(sdata);
1373
1374	if (!local->ops->add_nan_func)
1375		return -EOPNOTSUPP;
1376
1377	trace_drv_add_nan_func(local, sdata, nan_func);
1378	ret = local->ops->add_nan_func(&local->hw, &sdata->vif, nan_func);
1379	trace_drv_return_int(local, ret);
1380
1381	return ret;
1382}
1383
1384static inline void drv_del_nan_func(struct ieee80211_local *local,
1385				   struct ieee80211_sub_if_data *sdata,
1386				   u8 instance_id)
1387{
1388	might_sleep();
1389	check_sdata_in_driver(sdata);
1390
1391	trace_drv_del_nan_func(local, sdata, instance_id);
1392	if (local->ops->del_nan_func)
1393		local->ops->del_nan_func(&local->hw, &sdata->vif, instance_id);
1394	trace_drv_return_void(local);
1395}
1396
1397static inline int drv_set_tid_config(struct ieee80211_local *local,
1398				     struct ieee80211_sub_if_data *sdata,
1399				     struct ieee80211_sta *sta,
1400				     struct cfg80211_tid_config *tid_conf)
1401{
1402	int ret;
1403
1404	might_sleep();
1405	ret = local->ops->set_tid_config(&local->hw, &sdata->vif, sta,
1406					 tid_conf);
1407	trace_drv_return_int(local, ret);
1408
1409	return ret;
1410}
1411
1412static inline int drv_reset_tid_config(struct ieee80211_local *local,
1413				       struct ieee80211_sub_if_data *sdata,
1414				       struct ieee80211_sta *sta, u8 tids)
1415{
1416	int ret;
1417
1418	might_sleep();
1419	ret = local->ops->reset_tid_config(&local->hw, &sdata->vif, sta, tids);
1420	trace_drv_return_int(local, ret);
1421
1422	return ret;
1423}
1424
1425static inline void drv_update_vif_offload(struct ieee80211_local *local,
1426					  struct ieee80211_sub_if_data *sdata)
1427{
1428	might_sleep();
1429	check_sdata_in_driver(sdata);
1430
1431	if (!local->ops->update_vif_offload)
1432		return;
1433
1434	trace_drv_update_vif_offload(local, sdata);
1435	local->ops->update_vif_offload(&local->hw, &sdata->vif);
1436	trace_drv_return_void(local);
1437}
1438
1439static inline void drv_sta_set_4addr(struct ieee80211_local *local,
1440				     struct ieee80211_sub_if_data *sdata,
1441				     struct ieee80211_sta *sta, bool enabled)
1442{
1443	sdata = get_bss_sdata(sdata);
1444	if (!check_sdata_in_driver(sdata))
1445		return;
1446
1447	trace_drv_sta_set_4addr(local, sdata, sta, enabled);
1448	if (local->ops->sta_set_4addr)
1449		local->ops->sta_set_4addr(&local->hw, &sdata->vif, sta, enabled);
1450	trace_drv_return_void(local);
1451}
1452
1453static inline void drv_sta_set_decap_offload(struct ieee80211_local *local,
1454					     struct ieee80211_sub_if_data *sdata,
1455					     struct ieee80211_sta *sta,
1456					     bool enabled)
1457{
1458	sdata = get_bss_sdata(sdata);
1459	if (!check_sdata_in_driver(sdata))
1460		return;
1461
1462	trace_drv_sta_set_decap_offload(local, sdata, sta, enabled);
1463	if (local->ops->sta_set_decap_offload)
1464		local->ops->sta_set_decap_offload(&local->hw, &sdata->vif, sta,
1465						  enabled);
1466	trace_drv_return_void(local);
1467}
1468
1469static inline void drv_add_twt_setup(struct ieee80211_local *local,
1470				     struct ieee80211_sub_if_data *sdata,
1471				     struct ieee80211_sta *sta,
1472				     struct ieee80211_twt_setup *twt)
1473{
1474	struct ieee80211_twt_params *twt_agrt;
1475
1476	might_sleep();
1477
1478	if (!check_sdata_in_driver(sdata))
1479		return;
1480
1481	twt_agrt = (void *)twt->params;
1482
1483	trace_drv_add_twt_setup(local, sta, twt, twt_agrt);
1484	local->ops->add_twt_setup(&local->hw, sta, twt);
1485	trace_drv_return_void(local);
1486}
1487
1488static inline void drv_twt_teardown_request(struct ieee80211_local *local,
1489					    struct ieee80211_sub_if_data *sdata,
1490					    struct ieee80211_sta *sta,
1491					    u8 flowid)
1492{
1493	might_sleep();
1494	if (!check_sdata_in_driver(sdata))
1495		return;
1496
1497	if (!local->ops->twt_teardown_request)
1498		return;
1499
1500	trace_drv_twt_teardown_request(local, sta, flowid);
1501	local->ops->twt_teardown_request(&local->hw, sta, flowid);
1502	trace_drv_return_void(local);
1503}
1504
1505static inline int drv_net_fill_forward_path(struct ieee80211_local *local,
1506					    struct ieee80211_sub_if_data *sdata,
1507					    struct ieee80211_sta *sta,
1508					    struct net_device_path_ctx *ctx,
1509					    struct net_device_path *path)
1510{
1511	int ret = -EOPNOTSUPP;
1512
1513	sdata = get_bss_sdata(sdata);
1514	if (!check_sdata_in_driver(sdata))
1515		return -EIO;
1516
1517	trace_drv_net_fill_forward_path(local, sdata, sta);
1518	if (local->ops->net_fill_forward_path)
1519		ret = local->ops->net_fill_forward_path(&local->hw,
1520							&sdata->vif, sta,
1521							ctx, path);
1522	trace_drv_return_int(local, ret);
1523
1524	return ret;
1525}
1526
1527static inline int drv_net_setup_tc(struct ieee80211_local *local,
1528				   struct ieee80211_sub_if_data *sdata,
1529				   struct net_device *dev,
1530				   enum tc_setup_type type, void *type_data)
1531{
1532	int ret = -EOPNOTSUPP;
1533
1534	sdata = get_bss_sdata(sdata);
1535	trace_drv_net_setup_tc(local, sdata, type);
1536	if (local->ops->net_setup_tc)
1537		ret = local->ops->net_setup_tc(&local->hw, &sdata->vif, dev,
1538					       type, type_data);
1539	trace_drv_return_int(local, ret);
1540
1541	return ret;
1542}
1543
1544int drv_change_vif_links(struct ieee80211_local *local,
1545			 struct ieee80211_sub_if_data *sdata,
1546			 u16 old_links, u16 new_links,
1547			 struct ieee80211_bss_conf *old[IEEE80211_MLD_MAX_NUM_LINKS]);
1548int drv_change_sta_links(struct ieee80211_local *local,
1549			 struct ieee80211_sub_if_data *sdata,
1550			 struct ieee80211_sta *sta,
1551			 u16 old_links, u16 new_links);
1552
1553#endif /* __MAC80211_DRIVER_OPS */
1554