1 | /* SPDX-License-Identifier: GPL-2.0-only */ |
2 | /* |
3 | * LMAC Interface specific definitions for mac80211 Prism54 drivers |
4 | * |
5 | * Copyright (c) 2006, Michael Wu <flamingice@sourmilk.net> |
6 | * Copyright (c) 2007 - 2009, Christian Lamparter <chunkeey@web.de> |
7 | * |
8 | * Based on: |
9 | * - the islsm (softmac prism54) driver, which is: |
10 | * Copyright 2004-2006 Jean-Baptiste Note <jbnote@gmail.com>, et al. |
11 | * |
12 | * - LMAC API interface header file for STLC4560 (lmac_longbow.h) |
13 | * Copyright (C) 2007 Conexant Systems, Inc. |
14 | */ |
15 | |
16 | #ifndef LMAC_H |
17 | #define LMAC_H |
18 | |
19 | enum p54_control_frame_types { |
20 | P54_CONTROL_TYPE_SETUP = 0, |
21 | P54_CONTROL_TYPE_SCAN, |
22 | P54_CONTROL_TYPE_TRAP, |
23 | P54_CONTROL_TYPE_DCFINIT, |
24 | P54_CONTROL_TYPE_RX_KEYCACHE, |
25 | P54_CONTROL_TYPE_TIM, |
26 | P54_CONTROL_TYPE_PSM, |
27 | P54_CONTROL_TYPE_TXCANCEL, |
28 | P54_CONTROL_TYPE_TXDONE, |
29 | P54_CONTROL_TYPE_BURST, |
30 | P54_CONTROL_TYPE_STAT_READBACK, |
31 | P54_CONTROL_TYPE_BBP, |
32 | P54_CONTROL_TYPE_EEPROM_READBACK, |
33 | P54_CONTROL_TYPE_LED, |
34 | P54_CONTROL_TYPE_GPIO, |
35 | P54_CONTROL_TYPE_TIMER, |
36 | P54_CONTROL_TYPE_MODULATION, |
37 | P54_CONTROL_TYPE_SYNTH_CONFIG, |
38 | P54_CONTROL_TYPE_DETECTOR_VALUE, |
39 | P54_CONTROL_TYPE_XBOW_SYNTH_CFG, |
40 | P54_CONTROL_TYPE_CCE_QUIET, |
41 | P54_CONTROL_TYPE_PSM_STA_UNLOCK, |
42 | P54_CONTROL_TYPE_PCS, |
43 | P54_CONTROL_TYPE_BT_BALANCER = 28, |
44 | P54_CONTROL_TYPE_GROUP_ADDRESS_TABLE = 30, |
45 | P54_CONTROL_TYPE_ARPTABLE = 31, |
46 | P54_CONTROL_TYPE_BT_OPTIONS = 35, |
47 | }; |
48 | |
49 | #define P54_HDR_FLAG_CONTROL BIT(15) |
50 | #define P54_HDR_FLAG_CONTROL_OPSET (BIT(15) + BIT(0)) |
51 | #define P54_HDR_FLAG_DATA_ALIGN BIT(14) |
52 | |
53 | #define P54_HDR_FLAG_DATA_OUT_PROMISC BIT(0) |
54 | #define P54_HDR_FLAG_DATA_OUT_TIMESTAMP BIT(1) |
55 | #define P54_HDR_FLAG_DATA_OUT_SEQNR BIT(2) |
56 | #define P54_HDR_FLAG_DATA_OUT_BIT3 BIT(3) |
57 | #define P54_HDR_FLAG_DATA_OUT_BURST BIT(4) |
58 | #define P54_HDR_FLAG_DATA_OUT_NOCANCEL BIT(5) |
59 | #define P54_HDR_FLAG_DATA_OUT_CLEARTIM BIT(6) |
60 | #define P54_HDR_FLAG_DATA_OUT_HITCHHIKE BIT(7) |
61 | #define P54_HDR_FLAG_DATA_OUT_COMPRESS BIT(8) |
62 | #define P54_HDR_FLAG_DATA_OUT_CONCAT BIT(9) |
63 | #define P54_HDR_FLAG_DATA_OUT_PCS_ACCEPT BIT(10) |
64 | #define P54_HDR_FLAG_DATA_OUT_WAITEOSP BIT(11) |
65 | |
66 | #define P54_HDR_FLAG_DATA_IN_FCS_GOOD BIT(0) |
67 | #define P54_HDR_FLAG_DATA_IN_MATCH_MAC BIT(1) |
68 | #define P54_HDR_FLAG_DATA_IN_MCBC BIT(2) |
69 | #define P54_HDR_FLAG_DATA_IN_BEACON BIT(3) |
70 | #define P54_HDR_FLAG_DATA_IN_MATCH_BSS BIT(4) |
71 | #define P54_HDR_FLAG_DATA_IN_BCAST_BSS BIT(5) |
72 | #define P54_HDR_FLAG_DATA_IN_DATA BIT(6) |
73 | #define P54_HDR_FLAG_DATA_IN_TRUNCATED BIT(7) |
74 | #define P54_HDR_FLAG_DATA_IN_BIT8 BIT(8) |
75 | #define P54_HDR_FLAG_DATA_IN_TRANSPARENT BIT(9) |
76 | |
77 | struct p54_hdr { |
78 | __le16 flags; |
79 | __le16 len; |
80 | __le32 req_id; |
81 | __le16 type; /* enum p54_control_frame_types */ |
82 | u8 rts_tries; |
83 | u8 tries; |
84 | u8 data[]; |
85 | } __packed; |
86 | |
87 | #define GET_REQ_ID(skb) \ |
88 | (((struct p54_hdr *) ((struct sk_buff *) skb)->data)->req_id) \ |
89 | |
90 | #define FREE_AFTER_TX(skb) \ |
91 | ((((struct p54_hdr *) ((struct sk_buff *) skb)->data)-> \ |
92 | flags) == cpu_to_le16(P54_HDR_FLAG_CONTROL_OPSET)) |
93 | |
94 | #define IS_DATA_FRAME(skb) \ |
95 | (!((((struct p54_hdr *) ((struct sk_buff *) skb)->data)-> \ |
96 | flags) & cpu_to_le16(P54_HDR_FLAG_CONTROL))) |
97 | |
98 | #define GET_HW_QUEUE(skb) \ |
99 | (((struct p54_tx_data *)((struct p54_hdr *) \ |
100 | skb->data)->data)->hw_queue) |
101 | |
102 | /* |
103 | * shared interface ID definitions |
104 | * The interface ID is a unique identification of a specific interface. |
105 | * The following values are reserved: 0x0000, 0x0002, 0x0012, 0x0014, 0x0015 |
106 | */ |
107 | #define IF_ID_ISL36356A 0x0001 /* ISL36356A <-> Firmware */ |
108 | #define IF_ID_MVC 0x0003 /* MAC Virtual Coprocessor */ |
109 | #define IF_ID_DEBUG 0x0008 /* PolDebug Interface */ |
110 | #define IF_ID_PRODUCT 0x0009 |
111 | #define IF_ID_OEM 0x000a |
112 | #define IF_ID_PCI3877 0x000b /* 3877 <-> Host PCI */ |
113 | #define IF_ID_ISL37704C 0x000c /* ISL37704C <-> Fw */ |
114 | #define IF_ID_ISL39000 0x000f /* ISL39000 <-> Fw */ |
115 | #define IF_ID_ISL39300A 0x0010 /* ISL39300A <-> Fw */ |
116 | #define IF_ID_ISL37700_UAP 0x0016 /* ISL37700 uAP Fw <-> Fw */ |
117 | #define IF_ID_ISL39000_UAP 0x0017 /* ISL39000 uAP Fw <-> Fw */ |
118 | #define IF_ID_LMAC 0x001a /* Interface exposed by LMAC */ |
119 | |
120 | struct exp_if { |
121 | __le16 role; |
122 | __le16 if_id; |
123 | __le16 variant; |
124 | __le16 btm_compat; |
125 | __le16 top_compat; |
126 | } __packed; |
127 | |
128 | struct dep_if { |
129 | __le16 role; |
130 | __le16 if_id; |
131 | __le16 variant; |
132 | } __packed; |
133 | |
134 | /* driver <-> lmac definitions */ |
135 | struct p54_eeprom_lm86 { |
136 | union { |
137 | struct { |
138 | __le16 offset; |
139 | __le16 len; |
140 | u8 data[0]; |
141 | } __packed v1; |
142 | struct { |
143 | __le32 offset; |
144 | __le16 len; |
145 | u8 magic2; |
146 | u8 pad; |
147 | u8 magic[4]; |
148 | u8 data[0]; |
149 | } __packed v2; |
150 | } __packed; |
151 | } __packed; |
152 | |
153 | enum p54_rx_decrypt_status { |
154 | P54_DECRYPT_NONE = 0, |
155 | P54_DECRYPT_OK, |
156 | P54_DECRYPT_NOKEY, |
157 | P54_DECRYPT_NOMICHAEL, |
158 | P54_DECRYPT_NOCKIPMIC, |
159 | P54_DECRYPT_FAIL_WEP, |
160 | P54_DECRYPT_FAIL_TKIP, |
161 | P54_DECRYPT_FAIL_MICHAEL, |
162 | P54_DECRYPT_FAIL_CKIPKP, |
163 | P54_DECRYPT_FAIL_CKIPMIC, |
164 | P54_DECRYPT_FAIL_AESCCMP |
165 | }; |
166 | |
167 | struct p54_rx_data { |
168 | __le16 flags; |
169 | __le16 len; |
170 | __le16 freq; |
171 | u8 antenna; |
172 | u8 rate; |
173 | u8 ; |
174 | u8 quality; |
175 | u8 decrypt_status; |
176 | u8 ; |
177 | __le32 tsf32; |
178 | __le32 unalloc0; |
179 | u8 align[]; |
180 | } __packed; |
181 | |
182 | enum p54_trap_type { |
183 | P54_TRAP_SCAN = 0, |
184 | P54_TRAP_TIMER, |
185 | P54_TRAP_BEACON_TX, |
186 | P54_TRAP_FAA_RADIO_ON, |
187 | P54_TRAP_FAA_RADIO_OFF, |
188 | P54_TRAP_RADAR, |
189 | P54_TRAP_NO_BEACON, |
190 | P54_TRAP_TBTT, |
191 | P54_TRAP_SCO_ENTER, |
192 | P54_TRAP_SCO_EXIT |
193 | }; |
194 | |
195 | struct p54_trap { |
196 | __le16 event; |
197 | __le16 frequency; |
198 | } __packed; |
199 | |
200 | enum p54_frame_sent_status { |
201 | P54_TX_OK = 0, |
202 | P54_TX_FAILED, |
203 | P54_TX_PSM, |
204 | P54_TX_PSM_CANCELLED = 4 |
205 | }; |
206 | |
207 | struct p54_frame_sent { |
208 | u8 status; |
209 | u8 tries; |
210 | u8 ; |
211 | u8 quality; |
212 | __le16 seq; |
213 | u8 antenna; |
214 | u8 padding; |
215 | } __packed; |
216 | |
217 | enum p54_tx_data_crypt { |
218 | P54_CRYPTO_NONE = 0, |
219 | P54_CRYPTO_WEP, |
220 | P54_CRYPTO_TKIP, |
221 | P54_CRYPTO_TKIPMICHAEL, |
222 | P54_CRYPTO_CCX_WEPMIC, |
223 | P54_CRYPTO_CCX_KPMIC, |
224 | P54_CRYPTO_CCX_KP, |
225 | P54_CRYPTO_AESCCMP |
226 | }; |
227 | |
228 | enum p54_tx_data_queue { |
229 | P54_QUEUE_BEACON = 0, |
230 | P54_QUEUE_FWSCAN = 1, |
231 | P54_QUEUE_MGMT = 2, |
232 | P54_QUEUE_CAB = 3, |
233 | P54_QUEUE_DATA = 4, |
234 | |
235 | P54_QUEUE_AC_NUM = 4, |
236 | P54_QUEUE_AC_VO = 4, |
237 | P54_QUEUE_AC_VI = 5, |
238 | P54_QUEUE_AC_BE = 6, |
239 | P54_QUEUE_AC_BK = 7, |
240 | |
241 | /* keep last */ |
242 | P54_QUEUE_NUM = 8, |
243 | }; |
244 | |
245 | #define IS_QOS_QUEUE(n) (n >= P54_QUEUE_DATA) |
246 | |
247 | struct p54_tx_data { |
248 | u8 rateset[8]; |
249 | u8 rts_rate_idx; |
250 | u8 crypt_offset; |
251 | u8 key_type; |
252 | u8 key_len; |
253 | u8 key[16]; |
254 | u8 hw_queue; |
255 | u8 backlog; |
256 | __le16 durations[4]; |
257 | u8 tx_antenna; |
258 | union { |
259 | struct { |
260 | u8 cts_rate; |
261 | __le16 output_power; |
262 | } __packed longbow; |
263 | struct { |
264 | u8 output_power; |
265 | u8 cts_rate; |
266 | u8 unalloc; |
267 | } __packed normal; |
268 | } __packed; |
269 | u8 unalloc2[2]; |
270 | u8 align[]; |
271 | } __packed; |
272 | |
273 | /* unit is ms */ |
274 | #define P54_TX_FRAME_LIFETIME 2000 |
275 | #define P54_TX_TIMEOUT 4000 |
276 | #define P54_STATISTICS_UPDATE 5000 |
277 | |
278 | #define P54_FILTER_TYPE_NONE 0 |
279 | #define P54_FILTER_TYPE_STATION BIT(0) |
280 | #define P54_FILTER_TYPE_IBSS BIT(1) |
281 | #define P54_FILTER_TYPE_AP BIT(2) |
282 | #define P54_FILTER_TYPE_TRANSPARENT BIT(3) |
283 | #define P54_FILTER_TYPE_PROMISCUOUS BIT(4) |
284 | #define P54_FILTER_TYPE_HIBERNATE BIT(5) |
285 | #define P54_FILTER_TYPE_NOACK BIT(6) |
286 | #define P54_FILTER_TYPE_RX_DISABLED BIT(7) |
287 | |
288 | struct p54_setup_mac { |
289 | __le16 mac_mode; |
290 | u8 mac_addr[ETH_ALEN]; |
291 | u8 bssid[ETH_ALEN]; |
292 | u8 rx_antenna; |
293 | u8 rx_align; |
294 | union { |
295 | struct { |
296 | __le32 basic_rate_mask; |
297 | u8 rts_rates[8]; |
298 | __le32 rx_addr; |
299 | __le16 max_rx; |
300 | __le16 rxhw; |
301 | __le16 wakeup_timer; |
302 | __le16 unalloc0; |
303 | } __packed v1; |
304 | struct { |
305 | __le32 rx_addr; |
306 | __le16 max_rx; |
307 | __le16 rxhw; |
308 | __le16 timer; |
309 | __le16 truncate; |
310 | __le32 basic_rate_mask; |
311 | u8 sbss_offset; |
312 | u8 mcast_window; |
313 | u8 ; |
314 | u8 rx_ed_threshold; |
315 | __le32 ref_clock; |
316 | __le16 lpf_bandwidth; |
317 | __le16 osc_start_delay; |
318 | } __packed v2; |
319 | } __packed; |
320 | } __packed; |
321 | |
322 | #define P54_SETUP_V1_LEN 40 |
323 | #define P54_SETUP_V2_LEN (sizeof(struct p54_setup_mac)) |
324 | |
325 | #define P54_SCAN_EXIT BIT(0) |
326 | #define P54_SCAN_TRAP BIT(1) |
327 | #define P54_SCAN_ACTIVE BIT(2) |
328 | #define P54_SCAN_FILTER BIT(3) |
329 | |
330 | struct p54_scan_head { |
331 | __le16 mode; |
332 | __le16 dwell; |
333 | u8 scan_params[20]; |
334 | __le16 freq; |
335 | } __packed; |
336 | |
337 | struct p54_pa_curve_data_sample { |
338 | u8 rf_power; |
339 | u8 pa_detector; |
340 | u8 data_barker; |
341 | u8 data_bpsk; |
342 | u8 data_qpsk; |
343 | u8 data_16qam; |
344 | u8 data_64qam; |
345 | u8 padding; |
346 | } __packed; |
347 | |
348 | struct p54_scan_body { |
349 | u8 pa_points_per_curve; |
350 | u8 val_barker; |
351 | u8 val_bpsk; |
352 | u8 val_qpsk; |
353 | u8 val_16qam; |
354 | u8 val_64qam; |
355 | struct p54_pa_curve_data_sample curve_data[8]; |
356 | u8 dup_bpsk; |
357 | u8 dup_qpsk; |
358 | u8 dup_16qam; |
359 | u8 dup_64qam; |
360 | } __packed; |
361 | |
362 | /* |
363 | * Warning: Longbow's structures are bogus. |
364 | */ |
365 | struct p54_channel_output_limit_longbow { |
366 | __le16 rf_power_points[12]; |
367 | } __packed; |
368 | |
369 | struct p54_pa_curve_data_sample_longbow { |
370 | __le16 rf_power; |
371 | __le16 pa_detector; |
372 | struct { |
373 | __le16 data[4]; |
374 | } points[3] __packed; |
375 | } __packed; |
376 | |
377 | struct p54_scan_body_longbow { |
378 | struct p54_channel_output_limit_longbow power_limits; |
379 | struct p54_pa_curve_data_sample_longbow curve_data[8]; |
380 | __le16 unkn[6]; /* maybe more power_limits or rate_mask */ |
381 | } __packed; |
382 | |
383 | union p54_scan_body_union { |
384 | struct p54_scan_body normal; |
385 | struct p54_scan_body_longbow longbow; |
386 | } __packed; |
387 | |
388 | struct p54_scan_tail_rate { |
389 | __le32 basic_rate_mask; |
390 | u8 rts_rates[8]; |
391 | } __packed; |
392 | |
393 | struct p54_led { |
394 | __le16 flags; |
395 | __le16 mask[2]; |
396 | __le16 delay[2]; |
397 | } __packed; |
398 | |
399 | struct p54_edcf { |
400 | u8 flags; |
401 | u8 slottime; |
402 | u8 sifs; |
403 | u8 eofpad; |
404 | struct p54_edcf_queue_param queue[8]; |
405 | u8 mapping[4]; |
406 | __le16 frameburst; |
407 | __le16 round_trip_delay; |
408 | } __packed; |
409 | |
410 | struct p54_statistics { |
411 | __le32 rx_success; |
412 | __le32 rx_bad_fcs; |
413 | __le32 rx_abort; |
414 | __le32 rx_abort_phy; |
415 | __le32 rts_success; |
416 | __le32 rts_fail; |
417 | __le32 tsf32; |
418 | __le32 airtime; |
419 | __le32 noise; |
420 | __le32 sample_noise[8]; |
421 | __le32 sample_cca; |
422 | __le32 sample_tx; |
423 | } __packed; |
424 | |
425 | struct p54_xbow_synth { |
426 | __le16 magic1; |
427 | __le16 magic2; |
428 | __le16 freq; |
429 | u32 padding[5]; |
430 | } __packed; |
431 | |
432 | struct p54_timer { |
433 | __le32 interval; |
434 | } __packed; |
435 | |
436 | struct p54_keycache { |
437 | u8 entry; |
438 | u8 key_id; |
439 | u8 mac[ETH_ALEN]; |
440 | u8 padding[2]; |
441 | u8 key_type; |
442 | u8 key_len; |
443 | u8 key[24]; |
444 | } __packed; |
445 | |
446 | struct p54_burst { |
447 | u8 flags; |
448 | u8 queue; |
449 | u8 backlog; |
450 | u8 pad; |
451 | __le16 durations[32]; |
452 | } __packed; |
453 | |
454 | struct p54_psm_interval { |
455 | __le16 interval; |
456 | __le16 periods; |
457 | } __packed; |
458 | |
459 | #define P54_PSM_CAM 0 |
460 | #define P54_PSM BIT(0) |
461 | #define P54_PSM_DTIM BIT(1) |
462 | #define P54_PSM_MCBC BIT(2) |
463 | #define P54_PSM_CHECKSUM BIT(3) |
464 | #define P54_PSM_SKIP_MORE_DATA BIT(4) |
465 | #define P54_PSM_BEACON_TIMEOUT BIT(5) |
466 | #define P54_PSM_HFOSLEEP BIT(6) |
467 | #define P54_PSM_AUTOSWITCH_SLEEP BIT(7) |
468 | #define P54_PSM_LPIT BIT(8) |
469 | #define P54_PSM_BF_UCAST_SKIP BIT(9) |
470 | #define P54_PSM_BF_MCAST_SKIP BIT(10) |
471 | |
472 | struct p54_psm { |
473 | __le16 mode; |
474 | __le16 aid; |
475 | struct p54_psm_interval intervals[4]; |
476 | u8 ; |
477 | u8 ; |
478 | u8 nr; |
479 | u8 exclude[1]; |
480 | } __packed; |
481 | |
482 | #define MC_FILTER_ADDRESS_NUM 4 |
483 | |
484 | struct p54_group_address_table { |
485 | __le16 filter_enable; |
486 | __le16 num_address; |
487 | u8 mac_list[MC_FILTER_ADDRESS_NUM][ETH_ALEN]; |
488 | } __packed; |
489 | |
490 | struct p54_txcancel { |
491 | __le32 req_id; |
492 | } __packed; |
493 | |
494 | struct p54_sta_unlock { |
495 | u8 addr[ETH_ALEN]; |
496 | u16 padding; |
497 | } __packed; |
498 | |
499 | #define P54_TIM_CLEAR BIT(15) |
500 | struct p54_tim { |
501 | u8 count; |
502 | u8 padding[3]; |
503 | __le16 entry[8]; |
504 | } __packed; |
505 | |
506 | struct p54_cce_quiet { |
507 | __le32 period; |
508 | } __packed; |
509 | |
510 | struct p54_bt_balancer { |
511 | __le16 prio_thresh; |
512 | __le16 acl_thresh; |
513 | } __packed; |
514 | |
515 | struct p54_arp_table { |
516 | __le16 filter_enable; |
517 | u8 ipv4_addr[4]; |
518 | } __packed; |
519 | |
520 | /* LED control */ |
521 | int p54_set_leds(struct p54_common *priv); |
522 | int p54_init_leds(struct p54_common *priv); |
523 | void p54_unregister_leds(struct p54_common *priv); |
524 | |
525 | /* xmit functions */ |
526 | void p54_tx_80211(struct ieee80211_hw *dev, |
527 | struct ieee80211_tx_control *control, |
528 | struct sk_buff *skb); |
529 | int p54_tx_cancel(struct p54_common *priv, __le32 req_id); |
530 | void p54_tx(struct p54_common *priv, struct sk_buff *skb); |
531 | |
532 | /* synth/phy configuration */ |
533 | int p54_init_xbow_synth(struct p54_common *priv); |
534 | int p54_scan(struct p54_common *priv, u16 mode, u16 dwell); |
535 | |
536 | /* MAC */ |
537 | int p54_sta_unlock(struct p54_common *priv, u8 *addr); |
538 | int p54_update_beacon_tim(struct p54_common *priv, u16 aid, bool set); |
539 | int p54_setup_mac(struct p54_common *priv); |
540 | int p54_set_ps(struct p54_common *priv); |
541 | int p54_fetch_statistics(struct p54_common *priv); |
542 | int p54_set_groupfilter(struct p54_common *priv); |
543 | |
544 | /* e/v DCF setup */ |
545 | int p54_set_edcf(struct p54_common *priv); |
546 | |
547 | /* cryptographic engine */ |
548 | int p54_upload_key(struct p54_common *priv, u8 algo, int slot, |
549 | u8 idx, u8 len, u8 *addr, u8* key); |
550 | |
551 | /* eeprom */ |
552 | int p54_download_eeprom(struct p54_common *priv, void *buf, |
553 | u16 offset, u16 len); |
554 | struct p54_rssi_db_entry *(struct p54_common *p, const u16 freq); |
555 | |
556 | /* utility */ |
557 | u8 *p54_find_ie(struct sk_buff *skb, u8 ie); |
558 | |
559 | #endif /* LMAC_H */ |
560 | |