2 * This file is part of wl18xx
4 * Copyright (C) 2011 Texas Instruments
6 * This program is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU General Public License
8 * version 2 as published by the Free Software Foundation.
10 * This program is distributed in the hope that it will be useful, but
11 * WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 * General Public License for more details.
15 * You should have received a copy of the GNU General Public License
16 * along with this program; if not, write to the Free Software
17 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
22 #include <linux/module.h>
23 #include <linux/platform_device.h>
25 #include <linux/firmware.h>
27 #include "../wlcore/wlcore.h"
28 #include "../wlcore/debug.h"
29 #include "../wlcore/io.h"
30 #include "../wlcore/acx.h"
31 #include "../wlcore/tx.h"
32 #include "../wlcore/rx.h"
33 #include "../wlcore/boot.h"
46 #define WL18XX_RX_CHECKSUM_MASK 0x40
48 static char *ht_mode_param = NULL;
49 static char *board_type_param = NULL;
50 static bool checksum_param = false;
51 static int num_rx_desc_param = -1;
54 static int dc2dc_param = -1;
55 static int n_antennas_2_param = -1;
56 static int n_antennas_5_param = -1;
57 static int low_band_component_param = -1;
58 static int low_band_component_type_param = -1;
59 static int high_band_component_param = -1;
60 static int high_band_component_type_param = -1;
61 static int pwr_limit_reference_11_abg_param = -1;
63 static const u8 wl18xx_rate_to_idx_2ghz[] = {
64 /* MCS rates are used only with 11n */
65 15, /* WL18XX_CONF_HW_RXTX_RATE_MCS15 */
66 14, /* WL18XX_CONF_HW_RXTX_RATE_MCS14 */
67 13, /* WL18XX_CONF_HW_RXTX_RATE_MCS13 */
68 12, /* WL18XX_CONF_HW_RXTX_RATE_MCS12 */
69 11, /* WL18XX_CONF_HW_RXTX_RATE_MCS11 */
70 10, /* WL18XX_CONF_HW_RXTX_RATE_MCS10 */
71 9, /* WL18XX_CONF_HW_RXTX_RATE_MCS9 */
72 8, /* WL18XX_CONF_HW_RXTX_RATE_MCS8 */
73 7, /* WL18XX_CONF_HW_RXTX_RATE_MCS7 */
74 6, /* WL18XX_CONF_HW_RXTX_RATE_MCS6 */
75 5, /* WL18XX_CONF_HW_RXTX_RATE_MCS5 */
76 4, /* WL18XX_CONF_HW_RXTX_RATE_MCS4 */
77 3, /* WL18XX_CONF_HW_RXTX_RATE_MCS3 */
78 2, /* WL18XX_CONF_HW_RXTX_RATE_MCS2 */
79 1, /* WL18XX_CONF_HW_RXTX_RATE_MCS1 */
80 0, /* WL18XX_CONF_HW_RXTX_RATE_MCS0 */
82 11, /* WL18XX_CONF_HW_RXTX_RATE_54 */
83 10, /* WL18XX_CONF_HW_RXTX_RATE_48 */
84 9, /* WL18XX_CONF_HW_RXTX_RATE_36 */
85 8, /* WL18XX_CONF_HW_RXTX_RATE_24 */
87 /* TI-specific rate */
88 CONF_HW_RXTX_RATE_UNSUPPORTED, /* WL18XX_CONF_HW_RXTX_RATE_22 */
90 7, /* WL18XX_CONF_HW_RXTX_RATE_18 */
91 6, /* WL18XX_CONF_HW_RXTX_RATE_12 */
92 3, /* WL18XX_CONF_HW_RXTX_RATE_11 */
93 5, /* WL18XX_CONF_HW_RXTX_RATE_9 */
94 4, /* WL18XX_CONF_HW_RXTX_RATE_6 */
95 2, /* WL18XX_CONF_HW_RXTX_RATE_5_5 */
96 1, /* WL18XX_CONF_HW_RXTX_RATE_2 */
97 0 /* WL18XX_CONF_HW_RXTX_RATE_1 */
100 static const u8 wl18xx_rate_to_idx_5ghz[] = {
101 /* MCS rates are used only with 11n */
102 15, /* WL18XX_CONF_HW_RXTX_RATE_MCS15 */
103 14, /* WL18XX_CONF_HW_RXTX_RATE_MCS14 */
104 13, /* WL18XX_CONF_HW_RXTX_RATE_MCS13 */
105 12, /* WL18XX_CONF_HW_RXTX_RATE_MCS12 */
106 11, /* WL18XX_CONF_HW_RXTX_RATE_MCS11 */
107 10, /* WL18XX_CONF_HW_RXTX_RATE_MCS10 */
108 9, /* WL18XX_CONF_HW_RXTX_RATE_MCS9 */
109 8, /* WL18XX_CONF_HW_RXTX_RATE_MCS8 */
110 7, /* WL18XX_CONF_HW_RXTX_RATE_MCS7 */
111 6, /* WL18XX_CONF_HW_RXTX_RATE_MCS6 */
112 5, /* WL18XX_CONF_HW_RXTX_RATE_MCS5 */
113 4, /* WL18XX_CONF_HW_RXTX_RATE_MCS4 */
114 3, /* WL18XX_CONF_HW_RXTX_RATE_MCS3 */
115 2, /* WL18XX_CONF_HW_RXTX_RATE_MCS2 */
116 1, /* WL18XX_CONF_HW_RXTX_RATE_MCS1 */
117 0, /* WL18XX_CONF_HW_RXTX_RATE_MCS0 */
119 7, /* WL18XX_CONF_HW_RXTX_RATE_54 */
120 6, /* WL18XX_CONF_HW_RXTX_RATE_48 */
121 5, /* WL18XX_CONF_HW_RXTX_RATE_36 */
122 4, /* WL18XX_CONF_HW_RXTX_RATE_24 */
124 /* TI-specific rate */
125 CONF_HW_RXTX_RATE_UNSUPPORTED, /* WL18XX_CONF_HW_RXTX_RATE_22 */
127 3, /* WL18XX_CONF_HW_RXTX_RATE_18 */
128 2, /* WL18XX_CONF_HW_RXTX_RATE_12 */
129 CONF_HW_RXTX_RATE_UNSUPPORTED, /* WL18XX_CONF_HW_RXTX_RATE_11 */
130 1, /* WL18XX_CONF_HW_RXTX_RATE_9 */
131 0, /* WL18XX_CONF_HW_RXTX_RATE_6 */
132 CONF_HW_RXTX_RATE_UNSUPPORTED, /* WL18XX_CONF_HW_RXTX_RATE_5_5 */
133 CONF_HW_RXTX_RATE_UNSUPPORTED, /* WL18XX_CONF_HW_RXTX_RATE_2 */
134 CONF_HW_RXTX_RATE_UNSUPPORTED, /* WL18XX_CONF_HW_RXTX_RATE_1 */
137 static const u8 *wl18xx_band_rate_to_idx[] = {
138 [IEEE80211_BAND_2GHZ] = wl18xx_rate_to_idx_2ghz,
139 [IEEE80211_BAND_5GHZ] = wl18xx_rate_to_idx_5ghz
142 enum wl18xx_hw_rates {
143 WL18XX_CONF_HW_RXTX_RATE_MCS15 = 0,
144 WL18XX_CONF_HW_RXTX_RATE_MCS14,
145 WL18XX_CONF_HW_RXTX_RATE_MCS13,
146 WL18XX_CONF_HW_RXTX_RATE_MCS12,
147 WL18XX_CONF_HW_RXTX_RATE_MCS11,
148 WL18XX_CONF_HW_RXTX_RATE_MCS10,
149 WL18XX_CONF_HW_RXTX_RATE_MCS9,
150 WL18XX_CONF_HW_RXTX_RATE_MCS8,
151 WL18XX_CONF_HW_RXTX_RATE_MCS7,
152 WL18XX_CONF_HW_RXTX_RATE_MCS6,
153 WL18XX_CONF_HW_RXTX_RATE_MCS5,
154 WL18XX_CONF_HW_RXTX_RATE_MCS4,
155 WL18XX_CONF_HW_RXTX_RATE_MCS3,
156 WL18XX_CONF_HW_RXTX_RATE_MCS2,
157 WL18XX_CONF_HW_RXTX_RATE_MCS1,
158 WL18XX_CONF_HW_RXTX_RATE_MCS0,
159 WL18XX_CONF_HW_RXTX_RATE_54,
160 WL18XX_CONF_HW_RXTX_RATE_48,
161 WL18XX_CONF_HW_RXTX_RATE_36,
162 WL18XX_CONF_HW_RXTX_RATE_24,
163 WL18XX_CONF_HW_RXTX_RATE_22,
164 WL18XX_CONF_HW_RXTX_RATE_18,
165 WL18XX_CONF_HW_RXTX_RATE_12,
166 WL18XX_CONF_HW_RXTX_RATE_11,
167 WL18XX_CONF_HW_RXTX_RATE_9,
168 WL18XX_CONF_HW_RXTX_RATE_6,
169 WL18XX_CONF_HW_RXTX_RATE_5_5,
170 WL18XX_CONF_HW_RXTX_RATE_2,
171 WL18XX_CONF_HW_RXTX_RATE_1,
172 WL18XX_CONF_HW_RXTX_RATE_MAX,
175 static struct wlcore_conf wl18xx_conf = {
178 [CONF_SG_ACL_BT_MASTER_MIN_BR] = 10,
179 [CONF_SG_ACL_BT_MASTER_MAX_BR] = 180,
180 [CONF_SG_ACL_BT_SLAVE_MIN_BR] = 10,
181 [CONF_SG_ACL_BT_SLAVE_MAX_BR] = 180,
182 [CONF_SG_ACL_BT_MASTER_MIN_EDR] = 10,
183 [CONF_SG_ACL_BT_MASTER_MAX_EDR] = 80,
184 [CONF_SG_ACL_BT_SLAVE_MIN_EDR] = 10,
185 [CONF_SG_ACL_BT_SLAVE_MAX_EDR] = 80,
186 [CONF_SG_ACL_WLAN_PS_MASTER_BR] = 8,
187 [CONF_SG_ACL_WLAN_PS_SLAVE_BR] = 8,
188 [CONF_SG_ACL_WLAN_PS_MASTER_EDR] = 20,
189 [CONF_SG_ACL_WLAN_PS_SLAVE_EDR] = 20,
190 [CONF_SG_ACL_WLAN_ACTIVE_MASTER_MIN_BR] = 20,
191 [CONF_SG_ACL_WLAN_ACTIVE_MASTER_MAX_BR] = 35,
192 [CONF_SG_ACL_WLAN_ACTIVE_SLAVE_MIN_BR] = 16,
193 [CONF_SG_ACL_WLAN_ACTIVE_SLAVE_MAX_BR] = 35,
194 [CONF_SG_ACL_WLAN_ACTIVE_MASTER_MIN_EDR] = 32,
195 [CONF_SG_ACL_WLAN_ACTIVE_MASTER_MAX_EDR] = 50,
196 [CONF_SG_ACL_WLAN_ACTIVE_SLAVE_MIN_EDR] = 28,
197 [CONF_SG_ACL_WLAN_ACTIVE_SLAVE_MAX_EDR] = 50,
198 [CONF_SG_ACL_ACTIVE_SCAN_WLAN_BR] = 10,
199 [CONF_SG_ACL_ACTIVE_SCAN_WLAN_EDR] = 20,
200 [CONF_SG_ACL_PASSIVE_SCAN_BT_BR] = 75,
201 [CONF_SG_ACL_PASSIVE_SCAN_WLAN_BR] = 15,
202 [CONF_SG_ACL_PASSIVE_SCAN_BT_EDR] = 27,
203 [CONF_SG_ACL_PASSIVE_SCAN_WLAN_EDR] = 17,
204 /* active scan params */
205 [CONF_SG_AUTO_SCAN_PROBE_REQ] = 170,
206 [CONF_SG_ACTIVE_SCAN_DURATION_FACTOR_HV3] = 50,
207 [CONF_SG_ACTIVE_SCAN_DURATION_FACTOR_A2DP] = 100,
208 /* passive scan params */
209 [CONF_SG_PASSIVE_SCAN_DURATION_FACTOR_A2DP_BR] = 800,
210 [CONF_SG_PASSIVE_SCAN_DURATION_FACTOR_A2DP_EDR] = 200,
211 [CONF_SG_PASSIVE_SCAN_DURATION_FACTOR_HV3] = 200,
212 /* passive scan in dual antenna params */
213 [CONF_SG_CONSECUTIVE_HV3_IN_PASSIVE_SCAN] = 0,
214 [CONF_SG_BCN_HV3_COLLISION_THRESH_IN_PASSIVE_SCAN] = 0,
215 [CONF_SG_TX_RX_PROTECTION_BWIDTH_IN_PASSIVE_SCAN] = 0,
217 [CONF_SG_STA_FORCE_PS_IN_BT_SCO] = 1,
218 [CONF_SG_ANTENNA_CONFIGURATION] = 0,
219 [CONF_SG_BEACON_MISS_PERCENT] = 60,
220 [CONF_SG_DHCP_TIME] = 5000,
221 [CONF_SG_RXT] = 1200,
222 [CONF_SG_TXT] = 1000,
223 [CONF_SG_ADAPTIVE_RXT_TXT] = 1,
224 [CONF_SG_GENERAL_USAGE_BIT_MAP] = 3,
225 [CONF_SG_HV3_MAX_SERVED] = 6,
226 [CONF_SG_PS_POLL_TIMEOUT] = 10,
227 [CONF_SG_UPSD_TIMEOUT] = 10,
228 [CONF_SG_CONSECUTIVE_CTS_THRESHOLD] = 2,
229 [CONF_SG_STA_RX_WINDOW_AFTER_DTIM] = 5,
230 [CONF_SG_STA_CONNECTION_PROTECTION_TIME] = 30,
232 [CONF_AP_BEACON_MISS_TX] = 3,
233 [CONF_AP_RX_WINDOW_AFTER_BEACON] = 10,
234 [CONF_AP_BEACON_WINDOW_INTERVAL] = 2,
235 [CONF_AP_CONNECTION_PROTECTION_TIME] = 0,
236 [CONF_AP_BT_ACL_VAL_BT_SERVE_TIME] = 25,
237 [CONF_AP_BT_ACL_VAL_WL_SERVE_TIME] = 25,
238 /* CTS Diluting params */
239 [CONF_SG_CTS_DILUTED_BAD_RX_PACKETS_TH] = 0,
240 [CONF_SG_CTS_CHOP_IN_DUAL_ANT_SCO_MASTER] = 0,
242 .state = CONF_SG_PROTECTIVE,
245 .rx_msdu_life_time = 512000,
246 .packet_detection_threshold = 0,
247 .ps_poll_timeout = 15,
249 .rts_threshold = IEEE80211_MAX_RTS_THRESHOLD,
250 .rx_cca_threshold = 0,
251 .irq_blk_threshold = 0xFFFF,
252 .irq_pkt_threshold = 0,
254 .queue_type = CONF_RX_QUEUE_TYPE_LOW_PRIORITY,
257 .tx_energy_detection = 0,
260 .short_retry_limit = 10,
261 .long_retry_limit = 10,
284 .aifsn = CONF_TX_AIFS_PIFS,
291 .aifsn = CONF_TX_AIFS_PIFS,
295 .max_tx_retries = 100,
296 .ap_aging_period = 300,
300 .queue_id = CONF_TX_AC_BE,
301 .channel_type = CONF_CHANNEL_TYPE_EDCF,
302 .tsid = CONF_TX_AC_BE,
303 .ps_scheme = CONF_PS_SCHEME_LEGACY,
304 .ack_policy = CONF_ACK_POLICY_LEGACY,
308 .queue_id = CONF_TX_AC_BK,
309 .channel_type = CONF_CHANNEL_TYPE_EDCF,
310 .tsid = CONF_TX_AC_BK,
311 .ps_scheme = CONF_PS_SCHEME_LEGACY,
312 .ack_policy = CONF_ACK_POLICY_LEGACY,
316 .queue_id = CONF_TX_AC_VI,
317 .channel_type = CONF_CHANNEL_TYPE_EDCF,
318 .tsid = CONF_TX_AC_VI,
319 .ps_scheme = CONF_PS_SCHEME_LEGACY,
320 .ack_policy = CONF_ACK_POLICY_LEGACY,
324 .queue_id = CONF_TX_AC_VO,
325 .channel_type = CONF_CHANNEL_TYPE_EDCF,
326 .tsid = CONF_TX_AC_VO,
327 .ps_scheme = CONF_PS_SCHEME_LEGACY,
328 .ack_policy = CONF_ACK_POLICY_LEGACY,
332 .frag_threshold = IEEE80211_MAX_FRAG_THRESHOLD,
333 .tx_compl_timeout = 350,
334 .tx_compl_threshold = 10,
335 .basic_rate = CONF_HW_BIT_RATE_1MBPS,
336 .basic_rate_5 = CONF_HW_BIT_RATE_6MBPS,
337 .tmpl_short_retry_limit = 10,
338 .tmpl_long_retry_limit = 10,
339 .tx_watchdog_timeout = 5000,
340 .slow_link_thold = 3,
341 .fast_link_thold = 30,
344 .wake_up_event = CONF_WAKE_UP_EVENT_DTIM,
345 .listen_interval = 1,
346 .suspend_wake_up_event = CONF_WAKE_UP_EVENT_N_DTIM,
347 .suspend_listen_interval = 3,
348 .bcn_filt_mode = CONF_BCN_FILT_MODE_ENABLED,
349 .bcn_filt_ie_count = 3,
352 .ie = WLAN_EID_CHANNEL_SWITCH,
353 .rule = CONF_BCN_RULE_PASS_ON_APPEARANCE,
356 .ie = WLAN_EID_HT_OPERATION,
357 .rule = CONF_BCN_RULE_PASS_ON_CHANGE,
360 .ie = WLAN_EID_ERP_INFO,
361 .rule = CONF_BCN_RULE_PASS_ON_CHANGE,
364 .synch_fail_thold = 12,
365 .bss_lose_timeout = 400,
366 .beacon_rx_timeout = 10000,
367 .broadcast_timeout = 20000,
368 .rx_broadcast_in_ps = 1,
369 .ps_poll_threshold = 10,
370 .bet_enable = CONF_BET_MODE_ENABLE,
371 .bet_max_consecutive = 50,
372 .psm_entry_retries = 8,
373 .psm_exit_retries = 16,
374 .psm_entry_nullfunc_retries = 3,
375 .dynamic_ps_timeout = 1500,
377 .keep_alive_interval = 55000,
378 .max_listen_interval = 20,
379 .sta_sleep_auth = WL1271_PSM_ILLEGAL,
386 .host_clk_settling_time = 5000,
387 .host_fast_wakeup_support = CONF_FAST_WAKEUP_DISABLE,
391 .avg_weight_rssi_beacon = 20,
392 .avg_weight_rssi_data = 10,
393 .avg_weight_snr_beacon = 20,
394 .avg_weight_snr_data = 10,
397 .min_dwell_time_active = 7500,
398 .max_dwell_time_active = 30000,
399 .min_dwell_time_active_long = 25000,
400 .max_dwell_time_active_long = 50000,
401 .dwell_time_passive = 100000,
402 .dwell_time_dfs = 150000,
404 .split_scan_timeout = 50000,
408 * Values are in TU/1000 but since sched scan FW command
409 * params are in TUs rounding up may occur.
411 .base_dwell_time = 7500,
412 .max_dwell_time_delta = 22500,
413 /* based on 250bits per probe @1Mbps */
414 .dwell_time_delta_per_probe = 2000,
415 /* based on 250bits per probe @6Mbps (plus a bit more) */
416 .dwell_time_delta_per_probe_5 = 350,
417 .dwell_time_passive = 100000,
418 .dwell_time_dfs = 150000,
420 .rssi_threshold = -90,
424 .rx_ba_win_size = 32,
425 .tx_ba_win_size = 64,
426 .inactivity_timeout = 10000,
427 .tx_ba_tid_bitmap = CONF_TX_BA_ENABLED_TID_BITMAP,
433 .tx_min_block_num = 40,
435 .min_req_tx_blocks = 45,
436 .min_req_rx_blocks = 22,
442 .n_divider_fref_set_1 = 0xff, /* default */
443 .n_divider_fref_set_2 = 12,
444 .m_divider_fref_set_1 = 0xffff,
445 .m_divider_fref_set_2 = 148, /* default */
446 .coex_pll_stabilization_time = 0xffffffff, /* default */
447 .ldo_stabilization_time = 0xffff, /* default */
448 .fm_disturbed_band_margin = 0xff, /* default */
449 .swallow_clk_diff = 0xff, /* default */
458 .mode = WL12XX_FWLOG_ON_DEMAND,
461 .timestamp = WL12XX_FWLOG_TIMESTAMP_DISABLED,
462 .output = WL12XX_FWLOG_OUTPUT_HOST,
466 .rate_retry_score = 32000,
471 .inverse_curiosity_factor = 5,
473 .tx_fail_high_th = 10,
474 .per_alpha_shift = 4,
476 .per_beta1_shift = 10,
477 .per_beta2_shift = 8,
479 .rate_check_down = 12,
480 .rate_retry_policy = {
481 0x00, 0x00, 0x00, 0x00, 0x00,
482 0x00, 0x00, 0x00, 0x00, 0x00,
488 .hangover_period = 20,
490 .early_termination_mode = 1,
500 .bug_on_recovery = 0,
505 static struct wl18xx_priv_conf wl18xx_default_priv_conf = {
507 .mode = HT_MODE_DEFAULT,
510 .phy_standalone = 0x00,
511 .primary_clock_setting_time = 0x05,
512 .clock_valid_on_wake_up = 0x00,
513 .secondary_clock_setting_time = 0x05,
514 .board_type = BOARD_TYPE_HDK_18XX,
516 .dedicated_fem = FEM_NONE,
517 .low_band_component = COMPONENT_3_WAY_SWITCH,
518 .low_band_component_type = 0x04,
519 .high_band_component = COMPONENT_2_WAY_SWITCH,
520 .high_band_component_type = 0x09,
521 .tcxo_ldo_voltage = 0x00,
522 .xtal_itrim_val = 0x04,
524 .io_configuration = 0x01,
525 .sdio_configuration = 0x00,
528 .enable_tx_low_pwr_on_siso_rdl = 0x00,
530 .pwr_limit_reference_11_abg = 0x64,
531 .per_chan_pwr_limit_arr_11abg = {
532 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
533 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
534 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
535 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
536 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
537 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
538 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
539 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
540 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
541 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
542 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
543 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
544 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
545 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
546 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
547 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
548 0xff, 0xff, 0xff, 0xff, 0xff, 0xff },
549 .pwr_limit_reference_11p = 0x64,
550 .per_chan_bo_mode_11_abg = { 0x00, 0x00, 0x00, 0x00,
551 0x00, 0x00, 0x00, 0x00,
552 0x00, 0x00, 0x00, 0x00,
554 .per_chan_bo_mode_11_p = { 0x00, 0x00, 0x00, 0x00 },
555 .per_chan_pwr_limit_arr_11p = { 0xff, 0xff, 0xff, 0xff,
558 .low_power_val = 0x08,
559 .med_power_val = 0x12,
560 .high_power_val = 0x18,
561 .low_power_val_2nd = 0x05,
562 .med_power_val_2nd = 0x0a,
563 .high_power_val_2nd = 0x14,
564 .external_pa_dc2dc = 0,
565 .number_of_assembled_ant2_4 = 2,
566 .number_of_assembled_ant5 = 1,
571 static const struct wlcore_partition_set wl18xx_ptable[PART_TABLE_LEN] = {
572 [PART_TOP_PRCM_ELP_SOC] = {
573 .mem = { .start = 0x00A02000, .size = 0x00010000 },
574 .reg = { .start = 0x00807000, .size = 0x00005000 },
575 .mem2 = { .start = 0x00800000, .size = 0x0000B000 },
576 .mem3 = { .start = 0x00000000, .size = 0x00000000 },
579 .mem = { .start = 0x00000000, .size = 0x00014000 },
580 .reg = { .start = 0x00810000, .size = 0x0000BFFF },
581 .mem2 = { .start = 0x00000000, .size = 0x00000000 },
582 .mem3 = { .start = 0x00000000, .size = 0x00000000 },
585 .mem = { .start = 0x00700000, .size = 0x0000030c },
586 .reg = { .start = 0x00802000, .size = 0x00014578 },
587 .mem2 = { .start = 0x00B00404, .size = 0x00001000 },
588 .mem3 = { .start = 0x00C00000, .size = 0x00000400 },
591 .mem = { .start = 0x00800000, .size = 0x000050FC },
592 .reg = { .start = 0x00B00404, .size = 0x00001000 },
593 .mem2 = { .start = 0x00C00000, .size = 0x00000400 },
594 .mem3 = { .start = 0x00000000, .size = 0x00000000 },
597 .mem = { .start = 0x80926000,
598 .size = sizeof(struct wl18xx_mac_and_phy_params) },
599 .reg = { .start = 0x00000000, .size = 0x00000000 },
600 .mem2 = { .start = 0x00000000, .size = 0x00000000 },
601 .mem3 = { .start = 0x00000000, .size = 0x00000000 },
605 static const int wl18xx_rtable[REG_TABLE_LEN] = {
606 [REG_ECPU_CONTROL] = WL18XX_REG_ECPU_CONTROL,
607 [REG_INTERRUPT_NO_CLEAR] = WL18XX_REG_INTERRUPT_NO_CLEAR,
608 [REG_INTERRUPT_ACK] = WL18XX_REG_INTERRUPT_ACK,
609 [REG_COMMAND_MAILBOX_PTR] = WL18XX_REG_COMMAND_MAILBOX_PTR,
610 [REG_EVENT_MAILBOX_PTR] = WL18XX_REG_EVENT_MAILBOX_PTR,
611 [REG_INTERRUPT_TRIG] = WL18XX_REG_INTERRUPT_TRIG_H,
612 [REG_INTERRUPT_MASK] = WL18XX_REG_INTERRUPT_MASK,
613 [REG_PC_ON_RECOVERY] = WL18XX_SCR_PAD4,
614 [REG_CHIP_ID_B] = WL18XX_REG_CHIP_ID_B,
615 [REG_CMD_MBOX_ADDRESS] = WL18XX_CMD_MBOX_ADDRESS,
617 /* data access memory addresses, used with partition translation */
618 [REG_SLV_MEM_DATA] = WL18XX_SLV_MEM_DATA,
619 [REG_SLV_REG_DATA] = WL18XX_SLV_REG_DATA,
621 /* raw data access memory addresses */
622 [REG_RAW_FW_STATUS_ADDR] = WL18XX_FW_STATUS_ADDR,
625 static const struct wl18xx_clk_cfg wl18xx_clk_table[NUM_CLOCK_CONFIGS] = {
626 [CLOCK_CONFIG_16_2_M] = { 7, 104, 801, 4, true },
627 [CLOCK_CONFIG_16_368_M] = { 9, 132, 3751, 4, true },
628 [CLOCK_CONFIG_16_8_M] = { 7, 100, 0, 0, false },
629 [CLOCK_CONFIG_19_2_M] = { 8, 100, 0, 0, false },
630 [CLOCK_CONFIG_26_M] = { 13, 120, 0, 0, false },
631 [CLOCK_CONFIG_32_736_M] = { 9, 132, 3751, 4, true },
632 [CLOCK_CONFIG_33_6_M] = { 7, 100, 0, 0, false },
633 [CLOCK_CONFIG_38_468_M] = { 8, 100, 0, 0, false },
634 [CLOCK_CONFIG_52_M] = { 13, 120, 0, 0, false },
637 /* TODO: maybe move to a new header file? */
638 #define WL18XX_FW_NAME "ti-connectivity/wl18xx-fw-2.bin"
640 static int wl18xx_identify_chip(struct wl1271 *wl)
644 switch (wl->chip.id) {
645 case CHIP_ID_185x_PG20:
646 wl1271_debug(DEBUG_BOOT, "chip id 0x%x (185x PG20)",
648 wl->sr_fw_name = WL18XX_FW_NAME;
649 /* wl18xx uses the same firmware for PLT */
650 wl->plt_fw_name = WL18XX_FW_NAME;
651 wl->quirks |= WLCORE_QUIRK_RX_BLOCKSIZE_ALIGN |
652 WLCORE_QUIRK_TX_BLOCKSIZE_ALIGN |
653 WLCORE_QUIRK_NO_SCHED_SCAN_WHILE_CONN |
654 WLCORE_QUIRK_TX_PAD_LAST_FRAME |
655 WLCORE_QUIRK_REGDOMAIN_CONF |
656 WLCORE_QUIRK_DUAL_PROBE_TMPL;
658 wlcore_set_min_fw_ver(wl, WL18XX_CHIP_VER,
659 WL18XX_IFTYPE_VER, WL18XX_MAJOR_VER,
660 WL18XX_SUBTYPE_VER, WL18XX_MINOR_VER,
661 /* there's no separate multi-role FW */
664 case CHIP_ID_185x_PG10:
665 wl1271_warning("chip id 0x%x (185x PG10) is deprecated",
671 wl1271_warning("unsupported chip id: 0x%x", wl->chip.id);
676 wl->scan_templ_id_2_4 = CMD_TEMPL_CFG_PROBE_REQ_2_4;
677 wl->scan_templ_id_5 = CMD_TEMPL_CFG_PROBE_REQ_5;
678 wl->sched_scan_templ_id_2_4 = CMD_TEMPL_PROBE_REQ_2_4_PERIODIC;
679 wl->sched_scan_templ_id_5 = CMD_TEMPL_PROBE_REQ_5_PERIODIC;
680 wl->max_channels_5 = WL18XX_MAX_CHANNELS_5GHZ;
681 wl->ba_rx_session_count_max = WL18XX_RX_BA_MAX_SESSIONS;
686 static int wl18xx_set_clk(struct wl1271 *wl)
691 ret = wlcore_set_partition(wl, &wl->ptable[PART_TOP_PRCM_ELP_SOC]);
695 /* TODO: PG2: apparently we need to read the clk type */
697 ret = wl18xx_top_reg_read(wl, PRIMARY_CLK_DETECT, &clk_freq);
701 wl1271_debug(DEBUG_BOOT, "clock freq %d (%d, %d, %d, %d, %s)", clk_freq,
702 wl18xx_clk_table[clk_freq].n, wl18xx_clk_table[clk_freq].m,
703 wl18xx_clk_table[clk_freq].p, wl18xx_clk_table[clk_freq].q,
704 wl18xx_clk_table[clk_freq].swallow ? "swallow" : "spit");
706 ret = wl18xx_top_reg_write(wl, PLLSH_WCS_PLL_N,
707 wl18xx_clk_table[clk_freq].n);
711 ret = wl18xx_top_reg_write(wl, PLLSH_WCS_PLL_M,
712 wl18xx_clk_table[clk_freq].m);
716 if (wl18xx_clk_table[clk_freq].swallow) {
717 /* first the 16 lower bits */
718 ret = wl18xx_top_reg_write(wl, PLLSH_WCS_PLL_Q_FACTOR_CFG_1,
719 wl18xx_clk_table[clk_freq].q &
720 PLLSH_WCS_PLL_Q_FACTOR_CFG_1_MASK);
724 /* then the 16 higher bits, masked out */
725 ret = wl18xx_top_reg_write(wl, PLLSH_WCS_PLL_Q_FACTOR_CFG_2,
726 (wl18xx_clk_table[clk_freq].q >> 16) &
727 PLLSH_WCS_PLL_Q_FACTOR_CFG_2_MASK);
731 /* first the 16 lower bits */
732 ret = wl18xx_top_reg_write(wl, PLLSH_WCS_PLL_P_FACTOR_CFG_1,
733 wl18xx_clk_table[clk_freq].p &
734 PLLSH_WCS_PLL_P_FACTOR_CFG_1_MASK);
738 /* then the 16 higher bits, masked out */
739 ret = wl18xx_top_reg_write(wl, PLLSH_WCS_PLL_P_FACTOR_CFG_2,
740 (wl18xx_clk_table[clk_freq].p >> 16) &
741 PLLSH_WCS_PLL_P_FACTOR_CFG_2_MASK);
743 ret = wl18xx_top_reg_write(wl, PLLSH_WCS_PLL_SWALLOW_EN,
744 PLLSH_WCS_PLL_SWALLOW_EN_VAL2);
751 static int wl18xx_boot_soft_reset(struct wl1271 *wl)
756 ret = wlcore_write32(wl, WL18XX_ENABLE, 0x0);
760 /* disable auto calibration on start*/
761 ret = wlcore_write32(wl, WL18XX_SPARE_A2, 0xffff);
767 static int wl18xx_pre_boot(struct wl1271 *wl)
771 ret = wl18xx_set_clk(wl);
775 /* Continue the ELP wake up sequence */
776 ret = wlcore_write32(wl, WL18XX_WELP_ARM_COMMAND, WELP_ARM_COMMAND_VAL);
782 ret = wlcore_set_partition(wl, &wl->ptable[PART_BOOT]);
786 /* Disable interrupts */
787 ret = wlcore_write_reg(wl, REG_INTERRUPT_MASK, WL1271_ACX_INTR_ALL);
791 ret = wl18xx_boot_soft_reset(wl);
797 static int wl18xx_pre_upload(struct wl1271 *wl)
802 ret = wlcore_set_partition(wl, &wl->ptable[PART_BOOT]);
806 /* TODO: check if this is all needed */
807 ret = wlcore_write32(wl, WL18XX_EEPROMLESS_IND, WL18XX_EEPROMLESS_IND);
811 ret = wlcore_read_reg(wl, REG_CHIP_ID_B, &tmp);
815 wl1271_debug(DEBUG_BOOT, "chip id 0x%x", tmp);
817 ret = wlcore_read32(wl, WL18XX_SCR_PAD2, &tmp);
823 static int wl18xx_set_mac_and_phy(struct wl1271 *wl)
825 struct wl18xx_priv *priv = wl->priv;
826 struct wl18xx_mac_and_phy_params *params;
829 params = kmemdup(&priv->conf.phy, sizeof(*params), GFP_KERNEL);
835 ret = wlcore_set_partition(wl, &wl->ptable[PART_PHY_INIT]);
839 ret = wlcore_write(wl, WL18XX_PHY_INIT_MEM_ADDR, params,
840 sizeof(*params), false);
847 static int wl18xx_enable_interrupts(struct wl1271 *wl)
849 u32 event_mask, intr_mask;
852 event_mask = WL18XX_ACX_EVENTS_VECTOR;
853 intr_mask = WL18XX_INTR_MASK;
855 ret = wlcore_write_reg(wl, REG_INTERRUPT_MASK, event_mask);
859 wlcore_enable_interrupts(wl);
861 ret = wlcore_write_reg(wl, REG_INTERRUPT_MASK,
862 WL1271_ACX_INTR_ALL & ~intr_mask);
864 goto disable_interrupts;
869 wlcore_disable_interrupts(wl);
875 static int wl18xx_boot(struct wl1271 *wl)
879 ret = wl18xx_pre_boot(wl);
883 ret = wl18xx_pre_upload(wl);
887 ret = wlcore_boot_upload_firmware(wl);
891 ret = wl18xx_set_mac_and_phy(wl);
895 wl->event_mask = BSS_LOSS_EVENT_ID |
896 SCAN_COMPLETE_EVENT_ID |
897 RSSI_SNR_TRIGGER_0_EVENT_ID |
898 PERIODIC_SCAN_COMPLETE_EVENT_ID |
899 PERIODIC_SCAN_REPORT_EVENT_ID |
900 DUMMY_PACKET_EVENT_ID |
901 PEER_REMOVE_COMPLETE_EVENT_ID |
902 BA_SESSION_RX_CONSTRAINT_EVENT_ID |
903 REMAIN_ON_CHANNEL_COMPLETE_EVENT_ID |
904 INACTIVE_STA_EVENT_ID |
905 MAX_TX_FAILURE_EVENT_ID |
906 CHANNEL_SWITCH_COMPLETE_EVENT_ID |
907 DFS_CHANNELS_CONFIG_COMPLETE_EVENT;
909 ret = wlcore_boot_run_firmware(wl);
913 ret = wl18xx_enable_interrupts(wl);
919 static int wl18xx_trigger_cmd(struct wl1271 *wl, int cmd_box_addr,
920 void *buf, size_t len)
922 struct wl18xx_priv *priv = wl->priv;
924 memcpy(priv->cmd_buf, buf, len);
925 memset(priv->cmd_buf + len, 0, WL18XX_CMD_MAX_SIZE - len);
927 return wlcore_write(wl, cmd_box_addr, priv->cmd_buf,
928 WL18XX_CMD_MAX_SIZE, false);
931 static int wl18xx_ack_event(struct wl1271 *wl)
933 return wlcore_write_reg(wl, REG_INTERRUPT_TRIG,
934 WL18XX_INTR_TRIG_EVENT_ACK);
937 static u32 wl18xx_calc_tx_blocks(struct wl1271 *wl, u32 len, u32 spare_blks)
939 u32 blk_size = WL18XX_TX_HW_BLOCK_SIZE;
940 return (len + blk_size - 1) / blk_size + spare_blks;
944 wl18xx_set_tx_desc_blocks(struct wl1271 *wl, struct wl1271_tx_hw_descr *desc,
945 u32 blks, u32 spare_blks)
947 desc->wl18xx_mem.total_mem_blocks = blks;
951 wl18xx_set_tx_desc_data_len(struct wl1271 *wl, struct wl1271_tx_hw_descr *desc,
954 desc->length = cpu_to_le16(skb->len);
956 /* if only the last frame is to be padded, we unset this bit on Tx */
957 if (wl->quirks & WLCORE_QUIRK_TX_PAD_LAST_FRAME)
958 desc->wl18xx_mem.ctrl = WL18XX_TX_CTRL_NOT_PADDED;
960 desc->wl18xx_mem.ctrl = 0;
962 wl1271_debug(DEBUG_TX, "tx_fill_hdr: hlid: %d "
963 "len: %d life: %d mem: %d", desc->hlid,
964 le16_to_cpu(desc->length),
965 le16_to_cpu(desc->life_time),
966 desc->wl18xx_mem.total_mem_blocks);
969 static enum wl_rx_buf_align
970 wl18xx_get_rx_buf_align(struct wl1271 *wl, u32 rx_desc)
972 if (rx_desc & RX_BUF_PADDED_PAYLOAD)
973 return WLCORE_RX_BUF_PADDED;
975 return WLCORE_RX_BUF_ALIGNED;
978 static u32 wl18xx_get_rx_packet_len(struct wl1271 *wl, void *rx_data,
981 struct wl1271_rx_descriptor *desc = rx_data;
984 if (data_len < sizeof(*desc))
987 return data_len - sizeof(*desc);
990 static void wl18xx_tx_immediate_completion(struct wl1271 *wl)
992 wl18xx_tx_immediate_complete(wl);
995 static int wl18xx_set_host_cfg_bitmap(struct wl1271 *wl, u32 extra_mem_blk)
998 u32 sdio_align_size = 0;
999 u32 host_cfg_bitmap = HOST_IF_CFG_RX_FIFO_ENABLE |
1000 HOST_IF_CFG_ADD_RX_ALIGNMENT;
1002 /* Enable Tx SDIO padding */
1003 if (wl->quirks & WLCORE_QUIRK_TX_BLOCKSIZE_ALIGN) {
1004 host_cfg_bitmap |= HOST_IF_CFG_TX_PAD_TO_SDIO_BLK;
1005 sdio_align_size = WL12XX_BUS_BLOCK_SIZE;
1008 /* Enable Rx SDIO padding */
1009 if (wl->quirks & WLCORE_QUIRK_RX_BLOCKSIZE_ALIGN) {
1010 host_cfg_bitmap |= HOST_IF_CFG_RX_PAD_TO_SDIO_BLK;
1011 sdio_align_size = WL12XX_BUS_BLOCK_SIZE;
1014 ret = wl18xx_acx_host_if_cfg_bitmap(wl, host_cfg_bitmap,
1015 sdio_align_size, extra_mem_blk,
1016 WL18XX_HOST_IF_LEN_SIZE_FIELD);
1023 static int wl18xx_hw_init(struct wl1271 *wl)
1026 struct wl18xx_priv *priv = wl->priv;
1028 /* (re)init private structures. Relevant on recovery as well. */
1029 priv->last_fw_rls_idx = 0;
1030 priv->extra_spare_key_count = 0;
1032 /* set the default amount of spare blocks in the bitmap */
1033 ret = wl18xx_set_host_cfg_bitmap(wl, WL18XX_TX_HW_BLOCK_SPARE);
1037 if (checksum_param) {
1038 ret = wl18xx_acx_set_checksum_state(wl);
1046 static void wl18xx_set_tx_desc_csum(struct wl1271 *wl,
1047 struct wl1271_tx_hw_descr *desc,
1048 struct sk_buff *skb)
1051 struct iphdr *ip_hdr;
1053 if (!checksum_param) {
1054 desc->wl18xx_checksum_data = 0;
1058 if (skb->ip_summed != CHECKSUM_PARTIAL) {
1059 desc->wl18xx_checksum_data = 0;
1063 ip_hdr_offset = skb_network_header(skb) - skb_mac_header(skb);
1064 if (WARN_ON(ip_hdr_offset >= (1<<7))) {
1065 desc->wl18xx_checksum_data = 0;
1069 desc->wl18xx_checksum_data = ip_hdr_offset << 1;
1071 /* FW is interested only in the LSB of the protocol TCP=0 UDP=1 */
1072 ip_hdr = (void *)skb_network_header(skb);
1073 desc->wl18xx_checksum_data |= (ip_hdr->protocol & 0x01);
1076 static void wl18xx_set_rx_csum(struct wl1271 *wl,
1077 struct wl1271_rx_descriptor *desc,
1078 struct sk_buff *skb)
1080 if (desc->status & WL18XX_RX_CHECKSUM_MASK)
1081 skb->ip_summed = CHECKSUM_UNNECESSARY;
1084 static bool wl18xx_is_mimo_supported(struct wl1271 *wl)
1086 struct wl18xx_priv *priv = wl->priv;
1088 /* only support MIMO with multiple antennas, and when SISO
1089 * is not forced through config
1091 return (priv->conf.phy.number_of_assembled_ant2_4 >= 2) &&
1092 (priv->conf.ht.mode != HT_MODE_WIDE) &&
1093 (priv->conf.ht.mode != HT_MODE_SISO20);
1097 * TODO: instead of having these two functions to get the rate mask,
1098 * we should modify the wlvif->rate_set instead
1100 static u32 wl18xx_sta_get_ap_rate_mask(struct wl1271 *wl,
1101 struct wl12xx_vif *wlvif)
1103 u32 hw_rate_set = wlvif->rate_set;
1105 if (wlvif->channel_type == NL80211_CHAN_HT40MINUS ||
1106 wlvif->channel_type == NL80211_CHAN_HT40PLUS) {
1107 wl1271_debug(DEBUG_ACX, "using wide channel rate mask");
1108 hw_rate_set |= CONF_TX_RATE_USE_WIDE_CHAN;
1110 /* we don't support MIMO in wide-channel mode */
1111 hw_rate_set &= ~CONF_TX_MIMO_RATES;
1112 } else if (wl18xx_is_mimo_supported(wl)) {
1113 wl1271_debug(DEBUG_ACX, "using MIMO channel rate mask");
1114 hw_rate_set |= CONF_TX_MIMO_RATES;
1120 static u32 wl18xx_ap_get_mimo_wide_rate_mask(struct wl1271 *wl,
1121 struct wl12xx_vif *wlvif)
1123 if (wlvif->channel_type == NL80211_CHAN_HT40MINUS ||
1124 wlvif->channel_type == NL80211_CHAN_HT40PLUS) {
1125 wl1271_debug(DEBUG_ACX, "using wide channel rate mask");
1127 /* sanity check - we don't support this */
1128 if (WARN_ON(wlvif->band != IEEE80211_BAND_5GHZ))
1131 return CONF_TX_RATE_USE_WIDE_CHAN;
1132 } else if (wl18xx_is_mimo_supported(wl) &&
1133 wlvif->band == IEEE80211_BAND_2GHZ) {
1134 wl1271_debug(DEBUG_ACX, "using MIMO rate mask");
1136 * we don't care about HT channel here - if a peer doesn't
1137 * support MIMO, we won't enable it in its rates
1139 return CONF_TX_MIMO_RATES;
1145 static int wl18xx_get_pg_ver(struct wl1271 *wl, s8 *ver)
1148 s8 rom = 0, metal = 0, pg_ver = 0, rdl_ver = 0;
1151 ret = wlcore_set_partition(wl, &wl->ptable[PART_TOP_PRCM_ELP_SOC]);
1155 ret = wlcore_read32(wl, WL18XX_REG_FUSE_DATA_1_3, &fuse);
1159 pg_ver = (fuse & WL18XX_PG_VER_MASK) >> WL18XX_PG_VER_OFFSET;
1160 rom = (fuse & WL18XX_ROM_VER_MASK) >> WL18XX_ROM_VER_OFFSET;
1163 metal = (fuse & WL18XX_METAL_VER_MASK) >>
1164 WL18XX_METAL_VER_OFFSET;
1166 metal = (fuse & WL18XX_NEW_METAL_VER_MASK) >>
1167 WL18XX_NEW_METAL_VER_OFFSET;
1169 ret = wlcore_read32(wl, WL18XX_REG_FUSE_DATA_2_3, &fuse);
1173 rdl_ver = (fuse & WL18XX_RDL_VER_MASK) >> WL18XX_RDL_VER_OFFSET;
1174 if (rdl_ver > RDL_MAX)
1177 wl1271_info("wl18xx HW: RDL %d, %s, PG %x.%x (ROM %x)",
1178 rdl_ver, rdl_names[rdl_ver], pg_ver, metal, rom);
1183 ret = wlcore_set_partition(wl, &wl->ptable[PART_BOOT]);
1189 #define WL18XX_CONF_FILE_NAME "ti-connectivity/wl18xx-conf.bin"
1190 static int wl18xx_conf_init(struct wl1271 *wl, struct device *dev)
1192 struct wl18xx_priv *priv = wl->priv;
1193 struct wlcore_conf_file *conf_file;
1194 const struct firmware *fw;
1197 ret = request_firmware(&fw, WL18XX_CONF_FILE_NAME, dev);
1199 wl1271_error("could not get configuration binary %s: %d",
1200 WL18XX_CONF_FILE_NAME, ret);
1204 if (fw->size != WL18XX_CONF_SIZE) {
1205 wl1271_error("configuration binary file size is wrong, expected %zu got %zu",
1206 WL18XX_CONF_SIZE, fw->size);
1211 conf_file = (struct wlcore_conf_file *) fw->data;
1213 if (conf_file->header.magic != cpu_to_le32(WL18XX_CONF_MAGIC)) {
1214 wl1271_error("configuration binary file magic number mismatch, "
1215 "expected 0x%0x got 0x%0x", WL18XX_CONF_MAGIC,
1216 conf_file->header.magic);
1221 if (conf_file->header.version != cpu_to_le32(WL18XX_CONF_VERSION)) {
1222 wl1271_error("configuration binary file version not supported, "
1223 "expected 0x%08x got 0x%08x",
1224 WL18XX_CONF_VERSION, conf_file->header.version);
1229 memcpy(&wl->conf, &conf_file->core, sizeof(wl18xx_conf));
1230 memcpy(&priv->conf, &conf_file->priv, sizeof(priv->conf));
1235 wl1271_warning("falling back to default config");
1237 /* apply driver default configuration */
1238 memcpy(&wl->conf, &wl18xx_conf, sizeof(wl18xx_conf));
1239 /* apply default private configuration */
1240 memcpy(&priv->conf, &wl18xx_default_priv_conf, sizeof(priv->conf));
1242 /* For now we just fallback */
1246 release_firmware(fw);
1250 static int wl18xx_plt_init(struct wl1271 *wl)
1254 /* calibrator based auto/fem detect not supported for 18xx */
1255 if (wl->plt_mode == PLT_FEM_DETECT) {
1256 wl1271_error("wl18xx_plt_init: PLT FEM_DETECT not supported");
1260 ret = wlcore_write32(wl, WL18XX_SCR_PAD8, WL18XX_SCR_PAD8_PLT);
1264 return wl->ops->boot(wl);
1267 static int wl18xx_get_mac(struct wl1271 *wl)
1272 ret = wlcore_set_partition(wl, &wl->ptable[PART_TOP_PRCM_ELP_SOC]);
1276 ret = wlcore_read32(wl, WL18XX_REG_FUSE_BD_ADDR_1, &mac1);
1280 ret = wlcore_read32(wl, WL18XX_REG_FUSE_BD_ADDR_2, &mac2);
1284 /* these are the two parts of the BD_ADDR */
1285 wl->fuse_oui_addr = ((mac2 & 0xffff) << 8) +
1286 ((mac1 & 0xff000000) >> 24);
1287 wl->fuse_nic_addr = (mac1 & 0xffffff);
1289 ret = wlcore_set_partition(wl, &wl->ptable[PART_DOWN]);
1295 static int wl18xx_handle_static_data(struct wl1271 *wl,
1296 struct wl1271_static_data *static_data)
1298 struct wl18xx_static_data_priv *static_data_priv =
1299 (struct wl18xx_static_data_priv *) static_data->priv;
1301 strncpy(wl->chip.phy_fw_ver_str, static_data_priv->phy_version,
1302 sizeof(wl->chip.phy_fw_ver_str));
1304 /* make sure the string is NULL-terminated */
1305 wl->chip.phy_fw_ver_str[sizeof(wl->chip.phy_fw_ver_str) - 1] = '\0';
1307 wl1271_info("PHY firmware version: %s", static_data_priv->phy_version);
1312 static int wl18xx_get_spare_blocks(struct wl1271 *wl, bool is_gem)
1314 struct wl18xx_priv *priv = wl->priv;
1316 /* If we have keys requiring extra spare, indulge them */
1317 if (priv->extra_spare_key_count)
1318 return WL18XX_TX_HW_EXTRA_BLOCK_SPARE;
1320 return WL18XX_TX_HW_BLOCK_SPARE;
1323 static int wl18xx_set_key(struct wl1271 *wl, enum set_key_cmd cmd,
1324 struct ieee80211_vif *vif,
1325 struct ieee80211_sta *sta,
1326 struct ieee80211_key_conf *key_conf)
1328 struct wl18xx_priv *priv = wl->priv;
1329 bool change_spare = false, special_enc;
1332 wl1271_debug(DEBUG_CRYPT, "extra spare keys before: %d",
1333 priv->extra_spare_key_count);
1335 special_enc = key_conf->cipher == WL1271_CIPHER_SUITE_GEM ||
1336 key_conf->cipher == WLAN_CIPHER_SUITE_TKIP;
1338 ret = wlcore_set_key(wl, cmd, vif, sta, key_conf);
1343 * when adding the first or removing the last GEM/TKIP key,
1344 * we have to adjust the number of spare blocks.
1347 if (cmd == SET_KEY) {
1349 change_spare = (priv->extra_spare_key_count == 0);
1350 priv->extra_spare_key_count++;
1351 } else if (cmd == DISABLE_KEY) {
1353 change_spare = (priv->extra_spare_key_count == 1);
1354 priv->extra_spare_key_count--;
1358 wl1271_debug(DEBUG_CRYPT, "extra spare keys after: %d",
1359 priv->extra_spare_key_count);
1364 /* key is now set, change the spare blocks */
1365 if (priv->extra_spare_key_count)
1366 ret = wl18xx_set_host_cfg_bitmap(wl,
1367 WL18XX_TX_HW_EXTRA_BLOCK_SPARE);
1369 ret = wl18xx_set_host_cfg_bitmap(wl,
1370 WL18XX_TX_HW_BLOCK_SPARE);
1376 static u32 wl18xx_pre_pkt_send(struct wl1271 *wl,
1377 u32 buf_offset, u32 last_len)
1379 if (wl->quirks & WLCORE_QUIRK_TX_PAD_LAST_FRAME) {
1380 struct wl1271_tx_hw_descr *last_desc;
1382 /* get the last TX HW descriptor written to the aggr buf */
1383 last_desc = (struct wl1271_tx_hw_descr *)(wl->aggr_buf +
1384 buf_offset - last_len);
1386 /* the last frame is padded up to an SDIO block */
1387 last_desc->wl18xx_mem.ctrl &= ~WL18XX_TX_CTRL_NOT_PADDED;
1388 return ALIGN(buf_offset, WL12XX_BUS_BLOCK_SIZE);
1391 /* no modifications */
1395 static void wl18xx_sta_rc_update(struct wl1271 *wl,
1396 struct wl12xx_vif *wlvif,
1397 struct ieee80211_sta *sta,
1400 bool wide = sta->bandwidth >= IEEE80211_STA_RX_BW_40;
1402 wl1271_debug(DEBUG_MAC80211, "mac80211 sta_rc_update wide %d", wide);
1404 if (!(changed & IEEE80211_RC_BW_CHANGED))
1407 mutex_lock(&wl->mutex);
1410 if (WARN_ON(wlvif->bss_type != BSS_TYPE_STA_BSS))
1413 /* ignore the change before association */
1414 if (!test_bit(WLVIF_FLAG_STA_ASSOCIATED, &wlvif->flags))
1418 * If we started out as wide, we can change the operation mode. If we
1419 * thought this was a 20mhz AP, we have to reconnect
1421 if (wlvif->sta.role_chan_type == NL80211_CHAN_HT40MINUS ||
1422 wlvif->sta.role_chan_type == NL80211_CHAN_HT40PLUS)
1423 wl18xx_acx_peer_ht_operation_mode(wl, wlvif->sta.hlid, wide);
1425 ieee80211_connection_loss(wl12xx_wlvif_to_vif(wlvif));
1428 mutex_unlock(&wl->mutex);
1431 static int wl18xx_set_peer_cap(struct wl1271 *wl,
1432 struct ieee80211_sta_ht_cap *ht_cap,
1433 bool allow_ht_operation,
1434 u32 rate_set, u8 hlid)
1436 return wl18xx_acx_set_peer_cap(wl, ht_cap, allow_ht_operation,
1440 static bool wl18xx_lnk_high_prio(struct wl1271 *wl, u8 hlid,
1441 struct wl1271_link *lnk)
1444 struct wl18xx_fw_status_priv *status_priv =
1445 (struct wl18xx_fw_status_priv *)wl->fw_status_2->priv;
1446 u32 suspend_bitmap = le32_to_cpu(status_priv->link_suspend_bitmap);
1448 /* suspended links are never high priority */
1449 if (test_bit(hlid, (unsigned long *)&suspend_bitmap))
1452 /* the priority thresholds are taken from FW */
1453 if (test_bit(hlid, (unsigned long *)&wl->fw_fast_lnk_map) &&
1454 !test_bit(hlid, (unsigned long *)&wl->ap_fw_ps_map))
1455 thold = status_priv->tx_fast_link_prio_threshold;
1457 thold = status_priv->tx_slow_link_prio_threshold;
1459 return lnk->allocated_pkts < thold;
1462 static bool wl18xx_lnk_low_prio(struct wl1271 *wl, u8 hlid,
1463 struct wl1271_link *lnk)
1466 struct wl18xx_fw_status_priv *status_priv =
1467 (struct wl18xx_fw_status_priv *)wl->fw_status_2->priv;
1468 u32 suspend_bitmap = le32_to_cpu(status_priv->link_suspend_bitmap);
1470 if (test_bit(hlid, (unsigned long *)&suspend_bitmap))
1471 thold = status_priv->tx_suspend_threshold;
1472 else if (test_bit(hlid, (unsigned long *)&wl->fw_fast_lnk_map) &&
1473 !test_bit(hlid, (unsigned long *)&wl->ap_fw_ps_map))
1474 thold = status_priv->tx_fast_stop_threshold;
1476 thold = status_priv->tx_slow_stop_threshold;
1478 return lnk->allocated_pkts < thold;
1481 static int wl18xx_setup(struct wl1271 *wl);
1483 static struct wlcore_ops wl18xx_ops = {
1484 .setup = wl18xx_setup,
1485 .identify_chip = wl18xx_identify_chip,
1486 .boot = wl18xx_boot,
1487 .plt_init = wl18xx_plt_init,
1488 .trigger_cmd = wl18xx_trigger_cmd,
1489 .ack_event = wl18xx_ack_event,
1490 .wait_for_event = wl18xx_wait_for_event,
1491 .process_mailbox_events = wl18xx_process_mailbox_events,
1492 .calc_tx_blocks = wl18xx_calc_tx_blocks,
1493 .set_tx_desc_blocks = wl18xx_set_tx_desc_blocks,
1494 .set_tx_desc_data_len = wl18xx_set_tx_desc_data_len,
1495 .get_rx_buf_align = wl18xx_get_rx_buf_align,
1496 .get_rx_packet_len = wl18xx_get_rx_packet_len,
1497 .tx_immediate_compl = wl18xx_tx_immediate_completion,
1498 .tx_delayed_compl = NULL,
1499 .hw_init = wl18xx_hw_init,
1500 .set_tx_desc_csum = wl18xx_set_tx_desc_csum,
1501 .get_pg_ver = wl18xx_get_pg_ver,
1502 .set_rx_csum = wl18xx_set_rx_csum,
1503 .sta_get_ap_rate_mask = wl18xx_sta_get_ap_rate_mask,
1504 .ap_get_mimo_wide_rate_mask = wl18xx_ap_get_mimo_wide_rate_mask,
1505 .get_mac = wl18xx_get_mac,
1506 .debugfs_init = wl18xx_debugfs_add_files,
1507 .scan_start = wl18xx_scan_start,
1508 .scan_stop = wl18xx_scan_stop,
1509 .sched_scan_start = wl18xx_sched_scan_start,
1510 .sched_scan_stop = wl18xx_scan_sched_scan_stop,
1511 .handle_static_data = wl18xx_handle_static_data,
1512 .get_spare_blocks = wl18xx_get_spare_blocks,
1513 .set_key = wl18xx_set_key,
1514 .channel_switch = wl18xx_cmd_channel_switch,
1515 .pre_pkt_send = wl18xx_pre_pkt_send,
1516 .sta_rc_update = wl18xx_sta_rc_update,
1517 .set_peer_cap = wl18xx_set_peer_cap,
1518 .lnk_high_prio = wl18xx_lnk_high_prio,
1519 .lnk_low_prio = wl18xx_lnk_low_prio,
1522 /* HT cap appropriate for wide channels in 2Ghz */
1523 static struct ieee80211_sta_ht_cap wl18xx_siso40_ht_cap_2ghz = {
1524 .cap = IEEE80211_HT_CAP_SGI_20 | IEEE80211_HT_CAP_SGI_40 |
1525 IEEE80211_HT_CAP_SUP_WIDTH_20_40 | IEEE80211_HT_CAP_DSSSCCK40 |
1526 IEEE80211_HT_CAP_GRN_FLD,
1527 .ht_supported = true,
1528 .ampdu_factor = IEEE80211_HT_MAX_AMPDU_16K,
1529 .ampdu_density = IEEE80211_HT_MPDU_DENSITY_16,
1531 .rx_mask = { 0xff, 0, 0, 0, 0, 0, 0, 0, 0, 0, },
1532 .rx_highest = cpu_to_le16(150),
1533 .tx_params = IEEE80211_HT_MCS_TX_DEFINED,
1537 /* HT cap appropriate for wide channels in 5Ghz */
1538 static struct ieee80211_sta_ht_cap wl18xx_siso40_ht_cap_5ghz = {
1539 .cap = IEEE80211_HT_CAP_SGI_20 | IEEE80211_HT_CAP_SGI_40 |
1540 IEEE80211_HT_CAP_SUP_WIDTH_20_40 |
1541 IEEE80211_HT_CAP_GRN_FLD,
1542 .ht_supported = true,
1543 .ampdu_factor = IEEE80211_HT_MAX_AMPDU_16K,
1544 .ampdu_density = IEEE80211_HT_MPDU_DENSITY_16,
1546 .rx_mask = { 0xff, 0, 0, 0, 0, 0, 0, 0, 0, 0, },
1547 .rx_highest = cpu_to_le16(150),
1548 .tx_params = IEEE80211_HT_MCS_TX_DEFINED,
1552 /* HT cap appropriate for SISO 20 */
1553 static struct ieee80211_sta_ht_cap wl18xx_siso20_ht_cap = {
1554 .cap = IEEE80211_HT_CAP_SGI_20 |
1555 IEEE80211_HT_CAP_GRN_FLD,
1556 .ht_supported = true,
1557 .ampdu_factor = IEEE80211_HT_MAX_AMPDU_16K,
1558 .ampdu_density = IEEE80211_HT_MPDU_DENSITY_16,
1560 .rx_mask = { 0xff, 0, 0, 0, 0, 0, 0, 0, 0, 0, },
1561 .rx_highest = cpu_to_le16(72),
1562 .tx_params = IEEE80211_HT_MCS_TX_DEFINED,
1566 /* HT cap appropriate for MIMO rates in 20mhz channel */
1567 static struct ieee80211_sta_ht_cap wl18xx_mimo_ht_cap_2ghz = {
1568 .cap = IEEE80211_HT_CAP_SGI_20 |
1569 IEEE80211_HT_CAP_GRN_FLD,
1570 .ht_supported = true,
1571 .ampdu_factor = IEEE80211_HT_MAX_AMPDU_16K,
1572 .ampdu_density = IEEE80211_HT_MPDU_DENSITY_16,
1574 .rx_mask = { 0xff, 0xff, 0, 0, 0, 0, 0, 0, 0, 0, },
1575 .rx_highest = cpu_to_le16(144),
1576 .tx_params = IEEE80211_HT_MCS_TX_DEFINED,
1580 static int wl18xx_setup(struct wl1271 *wl)
1582 struct wl18xx_priv *priv = wl->priv;
1585 wl->rtable = wl18xx_rtable;
1586 wl->num_tx_desc = WL18XX_NUM_TX_DESCRIPTORS;
1587 wl->num_rx_desc = WL18XX_NUM_RX_DESCRIPTORS;
1588 wl->num_channels = 2;
1589 wl->num_mac_addr = WL18XX_NUM_MAC_ADDRESSES;
1590 wl->band_rate_to_idx = wl18xx_band_rate_to_idx;
1591 wl->hw_tx_rate_tbl_size = WL18XX_CONF_HW_RXTX_RATE_MAX;
1592 wl->hw_min_ht_rate = WL18XX_CONF_HW_RXTX_RATE_MCS0;
1593 wl->fw_status_priv_len = sizeof(struct wl18xx_fw_status_priv);
1594 wl->stats.fw_stats_len = sizeof(struct wl18xx_acx_statistics);
1595 wl->static_data_priv_len = sizeof(struct wl18xx_static_data_priv);
1597 if (num_rx_desc_param != -1)
1598 wl->num_rx_desc = num_rx_desc_param;
1600 ret = wl18xx_conf_init(wl, wl->dev);
1604 /* If the module param is set, update it in conf */
1605 if (board_type_param) {
1606 if (!strcmp(board_type_param, "fpga")) {
1607 priv->conf.phy.board_type = BOARD_TYPE_FPGA_18XX;
1608 } else if (!strcmp(board_type_param, "hdk")) {
1609 priv->conf.phy.board_type = BOARD_TYPE_HDK_18XX;
1610 } else if (!strcmp(board_type_param, "dvp")) {
1611 priv->conf.phy.board_type = BOARD_TYPE_DVP_18XX;
1612 } else if (!strcmp(board_type_param, "evb")) {
1613 priv->conf.phy.board_type = BOARD_TYPE_EVB_18XX;
1614 } else if (!strcmp(board_type_param, "com8")) {
1615 priv->conf.phy.board_type = BOARD_TYPE_COM8_18XX;
1617 wl1271_error("invalid board type '%s'",
1623 if (priv->conf.phy.board_type >= NUM_BOARD_TYPES) {
1624 wl1271_error("invalid board type '%d'",
1625 priv->conf.phy.board_type);
1629 if (low_band_component_param != -1)
1630 priv->conf.phy.low_band_component = low_band_component_param;
1631 if (low_band_component_type_param != -1)
1632 priv->conf.phy.low_band_component_type =
1633 low_band_component_type_param;
1634 if (high_band_component_param != -1)
1635 priv->conf.phy.high_band_component = high_band_component_param;
1636 if (high_band_component_type_param != -1)
1637 priv->conf.phy.high_band_component_type =
1638 high_band_component_type_param;
1639 if (pwr_limit_reference_11_abg_param != -1)
1640 priv->conf.phy.pwr_limit_reference_11_abg =
1641 pwr_limit_reference_11_abg_param;
1642 if (n_antennas_2_param != -1)
1643 priv->conf.phy.number_of_assembled_ant2_4 = n_antennas_2_param;
1644 if (n_antennas_5_param != -1)
1645 priv->conf.phy.number_of_assembled_ant5 = n_antennas_5_param;
1646 if (dc2dc_param != -1)
1647 priv->conf.phy.external_pa_dc2dc = dc2dc_param;
1649 if (ht_mode_param) {
1650 if (!strcmp(ht_mode_param, "default"))
1651 priv->conf.ht.mode = HT_MODE_DEFAULT;
1652 else if (!strcmp(ht_mode_param, "wide"))
1653 priv->conf.ht.mode = HT_MODE_WIDE;
1654 else if (!strcmp(ht_mode_param, "siso20"))
1655 priv->conf.ht.mode = HT_MODE_SISO20;
1657 wl1271_error("invalid ht_mode '%s'", ht_mode_param);
1662 if (priv->conf.ht.mode == HT_MODE_DEFAULT) {
1664 * Only support mimo with multiple antennas. Fall back to
1667 if (wl18xx_is_mimo_supported(wl))
1668 wlcore_set_ht_cap(wl, IEEE80211_BAND_2GHZ,
1669 &wl18xx_mimo_ht_cap_2ghz);
1671 wlcore_set_ht_cap(wl, IEEE80211_BAND_2GHZ,
1672 &wl18xx_siso40_ht_cap_2ghz);
1674 /* 5Ghz is always wide */
1675 wlcore_set_ht_cap(wl, IEEE80211_BAND_5GHZ,
1676 &wl18xx_siso40_ht_cap_5ghz);
1677 } else if (priv->conf.ht.mode == HT_MODE_WIDE) {
1678 wlcore_set_ht_cap(wl, IEEE80211_BAND_2GHZ,
1679 &wl18xx_siso40_ht_cap_2ghz);
1680 wlcore_set_ht_cap(wl, IEEE80211_BAND_5GHZ,
1681 &wl18xx_siso40_ht_cap_5ghz);
1682 } else if (priv->conf.ht.mode == HT_MODE_SISO20) {
1683 wlcore_set_ht_cap(wl, IEEE80211_BAND_2GHZ,
1684 &wl18xx_siso20_ht_cap);
1685 wlcore_set_ht_cap(wl, IEEE80211_BAND_5GHZ,
1686 &wl18xx_siso20_ht_cap);
1689 if (!checksum_param) {
1690 wl18xx_ops.set_rx_csum = NULL;
1691 wl18xx_ops.init_vif = NULL;
1694 /* Enable 11a Band only if we have 5G antennas */
1695 wl->enable_11a = (priv->conf.phy.number_of_assembled_ant5 != 0);
1700 static int wl18xx_probe(struct platform_device *pdev)
1703 struct ieee80211_hw *hw;
1706 hw = wlcore_alloc_hw(sizeof(struct wl18xx_priv),
1707 WL18XX_AGGR_BUFFER_SIZE,
1708 sizeof(struct wl18xx_event_mailbox));
1710 wl1271_error("can't allocate hw");
1716 wl->ops = &wl18xx_ops;
1717 wl->ptable = wl18xx_ptable;
1718 ret = wlcore_probe(wl, pdev);
1730 static const struct platform_device_id wl18xx_id_table[] = {
1732 { } /* Terminating Entry */
1734 MODULE_DEVICE_TABLE(platform, wl18xx_id_table);
1736 static struct platform_driver wl18xx_driver = {
1737 .probe = wl18xx_probe,
1738 .remove = wlcore_remove,
1739 .id_table = wl18xx_id_table,
1741 .name = "wl18xx_driver",
1742 .owner = THIS_MODULE,
1746 module_platform_driver(wl18xx_driver);
1747 module_param_named(ht_mode, ht_mode_param, charp, S_IRUSR);
1748 MODULE_PARM_DESC(ht_mode, "Force HT mode: wide or siso20");
1750 module_param_named(board_type, board_type_param, charp, S_IRUSR);
1751 MODULE_PARM_DESC(board_type, "Board type: fpga, hdk (default), evb, com8 or "
1754 module_param_named(checksum, checksum_param, bool, S_IRUSR);
1755 MODULE_PARM_DESC(checksum, "Enable TCP checksum: boolean (defaults to false)");
1757 module_param_named(dc2dc, dc2dc_param, int, S_IRUSR);
1758 MODULE_PARM_DESC(dc2dc, "External DC2DC: u8 (defaults to 0)");
1760 module_param_named(n_antennas_2, n_antennas_2_param, int, S_IRUSR);
1761 MODULE_PARM_DESC(n_antennas_2,
1762 "Number of installed 2.4GHz antennas: 1 (default) or 2");
1764 module_param_named(n_antennas_5, n_antennas_5_param, int, S_IRUSR);
1765 MODULE_PARM_DESC(n_antennas_5,
1766 "Number of installed 5GHz antennas: 1 (default) or 2");
1768 module_param_named(low_band_component, low_band_component_param, int,
1770 MODULE_PARM_DESC(low_band_component, "Low band component: u8 "
1771 "(default is 0x01)");
1773 module_param_named(low_band_component_type, low_band_component_type_param,
1775 MODULE_PARM_DESC(low_band_component_type, "Low band component type: u8 "
1776 "(default is 0x05 or 0x06 depending on the board_type)");
1778 module_param_named(high_band_component, high_band_component_param, int,
1780 MODULE_PARM_DESC(high_band_component, "High band component: u8, "
1781 "(default is 0x01)");
1783 module_param_named(high_band_component_type, high_band_component_type_param,
1785 MODULE_PARM_DESC(high_band_component_type, "High band component type: u8 "
1786 "(default is 0x09)");
1788 module_param_named(pwr_limit_reference_11_abg,
1789 pwr_limit_reference_11_abg_param, int, S_IRUSR);
1790 MODULE_PARM_DESC(pwr_limit_reference_11_abg, "Power limit reference: u8 "
1791 "(default is 0xc8)");
1793 module_param_named(num_rx_desc,
1794 num_rx_desc_param, int, S_IRUSR);
1795 MODULE_PARM_DESC(num_rx_desc_param,
1796 "Number of Rx descriptors: u8 (default is 32)");
1798 MODULE_LICENSE("GPL v2");
1799 MODULE_AUTHOR("Luciano Coelho <coelho@ti.com>");
1800 MODULE_FIRMWARE(WL18XX_FW_NAME);