16b4cac81SBjoern A. Zeeb /*- 28ac540d3SBjoern A. Zeeb * Copyright (c) 2020-2023 The FreeBSD Foundation 36b4cac81SBjoern A. Zeeb * Copyright (c) 2020-2021 Bjoern A. Zeeb 46b4cac81SBjoern A. Zeeb * 56b4cac81SBjoern A. Zeeb * This software was developed by Björn Zeeb under sponsorship from 66b4cac81SBjoern A. Zeeb * the FreeBSD Foundation. 76b4cac81SBjoern A. Zeeb * 86b4cac81SBjoern A. Zeeb * Redistribution and use in source and binary forms, with or without 96b4cac81SBjoern A. Zeeb * modification, are permitted provided that the following conditions 106b4cac81SBjoern A. Zeeb * are met: 116b4cac81SBjoern A. Zeeb * 1. Redistributions of source code must retain the above copyright 126b4cac81SBjoern A. Zeeb * notice, this list of conditions and the following disclaimer. 136b4cac81SBjoern A. Zeeb * 2. Redistributions in binary form must reproduce the above copyright 146b4cac81SBjoern A. Zeeb * notice, this list of conditions and the following disclaimer in the 156b4cac81SBjoern A. Zeeb * documentation and/or other materials provided with the distribution. 166b4cac81SBjoern A. Zeeb * 176b4cac81SBjoern A. Zeeb * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 186b4cac81SBjoern A. Zeeb * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 196b4cac81SBjoern A. Zeeb * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 206b4cac81SBjoern A. Zeeb * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 216b4cac81SBjoern A. Zeeb * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 226b4cac81SBjoern A. Zeeb * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 236b4cac81SBjoern A. Zeeb * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 246b4cac81SBjoern A. Zeeb * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 256b4cac81SBjoern A. Zeeb * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 266b4cac81SBjoern A. Zeeb * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 276b4cac81SBjoern A. Zeeb * SUCH DAMAGE. 286b4cac81SBjoern A. Zeeb */ 296b4cac81SBjoern A. Zeeb 306b4cac81SBjoern A. Zeeb /* 316b4cac81SBjoern A. Zeeb * Public functions are called linuxkpi_*(). 326b4cac81SBjoern A. Zeeb * Internal (static) functions are called lkpi_*(). 336b4cac81SBjoern A. Zeeb * 346b4cac81SBjoern A. Zeeb * The internal structures holding metadata over public structures are also 356b4cac81SBjoern A. Zeeb * called lkpi_xxx (usually with a member at the end called xxx). 366b4cac81SBjoern A. Zeeb * Note: we do not replicate the structure names but the general variable names 376b4cac81SBjoern A. Zeeb * for these (e.g., struct hw -> struct lkpi_hw, struct sta -> struct lkpi_sta). 386b4cac81SBjoern A. Zeeb * There are macros to access one from the other. 396b4cac81SBjoern A. Zeeb * We call the internal versions lxxx (e.g., hw -> lhw, sta -> lsta). 406b4cac81SBjoern A. Zeeb */ 416b4cac81SBjoern A. Zeeb 426b4cac81SBjoern A. Zeeb #ifndef _LKPI_SRC_LINUX_80211_H 436b4cac81SBjoern A. Zeeb #define _LKPI_SRC_LINUX_80211_H 446b4cac81SBjoern A. Zeeb 4559d262feSBjoern A. Zeeb #include "opt_wlan.h" 4659d262feSBjoern A. Zeeb 4759d262feSBjoern A. Zeeb #if defined(IEEE80211_DEBUG) && !defined(LINUXKPI_DEBUG_80211) 4859d262feSBjoern A. Zeeb #define LINUXKPI_DEBUG_80211 4959d262feSBjoern A. Zeeb #endif 5059d262feSBjoern A. Zeeb 5164d3da00SBjoern A. Zeeb /* #define LINUXKPI_DEBUG_80211 */ 5264d3da00SBjoern A. Zeeb 5364d3da00SBjoern A. Zeeb #ifndef D80211_TODO 548895b476SBjoern A. Zeeb #define D80211_TODO 0x00000001 5564d3da00SBjoern A. Zeeb #endif 5664d3da00SBjoern A. Zeeb #ifndef D80211_IMPROVE 578895b476SBjoern A. Zeeb #define D80211_IMPROVE 0x00000002 5864d3da00SBjoern A. Zeeb #endif 598895b476SBjoern A. Zeeb #define D80211_IMPROVE_TXQ 0x00000004 608895b476SBjoern A. Zeeb #define D80211_TRACE 0x00000010 618895b476SBjoern A. Zeeb #define D80211_TRACEOK 0x00000020 628895b476SBjoern A. Zeeb #define D80211_TRACE_TX 0x00000100 638895b476SBjoern A. Zeeb #define D80211_TRACE_TX_DUMP 0x00000200 648895b476SBjoern A. Zeeb #define D80211_TRACE_RX 0x00001000 658895b476SBjoern A. Zeeb #define D80211_TRACE_RX_DUMP 0x00002000 668895b476SBjoern A. Zeeb #define D80211_TRACE_RX_BEACONS 0x00004000 6764d3da00SBjoern A. Zeeb #define D80211_TRACEX (D80211_TRACE_TX|D80211_TRACE_RX) 6864d3da00SBjoern A. Zeeb #define D80211_TRACEX_DUMP (D80211_TRACE_TX_DUMP|D80211_TRACE_RX_DUMP) 698895b476SBjoern A. Zeeb #define D80211_TRACE_STA 0x00010000 7011db70b6SBjoern A. Zeeb #define D80211_TRACE_HW_CRYPTO 0x00020000 718895b476SBjoern A. Zeeb #define D80211_TRACE_MO 0x00100000 729fb91463SBjoern A. Zeeb #define D80211_TRACE_MODE 0x0f000000 739fb91463SBjoern A. Zeeb #define D80211_TRACE_MODE_HT 0x01000000 749fb91463SBjoern A. Zeeb #define D80211_TRACE_MODE_VHT 0x02000000 759fb91463SBjoern A. Zeeb #define D80211_TRACE_MODE_HE 0x04000000 769fb91463SBjoern A. Zeeb #define D80211_TRACE_MODE_EHT 0x08000000 7764d3da00SBjoern A. Zeeb 785a9a0d78SBjoern A. Zeeb #define IMPROVE_TXQ(...) \ 795a9a0d78SBjoern A. Zeeb if (linuxkpi_debug_80211 & D80211_IMPROVE_TXQ) \ 805a9a0d78SBjoern A. Zeeb printf("%s:%d: XXX LKPI80211 IMPROVE_TXQ\n", __func__, __LINE__) 815a9a0d78SBjoern A. Zeeb 82a4cdb785SBjoern A. Zeeb #define IMPROVE_HT(fmt, ...) \ 839fb91463SBjoern A. Zeeb if (linuxkpi_debug_80211 & D80211_TRACE_MODE_HT) \ 84a4cdb785SBjoern A. Zeeb printf("%s:%d: XXX LKPI80211 IMPROVE_HT " fmt "\n", \ 85a4cdb785SBjoern A. Zeeb __func__, __LINE__, ##__VA_ARGS__); 869fb91463SBjoern A. Zeeb 87759a996dSBjoern A. Zeeb #define MTAG_ABI_LKPI80211 1707696513 /* LinuxKPI 802.11 KBI */ 88759a996dSBjoern A. Zeeb 89759a996dSBjoern A. Zeeb /* 90759a996dSBjoern A. Zeeb * Deferred RX path. 91759a996dSBjoern A. Zeeb * We need to pass *ni along (and possibly more in the future so 92759a996dSBjoern A. Zeeb * we use a struct right from the start. 93759a996dSBjoern A. Zeeb */ 94759a996dSBjoern A. Zeeb #define LKPI80211_TAG_RXNI 0 /* deferred RX path */ 95759a996dSBjoern A. Zeeb struct lkpi_80211_tag_rxni { 96759a996dSBjoern A. Zeeb struct ieee80211_node *ni; /* MUST hold a reference to it. */ 97759a996dSBjoern A. Zeeb }; 98759a996dSBjoern A. Zeeb 996b4cac81SBjoern A. Zeeb struct lkpi_radiotap_tx_hdr { 1006b4cac81SBjoern A. Zeeb struct ieee80211_radiotap_header wt_ihdr; 1016b4cac81SBjoern A. Zeeb uint8_t wt_flags; 1026b4cac81SBjoern A. Zeeb uint8_t wt_rate; 1036b4cac81SBjoern A. Zeeb uint16_t wt_chan_freq; 1046b4cac81SBjoern A. Zeeb uint16_t wt_chan_flags; 1056b4cac81SBjoern A. Zeeb } __packed; 1066b4cac81SBjoern A. Zeeb #define LKPI_RTAP_TX_FLAGS_PRESENT \ 1076b4cac81SBjoern A. Zeeb ((1 << IEEE80211_RADIOTAP_FLAGS) | \ 1086b4cac81SBjoern A. Zeeb (1 << IEEE80211_RADIOTAP_RATE) | \ 1096b4cac81SBjoern A. Zeeb (1 << IEEE80211_RADIOTAP_CHANNEL)) 1106b4cac81SBjoern A. Zeeb 1116b4cac81SBjoern A. Zeeb struct lkpi_radiotap_rx_hdr { 1126b4cac81SBjoern A. Zeeb struct ieee80211_radiotap_header wr_ihdr; 1136b4cac81SBjoern A. Zeeb uint64_t wr_tsft; 1146b4cac81SBjoern A. Zeeb uint8_t wr_flags; 1156b4cac81SBjoern A. Zeeb uint8_t wr_rate; 1166b4cac81SBjoern A. Zeeb uint16_t wr_chan_freq; 1176b4cac81SBjoern A. Zeeb uint16_t wr_chan_flags; 1186b4cac81SBjoern A. Zeeb int8_t wr_dbm_antsignal; 1196b4cac81SBjoern A. Zeeb int8_t wr_dbm_antnoise; 1206b4cac81SBjoern A. Zeeb } __packed __aligned(8); 1216b4cac81SBjoern A. Zeeb #define LKPI_RTAP_RX_FLAGS_PRESENT \ 1226b4cac81SBjoern A. Zeeb ((1 << IEEE80211_RADIOTAP_TSFT) | \ 1236b4cac81SBjoern A. Zeeb (1 << IEEE80211_RADIOTAP_FLAGS) | \ 1246b4cac81SBjoern A. Zeeb (1 << IEEE80211_RADIOTAP_RATE) | \ 1256b4cac81SBjoern A. Zeeb (1 << IEEE80211_RADIOTAP_CHANNEL) | \ 1266b4cac81SBjoern A. Zeeb (1 << IEEE80211_RADIOTAP_DBM_ANTSIGNAL) | \ 1276b4cac81SBjoern A. Zeeb (1 << IEEE80211_RADIOTAP_DBM_ANTNOISE)) 1286b4cac81SBjoern A. Zeeb 129*a8f735a6SBjoern A. Zeeb struct lkpi_hw; 130*a8f735a6SBjoern A. Zeeb 1316b4cac81SBjoern A. Zeeb struct lkpi_txq { 1325a9a0d78SBjoern A. Zeeb TAILQ_ENTRY(lkpi_txq) txq_entry; 1335a9a0d78SBjoern A. Zeeb 134eac3646fSBjoern A. Zeeb struct mtx ltxq_mtx; 1356b4cac81SBjoern A. Zeeb bool seen_dequeue; 1365a9a0d78SBjoern A. Zeeb bool stopped; 1375a9a0d78SBjoern A. Zeeb uint32_t txq_generation; 1386b4cac81SBjoern A. Zeeb struct sk_buff_head skbq; 1396b4cac81SBjoern A. Zeeb 1406b4cac81SBjoern A. Zeeb /* Must be last! */ 1416b4cac81SBjoern A. Zeeb struct ieee80211_txq txq __aligned(CACHE_LINE_SIZE); 1426b4cac81SBjoern A. Zeeb }; 1436b4cac81SBjoern A. Zeeb #define TXQ_TO_LTXQ(_txq) container_of(_txq, struct lkpi_txq, txq) 1446b4cac81SBjoern A. Zeeb 1456b4cac81SBjoern A. Zeeb 1466b4cac81SBjoern A. Zeeb struct lkpi_sta { 147*a8f735a6SBjoern A. Zeeb struct list_head lsta_list; 1486b4cac81SBjoern A. Zeeb struct ieee80211_node *ni; 149*a8f735a6SBjoern A. Zeeb struct ieee80211_hw *hw; /* back pointer f. locking. */ 1506b4cac81SBjoern A. Zeeb 1516b4cac81SBjoern A. Zeeb /* Deferred TX path. */ 1526b4cac81SBjoern A. Zeeb /* Eventually we might want to migrate this into net80211 entirely. */ 1536b4cac81SBjoern A. Zeeb /* XXX-BZ can we use sta->txq[] instead directly? */ 1546b4cac81SBjoern A. Zeeb struct task txq_task; 1556b4cac81SBjoern A. Zeeb struct mbufq txq; 1566b4cac81SBjoern A. Zeeb struct mtx txq_mtx; 1576b4cac81SBjoern A. Zeeb 15811db70b6SBjoern A. Zeeb struct ieee80211_key_conf *kc[IEEE80211_WEP_NKID]; 1596b4cac81SBjoern A. Zeeb enum ieee80211_sta_state state; 1600936c648SBjoern A. Zeeb bool txq_ready; /* Can we run the taskq? */ 1616b4cac81SBjoern A. Zeeb bool added_to_drv; /* Driver knows; i.e. we called ...(). */ 162d9f59799SBjoern A. Zeeb bool in_mgd; /* XXX-BZ should this be per-vif? */ 1636b4cac81SBjoern A. Zeeb 1646b4cac81SBjoern A. Zeeb /* Must be last! */ 1656b4cac81SBjoern A. Zeeb struct ieee80211_sta sta __aligned(CACHE_LINE_SIZE); 1666b4cac81SBjoern A. Zeeb }; 1676b4cac81SBjoern A. Zeeb #define STA_TO_LSTA(_sta) container_of(_sta, struct lkpi_sta, sta) 1686b4cac81SBjoern A. Zeeb #define LSTA_TO_STA(_lsta) (&(_lsta)->sta) 1696b4cac81SBjoern A. Zeeb 170*a8f735a6SBjoern A. Zeeb /* Either protected by wiphy lock or rcu for the list. */ 1716b4cac81SBjoern A. Zeeb struct lkpi_vif { 1726b4cac81SBjoern A. Zeeb TAILQ_ENTRY(lkpi_vif) lvif_entry; 1736b4cac81SBjoern A. Zeeb struct ieee80211vap iv_vap; 1744aff4048SBjoern A. Zeeb eventhandler_tag lvif_ifllevent; 1756b4cac81SBjoern A. Zeeb 17640839418SBjoern A. Zeeb struct sysctl_ctx_list sysctl_ctx; 17740839418SBjoern A. Zeeb 1786b4cac81SBjoern A. Zeeb struct mtx mtx; 1796b4cac81SBjoern A. Zeeb struct wireless_dev wdev; 1806b4cac81SBjoern A. Zeeb 1816b4cac81SBjoern A. Zeeb /* Other local stuff. */ 1826b4cac81SBjoern A. Zeeb int (*iv_newstate)(struct ieee80211vap *, 1836b4cac81SBjoern A. Zeeb enum ieee80211_state, int); 184d9f59799SBjoern A. Zeeb struct ieee80211_node * (*iv_update_bss)(struct ieee80211vap *, 185d9f59799SBjoern A. Zeeb struct ieee80211_node *); 186*a8f735a6SBjoern A. Zeeb struct list_head lsta_list; 187*a8f735a6SBjoern A. Zeeb 1882ac8a218SBjoern A. Zeeb struct lkpi_sta *lvif_bss; 1892ac8a218SBjoern A. Zeeb bool lvif_bss_synched; 1906b4cac81SBjoern A. Zeeb bool added_to_drv; /* Driver knows; i.e. we called add_interface(). */ 1916b4cac81SBjoern A. Zeeb 1925a9a0d78SBjoern A. Zeeb bool hw_queue_stopped[IEEE80211_NUM_ACS]; 1935a9a0d78SBjoern A. Zeeb 1946b4cac81SBjoern A. Zeeb /* Must be last! */ 1956b4cac81SBjoern A. Zeeb struct ieee80211_vif vif __aligned(CACHE_LINE_SIZE); 1966b4cac81SBjoern A. Zeeb }; 1976b4cac81SBjoern A. Zeeb #define VAP_TO_LVIF(_vap) container_of(_vap, struct lkpi_vif, iv_vap) 1986b4cac81SBjoern A. Zeeb #define LVIF_TO_VAP(_lvif) (&(_lvif)->iv_vap) 1996b4cac81SBjoern A. Zeeb #define VIF_TO_LVIF(_vif) container_of(_vif, struct lkpi_vif, vif) 2006b4cac81SBjoern A. Zeeb #define LVIF_TO_VIF(_lvif) (&(_lvif)->vif) 2016b4cac81SBjoern A. Zeeb 2026b4cac81SBjoern A. Zeeb 2036b4cac81SBjoern A. Zeeb struct lkpi_hw { /* name it mac80211_sc? */ 2046b4cac81SBjoern A. Zeeb const struct ieee80211_ops *ops; 2056b4cac81SBjoern A. Zeeb struct ieee80211_scan_request *hw_req; 2066b4cac81SBjoern A. Zeeb struct workqueue_struct *workq; 2076b4cac81SBjoern A. Zeeb 2086b4cac81SBjoern A. Zeeb /* FreeBSD specific compat. */ 2096b4cac81SBjoern A. Zeeb /* Linux device is in hw.wiphy->dev after SET_IEEE80211_DEV(). */ 2106b4cac81SBjoern A. Zeeb struct ieee80211com *ic; 2116b4cac81SBjoern A. Zeeb struct lkpi_radiotap_tx_hdr rtap_tx; 2126b4cac81SBjoern A. Zeeb struct lkpi_radiotap_rx_hdr rtap_rx; 2136b4cac81SBjoern A. Zeeb 2146b4cac81SBjoern A. Zeeb TAILQ_HEAD(, lkpi_vif) lvif_head; 2158891c455SBjoern A. Zeeb struct sx lvif_sx; 2166b4cac81SBjoern A. Zeeb 217ac1d519cSBjoern A. Zeeb struct sx sx; /* XXX-BZ Can this be wiphy->mtx in the future? */ 2186b4cac81SBjoern A. Zeeb 219eac3646fSBjoern A. Zeeb struct mtx txq_mtx; 2205a9a0d78SBjoern A. Zeeb uint32_t txq_generation[IEEE80211_NUM_ACS]; 2215a9a0d78SBjoern A. Zeeb TAILQ_HEAD(, lkpi_txq) scheduled_txqs[IEEE80211_NUM_ACS]; 2225a9a0d78SBjoern A. Zeeb 223759a996dSBjoern A. Zeeb /* Deferred RX path. */ 224759a996dSBjoern A. Zeeb struct task rxq_task; 225759a996dSBjoern A. Zeeb struct mbufq rxq; 226759a996dSBjoern A. Zeeb struct mtx rxq_mtx; 227759a996dSBjoern A. Zeeb 228a486fbbdSBjoern A. Zeeb /* Scan functions we overload to handle depending on scan mode. */ 229a486fbbdSBjoern A. Zeeb void (*ic_scan_curchan)(struct ieee80211_scan_state *, 230a486fbbdSBjoern A. Zeeb unsigned long); 231a486fbbdSBjoern A. Zeeb void (*ic_scan_mindwell)(struct ieee80211_scan_state *); 232a486fbbdSBjoern A. Zeeb 2336b4cac81SBjoern A. Zeeb /* Node functions we overload to sync state. */ 2346b4cac81SBjoern A. Zeeb struct ieee80211_node * (*ic_node_alloc)(struct ieee80211vap *, 2356b4cac81SBjoern A. Zeeb const uint8_t [IEEE80211_ADDR_LEN]); 2366b4cac81SBjoern A. Zeeb int (*ic_node_init)(struct ieee80211_node *); 2376b4cac81SBjoern A. Zeeb void (*ic_node_cleanup)(struct ieee80211_node *); 2386b4cac81SBjoern A. Zeeb void (*ic_node_free)(struct ieee80211_node *); 2396b4cac81SBjoern A. Zeeb 2409fb91463SBjoern A. Zeeb /* HT and later functions. */ 2419fb91463SBjoern A. Zeeb int (*ic_recv_action)(struct ieee80211_node *, 2429fb91463SBjoern A. Zeeb const struct ieee80211_frame *, 2439fb91463SBjoern A. Zeeb const uint8_t *, const uint8_t *); 2449fb91463SBjoern A. Zeeb int (*ic_send_action)(struct ieee80211_node *, 2459fb91463SBjoern A. Zeeb int, int, void *); 2469fb91463SBjoern A. Zeeb int (*ic_ampdu_enable)(struct ieee80211_node *, 2479fb91463SBjoern A. Zeeb struct ieee80211_tx_ampdu *); 2489fb91463SBjoern A. Zeeb int (*ic_addba_request)(struct ieee80211_node *, 2499fb91463SBjoern A. Zeeb struct ieee80211_tx_ampdu *, int, int, int); 2509fb91463SBjoern A. Zeeb int (*ic_addba_response)(struct ieee80211_node *, 2519fb91463SBjoern A. Zeeb struct ieee80211_tx_ampdu *, int, int, int); 2529fb91463SBjoern A. Zeeb void (*ic_addba_stop)(struct ieee80211_node *, 2539fb91463SBjoern A. Zeeb struct ieee80211_tx_ampdu *); 2549fb91463SBjoern A. Zeeb void (*ic_addba_response_timeout)(struct ieee80211_node *, 2559fb91463SBjoern A. Zeeb struct ieee80211_tx_ampdu *); 2569fb91463SBjoern A. Zeeb void (*ic_bar_response)(struct ieee80211_node *, 2579fb91463SBjoern A. Zeeb struct ieee80211_tx_ampdu *, int); 2589fb91463SBjoern A. Zeeb int (*ic_ampdu_rx_start)(struct ieee80211_node *, 2599fb91463SBjoern A. Zeeb struct ieee80211_rx_ampdu *, int, int, int); 2609fb91463SBjoern A. Zeeb void (*ic_ampdu_rx_stop)(struct ieee80211_node *, 2619fb91463SBjoern A. Zeeb struct ieee80211_rx_ampdu *); 2629fb91463SBjoern A. Zeeb 2636b4cac81SBjoern A. Zeeb #define LKPI_MAC80211_DRV_STARTED 0x00000001 2646b4cac81SBjoern A. Zeeb uint32_t sc_flags; 265a486fbbdSBjoern A. Zeeb #define LKPI_LHW_SCAN_RUNNING 0x00000001 266a486fbbdSBjoern A. Zeeb #define LKPI_LHW_SCAN_HW 0x00000002 2676b4cac81SBjoern A. Zeeb uint32_t scan_flags; 2688ac540d3SBjoern A. Zeeb struct mtx scan_mtx; 269d9945d78SBjoern A. Zeeb 270d9945d78SBjoern A. Zeeb int supbands; /* Number of supported bands. */ 271d9945d78SBjoern A. Zeeb int max_rates; /* Maximum number of bitrates supported in any channel. */ 272d9945d78SBjoern A. Zeeb int scan_ie_len; /* Length of common per-band scan IEs. */ 273d9945d78SBjoern A. Zeeb 2746b4cac81SBjoern A. Zeeb bool update_mc; 2754a67f1dfSBjoern A. Zeeb bool update_wme; 276759a996dSBjoern A. Zeeb bool rxq_stopped; 2776b4cac81SBjoern A. Zeeb 2786b4cac81SBjoern A. Zeeb /* Must be last! */ 2796b4cac81SBjoern A. Zeeb struct ieee80211_hw hw __aligned(CACHE_LINE_SIZE); 2806b4cac81SBjoern A. Zeeb }; 2816b4cac81SBjoern A. Zeeb #define LHW_TO_HW(_lhw) (&(_lhw)->hw) 2826b4cac81SBjoern A. Zeeb #define HW_TO_LHW(_hw) container_of(_hw, struct lkpi_hw, hw) 2836b4cac81SBjoern A. Zeeb 284c5e25798SBjoern A. Zeeb struct lkpi_chanctx { 285c5e25798SBjoern A. Zeeb bool added_to_drv; /* Managed by MO */ 286d1af434dSBjoern A. Zeeb struct ieee80211_chanctx_conf chanctx_conf __aligned(CACHE_LINE_SIZE); 287c5e25798SBjoern A. Zeeb }; 288c5e25798SBjoern A. Zeeb #define LCHANCTX_TO_CHANCTX_CONF(_lchanctx) \ 289d1af434dSBjoern A. Zeeb (&(_lchanctx)->chanctx_conf) 290c5e25798SBjoern A. Zeeb #define CHANCTX_CONF_TO_LCHANCTX(_conf) \ 291d1af434dSBjoern A. Zeeb container_of(_conf, struct lkpi_chanctx, chanctx_conf) 292c5e25798SBjoern A. Zeeb 2936b4cac81SBjoern A. Zeeb struct lkpi_wiphy { 2946b4cac81SBjoern A. Zeeb const struct cfg80211_ops *ops; 2956b4cac81SBjoern A. Zeeb 296ac1d519cSBjoern A. Zeeb struct work_struct wwk; 297ac1d519cSBjoern A. Zeeb struct list_head wwk_list; 298ac1d519cSBjoern A. Zeeb struct mtx wwk_mtx; 299ac1d519cSBjoern A. Zeeb 3006b4cac81SBjoern A. Zeeb /* Must be last! */ 3016b4cac81SBjoern A. Zeeb struct wiphy wiphy __aligned(CACHE_LINE_SIZE); 3026b4cac81SBjoern A. Zeeb }; 3036b4cac81SBjoern A. Zeeb #define WIPHY_TO_LWIPHY(_wiphy) container_of(_wiphy, struct lkpi_wiphy, wiphy) 3046b4cac81SBjoern A. Zeeb #define LWIPHY_TO_WIPHY(_lwiphy) (&(_lwiphy)->wiphy) 3056b4cac81SBjoern A. Zeeb 306ac1d519cSBjoern A. Zeeb #define LKPI_80211_LWIPHY_WORK_LOCK_INIT(_lwiphy) \ 307ac1d519cSBjoern A. Zeeb mtx_init(&(_lwiphy)->wwk_mtx, "lwiphy-work", NULL, MTX_DEF); 308ac1d519cSBjoern A. Zeeb #define LKPI_80211_LWIPHY_WORK_LOCK_DESTROY(_lwiphy) \ 309ac1d519cSBjoern A. Zeeb mtx_destroy(&(_lwiphy)->wwk_mtx) 310ac1d519cSBjoern A. Zeeb #define LKPI_80211_LWIPHY_WORK_LOCK(_lwiphy) \ 311ac1d519cSBjoern A. Zeeb mtx_lock(&(_lwiphy)->wwk_mtx) 312ac1d519cSBjoern A. Zeeb #define LKPI_80211_LWIPHY_WORK_UNLOCK(_lwiphy) \ 313ac1d519cSBjoern A. Zeeb mtx_unlock(&(_lwiphy)->wwk_mtx) 314ac1d519cSBjoern A. Zeeb #define LKPI_80211_LWIPHY_WORK_LOCK_ASSERT(_lwiphy) \ 315ac1d519cSBjoern A. Zeeb mtx_assert(&(_lwiphy)->wwk_mtx, MA_OWNED) 316ac1d519cSBjoern A. Zeeb #define LKPI_80211_LWIPHY_WORK_UNLOCK_ASSERT(_lwiphy) \ 317ac1d519cSBjoern A. Zeeb mtx_assert(&(_lwiphy)->wwk_mtx, MA_NOTOWNED) 318ac1d519cSBjoern A. Zeeb 3198ac540d3SBjoern A. Zeeb #define LKPI_80211_LHW_LOCK_INIT(_lhw) \ 3208ac540d3SBjoern A. Zeeb sx_init_flags(&(_lhw)->sx, "lhw", SX_RECURSE); 3218ac540d3SBjoern A. Zeeb #define LKPI_80211_LHW_LOCK_DESTROY(_lhw) \ 3228ac540d3SBjoern A. Zeeb sx_destroy(&(_lhw)->sx); 3238ac540d3SBjoern A. Zeeb #define LKPI_80211_LHW_LOCK(_lhw) \ 3248ac540d3SBjoern A. Zeeb sx_xlock(&(_lhw)->sx) 3258ac540d3SBjoern A. Zeeb #define LKPI_80211_LHW_UNLOCK(_lhw) \ 3268ac540d3SBjoern A. Zeeb sx_xunlock(&(_lhw)->sx) 3276b4cac81SBjoern A. Zeeb #define LKPI_80211_LHW_LOCK_ASSERT(_lhw) \ 3288ac540d3SBjoern A. Zeeb sx_assert(&(_lhw)->sx, SA_LOCKED) 3296b4cac81SBjoern A. Zeeb #define LKPI_80211_LHW_UNLOCK_ASSERT(_lhw) \ 3308ac540d3SBjoern A. Zeeb sx_assert(&(_lhw)->sx, SA_UNLOCKED) 3318ac540d3SBjoern A. Zeeb 3328ac540d3SBjoern A. Zeeb #define LKPI_80211_LHW_SCAN_LOCK_INIT(_lhw) \ 3338ac540d3SBjoern A. Zeeb mtx_init(&(_lhw)->scan_mtx, "lhw-scan", NULL, MTX_DEF | MTX_RECURSE); 3348ac540d3SBjoern A. Zeeb #define LKPI_80211_LHW_SCAN_LOCK_DESTROY(_lhw) \ 3358ac540d3SBjoern A. Zeeb mtx_destroy(&(_lhw)->scan_mtx); 3368ac540d3SBjoern A. Zeeb #define LKPI_80211_LHW_SCAN_LOCK(_lhw) \ 3378ac540d3SBjoern A. Zeeb mtx_lock(&(_lhw)->scan_mtx) 3388ac540d3SBjoern A. Zeeb #define LKPI_80211_LHW_SCAN_UNLOCK(_lhw) \ 3398ac540d3SBjoern A. Zeeb mtx_unlock(&(_lhw)->scan_mtx) 3408ac540d3SBjoern A. Zeeb #define LKPI_80211_LHW_SCAN_LOCK_ASSERT(_lhw) \ 3418ac540d3SBjoern A. Zeeb mtx_assert(&(_lhw)->scan_mtx, MA_OWNED) 3428ac540d3SBjoern A. Zeeb #define LKPI_80211_LHW_SCAN_UNLOCK_ASSERT(_lhw) \ 3438ac540d3SBjoern A. Zeeb mtx_assert(&(_lhw)->scan_mtx, MA_NOTOWNED) 3446b4cac81SBjoern A. Zeeb 345eac3646fSBjoern A. Zeeb #define LKPI_80211_LHW_TXQ_LOCK_INIT(_lhw) \ 346eac3646fSBjoern A. Zeeb mtx_init(&(_lhw)->txq_mtx, "lhw-txq", NULL, MTX_DEF | MTX_RECURSE); 347eac3646fSBjoern A. Zeeb #define LKPI_80211_LHW_TXQ_LOCK_DESTROY(_lhw) \ 348eac3646fSBjoern A. Zeeb mtx_destroy(&(_lhw)->txq_mtx); 349eac3646fSBjoern A. Zeeb #define LKPI_80211_LHW_TXQ_LOCK(_lhw) \ 350eac3646fSBjoern A. Zeeb mtx_lock(&(_lhw)->txq_mtx) 351eac3646fSBjoern A. Zeeb #define LKPI_80211_LHW_TXQ_UNLOCK(_lhw) \ 352eac3646fSBjoern A. Zeeb mtx_unlock(&(_lhw)->txq_mtx) 353eac3646fSBjoern A. Zeeb #define LKPI_80211_LHW_TXQ_LOCK_ASSERT(_lhw) \ 354eac3646fSBjoern A. Zeeb mtx_assert(&(_lhw)->txq_mtx, MA_OWNED) 355eac3646fSBjoern A. Zeeb #define LKPI_80211_LHW_TXQ_UNLOCK_ASSERT(_lhw) \ 356eac3646fSBjoern A. Zeeb mtx_assert(&(_lhw)->txq_mtx, MA_NOTOWNED) 357eac3646fSBjoern A. Zeeb 358759a996dSBjoern A. Zeeb #define LKPI_80211_LHW_RXQ_LOCK_INIT(_lhw) \ 359759a996dSBjoern A. Zeeb mtx_init(&(_lhw)->rxq_mtx, "lhw-rxq", NULL, MTX_DEF | MTX_RECURSE); 360759a996dSBjoern A. Zeeb #define LKPI_80211_LHW_RXQ_LOCK_DESTROY(_lhw) \ 361759a996dSBjoern A. Zeeb mtx_destroy(&(_lhw)->rxq_mtx); 362759a996dSBjoern A. Zeeb #define LKPI_80211_LHW_RXQ_LOCK(_lhw) \ 363759a996dSBjoern A. Zeeb mtx_lock(&(_lhw)->rxq_mtx) 364759a996dSBjoern A. Zeeb #define LKPI_80211_LHW_RXQ_UNLOCK(_lhw) \ 365759a996dSBjoern A. Zeeb mtx_unlock(&(_lhw)->rxq_mtx) 366759a996dSBjoern A. Zeeb #define LKPI_80211_LHW_RXQ_LOCK_ASSERT(_lhw) \ 367759a996dSBjoern A. Zeeb mtx_assert(&(_lhw)->rxq_mtx, MA_OWNED) 368759a996dSBjoern A. Zeeb #define LKPI_80211_LHW_RXQ_UNLOCK_ASSERT(_lhw) \ 369759a996dSBjoern A. Zeeb mtx_assert(&(_lhw)->rxq_mtx, MA_NOTOWNED) 370759a996dSBjoern A. Zeeb 3718891c455SBjoern A. Zeeb #define LKPI_80211_LHW_LVIF_LOCK(_lhw) sx_xlock(&(_lhw)->lvif_sx) 3728891c455SBjoern A. Zeeb #define LKPI_80211_LHW_LVIF_UNLOCK(_lhw) sx_xunlock(&(_lhw)->lvif_sx) 3738891c455SBjoern A. Zeeb 3746b4cac81SBjoern A. Zeeb #define LKPI_80211_LVIF_LOCK(_lvif) mtx_lock(&(_lvif)->mtx) 3756b4cac81SBjoern A. Zeeb #define LKPI_80211_LVIF_UNLOCK(_lvif) mtx_unlock(&(_lvif)->mtx) 3766b4cac81SBjoern A. Zeeb 377fa4e4257SBjoern A. Zeeb #define LKPI_80211_LSTA_TXQ_LOCK_INIT(_lsta) \ 378fa4e4257SBjoern A. Zeeb mtx_init(&(_lsta)->txq_mtx, "lsta-txq", NULL, MTX_DEF); 379fa4e4257SBjoern A. Zeeb #define LKPI_80211_LSTA_TXQ_LOCK_DESTROY(_lsta) \ 380fa4e4257SBjoern A. Zeeb mtx_destroy(&(_lsta)->txq_mtx); 381fa4e4257SBjoern A. Zeeb #define LKPI_80211_LSTA_TXQ_LOCK(_lsta) \ 382fa4e4257SBjoern A. Zeeb mtx_lock(&(_lsta)->txq_mtx) 383fa4e4257SBjoern A. Zeeb #define LKPI_80211_LSTA_TXQ_UNLOCK(_lsta) \ 384fa4e4257SBjoern A. Zeeb mtx_unlock(&(_lsta)->txq_mtx) 385fa4e4257SBjoern A. Zeeb #define LKPI_80211_LSTA_TXQ_LOCK_ASSERT(_lsta) \ 386fa4e4257SBjoern A. Zeeb mtx_assert(&(_lsta)->txq_mtx, MA_OWNED) 387fa4e4257SBjoern A. Zeeb #define LKPI_80211_LSTA_TXQ_UNLOCK_ASSERT(_lsta) \ 388fa4e4257SBjoern A. Zeeb mtx_assert(&(_lsta)->txq_mtx, MA_NOTOWNED) 3896b4cac81SBjoern A. Zeeb 390eac3646fSBjoern A. Zeeb #define LKPI_80211_LTXQ_LOCK_INIT(_ltxq) \ 391eac3646fSBjoern A. Zeeb mtx_init(&(_ltxq)->ltxq_mtx, "ltxq", NULL, MTX_DEF); 392eac3646fSBjoern A. Zeeb #define LKPI_80211_LTXQ_LOCK_DESTROY(_ltxq) \ 393eac3646fSBjoern A. Zeeb mtx_destroy(&(_ltxq)->ltxq_mtx); 394eac3646fSBjoern A. Zeeb #define LKPI_80211_LTXQ_LOCK(_ltxq) \ 395eac3646fSBjoern A. Zeeb mtx_lock(&(_ltxq)->ltxq_mtx) 396eac3646fSBjoern A. Zeeb #define LKPI_80211_LTXQ_UNLOCK(_ltxq) \ 397eac3646fSBjoern A. Zeeb mtx_unlock(&(_ltxq)->ltxq_mtx) 398eac3646fSBjoern A. Zeeb #define LKPI_80211_LTXQ_LOCK_ASSERT(_ltxq) \ 399eac3646fSBjoern A. Zeeb mtx_assert(&(_ltxq)->ltxq_mtx, MA_OWNED) 400eac3646fSBjoern A. Zeeb #define LKPI_80211_LTXQ_UNLOCK_ASSERT(_ltxq) \ 401eac3646fSBjoern A. Zeeb mtx_assert(&(_ltxq)->ltxq_mtx, MA_NOTOWNED) 4026b4cac81SBjoern A. Zeeb 4036b4cac81SBjoern A. Zeeb int lkpi_80211_mo_start(struct ieee80211_hw *); 4047b43f4d0SBjoern A. Zeeb void lkpi_80211_mo_stop(struct ieee80211_hw *, bool); 405527687a9SBjoern A. Zeeb int lkpi_80211_mo_get_antenna(struct ieee80211_hw *, u32 *, u32 *); 4066b4cac81SBjoern A. Zeeb int lkpi_80211_mo_set_frag_threshold(struct ieee80211_hw *, uint32_t); 4076b4cac81SBjoern A. Zeeb int lkpi_80211_mo_set_rts_threshold(struct ieee80211_hw *, uint32_t); 4086b4cac81SBjoern A. Zeeb int lkpi_80211_mo_add_interface(struct ieee80211_hw *, struct ieee80211_vif *); 4096b4cac81SBjoern A. Zeeb void lkpi_80211_mo_remove_interface(struct ieee80211_hw *, struct ieee80211_vif *); 4106b4cac81SBjoern A. Zeeb int lkpi_80211_mo_hw_scan(struct ieee80211_hw *, struct ieee80211_vif *, 4116b4cac81SBjoern A. Zeeb struct ieee80211_scan_request *); 4126b4cac81SBjoern A. Zeeb void lkpi_80211_mo_cancel_hw_scan(struct ieee80211_hw *, struct ieee80211_vif *); 4136b4cac81SBjoern A. Zeeb void lkpi_80211_mo_sw_scan_complete(struct ieee80211_hw *, struct ieee80211_vif *); 4146b4cac81SBjoern A. Zeeb void lkpi_80211_mo_sw_scan_start(struct ieee80211_hw *, struct ieee80211_vif *, 4156b4cac81SBjoern A. Zeeb const u8 *); 4166b4cac81SBjoern A. Zeeb u64 lkpi_80211_mo_prepare_multicast(struct ieee80211_hw *, 4176b4cac81SBjoern A. Zeeb struct netdev_hw_addr_list *); 4186b4cac81SBjoern A. Zeeb void lkpi_80211_mo_configure_filter(struct ieee80211_hw *, unsigned int, 4196b4cac81SBjoern A. Zeeb unsigned int *, u64); 4206b4cac81SBjoern A. Zeeb int lkpi_80211_mo_sta_state(struct ieee80211_hw *, struct ieee80211_vif *, 421e7fe0373SBjoern A. Zeeb struct lkpi_sta *, enum ieee80211_sta_state); 4226b4cac81SBjoern A. Zeeb int lkpi_80211_mo_config(struct ieee80211_hw *, uint32_t); 4236b4cac81SBjoern A. Zeeb int lkpi_80211_mo_assign_vif_chanctx(struct ieee80211_hw *, struct ieee80211_vif *, 42468541546SBjoern A. Zeeb struct ieee80211_bss_conf *, struct ieee80211_chanctx_conf *); 4256b4cac81SBjoern A. Zeeb void lkpi_80211_mo_unassign_vif_chanctx(struct ieee80211_hw *, struct ieee80211_vif *, 42668541546SBjoern A. Zeeb struct ieee80211_bss_conf *, struct ieee80211_chanctx_conf **); 4276b4cac81SBjoern A. Zeeb int lkpi_80211_mo_add_chanctx(struct ieee80211_hw *, struct ieee80211_chanctx_conf *); 4286b4cac81SBjoern A. Zeeb void lkpi_80211_mo_change_chanctx(struct ieee80211_hw *, 4296b4cac81SBjoern A. Zeeb struct ieee80211_chanctx_conf *, uint32_t); 4306b4cac81SBjoern A. Zeeb void lkpi_80211_mo_remove_chanctx(struct ieee80211_hw *, 4316b4cac81SBjoern A. Zeeb struct ieee80211_chanctx_conf *); 4326b4cac81SBjoern A. Zeeb void lkpi_80211_mo_bss_info_changed(struct ieee80211_hw *, struct ieee80211_vif *, 433467d3e2eSBjoern A. Zeeb struct ieee80211_bss_conf *, uint64_t); 4346b4cac81SBjoern A. Zeeb int lkpi_80211_mo_conf_tx(struct ieee80211_hw *, struct ieee80211_vif *, 43568541546SBjoern A. Zeeb uint32_t, uint16_t, const struct ieee80211_tx_queue_params *); 4366b4cac81SBjoern A. Zeeb void lkpi_80211_mo_flush(struct ieee80211_hw *, struct ieee80211_vif *, 4376b4cac81SBjoern A. Zeeb uint32_t, bool); 4386b4cac81SBjoern A. Zeeb void lkpi_80211_mo_mgd_prepare_tx(struct ieee80211_hw *, struct ieee80211_vif *, 4396b4cac81SBjoern A. Zeeb struct ieee80211_prep_tx_info *); 4406b4cac81SBjoern A. Zeeb void lkpi_80211_mo_mgd_complete_tx(struct ieee80211_hw *, struct ieee80211_vif *, 4416b4cac81SBjoern A. Zeeb struct ieee80211_prep_tx_info *); 4426b4cac81SBjoern A. Zeeb void lkpi_80211_mo_tx(struct ieee80211_hw *, struct ieee80211_tx_control *, 4436b4cac81SBjoern A. Zeeb struct sk_buff *); 4446b4cac81SBjoern A. Zeeb void lkpi_80211_mo_wake_tx_queue(struct ieee80211_hw *, struct ieee80211_txq *); 4456b4cac81SBjoern A. Zeeb void lkpi_80211_mo_sync_rx_queues(struct ieee80211_hw *); 4466b4cac81SBjoern A. Zeeb void lkpi_80211_mo_sta_pre_rcu_remove(struct ieee80211_hw *, 4476b4cac81SBjoern A. Zeeb struct ieee80211_vif *, struct ieee80211_sta *); 4486b4cac81SBjoern A. Zeeb int lkpi_80211_mo_set_key(struct ieee80211_hw *, enum set_key_cmd, 4496b4cac81SBjoern A. Zeeb struct ieee80211_vif *, struct ieee80211_sta *, 4506b4cac81SBjoern A. Zeeb struct ieee80211_key_conf *); 4519fb91463SBjoern A. Zeeb int lkpi_80211_mo_ampdu_action(struct ieee80211_hw *, struct ieee80211_vif *, 4529fb91463SBjoern A. Zeeb struct ieee80211_ampdu_params *); 45340839418SBjoern A. Zeeb int lkpi_80211_mo_sta_statistics(struct ieee80211_hw *, struct ieee80211_vif *, 45440839418SBjoern A. Zeeb struct ieee80211_sta *, struct station_info *); 4556b4cac81SBjoern A. Zeeb 4566b4cac81SBjoern A. Zeeb #endif /* _LKPI_SRC_LINUX_80211_H */ 457