xref: /dragonfly/sys/dev/netif/iwn/if_iwnvar.h (revision 977fc0dbd55bbe973415ca40aeefb0f85e3af012)
1 /*        $FreeBSD$ */
2 /*        $OpenBSD: if_iwnvar.h,v 1.18 2010/04/30 16:06:46 damien Exp $         */
3 
4 /*-
5  * Copyright (c) 2013 Cedric GROSS <cg@cgross.info>
6  * Copyright (c) 2011 Intel Corporation
7  * Copyright (c) 2007, 2008
8  *        Damien Bergamini <damien.bergamini@free.fr>
9  * Copyright (c) 2008 Sam Leffler, Errno Consulting
10  *
11  * Permission to use, copy, modify, and distribute this software for any
12  * purpose with or without fee is hereby granted, provided that the above
13  * copyright notice and this permission notice appear in all copies.
14  *
15  * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
16  * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
17  * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
18  * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
19  * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
20  * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
21  * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
22  */
23 enum iwn_rxon_ctx_id {
24                     IWN_RXON_BSS_CTX,
25                     IWN_RXON_PAN_CTX,
26                     IWN_NUM_RXON_CTX
27 };
28 
29 struct iwn_pan_slot {
30           uint16_t  time;
31           uint8_t             type;
32           uint8_t             reserved;
33 } __packed;
34 
35 struct iwn_pan_params_cmd {
36           uint16_t flags;
37 #define   IWN_PAN_PARAMS_FLG_SLOTTED_MODE         (1 << 3)
38 
39           uint8_t reserved;
40           uint8_t num_slots;
41           struct iwn_pan_slot slots[10];
42 } __packed;
43 
44 struct iwn_led_mode
45 {
46           uint8_t             led_cur_mode;
47           uint64_t  led_cur_bt;
48           uint64_t  led_last_bt;
49           uint64_t  led_cur_tpt;
50           uint64_t  led_last_tpt;
51           uint64_t  led_bt_diff;
52           int                 led_cur_time;
53           int                 led_last_time;
54 };
55 
56 struct iwn_rx_radiotap_header {
57           struct ieee80211_radiotap_header wr_ihdr;
58           uint64_t  wr_tsft;
59           uint8_t             wr_flags;
60           uint8_t             wr_rate;
61           uint16_t  wr_chan_freq;
62           uint16_t  wr_chan_flags;
63           int8_t              wr_dbm_antsignal;
64           int8_t              wr_dbm_antnoise;
65 } __packed;
66 
67 #define IWN_RX_RADIOTAP_PRESENT                                                           \
68           ((1 << IEEE80211_RADIOTAP_TSFT) |                                     \
69            (1 << IEEE80211_RADIOTAP_FLAGS) |                                    \
70            (1 << IEEE80211_RADIOTAP_RATE) |                                     \
71            (1 << IEEE80211_RADIOTAP_CHANNEL) |                                  \
72            (1 << IEEE80211_RADIOTAP_DBM_ANTSIGNAL) |                            \
73            (1 << IEEE80211_RADIOTAP_DBM_ANTNOISE))
74 
75 struct iwn_tx_radiotap_header {
76           struct ieee80211_radiotap_header wt_ihdr;
77           uint8_t             wt_flags;
78           uint8_t             wt_rate;
79           uint16_t  wt_chan_freq;
80           uint16_t  wt_chan_flags;
81 } __packed;
82 
83 #define IWN_TX_RADIOTAP_PRESENT                                                           \
84           ((1 << IEEE80211_RADIOTAP_FLAGS) |                                    \
85            (1 << IEEE80211_RADIOTAP_RATE) |                                     \
86            (1 << IEEE80211_RADIOTAP_CHANNEL))
87 
88 struct iwn_dma_info {
89           bus_dma_tag_t                 tag;
90           bus_dmamap_t                  map;
91           bus_dma_segment_t   seg;
92           bus_addr_t                    paddr;
93           caddr_t                       vaddr;
94           bus_size_t                    size;
95 };
96 
97 struct iwn_tx_data {
98           bus_dmamap_t                  map;
99           bus_addr_t                    cmd_paddr;
100           bus_addr_t                    scratch_paddr;
101           struct mbuf                   *m;
102           struct ieee80211_node         *ni;
103 };
104 
105 struct iwn_tx_ring {
106           struct iwn_dma_info desc_dma;
107           struct iwn_dma_info cmd_dma;
108           struct iwn_tx_desc  *desc;
109           struct iwn_tx_cmd   *cmd;
110           struct iwn_tx_data  data[IWN_TX_RING_COUNT];
111           bus_dma_tag_t                 data_dmat;
112           int                           qid;
113           int                           queued;
114           int                           cur;
115           int                           read;
116 };
117 
118 struct iwn_softc;
119 
120 struct iwn_rx_data {
121           struct mbuf         *m;
122           bus_dmamap_t        map;
123 };
124 
125 struct iwn_rx_ring {
126           struct iwn_dma_info desc_dma;
127           struct iwn_dma_info stat_dma;
128           uint32_t            *desc;
129           struct iwn_rx_status          *stat;
130           struct iwn_rx_data  data[IWN_RX_RING_COUNT];
131           bus_dma_tag_t                 data_dmat;
132           int                           cur;
133 };
134 
135 struct iwn_node {
136           struct    ieee80211_node                ni;       /* must be the first */
137           uint16_t                      disable_tid;
138           uint8_t                                 id;
139           struct {
140                     uint64_t            bitmap;
141                     int                           startidx;
142                     int                           nframes;
143           } agg[IEEE80211_TID_SIZE];
144 };
145 
146 struct iwn_calib_state {
147           uint8_t             state;
148 #define IWN_CALIB_STATE_INIT  0
149 #define IWN_CALIB_STATE_ASSOC 1
150 #define IWN_CALIB_STATE_RUN   2
151 
152           u_int               nbeacons;
153           uint32_t  noise[3];
154           uint32_t  rssi[3];
155           uint32_t  ofdm_x1;
156           uint32_t  ofdm_mrc_x1;
157           uint32_t  ofdm_x4;
158           uint32_t  ofdm_mrc_x4;
159           uint32_t  cck_x4;
160           uint32_t  cck_mrc_x4;
161           uint32_t  bad_plcp_ofdm;
162           uint32_t  fa_ofdm;
163           uint32_t  bad_plcp_cck;
164           uint32_t  fa_cck;
165           uint32_t  low_fa;
166           uint32_t  bad_plcp_ht;
167           uint8_t             cck_state;
168 #define IWN_CCK_STATE_INIT    0
169 #define IWN_CCK_STATE_LOFA    1
170 #define IWN_CCK_STATE_HIFA    2
171 
172           uint8_t             noise_samples[20];
173           u_int               cur_noise_sample;
174           uint8_t             noise_ref;
175           uint32_t  energy_samples[10];
176           u_int               cur_energy_sample;
177           uint32_t  energy_cck;
178 };
179 
180 struct iwn_calib_info {
181           uint8_t             *buf;
182           u_int               len;
183 };
184 
185 struct iwn_fw_part {
186           const uint8_t       *text;
187           uint32_t  textsz;
188           const uint8_t       *data;
189           uint32_t  datasz;
190 };
191 
192 struct iwn_fw_info {
193           const uint8_t                 *data;
194           size_t                        size;
195           struct iwn_fw_part  init;
196           struct iwn_fw_part  main;
197           struct iwn_fw_part  boot;
198 };
199 
200 struct iwn_ops {
201           int                 (*load_firmware)(struct iwn_softc *);
202           void                (*read_eeprom)(struct iwn_softc *);
203           int                 (*post_alive)(struct iwn_softc *);
204           int                 (*nic_config)(struct iwn_softc *);
205           void                (*update_sched)(struct iwn_softc *, int, int, uint8_t,
206                                   uint16_t);
207           int                 (*get_temperature)(struct iwn_softc *);
208           int                 (*get_rssi)(struct iwn_softc *, struct iwn_rx_stat *);
209           int                 (*set_txpower)(struct iwn_softc *,
210                                   struct ieee80211_channel *, int);
211           int                 (*init_gains)(struct iwn_softc *);
212           int                 (*set_gains)(struct iwn_softc *);
213           int                 (*add_node)(struct iwn_softc *, struct iwn_node_info *,
214                                   int);
215           void                (*tx_done)(struct iwn_softc *, struct iwn_rx_desc *,
216                                   struct iwn_rx_data *);
217           void                (*ampdu_tx_start)(struct iwn_softc *,
218                                   struct ieee80211_node *, int, uint8_t, uint16_t);
219           void                (*ampdu_tx_stop)(struct iwn_softc *, int, uint8_t,
220                                   uint16_t);
221 };
222 
223 struct iwn_vap {
224           struct ieee80211vap iv_vap;
225           uint8_t                       iv_ridx;
226 
227           int                           (*iv_newstate)(struct ieee80211vap *,
228                                             enum ieee80211_state, int);
229           int                           ctx;
230           int                           beacon_int;
231 
232 };
233 #define   IWN_VAP(_vap)       ((struct iwn_vap *)(_vap))
234 
235 struct iwn_softc {
236           device_t            sc_dev;
237           int                           sc_debug;
238           struct cdev                   *sc_cdev;
239 #if defined(__DragonFly__)
240           struct lock                   sc_lk;
241 #else
242           struct mtx                    sc_mtx;
243 #endif
244           struct ieee80211com sc_ic;
245 
246           u_int                         sc_flags;
247 #define IWN_FLAG_HAS_OTPROM   (1 << 1)
248 #define IWN_FLAG_CALIB_DONE   (1 << 2)
249 #define IWN_FLAG_USE_ICT      (1 << 3)
250 #define IWN_FLAG_INTERNAL_PA  (1 << 4)
251 #define IWN_FLAG_HAS_11N      (1 << 6)
252 #define IWN_FLAG_ENH_SENS     (1 << 7)
253 #define IWN_FLAG_ADV_BTCOEX   (1 << 8)
254 #define IWN_FLAG_PAN_SUPPORT  (1 << 9)
255 #define IWN_FLAG_BTCOEX                 (1 << 10)
256 #define   IWN_FLAG_RUNNING    (1 << 11)
257 
258           uint8_t             hw_type;
259           /* subdevice_id used to adjust configuration */
260           uint16_t            subdevice_id;
261 
262           struct iwn_ops                ops;
263           const char                    *fwname;
264           const struct iwn_sensitivity_limits
265                                         *limits;
266           int                           ntxqs;
267           int                           firstaggqueue;
268           int                           ndmachnls;
269           uint8_t                       broadcast_id;
270           int                           rxonsz;
271           int                           schedsz;
272           uint32_t            fw_text_maxsz;
273           uint32_t            fw_data_maxsz;
274           uint32_t            fwsz;
275           bus_size_t                    sched_txfact_addr;
276           uint32_t            reset_noise_gain;
277           uint32_t            noise_gain;
278 
279           /* TX scheduler rings. */
280           struct iwn_dma_info sched_dma;
281           uint16_t            *sched;
282           uint32_t            sched_base;
283 
284           /* "Keep Warm" page. */
285           struct iwn_dma_info kw_dma;
286 
287           /* Firmware image. */
288           const struct firmware         *fw_fp;
289 
290           /* Firmware DMA transfer. */
291           struct iwn_dma_info fw_dma;
292 
293           /* ICT table. */
294           struct iwn_dma_info ict_dma;
295           uint32_t            *ict;
296           int                           ict_cur;
297 
298           /* TX/RX rings. */
299           struct iwn_tx_ring  txq[IWN5000_NTXQUEUES];
300           struct iwn_rx_ring  rxq;
301 
302           struct resource               *mem;
303           bus_space_tag_t               sc_st;
304           bus_space_handle_t  sc_sh;
305           struct resource               *irq;
306           void                          *sc_ih;
307           bus_size_t                    sc_sz;
308           int                           sc_cap_off;         /* PCIe Capabilities. */
309 
310           /* Tasks used by the driver */
311           struct task                   sc_radioon_task;
312           struct task                   sc_radiooff_task;
313           struct task                   sc_panic_task;
314           struct task                   sc_xmit_task;
315 
316           /* Taskqueue */
317           struct taskqueue    *sc_tq;
318 
319           /* Calibration information */
320           struct callout                calib_to;
321           int                           calib_cnt;
322           struct iwn_calib_state        calib;
323           int                           last_calib_ticks;
324           struct callout                watchdog_to;
325           struct iwn_fw_info  fw;
326           struct iwn_calib_info         calibcmd[IWN5000_PHY_CALIB_MAX_RESULT];
327           uint32_t            errptr;
328 
329           struct iwn_rx_stat  last_rx_stat;
330           int                           last_rx_valid;
331           struct iwn_ucode_info         ucode_info;
332           struct iwn_rxon               rx_on[IWN_NUM_RXON_CTX];
333           struct iwn_rxon               *rxon;
334           int                           ctx;
335           struct ieee80211vap *ivap[IWN_NUM_RXON_CTX];
336 
337           /* General statistics */
338           /*
339            * The statistics are reset after each channel
340            * change.  So it may be zeroed after things like
341            * a background scan.
342            *
343            * So for now, this is just a cheap hack to
344            * expose the last received statistics dump
345            * via an ioctl().  Later versions of this
346            * could expose the last 'n' messages, or just
347            * provide a pipeline for the firmware responses
348            * via something like BPF.
349            */
350           struct iwn_stats    last_stat;
351           int                           last_stat_valid;
352 
353           uint8_t                       uc_scan_progress;
354           uint32_t            rawtemp;
355           int                           temp;
356           int                           noise;
357           uint32_t            qfullmsk;
358 
359           uint32_t            prom_base;
360           struct iwn4965_eeprom_band
361                                         bands[IWN_NBANDS];
362           struct iwn_eeprom_chan        eeprom_channels[IWN_NBANDS][IWN_MAX_CHAN_PER_BAND];
363           uint16_t            rfcfg;
364           uint8_t                       calib_ver;
365           char                          eeprom_domain[4];
366           uint32_t            eeprom_crystal;
367           int16_t                       eeprom_temp;
368           int16_t                       eeprom_temp_high;
369           int16_t                       eeprom_voltage;
370           int8_t                        maxpwr2GHz;
371           int8_t                        maxpwr5GHz;
372           int8_t                        maxpwr[IEEE80211_CHAN_MAX];
373 
374           uint32_t            tlv_feature_flags;
375 
376           int32_t                       temp_off;
377           uint32_t            int_mask;
378           uint8_t                       ntxchains;
379           uint8_t                       nrxchains;
380           uint8_t                       txchainmask;
381           uint8_t                       rxchainmask;
382           uint8_t                       chainmask;
383 
384           int                           sc_tx_timer;
385           int                           sc_scan_timer;
386 
387           /* Are we doing a scan? */
388           int                           sc_is_scanning;
389 
390           /* Are we waiting for a beacon before xmit? */
391           int                           sc_beacon_wait;
392 
393           struct ieee80211_tx_ampdu *qid2tap[IWN5000_NTXQUEUES];
394 
395           int                           (*sc_ampdu_rx_start)(struct ieee80211_node *,
396                                             struct ieee80211_rx_ampdu *, int, int, int);
397           void                          (*sc_ampdu_rx_stop)(struct ieee80211_node *,
398                                             struct ieee80211_rx_ampdu *);
399           int                           (*sc_addba_request)(struct ieee80211_node *,
400                                             struct ieee80211_tx_ampdu *, int, int, int);
401           int                           (*sc_addba_response)(struct ieee80211_node *,
402                                             struct ieee80211_tx_ampdu *, int, int, int);
403           void                          (*sc_addba_stop)(struct ieee80211_node *,
404                                             struct ieee80211_tx_ampdu *);
405 
406           struct    iwn_led_mode sc_led;
407 
408           struct iwn_rx_radiotap_header sc_rxtap;
409           struct iwn_tx_radiotap_header sc_txtap;
410 
411           /* The power save level originally configured by user */
412           int                           desired_pwrsave_level;
413 
414           /*
415            * The current power save level, this may differ from the
416            * configured value due to thermal throttling etc.
417            */
418           int                           current_pwrsave_level;
419 
420           /* For specific params */
421           const struct iwn_base_params *base_params;
422 
423 #define   IWN_UCODE_API(ver)  (((ver) & 0x0000FF00) >> 8)
424           uint32_t            ucode_rev;
425 
426           /*
427            * Global queue for queuing xmit frames
428            * when we can't yet transmit (eg raw
429            * frames whilst waiting for beacons.)
430            */
431           struct mbufq                  sc_xmit_queue;
432 };
433 
434 #if defined(__DragonFly__)
435 #define IWN_LOCK_INIT(_sc) \
436           lockinit(&(_sc)->sc_lk, device_get_nameunit((_sc)->sc_dev), 0, 0)
437 #define IWN_LOCK(_sc)                             lockmgr(&(_sc)->sc_lk, LK_EXCLUSIVE)
438 #define IWN_LOCK_ASSERT(_sc)            KKASSERT(lockstatus(&(_sc)->sc_lk, curthread) == LK_EXCLUSIVE);
439 #define IWN_UNLOCK(_sc)                           lockmgr(&(_sc)->sc_lk, LK_RELEASE)
440 #define IWN_LOCK_DESTROY(_sc)           lockuninit(&(_sc)->sc_lk)
441 #else
442 #define IWN_LOCK_INIT(_sc) \
443           mtx_init(&(_sc)->sc_mtx, device_get_nameunit((_sc)->sc_dev), \
444               MTX_NETWORK_LOCK, MTX_DEF)
445 #define IWN_LOCK(_sc)                             mtx_lock(&(_sc)->sc_mtx)
446 #define IWN_LOCK_ASSERT(_sc)            mtx_assert(&(_sc)->sc_mtx, MA_OWNED)
447 #define IWN_UNLOCK(_sc)                           mtx_unlock(&(_sc)->sc_mtx)
448 #define IWN_LOCK_DESTROY(_sc)           mtx_destroy(&(_sc)->sc_mtx)
449 #endif
450