diff options
Diffstat (limited to 'drivers/net/wireless/zydas/zd1211rw')
-rw-r--r-- | drivers/net/wireless/zydas/zd1211rw/Kconfig | 19 | ||||
-rw-r--r-- | drivers/net/wireless/zydas/zd1211rw/Makefile | 9 | ||||
-rw-r--r-- | drivers/net/wireless/zydas/zd1211rw/zd_chip.c | 1560 | ||||
-rw-r--r-- | drivers/net/wireless/zydas/zd1211rw/zd_chip.h | 983 | ||||
-rw-r--r-- | drivers/net/wireless/zydas/zd1211rw/zd_def.h | 69 | ||||
-rw-r--r-- | drivers/net/wireless/zydas/zd1211rw/zd_mac.c | 1550 | ||||
-rw-r--r-- | drivers/net/wireless/zydas/zd1211rw/zd_mac.h | 327 | ||||
-rw-r--r-- | drivers/net/wireless/zydas/zd1211rw/zd_rf.c | 181 | ||||
-rw-r--r-- | drivers/net/wireless/zydas/zd1211rw/zd_rf.h | 110 | ||||
-rw-r--r-- | drivers/net/wireless/zydas/zd1211rw/zd_rf_al2230.c | 443 | ||||
-rw-r--r-- | drivers/net/wireless/zydas/zd1211rw/zd_rf_al7230b.c | 494 | ||||
-rw-r--r-- | drivers/net/wireless/zydas/zd1211rw/zd_rf_rf2959.c | 281 | ||||
-rw-r--r-- | drivers/net/wireless/zydas/zd1211rw/zd_rf_uw2453.c | 539 | ||||
-rw-r--r-- | drivers/net/wireless/zydas/zd1211rw/zd_usb.c | 2060 | ||||
-rw-r--r-- | drivers/net/wireless/zydas/zd1211rw/zd_usb.h | 292 |
15 files changed, 8917 insertions, 0 deletions
diff --git a/drivers/net/wireless/zydas/zd1211rw/Kconfig b/drivers/net/wireless/zydas/zd1211rw/Kconfig new file mode 100644 index 000000000000..95920581860a --- /dev/null +++ b/drivers/net/wireless/zydas/zd1211rw/Kconfig | |||
@@ -0,0 +1,19 @@ | |||
1 | config ZD1211RW | ||
2 | tristate "ZyDAS ZD1211/ZD1211B USB-wireless support" | ||
3 | depends on USB && MAC80211 | ||
4 | select FW_LOADER | ||
5 | ---help--- | ||
6 | This is a driver for the ZyDAS ZD1211/ZD1211B wireless | ||
7 | chip, present in many USB-wireless adapters. | ||
8 | |||
9 | Device firmware is required alongside this driver. You can download | ||
10 | the firmware distribution from http://sf.net/projects/zd1211/files/ | ||
11 | |||
12 | config ZD1211RW_DEBUG | ||
13 | bool "ZyDAS ZD1211 debugging" | ||
14 | depends on ZD1211RW | ||
15 | ---help--- | ||
16 | ZD1211 debugging messages. Choosing Y will result in additional debug | ||
17 | messages being saved to your kernel logs, which may help debug any | ||
18 | problems. | ||
19 | |||
diff --git a/drivers/net/wireless/zydas/zd1211rw/Makefile b/drivers/net/wireless/zydas/zd1211rw/Makefile new file mode 100644 index 000000000000..5728a918e508 --- /dev/null +++ b/drivers/net/wireless/zydas/zd1211rw/Makefile | |||
@@ -0,0 +1,9 @@ | |||
1 | obj-$(CONFIG_ZD1211RW) += zd1211rw.o | ||
2 | |||
3 | zd1211rw-objs := zd_chip.o zd_mac.o \ | ||
4 | zd_rf_al2230.o zd_rf_rf2959.o \ | ||
5 | zd_rf_al7230b.o zd_rf_uw2453.o \ | ||
6 | zd_rf.o zd_usb.o | ||
7 | |||
8 | ccflags-$(CONFIG_ZD1211RW_DEBUG) := -DDEBUG | ||
9 | |||
diff --git a/drivers/net/wireless/zydas/zd1211rw/zd_chip.c b/drivers/net/wireless/zydas/zd1211rw/zd_chip.c new file mode 100644 index 000000000000..07b94eda9604 --- /dev/null +++ b/drivers/net/wireless/zydas/zd1211rw/zd_chip.c | |||
@@ -0,0 +1,1560 @@ | |||
1 | /* ZD1211 USB-WLAN driver for Linux | ||
2 | * | ||
3 | * Copyright (C) 2005-2007 Ulrich Kunitz <kune@deine-taler.de> | ||
4 | * Copyright (C) 2006-2007 Daniel Drake <dsd@gentoo.org> | ||
5 | * | ||
6 | * This program is free software; you can redistribute it and/or modify | ||
7 | * it under the terms of the GNU General Public License as published by | ||
8 | * the Free Software Foundation; either version 2 of the License, or | ||
9 | * (at your option) any later version. | ||
10 | * | ||
11 | * This program is distributed in the hope that it will be useful, | ||
12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
14 | * GNU General Public License for more details. | ||
15 | * | ||
16 | * You should have received a copy of the GNU General Public License | ||
17 | * along with this program; if not, see <http://www.gnu.org/licenses/>. | ||
18 | */ | ||
19 | |||
20 | /* This file implements all the hardware specific functions for the ZD1211 | ||
21 | * and ZD1211B chips. Support for the ZD1211B was possible after Timothy | ||
22 | * Legge sent me a ZD1211B device. Thank you Tim. -- Uli | ||
23 | */ | ||
24 | |||
25 | #include <linux/kernel.h> | ||
26 | #include <linux/errno.h> | ||
27 | #include <linux/slab.h> | ||
28 | |||
29 | #include "zd_def.h" | ||
30 | #include "zd_chip.h" | ||
31 | #include "zd_mac.h" | ||
32 | #include "zd_rf.h" | ||
33 | |||
34 | void zd_chip_init(struct zd_chip *chip, | ||
35 | struct ieee80211_hw *hw, | ||
36 | struct usb_interface *intf) | ||
37 | { | ||
38 | memset(chip, 0, sizeof(*chip)); | ||
39 | mutex_init(&chip->mutex); | ||
40 | zd_usb_init(&chip->usb, hw, intf); | ||
41 | zd_rf_init(&chip->rf); | ||
42 | } | ||
43 | |||
44 | void zd_chip_clear(struct zd_chip *chip) | ||
45 | { | ||
46 | ZD_ASSERT(!mutex_is_locked(&chip->mutex)); | ||
47 | zd_usb_clear(&chip->usb); | ||
48 | zd_rf_clear(&chip->rf); | ||
49 | mutex_destroy(&chip->mutex); | ||
50 | ZD_MEMCLEAR(chip, sizeof(*chip)); | ||
51 | } | ||
52 | |||
53 | static int scnprint_mac_oui(struct zd_chip *chip, char *buffer, size_t size) | ||
54 | { | ||
55 | u8 *addr = zd_mac_get_perm_addr(zd_chip_to_mac(chip)); | ||
56 | return scnprintf(buffer, size, "%02x-%02x-%02x", | ||
57 | addr[0], addr[1], addr[2]); | ||
58 | } | ||
59 | |||
60 | /* Prints an identifier line, which will support debugging. */ | ||
61 | static int scnprint_id(struct zd_chip *chip, char *buffer, size_t size) | ||
62 | { | ||
63 | int i = 0; | ||
64 | |||
65 | i = scnprintf(buffer, size, "zd1211%s chip ", | ||
66 | zd_chip_is_zd1211b(chip) ? "b" : ""); | ||
67 | i += zd_usb_scnprint_id(&chip->usb, buffer+i, size-i); | ||
68 | i += scnprintf(buffer+i, size-i, " "); | ||
69 | i += scnprint_mac_oui(chip, buffer+i, size-i); | ||
70 | i += scnprintf(buffer+i, size-i, " "); | ||
71 | i += zd_rf_scnprint_id(&chip->rf, buffer+i, size-i); | ||
72 | i += scnprintf(buffer+i, size-i, " pa%1x %c%c%c%c%c", chip->pa_type, | ||
73 | chip->patch_cck_gain ? 'g' : '-', | ||
74 | chip->patch_cr157 ? '7' : '-', | ||
75 | chip->patch_6m_band_edge ? '6' : '-', | ||
76 | chip->new_phy_layout ? 'N' : '-', | ||
77 | chip->al2230s_bit ? 'S' : '-'); | ||
78 | return i; | ||
79 | } | ||
80 | |||
81 | static void print_id(struct zd_chip *chip) | ||
82 | { | ||
83 | char buffer[80]; | ||
84 | |||
85 | scnprint_id(chip, buffer, sizeof(buffer)); | ||
86 | buffer[sizeof(buffer)-1] = 0; | ||
87 | dev_info(zd_chip_dev(chip), "%s\n", buffer); | ||
88 | } | ||
89 | |||
90 | static zd_addr_t inc_addr(zd_addr_t addr) | ||
91 | { | ||
92 | u16 a = (u16)addr; | ||
93 | /* Control registers use byte addressing, but everything else uses word | ||
94 | * addressing. */ | ||
95 | if ((a & 0xf000) == CR_START) | ||
96 | a += 2; | ||
97 | else | ||
98 | a += 1; | ||
99 | return (zd_addr_t)a; | ||
100 | } | ||
101 | |||
102 | /* Read a variable number of 32-bit values. Parameter count is not allowed to | ||
103 | * exceed USB_MAX_IOREAD32_COUNT. | ||
104 | */ | ||
105 | int zd_ioread32v_locked(struct zd_chip *chip, u32 *values, const zd_addr_t *addr, | ||
106 | unsigned int count) | ||
107 | { | ||
108 | int r; | ||
109 | int i; | ||
110 | zd_addr_t a16[USB_MAX_IOREAD32_COUNT * 2]; | ||
111 | u16 v16[USB_MAX_IOREAD32_COUNT * 2]; | ||
112 | unsigned int count16; | ||
113 | |||
114 | if (count > USB_MAX_IOREAD32_COUNT) | ||
115 | return -EINVAL; | ||
116 | |||
117 | /* Use stack for values and addresses. */ | ||
118 | count16 = 2 * count; | ||
119 | BUG_ON(count16 * sizeof(zd_addr_t) > sizeof(a16)); | ||
120 | BUG_ON(count16 * sizeof(u16) > sizeof(v16)); | ||
121 | |||
122 | for (i = 0; i < count; i++) { | ||
123 | int j = 2*i; | ||
124 | /* We read the high word always first. */ | ||
125 | a16[j] = inc_addr(addr[i]); | ||
126 | a16[j+1] = addr[i]; | ||
127 | } | ||
128 | |||
129 | r = zd_ioread16v_locked(chip, v16, a16, count16); | ||
130 | if (r) { | ||
131 | dev_dbg_f(zd_chip_dev(chip), | ||
132 | "error: %s. Error number %d\n", __func__, r); | ||
133 | return r; | ||
134 | } | ||
135 | |||
136 | for (i = 0; i < count; i++) { | ||
137 | int j = 2*i; | ||
138 | values[i] = (v16[j] << 16) | v16[j+1]; | ||
139 | } | ||
140 | |||
141 | return 0; | ||
142 | } | ||
143 | |||
144 | static int _zd_iowrite32v_async_locked(struct zd_chip *chip, | ||
145 | const struct zd_ioreq32 *ioreqs, | ||
146 | unsigned int count) | ||
147 | { | ||
148 | int i, j, r; | ||
149 | struct zd_ioreq16 ioreqs16[USB_MAX_IOWRITE32_COUNT * 2]; | ||
150 | unsigned int count16; | ||
151 | |||
152 | /* Use stack for values and addresses. */ | ||
153 | |||
154 | ZD_ASSERT(mutex_is_locked(&chip->mutex)); | ||
155 | |||
156 | if (count == 0) | ||
157 | return 0; | ||
158 | if (count > USB_MAX_IOWRITE32_COUNT) | ||
159 | return -EINVAL; | ||
160 | |||
161 | count16 = 2 * count; | ||
162 | BUG_ON(count16 * sizeof(struct zd_ioreq16) > sizeof(ioreqs16)); | ||
163 | |||
164 | for (i = 0; i < count; i++) { | ||
165 | j = 2*i; | ||
166 | /* We write the high word always first. */ | ||
167 | ioreqs16[j].value = ioreqs[i].value >> 16; | ||
168 | ioreqs16[j].addr = inc_addr(ioreqs[i].addr); | ||
169 | ioreqs16[j+1].value = ioreqs[i].value; | ||
170 | ioreqs16[j+1].addr = ioreqs[i].addr; | ||
171 | } | ||
172 | |||
173 | r = zd_usb_iowrite16v_async(&chip->usb, ioreqs16, count16); | ||
174 | #ifdef DEBUG | ||
175 | if (r) { | ||
176 | dev_dbg_f(zd_chip_dev(chip), | ||
177 | "error %d in zd_usb_write16v\n", r); | ||
178 | } | ||
179 | #endif /* DEBUG */ | ||
180 | return r; | ||
181 | } | ||
182 | |||
183 | int _zd_iowrite32v_locked(struct zd_chip *chip, const struct zd_ioreq32 *ioreqs, | ||
184 | unsigned int count) | ||
185 | { | ||
186 | int r; | ||
187 | |||
188 | zd_usb_iowrite16v_async_start(&chip->usb); | ||
189 | r = _zd_iowrite32v_async_locked(chip, ioreqs, count); | ||
190 | if (r) { | ||
191 | zd_usb_iowrite16v_async_end(&chip->usb, 0); | ||
192 | return r; | ||
193 | } | ||
194 | return zd_usb_iowrite16v_async_end(&chip->usb, 50 /* ms */); | ||
195 | } | ||
196 | |||
197 | int zd_iowrite16a_locked(struct zd_chip *chip, | ||
198 | const struct zd_ioreq16 *ioreqs, unsigned int count) | ||
199 | { | ||
200 | int r; | ||
201 | unsigned int i, j, t, max; | ||
202 | |||
203 | ZD_ASSERT(mutex_is_locked(&chip->mutex)); | ||
204 | zd_usb_iowrite16v_async_start(&chip->usb); | ||
205 | |||
206 | for (i = 0; i < count; i += j + t) { | ||
207 | t = 0; | ||
208 | max = count-i; | ||
209 | if (max > USB_MAX_IOWRITE16_COUNT) | ||
210 | max = USB_MAX_IOWRITE16_COUNT; | ||
211 | for (j = 0; j < max; j++) { | ||
212 | if (!ioreqs[i+j].addr) { | ||
213 | t = 1; | ||
214 | break; | ||
215 | } | ||
216 | } | ||
217 | |||
218 | r = zd_usb_iowrite16v_async(&chip->usb, &ioreqs[i], j); | ||
219 | if (r) { | ||
220 | zd_usb_iowrite16v_async_end(&chip->usb, 0); | ||
221 | dev_dbg_f(zd_chip_dev(chip), | ||
222 | "error zd_usb_iowrite16v. Error number %d\n", | ||
223 | r); | ||
224 | return r; | ||
225 | } | ||
226 | } | ||
227 | |||
228 | return zd_usb_iowrite16v_async_end(&chip->usb, 50 /* ms */); | ||
229 | } | ||
230 | |||
231 | /* Writes a variable number of 32 bit registers. The functions will split | ||
232 | * that in several USB requests. A split can be forced by inserting an IO | ||
233 | * request with an zero address field. | ||
234 | */ | ||
235 | int zd_iowrite32a_locked(struct zd_chip *chip, | ||
236 | const struct zd_ioreq32 *ioreqs, unsigned int count) | ||
237 | { | ||
238 | int r; | ||
239 | unsigned int i, j, t, max; | ||
240 | |||
241 | zd_usb_iowrite16v_async_start(&chip->usb); | ||
242 | |||
243 | for (i = 0; i < count; i += j + t) { | ||
244 | t = 0; | ||
245 | max = count-i; | ||
246 | if (max > USB_MAX_IOWRITE32_COUNT) | ||
247 | max = USB_MAX_IOWRITE32_COUNT; | ||
248 | for (j = 0; j < max; j++) { | ||
249 | if (!ioreqs[i+j].addr) { | ||
250 | t = 1; | ||
251 | break; | ||
252 | } | ||
253 | } | ||
254 | |||
255 | r = _zd_iowrite32v_async_locked(chip, &ioreqs[i], j); | ||
256 | if (r) { | ||
257 | zd_usb_iowrite16v_async_end(&chip->usb, 0); | ||
258 | dev_dbg_f(zd_chip_dev(chip), | ||
259 | "error _%s. Error number %d\n", __func__, | ||
260 | r); | ||
261 | return r; | ||
262 | } | ||
263 | } | ||
264 | |||
265 | return zd_usb_iowrite16v_async_end(&chip->usb, 50 /* ms */); | ||
266 | } | ||
267 | |||
268 | int zd_ioread16(struct zd_chip *chip, zd_addr_t addr, u16 *value) | ||
269 | { | ||
270 | int r; | ||
271 | |||
272 | mutex_lock(&chip->mutex); | ||
273 | r = zd_ioread16_locked(chip, value, addr); | ||
274 | mutex_unlock(&chip->mutex); | ||
275 | return r; | ||
276 | } | ||
277 | |||
278 | int zd_ioread32(struct zd_chip *chip, zd_addr_t addr, u32 *value) | ||
279 | { | ||
280 | int r; | ||
281 | |||
282 | mutex_lock(&chip->mutex); | ||
283 | r = zd_ioread32_locked(chip, value, addr); | ||
284 | mutex_unlock(&chip->mutex); | ||
285 | return r; | ||
286 | } | ||
287 | |||
288 | int zd_iowrite16(struct zd_chip *chip, zd_addr_t addr, u16 value) | ||
289 | { | ||
290 | int r; | ||
291 | |||
292 | mutex_lock(&chip->mutex); | ||
293 | r = zd_iowrite16_locked(chip, value, addr); | ||
294 | mutex_unlock(&chip->mutex); | ||
295 | return r; | ||
296 | } | ||
297 | |||
298 | int zd_iowrite32(struct zd_chip *chip, zd_addr_t addr, u32 value) | ||
299 | { | ||
300 | int r; | ||
301 | |||
302 | mutex_lock(&chip->mutex); | ||
303 | r = zd_iowrite32_locked(chip, value, addr); | ||
304 | mutex_unlock(&chip->mutex); | ||
305 | return r; | ||
306 | } | ||
307 | |||
308 | int zd_ioread32v(struct zd_chip *chip, const zd_addr_t *addresses, | ||
309 | u32 *values, unsigned int count) | ||
310 | { | ||
311 | int r; | ||
312 | |||
313 | mutex_lock(&chip->mutex); | ||
314 | r = zd_ioread32v_locked(chip, values, addresses, count); | ||
315 | mutex_unlock(&chip->mutex); | ||
316 | return r; | ||
317 | } | ||
318 | |||
319 | int zd_iowrite32a(struct zd_chip *chip, const struct zd_ioreq32 *ioreqs, | ||
320 | unsigned int count) | ||
321 | { | ||
322 | int r; | ||
323 | |||
324 | mutex_lock(&chip->mutex); | ||
325 | r = zd_iowrite32a_locked(chip, ioreqs, count); | ||
326 | mutex_unlock(&chip->mutex); | ||
327 | return r; | ||
328 | } | ||
329 | |||
330 | static int read_pod(struct zd_chip *chip, u8 *rf_type) | ||
331 | { | ||
332 | int r; | ||
333 | u32 value; | ||
334 | |||
335 | ZD_ASSERT(mutex_is_locked(&chip->mutex)); | ||
336 | r = zd_ioread32_locked(chip, &value, E2P_POD); | ||
337 | if (r) | ||
338 | goto error; | ||
339 | dev_dbg_f(zd_chip_dev(chip), "E2P_POD %#010x\n", value); | ||
340 | |||
341 | /* FIXME: AL2230 handling (Bit 7 in POD) */ | ||
342 | *rf_type = value & 0x0f; | ||
343 | chip->pa_type = (value >> 16) & 0x0f; | ||
344 | chip->patch_cck_gain = (value >> 8) & 0x1; | ||
345 | chip->patch_cr157 = (value >> 13) & 0x1; | ||
346 | chip->patch_6m_band_edge = (value >> 21) & 0x1; | ||
347 | chip->new_phy_layout = (value >> 31) & 0x1; | ||
348 | chip->al2230s_bit = (value >> 7) & 0x1; | ||
349 | chip->link_led = ((value >> 4) & 1) ? LED1 : LED2; | ||
350 | chip->supports_tx_led = 1; | ||
351 | if (value & (1 << 24)) { /* LED scenario */ | ||
352 | if (value & (1 << 29)) | ||
353 | chip->supports_tx_led = 0; | ||
354 | } | ||
355 | |||
356 | dev_dbg_f(zd_chip_dev(chip), | ||
357 | "RF %s %#01x PA type %#01x patch CCK %d patch CR157 %d " | ||
358 | "patch 6M %d new PHY %d link LED%d tx led %d\n", | ||
359 | zd_rf_name(*rf_type), *rf_type, | ||
360 | chip->pa_type, chip->patch_cck_gain, | ||
361 | chip->patch_cr157, chip->patch_6m_band_edge, | ||
362 | chip->new_phy_layout, | ||
363 | chip->link_led == LED1 ? 1 : 2, | ||
364 | chip->supports_tx_led); | ||
365 | return 0; | ||
366 | error: | ||
367 | *rf_type = 0; | ||
368 | chip->pa_type = 0; | ||
369 | chip->patch_cck_gain = 0; | ||
370 | chip->patch_cr157 = 0; | ||
371 | chip->patch_6m_band_edge = 0; | ||
372 | chip->new_phy_layout = 0; | ||
373 | return r; | ||
374 | } | ||
375 | |||
376 | static int zd_write_mac_addr_common(struct zd_chip *chip, const u8 *mac_addr, | ||
377 | const struct zd_ioreq32 *in_reqs, | ||
378 | const char *type) | ||
379 | { | ||
380 | int r; | ||
381 | struct zd_ioreq32 reqs[2] = {in_reqs[0], in_reqs[1]}; | ||
382 | |||
383 | if (mac_addr) { | ||
384 | reqs[0].value = (mac_addr[3] << 24) | ||
385 | | (mac_addr[2] << 16) | ||
386 | | (mac_addr[1] << 8) | ||
387 | | mac_addr[0]; | ||
388 | reqs[1].value = (mac_addr[5] << 8) | ||
389 | | mac_addr[4]; | ||
390 | dev_dbg_f(zd_chip_dev(chip), "%s addr %pM\n", type, mac_addr); | ||
391 | } else { | ||
392 | dev_dbg_f(zd_chip_dev(chip), "set NULL %s\n", type); | ||
393 | } | ||
394 | |||
395 | mutex_lock(&chip->mutex); | ||
396 | r = zd_iowrite32a_locked(chip, reqs, ARRAY_SIZE(reqs)); | ||
397 | mutex_unlock(&chip->mutex); | ||
398 | return r; | ||
399 | } | ||
400 | |||
401 | /* MAC address: if custom mac addresses are to be used CR_MAC_ADDR_P1 and | ||
402 | * CR_MAC_ADDR_P2 must be overwritten | ||
403 | */ | ||
404 | int zd_write_mac_addr(struct zd_chip *chip, const u8 *mac_addr) | ||
405 | { | ||
406 | static const struct zd_ioreq32 reqs[2] = { | ||
407 | [0] = { .addr = CR_MAC_ADDR_P1 }, | ||
408 | [1] = { .addr = CR_MAC_ADDR_P2 }, | ||
409 | }; | ||
410 | |||
411 | return zd_write_mac_addr_common(chip, mac_addr, reqs, "mac"); | ||
412 | } | ||
413 | |||
414 | int zd_write_bssid(struct zd_chip *chip, const u8 *bssid) | ||
415 | { | ||
416 | static const struct zd_ioreq32 reqs[2] = { | ||
417 | [0] = { .addr = CR_BSSID_P1 }, | ||
418 | [1] = { .addr = CR_BSSID_P2 }, | ||
419 | }; | ||
420 | |||
421 | return zd_write_mac_addr_common(chip, bssid, reqs, "bssid"); | ||
422 | } | ||
423 | |||
424 | int zd_read_regdomain(struct zd_chip *chip, u8 *regdomain) | ||
425 | { | ||
426 | int r; | ||
427 | u32 value; | ||
428 | |||
429 | mutex_lock(&chip->mutex); | ||
430 | r = zd_ioread32_locked(chip, &value, E2P_SUBID); | ||
431 | mutex_unlock(&chip->mutex); | ||
432 | if (r) | ||
433 | return r; | ||
434 | |||
435 | *regdomain = value >> 16; | ||
436 | dev_dbg_f(zd_chip_dev(chip), "regdomain: %#04x\n", *regdomain); | ||
437 | |||
438 | return 0; | ||
439 | } | ||
440 | |||
441 | static int read_values(struct zd_chip *chip, u8 *values, size_t count, | ||
442 | zd_addr_t e2p_addr, u32 guard) | ||
443 | { | ||
444 | int r; | ||
445 | int i; | ||
446 | u32 v; | ||
447 | |||
448 | ZD_ASSERT(mutex_is_locked(&chip->mutex)); | ||
449 | for (i = 0;;) { | ||
450 | r = zd_ioread32_locked(chip, &v, | ||
451 | (zd_addr_t)((u16)e2p_addr+i/2)); | ||
452 | if (r) | ||
453 | return r; | ||
454 | v -= guard; | ||
455 | if (i+4 < count) { | ||
456 | values[i++] = v; | ||
457 | values[i++] = v >> 8; | ||
458 | values[i++] = v >> 16; | ||
459 | values[i++] = v >> 24; | ||
460 | continue; | ||
461 | } | ||
462 | for (;i < count; i++) | ||
463 | values[i] = v >> (8*(i%3)); | ||
464 | return 0; | ||
465 | } | ||
466 | } | ||
467 | |||
468 | static int read_pwr_cal_values(struct zd_chip *chip) | ||
469 | { | ||
470 | return read_values(chip, chip->pwr_cal_values, | ||
471 | E2P_CHANNEL_COUNT, E2P_PWR_CAL_VALUE1, | ||
472 | 0); | ||
473 | } | ||
474 | |||
475 | static int read_pwr_int_values(struct zd_chip *chip) | ||
476 | { | ||
477 | return read_values(chip, chip->pwr_int_values, | ||
478 | E2P_CHANNEL_COUNT, E2P_PWR_INT_VALUE1, | ||
479 | E2P_PWR_INT_GUARD); | ||
480 | } | ||
481 | |||
482 | static int read_ofdm_cal_values(struct zd_chip *chip) | ||
483 | { | ||
484 | int r; | ||
485 | int i; | ||
486 | static const zd_addr_t addresses[] = { | ||
487 | E2P_36M_CAL_VALUE1, | ||
488 | E2P_48M_CAL_VALUE1, | ||
489 | E2P_54M_CAL_VALUE1, | ||
490 | }; | ||
491 | |||
492 | for (i = 0; i < 3; i++) { | ||
493 | r = read_values(chip, chip->ofdm_cal_values[i], | ||
494 | E2P_CHANNEL_COUNT, addresses[i], 0); | ||
495 | if (r) | ||
496 | return r; | ||
497 | } | ||
498 | return 0; | ||
499 | } | ||
500 | |||
501 | static int read_cal_int_tables(struct zd_chip *chip) | ||
502 | { | ||
503 | int r; | ||
504 | |||
505 | r = read_pwr_cal_values(chip); | ||
506 | if (r) | ||
507 | return r; | ||
508 | r = read_pwr_int_values(chip); | ||
509 | if (r) | ||
510 | return r; | ||
511 | r = read_ofdm_cal_values(chip); | ||
512 | if (r) | ||
513 | return r; | ||
514 | return 0; | ||
515 | } | ||
516 | |||
517 | /* phy means physical registers */ | ||
518 | int zd_chip_lock_phy_regs(struct zd_chip *chip) | ||
519 | { | ||
520 | int r; | ||
521 | u32 tmp; | ||
522 | |||
523 | ZD_ASSERT(mutex_is_locked(&chip->mutex)); | ||
524 | r = zd_ioread32_locked(chip, &tmp, CR_REG1); | ||
525 | if (r) { | ||
526 | dev_err(zd_chip_dev(chip), "error ioread32(CR_REG1): %d\n", r); | ||
527 | return r; | ||
528 | } | ||
529 | |||
530 | tmp &= ~UNLOCK_PHY_REGS; | ||
531 | |||
532 | r = zd_iowrite32_locked(chip, tmp, CR_REG1); | ||
533 | if (r) | ||
534 | dev_err(zd_chip_dev(chip), "error iowrite32(CR_REG1): %d\n", r); | ||
535 | return r; | ||
536 | } | ||
537 | |||
538 | int zd_chip_unlock_phy_regs(struct zd_chip *chip) | ||
539 | { | ||
540 | int r; | ||
541 | u32 tmp; | ||
542 | |||
543 | ZD_ASSERT(mutex_is_locked(&chip->mutex)); | ||
544 | r = zd_ioread32_locked(chip, &tmp, CR_REG1); | ||
545 | if (r) { | ||
546 | dev_err(zd_chip_dev(chip), | ||
547 | "error ioread32(CR_REG1): %d\n", r); | ||
548 | return r; | ||
549 | } | ||
550 | |||
551 | tmp |= UNLOCK_PHY_REGS; | ||
552 | |||
553 | r = zd_iowrite32_locked(chip, tmp, CR_REG1); | ||
554 | if (r) | ||
555 | dev_err(zd_chip_dev(chip), "error iowrite32(CR_REG1): %d\n", r); | ||
556 | return r; | ||
557 | } | ||
558 | |||
559 | /* ZD_CR157 can be optionally patched by the EEPROM for original ZD1211 */ | ||
560 | static int patch_cr157(struct zd_chip *chip) | ||
561 | { | ||
562 | int r; | ||
563 | u16 value; | ||
564 | |||
565 | if (!chip->patch_cr157) | ||
566 | return 0; | ||
567 | |||
568 | r = zd_ioread16_locked(chip, &value, E2P_PHY_REG); | ||
569 | if (r) | ||
570 | return r; | ||
571 | |||
572 | dev_dbg_f(zd_chip_dev(chip), "patching value %x\n", value >> 8); | ||
573 | return zd_iowrite32_locked(chip, value >> 8, ZD_CR157); | ||
574 | } | ||
575 | |||
576 | /* | ||
577 | * 6M band edge can be optionally overwritten for certain RF's | ||
578 | * Vendor driver says: for FCC regulation, enabled per HWFeature 6M band edge | ||
579 | * bit (for AL2230, AL2230S) | ||
580 | */ | ||
581 | static int patch_6m_band_edge(struct zd_chip *chip, u8 channel) | ||
582 | { | ||
583 | ZD_ASSERT(mutex_is_locked(&chip->mutex)); | ||
584 | if (!chip->patch_6m_band_edge) | ||
585 | return 0; | ||
586 | |||
587 | return zd_rf_patch_6m_band_edge(&chip->rf, channel); | ||
588 | } | ||
589 | |||
590 | /* Generic implementation of 6M band edge patching, used by most RFs via | ||
591 | * zd_rf_generic_patch_6m() */ | ||
592 | int zd_chip_generic_patch_6m_band(struct zd_chip *chip, int channel) | ||
593 | { | ||
594 | struct zd_ioreq16 ioreqs[] = { | ||
595 | { ZD_CR128, 0x14 }, { ZD_CR129, 0x12 }, { ZD_CR130, 0x10 }, | ||
596 | { ZD_CR47, 0x1e }, | ||
597 | }; | ||
598 | |||
599 | /* FIXME: Channel 11 is not the edge for all regulatory domains. */ | ||
600 | if (channel == 1 || channel == 11) | ||
601 | ioreqs[0].value = 0x12; | ||
602 | |||
603 | dev_dbg_f(zd_chip_dev(chip), "patching for channel %d\n", channel); | ||
604 | return zd_iowrite16a_locked(chip, ioreqs, ARRAY_SIZE(ioreqs)); | ||
605 | } | ||
606 | |||
607 | static int zd1211_hw_reset_phy(struct zd_chip *chip) | ||
608 | { | ||
609 | static const struct zd_ioreq16 ioreqs[] = { | ||
610 | { ZD_CR0, 0x0a }, { ZD_CR1, 0x06 }, { ZD_CR2, 0x26 }, | ||
611 | { ZD_CR3, 0x38 }, { ZD_CR4, 0x80 }, { ZD_CR9, 0xa0 }, | ||
612 | { ZD_CR10, 0x81 }, { ZD_CR11, 0x00 }, { ZD_CR12, 0x7f }, | ||
613 | { ZD_CR13, 0x8c }, { ZD_CR14, 0x80 }, { ZD_CR15, 0x3d }, | ||
614 | { ZD_CR16, 0x20 }, { ZD_CR17, 0x1e }, { ZD_CR18, 0x0a }, | ||
615 | { ZD_CR19, 0x48 }, { ZD_CR20, 0x0c }, { ZD_CR21, 0x0c }, | ||
616 | { ZD_CR22, 0x23 }, { ZD_CR23, 0x90 }, { ZD_CR24, 0x14 }, | ||
617 | { ZD_CR25, 0x40 }, { ZD_CR26, 0x10 }, { ZD_CR27, 0x19 }, | ||
618 | { ZD_CR28, 0x7f }, { ZD_CR29, 0x80 }, { ZD_CR30, 0x4b }, | ||
619 | { ZD_CR31, 0x60 }, { ZD_CR32, 0x43 }, { ZD_CR33, 0x08 }, | ||
620 | { ZD_CR34, 0x06 }, { ZD_CR35, 0x0a }, { ZD_CR36, 0x00 }, | ||
621 | { ZD_CR37, 0x00 }, { ZD_CR38, 0x38 }, { ZD_CR39, 0x0c }, | ||
622 | { ZD_CR40, 0x84 }, { ZD_CR41, 0x2a }, { ZD_CR42, 0x80 }, | ||
623 | { ZD_CR43, 0x10 }, { ZD_CR44, 0x12 }, { ZD_CR46, 0xff }, | ||
624 | { ZD_CR47, 0x1E }, { ZD_CR48, 0x26 }, { ZD_CR49, 0x5b }, | ||
625 | { ZD_CR64, 0xd0 }, { ZD_CR65, 0x04 }, { ZD_CR66, 0x58 }, | ||
626 | { ZD_CR67, 0xc9 }, { ZD_CR68, 0x88 }, { ZD_CR69, 0x41 }, | ||
627 | { ZD_CR70, 0x23 }, { ZD_CR71, 0x10 }, { ZD_CR72, 0xff }, | ||
628 | { ZD_CR73, 0x32 }, { ZD_CR74, 0x30 }, { ZD_CR75, 0x65 }, | ||
629 | { ZD_CR76, 0x41 }, { ZD_CR77, 0x1b }, { ZD_CR78, 0x30 }, | ||
630 | { ZD_CR79, 0x68 }, { ZD_CR80, 0x64 }, { ZD_CR81, 0x64 }, | ||
631 | { ZD_CR82, 0x00 }, { ZD_CR83, 0x00 }, { ZD_CR84, 0x00 }, | ||
632 | { ZD_CR85, 0x02 }, { ZD_CR86, 0x00 }, { ZD_CR87, 0x00 }, | ||
633 | { ZD_CR88, 0xff }, { ZD_CR89, 0xfc }, { ZD_CR90, 0x00 }, | ||
634 | { ZD_CR91, 0x00 }, { ZD_CR92, 0x00 }, { ZD_CR93, 0x08 }, | ||
635 | { ZD_CR94, 0x00 }, { ZD_CR95, 0x00 }, { ZD_CR96, 0xff }, | ||
636 | { ZD_CR97, 0xe7 }, { ZD_CR98, 0x00 }, { ZD_CR99, 0x00 }, | ||
637 | { ZD_CR100, 0x00 }, { ZD_CR101, 0xae }, { ZD_CR102, 0x02 }, | ||
638 | { ZD_CR103, 0x00 }, { ZD_CR104, 0x03 }, { ZD_CR105, 0x65 }, | ||
639 | { ZD_CR106, 0x04 }, { ZD_CR107, 0x00 }, { ZD_CR108, 0x0a }, | ||
640 | { ZD_CR109, 0xaa }, { ZD_CR110, 0xaa }, { ZD_CR111, 0x25 }, | ||
641 | { ZD_CR112, 0x25 }, { ZD_CR113, 0x00 }, { ZD_CR119, 0x1e }, | ||
642 | { ZD_CR125, 0x90 }, { ZD_CR126, 0x00 }, { ZD_CR127, 0x00 }, | ||
643 | { }, | ||
644 | { ZD_CR5, 0x00 }, { ZD_CR6, 0x00 }, { ZD_CR7, 0x00 }, | ||
645 | { ZD_CR8, 0x00 }, { ZD_CR9, 0x20 }, { ZD_CR12, 0xf0 }, | ||
646 | { ZD_CR20, 0x0e }, { ZD_CR21, 0x0e }, { ZD_CR27, 0x10 }, | ||
647 | { ZD_CR44, 0x33 }, { ZD_CR47, 0x1E }, { ZD_CR83, 0x24 }, | ||
648 | { ZD_CR84, 0x04 }, { ZD_CR85, 0x00 }, { ZD_CR86, 0x0C }, | ||
649 | { ZD_CR87, 0x12 }, { ZD_CR88, 0x0C }, { ZD_CR89, 0x00 }, | ||
650 | { ZD_CR90, 0x10 }, { ZD_CR91, 0x08 }, { ZD_CR93, 0x00 }, | ||
651 | { ZD_CR94, 0x01 }, { ZD_CR95, 0x00 }, { ZD_CR96, 0x50 }, | ||
652 | { ZD_CR97, 0x37 }, { ZD_CR98, 0x35 }, { ZD_CR101, 0x13 }, | ||
653 | { ZD_CR102, 0x27 }, { ZD_CR103, 0x27 }, { ZD_CR104, 0x18 }, | ||
654 | { ZD_CR105, 0x12 }, { ZD_CR109, 0x27 }, { ZD_CR110, 0x27 }, | ||
655 | { ZD_CR111, 0x27 }, { ZD_CR112, 0x27 }, { ZD_CR113, 0x27 }, | ||
656 | { ZD_CR114, 0x27 }, { ZD_CR115, 0x26 }, { ZD_CR116, 0x24 }, | ||
657 | { ZD_CR117, 0xfc }, { ZD_CR118, 0xfa }, { ZD_CR120, 0x4f }, | ||
658 | { ZD_CR125, 0xaa }, { ZD_CR127, 0x03 }, { ZD_CR128, 0x14 }, | ||
659 | { ZD_CR129, 0x12 }, { ZD_CR130, 0x10 }, { ZD_CR131, 0x0C }, | ||
660 | { ZD_CR136, 0xdf }, { ZD_CR137, 0x40 }, { ZD_CR138, 0xa0 }, | ||
661 | { ZD_CR139, 0xb0 }, { ZD_CR140, 0x99 }, { ZD_CR141, 0x82 }, | ||
662 | { ZD_CR142, 0x54 }, { ZD_CR143, 0x1c }, { ZD_CR144, 0x6c }, | ||
663 | { ZD_CR147, 0x07 }, { ZD_CR148, 0x4c }, { ZD_CR149, 0x50 }, | ||
664 | { ZD_CR150, 0x0e }, { ZD_CR151, 0x18 }, { ZD_CR160, 0xfe }, | ||
665 | { ZD_CR161, 0xee }, { ZD_CR162, 0xaa }, { ZD_CR163, 0xfa }, | ||
666 | { ZD_CR164, 0xfa }, { ZD_CR165, 0xea }, { ZD_CR166, 0xbe }, | ||
667 | { ZD_CR167, 0xbe }, { ZD_CR168, 0x6a }, { ZD_CR169, 0xba }, | ||
668 | { ZD_CR170, 0xba }, { ZD_CR171, 0xba }, | ||
669 | /* Note: ZD_CR204 must lead the ZD_CR203 */ | ||
670 | { ZD_CR204, 0x7d }, | ||
671 | { }, | ||
672 | { ZD_CR203, 0x30 }, | ||
673 | }; | ||
674 | |||
675 | int r, t; | ||
676 | |||
677 | dev_dbg_f(zd_chip_dev(chip), "\n"); | ||
678 | |||
679 | r = zd_chip_lock_phy_regs(chip); | ||
680 | if (r) | ||
681 | goto out; | ||
682 | |||
683 | r = zd_iowrite16a_locked(chip, ioreqs, ARRAY_SIZE(ioreqs)); | ||
684 | if (r) | ||
685 | goto unlock; | ||
686 | |||
687 | r = patch_cr157(chip); | ||
688 | unlock: | ||
689 | t = zd_chip_unlock_phy_regs(chip); | ||
690 | if (t && !r) | ||
691 | r = t; | ||
692 | out: | ||
693 | return r; | ||
694 | } | ||
695 | |||
696 | static int zd1211b_hw_reset_phy(struct zd_chip *chip) | ||
697 | { | ||
698 | static const struct zd_ioreq16 ioreqs[] = { | ||
699 | { ZD_CR0, 0x14 }, { ZD_CR1, 0x06 }, { ZD_CR2, 0x26 }, | ||
700 | { ZD_CR3, 0x38 }, { ZD_CR4, 0x80 }, { ZD_CR9, 0xe0 }, | ||
701 | { ZD_CR10, 0x81 }, | ||
702 | /* power control { { ZD_CR11, 1 << 6 }, */ | ||
703 | { ZD_CR11, 0x00 }, | ||
704 | { ZD_CR12, 0xf0 }, { ZD_CR13, 0x8c }, { ZD_CR14, 0x80 }, | ||
705 | { ZD_CR15, 0x3d }, { ZD_CR16, 0x20 }, { ZD_CR17, 0x1e }, | ||
706 | { ZD_CR18, 0x0a }, { ZD_CR19, 0x48 }, | ||
707 | { ZD_CR20, 0x10 }, /* Org:0x0E, ComTrend:RalLink AP */ | ||
708 | { ZD_CR21, 0x0e }, { ZD_CR22, 0x23 }, { ZD_CR23, 0x90 }, | ||
709 | { ZD_CR24, 0x14 }, { ZD_CR25, 0x40 }, { ZD_CR26, 0x10 }, | ||
710 | { ZD_CR27, 0x10 }, { ZD_CR28, 0x7f }, { ZD_CR29, 0x80 }, | ||
711 | { ZD_CR30, 0x4b }, /* ASIC/FWT, no jointly decoder */ | ||
712 | { ZD_CR31, 0x60 }, { ZD_CR32, 0x43 }, { ZD_CR33, 0x08 }, | ||
713 | { ZD_CR34, 0x06 }, { ZD_CR35, 0x0a }, { ZD_CR36, 0x00 }, | ||
714 | { ZD_CR37, 0x00 }, { ZD_CR38, 0x38 }, { ZD_CR39, 0x0c }, | ||
715 | { ZD_CR40, 0x84 }, { ZD_CR41, 0x2a }, { ZD_CR42, 0x80 }, | ||
716 | { ZD_CR43, 0x10 }, { ZD_CR44, 0x33 }, { ZD_CR46, 0xff }, | ||
717 | { ZD_CR47, 0x1E }, { ZD_CR48, 0x26 }, { ZD_CR49, 0x5b }, | ||
718 | { ZD_CR64, 0xd0 }, { ZD_CR65, 0x04 }, { ZD_CR66, 0x58 }, | ||
719 | { ZD_CR67, 0xc9 }, { ZD_CR68, 0x88 }, { ZD_CR69, 0x41 }, | ||
720 | { ZD_CR70, 0x23 }, { ZD_CR71, 0x10 }, { ZD_CR72, 0xff }, | ||
721 | { ZD_CR73, 0x32 }, { ZD_CR74, 0x30 }, { ZD_CR75, 0x65 }, | ||
722 | { ZD_CR76, 0x41 }, { ZD_CR77, 0x1b }, { ZD_CR78, 0x30 }, | ||
723 | { ZD_CR79, 0xf0 }, { ZD_CR80, 0x64 }, { ZD_CR81, 0x64 }, | ||
724 | { ZD_CR82, 0x00 }, { ZD_CR83, 0x24 }, { ZD_CR84, 0x04 }, | ||
725 | { ZD_CR85, 0x00 }, { ZD_CR86, 0x0c }, { ZD_CR87, 0x12 }, | ||
726 | { ZD_CR88, 0x0c }, { ZD_CR89, 0x00 }, { ZD_CR90, 0x58 }, | ||
727 | { ZD_CR91, 0x04 }, { ZD_CR92, 0x00 }, { ZD_CR93, 0x00 }, | ||
728 | { ZD_CR94, 0x01 }, | ||
729 | { ZD_CR95, 0x20 }, /* ZD1211B */ | ||
730 | { ZD_CR96, 0x50 }, { ZD_CR97, 0x37 }, { ZD_CR98, 0x35 }, | ||
731 | { ZD_CR99, 0x00 }, { ZD_CR100, 0x01 }, { ZD_CR101, 0x13 }, | ||
732 | { ZD_CR102, 0x27 }, { ZD_CR103, 0x27 }, { ZD_CR104, 0x18 }, | ||
733 | { ZD_CR105, 0x12 }, { ZD_CR106, 0x04 }, { ZD_CR107, 0x00 }, | ||
734 | { ZD_CR108, 0x0a }, { ZD_CR109, 0x27 }, { ZD_CR110, 0x27 }, | ||
735 | { ZD_CR111, 0x27 }, { ZD_CR112, 0x27 }, { ZD_CR113, 0x27 }, | ||
736 | { ZD_CR114, 0x27 }, { ZD_CR115, 0x26 }, { ZD_CR116, 0x24 }, | ||
737 | { ZD_CR117, 0xfc }, { ZD_CR118, 0xfa }, { ZD_CR119, 0x1e }, | ||
738 | { ZD_CR125, 0x90 }, { ZD_CR126, 0x00 }, { ZD_CR127, 0x00 }, | ||
739 | { ZD_CR128, 0x14 }, { ZD_CR129, 0x12 }, { ZD_CR130, 0x10 }, | ||
740 | { ZD_CR131, 0x0c }, { ZD_CR136, 0xdf }, { ZD_CR137, 0xa0 }, | ||
741 | { ZD_CR138, 0xa8 }, { ZD_CR139, 0xb4 }, { ZD_CR140, 0x98 }, | ||
742 | { ZD_CR141, 0x82 }, { ZD_CR142, 0x53 }, { ZD_CR143, 0x1c }, | ||
743 | { ZD_CR144, 0x6c }, { ZD_CR147, 0x07 }, { ZD_CR148, 0x40 }, | ||
744 | { ZD_CR149, 0x40 }, /* Org:0x50 ComTrend:RalLink AP */ | ||
745 | { ZD_CR150, 0x14 }, /* Org:0x0E ComTrend:RalLink AP */ | ||
746 | { ZD_CR151, 0x18 }, { ZD_CR159, 0x70 }, { ZD_CR160, 0xfe }, | ||
747 | { ZD_CR161, 0xee }, { ZD_CR162, 0xaa }, { ZD_CR163, 0xfa }, | ||
748 | { ZD_CR164, 0xfa }, { ZD_CR165, 0xea }, { ZD_CR166, 0xbe }, | ||
749 | { ZD_CR167, 0xbe }, { ZD_CR168, 0x6a }, { ZD_CR169, 0xba }, | ||
750 | { ZD_CR170, 0xba }, { ZD_CR171, 0xba }, | ||
751 | /* Note: ZD_CR204 must lead the ZD_CR203 */ | ||
752 | { ZD_CR204, 0x7d }, | ||
753 | {}, | ||
754 | { ZD_CR203, 0x30 }, | ||
755 | }; | ||
756 | |||
757 | int r, t; | ||
758 | |||
759 | dev_dbg_f(zd_chip_dev(chip), "\n"); | ||
760 | |||
761 | r = zd_chip_lock_phy_regs(chip); | ||
762 | if (r) | ||
763 | goto out; | ||
764 | |||
765 | r = zd_iowrite16a_locked(chip, ioreqs, ARRAY_SIZE(ioreqs)); | ||
766 | t = zd_chip_unlock_phy_regs(chip); | ||
767 | if (t && !r) | ||
768 | r = t; | ||
769 | out: | ||
770 | return r; | ||
771 | } | ||
772 | |||
773 | static int hw_reset_phy(struct zd_chip *chip) | ||
774 | { | ||
775 | return zd_chip_is_zd1211b(chip) ? zd1211b_hw_reset_phy(chip) : | ||
776 | zd1211_hw_reset_phy(chip); | ||
777 | } | ||
778 | |||
779 | static int zd1211_hw_init_hmac(struct zd_chip *chip) | ||
780 | { | ||
781 | static const struct zd_ioreq32 ioreqs[] = { | ||
782 | { CR_ZD1211_RETRY_MAX, ZD1211_RETRY_COUNT }, | ||
783 | { CR_RX_THRESHOLD, 0x000c0640 }, | ||
784 | }; | ||
785 | |||
786 | dev_dbg_f(zd_chip_dev(chip), "\n"); | ||
787 | ZD_ASSERT(mutex_is_locked(&chip->mutex)); | ||
788 | return zd_iowrite32a_locked(chip, ioreqs, ARRAY_SIZE(ioreqs)); | ||
789 | } | ||
790 | |||
791 | static int zd1211b_hw_init_hmac(struct zd_chip *chip) | ||
792 | { | ||
793 | static const struct zd_ioreq32 ioreqs[] = { | ||
794 | { CR_ZD1211B_RETRY_MAX, ZD1211B_RETRY_COUNT }, | ||
795 | { CR_ZD1211B_CWIN_MAX_MIN_AC0, 0x007f003f }, | ||
796 | { CR_ZD1211B_CWIN_MAX_MIN_AC1, 0x007f003f }, | ||
797 | { CR_ZD1211B_CWIN_MAX_MIN_AC2, 0x003f001f }, | ||
798 | { CR_ZD1211B_CWIN_MAX_MIN_AC3, 0x001f000f }, | ||
799 | { CR_ZD1211B_AIFS_CTL1, 0x00280028 }, | ||
800 | { CR_ZD1211B_AIFS_CTL2, 0x008C003C }, | ||
801 | { CR_ZD1211B_TXOP, 0x01800824 }, | ||
802 | { CR_RX_THRESHOLD, 0x000c0eff, }, | ||
803 | }; | ||
804 | |||
805 | dev_dbg_f(zd_chip_dev(chip), "\n"); | ||
806 | ZD_ASSERT(mutex_is_locked(&chip->mutex)); | ||
807 | return zd_iowrite32a_locked(chip, ioreqs, ARRAY_SIZE(ioreqs)); | ||
808 | } | ||
809 | |||
810 | static int hw_init_hmac(struct zd_chip *chip) | ||
811 | { | ||
812 | int r; | ||
813 | static const struct zd_ioreq32 ioreqs[] = { | ||
814 | { CR_ACK_TIMEOUT_EXT, 0x20 }, | ||
815 | { CR_ADDA_MBIAS_WARMTIME, 0x30000808 }, | ||
816 | { CR_SNIFFER_ON, 0 }, | ||
817 | { CR_RX_FILTER, STA_RX_FILTER }, | ||
818 | { CR_GROUP_HASH_P1, 0x00 }, | ||
819 | { CR_GROUP_HASH_P2, 0x80000000 }, | ||
820 | { CR_REG1, 0xa4 }, | ||
821 | { CR_ADDA_PWR_DWN, 0x7f }, | ||
822 | { CR_BCN_PLCP_CFG, 0x00f00401 }, | ||
823 | { CR_PHY_DELAY, 0x00 }, | ||
824 | { CR_ACK_TIMEOUT_EXT, 0x80 }, | ||
825 | { CR_ADDA_PWR_DWN, 0x00 }, | ||
826 | { CR_ACK_TIME_80211, 0x100 }, | ||
827 | { CR_RX_PE_DELAY, 0x70 }, | ||
828 | { CR_PS_CTRL, 0x10000000 }, | ||
829 | { CR_RTS_CTS_RATE, 0x02030203 }, | ||
830 | { CR_AFTER_PNP, 0x1 }, | ||
831 | { CR_WEP_PROTECT, 0x114 }, | ||
832 | { CR_IFS_VALUE, IFS_VALUE_DEFAULT }, | ||
833 | { CR_CAM_MODE, MODE_AP_WDS}, | ||
834 | }; | ||
835 | |||
836 | ZD_ASSERT(mutex_is_locked(&chip->mutex)); | ||
837 | r = zd_iowrite32a_locked(chip, ioreqs, ARRAY_SIZE(ioreqs)); | ||
838 | if (r) | ||
839 | return r; | ||
840 | |||
841 | return zd_chip_is_zd1211b(chip) ? | ||
842 | zd1211b_hw_init_hmac(chip) : zd1211_hw_init_hmac(chip); | ||
843 | } | ||
844 | |||
845 | struct aw_pt_bi { | ||
846 | u32 atim_wnd_period; | ||
847 | u32 pre_tbtt; | ||
848 | u32 beacon_interval; | ||
849 | }; | ||
850 | |||
851 | static int get_aw_pt_bi(struct zd_chip *chip, struct aw_pt_bi *s) | ||
852 | { | ||
853 | int r; | ||
854 | static const zd_addr_t aw_pt_bi_addr[] = | ||
855 | { CR_ATIM_WND_PERIOD, CR_PRE_TBTT, CR_BCN_INTERVAL }; | ||
856 | u32 values[3]; | ||
857 | |||
858 | r = zd_ioread32v_locked(chip, values, (const zd_addr_t *)aw_pt_bi_addr, | ||
859 | ARRAY_SIZE(aw_pt_bi_addr)); | ||
860 | if (r) { | ||
861 | memset(s, 0, sizeof(*s)); | ||
862 | return r; | ||
863 | } | ||
864 | |||
865 | s->atim_wnd_period = values[0]; | ||
866 | s->pre_tbtt = values[1]; | ||
867 | s->beacon_interval = values[2]; | ||
868 | return 0; | ||
869 | } | ||
870 | |||
871 | static int set_aw_pt_bi(struct zd_chip *chip, struct aw_pt_bi *s) | ||
872 | { | ||
873 | struct zd_ioreq32 reqs[3]; | ||
874 | u16 b_interval = s->beacon_interval & 0xffff; | ||
875 | |||
876 | if (b_interval <= 5) | ||
877 | b_interval = 5; | ||
878 | if (s->pre_tbtt < 4 || s->pre_tbtt >= b_interval) | ||
879 | s->pre_tbtt = b_interval - 1; | ||
880 | if (s->atim_wnd_period >= s->pre_tbtt) | ||
881 | s->atim_wnd_period = s->pre_tbtt - 1; | ||
882 | |||
883 | reqs[0].addr = CR_ATIM_WND_PERIOD; | ||
884 | reqs[0].value = s->atim_wnd_period; | ||
885 | reqs[1].addr = CR_PRE_TBTT; | ||
886 | reqs[1].value = s->pre_tbtt; | ||
887 | reqs[2].addr = CR_BCN_INTERVAL; | ||
888 | reqs[2].value = (s->beacon_interval & ~0xffff) | b_interval; | ||
889 | |||
890 | return zd_iowrite32a_locked(chip, reqs, ARRAY_SIZE(reqs)); | ||
891 | } | ||
892 | |||
893 | |||
894 | static int set_beacon_interval(struct zd_chip *chip, u16 interval, | ||
895 | u8 dtim_period, int type) | ||
896 | { | ||
897 | int r; | ||
898 | struct aw_pt_bi s; | ||
899 | u32 b_interval, mode_flag; | ||
900 | |||
901 | ZD_ASSERT(mutex_is_locked(&chip->mutex)); | ||
902 | |||
903 | if (interval > 0) { | ||
904 | switch (type) { | ||
905 | case NL80211_IFTYPE_ADHOC: | ||
906 | case NL80211_IFTYPE_MESH_POINT: | ||
907 | mode_flag = BCN_MODE_IBSS; | ||
908 | break; | ||
909 | case NL80211_IFTYPE_AP: | ||
910 | mode_flag = BCN_MODE_AP; | ||
911 | break; | ||
912 | default: | ||
913 | mode_flag = 0; | ||
914 | break; | ||
915 | } | ||
916 | } else { | ||
917 | dtim_period = 0; | ||
918 | mode_flag = 0; | ||
919 | } | ||
920 | |||
921 | b_interval = mode_flag | (dtim_period << 16) | interval; | ||
922 | |||
923 | r = zd_iowrite32_locked(chip, b_interval, CR_BCN_INTERVAL); | ||
924 | if (r) | ||
925 | return r; | ||
926 | r = get_aw_pt_bi(chip, &s); | ||
927 | if (r) | ||
928 | return r; | ||
929 | return set_aw_pt_bi(chip, &s); | ||
930 | } | ||
931 | |||
932 | int zd_set_beacon_interval(struct zd_chip *chip, u16 interval, u8 dtim_period, | ||
933 | int type) | ||
934 | { | ||
935 | int r; | ||
936 | |||
937 | mutex_lock(&chip->mutex); | ||
938 | r = set_beacon_interval(chip, interval, dtim_period, type); | ||
939 | mutex_unlock(&chip->mutex); | ||
940 | return r; | ||
941 | } | ||
942 | |||
943 | static int hw_init(struct zd_chip *chip) | ||
944 | { | ||
945 | int r; | ||
946 | |||
947 | dev_dbg_f(zd_chip_dev(chip), "\n"); | ||
948 | ZD_ASSERT(mutex_is_locked(&chip->mutex)); | ||
949 | r = hw_reset_phy(chip); | ||
950 | if (r) | ||
951 | return r; | ||
952 | |||
953 | r = hw_init_hmac(chip); | ||
954 | if (r) | ||
955 | return r; | ||
956 | |||
957 | return set_beacon_interval(chip, 100, 0, NL80211_IFTYPE_UNSPECIFIED); | ||
958 | } | ||
959 | |||
960 | static zd_addr_t fw_reg_addr(struct zd_chip *chip, u16 offset) | ||
961 | { | ||
962 | return (zd_addr_t)((u16)chip->fw_regs_base + offset); | ||
963 | } | ||
964 | |||
965 | #ifdef DEBUG | ||
966 | static int dump_cr(struct zd_chip *chip, const zd_addr_t addr, | ||
967 | const char *addr_string) | ||
968 | { | ||
969 | int r; | ||
970 | u32 value; | ||
971 | |||
972 | r = zd_ioread32_locked(chip, &value, addr); | ||
973 | if (r) { | ||
974 | dev_dbg_f(zd_chip_dev(chip), | ||
975 | "error reading %s. Error number %d\n", addr_string, r); | ||
976 | return r; | ||
977 | } | ||
978 | |||
979 | dev_dbg_f(zd_chip_dev(chip), "%s %#010x\n", | ||
980 | addr_string, (unsigned int)value); | ||
981 | return 0; | ||
982 | } | ||
983 | |||
984 | static int test_init(struct zd_chip *chip) | ||
985 | { | ||
986 | int r; | ||
987 | |||
988 | r = dump_cr(chip, CR_AFTER_PNP, "CR_AFTER_PNP"); | ||
989 | if (r) | ||
990 | return r; | ||
991 | r = dump_cr(chip, CR_GPI_EN, "CR_GPI_EN"); | ||
992 | if (r) | ||
993 | return r; | ||
994 | return dump_cr(chip, CR_INTERRUPT, "CR_INTERRUPT"); | ||
995 | } | ||
996 | |||
997 | static void dump_fw_registers(struct zd_chip *chip) | ||
998 | { | ||
999 | const zd_addr_t addr[4] = { | ||
1000 | fw_reg_addr(chip, FW_REG_FIRMWARE_VER), | ||
1001 | fw_reg_addr(chip, FW_REG_USB_SPEED), | ||
1002 | fw_reg_addr(chip, FW_REG_FIX_TX_RATE), | ||
1003 | fw_reg_addr(chip, FW_REG_LED_LINK_STATUS), | ||
1004 | }; | ||
1005 | |||
1006 | int r; | ||
1007 | u16 values[4]; | ||
1008 | |||
1009 | r = zd_ioread16v_locked(chip, values, (const zd_addr_t*)addr, | ||
1010 | ARRAY_SIZE(addr)); | ||
1011 | if (r) { | ||
1012 | dev_dbg_f(zd_chip_dev(chip), "error %d zd_ioread16v_locked\n", | ||
1013 | r); | ||
1014 | return; | ||
1015 | } | ||
1016 | |||
1017 | dev_dbg_f(zd_chip_dev(chip), "FW_FIRMWARE_VER %#06hx\n", values[0]); | ||
1018 | dev_dbg_f(zd_chip_dev(chip), "FW_USB_SPEED %#06hx\n", values[1]); | ||
1019 | dev_dbg_f(zd_chip_dev(chip), "FW_FIX_TX_RATE %#06hx\n", values[2]); | ||
1020 | dev_dbg_f(zd_chip_dev(chip), "FW_LINK_STATUS %#06hx\n", values[3]); | ||
1021 | } | ||
1022 | #endif /* DEBUG */ | ||
1023 | |||
1024 | static int print_fw_version(struct zd_chip *chip) | ||
1025 | { | ||
1026 | struct wiphy *wiphy = zd_chip_to_mac(chip)->hw->wiphy; | ||
1027 | int r; | ||
1028 | u16 version; | ||
1029 | |||
1030 | r = zd_ioread16_locked(chip, &version, | ||
1031 | fw_reg_addr(chip, FW_REG_FIRMWARE_VER)); | ||
1032 | if (r) | ||
1033 | return r; | ||
1034 | |||
1035 | dev_info(zd_chip_dev(chip),"firmware version %04hx\n", version); | ||
1036 | |||
1037 | snprintf(wiphy->fw_version, sizeof(wiphy->fw_version), | ||
1038 | "%04hx", version); | ||
1039 | |||
1040 | return 0; | ||
1041 | } | ||
1042 | |||
1043 | static int set_mandatory_rates(struct zd_chip *chip, int gmode) | ||
1044 | { | ||
1045 | u32 rates; | ||
1046 | ZD_ASSERT(mutex_is_locked(&chip->mutex)); | ||
1047 | /* This sets the mandatory rates, which only depend from the standard | ||
1048 | * that the device is supporting. Until further notice we should try | ||
1049 | * to support 802.11g also for full speed USB. | ||
1050 | */ | ||
1051 | if (!gmode) | ||
1052 | rates = CR_RATE_1M|CR_RATE_2M|CR_RATE_5_5M|CR_RATE_11M; | ||
1053 | else | ||
1054 | rates = CR_RATE_1M|CR_RATE_2M|CR_RATE_5_5M|CR_RATE_11M| | ||
1055 | CR_RATE_6M|CR_RATE_12M|CR_RATE_24M; | ||
1056 | |||
1057 | return zd_iowrite32_locked(chip, rates, CR_MANDATORY_RATE_TBL); | ||
1058 | } | ||
1059 | |||
1060 | int zd_chip_set_rts_cts_rate_locked(struct zd_chip *chip, | ||
1061 | int preamble) | ||
1062 | { | ||
1063 | u32 value = 0; | ||
1064 | |||
1065 | dev_dbg_f(zd_chip_dev(chip), "preamble=%x\n", preamble); | ||
1066 | value |= preamble << RTSCTS_SH_RTS_PMB_TYPE; | ||
1067 | value |= preamble << RTSCTS_SH_CTS_PMB_TYPE; | ||
1068 | |||
1069 | /* We always send 11M RTS/self-CTS messages, like the vendor driver. */ | ||
1070 | value |= ZD_PURE_RATE(ZD_CCK_RATE_11M) << RTSCTS_SH_RTS_RATE; | ||
1071 | value |= ZD_RX_CCK << RTSCTS_SH_RTS_MOD_TYPE; | ||
1072 | value |= ZD_PURE_RATE(ZD_CCK_RATE_11M) << RTSCTS_SH_CTS_RATE; | ||
1073 | value |= ZD_RX_CCK << RTSCTS_SH_CTS_MOD_TYPE; | ||
1074 | |||
1075 | return zd_iowrite32_locked(chip, value, CR_RTS_CTS_RATE); | ||
1076 | } | ||
1077 | |||
1078 | int zd_chip_enable_hwint(struct zd_chip *chip) | ||
1079 | { | ||
1080 | int r; | ||
1081 | |||
1082 | mutex_lock(&chip->mutex); | ||
1083 | r = zd_iowrite32_locked(chip, HWINT_ENABLED, CR_INTERRUPT); | ||
1084 | mutex_unlock(&chip->mutex); | ||
1085 | return r; | ||
1086 | } | ||
1087 | |||
1088 | static int disable_hwint(struct zd_chip *chip) | ||
1089 | { | ||
1090 | return zd_iowrite32_locked(chip, HWINT_DISABLED, CR_INTERRUPT); | ||
1091 | } | ||
1092 | |||
1093 | int zd_chip_disable_hwint(struct zd_chip *chip) | ||
1094 | { | ||
1095 | int r; | ||
1096 | |||
1097 | mutex_lock(&chip->mutex); | ||
1098 | r = disable_hwint(chip); | ||
1099 | mutex_unlock(&chip->mutex); | ||
1100 | return r; | ||
1101 | } | ||
1102 | |||
1103 | static int read_fw_regs_offset(struct zd_chip *chip) | ||
1104 | { | ||
1105 | int r; | ||
1106 | |||
1107 | ZD_ASSERT(mutex_is_locked(&chip->mutex)); | ||
1108 | r = zd_ioread16_locked(chip, (u16*)&chip->fw_regs_base, | ||
1109 | FWRAW_REGS_ADDR); | ||
1110 | if (r) | ||
1111 | return r; | ||
1112 | dev_dbg_f(zd_chip_dev(chip), "fw_regs_base: %#06hx\n", | ||
1113 | (u16)chip->fw_regs_base); | ||
1114 | |||
1115 | return 0; | ||
1116 | } | ||
1117 | |||
1118 | /* Read mac address using pre-firmware interface */ | ||
1119 | int zd_chip_read_mac_addr_fw(struct zd_chip *chip, u8 *addr) | ||
1120 | { | ||
1121 | dev_dbg_f(zd_chip_dev(chip), "\n"); | ||
1122 | return zd_usb_read_fw(&chip->usb, E2P_MAC_ADDR_P1, addr, | ||
1123 | ETH_ALEN); | ||
1124 | } | ||
1125 | |||
1126 | int zd_chip_init_hw(struct zd_chip *chip) | ||
1127 | { | ||
1128 | int r; | ||
1129 | u8 rf_type; | ||
1130 | |||
1131 | dev_dbg_f(zd_chip_dev(chip), "\n"); | ||
1132 | |||
1133 | mutex_lock(&chip->mutex); | ||
1134 | |||
1135 | #ifdef DEBUG | ||
1136 | r = test_init(chip); | ||
1137 | if (r) | ||
1138 | goto out; | ||
1139 | #endif | ||
1140 | r = zd_iowrite32_locked(chip, 1, CR_AFTER_PNP); | ||
1141 | if (r) | ||
1142 | goto out; | ||
1143 | |||
1144 | r = read_fw_regs_offset(chip); | ||
1145 | if (r) | ||
1146 | goto out; | ||
1147 | |||
1148 | /* GPI is always disabled, also in the other driver. | ||
1149 | */ | ||
1150 | r = zd_iowrite32_locked(chip, 0, CR_GPI_EN); | ||
1151 | if (r) | ||
1152 | goto out; | ||
1153 | r = zd_iowrite32_locked(chip, CWIN_SIZE, CR_CWMIN_CWMAX); | ||
1154 | if (r) | ||
1155 | goto out; | ||
1156 | /* Currently we support IEEE 802.11g for full and high speed USB. | ||
1157 | * It might be discussed, whether we should support pure b mode for | ||
1158 | * full speed USB. | ||
1159 | */ | ||
1160 | r = set_mandatory_rates(chip, 1); | ||
1161 | if (r) | ||
1162 | goto out; | ||
1163 | /* Disabling interrupts is certainly a smart thing here. | ||
1164 | */ | ||
1165 | r = disable_hwint(chip); | ||
1166 | if (r) | ||
1167 | goto out; | ||
1168 | r = read_pod(chip, &rf_type); | ||
1169 | if (r) | ||
1170 | goto out; | ||
1171 | r = hw_init(chip); | ||
1172 | if (r) | ||
1173 | goto out; | ||
1174 | r = zd_rf_init_hw(&chip->rf, rf_type); | ||
1175 | if (r) | ||
1176 | goto out; | ||
1177 | |||
1178 | r = print_fw_version(chip); | ||
1179 | if (r) | ||
1180 | goto out; | ||
1181 | |||
1182 | #ifdef DEBUG | ||
1183 | dump_fw_registers(chip); | ||
1184 | r = test_init(chip); | ||
1185 | if (r) | ||
1186 | goto out; | ||
1187 | #endif /* DEBUG */ | ||
1188 | |||
1189 | r = read_cal_int_tables(chip); | ||
1190 | if (r) | ||
1191 | goto out; | ||
1192 | |||
1193 | print_id(chip); | ||
1194 | out: | ||
1195 | mutex_unlock(&chip->mutex); | ||
1196 | return r; | ||
1197 | } | ||
1198 | |||
1199 | static int update_pwr_int(struct zd_chip *chip, u8 channel) | ||
1200 | { | ||
1201 | u8 value = chip->pwr_int_values[channel - 1]; | ||
1202 | return zd_iowrite16_locked(chip, value, ZD_CR31); | ||
1203 | } | ||
1204 | |||
1205 | static int update_pwr_cal(struct zd_chip *chip, u8 channel) | ||
1206 | { | ||
1207 | u8 value = chip->pwr_cal_values[channel-1]; | ||
1208 | return zd_iowrite16_locked(chip, value, ZD_CR68); | ||
1209 | } | ||
1210 | |||
1211 | static int update_ofdm_cal(struct zd_chip *chip, u8 channel) | ||
1212 | { | ||
1213 | struct zd_ioreq16 ioreqs[3]; | ||
1214 | |||
1215 | ioreqs[0].addr = ZD_CR67; | ||
1216 | ioreqs[0].value = chip->ofdm_cal_values[OFDM_36M_INDEX][channel-1]; | ||
1217 | ioreqs[1].addr = ZD_CR66; | ||
1218 | ioreqs[1].value = chip->ofdm_cal_values[OFDM_48M_INDEX][channel-1]; | ||
1219 | ioreqs[2].addr = ZD_CR65; | ||
1220 | ioreqs[2].value = chip->ofdm_cal_values[OFDM_54M_INDEX][channel-1]; | ||
1221 | |||
1222 | return zd_iowrite16a_locked(chip, ioreqs, ARRAY_SIZE(ioreqs)); | ||
1223 | } | ||
1224 | |||
1225 | static int update_channel_integration_and_calibration(struct zd_chip *chip, | ||
1226 | u8 channel) | ||
1227 | { | ||
1228 | int r; | ||
1229 | |||
1230 | if (!zd_rf_should_update_pwr_int(&chip->rf)) | ||
1231 | return 0; | ||
1232 | |||
1233 | r = update_pwr_int(chip, channel); | ||
1234 | if (r) | ||
1235 | return r; | ||
1236 | if (zd_chip_is_zd1211b(chip)) { | ||
1237 | static const struct zd_ioreq16 ioreqs[] = { | ||
1238 | { ZD_CR69, 0x28 }, | ||
1239 | {}, | ||
1240 | { ZD_CR69, 0x2a }, | ||
1241 | }; | ||
1242 | |||
1243 | r = update_ofdm_cal(chip, channel); | ||
1244 | if (r) | ||
1245 | return r; | ||
1246 | r = update_pwr_cal(chip, channel); | ||
1247 | if (r) | ||
1248 | return r; | ||
1249 | r = zd_iowrite16a_locked(chip, ioreqs, ARRAY_SIZE(ioreqs)); | ||
1250 | if (r) | ||
1251 | return r; | ||
1252 | } | ||
1253 | |||
1254 | return 0; | ||
1255 | } | ||
1256 | |||
1257 | /* The CCK baseband gain can be optionally patched by the EEPROM */ | ||
1258 | static int patch_cck_gain(struct zd_chip *chip) | ||
1259 | { | ||
1260 | int r; | ||
1261 | u32 value; | ||
1262 | |||
1263 | if (!chip->patch_cck_gain || !zd_rf_should_patch_cck_gain(&chip->rf)) | ||
1264 | return 0; | ||
1265 | |||
1266 | ZD_ASSERT(mutex_is_locked(&chip->mutex)); | ||
1267 | r = zd_ioread32_locked(chip, &value, E2P_PHY_REG); | ||
1268 | if (r) | ||
1269 | return r; | ||
1270 | dev_dbg_f(zd_chip_dev(chip), "patching value %x\n", value & 0xff); | ||
1271 | return zd_iowrite16_locked(chip, value & 0xff, ZD_CR47); | ||
1272 | } | ||
1273 | |||
1274 | int zd_chip_set_channel(struct zd_chip *chip, u8 channel) | ||
1275 | { | ||
1276 | int r, t; | ||
1277 | |||
1278 | mutex_lock(&chip->mutex); | ||
1279 | r = zd_chip_lock_phy_regs(chip); | ||
1280 | if (r) | ||
1281 | goto out; | ||
1282 | r = zd_rf_set_channel(&chip->rf, channel); | ||
1283 | if (r) | ||
1284 | goto unlock; | ||
1285 | r = update_channel_integration_and_calibration(chip, channel); | ||
1286 | if (r) | ||
1287 | goto unlock; | ||
1288 | r = patch_cck_gain(chip); | ||
1289 | if (r) | ||
1290 | goto unlock; | ||
1291 | r = patch_6m_band_edge(chip, channel); | ||
1292 | if (r) | ||
1293 | goto unlock; | ||
1294 | r = zd_iowrite32_locked(chip, 0, CR_CONFIG_PHILIPS); | ||
1295 | unlock: | ||
1296 | t = zd_chip_unlock_phy_regs(chip); | ||
1297 | if (t && !r) | ||
1298 | r = t; | ||
1299 | out: | ||
1300 | mutex_unlock(&chip->mutex); | ||
1301 | return r; | ||
1302 | } | ||
1303 | |||
1304 | u8 zd_chip_get_channel(struct zd_chip *chip) | ||
1305 | { | ||
1306 | u8 channel; | ||
1307 | |||
1308 | mutex_lock(&chip->mutex); | ||
1309 | channel = chip->rf.channel; | ||
1310 | mutex_unlock(&chip->mutex); | ||
1311 | return channel; | ||
1312 | } | ||
1313 | |||
1314 | int zd_chip_control_leds(struct zd_chip *chip, enum led_status status) | ||
1315 | { | ||
1316 | const zd_addr_t a[] = { | ||
1317 | fw_reg_addr(chip, FW_REG_LED_LINK_STATUS), | ||
1318 | CR_LED, | ||
1319 | }; | ||
1320 | |||
1321 | int r; | ||
1322 | u16 v[ARRAY_SIZE(a)]; | ||
1323 | struct zd_ioreq16 ioreqs[ARRAY_SIZE(a)] = { | ||
1324 | [0] = { fw_reg_addr(chip, FW_REG_LED_LINK_STATUS) }, | ||
1325 | [1] = { CR_LED }, | ||
1326 | }; | ||
1327 | u16 other_led; | ||
1328 | |||
1329 | mutex_lock(&chip->mutex); | ||
1330 | r = zd_ioread16v_locked(chip, v, (const zd_addr_t *)a, ARRAY_SIZE(a)); | ||
1331 | if (r) | ||
1332 | goto out; | ||
1333 | |||
1334 | other_led = chip->link_led == LED1 ? LED2 : LED1; | ||
1335 | |||
1336 | switch (status) { | ||
1337 | case ZD_LED_OFF: | ||
1338 | ioreqs[0].value = FW_LINK_OFF; | ||
1339 | ioreqs[1].value = v[1] & ~(LED1|LED2); | ||
1340 | break; | ||
1341 | case ZD_LED_SCANNING: | ||
1342 | ioreqs[0].value = FW_LINK_OFF; | ||
1343 | ioreqs[1].value = v[1] & ~other_led; | ||
1344 | if (get_seconds() % 3 == 0) { | ||
1345 | ioreqs[1].value &= ~chip->link_led; | ||
1346 | } else { | ||
1347 | ioreqs[1].value |= chip->link_led; | ||
1348 | } | ||
1349 | break; | ||
1350 | case ZD_LED_ASSOCIATED: | ||
1351 | ioreqs[0].value = FW_LINK_TX; | ||
1352 | ioreqs[1].value = v[1] & ~other_led; | ||
1353 | ioreqs[1].value |= chip->link_led; | ||
1354 | break; | ||
1355 | default: | ||
1356 | r = -EINVAL; | ||
1357 | goto out; | ||
1358 | } | ||
1359 | |||
1360 | if (v[0] != ioreqs[0].value || v[1] != ioreqs[1].value) { | ||
1361 | r = zd_iowrite16a_locked(chip, ioreqs, ARRAY_SIZE(ioreqs)); | ||
1362 | if (r) | ||
1363 | goto out; | ||
1364 | } | ||
1365 | r = 0; | ||
1366 | out: | ||
1367 | mutex_unlock(&chip->mutex); | ||
1368 | return r; | ||
1369 | } | ||
1370 | |||
1371 | int zd_chip_set_basic_rates(struct zd_chip *chip, u16 cr_rates) | ||
1372 | { | ||
1373 | int r; | ||
1374 | |||
1375 | if (cr_rates & ~(CR_RATES_80211B|CR_RATES_80211G)) | ||
1376 | return -EINVAL; | ||
1377 | |||
1378 | mutex_lock(&chip->mutex); | ||
1379 | r = zd_iowrite32_locked(chip, cr_rates, CR_BASIC_RATE_TBL); | ||
1380 | mutex_unlock(&chip->mutex); | ||
1381 | return r; | ||
1382 | } | ||
1383 | |||
1384 | static inline u8 zd_rate_from_ofdm_plcp_header(const void *rx_frame) | ||
1385 | { | ||
1386 | return ZD_OFDM | zd_ofdm_plcp_header_rate(rx_frame); | ||
1387 | } | ||
1388 | |||
1389 | /** | ||
1390 | * zd_rx_rate - report zd-rate | ||
1391 | * @rx_frame - received frame | ||
1392 | * @rx_status - rx_status as given by the device | ||
1393 | * | ||
1394 | * This function converts the rate as encoded in the received packet to the | ||
1395 | * zd-rate, we are using on other places in the driver. | ||
1396 | */ | ||
1397 | u8 zd_rx_rate(const void *rx_frame, const struct rx_status *status) | ||
1398 | { | ||
1399 | u8 zd_rate; | ||
1400 | if (status->frame_status & ZD_RX_OFDM) { | ||
1401 | zd_rate = zd_rate_from_ofdm_plcp_header(rx_frame); | ||
1402 | } else { | ||
1403 | switch (zd_cck_plcp_header_signal(rx_frame)) { | ||
1404 | case ZD_CCK_PLCP_SIGNAL_1M: | ||
1405 | zd_rate = ZD_CCK_RATE_1M; | ||
1406 | break; | ||
1407 | case ZD_CCK_PLCP_SIGNAL_2M: | ||
1408 | zd_rate = ZD_CCK_RATE_2M; | ||
1409 | break; | ||
1410 | case ZD_CCK_PLCP_SIGNAL_5M5: | ||
1411 | zd_rate = ZD_CCK_RATE_5_5M; | ||
1412 | break; | ||
1413 | case ZD_CCK_PLCP_SIGNAL_11M: | ||
1414 | zd_rate = ZD_CCK_RATE_11M; | ||
1415 | break; | ||
1416 | default: | ||
1417 | zd_rate = 0; | ||
1418 | } | ||
1419 | } | ||
1420 | |||
1421 | return zd_rate; | ||
1422 | } | ||
1423 | |||
1424 | int zd_chip_switch_radio_on(struct zd_chip *chip) | ||
1425 | { | ||
1426 | int r; | ||
1427 | |||
1428 | mutex_lock(&chip->mutex); | ||
1429 | r = zd_switch_radio_on(&chip->rf); | ||
1430 | mutex_unlock(&chip->mutex); | ||
1431 | return r; | ||
1432 | } | ||
1433 | |||
1434 | int zd_chip_switch_radio_off(struct zd_chip *chip) | ||
1435 | { | ||
1436 | int r; | ||
1437 | |||
1438 | mutex_lock(&chip->mutex); | ||
1439 | r = zd_switch_radio_off(&chip->rf); | ||
1440 | mutex_unlock(&chip->mutex); | ||
1441 | return r; | ||
1442 | } | ||
1443 | |||
1444 | int zd_chip_enable_int(struct zd_chip *chip) | ||
1445 | { | ||
1446 | int r; | ||
1447 | |||
1448 | mutex_lock(&chip->mutex); | ||
1449 | r = zd_usb_enable_int(&chip->usb); | ||
1450 | mutex_unlock(&chip->mutex); | ||
1451 | return r; | ||
1452 | } | ||
1453 | |||
1454 | void zd_chip_disable_int(struct zd_chip *chip) | ||
1455 | { | ||
1456 | mutex_lock(&chip->mutex); | ||
1457 | zd_usb_disable_int(&chip->usb); | ||
1458 | mutex_unlock(&chip->mutex); | ||
1459 | |||
1460 | /* cancel pending interrupt work */ | ||
1461 | cancel_work_sync(&zd_chip_to_mac(chip)->process_intr); | ||
1462 | } | ||
1463 | |||
1464 | int zd_chip_enable_rxtx(struct zd_chip *chip) | ||
1465 | { | ||
1466 | int r; | ||
1467 | |||
1468 | mutex_lock(&chip->mutex); | ||
1469 | zd_usb_enable_tx(&chip->usb); | ||
1470 | r = zd_usb_enable_rx(&chip->usb); | ||
1471 | zd_tx_watchdog_enable(&chip->usb); | ||
1472 | mutex_unlock(&chip->mutex); | ||
1473 | return r; | ||
1474 | } | ||
1475 | |||
1476 | void zd_chip_disable_rxtx(struct zd_chip *chip) | ||
1477 | { | ||
1478 | mutex_lock(&chip->mutex); | ||
1479 | zd_tx_watchdog_disable(&chip->usb); | ||
1480 | zd_usb_disable_rx(&chip->usb); | ||
1481 | zd_usb_disable_tx(&chip->usb); | ||
1482 | mutex_unlock(&chip->mutex); | ||
1483 | } | ||
1484 | |||
1485 | int zd_rfwritev_locked(struct zd_chip *chip, | ||
1486 | const u32* values, unsigned int count, u8 bits) | ||
1487 | { | ||
1488 | int r; | ||
1489 | unsigned int i; | ||
1490 | |||
1491 | for (i = 0; i < count; i++) { | ||
1492 | r = zd_rfwrite_locked(chip, values[i], bits); | ||
1493 | if (r) | ||
1494 | return r; | ||
1495 | } | ||
1496 | |||
1497 | return 0; | ||
1498 | } | ||
1499 | |||
1500 | /* | ||
1501 | * We can optionally program the RF directly through CR regs, if supported by | ||
1502 | * the hardware. This is much faster than the older method. | ||
1503 | */ | ||
1504 | int zd_rfwrite_cr_locked(struct zd_chip *chip, u32 value) | ||
1505 | { | ||
1506 | const struct zd_ioreq16 ioreqs[] = { | ||
1507 | { ZD_CR244, (value >> 16) & 0xff }, | ||
1508 | { ZD_CR243, (value >> 8) & 0xff }, | ||
1509 | { ZD_CR242, value & 0xff }, | ||
1510 | }; | ||
1511 | ZD_ASSERT(mutex_is_locked(&chip->mutex)); | ||
1512 | return zd_iowrite16a_locked(chip, ioreqs, ARRAY_SIZE(ioreqs)); | ||
1513 | } | ||
1514 | |||
1515 | int zd_rfwritev_cr_locked(struct zd_chip *chip, | ||
1516 | const u32 *values, unsigned int count) | ||
1517 | { | ||
1518 | int r; | ||
1519 | unsigned int i; | ||
1520 | |||
1521 | for (i = 0; i < count; i++) { | ||
1522 | r = zd_rfwrite_cr_locked(chip, values[i]); | ||
1523 | if (r) | ||
1524 | return r; | ||
1525 | } | ||
1526 | |||
1527 | return 0; | ||
1528 | } | ||
1529 | |||
1530 | int zd_chip_set_multicast_hash(struct zd_chip *chip, | ||
1531 | struct zd_mc_hash *hash) | ||
1532 | { | ||
1533 | const struct zd_ioreq32 ioreqs[] = { | ||
1534 | { CR_GROUP_HASH_P1, hash->low }, | ||
1535 | { CR_GROUP_HASH_P2, hash->high }, | ||
1536 | }; | ||
1537 | |||
1538 | return zd_iowrite32a(chip, ioreqs, ARRAY_SIZE(ioreqs)); | ||
1539 | } | ||
1540 | |||
1541 | u64 zd_chip_get_tsf(struct zd_chip *chip) | ||
1542 | { | ||
1543 | int r; | ||
1544 | static const zd_addr_t aw_pt_bi_addr[] = | ||
1545 | { CR_TSF_LOW_PART, CR_TSF_HIGH_PART }; | ||
1546 | u32 values[2]; | ||
1547 | u64 tsf; | ||
1548 | |||
1549 | mutex_lock(&chip->mutex); | ||
1550 | r = zd_ioread32v_locked(chip, values, (const zd_addr_t *)aw_pt_bi_addr, | ||
1551 | ARRAY_SIZE(aw_pt_bi_addr)); | ||
1552 | mutex_unlock(&chip->mutex); | ||
1553 | if (r) | ||
1554 | return 0; | ||
1555 | |||
1556 | tsf = values[1]; | ||
1557 | tsf = (tsf << 32) | values[0]; | ||
1558 | |||
1559 | return tsf; | ||
1560 | } | ||
diff --git a/drivers/net/wireless/zydas/zd1211rw/zd_chip.h b/drivers/net/wireless/zydas/zd1211rw/zd_chip.h new file mode 100644 index 000000000000..b03786c9f3aa --- /dev/null +++ b/drivers/net/wireless/zydas/zd1211rw/zd_chip.h | |||
@@ -0,0 +1,983 @@ | |||
1 | /* ZD1211 USB-WLAN driver for Linux | ||
2 | * | ||
3 | * Copyright (C) 2005-2007 Ulrich Kunitz <kune@deine-taler.de> | ||
4 | * Copyright (C) 2006-2007 Daniel Drake <dsd@gentoo.org> | ||
5 | * | ||
6 | * This program is free software; you can redistribute it and/or modify | ||
7 | * it under the terms of the GNU General Public License as published by | ||
8 | * the Free Software Foundation; either version 2 of the License, or | ||
9 | * (at your option) any later version. | ||
10 | * | ||
11 | * This program is distributed in the hope that it will be useful, | ||
12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
14 | * GNU General Public License for more details. | ||
15 | * | ||
16 | * You should have received a copy of the GNU General Public License | ||
17 | * along with this program; if not, see <http://www.gnu.org/licenses/>. | ||
18 | */ | ||
19 | |||
20 | #ifndef _ZD_CHIP_H | ||
21 | #define _ZD_CHIP_H | ||
22 | |||
23 | #include <net/mac80211.h> | ||
24 | |||
25 | #include "zd_rf.h" | ||
26 | #include "zd_usb.h" | ||
27 | |||
28 | /* Header for the Media Access Controller (MAC) and the Baseband Processor | ||
29 | * (BBP). It appears that the ZD1211 wraps the old ZD1205 with USB glue and | ||
30 | * adds a processor for handling the USB protocol. | ||
31 | */ | ||
32 | |||
33 | /* Address space */ | ||
34 | enum { | ||
35 | /* CONTROL REGISTERS */ | ||
36 | CR_START = 0x9000, | ||
37 | |||
38 | |||
39 | /* FIRMWARE */ | ||
40 | FW_START = 0xee00, | ||
41 | |||
42 | |||
43 | /* EEPROM */ | ||
44 | E2P_START = 0xf800, | ||
45 | E2P_LEN = 0x800, | ||
46 | |||
47 | /* EEPROM layout */ | ||
48 | E2P_LOAD_CODE_LEN = 0xe, /* base 0xf800 */ | ||
49 | E2P_LOAD_VECT_LEN = 0x9, /* base 0xf80e */ | ||
50 | /* E2P_DATA indexes into this */ | ||
51 | E2P_DATA_LEN = 0x7e, /* base 0xf817 */ | ||
52 | E2P_BOOT_CODE_LEN = 0x760, /* base 0xf895 */ | ||
53 | E2P_INTR_VECT_LEN = 0xb, /* base 0xfff5 */ | ||
54 | |||
55 | /* Some precomputed offsets into the EEPROM */ | ||
56 | E2P_DATA_OFFSET = E2P_LOAD_CODE_LEN + E2P_LOAD_VECT_LEN, | ||
57 | E2P_BOOT_CODE_OFFSET = E2P_DATA_OFFSET + E2P_DATA_LEN, | ||
58 | }; | ||
59 | |||
60 | #define CTL_REG(offset) ((zd_addr_t)(CR_START + (offset))) | ||
61 | #define E2P_DATA(offset) ((zd_addr_t)(E2P_START + E2P_DATA_OFFSET + (offset))) | ||
62 | #define FWRAW_DATA(offset) ((zd_addr_t)(FW_START + (offset))) | ||
63 | |||
64 | /* 8-bit hardware registers */ | ||
65 | #define ZD_CR0 CTL_REG(0x0000) | ||
66 | #define ZD_CR1 CTL_REG(0x0004) | ||
67 | #define ZD_CR2 CTL_REG(0x0008) | ||
68 | #define ZD_CR3 CTL_REG(0x000C) | ||
69 | |||
70 | #define ZD_CR5 CTL_REG(0x0010) | ||
71 | /* bit 5: if set short preamble used | ||
72 | * bit 6: filter band - Japan channel 14 on, else off | ||
73 | */ | ||
74 | #define ZD_CR6 CTL_REG(0x0014) | ||
75 | #define ZD_CR7 CTL_REG(0x0018) | ||
76 | #define ZD_CR8 CTL_REG(0x001C) | ||
77 | |||
78 | #define ZD_CR4 CTL_REG(0x0020) | ||
79 | |||
80 | #define ZD_CR9 CTL_REG(0x0024) | ||
81 | /* bit 2: antenna switch (together with ZD_CR10) */ | ||
82 | #define ZD_CR10 CTL_REG(0x0028) | ||
83 | /* bit 1: antenna switch (together with ZD_CR9) | ||
84 | * RF2959 controls with ZD_CR11 radion on and off | ||
85 | */ | ||
86 | #define ZD_CR11 CTL_REG(0x002C) | ||
87 | /* bit 6: TX power control for OFDM | ||
88 | * RF2959 controls with ZD_CR10 radio on and off | ||
89 | */ | ||
90 | #define ZD_CR12 CTL_REG(0x0030) | ||
91 | #define ZD_CR13 CTL_REG(0x0034) | ||
92 | #define ZD_CR14 CTL_REG(0x0038) | ||
93 | #define ZD_CR15 CTL_REG(0x003C) | ||
94 | #define ZD_CR16 CTL_REG(0x0040) | ||
95 | #define ZD_CR17 CTL_REG(0x0044) | ||
96 | #define ZD_CR18 CTL_REG(0x0048) | ||
97 | #define ZD_CR19 CTL_REG(0x004C) | ||
98 | #define ZD_CR20 CTL_REG(0x0050) | ||
99 | #define ZD_CR21 CTL_REG(0x0054) | ||
100 | #define ZD_CR22 CTL_REG(0x0058) | ||
101 | #define ZD_CR23 CTL_REG(0x005C) | ||
102 | #define ZD_CR24 CTL_REG(0x0060) /* CCA threshold */ | ||
103 | #define ZD_CR25 CTL_REG(0x0064) | ||
104 | #define ZD_CR26 CTL_REG(0x0068) | ||
105 | #define ZD_CR27 CTL_REG(0x006C) | ||
106 | #define ZD_CR28 CTL_REG(0x0070) | ||
107 | #define ZD_CR29 CTL_REG(0x0074) | ||
108 | #define ZD_CR30 CTL_REG(0x0078) | ||
109 | #define ZD_CR31 CTL_REG(0x007C) /* TX power control for RF in | ||
110 | * CCK mode | ||
111 | */ | ||
112 | #define ZD_CR32 CTL_REG(0x0080) | ||
113 | #define ZD_CR33 CTL_REG(0x0084) | ||
114 | #define ZD_CR34 CTL_REG(0x0088) | ||
115 | #define ZD_CR35 CTL_REG(0x008C) | ||
116 | #define ZD_CR36 CTL_REG(0x0090) | ||
117 | #define ZD_CR37 CTL_REG(0x0094) | ||
118 | #define ZD_CR38 CTL_REG(0x0098) | ||
119 | #define ZD_CR39 CTL_REG(0x009C) | ||
120 | #define ZD_CR40 CTL_REG(0x00A0) | ||
121 | #define ZD_CR41 CTL_REG(0x00A4) | ||
122 | #define ZD_CR42 CTL_REG(0x00A8) | ||
123 | #define ZD_CR43 CTL_REG(0x00AC) | ||
124 | #define ZD_CR44 CTL_REG(0x00B0) | ||
125 | #define ZD_CR45 CTL_REG(0x00B4) | ||
126 | #define ZD_CR46 CTL_REG(0x00B8) | ||
127 | #define ZD_CR47 CTL_REG(0x00BC) /* CCK baseband gain | ||
128 | * (patch value might be in EEPROM) | ||
129 | */ | ||
130 | #define ZD_CR48 CTL_REG(0x00C0) | ||
131 | #define ZD_CR49 CTL_REG(0x00C4) | ||
132 | #define ZD_CR50 CTL_REG(0x00C8) | ||
133 | #define ZD_CR51 CTL_REG(0x00CC) /* TX power control for RF in | ||
134 | * 6-36M modes | ||
135 | */ | ||
136 | #define ZD_CR52 CTL_REG(0x00D0) /* TX power control for RF in | ||
137 | * 48M mode | ||
138 | */ | ||
139 | #define ZD_CR53 CTL_REG(0x00D4) /* TX power control for RF in | ||
140 | * 54M mode | ||
141 | */ | ||
142 | #define ZD_CR54 CTL_REG(0x00D8) | ||
143 | #define ZD_CR55 CTL_REG(0x00DC) | ||
144 | #define ZD_CR56 CTL_REG(0x00E0) | ||
145 | #define ZD_CR57 CTL_REG(0x00E4) | ||
146 | #define ZD_CR58 CTL_REG(0x00E8) | ||
147 | #define ZD_CR59 CTL_REG(0x00EC) | ||
148 | #define ZD_CR60 CTL_REG(0x00F0) | ||
149 | #define ZD_CR61 CTL_REG(0x00F4) | ||
150 | #define ZD_CR62 CTL_REG(0x00F8) | ||
151 | #define ZD_CR63 CTL_REG(0x00FC) | ||
152 | #define ZD_CR64 CTL_REG(0x0100) | ||
153 | #define ZD_CR65 CTL_REG(0x0104) /* OFDM 54M calibration */ | ||
154 | #define ZD_CR66 CTL_REG(0x0108) /* OFDM 48M calibration */ | ||
155 | #define ZD_CR67 CTL_REG(0x010C) /* OFDM 36M calibration */ | ||
156 | #define ZD_CR68 CTL_REG(0x0110) /* CCK calibration */ | ||
157 | #define ZD_CR69 CTL_REG(0x0114) | ||
158 | #define ZD_CR70 CTL_REG(0x0118) | ||
159 | #define ZD_CR71 CTL_REG(0x011C) | ||
160 | #define ZD_CR72 CTL_REG(0x0120) | ||
161 | #define ZD_CR73 CTL_REG(0x0124) | ||
162 | #define ZD_CR74 CTL_REG(0x0128) | ||
163 | #define ZD_CR75 CTL_REG(0x012C) | ||
164 | #define ZD_CR76 CTL_REG(0x0130) | ||
165 | #define ZD_CR77 CTL_REG(0x0134) | ||
166 | #define ZD_CR78 CTL_REG(0x0138) | ||
167 | #define ZD_CR79 CTL_REG(0x013C) | ||
168 | #define ZD_CR80 CTL_REG(0x0140) | ||
169 | #define ZD_CR81 CTL_REG(0x0144) | ||
170 | #define ZD_CR82 CTL_REG(0x0148) | ||
171 | #define ZD_CR83 CTL_REG(0x014C) | ||
172 | #define ZD_CR84 CTL_REG(0x0150) | ||
173 | #define ZD_CR85 CTL_REG(0x0154) | ||
174 | #define ZD_CR86 CTL_REG(0x0158) | ||
175 | #define ZD_CR87 CTL_REG(0x015C) | ||
176 | #define ZD_CR88 CTL_REG(0x0160) | ||
177 | #define ZD_CR89 CTL_REG(0x0164) | ||
178 | #define ZD_CR90 CTL_REG(0x0168) | ||
179 | #define ZD_CR91 CTL_REG(0x016C) | ||
180 | #define ZD_CR92 CTL_REG(0x0170) | ||
181 | #define ZD_CR93 CTL_REG(0x0174) | ||
182 | #define ZD_CR94 CTL_REG(0x0178) | ||
183 | #define ZD_CR95 CTL_REG(0x017C) | ||
184 | #define ZD_CR96 CTL_REG(0x0180) | ||
185 | #define ZD_CR97 CTL_REG(0x0184) | ||
186 | #define ZD_CR98 CTL_REG(0x0188) | ||
187 | #define ZD_CR99 CTL_REG(0x018C) | ||
188 | #define ZD_CR100 CTL_REG(0x0190) | ||
189 | #define ZD_CR101 CTL_REG(0x0194) | ||
190 | #define ZD_CR102 CTL_REG(0x0198) | ||
191 | #define ZD_CR103 CTL_REG(0x019C) | ||
192 | #define ZD_CR104 CTL_REG(0x01A0) | ||
193 | #define ZD_CR105 CTL_REG(0x01A4) | ||
194 | #define ZD_CR106 CTL_REG(0x01A8) | ||
195 | #define ZD_CR107 CTL_REG(0x01AC) | ||
196 | #define ZD_CR108 CTL_REG(0x01B0) | ||
197 | #define ZD_CR109 CTL_REG(0x01B4) | ||
198 | #define ZD_CR110 CTL_REG(0x01B8) | ||
199 | #define ZD_CR111 CTL_REG(0x01BC) | ||
200 | #define ZD_CR112 CTL_REG(0x01C0) | ||
201 | #define ZD_CR113 CTL_REG(0x01C4) | ||
202 | #define ZD_CR114 CTL_REG(0x01C8) | ||
203 | #define ZD_CR115 CTL_REG(0x01CC) | ||
204 | #define ZD_CR116 CTL_REG(0x01D0) | ||
205 | #define ZD_CR117 CTL_REG(0x01D4) | ||
206 | #define ZD_CR118 CTL_REG(0x01D8) | ||
207 | #define ZD_CR119 CTL_REG(0x01DC) | ||
208 | #define ZD_CR120 CTL_REG(0x01E0) | ||
209 | #define ZD_CR121 CTL_REG(0x01E4) | ||
210 | #define ZD_CR122 CTL_REG(0x01E8) | ||
211 | #define ZD_CR123 CTL_REG(0x01EC) | ||
212 | #define ZD_CR124 CTL_REG(0x01F0) | ||
213 | #define ZD_CR125 CTL_REG(0x01F4) | ||
214 | #define ZD_CR126 CTL_REG(0x01F8) | ||
215 | #define ZD_CR127 CTL_REG(0x01FC) | ||
216 | #define ZD_CR128 CTL_REG(0x0200) | ||
217 | #define ZD_CR129 CTL_REG(0x0204) | ||
218 | #define ZD_CR130 CTL_REG(0x0208) | ||
219 | #define ZD_CR131 CTL_REG(0x020C) | ||
220 | #define ZD_CR132 CTL_REG(0x0210) | ||
221 | #define ZD_CR133 CTL_REG(0x0214) | ||
222 | #define ZD_CR134 CTL_REG(0x0218) | ||
223 | #define ZD_CR135 CTL_REG(0x021C) | ||
224 | #define ZD_CR136 CTL_REG(0x0220) | ||
225 | #define ZD_CR137 CTL_REG(0x0224) | ||
226 | #define ZD_CR138 CTL_REG(0x0228) | ||
227 | #define ZD_CR139 CTL_REG(0x022C) | ||
228 | #define ZD_CR140 CTL_REG(0x0230) | ||
229 | #define ZD_CR141 CTL_REG(0x0234) | ||
230 | #define ZD_CR142 CTL_REG(0x0238) | ||
231 | #define ZD_CR143 CTL_REG(0x023C) | ||
232 | #define ZD_CR144 CTL_REG(0x0240) | ||
233 | #define ZD_CR145 CTL_REG(0x0244) | ||
234 | #define ZD_CR146 CTL_REG(0x0248) | ||
235 | #define ZD_CR147 CTL_REG(0x024C) | ||
236 | #define ZD_CR148 CTL_REG(0x0250) | ||
237 | #define ZD_CR149 CTL_REG(0x0254) | ||
238 | #define ZD_CR150 CTL_REG(0x0258) | ||
239 | #define ZD_CR151 CTL_REG(0x025C) | ||
240 | #define ZD_CR152 CTL_REG(0x0260) | ||
241 | #define ZD_CR153 CTL_REG(0x0264) | ||
242 | #define ZD_CR154 CTL_REG(0x0268) | ||
243 | #define ZD_CR155 CTL_REG(0x026C) | ||
244 | #define ZD_CR156 CTL_REG(0x0270) | ||
245 | #define ZD_CR157 CTL_REG(0x0274) | ||
246 | #define ZD_CR158 CTL_REG(0x0278) | ||
247 | #define ZD_CR159 CTL_REG(0x027C) | ||
248 | #define ZD_CR160 CTL_REG(0x0280) | ||
249 | #define ZD_CR161 CTL_REG(0x0284) | ||
250 | #define ZD_CR162 CTL_REG(0x0288) | ||
251 | #define ZD_CR163 CTL_REG(0x028C) | ||
252 | #define ZD_CR164 CTL_REG(0x0290) | ||
253 | #define ZD_CR165 CTL_REG(0x0294) | ||
254 | #define ZD_CR166 CTL_REG(0x0298) | ||
255 | #define ZD_CR167 CTL_REG(0x029C) | ||
256 | #define ZD_CR168 CTL_REG(0x02A0) | ||
257 | #define ZD_CR169 CTL_REG(0x02A4) | ||
258 | #define ZD_CR170 CTL_REG(0x02A8) | ||
259 | #define ZD_CR171 CTL_REG(0x02AC) | ||
260 | #define ZD_CR172 CTL_REG(0x02B0) | ||
261 | #define ZD_CR173 CTL_REG(0x02B4) | ||
262 | #define ZD_CR174 CTL_REG(0x02B8) | ||
263 | #define ZD_CR175 CTL_REG(0x02BC) | ||
264 | #define ZD_CR176 CTL_REG(0x02C0) | ||
265 | #define ZD_CR177 CTL_REG(0x02C4) | ||
266 | #define ZD_CR178 CTL_REG(0x02C8) | ||
267 | #define ZD_CR179 CTL_REG(0x02CC) | ||
268 | #define ZD_CR180 CTL_REG(0x02D0) | ||
269 | #define ZD_CR181 CTL_REG(0x02D4) | ||
270 | #define ZD_CR182 CTL_REG(0x02D8) | ||
271 | #define ZD_CR183 CTL_REG(0x02DC) | ||
272 | #define ZD_CR184 CTL_REG(0x02E0) | ||
273 | #define ZD_CR185 CTL_REG(0x02E4) | ||
274 | #define ZD_CR186 CTL_REG(0x02E8) | ||
275 | #define ZD_CR187 CTL_REG(0x02EC) | ||
276 | #define ZD_CR188 CTL_REG(0x02F0) | ||
277 | #define ZD_CR189 CTL_REG(0x02F4) | ||
278 | #define ZD_CR190 CTL_REG(0x02F8) | ||
279 | #define ZD_CR191 CTL_REG(0x02FC) | ||
280 | #define ZD_CR192 CTL_REG(0x0300) | ||
281 | #define ZD_CR193 CTL_REG(0x0304) | ||
282 | #define ZD_CR194 CTL_REG(0x0308) | ||
283 | #define ZD_CR195 CTL_REG(0x030C) | ||
284 | #define ZD_CR196 CTL_REG(0x0310) | ||
285 | #define ZD_CR197 CTL_REG(0x0314) | ||
286 | #define ZD_CR198 CTL_REG(0x0318) | ||
287 | #define ZD_CR199 CTL_REG(0x031C) | ||
288 | #define ZD_CR200 CTL_REG(0x0320) | ||
289 | #define ZD_CR201 CTL_REG(0x0324) | ||
290 | #define ZD_CR202 CTL_REG(0x0328) | ||
291 | #define ZD_CR203 CTL_REG(0x032C) /* I2C bus template value & flash | ||
292 | * control | ||
293 | */ | ||
294 | #define ZD_CR204 CTL_REG(0x0330) | ||
295 | #define ZD_CR205 CTL_REG(0x0334) | ||
296 | #define ZD_CR206 CTL_REG(0x0338) | ||
297 | #define ZD_CR207 CTL_REG(0x033C) | ||
298 | #define ZD_CR208 CTL_REG(0x0340) | ||
299 | #define ZD_CR209 CTL_REG(0x0344) | ||
300 | #define ZD_CR210 CTL_REG(0x0348) | ||
301 | #define ZD_CR211 CTL_REG(0x034C) | ||
302 | #define ZD_CR212 CTL_REG(0x0350) | ||
303 | #define ZD_CR213 CTL_REG(0x0354) | ||
304 | #define ZD_CR214 CTL_REG(0x0358) | ||
305 | #define ZD_CR215 CTL_REG(0x035C) | ||
306 | #define ZD_CR216 CTL_REG(0x0360) | ||
307 | #define ZD_CR217 CTL_REG(0x0364) | ||
308 | #define ZD_CR218 CTL_REG(0x0368) | ||
309 | #define ZD_CR219 CTL_REG(0x036C) | ||
310 | #define ZD_CR220 CTL_REG(0x0370) | ||
311 | #define ZD_CR221 CTL_REG(0x0374) | ||
312 | #define ZD_CR222 CTL_REG(0x0378) | ||
313 | #define ZD_CR223 CTL_REG(0x037C) | ||
314 | #define ZD_CR224 CTL_REG(0x0380) | ||
315 | #define ZD_CR225 CTL_REG(0x0384) | ||
316 | #define ZD_CR226 CTL_REG(0x0388) | ||
317 | #define ZD_CR227 CTL_REG(0x038C) | ||
318 | #define ZD_CR228 CTL_REG(0x0390) | ||
319 | #define ZD_CR229 CTL_REG(0x0394) | ||
320 | #define ZD_CR230 CTL_REG(0x0398) | ||
321 | #define ZD_CR231 CTL_REG(0x039C) | ||
322 | #define ZD_CR232 CTL_REG(0x03A0) | ||
323 | #define ZD_CR233 CTL_REG(0x03A4) | ||
324 | #define ZD_CR234 CTL_REG(0x03A8) | ||
325 | #define ZD_CR235 CTL_REG(0x03AC) | ||
326 | #define ZD_CR236 CTL_REG(0x03B0) | ||
327 | |||
328 | #define ZD_CR240 CTL_REG(0x03C0) | ||
329 | /* bit 7: host-controlled RF register writes | ||
330 | * ZD_CR241-ZD_CR245: for hardware controlled writing of RF bits, not needed for | ||
331 | * USB | ||
332 | */ | ||
333 | #define ZD_CR241 CTL_REG(0x03C4) | ||
334 | #define ZD_CR242 CTL_REG(0x03C8) | ||
335 | #define ZD_CR243 CTL_REG(0x03CC) | ||
336 | #define ZD_CR244 CTL_REG(0x03D0) | ||
337 | #define ZD_CR245 CTL_REG(0x03D4) | ||
338 | |||
339 | #define ZD_CR251 CTL_REG(0x03EC) /* only used for activation and | ||
340 | * deactivation of Airoha RFs AL2230 | ||
341 | * and AL7230B | ||
342 | */ | ||
343 | #define ZD_CR252 CTL_REG(0x03F0) | ||
344 | #define ZD_CR253 CTL_REG(0x03F4) | ||
345 | #define ZD_CR254 CTL_REG(0x03F8) | ||
346 | #define ZD_CR255 CTL_REG(0x03FC) | ||
347 | |||
348 | #define CR_MAX_PHY_REG 255 | ||
349 | |||
350 | /* Taken from the ZYDAS driver, not all of them are relevant for the ZD1211 | ||
351 | * driver. | ||
352 | */ | ||
353 | |||
354 | #define CR_RF_IF_CLK CTL_REG(0x0400) | ||
355 | #define CR_RF_IF_DATA CTL_REG(0x0404) | ||
356 | #define CR_PE1_PE2 CTL_REG(0x0408) | ||
357 | #define CR_PE2_DLY CTL_REG(0x040C) | ||
358 | #define CR_LE1 CTL_REG(0x0410) | ||
359 | #define CR_LE2 CTL_REG(0x0414) | ||
360 | /* Seems to enable/disable GPI (General Purpose IO?) */ | ||
361 | #define CR_GPI_EN CTL_REG(0x0418) | ||
362 | #define CR_RADIO_PD CTL_REG(0x042C) | ||
363 | #define CR_RF2948_PD CTL_REG(0x042C) | ||
364 | #define CR_ENABLE_PS_MANUAL_AGC CTL_REG(0x043C) | ||
365 | #define CR_CONFIG_PHILIPS CTL_REG(0x0440) | ||
366 | #define CR_SA2400_SER_AP CTL_REG(0x0444) | ||
367 | #define CR_I2C_WRITE CTL_REG(0x0444) | ||
368 | #define CR_SA2400_SER_RP CTL_REG(0x0448) | ||
369 | #define CR_RADIO_PE CTL_REG(0x0458) | ||
370 | #define CR_RST_BUS_MASTER CTL_REG(0x045C) | ||
371 | #define CR_RFCFG CTL_REG(0x0464) | ||
372 | #define CR_HSTSCHG CTL_REG(0x046C) | ||
373 | #define CR_PHY_ON CTL_REG(0x0474) | ||
374 | #define CR_RX_DELAY CTL_REG(0x0478) | ||
375 | #define CR_RX_PE_DELAY CTL_REG(0x047C) | ||
376 | #define CR_GPIO_1 CTL_REG(0x0490) | ||
377 | #define CR_GPIO_2 CTL_REG(0x0494) | ||
378 | #define CR_EncryBufMux CTL_REG(0x04A8) | ||
379 | #define CR_PS_CTRL CTL_REG(0x0500) | ||
380 | #define CR_ADDA_PWR_DWN CTL_REG(0x0504) | ||
381 | #define CR_ADDA_MBIAS_WARMTIME CTL_REG(0x0508) | ||
382 | #define CR_MAC_PS_STATE CTL_REG(0x050C) | ||
383 | |||
384 | #define CR_INTERRUPT CTL_REG(0x0510) | ||
385 | #define INT_TX_COMPLETE (1 << 0) | ||
386 | #define INT_RX_COMPLETE (1 << 1) | ||
387 | #define INT_RETRY_FAIL (1 << 2) | ||
388 | #define INT_WAKEUP (1 << 3) | ||
389 | #define INT_DTIM_NOTIFY (1 << 5) | ||
390 | #define INT_CFG_NEXT_BCN (1 << 6) | ||
391 | #define INT_BUS_ABORT (1 << 7) | ||
392 | #define INT_TX_FIFO_READY (1 << 8) | ||
393 | #define INT_UART (1 << 9) | ||
394 | #define INT_TX_COMPLETE_EN (1 << 16) | ||
395 | #define INT_RX_COMPLETE_EN (1 << 17) | ||
396 | #define INT_RETRY_FAIL_EN (1 << 18) | ||
397 | #define INT_WAKEUP_EN (1 << 19) | ||
398 | #define INT_DTIM_NOTIFY_EN (1 << 21) | ||
399 | #define INT_CFG_NEXT_BCN_EN (1 << 22) | ||
400 | #define INT_BUS_ABORT_EN (1 << 23) | ||
401 | #define INT_TX_FIFO_READY_EN (1 << 24) | ||
402 | #define INT_UART_EN (1 << 25) | ||
403 | |||
404 | #define CR_TSF_LOW_PART CTL_REG(0x0514) | ||
405 | #define CR_TSF_HIGH_PART CTL_REG(0x0518) | ||
406 | |||
407 | /* Following three values are in time units (1024us) | ||
408 | * Following condition must be met: | ||
409 | * atim < tbtt < bcn | ||
410 | */ | ||
411 | #define CR_ATIM_WND_PERIOD CTL_REG(0x051C) | ||
412 | #define CR_BCN_INTERVAL CTL_REG(0x0520) | ||
413 | #define CR_PRE_TBTT CTL_REG(0x0524) | ||
414 | /* in units of TU(1024us) */ | ||
415 | |||
416 | /* for UART support */ | ||
417 | #define CR_UART_RBR_THR_DLL CTL_REG(0x0540) | ||
418 | #define CR_UART_DLM_IER CTL_REG(0x0544) | ||
419 | #define CR_UART_IIR_FCR CTL_REG(0x0548) | ||
420 | #define CR_UART_LCR CTL_REG(0x054c) | ||
421 | #define CR_UART_MCR CTL_REG(0x0550) | ||
422 | #define CR_UART_LSR CTL_REG(0x0554) | ||
423 | #define CR_UART_MSR CTL_REG(0x0558) | ||
424 | #define CR_UART_ECR CTL_REG(0x055c) | ||
425 | #define CR_UART_STATUS CTL_REG(0x0560) | ||
426 | |||
427 | #define CR_PCI_TX_ADDR_P1 CTL_REG(0x0600) | ||
428 | #define CR_PCI_TX_AddR_P2 CTL_REG(0x0604) | ||
429 | #define CR_PCI_RX_AddR_P1 CTL_REG(0x0608) | ||
430 | #define CR_PCI_RX_AddR_P2 CTL_REG(0x060C) | ||
431 | |||
432 | /* must be overwritten if custom MAC address will be used */ | ||
433 | #define CR_MAC_ADDR_P1 CTL_REG(0x0610) | ||
434 | #define CR_MAC_ADDR_P2 CTL_REG(0x0614) | ||
435 | #define CR_BSSID_P1 CTL_REG(0x0618) | ||
436 | #define CR_BSSID_P2 CTL_REG(0x061C) | ||
437 | #define CR_BCN_PLCP_CFG CTL_REG(0x0620) | ||
438 | |||
439 | /* Group hash table for filtering incoming packets. | ||
440 | * | ||
441 | * The group hash table is 64 bit large and split over two parts. The first | ||
442 | * part is the lower part. The upper 6 bits of the last byte of the target | ||
443 | * address are used as index. Packets are received if the hash table bit is | ||
444 | * set. This is used for multicast handling, but for broadcasts (address | ||
445 | * ff:ff:ff:ff:ff:ff) the highest bit in the second table must also be set. | ||
446 | */ | ||
447 | #define CR_GROUP_HASH_P1 CTL_REG(0x0624) | ||
448 | #define CR_GROUP_HASH_P2 CTL_REG(0x0628) | ||
449 | |||
450 | #define CR_RX_TIMEOUT CTL_REG(0x062C) | ||
451 | |||
452 | /* Basic rates supported by the BSS. When producing ACK or CTS messages, the | ||
453 | * device will use a rate in this table that is less than or equal to the rate | ||
454 | * of the incoming frame which prompted the response. */ | ||
455 | #define CR_BASIC_RATE_TBL CTL_REG(0x0630) | ||
456 | #define CR_RATE_1M (1 << 0) /* 802.11b */ | ||
457 | #define CR_RATE_2M (1 << 1) /* 802.11b */ | ||
458 | #define CR_RATE_5_5M (1 << 2) /* 802.11b */ | ||
459 | #define CR_RATE_11M (1 << 3) /* 802.11b */ | ||
460 | #define CR_RATE_6M (1 << 8) /* 802.11g */ | ||
461 | #define CR_RATE_9M (1 << 9) /* 802.11g */ | ||
462 | #define CR_RATE_12M (1 << 10) /* 802.11g */ | ||
463 | #define CR_RATE_18M (1 << 11) /* 802.11g */ | ||
464 | #define CR_RATE_24M (1 << 12) /* 802.11g */ | ||
465 | #define CR_RATE_36M (1 << 13) /* 802.11g */ | ||
466 | #define CR_RATE_48M (1 << 14) /* 802.11g */ | ||
467 | #define CR_RATE_54M (1 << 15) /* 802.11g */ | ||
468 | #define CR_RATES_80211G 0xff00 | ||
469 | #define CR_RATES_80211B 0x000f | ||
470 | |||
471 | /* Mandatory rates required in the BSS. When producing ACK or CTS messages, if | ||
472 | * the device could not find an appropriate rate in CR_BASIC_RATE_TBL, it will | ||
473 | * look for a rate in this table that is less than or equal to the rate of | ||
474 | * the incoming frame. */ | ||
475 | #define CR_MANDATORY_RATE_TBL CTL_REG(0x0634) | ||
476 | #define CR_RTS_CTS_RATE CTL_REG(0x0638) | ||
477 | |||
478 | /* These are all bit indexes in CR_RTS_CTS_RATE, so remember to shift. */ | ||
479 | #define RTSCTS_SH_RTS_RATE 0 | ||
480 | #define RTSCTS_SH_EXP_CTS_RATE 4 | ||
481 | #define RTSCTS_SH_RTS_MOD_TYPE 8 | ||
482 | #define RTSCTS_SH_RTS_PMB_TYPE 9 | ||
483 | #define RTSCTS_SH_CTS_RATE 16 | ||
484 | #define RTSCTS_SH_CTS_MOD_TYPE 24 | ||
485 | #define RTSCTS_SH_CTS_PMB_TYPE 25 | ||
486 | |||
487 | #define CR_WEP_PROTECT CTL_REG(0x063C) | ||
488 | #define CR_RX_THRESHOLD CTL_REG(0x0640) | ||
489 | |||
490 | /* register for controlling the LEDS */ | ||
491 | #define CR_LED CTL_REG(0x0644) | ||
492 | /* masks for controlling LEDs */ | ||
493 | #define LED1 (1 << 8) | ||
494 | #define LED2 (1 << 9) | ||
495 | #define LED_SW (1 << 10) | ||
496 | |||
497 | /* Seems to indicate that the configuration is over. | ||
498 | */ | ||
499 | #define CR_AFTER_PNP CTL_REG(0x0648) | ||
500 | #define CR_ACK_TIME_80211 CTL_REG(0x0658) | ||
501 | |||
502 | #define CR_RX_OFFSET CTL_REG(0x065c) | ||
503 | |||
504 | #define CR_BCN_LENGTH CTL_REG(0x0664) | ||
505 | #define CR_PHY_DELAY CTL_REG(0x066C) | ||
506 | #define CR_BCN_FIFO CTL_REG(0x0670) | ||
507 | #define CR_SNIFFER_ON CTL_REG(0x0674) | ||
508 | |||
509 | #define CR_ENCRYPTION_TYPE CTL_REG(0x0678) | ||
510 | #define NO_WEP 0 | ||
511 | #define WEP64 1 | ||
512 | #define WEP128 5 | ||
513 | #define WEP256 6 | ||
514 | #define ENC_SNIFFER 8 | ||
515 | |||
516 | #define CR_ZD1211_RETRY_MAX CTL_REG(0x067C) | ||
517 | |||
518 | #define CR_REG1 CTL_REG(0x0680) | ||
519 | /* Setting the bit UNLOCK_PHY_REGS disallows the write access to physical | ||
520 | * registers, so one could argue it is a LOCK bit. But calling it | ||
521 | * LOCK_PHY_REGS makes it confusing. | ||
522 | */ | ||
523 | #define UNLOCK_PHY_REGS (1 << 7) | ||
524 | |||
525 | #define CR_DEVICE_STATE CTL_REG(0x0684) | ||
526 | #define CR_UNDERRUN_CNT CTL_REG(0x0688) | ||
527 | |||
528 | #define CR_RX_FILTER CTL_REG(0x068c) | ||
529 | #define RX_FILTER_ASSOC_REQUEST (1 << 0) | ||
530 | #define RX_FILTER_ASSOC_RESPONSE (1 << 1) | ||
531 | #define RX_FILTER_REASSOC_REQUEST (1 << 2) | ||
532 | #define RX_FILTER_REASSOC_RESPONSE (1 << 3) | ||
533 | #define RX_FILTER_PROBE_REQUEST (1 << 4) | ||
534 | #define RX_FILTER_PROBE_RESPONSE (1 << 5) | ||
535 | /* bits 6 and 7 reserved */ | ||
536 | #define RX_FILTER_BEACON (1 << 8) | ||
537 | #define RX_FILTER_ATIM (1 << 9) | ||
538 | #define RX_FILTER_DISASSOC (1 << 10) | ||
539 | #define RX_FILTER_AUTH (1 << 11) | ||
540 | #define RX_FILTER_DEAUTH (1 << 12) | ||
541 | #define RX_FILTER_PSPOLL (1 << 26) | ||
542 | #define RX_FILTER_RTS (1 << 27) | ||
543 | #define RX_FILTER_CTS (1 << 28) | ||
544 | #define RX_FILTER_ACK (1 << 29) | ||
545 | #define RX_FILTER_CFEND (1 << 30) | ||
546 | #define RX_FILTER_CFACK (1 << 31) | ||
547 | |||
548 | /* Enable bits for all frames you are interested in. */ | ||
549 | #define STA_RX_FILTER (RX_FILTER_ASSOC_REQUEST | RX_FILTER_ASSOC_RESPONSE | \ | ||
550 | RX_FILTER_REASSOC_REQUEST | RX_FILTER_REASSOC_RESPONSE | \ | ||
551 | RX_FILTER_PROBE_REQUEST | RX_FILTER_PROBE_RESPONSE | \ | ||
552 | (0x3 << 6) /* vendor driver sets these reserved bits */ | \ | ||
553 | RX_FILTER_BEACON | RX_FILTER_ATIM | RX_FILTER_DISASSOC | \ | ||
554 | RX_FILTER_AUTH | RX_FILTER_DEAUTH | \ | ||
555 | (0x7 << 13) /* vendor driver sets these reserved bits */ | \ | ||
556 | RX_FILTER_PSPOLL | RX_FILTER_ACK) /* 0x2400ffff */ | ||
557 | |||
558 | #define RX_FILTER_CTRL (RX_FILTER_RTS | RX_FILTER_CTS | \ | ||
559 | RX_FILTER_CFEND | RX_FILTER_CFACK) | ||
560 | |||
561 | #define BCN_MODE_AP 0x1000000 | ||
562 | #define BCN_MODE_IBSS 0x2000000 | ||
563 | |||
564 | /* Monitor mode sets filter to 0xfffff */ | ||
565 | |||
566 | #define CR_ACK_TIMEOUT_EXT CTL_REG(0x0690) | ||
567 | #define CR_BCN_FIFO_SEMAPHORE CTL_REG(0x0694) | ||
568 | |||
569 | #define CR_IFS_VALUE CTL_REG(0x0698) | ||
570 | #define IFS_VALUE_DIFS_SH 0 | ||
571 | #define IFS_VALUE_EIFS_SH 12 | ||
572 | #define IFS_VALUE_SIFS_SH 24 | ||
573 | #define IFS_VALUE_DEFAULT (( 50 << IFS_VALUE_DIFS_SH) | \ | ||
574 | (1148 << IFS_VALUE_EIFS_SH) | \ | ||
575 | ( 10 << IFS_VALUE_SIFS_SH)) | ||
576 | |||
577 | #define CR_RX_TIME_OUT CTL_REG(0x069C) | ||
578 | #define CR_TOTAL_RX_FRM CTL_REG(0x06A0) | ||
579 | #define CR_CRC32_CNT CTL_REG(0x06A4) | ||
580 | #define CR_CRC16_CNT CTL_REG(0x06A8) | ||
581 | #define CR_DECRYPTION_ERR_UNI CTL_REG(0x06AC) | ||
582 | #define CR_RX_FIFO_OVERRUN CTL_REG(0x06B0) | ||
583 | |||
584 | #define CR_DECRYPTION_ERR_MUL CTL_REG(0x06BC) | ||
585 | |||
586 | #define CR_NAV_CNT CTL_REG(0x06C4) | ||
587 | #define CR_NAV_CCA CTL_REG(0x06C8) | ||
588 | #define CR_RETRY_CNT CTL_REG(0x06CC) | ||
589 | |||
590 | #define CR_READ_TCB_ADDR CTL_REG(0x06E8) | ||
591 | #define CR_READ_RFD_ADDR CTL_REG(0x06EC) | ||
592 | #define CR_CWMIN_CWMAX CTL_REG(0x06F0) | ||
593 | #define CR_TOTAL_TX_FRM CTL_REG(0x06F4) | ||
594 | |||
595 | /* CAM: Continuous Access Mode (power management) */ | ||
596 | #define CR_CAM_MODE CTL_REG(0x0700) | ||
597 | #define MODE_IBSS 0x0 | ||
598 | #define MODE_AP 0x1 | ||
599 | #define MODE_STA 0x2 | ||
600 | #define MODE_AP_WDS 0x3 | ||
601 | |||
602 | #define CR_CAM_ROLL_TB_LOW CTL_REG(0x0704) | ||
603 | #define CR_CAM_ROLL_TB_HIGH CTL_REG(0x0708) | ||
604 | #define CR_CAM_ADDRESS CTL_REG(0x070C) | ||
605 | #define CR_CAM_DATA CTL_REG(0x0710) | ||
606 | |||
607 | #define CR_ROMDIR CTL_REG(0x0714) | ||
608 | |||
609 | #define CR_DECRY_ERR_FLG_LOW CTL_REG(0x0714) | ||
610 | #define CR_DECRY_ERR_FLG_HIGH CTL_REG(0x0718) | ||
611 | |||
612 | #define CR_WEPKEY0 CTL_REG(0x0720) | ||
613 | #define CR_WEPKEY1 CTL_REG(0x0724) | ||
614 | #define CR_WEPKEY2 CTL_REG(0x0728) | ||
615 | #define CR_WEPKEY3 CTL_REG(0x072C) | ||
616 | #define CR_WEPKEY4 CTL_REG(0x0730) | ||
617 | #define CR_WEPKEY5 CTL_REG(0x0734) | ||
618 | #define CR_WEPKEY6 CTL_REG(0x0738) | ||
619 | #define CR_WEPKEY7 CTL_REG(0x073C) | ||
620 | #define CR_WEPKEY8 CTL_REG(0x0740) | ||
621 | #define CR_WEPKEY9 CTL_REG(0x0744) | ||
622 | #define CR_WEPKEY10 CTL_REG(0x0748) | ||
623 | #define CR_WEPKEY11 CTL_REG(0x074C) | ||
624 | #define CR_WEPKEY12 CTL_REG(0x0750) | ||
625 | #define CR_WEPKEY13 CTL_REG(0x0754) | ||
626 | #define CR_WEPKEY14 CTL_REG(0x0758) | ||
627 | #define CR_WEPKEY15 CTL_REG(0x075c) | ||
628 | #define CR_TKIP_MODE CTL_REG(0x0760) | ||
629 | |||
630 | #define CR_EEPROM_PROTECT0 CTL_REG(0x0758) | ||
631 | #define CR_EEPROM_PROTECT1 CTL_REG(0x075C) | ||
632 | |||
633 | #define CR_DBG_FIFO_RD CTL_REG(0x0800) | ||
634 | #define CR_DBG_SELECT CTL_REG(0x0804) | ||
635 | #define CR_FIFO_Length CTL_REG(0x0808) | ||
636 | |||
637 | |||
638 | #define CR_RSSI_MGC CTL_REG(0x0810) | ||
639 | |||
640 | #define CR_PON CTL_REG(0x0818) | ||
641 | #define CR_RX_ON CTL_REG(0x081C) | ||
642 | #define CR_TX_ON CTL_REG(0x0820) | ||
643 | #define CR_CHIP_EN CTL_REG(0x0824) | ||
644 | #define CR_LO_SW CTL_REG(0x0828) | ||
645 | #define CR_TXRX_SW CTL_REG(0x082C) | ||
646 | #define CR_S_MD CTL_REG(0x0830) | ||
647 | |||
648 | #define CR_USB_DEBUG_PORT CTL_REG(0x0888) | ||
649 | #define CR_ZD1211B_CWIN_MAX_MIN_AC0 CTL_REG(0x0b00) | ||
650 | #define CR_ZD1211B_CWIN_MAX_MIN_AC1 CTL_REG(0x0b04) | ||
651 | #define CR_ZD1211B_CWIN_MAX_MIN_AC2 CTL_REG(0x0b08) | ||
652 | #define CR_ZD1211B_CWIN_MAX_MIN_AC3 CTL_REG(0x0b0c) | ||
653 | #define CR_ZD1211B_AIFS_CTL1 CTL_REG(0x0b10) | ||
654 | #define CR_ZD1211B_AIFS_CTL2 CTL_REG(0x0b14) | ||
655 | #define CR_ZD1211B_TXOP CTL_REG(0x0b20) | ||
656 | #define CR_ZD1211B_RETRY_MAX CTL_REG(0x0b28) | ||
657 | |||
658 | /* Value for CR_ZD1211_RETRY_MAX & CR_ZD1211B_RETRY_MAX. Vendor driver uses 2, | ||
659 | * we use 0. The first rate is tried (count+2), then all next rates are tried | ||
660 | * twice, until 1 Mbits is tried. */ | ||
661 | #define ZD1211_RETRY_COUNT 0 | ||
662 | #define ZD1211B_RETRY_COUNT \ | ||
663 | (ZD1211_RETRY_COUNT << 0)| \ | ||
664 | (ZD1211_RETRY_COUNT << 8)| \ | ||
665 | (ZD1211_RETRY_COUNT << 16)| \ | ||
666 | (ZD1211_RETRY_COUNT << 24) | ||
667 | |||
668 | /* Used to detect PLL lock */ | ||
669 | #define UW2453_INTR_REG ((zd_addr_t)0x85c1) | ||
670 | |||
671 | #define CWIN_SIZE 0x007f043f | ||
672 | |||
673 | |||
674 | #define HWINT_ENABLED \ | ||
675 | (INT_TX_COMPLETE_EN| \ | ||
676 | INT_RX_COMPLETE_EN| \ | ||
677 | INT_RETRY_FAIL_EN| \ | ||
678 | INT_WAKEUP_EN| \ | ||
679 | INT_CFG_NEXT_BCN_EN) | ||
680 | |||
681 | #define HWINT_DISABLED 0 | ||
682 | |||
683 | #define E2P_PWR_INT_GUARD 8 | ||
684 | #define E2P_CHANNEL_COUNT 14 | ||
685 | |||
686 | /* If you compare this addresses with the ZYDAS orignal driver, please notify | ||
687 | * that we use word mapping for the EEPROM. | ||
688 | */ | ||
689 | |||
690 | /* | ||
691 | * Upper 16 bit contains the regulatory domain. | ||
692 | */ | ||
693 | #define E2P_SUBID E2P_DATA(0x00) | ||
694 | #define E2P_POD E2P_DATA(0x02) | ||
695 | #define E2P_MAC_ADDR_P1 E2P_DATA(0x04) | ||
696 | #define E2P_MAC_ADDR_P2 E2P_DATA(0x06) | ||
697 | #define E2P_PWR_CAL_VALUE1 E2P_DATA(0x08) | ||
698 | #define E2P_PWR_CAL_VALUE2 E2P_DATA(0x0a) | ||
699 | #define E2P_PWR_CAL_VALUE3 E2P_DATA(0x0c) | ||
700 | #define E2P_PWR_CAL_VALUE4 E2P_DATA(0x0e) | ||
701 | #define E2P_PWR_INT_VALUE1 E2P_DATA(0x10) | ||
702 | #define E2P_PWR_INT_VALUE2 E2P_DATA(0x12) | ||
703 | #define E2P_PWR_INT_VALUE3 E2P_DATA(0x14) | ||
704 | #define E2P_PWR_INT_VALUE4 E2P_DATA(0x16) | ||
705 | |||
706 | /* Contains a bit for each allowed channel. It gives for Europe (ETSI 0x30) | ||
707 | * also only 11 channels. */ | ||
708 | #define E2P_ALLOWED_CHANNEL E2P_DATA(0x18) | ||
709 | |||
710 | #define E2P_DEVICE_VER E2P_DATA(0x20) | ||
711 | #define E2P_PHY_REG E2P_DATA(0x25) | ||
712 | #define E2P_36M_CAL_VALUE1 E2P_DATA(0x28) | ||
713 | #define E2P_36M_CAL_VALUE2 E2P_DATA(0x2a) | ||
714 | #define E2P_36M_CAL_VALUE3 E2P_DATA(0x2c) | ||
715 | #define E2P_36M_CAL_VALUE4 E2P_DATA(0x2e) | ||
716 | #define E2P_11A_INT_VALUE1 E2P_DATA(0x30) | ||
717 | #define E2P_11A_INT_VALUE2 E2P_DATA(0x32) | ||
718 | #define E2P_11A_INT_VALUE3 E2P_DATA(0x34) | ||
719 | #define E2P_11A_INT_VALUE4 E2P_DATA(0x36) | ||
720 | #define E2P_48M_CAL_VALUE1 E2P_DATA(0x38) | ||
721 | #define E2P_48M_CAL_VALUE2 E2P_DATA(0x3a) | ||
722 | #define E2P_48M_CAL_VALUE3 E2P_DATA(0x3c) | ||
723 | #define E2P_48M_CAL_VALUE4 E2P_DATA(0x3e) | ||
724 | #define E2P_48M_INT_VALUE1 E2P_DATA(0x40) | ||
725 | #define E2P_48M_INT_VALUE2 E2P_DATA(0x42) | ||
726 | #define E2P_48M_INT_VALUE3 E2P_DATA(0x44) | ||
727 | #define E2P_48M_INT_VALUE4 E2P_DATA(0x46) | ||
728 | #define E2P_54M_CAL_VALUE1 E2P_DATA(0x48) /* ??? */ | ||
729 | #define E2P_54M_CAL_VALUE2 E2P_DATA(0x4a) | ||
730 | #define E2P_54M_CAL_VALUE3 E2P_DATA(0x4c) | ||
731 | #define E2P_54M_CAL_VALUE4 E2P_DATA(0x4e) | ||
732 | #define E2P_54M_INT_VALUE1 E2P_DATA(0x50) | ||
733 | #define E2P_54M_INT_VALUE2 E2P_DATA(0x52) | ||
734 | #define E2P_54M_INT_VALUE3 E2P_DATA(0x54) | ||
735 | #define E2P_54M_INT_VALUE4 E2P_DATA(0x56) | ||
736 | |||
737 | /* This word contains the base address of the FW_REG_ registers below */ | ||
738 | #define FWRAW_REGS_ADDR FWRAW_DATA(0x1d) | ||
739 | |||
740 | /* All 16 bit values, offset from the address in FWRAW_REGS_ADDR */ | ||
741 | enum { | ||
742 | FW_REG_FIRMWARE_VER = 0, | ||
743 | /* non-zero if USB high speed connection */ | ||
744 | FW_REG_USB_SPEED = 1, | ||
745 | FW_REG_FIX_TX_RATE = 2, | ||
746 | /* Seems to be able to control LEDs over the firmware */ | ||
747 | FW_REG_LED_LINK_STATUS = 3, | ||
748 | FW_REG_SOFT_RESET = 4, | ||
749 | FW_REG_FLASH_CHK = 5, | ||
750 | }; | ||
751 | |||
752 | /* Values for FW_LINK_STATUS */ | ||
753 | #define FW_LINK_OFF 0x0 | ||
754 | #define FW_LINK_TX 0x1 | ||
755 | /* 0x2 - link led on? */ | ||
756 | |||
757 | enum { | ||
758 | /* indices for ofdm_cal_values */ | ||
759 | OFDM_36M_INDEX = 0, | ||
760 | OFDM_48M_INDEX = 1, | ||
761 | OFDM_54M_INDEX = 2, | ||
762 | }; | ||
763 | |||
764 | struct zd_chip { | ||
765 | struct zd_usb usb; | ||
766 | struct zd_rf rf; | ||
767 | struct mutex mutex; | ||
768 | /* Base address of FW_REG_ registers */ | ||
769 | zd_addr_t fw_regs_base; | ||
770 | /* EepSetPoint in the vendor driver */ | ||
771 | u8 pwr_cal_values[E2P_CHANNEL_COUNT]; | ||
772 | /* integration values in the vendor driver */ | ||
773 | u8 pwr_int_values[E2P_CHANNEL_COUNT]; | ||
774 | /* SetPointOFDM in the vendor driver */ | ||
775 | u8 ofdm_cal_values[3][E2P_CHANNEL_COUNT]; | ||
776 | u16 link_led; | ||
777 | unsigned int pa_type:4, | ||
778 | patch_cck_gain:1, patch_cr157:1, patch_6m_band_edge:1, | ||
779 | new_phy_layout:1, al2230s_bit:1, | ||
780 | supports_tx_led:1; | ||
781 | }; | ||
782 | |||
783 | static inline struct zd_chip *zd_usb_to_chip(struct zd_usb *usb) | ||
784 | { | ||
785 | return container_of(usb, struct zd_chip, usb); | ||
786 | } | ||
787 | |||
788 | static inline struct zd_chip *zd_rf_to_chip(struct zd_rf *rf) | ||
789 | { | ||
790 | return container_of(rf, struct zd_chip, rf); | ||
791 | } | ||
792 | |||
793 | #define zd_chip_dev(chip) (&(chip)->usb.intf->dev) | ||
794 | |||
795 | void zd_chip_init(struct zd_chip *chip, | ||
796 | struct ieee80211_hw *hw, | ||
797 | struct usb_interface *intf); | ||
798 | void zd_chip_clear(struct zd_chip *chip); | ||
799 | int zd_chip_read_mac_addr_fw(struct zd_chip *chip, u8 *addr); | ||
800 | int zd_chip_init_hw(struct zd_chip *chip); | ||
801 | int zd_chip_reset(struct zd_chip *chip); | ||
802 | |||
803 | static inline int zd_chip_is_zd1211b(struct zd_chip *chip) | ||
804 | { | ||
805 | return chip->usb.is_zd1211b; | ||
806 | } | ||
807 | |||
808 | static inline int zd_ioread16v_locked(struct zd_chip *chip, u16 *values, | ||
809 | const zd_addr_t *addresses, | ||
810 | unsigned int count) | ||
811 | { | ||
812 | ZD_ASSERT(mutex_is_locked(&chip->mutex)); | ||
813 | return zd_usb_ioread16v(&chip->usb, values, addresses, count); | ||
814 | } | ||
815 | |||
816 | static inline int zd_ioread16_locked(struct zd_chip *chip, u16 *value, | ||
817 | const zd_addr_t addr) | ||
818 | { | ||
819 | ZD_ASSERT(mutex_is_locked(&chip->mutex)); | ||
820 | return zd_usb_ioread16(&chip->usb, value, addr); | ||
821 | } | ||
822 | |||
823 | int zd_ioread32v_locked(struct zd_chip *chip, u32 *values, | ||
824 | const zd_addr_t *addresses, unsigned int count); | ||
825 | |||
826 | static inline int zd_ioread32_locked(struct zd_chip *chip, u32 *value, | ||
827 | const zd_addr_t addr) | ||
828 | { | ||
829 | return zd_ioread32v_locked(chip, value, &addr, 1); | ||
830 | } | ||
831 | |||
832 | static inline int zd_iowrite16_locked(struct zd_chip *chip, u16 value, | ||
833 | zd_addr_t addr) | ||
834 | { | ||
835 | struct zd_ioreq16 ioreq; | ||
836 | |||
837 | ZD_ASSERT(mutex_is_locked(&chip->mutex)); | ||
838 | ioreq.addr = addr; | ||
839 | ioreq.value = value; | ||
840 | |||
841 | return zd_usb_iowrite16v(&chip->usb, &ioreq, 1); | ||
842 | } | ||
843 | |||
844 | int zd_iowrite16a_locked(struct zd_chip *chip, | ||
845 | const struct zd_ioreq16 *ioreqs, unsigned int count); | ||
846 | |||
847 | int _zd_iowrite32v_locked(struct zd_chip *chip, const struct zd_ioreq32 *ioreqs, | ||
848 | unsigned int count); | ||
849 | |||
850 | static inline int zd_iowrite32_locked(struct zd_chip *chip, u32 value, | ||
851 | zd_addr_t addr) | ||
852 | { | ||
853 | struct zd_ioreq32 ioreq; | ||
854 | |||
855 | ioreq.addr = addr; | ||
856 | ioreq.value = value; | ||
857 | |||
858 | return _zd_iowrite32v_locked(chip, &ioreq, 1); | ||
859 | } | ||
860 | |||
861 | int zd_iowrite32a_locked(struct zd_chip *chip, | ||
862 | const struct zd_ioreq32 *ioreqs, unsigned int count); | ||
863 | |||
864 | static inline int zd_rfwrite_locked(struct zd_chip *chip, u32 value, u8 bits) | ||
865 | { | ||
866 | ZD_ASSERT(mutex_is_locked(&chip->mutex)); | ||
867 | return zd_usb_rfwrite(&chip->usb, value, bits); | ||
868 | } | ||
869 | |||
870 | int zd_rfwrite_cr_locked(struct zd_chip *chip, u32 value); | ||
871 | |||
872 | int zd_rfwritev_locked(struct zd_chip *chip, | ||
873 | const u32* values, unsigned int count, u8 bits); | ||
874 | int zd_rfwritev_cr_locked(struct zd_chip *chip, | ||
875 | const u32* values, unsigned int count); | ||
876 | |||
877 | /* Locking functions for reading and writing registers. | ||
878 | * The different parameters are intentional. | ||
879 | */ | ||
880 | int zd_ioread16(struct zd_chip *chip, zd_addr_t addr, u16 *value); | ||
881 | int zd_iowrite16(struct zd_chip *chip, zd_addr_t addr, u16 value); | ||
882 | int zd_ioread32(struct zd_chip *chip, zd_addr_t addr, u32 *value); | ||
883 | int zd_iowrite32(struct zd_chip *chip, zd_addr_t addr, u32 value); | ||
884 | int zd_ioread32v(struct zd_chip *chip, const zd_addr_t *addresses, | ||
885 | u32 *values, unsigned int count); | ||
886 | int zd_iowrite32a(struct zd_chip *chip, const struct zd_ioreq32 *ioreqs, | ||
887 | unsigned int count); | ||
888 | |||
889 | int zd_chip_set_channel(struct zd_chip *chip, u8 channel); | ||
890 | static inline u8 _zd_chip_get_channel(struct zd_chip *chip) | ||
891 | { | ||
892 | return chip->rf.channel; | ||
893 | } | ||
894 | u8 zd_chip_get_channel(struct zd_chip *chip); | ||
895 | int zd_read_regdomain(struct zd_chip *chip, u8 *regdomain); | ||
896 | int zd_write_mac_addr(struct zd_chip *chip, const u8 *mac_addr); | ||
897 | int zd_write_bssid(struct zd_chip *chip, const u8 *bssid); | ||
898 | int zd_chip_switch_radio_on(struct zd_chip *chip); | ||
899 | int zd_chip_switch_radio_off(struct zd_chip *chip); | ||
900 | int zd_chip_enable_int(struct zd_chip *chip); | ||
901 | void zd_chip_disable_int(struct zd_chip *chip); | ||
902 | int zd_chip_enable_rxtx(struct zd_chip *chip); | ||
903 | void zd_chip_disable_rxtx(struct zd_chip *chip); | ||
904 | int zd_chip_enable_hwint(struct zd_chip *chip); | ||
905 | int zd_chip_disable_hwint(struct zd_chip *chip); | ||
906 | int zd_chip_generic_patch_6m_band(struct zd_chip *chip, int channel); | ||
907 | int zd_chip_set_rts_cts_rate_locked(struct zd_chip *chip, int preamble); | ||
908 | |||
909 | static inline int zd_get_encryption_type(struct zd_chip *chip, u32 *type) | ||
910 | { | ||
911 | return zd_ioread32(chip, CR_ENCRYPTION_TYPE, type); | ||
912 | } | ||
913 | |||
914 | static inline int zd_set_encryption_type(struct zd_chip *chip, u32 type) | ||
915 | { | ||
916 | return zd_iowrite32(chip, CR_ENCRYPTION_TYPE, type); | ||
917 | } | ||
918 | |||
919 | static inline int zd_chip_get_basic_rates(struct zd_chip *chip, u16 *cr_rates) | ||
920 | { | ||
921 | return zd_ioread16(chip, CR_BASIC_RATE_TBL, cr_rates); | ||
922 | } | ||
923 | |||
924 | int zd_chip_set_basic_rates(struct zd_chip *chip, u16 cr_rates); | ||
925 | |||
926 | int zd_chip_lock_phy_regs(struct zd_chip *chip); | ||
927 | int zd_chip_unlock_phy_regs(struct zd_chip *chip); | ||
928 | |||
929 | enum led_status { | ||
930 | ZD_LED_OFF = 0, | ||
931 | ZD_LED_SCANNING = 1, | ||
932 | ZD_LED_ASSOCIATED = 2, | ||
933 | }; | ||
934 | |||
935 | int zd_chip_control_leds(struct zd_chip *chip, enum led_status status); | ||
936 | |||
937 | int zd_set_beacon_interval(struct zd_chip *chip, u16 interval, u8 dtim_period, | ||
938 | int type); | ||
939 | |||
940 | static inline int zd_get_beacon_interval(struct zd_chip *chip, u32 *interval) | ||
941 | { | ||
942 | return zd_ioread32(chip, CR_BCN_INTERVAL, interval); | ||
943 | } | ||
944 | |||
945 | struct rx_status; | ||
946 | |||
947 | u8 zd_rx_rate(const void *rx_frame, const struct rx_status *status); | ||
948 | |||
949 | struct zd_mc_hash { | ||
950 | u32 low; | ||
951 | u32 high; | ||
952 | }; | ||
953 | |||
954 | static inline void zd_mc_clear(struct zd_mc_hash *hash) | ||
955 | { | ||
956 | hash->low = 0; | ||
957 | /* The interfaces must always received broadcasts. | ||
958 | * The hash of the broadcast address ff:ff:ff:ff:ff:ff is 63. | ||
959 | */ | ||
960 | hash->high = 0x80000000; | ||
961 | } | ||
962 | |||
963 | static inline void zd_mc_add_all(struct zd_mc_hash *hash) | ||
964 | { | ||
965 | hash->low = hash->high = 0xffffffff; | ||
966 | } | ||
967 | |||
968 | static inline void zd_mc_add_addr(struct zd_mc_hash *hash, u8 *addr) | ||
969 | { | ||
970 | unsigned int i = addr[5] >> 2; | ||
971 | if (i < 32) { | ||
972 | hash->low |= 1 << i; | ||
973 | } else { | ||
974 | hash->high |= 1 << (i-32); | ||
975 | } | ||
976 | } | ||
977 | |||
978 | int zd_chip_set_multicast_hash(struct zd_chip *chip, | ||
979 | struct zd_mc_hash *hash); | ||
980 | |||
981 | u64 zd_chip_get_tsf(struct zd_chip *chip); | ||
982 | |||
983 | #endif /* _ZD_CHIP_H */ | ||
diff --git a/drivers/net/wireless/zydas/zd1211rw/zd_def.h b/drivers/net/wireless/zydas/zd1211rw/zd_def.h new file mode 100644 index 000000000000..41bd755bc135 --- /dev/null +++ b/drivers/net/wireless/zydas/zd1211rw/zd_def.h | |||
@@ -0,0 +1,69 @@ | |||
1 | /* ZD1211 USB-WLAN driver for Linux | ||
2 | * | ||
3 | * Copyright (C) 2005-2007 Ulrich Kunitz <kune@deine-taler.de> | ||
4 | * Copyright (C) 2006-2007 Daniel Drake <dsd@gentoo.org> | ||
5 | * | ||
6 | * This program is free software; you can redistribute it and/or modify | ||
7 | * it under the terms of the GNU General Public License as published by | ||
8 | * the Free Software Foundation; either version 2 of the License, or | ||
9 | * (at your option) any later version. | ||
10 | * | ||
11 | * This program is distributed in the hope that it will be useful, | ||
12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
14 | * GNU General Public License for more details. | ||
15 | * | ||
16 | * You should have received a copy of the GNU General Public License | ||
17 | * along with this program; if not, see <http://www.gnu.org/licenses/>. | ||
18 | */ | ||
19 | |||
20 | #ifndef _ZD_DEF_H | ||
21 | #define _ZD_DEF_H | ||
22 | |||
23 | #include <linux/kernel.h> | ||
24 | #include <linux/stringify.h> | ||
25 | #include <linux/device.h> | ||
26 | |||
27 | typedef u16 __nocast zd_addr_t; | ||
28 | |||
29 | #define dev_printk_f(level, dev, fmt, args...) \ | ||
30 | dev_printk(level, dev, "%s() " fmt, __func__, ##args) | ||
31 | |||
32 | #ifdef DEBUG | ||
33 | # define dev_dbg_f(dev, fmt, args...) \ | ||
34 | dev_printk_f(KERN_DEBUG, dev, fmt, ## args) | ||
35 | # define dev_dbg_f_limit(dev, fmt, args...) do { \ | ||
36 | if (net_ratelimit()) \ | ||
37 | dev_printk_f(KERN_DEBUG, dev, fmt, ## args); \ | ||
38 | } while (0) | ||
39 | # define dev_dbg_f_cond(dev, cond, fmt, args...) ({ \ | ||
40 | bool __cond = !!(cond); \ | ||
41 | if (unlikely(__cond)) \ | ||
42 | dev_printk_f(KERN_DEBUG, dev, fmt, ## args); \ | ||
43 | }) | ||
44 | #else | ||
45 | # define dev_dbg_f(dev, fmt, args...) do { (void)(dev); } while (0) | ||
46 | # define dev_dbg_f_limit(dev, fmt, args...) do { (void)(dev); } while (0) | ||
47 | # define dev_dbg_f_cond(dev, cond, fmt, args...) do { (void)(dev); } while (0) | ||
48 | #endif /* DEBUG */ | ||
49 | |||
50 | #ifdef DEBUG | ||
51 | # define ZD_ASSERT(x) \ | ||
52 | do { \ | ||
53 | if (unlikely(!(x))) { \ | ||
54 | pr_debug("%s:%d ASSERT %s VIOLATED!\n", \ | ||
55 | __FILE__, __LINE__, __stringify(x)); \ | ||
56 | dump_stack(); \ | ||
57 | } \ | ||
58 | } while (0) | ||
59 | #else | ||
60 | # define ZD_ASSERT(x) do { } while (0) | ||
61 | #endif | ||
62 | |||
63 | #ifdef DEBUG | ||
64 | # define ZD_MEMCLEAR(pointer, size) memset((pointer), 0xff, (size)) | ||
65 | #else | ||
66 | # define ZD_MEMCLEAR(pointer, size) do { } while (0) | ||
67 | #endif | ||
68 | |||
69 | #endif /* _ZD_DEF_H */ | ||
diff --git a/drivers/net/wireless/zydas/zd1211rw/zd_mac.c b/drivers/net/wireless/zydas/zd1211rw/zd_mac.c new file mode 100644 index 000000000000..e539d9b1b562 --- /dev/null +++ b/drivers/net/wireless/zydas/zd1211rw/zd_mac.c | |||
@@ -0,0 +1,1550 @@ | |||
1 | /* ZD1211 USB-WLAN driver for Linux | ||
2 | * | ||
3 | * Copyright (C) 2005-2007 Ulrich Kunitz <kune@deine-taler.de> | ||
4 | * Copyright (C) 2006-2007 Daniel Drake <dsd@gentoo.org> | ||
5 | * Copyright (C) 2006-2007 Michael Wu <flamingice@sourmilk.net> | ||
6 | * Copyright (C) 2007-2008 Luis R. Rodriguez <mcgrof@winlab.rutgers.edu> | ||
7 | * | ||
8 | * This program is free software; you can redistribute it and/or modify | ||
9 | * it under the terms of the GNU General Public License as published by | ||
10 | * the Free Software Foundation; either version 2 of the License, or | ||
11 | * (at your option) any later version. | ||
12 | * | ||
13 | * This program is distributed in the hope that it will be useful, | ||
14 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
15 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
16 | * GNU General Public License for more details. | ||
17 | * | ||
18 | * You should have received a copy of the GNU General Public License | ||
19 | * along with this program; if not, see <http://www.gnu.org/licenses/>. | ||
20 | */ | ||
21 | |||
22 | #include <linux/netdevice.h> | ||
23 | #include <linux/etherdevice.h> | ||
24 | #include <linux/slab.h> | ||
25 | #include <linux/usb.h> | ||
26 | #include <linux/jiffies.h> | ||
27 | #include <net/ieee80211_radiotap.h> | ||
28 | |||
29 | #include "zd_def.h" | ||
30 | #include "zd_chip.h" | ||
31 | #include "zd_mac.h" | ||
32 | #include "zd_rf.h" | ||
33 | |||
34 | struct zd_reg_alpha2_map { | ||
35 | u32 reg; | ||
36 | char alpha2[2]; | ||
37 | }; | ||
38 | |||
39 | static struct zd_reg_alpha2_map reg_alpha2_map[] = { | ||
40 | { ZD_REGDOMAIN_FCC, "US" }, | ||
41 | { ZD_REGDOMAIN_IC, "CA" }, | ||
42 | { ZD_REGDOMAIN_ETSI, "DE" }, /* Generic ETSI, use most restrictive */ | ||
43 | { ZD_REGDOMAIN_JAPAN, "JP" }, | ||
44 | { ZD_REGDOMAIN_JAPAN_2, "JP" }, | ||
45 | { ZD_REGDOMAIN_JAPAN_3, "JP" }, | ||
46 | { ZD_REGDOMAIN_SPAIN, "ES" }, | ||
47 | { ZD_REGDOMAIN_FRANCE, "FR" }, | ||
48 | }; | ||
49 | |||
50 | /* This table contains the hardware specific values for the modulation rates. */ | ||
51 | static const struct ieee80211_rate zd_rates[] = { | ||
52 | { .bitrate = 10, | ||
53 | .hw_value = ZD_CCK_RATE_1M, }, | ||
54 | { .bitrate = 20, | ||
55 | .hw_value = ZD_CCK_RATE_2M, | ||
56 | .hw_value_short = ZD_CCK_RATE_2M | ZD_CCK_PREA_SHORT, | ||
57 | .flags = IEEE80211_RATE_SHORT_PREAMBLE }, | ||
58 | { .bitrate = 55, | ||
59 | .hw_value = ZD_CCK_RATE_5_5M, | ||
60 | .hw_value_short = ZD_CCK_RATE_5_5M | ZD_CCK_PREA_SHORT, | ||
61 | .flags = IEEE80211_RATE_SHORT_PREAMBLE }, | ||
62 | { .bitrate = 110, | ||
63 | .hw_value = ZD_CCK_RATE_11M, | ||
64 | .hw_value_short = ZD_CCK_RATE_11M | ZD_CCK_PREA_SHORT, | ||
65 | .flags = IEEE80211_RATE_SHORT_PREAMBLE }, | ||
66 | { .bitrate = 60, | ||
67 | .hw_value = ZD_OFDM_RATE_6M, | ||
68 | .flags = 0 }, | ||
69 | { .bitrate = 90, | ||
70 | .hw_value = ZD_OFDM_RATE_9M, | ||
71 | .flags = 0 }, | ||
72 | { .bitrate = 120, | ||
73 | .hw_value = ZD_OFDM_RATE_12M, | ||
74 | .flags = 0 }, | ||
75 | { .bitrate = 180, | ||
76 | .hw_value = ZD_OFDM_RATE_18M, | ||
77 | .flags = 0 }, | ||
78 | { .bitrate = 240, | ||
79 | .hw_value = ZD_OFDM_RATE_24M, | ||
80 | .flags = 0 }, | ||
81 | { .bitrate = 360, | ||
82 | .hw_value = ZD_OFDM_RATE_36M, | ||
83 | .flags = 0 }, | ||
84 | { .bitrate = 480, | ||
85 | .hw_value = ZD_OFDM_RATE_48M, | ||
86 | .flags = 0 }, | ||
87 | { .bitrate = 540, | ||
88 | .hw_value = ZD_OFDM_RATE_54M, | ||
89 | .flags = 0 }, | ||
90 | }; | ||
91 | |||
92 | /* | ||
93 | * Zydas retry rates table. Each line is listed in the same order as | ||
94 | * in zd_rates[] and contains all the rate used when a packet is sent | ||
95 | * starting with a given rates. Let's consider an example : | ||
96 | * | ||
97 | * "11 Mbits : 4, 3, 2, 1, 0" means : | ||
98 | * - packet is sent using 4 different rates | ||
99 | * - 1st rate is index 3 (ie 11 Mbits) | ||
100 | * - 2nd rate is index 2 (ie 5.5 Mbits) | ||
101 | * - 3rd rate is index 1 (ie 2 Mbits) | ||
102 | * - 4th rate is index 0 (ie 1 Mbits) | ||
103 | */ | ||
104 | |||
105 | static const struct tx_retry_rate zd_retry_rates[] = { | ||
106 | { /* 1 Mbits */ 1, { 0 }}, | ||
107 | { /* 2 Mbits */ 2, { 1, 0 }}, | ||
108 | { /* 5.5 Mbits */ 3, { 2, 1, 0 }}, | ||
109 | { /* 11 Mbits */ 4, { 3, 2, 1, 0 }}, | ||
110 | { /* 6 Mbits */ 5, { 4, 3, 2, 1, 0 }}, | ||
111 | { /* 9 Mbits */ 6, { 5, 4, 3, 2, 1, 0}}, | ||
112 | { /* 12 Mbits */ 5, { 6, 3, 2, 1, 0 }}, | ||
113 | { /* 18 Mbits */ 6, { 7, 6, 3, 2, 1, 0 }}, | ||
114 | { /* 24 Mbits */ 6, { 8, 6, 3, 2, 1, 0 }}, | ||
115 | { /* 36 Mbits */ 7, { 9, 8, 6, 3, 2, 1, 0 }}, | ||
116 | { /* 48 Mbits */ 8, {10, 9, 8, 6, 3, 2, 1, 0 }}, | ||
117 | { /* 54 Mbits */ 9, {11, 10, 9, 8, 6, 3, 2, 1, 0 }} | ||
118 | }; | ||
119 | |||
120 | static const struct ieee80211_channel zd_channels[] = { | ||
121 | { .center_freq = 2412, .hw_value = 1 }, | ||
122 | { .center_freq = 2417, .hw_value = 2 }, | ||
123 | { .center_freq = 2422, .hw_value = 3 }, | ||
124 | { .center_freq = 2427, .hw_value = 4 }, | ||
125 | { .center_freq = 2432, .hw_value = 5 }, | ||
126 | { .center_freq = 2437, .hw_value = 6 }, | ||
127 | { .center_freq = 2442, .hw_value = 7 }, | ||
128 | { .center_freq = 2447, .hw_value = 8 }, | ||
129 | { .center_freq = 2452, .hw_value = 9 }, | ||
130 | { .center_freq = 2457, .hw_value = 10 }, | ||
131 | { .center_freq = 2462, .hw_value = 11 }, | ||
132 | { .center_freq = 2467, .hw_value = 12 }, | ||
133 | { .center_freq = 2472, .hw_value = 13 }, | ||
134 | { .center_freq = 2484, .hw_value = 14 }, | ||
135 | }; | ||
136 | |||
137 | static void housekeeping_init(struct zd_mac *mac); | ||
138 | static void housekeeping_enable(struct zd_mac *mac); | ||
139 | static void housekeeping_disable(struct zd_mac *mac); | ||
140 | static void beacon_init(struct zd_mac *mac); | ||
141 | static void beacon_enable(struct zd_mac *mac); | ||
142 | static void beacon_disable(struct zd_mac *mac); | ||
143 | static void set_rts_cts(struct zd_mac *mac, unsigned int short_preamble); | ||
144 | static int zd_mac_config_beacon(struct ieee80211_hw *hw, | ||
145 | struct sk_buff *beacon, bool in_intr); | ||
146 | |||
147 | static int zd_reg2alpha2(u8 regdomain, char *alpha2) | ||
148 | { | ||
149 | unsigned int i; | ||
150 | struct zd_reg_alpha2_map *reg_map; | ||
151 | for (i = 0; i < ARRAY_SIZE(reg_alpha2_map); i++) { | ||
152 | reg_map = ®_alpha2_map[i]; | ||
153 | if (regdomain == reg_map->reg) { | ||
154 | alpha2[0] = reg_map->alpha2[0]; | ||
155 | alpha2[1] = reg_map->alpha2[1]; | ||
156 | return 0; | ||
157 | } | ||
158 | } | ||
159 | return 1; | ||
160 | } | ||
161 | |||
162 | static int zd_check_signal(struct ieee80211_hw *hw, int signal) | ||
163 | { | ||
164 | struct zd_mac *mac = zd_hw_mac(hw); | ||
165 | |||
166 | dev_dbg_f_cond(zd_mac_dev(mac), signal < 0 || signal > 100, | ||
167 | "%s: signal value from device not in range 0..100, " | ||
168 | "but %d.\n", __func__, signal); | ||
169 | |||
170 | if (signal < 0) | ||
171 | signal = 0; | ||
172 | else if (signal > 100) | ||
173 | signal = 100; | ||
174 | |||
175 | return signal; | ||
176 | } | ||
177 | |||
178 | int zd_mac_preinit_hw(struct ieee80211_hw *hw) | ||
179 | { | ||
180 | int r; | ||
181 | u8 addr[ETH_ALEN]; | ||
182 | struct zd_mac *mac = zd_hw_mac(hw); | ||
183 | |||
184 | r = zd_chip_read_mac_addr_fw(&mac->chip, addr); | ||
185 | if (r) | ||
186 | return r; | ||
187 | |||
188 | SET_IEEE80211_PERM_ADDR(hw, addr); | ||
189 | |||
190 | return 0; | ||
191 | } | ||
192 | |||
193 | int zd_mac_init_hw(struct ieee80211_hw *hw) | ||
194 | { | ||
195 | int r; | ||
196 | struct zd_mac *mac = zd_hw_mac(hw); | ||
197 | struct zd_chip *chip = &mac->chip; | ||
198 | char alpha2[2]; | ||
199 | u8 default_regdomain; | ||
200 | |||
201 | r = zd_chip_enable_int(chip); | ||
202 | if (r) | ||
203 | goto out; | ||
204 | r = zd_chip_init_hw(chip); | ||
205 | if (r) | ||
206 | goto disable_int; | ||
207 | |||
208 | ZD_ASSERT(!irqs_disabled()); | ||
209 | |||
210 | r = zd_read_regdomain(chip, &default_regdomain); | ||
211 | if (r) | ||
212 | goto disable_int; | ||
213 | spin_lock_irq(&mac->lock); | ||
214 | mac->regdomain = mac->default_regdomain = default_regdomain; | ||
215 | spin_unlock_irq(&mac->lock); | ||
216 | |||
217 | /* We must inform the device that we are doing encryption/decryption in | ||
218 | * software at the moment. */ | ||
219 | r = zd_set_encryption_type(chip, ENC_SNIFFER); | ||
220 | if (r) | ||
221 | goto disable_int; | ||
222 | |||
223 | r = zd_reg2alpha2(mac->regdomain, alpha2); | ||
224 | if (r) | ||
225 | goto disable_int; | ||
226 | |||
227 | r = regulatory_hint(hw->wiphy, alpha2); | ||
228 | disable_int: | ||
229 | zd_chip_disable_int(chip); | ||
230 | out: | ||
231 | return r; | ||
232 | } | ||
233 | |||
234 | void zd_mac_clear(struct zd_mac *mac) | ||
235 | { | ||
236 | flush_workqueue(zd_workqueue); | ||
237 | zd_chip_clear(&mac->chip); | ||
238 | ZD_ASSERT(!spin_is_locked(&mac->lock)); | ||
239 | ZD_MEMCLEAR(mac, sizeof(struct zd_mac)); | ||
240 | } | ||
241 | |||
242 | static int set_rx_filter(struct zd_mac *mac) | ||
243 | { | ||
244 | unsigned long flags; | ||
245 | u32 filter = STA_RX_FILTER; | ||
246 | |||
247 | spin_lock_irqsave(&mac->lock, flags); | ||
248 | if (mac->pass_ctrl) | ||
249 | filter |= RX_FILTER_CTRL; | ||
250 | spin_unlock_irqrestore(&mac->lock, flags); | ||
251 | |||
252 | return zd_iowrite32(&mac->chip, CR_RX_FILTER, filter); | ||
253 | } | ||
254 | |||
255 | static int set_mac_and_bssid(struct zd_mac *mac) | ||
256 | { | ||
257 | int r; | ||
258 | |||
259 | if (!mac->vif) | ||
260 | return -1; | ||
261 | |||
262 | r = zd_write_mac_addr(&mac->chip, mac->vif->addr); | ||
263 | if (r) | ||
264 | return r; | ||
265 | |||
266 | /* Vendor driver after setting MAC either sets BSSID for AP or | ||
267 | * filter for other modes. | ||
268 | */ | ||
269 | if (mac->type != NL80211_IFTYPE_AP) | ||
270 | return set_rx_filter(mac); | ||
271 | else | ||
272 | return zd_write_bssid(&mac->chip, mac->vif->addr); | ||
273 | } | ||
274 | |||
275 | static int set_mc_hash(struct zd_mac *mac) | ||
276 | { | ||
277 | struct zd_mc_hash hash; | ||
278 | zd_mc_clear(&hash); | ||
279 | return zd_chip_set_multicast_hash(&mac->chip, &hash); | ||
280 | } | ||
281 | |||
282 | int zd_op_start(struct ieee80211_hw *hw) | ||
283 | { | ||
284 | struct zd_mac *mac = zd_hw_mac(hw); | ||
285 | struct zd_chip *chip = &mac->chip; | ||
286 | struct zd_usb *usb = &chip->usb; | ||
287 | int r; | ||
288 | |||
289 | if (!usb->initialized) { | ||
290 | r = zd_usb_init_hw(usb); | ||
291 | if (r) | ||
292 | goto out; | ||
293 | } | ||
294 | |||
295 | r = zd_chip_enable_int(chip); | ||
296 | if (r < 0) | ||
297 | goto out; | ||
298 | |||
299 | r = zd_chip_set_basic_rates(chip, CR_RATES_80211B | CR_RATES_80211G); | ||
300 | if (r < 0) | ||
301 | goto disable_int; | ||
302 | r = set_rx_filter(mac); | ||
303 | if (r) | ||
304 | goto disable_int; | ||
305 | r = set_mc_hash(mac); | ||
306 | if (r) | ||
307 | goto disable_int; | ||
308 | |||
309 | /* Wait after setting the multicast hash table and powering on | ||
310 | * the radio otherwise interface bring up will fail. This matches | ||
311 | * what the vendor driver did. | ||
312 | */ | ||
313 | msleep(10); | ||
314 | |||
315 | r = zd_chip_switch_radio_on(chip); | ||
316 | if (r < 0) { | ||
317 | dev_err(zd_chip_dev(chip), | ||
318 | "%s: failed to set radio on\n", __func__); | ||
319 | goto disable_int; | ||
320 | } | ||
321 | r = zd_chip_enable_rxtx(chip); | ||
322 | if (r < 0) | ||
323 | goto disable_radio; | ||
324 | r = zd_chip_enable_hwint(chip); | ||
325 | if (r < 0) | ||
326 | goto disable_rxtx; | ||
327 | |||
328 | housekeeping_enable(mac); | ||
329 | beacon_enable(mac); | ||
330 | set_bit(ZD_DEVICE_RUNNING, &mac->flags); | ||
331 | return 0; | ||
332 | disable_rxtx: | ||
333 | zd_chip_disable_rxtx(chip); | ||
334 | disable_radio: | ||
335 | zd_chip_switch_radio_off(chip); | ||
336 | disable_int: | ||
337 | zd_chip_disable_int(chip); | ||
338 | out: | ||
339 | return r; | ||
340 | } | ||
341 | |||
342 | void zd_op_stop(struct ieee80211_hw *hw) | ||
343 | { | ||
344 | struct zd_mac *mac = zd_hw_mac(hw); | ||
345 | struct zd_chip *chip = &mac->chip; | ||
346 | struct sk_buff *skb; | ||
347 | struct sk_buff_head *ack_wait_queue = &mac->ack_wait_queue; | ||
348 | |||
349 | clear_bit(ZD_DEVICE_RUNNING, &mac->flags); | ||
350 | |||
351 | /* The order here deliberately is a little different from the open() | ||
352 | * method, since we need to make sure there is no opportunity for RX | ||
353 | * frames to be processed by mac80211 after we have stopped it. | ||
354 | */ | ||
355 | |||
356 | zd_chip_disable_rxtx(chip); | ||
357 | beacon_disable(mac); | ||
358 | housekeeping_disable(mac); | ||
359 | flush_workqueue(zd_workqueue); | ||
360 | |||
361 | zd_chip_disable_hwint(chip); | ||
362 | zd_chip_switch_radio_off(chip); | ||
363 | zd_chip_disable_int(chip); | ||
364 | |||
365 | |||
366 | while ((skb = skb_dequeue(ack_wait_queue))) | ||
367 | dev_kfree_skb_any(skb); | ||
368 | } | ||
369 | |||
370 | int zd_restore_settings(struct zd_mac *mac) | ||
371 | { | ||
372 | struct sk_buff *beacon; | ||
373 | struct zd_mc_hash multicast_hash; | ||
374 | unsigned int short_preamble; | ||
375 | int r, beacon_interval, beacon_period; | ||
376 | u8 channel; | ||
377 | |||
378 | dev_dbg_f(zd_mac_dev(mac), "\n"); | ||
379 | |||
380 | spin_lock_irq(&mac->lock); | ||
381 | multicast_hash = mac->multicast_hash; | ||
382 | short_preamble = mac->short_preamble; | ||
383 | beacon_interval = mac->beacon.interval; | ||
384 | beacon_period = mac->beacon.period; | ||
385 | channel = mac->channel; | ||
386 | spin_unlock_irq(&mac->lock); | ||
387 | |||
388 | r = set_mac_and_bssid(mac); | ||
389 | if (r < 0) { | ||
390 | dev_dbg_f(zd_mac_dev(mac), "set_mac_and_bssid failed, %d\n", r); | ||
391 | return r; | ||
392 | } | ||
393 | |||
394 | r = zd_chip_set_channel(&mac->chip, channel); | ||
395 | if (r < 0) { | ||
396 | dev_dbg_f(zd_mac_dev(mac), "zd_chip_set_channel failed, %d\n", | ||
397 | r); | ||
398 | return r; | ||
399 | } | ||
400 | |||
401 | set_rts_cts(mac, short_preamble); | ||
402 | |||
403 | r = zd_chip_set_multicast_hash(&mac->chip, &multicast_hash); | ||
404 | if (r < 0) { | ||
405 | dev_dbg_f(zd_mac_dev(mac), | ||
406 | "zd_chip_set_multicast_hash failed, %d\n", r); | ||
407 | return r; | ||
408 | } | ||
409 | |||
410 | if (mac->type == NL80211_IFTYPE_MESH_POINT || | ||
411 | mac->type == NL80211_IFTYPE_ADHOC || | ||
412 | mac->type == NL80211_IFTYPE_AP) { | ||
413 | if (mac->vif != NULL) { | ||
414 | beacon = ieee80211_beacon_get(mac->hw, mac->vif); | ||
415 | if (beacon) | ||
416 | zd_mac_config_beacon(mac->hw, beacon, false); | ||
417 | } | ||
418 | |||
419 | zd_set_beacon_interval(&mac->chip, beacon_interval, | ||
420 | beacon_period, mac->type); | ||
421 | |||
422 | spin_lock_irq(&mac->lock); | ||
423 | mac->beacon.last_update = jiffies; | ||
424 | spin_unlock_irq(&mac->lock); | ||
425 | } | ||
426 | |||
427 | return 0; | ||
428 | } | ||
429 | |||
430 | /** | ||
431 | * zd_mac_tx_status - reports tx status of a packet if required | ||
432 | * @hw - a &struct ieee80211_hw pointer | ||
433 | * @skb - a sk-buffer | ||
434 | * @flags: extra flags to set in the TX status info | ||
435 | * @ackssi: ACK signal strength | ||
436 | * @success - True for successful transmission of the frame | ||
437 | * | ||
438 | * This information calls ieee80211_tx_status_irqsafe() if required by the | ||
439 | * control information. It copies the control information into the status | ||
440 | * information. | ||
441 | * | ||
442 | * If no status information has been requested, the skb is freed. | ||
443 | */ | ||
444 | static void zd_mac_tx_status(struct ieee80211_hw *hw, struct sk_buff *skb, | ||
445 | int ackssi, struct tx_status *tx_status) | ||
446 | { | ||
447 | struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb); | ||
448 | int i; | ||
449 | int success = 1, retry = 1; | ||
450 | int first_idx; | ||
451 | const struct tx_retry_rate *retries; | ||
452 | |||
453 | ieee80211_tx_info_clear_status(info); | ||
454 | |||
455 | if (tx_status) { | ||
456 | success = !tx_status->failure; | ||
457 | retry = tx_status->retry + success; | ||
458 | } | ||
459 | |||
460 | if (success) { | ||
461 | /* success */ | ||
462 | info->flags |= IEEE80211_TX_STAT_ACK; | ||
463 | } else { | ||
464 | /* failure */ | ||
465 | info->flags &= ~IEEE80211_TX_STAT_ACK; | ||
466 | } | ||
467 | |||
468 | first_idx = info->status.rates[0].idx; | ||
469 | ZD_ASSERT(0<=first_idx && first_idx<ARRAY_SIZE(zd_retry_rates)); | ||
470 | retries = &zd_retry_rates[first_idx]; | ||
471 | ZD_ASSERT(1 <= retry && retry <= retries->count); | ||
472 | |||
473 | info->status.rates[0].idx = retries->rate[0]; | ||
474 | info->status.rates[0].count = 1; // (retry > 1 ? 2 : 1); | ||
475 | |||
476 | for (i=1; i<IEEE80211_TX_MAX_RATES-1 && i<retry; i++) { | ||
477 | info->status.rates[i].idx = retries->rate[i]; | ||
478 | info->status.rates[i].count = 1; // ((i==retry-1) && success ? 1:2); | ||
479 | } | ||
480 | for (; i<IEEE80211_TX_MAX_RATES && i<retry; i++) { | ||
481 | info->status.rates[i].idx = retries->rate[retry - 1]; | ||
482 | info->status.rates[i].count = 1; // (success ? 1:2); | ||
483 | } | ||
484 | if (i<IEEE80211_TX_MAX_RATES) | ||
485 | info->status.rates[i].idx = -1; /* terminate */ | ||
486 | |||
487 | info->status.ack_signal = zd_check_signal(hw, ackssi); | ||
488 | ieee80211_tx_status_irqsafe(hw, skb); | ||
489 | } | ||
490 | |||
491 | /** | ||
492 | * zd_mac_tx_failed - callback for failed frames | ||
493 | * @dev: the mac80211 wireless device | ||
494 | * | ||
495 | * This function is called if a frame couldn't be successfully | ||
496 | * transferred. The first frame from the tx queue, will be selected and | ||
497 | * reported as error to the upper layers. | ||
498 | */ | ||
499 | void zd_mac_tx_failed(struct urb *urb) | ||
500 | { | ||
501 | struct ieee80211_hw * hw = zd_usb_to_hw(urb->context); | ||
502 | struct zd_mac *mac = zd_hw_mac(hw); | ||
503 | struct sk_buff_head *q = &mac->ack_wait_queue; | ||
504 | struct sk_buff *skb; | ||
505 | struct tx_status *tx_status = (struct tx_status *)urb->transfer_buffer; | ||
506 | unsigned long flags; | ||
507 | int success = !tx_status->failure; | ||
508 | int retry = tx_status->retry + success; | ||
509 | int found = 0; | ||
510 | int i, position = 0; | ||
511 | |||
512 | q = &mac->ack_wait_queue; | ||
513 | spin_lock_irqsave(&q->lock, flags); | ||
514 | |||
515 | skb_queue_walk(q, skb) { | ||
516 | struct ieee80211_hdr *tx_hdr; | ||
517 | struct ieee80211_tx_info *info; | ||
518 | int first_idx, final_idx; | ||
519 | const struct tx_retry_rate *retries; | ||
520 | u8 final_rate; | ||
521 | |||
522 | position ++; | ||
523 | |||
524 | /* if the hardware reports a failure and we had a 802.11 ACK | ||
525 | * pending, then we skip the first skb when searching for a | ||
526 | * matching frame */ | ||
527 | if (tx_status->failure && mac->ack_pending && | ||
528 | skb_queue_is_first(q, skb)) { | ||
529 | continue; | ||
530 | } | ||
531 | |||
532 | tx_hdr = (struct ieee80211_hdr *)skb->data; | ||
533 | |||
534 | /* we skip all frames not matching the reported destination */ | ||
535 | if (unlikely(!ether_addr_equal(tx_hdr->addr1, tx_status->mac))) | ||
536 | continue; | ||
537 | |||
538 | /* we skip all frames not matching the reported final rate */ | ||
539 | |||
540 | info = IEEE80211_SKB_CB(skb); | ||
541 | first_idx = info->status.rates[0].idx; | ||
542 | ZD_ASSERT(0<=first_idx && first_idx<ARRAY_SIZE(zd_retry_rates)); | ||
543 | retries = &zd_retry_rates[first_idx]; | ||
544 | if (retry <= 0 || retry > retries->count) | ||
545 | continue; | ||
546 | |||
547 | final_idx = retries->rate[retry - 1]; | ||
548 | final_rate = zd_rates[final_idx].hw_value; | ||
549 | |||
550 | if (final_rate != tx_status->rate) { | ||
551 | continue; | ||
552 | } | ||
553 | |||
554 | found = 1; | ||
555 | break; | ||
556 | } | ||
557 | |||
558 | if (found) { | ||
559 | for (i=1; i<=position; i++) { | ||
560 | skb = __skb_dequeue(q); | ||
561 | zd_mac_tx_status(hw, skb, | ||
562 | mac->ack_pending ? mac->ack_signal : 0, | ||
563 | i == position ? tx_status : NULL); | ||
564 | mac->ack_pending = 0; | ||
565 | } | ||
566 | } | ||
567 | |||
568 | spin_unlock_irqrestore(&q->lock, flags); | ||
569 | } | ||
570 | |||
571 | /** | ||
572 | * zd_mac_tx_to_dev - callback for USB layer | ||
573 | * @skb: a &sk_buff pointer | ||
574 | * @error: error value, 0 if transmission successful | ||
575 | * | ||
576 | * Informs the MAC layer that the frame has successfully transferred to the | ||
577 | * device. If an ACK is required and the transfer to the device has been | ||
578 | * successful, the packets are put on the @ack_wait_queue with | ||
579 | * the control set removed. | ||
580 | */ | ||
581 | void zd_mac_tx_to_dev(struct sk_buff *skb, int error) | ||
582 | { | ||
583 | struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb); | ||
584 | struct ieee80211_hw *hw = info->rate_driver_data[0]; | ||
585 | struct zd_mac *mac = zd_hw_mac(hw); | ||
586 | |||
587 | ieee80211_tx_info_clear_status(info); | ||
588 | |||
589 | skb_pull(skb, sizeof(struct zd_ctrlset)); | ||
590 | if (unlikely(error || | ||
591 | (info->flags & IEEE80211_TX_CTL_NO_ACK))) { | ||
592 | /* | ||
593 | * FIXME : do we need to fill in anything ? | ||
594 | */ | ||
595 | ieee80211_tx_status_irqsafe(hw, skb); | ||
596 | } else { | ||
597 | struct sk_buff_head *q = &mac->ack_wait_queue; | ||
598 | |||
599 | skb_queue_tail(q, skb); | ||
600 | while (skb_queue_len(q) > ZD_MAC_MAX_ACK_WAITERS) { | ||
601 | zd_mac_tx_status(hw, skb_dequeue(q), | ||
602 | mac->ack_pending ? mac->ack_signal : 0, | ||
603 | NULL); | ||
604 | mac->ack_pending = 0; | ||
605 | } | ||
606 | } | ||
607 | } | ||
608 | |||
609 | static int zd_calc_tx_length_us(u8 *service, u8 zd_rate, u16 tx_length) | ||
610 | { | ||
611 | /* ZD_PURE_RATE() must be used to remove the modulation type flag of | ||
612 | * the zd-rate values. | ||
613 | */ | ||
614 | static const u8 rate_divisor[] = { | ||
615 | [ZD_PURE_RATE(ZD_CCK_RATE_1M)] = 1, | ||
616 | [ZD_PURE_RATE(ZD_CCK_RATE_2M)] = 2, | ||
617 | /* Bits must be doubled. */ | ||
618 | [ZD_PURE_RATE(ZD_CCK_RATE_5_5M)] = 11, | ||
619 | [ZD_PURE_RATE(ZD_CCK_RATE_11M)] = 11, | ||
620 | [ZD_PURE_RATE(ZD_OFDM_RATE_6M)] = 6, | ||
621 | [ZD_PURE_RATE(ZD_OFDM_RATE_9M)] = 9, | ||
622 | [ZD_PURE_RATE(ZD_OFDM_RATE_12M)] = 12, | ||
623 | [ZD_PURE_RATE(ZD_OFDM_RATE_18M)] = 18, | ||
624 | [ZD_PURE_RATE(ZD_OFDM_RATE_24M)] = 24, | ||
625 | [ZD_PURE_RATE(ZD_OFDM_RATE_36M)] = 36, | ||
626 | [ZD_PURE_RATE(ZD_OFDM_RATE_48M)] = 48, | ||
627 | [ZD_PURE_RATE(ZD_OFDM_RATE_54M)] = 54, | ||
628 | }; | ||
629 | |||
630 | u32 bits = (u32)tx_length * 8; | ||
631 | u32 divisor; | ||
632 | |||
633 | divisor = rate_divisor[ZD_PURE_RATE(zd_rate)]; | ||
634 | if (divisor == 0) | ||
635 | return -EINVAL; | ||
636 | |||
637 | switch (zd_rate) { | ||
638 | case ZD_CCK_RATE_5_5M: | ||
639 | bits = (2*bits) + 10; /* round up to the next integer */ | ||
640 | break; | ||
641 | case ZD_CCK_RATE_11M: | ||
642 | if (service) { | ||
643 | u32 t = bits % 11; | ||
644 | *service &= ~ZD_PLCP_SERVICE_LENGTH_EXTENSION; | ||
645 | if (0 < t && t <= 3) { | ||
646 | *service |= ZD_PLCP_SERVICE_LENGTH_EXTENSION; | ||
647 | } | ||
648 | } | ||
649 | bits += 10; /* round up to the next integer */ | ||
650 | break; | ||
651 | } | ||
652 | |||
653 | return bits/divisor; | ||
654 | } | ||
655 | |||
656 | static void cs_set_control(struct zd_mac *mac, struct zd_ctrlset *cs, | ||
657 | struct ieee80211_hdr *header, | ||
658 | struct ieee80211_tx_info *info) | ||
659 | { | ||
660 | /* | ||
661 | * CONTROL TODO: | ||
662 | * - if backoff needed, enable bit 0 | ||
663 | * - if burst (backoff not needed) disable bit 0 | ||
664 | */ | ||
665 | |||
666 | cs->control = 0; | ||
667 | |||
668 | /* First fragment */ | ||
669 | if (info->flags & IEEE80211_TX_CTL_FIRST_FRAGMENT) | ||
670 | cs->control |= ZD_CS_NEED_RANDOM_BACKOFF; | ||
671 | |||
672 | /* No ACK expected (multicast, etc.) */ | ||
673 | if (info->flags & IEEE80211_TX_CTL_NO_ACK) | ||
674 | cs->control |= ZD_CS_NO_ACK; | ||
675 | |||
676 | /* PS-POLL */ | ||
677 | if (ieee80211_is_pspoll(header->frame_control)) | ||
678 | cs->control |= ZD_CS_PS_POLL_FRAME; | ||
679 | |||
680 | if (info->control.rates[0].flags & IEEE80211_TX_RC_USE_RTS_CTS) | ||
681 | cs->control |= ZD_CS_RTS; | ||
682 | |||
683 | if (info->control.rates[0].flags & IEEE80211_TX_RC_USE_CTS_PROTECT) | ||
684 | cs->control |= ZD_CS_SELF_CTS; | ||
685 | |||
686 | /* FIXME: Management frame? */ | ||
687 | } | ||
688 | |||
689 | static bool zd_mac_match_cur_beacon(struct zd_mac *mac, struct sk_buff *beacon) | ||
690 | { | ||
691 | if (!mac->beacon.cur_beacon) | ||
692 | return false; | ||
693 | |||
694 | if (mac->beacon.cur_beacon->len != beacon->len) | ||
695 | return false; | ||
696 | |||
697 | return !memcmp(beacon->data, mac->beacon.cur_beacon->data, beacon->len); | ||
698 | } | ||
699 | |||
700 | static void zd_mac_free_cur_beacon_locked(struct zd_mac *mac) | ||
701 | { | ||
702 | ZD_ASSERT(mutex_is_locked(&mac->chip.mutex)); | ||
703 | |||
704 | kfree_skb(mac->beacon.cur_beacon); | ||
705 | mac->beacon.cur_beacon = NULL; | ||
706 | } | ||
707 | |||
708 | static void zd_mac_free_cur_beacon(struct zd_mac *mac) | ||
709 | { | ||
710 | mutex_lock(&mac->chip.mutex); | ||
711 | zd_mac_free_cur_beacon_locked(mac); | ||
712 | mutex_unlock(&mac->chip.mutex); | ||
713 | } | ||
714 | |||
715 | static int zd_mac_config_beacon(struct ieee80211_hw *hw, struct sk_buff *beacon, | ||
716 | bool in_intr) | ||
717 | { | ||
718 | struct zd_mac *mac = zd_hw_mac(hw); | ||
719 | int r, ret, num_cmds, req_pos = 0; | ||
720 | u32 tmp, j = 0; | ||
721 | /* 4 more bytes for tail CRC */ | ||
722 | u32 full_len = beacon->len + 4; | ||
723 | unsigned long end_jiffies, message_jiffies; | ||
724 | struct zd_ioreq32 *ioreqs; | ||
725 | |||
726 | mutex_lock(&mac->chip.mutex); | ||
727 | |||
728 | /* Check if hw already has this beacon. */ | ||
729 | if (zd_mac_match_cur_beacon(mac, beacon)) { | ||
730 | r = 0; | ||
731 | goto out_nofree; | ||
732 | } | ||
733 | |||
734 | /* Alloc memory for full beacon write at once. */ | ||
735 | num_cmds = 1 + zd_chip_is_zd1211b(&mac->chip) + full_len; | ||
736 | ioreqs = kmalloc(num_cmds * sizeof(struct zd_ioreq32), GFP_KERNEL); | ||
737 | if (!ioreqs) { | ||
738 | r = -ENOMEM; | ||
739 | goto out_nofree; | ||
740 | } | ||
741 | |||
742 | r = zd_iowrite32_locked(&mac->chip, 0, CR_BCN_FIFO_SEMAPHORE); | ||
743 | if (r < 0) | ||
744 | goto out; | ||
745 | r = zd_ioread32_locked(&mac->chip, &tmp, CR_BCN_FIFO_SEMAPHORE); | ||
746 | if (r < 0) | ||
747 | goto release_sema; | ||
748 | if (in_intr && tmp & 0x2) { | ||
749 | r = -EBUSY; | ||
750 | goto release_sema; | ||
751 | } | ||
752 | |||
753 | end_jiffies = jiffies + HZ / 2; /*~500ms*/ | ||
754 | message_jiffies = jiffies + HZ / 10; /*~100ms*/ | ||
755 | while (tmp & 0x2) { | ||
756 | r = zd_ioread32_locked(&mac->chip, &tmp, CR_BCN_FIFO_SEMAPHORE); | ||
757 | if (r < 0) | ||
758 | goto release_sema; | ||
759 | if (time_is_before_eq_jiffies(message_jiffies)) { | ||
760 | message_jiffies = jiffies + HZ / 10; | ||
761 | dev_err(zd_mac_dev(mac), | ||
762 | "CR_BCN_FIFO_SEMAPHORE not ready\n"); | ||
763 | if (time_is_before_eq_jiffies(end_jiffies)) { | ||
764 | dev_err(zd_mac_dev(mac), | ||
765 | "Giving up beacon config.\n"); | ||
766 | r = -ETIMEDOUT; | ||
767 | goto reset_device; | ||
768 | } | ||
769 | } | ||
770 | msleep(20); | ||
771 | } | ||
772 | |||
773 | ioreqs[req_pos].addr = CR_BCN_FIFO; | ||
774 | ioreqs[req_pos].value = full_len - 1; | ||
775 | req_pos++; | ||
776 | if (zd_chip_is_zd1211b(&mac->chip)) { | ||
777 | ioreqs[req_pos].addr = CR_BCN_LENGTH; | ||
778 | ioreqs[req_pos].value = full_len - 1; | ||
779 | req_pos++; | ||
780 | } | ||
781 | |||
782 | for (j = 0 ; j < beacon->len; j++) { | ||
783 | ioreqs[req_pos].addr = CR_BCN_FIFO; | ||
784 | ioreqs[req_pos].value = *((u8 *)(beacon->data + j)); | ||
785 | req_pos++; | ||
786 | } | ||
787 | |||
788 | for (j = 0; j < 4; j++) { | ||
789 | ioreqs[req_pos].addr = CR_BCN_FIFO; | ||
790 | ioreqs[req_pos].value = 0x0; | ||
791 | req_pos++; | ||
792 | } | ||
793 | |||
794 | BUG_ON(req_pos != num_cmds); | ||
795 | |||
796 | r = zd_iowrite32a_locked(&mac->chip, ioreqs, num_cmds); | ||
797 | |||
798 | release_sema: | ||
799 | /* | ||
800 | * Try very hard to release device beacon semaphore, as otherwise | ||
801 | * device/driver can be left in unusable state. | ||
802 | */ | ||
803 | end_jiffies = jiffies + HZ / 2; /*~500ms*/ | ||
804 | ret = zd_iowrite32_locked(&mac->chip, 1, CR_BCN_FIFO_SEMAPHORE); | ||
805 | while (ret < 0) { | ||
806 | if (in_intr || time_is_before_eq_jiffies(end_jiffies)) { | ||
807 | ret = -ETIMEDOUT; | ||
808 | break; | ||
809 | } | ||
810 | |||
811 | msleep(20); | ||
812 | ret = zd_iowrite32_locked(&mac->chip, 1, CR_BCN_FIFO_SEMAPHORE); | ||
813 | } | ||
814 | |||
815 | if (ret < 0) | ||
816 | dev_err(zd_mac_dev(mac), "Could not release " | ||
817 | "CR_BCN_FIFO_SEMAPHORE!\n"); | ||
818 | if (r < 0 || ret < 0) { | ||
819 | if (r >= 0) | ||
820 | r = ret; | ||
821 | |||
822 | /* We don't know if beacon was written successfully or not, | ||
823 | * so clear current. */ | ||
824 | zd_mac_free_cur_beacon_locked(mac); | ||
825 | |||
826 | goto out; | ||
827 | } | ||
828 | |||
829 | /* Beacon has now been written successfully, update current. */ | ||
830 | zd_mac_free_cur_beacon_locked(mac); | ||
831 | mac->beacon.cur_beacon = beacon; | ||
832 | beacon = NULL; | ||
833 | |||
834 | /* 802.11b/g 2.4G CCK 1Mb | ||
835 | * 802.11a, not yet implemented, uses different values (see GPL vendor | ||
836 | * driver) | ||
837 | */ | ||
838 | r = zd_iowrite32_locked(&mac->chip, 0x00000400 | (full_len << 19), | ||
839 | CR_BCN_PLCP_CFG); | ||
840 | out: | ||
841 | kfree(ioreqs); | ||
842 | out_nofree: | ||
843 | kfree_skb(beacon); | ||
844 | mutex_unlock(&mac->chip.mutex); | ||
845 | |||
846 | return r; | ||
847 | |||
848 | reset_device: | ||
849 | zd_mac_free_cur_beacon_locked(mac); | ||
850 | kfree_skb(beacon); | ||
851 | |||
852 | mutex_unlock(&mac->chip.mutex); | ||
853 | kfree(ioreqs); | ||
854 | |||
855 | /* semaphore stuck, reset device to avoid fw freeze later */ | ||
856 | dev_warn(zd_mac_dev(mac), "CR_BCN_FIFO_SEMAPHORE stuck, " | ||
857 | "resetting device..."); | ||
858 | usb_queue_reset_device(mac->chip.usb.intf); | ||
859 | |||
860 | return r; | ||
861 | } | ||
862 | |||
863 | static int fill_ctrlset(struct zd_mac *mac, | ||
864 | struct sk_buff *skb) | ||
865 | { | ||
866 | int r; | ||
867 | struct ieee80211_hdr *hdr = (struct ieee80211_hdr *) skb->data; | ||
868 | unsigned int frag_len = skb->len + FCS_LEN; | ||
869 | unsigned int packet_length; | ||
870 | struct ieee80211_rate *txrate; | ||
871 | struct zd_ctrlset *cs = (struct zd_ctrlset *) | ||
872 | skb_push(skb, sizeof(struct zd_ctrlset)); | ||
873 | struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb); | ||
874 | |||
875 | ZD_ASSERT(frag_len <= 0xffff); | ||
876 | |||
877 | /* | ||
878 | * Firmware computes the duration itself (for all frames except PSPoll) | ||
879 | * and needs the field set to 0 at input, otherwise firmware messes up | ||
880 | * duration_id and sets bits 14 and 15 on. | ||
881 | */ | ||
882 | if (!ieee80211_is_pspoll(hdr->frame_control)) | ||
883 | hdr->duration_id = 0; | ||
884 | |||
885 | txrate = ieee80211_get_tx_rate(mac->hw, info); | ||
886 | |||
887 | cs->modulation = txrate->hw_value; | ||
888 | if (info->control.rates[0].flags & IEEE80211_TX_RC_USE_SHORT_PREAMBLE) | ||
889 | cs->modulation = txrate->hw_value_short; | ||
890 | |||
891 | cs->tx_length = cpu_to_le16(frag_len); | ||
892 | |||
893 | cs_set_control(mac, cs, hdr, info); | ||
894 | |||
895 | packet_length = frag_len + sizeof(struct zd_ctrlset) + 10; | ||
896 | ZD_ASSERT(packet_length <= 0xffff); | ||
897 | /* ZD1211B: Computing the length difference this way, gives us | ||
898 | * flexibility to compute the packet length. | ||
899 | */ | ||
900 | cs->packet_length = cpu_to_le16(zd_chip_is_zd1211b(&mac->chip) ? | ||
901 | packet_length - frag_len : packet_length); | ||
902 | |||
903 | /* | ||
904 | * CURRENT LENGTH: | ||
905 | * - transmit frame length in microseconds | ||
906 | * - seems to be derived from frame length | ||
907 | * - see Cal_Us_Service() in zdinlinef.h | ||
908 | * - if macp->bTxBurstEnable is enabled, then multiply by 4 | ||
909 | * - bTxBurstEnable is never set in the vendor driver | ||
910 | * | ||
911 | * SERVICE: | ||
912 | * - "for PLCP configuration" | ||
913 | * - always 0 except in some situations at 802.11b 11M | ||
914 | * - see line 53 of zdinlinef.h | ||
915 | */ | ||
916 | cs->service = 0; | ||
917 | r = zd_calc_tx_length_us(&cs->service, ZD_RATE(cs->modulation), | ||
918 | le16_to_cpu(cs->tx_length)); | ||
919 | if (r < 0) | ||
920 | return r; | ||
921 | cs->current_length = cpu_to_le16(r); | ||
922 | cs->next_frame_length = 0; | ||
923 | |||
924 | return 0; | ||
925 | } | ||
926 | |||
927 | /** | ||
928 | * zd_op_tx - transmits a network frame to the device | ||
929 | * | ||
930 | * @dev: mac80211 hardware device | ||
931 | * @skb: socket buffer | ||
932 | * @control: the control structure | ||
933 | * | ||
934 | * This function transmit an IEEE 802.11 network frame to the device. The | ||
935 | * control block of the skbuff will be initialized. If necessary the incoming | ||
936 | * mac80211 queues will be stopped. | ||
937 | */ | ||
938 | static void zd_op_tx(struct ieee80211_hw *hw, | ||
939 | struct ieee80211_tx_control *control, | ||
940 | struct sk_buff *skb) | ||
941 | { | ||
942 | struct zd_mac *mac = zd_hw_mac(hw); | ||
943 | struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb); | ||
944 | int r; | ||
945 | |||
946 | r = fill_ctrlset(mac, skb); | ||
947 | if (r) | ||
948 | goto fail; | ||
949 | |||
950 | info->rate_driver_data[0] = hw; | ||
951 | |||
952 | r = zd_usb_tx(&mac->chip.usb, skb); | ||
953 | if (r) | ||
954 | goto fail; | ||
955 | return; | ||
956 | |||
957 | fail: | ||
958 | dev_kfree_skb(skb); | ||
959 | } | ||
960 | |||
961 | /** | ||
962 | * filter_ack - filters incoming packets for acknowledgements | ||
963 | * @dev: the mac80211 device | ||
964 | * @rx_hdr: received header | ||
965 | * @stats: the status for the received packet | ||
966 | * | ||
967 | * This functions looks for ACK packets and tries to match them with the | ||
968 | * frames in the tx queue. If a match is found the frame will be dequeued and | ||
969 | * the upper layers is informed about the successful transmission. If | ||
970 | * mac80211 queues have been stopped and the number of frames still to be | ||
971 | * transmitted is low the queues will be opened again. | ||
972 | * | ||
973 | * Returns 1 if the frame was an ACK, 0 if it was ignored. | ||
974 | */ | ||
975 | static int filter_ack(struct ieee80211_hw *hw, struct ieee80211_hdr *rx_hdr, | ||
976 | struct ieee80211_rx_status *stats) | ||
977 | { | ||
978 | struct zd_mac *mac = zd_hw_mac(hw); | ||
979 | struct sk_buff *skb; | ||
980 | struct sk_buff_head *q; | ||
981 | unsigned long flags; | ||
982 | int found = 0; | ||
983 | int i, position = 0; | ||
984 | |||
985 | if (!ieee80211_is_ack(rx_hdr->frame_control)) | ||
986 | return 0; | ||
987 | |||
988 | q = &mac->ack_wait_queue; | ||
989 | spin_lock_irqsave(&q->lock, flags); | ||
990 | skb_queue_walk(q, skb) { | ||
991 | struct ieee80211_hdr *tx_hdr; | ||
992 | |||
993 | position ++; | ||
994 | |||
995 | if (mac->ack_pending && skb_queue_is_first(q, skb)) | ||
996 | continue; | ||
997 | |||
998 | tx_hdr = (struct ieee80211_hdr *)skb->data; | ||
999 | if (likely(ether_addr_equal(tx_hdr->addr2, rx_hdr->addr1))) | ||
1000 | { | ||
1001 | found = 1; | ||
1002 | break; | ||
1003 | } | ||
1004 | } | ||
1005 | |||
1006 | if (found) { | ||
1007 | for (i=1; i<position; i++) { | ||
1008 | skb = __skb_dequeue(q); | ||
1009 | zd_mac_tx_status(hw, skb, | ||
1010 | mac->ack_pending ? mac->ack_signal : 0, | ||
1011 | NULL); | ||
1012 | mac->ack_pending = 0; | ||
1013 | } | ||
1014 | |||
1015 | mac->ack_pending = 1; | ||
1016 | mac->ack_signal = stats->signal; | ||
1017 | |||
1018 | /* Prevent pending tx-packet on AP-mode */ | ||
1019 | if (mac->type == NL80211_IFTYPE_AP) { | ||
1020 | skb = __skb_dequeue(q); | ||
1021 | zd_mac_tx_status(hw, skb, mac->ack_signal, NULL); | ||
1022 | mac->ack_pending = 0; | ||
1023 | } | ||
1024 | } | ||
1025 | |||
1026 | spin_unlock_irqrestore(&q->lock, flags); | ||
1027 | return 1; | ||
1028 | } | ||
1029 | |||
1030 | int zd_mac_rx(struct ieee80211_hw *hw, const u8 *buffer, unsigned int length) | ||
1031 | { | ||
1032 | struct zd_mac *mac = zd_hw_mac(hw); | ||
1033 | struct ieee80211_rx_status stats; | ||
1034 | const struct rx_status *status; | ||
1035 | struct sk_buff *skb; | ||
1036 | int bad_frame = 0; | ||
1037 | __le16 fc; | ||
1038 | int need_padding; | ||
1039 | int i; | ||
1040 | u8 rate; | ||
1041 | |||
1042 | if (length < ZD_PLCP_HEADER_SIZE + 10 /* IEEE80211_1ADDR_LEN */ + | ||
1043 | FCS_LEN + sizeof(struct rx_status)) | ||
1044 | return -EINVAL; | ||
1045 | |||
1046 | memset(&stats, 0, sizeof(stats)); | ||
1047 | |||
1048 | /* Note about pass_failed_fcs and pass_ctrl access below: | ||
1049 | * mac locking intentionally omitted here, as this is the only unlocked | ||
1050 | * reader and the only writer is configure_filter. Plus, if there were | ||
1051 | * any races accessing these variables, it wouldn't really matter. | ||
1052 | * If mac80211 ever provides a way for us to access filter flags | ||
1053 | * from outside configure_filter, we could improve on this. Also, this | ||
1054 | * situation may change once we implement some kind of DMA-into-skb | ||
1055 | * RX path. */ | ||
1056 | |||
1057 | /* Caller has to ensure that length >= sizeof(struct rx_status). */ | ||
1058 | status = (struct rx_status *) | ||
1059 | (buffer + (length - sizeof(struct rx_status))); | ||
1060 | if (status->frame_status & ZD_RX_ERROR) { | ||
1061 | if (mac->pass_failed_fcs && | ||
1062 | (status->frame_status & ZD_RX_CRC32_ERROR)) { | ||
1063 | stats.flag |= RX_FLAG_FAILED_FCS_CRC; | ||
1064 | bad_frame = 1; | ||
1065 | } else { | ||
1066 | return -EINVAL; | ||
1067 | } | ||
1068 | } | ||
1069 | |||
1070 | stats.freq = zd_channels[_zd_chip_get_channel(&mac->chip) - 1].center_freq; | ||
1071 | stats.band = IEEE80211_BAND_2GHZ; | ||
1072 | stats.signal = zd_check_signal(hw, status->signal_strength); | ||
1073 | |||
1074 | rate = zd_rx_rate(buffer, status); | ||
1075 | |||
1076 | /* todo: return index in the big switches in zd_rx_rate instead */ | ||
1077 | for (i = 0; i < mac->band.n_bitrates; i++) | ||
1078 | if (rate == mac->band.bitrates[i].hw_value) | ||
1079 | stats.rate_idx = i; | ||
1080 | |||
1081 | length -= ZD_PLCP_HEADER_SIZE + sizeof(struct rx_status); | ||
1082 | buffer += ZD_PLCP_HEADER_SIZE; | ||
1083 | |||
1084 | /* Except for bad frames, filter each frame to see if it is an ACK, in | ||
1085 | * which case our internal TX tracking is updated. Normally we then | ||
1086 | * bail here as there's no need to pass ACKs on up to the stack, but | ||
1087 | * there is also the case where the stack has requested us to pass | ||
1088 | * control frames on up (pass_ctrl) which we must consider. */ | ||
1089 | if (!bad_frame && | ||
1090 | filter_ack(hw, (struct ieee80211_hdr *)buffer, &stats) | ||
1091 | && !mac->pass_ctrl) | ||
1092 | return 0; | ||
1093 | |||
1094 | fc = get_unaligned((__le16*)buffer); | ||
1095 | need_padding = ieee80211_is_data_qos(fc) ^ ieee80211_has_a4(fc); | ||
1096 | |||
1097 | skb = dev_alloc_skb(length + (need_padding ? 2 : 0)); | ||
1098 | if (skb == NULL) | ||
1099 | return -ENOMEM; | ||
1100 | if (need_padding) { | ||
1101 | /* Make sure the payload data is 4 byte aligned. */ | ||
1102 | skb_reserve(skb, 2); | ||
1103 | } | ||
1104 | |||
1105 | /* FIXME : could we avoid this big memcpy ? */ | ||
1106 | memcpy(skb_put(skb, length), buffer, length); | ||
1107 | |||
1108 | memcpy(IEEE80211_SKB_RXCB(skb), &stats, sizeof(stats)); | ||
1109 | ieee80211_rx_irqsafe(hw, skb); | ||
1110 | return 0; | ||
1111 | } | ||
1112 | |||
1113 | static int zd_op_add_interface(struct ieee80211_hw *hw, | ||
1114 | struct ieee80211_vif *vif) | ||
1115 | { | ||
1116 | struct zd_mac *mac = zd_hw_mac(hw); | ||
1117 | |||
1118 | /* using NL80211_IFTYPE_UNSPECIFIED to indicate no mode selected */ | ||
1119 | if (mac->type != NL80211_IFTYPE_UNSPECIFIED) | ||
1120 | return -EOPNOTSUPP; | ||
1121 | |||
1122 | switch (vif->type) { | ||
1123 | case NL80211_IFTYPE_MONITOR: | ||
1124 | case NL80211_IFTYPE_MESH_POINT: | ||
1125 | case NL80211_IFTYPE_STATION: | ||
1126 | case NL80211_IFTYPE_ADHOC: | ||
1127 | case NL80211_IFTYPE_AP: | ||
1128 | mac->type = vif->type; | ||
1129 | break; | ||
1130 | default: | ||
1131 | return -EOPNOTSUPP; | ||
1132 | } | ||
1133 | |||
1134 | mac->vif = vif; | ||
1135 | |||
1136 | return set_mac_and_bssid(mac); | ||
1137 | } | ||
1138 | |||
1139 | static void zd_op_remove_interface(struct ieee80211_hw *hw, | ||
1140 | struct ieee80211_vif *vif) | ||
1141 | { | ||
1142 | struct zd_mac *mac = zd_hw_mac(hw); | ||
1143 | mac->type = NL80211_IFTYPE_UNSPECIFIED; | ||
1144 | mac->vif = NULL; | ||
1145 | zd_set_beacon_interval(&mac->chip, 0, 0, NL80211_IFTYPE_UNSPECIFIED); | ||
1146 | zd_write_mac_addr(&mac->chip, NULL); | ||
1147 | |||
1148 | zd_mac_free_cur_beacon(mac); | ||
1149 | } | ||
1150 | |||
1151 | static int zd_op_config(struct ieee80211_hw *hw, u32 changed) | ||
1152 | { | ||
1153 | struct zd_mac *mac = zd_hw_mac(hw); | ||
1154 | struct ieee80211_conf *conf = &hw->conf; | ||
1155 | |||
1156 | spin_lock_irq(&mac->lock); | ||
1157 | mac->channel = conf->chandef.chan->hw_value; | ||
1158 | spin_unlock_irq(&mac->lock); | ||
1159 | |||
1160 | return zd_chip_set_channel(&mac->chip, conf->chandef.chan->hw_value); | ||
1161 | } | ||
1162 | |||
1163 | static void zd_beacon_done(struct zd_mac *mac) | ||
1164 | { | ||
1165 | struct sk_buff *skb, *beacon; | ||
1166 | |||
1167 | if (!test_bit(ZD_DEVICE_RUNNING, &mac->flags)) | ||
1168 | return; | ||
1169 | if (!mac->vif || mac->vif->type != NL80211_IFTYPE_AP) | ||
1170 | return; | ||
1171 | |||
1172 | /* | ||
1173 | * Send out buffered broad- and multicast frames. | ||
1174 | */ | ||
1175 | while (!ieee80211_queue_stopped(mac->hw, 0)) { | ||
1176 | skb = ieee80211_get_buffered_bc(mac->hw, mac->vif); | ||
1177 | if (!skb) | ||
1178 | break; | ||
1179 | zd_op_tx(mac->hw, NULL, skb); | ||
1180 | } | ||
1181 | |||
1182 | /* | ||
1183 | * Fetch next beacon so that tim_count is updated. | ||
1184 | */ | ||
1185 | beacon = ieee80211_beacon_get(mac->hw, mac->vif); | ||
1186 | if (beacon) | ||
1187 | zd_mac_config_beacon(mac->hw, beacon, true); | ||
1188 | |||
1189 | spin_lock_irq(&mac->lock); | ||
1190 | mac->beacon.last_update = jiffies; | ||
1191 | spin_unlock_irq(&mac->lock); | ||
1192 | } | ||
1193 | |||
1194 | static void zd_process_intr(struct work_struct *work) | ||
1195 | { | ||
1196 | u16 int_status; | ||
1197 | unsigned long flags; | ||
1198 | struct zd_mac *mac = container_of(work, struct zd_mac, process_intr); | ||
1199 | |||
1200 | spin_lock_irqsave(&mac->lock, flags); | ||
1201 | int_status = le16_to_cpu(*(__le16 *)(mac->intr_buffer + 4)); | ||
1202 | spin_unlock_irqrestore(&mac->lock, flags); | ||
1203 | |||
1204 | if (int_status & INT_CFG_NEXT_BCN) { | ||
1205 | /*dev_dbg_f_limit(zd_mac_dev(mac), "INT_CFG_NEXT_BCN\n");*/ | ||
1206 | zd_beacon_done(mac); | ||
1207 | } else { | ||
1208 | dev_dbg_f(zd_mac_dev(mac), "Unsupported interrupt\n"); | ||
1209 | } | ||
1210 | |||
1211 | zd_chip_enable_hwint(&mac->chip); | ||
1212 | } | ||
1213 | |||
1214 | |||
1215 | static u64 zd_op_prepare_multicast(struct ieee80211_hw *hw, | ||
1216 | struct netdev_hw_addr_list *mc_list) | ||
1217 | { | ||
1218 | struct zd_mac *mac = zd_hw_mac(hw); | ||
1219 | struct zd_mc_hash hash; | ||
1220 | struct netdev_hw_addr *ha; | ||
1221 | |||
1222 | zd_mc_clear(&hash); | ||
1223 | |||
1224 | netdev_hw_addr_list_for_each(ha, mc_list) { | ||
1225 | dev_dbg_f(zd_mac_dev(mac), "mc addr %pM\n", ha->addr); | ||
1226 | zd_mc_add_addr(&hash, ha->addr); | ||
1227 | } | ||
1228 | |||
1229 | return hash.low | ((u64)hash.high << 32); | ||
1230 | } | ||
1231 | |||
1232 | #define SUPPORTED_FIF_FLAGS \ | ||
1233 | (FIF_ALLMULTI | FIF_FCSFAIL | FIF_CONTROL | \ | ||
1234 | FIF_OTHER_BSS | FIF_BCN_PRBRESP_PROMISC) | ||
1235 | static void zd_op_configure_filter(struct ieee80211_hw *hw, | ||
1236 | unsigned int changed_flags, | ||
1237 | unsigned int *new_flags, | ||
1238 | u64 multicast) | ||
1239 | { | ||
1240 | struct zd_mc_hash hash = { | ||
1241 | .low = multicast, | ||
1242 | .high = multicast >> 32, | ||
1243 | }; | ||
1244 | struct zd_mac *mac = zd_hw_mac(hw); | ||
1245 | unsigned long flags; | ||
1246 | int r; | ||
1247 | |||
1248 | /* Only deal with supported flags */ | ||
1249 | changed_flags &= SUPPORTED_FIF_FLAGS; | ||
1250 | *new_flags &= SUPPORTED_FIF_FLAGS; | ||
1251 | |||
1252 | /* | ||
1253 | * If multicast parameter (as returned by zd_op_prepare_multicast) | ||
1254 | * has changed, no bit in changed_flags is set. To handle this | ||
1255 | * situation, we do not return if changed_flags is 0. If we do so, | ||
1256 | * we will have some issue with IPv6 which uses multicast for link | ||
1257 | * layer address resolution. | ||
1258 | */ | ||
1259 | if (*new_flags & FIF_ALLMULTI) | ||
1260 | zd_mc_add_all(&hash); | ||
1261 | |||
1262 | spin_lock_irqsave(&mac->lock, flags); | ||
1263 | mac->pass_failed_fcs = !!(*new_flags & FIF_FCSFAIL); | ||
1264 | mac->pass_ctrl = !!(*new_flags & FIF_CONTROL); | ||
1265 | mac->multicast_hash = hash; | ||
1266 | spin_unlock_irqrestore(&mac->lock, flags); | ||
1267 | |||
1268 | zd_chip_set_multicast_hash(&mac->chip, &hash); | ||
1269 | |||
1270 | if (changed_flags & FIF_CONTROL) { | ||
1271 | r = set_rx_filter(mac); | ||
1272 | if (r) | ||
1273 | dev_err(zd_mac_dev(mac), "set_rx_filter error %d\n", r); | ||
1274 | } | ||
1275 | |||
1276 | /* no handling required for FIF_OTHER_BSS as we don't currently | ||
1277 | * do BSSID filtering */ | ||
1278 | /* FIXME: in future it would be nice to enable the probe response | ||
1279 | * filter (so that the driver doesn't see them) until | ||
1280 | * FIF_BCN_PRBRESP_PROMISC is set. however due to atomicity here, we'd | ||
1281 | * have to schedule work to enable prbresp reception, which might | ||
1282 | * happen too late. For now we'll just listen and forward them all the | ||
1283 | * time. */ | ||
1284 | } | ||
1285 | |||
1286 | static void set_rts_cts(struct zd_mac *mac, unsigned int short_preamble) | ||
1287 | { | ||
1288 | mutex_lock(&mac->chip.mutex); | ||
1289 | zd_chip_set_rts_cts_rate_locked(&mac->chip, short_preamble); | ||
1290 | mutex_unlock(&mac->chip.mutex); | ||
1291 | } | ||
1292 | |||
1293 | static void zd_op_bss_info_changed(struct ieee80211_hw *hw, | ||
1294 | struct ieee80211_vif *vif, | ||
1295 | struct ieee80211_bss_conf *bss_conf, | ||
1296 | u32 changes) | ||
1297 | { | ||
1298 | struct zd_mac *mac = zd_hw_mac(hw); | ||
1299 | int associated; | ||
1300 | |||
1301 | dev_dbg_f(zd_mac_dev(mac), "changes: %x\n", changes); | ||
1302 | |||
1303 | if (mac->type == NL80211_IFTYPE_MESH_POINT || | ||
1304 | mac->type == NL80211_IFTYPE_ADHOC || | ||
1305 | mac->type == NL80211_IFTYPE_AP) { | ||
1306 | associated = true; | ||
1307 | if (changes & BSS_CHANGED_BEACON) { | ||
1308 | struct sk_buff *beacon = ieee80211_beacon_get(hw, vif); | ||
1309 | |||
1310 | if (beacon) { | ||
1311 | zd_chip_disable_hwint(&mac->chip); | ||
1312 | zd_mac_config_beacon(hw, beacon, false); | ||
1313 | zd_chip_enable_hwint(&mac->chip); | ||
1314 | } | ||
1315 | } | ||
1316 | |||
1317 | if (changes & BSS_CHANGED_BEACON_ENABLED) { | ||
1318 | u16 interval = 0; | ||
1319 | u8 period = 0; | ||
1320 | |||
1321 | if (bss_conf->enable_beacon) { | ||
1322 | period = bss_conf->dtim_period; | ||
1323 | interval = bss_conf->beacon_int; | ||
1324 | } | ||
1325 | |||
1326 | spin_lock_irq(&mac->lock); | ||
1327 | mac->beacon.period = period; | ||
1328 | mac->beacon.interval = interval; | ||
1329 | mac->beacon.last_update = jiffies; | ||
1330 | spin_unlock_irq(&mac->lock); | ||
1331 | |||
1332 | zd_set_beacon_interval(&mac->chip, interval, period, | ||
1333 | mac->type); | ||
1334 | } | ||
1335 | } else | ||
1336 | associated = is_valid_ether_addr(bss_conf->bssid); | ||
1337 | |||
1338 | spin_lock_irq(&mac->lock); | ||
1339 | mac->associated = associated; | ||
1340 | spin_unlock_irq(&mac->lock); | ||
1341 | |||
1342 | /* TODO: do hardware bssid filtering */ | ||
1343 | |||
1344 | if (changes & BSS_CHANGED_ERP_PREAMBLE) { | ||
1345 | spin_lock_irq(&mac->lock); | ||
1346 | mac->short_preamble = bss_conf->use_short_preamble; | ||
1347 | spin_unlock_irq(&mac->lock); | ||
1348 | |||
1349 | set_rts_cts(mac, bss_conf->use_short_preamble); | ||
1350 | } | ||
1351 | } | ||
1352 | |||
1353 | static u64 zd_op_get_tsf(struct ieee80211_hw *hw, struct ieee80211_vif *vif) | ||
1354 | { | ||
1355 | struct zd_mac *mac = zd_hw_mac(hw); | ||
1356 | return zd_chip_get_tsf(&mac->chip); | ||
1357 | } | ||
1358 | |||
1359 | static const struct ieee80211_ops zd_ops = { | ||
1360 | .tx = zd_op_tx, | ||
1361 | .start = zd_op_start, | ||
1362 | .stop = zd_op_stop, | ||
1363 | .add_interface = zd_op_add_interface, | ||
1364 | .remove_interface = zd_op_remove_interface, | ||
1365 | .config = zd_op_config, | ||
1366 | .prepare_multicast = zd_op_prepare_multicast, | ||
1367 | .configure_filter = zd_op_configure_filter, | ||
1368 | .bss_info_changed = zd_op_bss_info_changed, | ||
1369 | .get_tsf = zd_op_get_tsf, | ||
1370 | }; | ||
1371 | |||
1372 | struct ieee80211_hw *zd_mac_alloc_hw(struct usb_interface *intf) | ||
1373 | { | ||
1374 | struct zd_mac *mac; | ||
1375 | struct ieee80211_hw *hw; | ||
1376 | |||
1377 | hw = ieee80211_alloc_hw(sizeof(struct zd_mac), &zd_ops); | ||
1378 | if (!hw) { | ||
1379 | dev_dbg_f(&intf->dev, "out of memory\n"); | ||
1380 | return NULL; | ||
1381 | } | ||
1382 | |||
1383 | mac = zd_hw_mac(hw); | ||
1384 | |||
1385 | memset(mac, 0, sizeof(*mac)); | ||
1386 | spin_lock_init(&mac->lock); | ||
1387 | mac->hw = hw; | ||
1388 | |||
1389 | mac->type = NL80211_IFTYPE_UNSPECIFIED; | ||
1390 | |||
1391 | memcpy(mac->channels, zd_channels, sizeof(zd_channels)); | ||
1392 | memcpy(mac->rates, zd_rates, sizeof(zd_rates)); | ||
1393 | mac->band.n_bitrates = ARRAY_SIZE(zd_rates); | ||
1394 | mac->band.bitrates = mac->rates; | ||
1395 | mac->band.n_channels = ARRAY_SIZE(zd_channels); | ||
1396 | mac->band.channels = mac->channels; | ||
1397 | |||
1398 | hw->wiphy->bands[IEEE80211_BAND_2GHZ] = &mac->band; | ||
1399 | |||
1400 | ieee80211_hw_set(hw, MFP_CAPABLE); | ||
1401 | ieee80211_hw_set(hw, HOST_BROADCAST_PS_BUFFERING); | ||
1402 | ieee80211_hw_set(hw, RX_INCLUDES_FCS); | ||
1403 | ieee80211_hw_set(hw, SIGNAL_UNSPEC); | ||
1404 | |||
1405 | hw->wiphy->interface_modes = | ||
1406 | BIT(NL80211_IFTYPE_MESH_POINT) | | ||
1407 | BIT(NL80211_IFTYPE_STATION) | | ||
1408 | BIT(NL80211_IFTYPE_ADHOC) | | ||
1409 | BIT(NL80211_IFTYPE_AP); | ||
1410 | |||
1411 | hw->max_signal = 100; | ||
1412 | hw->queues = 1; | ||
1413 | hw->extra_tx_headroom = sizeof(struct zd_ctrlset); | ||
1414 | |||
1415 | /* | ||
1416 | * Tell mac80211 that we support multi rate retries | ||
1417 | */ | ||
1418 | hw->max_rates = IEEE80211_TX_MAX_RATES; | ||
1419 | hw->max_rate_tries = 18; /* 9 rates * 2 retries/rate */ | ||
1420 | |||
1421 | skb_queue_head_init(&mac->ack_wait_queue); | ||
1422 | mac->ack_pending = 0; | ||
1423 | |||
1424 | zd_chip_init(&mac->chip, hw, intf); | ||
1425 | housekeeping_init(mac); | ||
1426 | beacon_init(mac); | ||
1427 | INIT_WORK(&mac->process_intr, zd_process_intr); | ||
1428 | |||
1429 | SET_IEEE80211_DEV(hw, &intf->dev); | ||
1430 | return hw; | ||
1431 | } | ||
1432 | |||
1433 | #define BEACON_WATCHDOG_DELAY round_jiffies_relative(HZ) | ||
1434 | |||
1435 | static void beacon_watchdog_handler(struct work_struct *work) | ||
1436 | { | ||
1437 | struct zd_mac *mac = | ||
1438 | container_of(work, struct zd_mac, beacon.watchdog_work.work); | ||
1439 | struct sk_buff *beacon; | ||
1440 | unsigned long timeout; | ||
1441 | int interval, period; | ||
1442 | |||
1443 | if (!test_bit(ZD_DEVICE_RUNNING, &mac->flags)) | ||
1444 | goto rearm; | ||
1445 | if (mac->type != NL80211_IFTYPE_AP || !mac->vif) | ||
1446 | goto rearm; | ||
1447 | |||
1448 | spin_lock_irq(&mac->lock); | ||
1449 | interval = mac->beacon.interval; | ||
1450 | period = mac->beacon.period; | ||
1451 | timeout = mac->beacon.last_update + | ||
1452 | msecs_to_jiffies(interval * 1024 / 1000) * 3; | ||
1453 | spin_unlock_irq(&mac->lock); | ||
1454 | |||
1455 | if (interval > 0 && time_is_before_jiffies(timeout)) { | ||
1456 | dev_dbg_f(zd_mac_dev(mac), "beacon interrupt stalled, " | ||
1457 | "restarting. " | ||
1458 | "(interval: %d, dtim: %d)\n", | ||
1459 | interval, period); | ||
1460 | |||
1461 | zd_chip_disable_hwint(&mac->chip); | ||
1462 | |||
1463 | beacon = ieee80211_beacon_get(mac->hw, mac->vif); | ||
1464 | if (beacon) { | ||
1465 | zd_mac_free_cur_beacon(mac); | ||
1466 | |||
1467 | zd_mac_config_beacon(mac->hw, beacon, false); | ||
1468 | } | ||
1469 | |||
1470 | zd_set_beacon_interval(&mac->chip, interval, period, mac->type); | ||
1471 | |||
1472 | zd_chip_enable_hwint(&mac->chip); | ||
1473 | |||
1474 | spin_lock_irq(&mac->lock); | ||
1475 | mac->beacon.last_update = jiffies; | ||
1476 | spin_unlock_irq(&mac->lock); | ||
1477 | } | ||
1478 | |||
1479 | rearm: | ||
1480 | queue_delayed_work(zd_workqueue, &mac->beacon.watchdog_work, | ||
1481 | BEACON_WATCHDOG_DELAY); | ||
1482 | } | ||
1483 | |||
1484 | static void beacon_init(struct zd_mac *mac) | ||
1485 | { | ||
1486 | INIT_DELAYED_WORK(&mac->beacon.watchdog_work, beacon_watchdog_handler); | ||
1487 | } | ||
1488 | |||
1489 | static void beacon_enable(struct zd_mac *mac) | ||
1490 | { | ||
1491 | dev_dbg_f(zd_mac_dev(mac), "\n"); | ||
1492 | |||
1493 | mac->beacon.last_update = jiffies; | ||
1494 | queue_delayed_work(zd_workqueue, &mac->beacon.watchdog_work, | ||
1495 | BEACON_WATCHDOG_DELAY); | ||
1496 | } | ||
1497 | |||
1498 | static void beacon_disable(struct zd_mac *mac) | ||
1499 | { | ||
1500 | dev_dbg_f(zd_mac_dev(mac), "\n"); | ||
1501 | cancel_delayed_work_sync(&mac->beacon.watchdog_work); | ||
1502 | |||
1503 | zd_mac_free_cur_beacon(mac); | ||
1504 | } | ||
1505 | |||
1506 | #define LINK_LED_WORK_DELAY HZ | ||
1507 | |||
1508 | static void link_led_handler(struct work_struct *work) | ||
1509 | { | ||
1510 | struct zd_mac *mac = | ||
1511 | container_of(work, struct zd_mac, housekeeping.link_led_work.work); | ||
1512 | struct zd_chip *chip = &mac->chip; | ||
1513 | int is_associated; | ||
1514 | int r; | ||
1515 | |||
1516 | if (!test_bit(ZD_DEVICE_RUNNING, &mac->flags)) | ||
1517 | goto requeue; | ||
1518 | |||
1519 | spin_lock_irq(&mac->lock); | ||
1520 | is_associated = mac->associated; | ||
1521 | spin_unlock_irq(&mac->lock); | ||
1522 | |||
1523 | r = zd_chip_control_leds(chip, | ||
1524 | is_associated ? ZD_LED_ASSOCIATED : ZD_LED_SCANNING); | ||
1525 | if (r) | ||
1526 | dev_dbg_f(zd_mac_dev(mac), "zd_chip_control_leds error %d\n", r); | ||
1527 | |||
1528 | requeue: | ||
1529 | queue_delayed_work(zd_workqueue, &mac->housekeeping.link_led_work, | ||
1530 | LINK_LED_WORK_DELAY); | ||
1531 | } | ||
1532 | |||
1533 | static void housekeeping_init(struct zd_mac *mac) | ||
1534 | { | ||
1535 | INIT_DELAYED_WORK(&mac->housekeeping.link_led_work, link_led_handler); | ||
1536 | } | ||
1537 | |||
1538 | static void housekeeping_enable(struct zd_mac *mac) | ||
1539 | { | ||
1540 | dev_dbg_f(zd_mac_dev(mac), "\n"); | ||
1541 | queue_delayed_work(zd_workqueue, &mac->housekeeping.link_led_work, | ||
1542 | 0); | ||
1543 | } | ||
1544 | |||
1545 | static void housekeeping_disable(struct zd_mac *mac) | ||
1546 | { | ||
1547 | dev_dbg_f(zd_mac_dev(mac), "\n"); | ||
1548 | cancel_delayed_work_sync(&mac->housekeeping.link_led_work); | ||
1549 | zd_chip_control_leds(&mac->chip, ZD_LED_OFF); | ||
1550 | } | ||
diff --git a/drivers/net/wireless/zydas/zd1211rw/zd_mac.h b/drivers/net/wireless/zydas/zd1211rw/zd_mac.h new file mode 100644 index 000000000000..5a484235308f --- /dev/null +++ b/drivers/net/wireless/zydas/zd1211rw/zd_mac.h | |||
@@ -0,0 +1,327 @@ | |||
1 | /* ZD1211 USB-WLAN driver for Linux | ||
2 | * | ||
3 | * Copyright (C) 2005-2007 Ulrich Kunitz <kune@deine-taler.de> | ||
4 | * Copyright (C) 2006-2007 Daniel Drake <dsd@gentoo.org> | ||
5 | * | ||
6 | * This program is free software; you can redistribute it and/or modify | ||
7 | * it under the terms of the GNU General Public License as published by | ||
8 | * the Free Software Foundation; either version 2 of the License, or | ||
9 | * (at your option) any later version. | ||
10 | * | ||
11 | * This program is distributed in the hope that it will be useful, | ||
12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
14 | * GNU General Public License for more details. | ||
15 | * | ||
16 | * You should have received a copy of the GNU General Public License | ||
17 | * along with this program; if not, see <http://www.gnu.org/licenses/>. | ||
18 | */ | ||
19 | |||
20 | #ifndef _ZD_MAC_H | ||
21 | #define _ZD_MAC_H | ||
22 | |||
23 | #include <linux/kernel.h> | ||
24 | #include <net/mac80211.h> | ||
25 | |||
26 | #include "zd_chip.h" | ||
27 | |||
28 | struct zd_ctrlset { | ||
29 | u8 modulation; | ||
30 | __le16 tx_length; | ||
31 | u8 control; | ||
32 | /* stores only the difference to tx_length on ZD1211B */ | ||
33 | __le16 packet_length; | ||
34 | __le16 current_length; | ||
35 | u8 service; | ||
36 | __le16 next_frame_length; | ||
37 | } __packed; | ||
38 | |||
39 | #define ZD_CS_RESERVED_SIZE 25 | ||
40 | |||
41 | /* The field modulation of struct zd_ctrlset controls the bit rate, the use | ||
42 | * of short or long preambles in 802.11b (CCK mode) or the use of 802.11a or | ||
43 | * 802.11g in OFDM mode. | ||
44 | * | ||
45 | * The term zd-rate is used for the combination of the modulation type flag | ||
46 | * and the "pure" rate value. | ||
47 | */ | ||
48 | #define ZD_PURE_RATE_MASK 0x0f | ||
49 | #define ZD_MODULATION_TYPE_MASK 0x10 | ||
50 | #define ZD_RATE_MASK (ZD_PURE_RATE_MASK|ZD_MODULATION_TYPE_MASK) | ||
51 | #define ZD_PURE_RATE(modulation) ((modulation) & ZD_PURE_RATE_MASK) | ||
52 | #define ZD_MODULATION_TYPE(modulation) ((modulation) & ZD_MODULATION_TYPE_MASK) | ||
53 | #define ZD_RATE(modulation) ((modulation) & ZD_RATE_MASK) | ||
54 | |||
55 | /* The two possible modulation types. Notify that 802.11b doesn't use the CCK | ||
56 | * codeing for the 1 and 2 MBit/s rate. We stay with the term here to remain | ||
57 | * consistent with uses the term at other places. | ||
58 | */ | ||
59 | #define ZD_CCK 0x00 | ||
60 | #define ZD_OFDM 0x10 | ||
61 | |||
62 | /* The ZD1211 firmware uses proprietary encodings of the 802.11b (CCK) rates. | ||
63 | * For OFDM the PLCP rate encodings are used. We combine these "pure" rates | ||
64 | * with the modulation type flag and call the resulting values zd-rates. | ||
65 | */ | ||
66 | #define ZD_CCK_RATE_1M (ZD_CCK|0x00) | ||
67 | #define ZD_CCK_RATE_2M (ZD_CCK|0x01) | ||
68 | #define ZD_CCK_RATE_5_5M (ZD_CCK|0x02) | ||
69 | #define ZD_CCK_RATE_11M (ZD_CCK|0x03) | ||
70 | #define ZD_OFDM_RATE_6M (ZD_OFDM|ZD_OFDM_PLCP_RATE_6M) | ||
71 | #define ZD_OFDM_RATE_9M (ZD_OFDM|ZD_OFDM_PLCP_RATE_9M) | ||
72 | #define ZD_OFDM_RATE_12M (ZD_OFDM|ZD_OFDM_PLCP_RATE_12M) | ||
73 | #define ZD_OFDM_RATE_18M (ZD_OFDM|ZD_OFDM_PLCP_RATE_18M) | ||
74 | #define ZD_OFDM_RATE_24M (ZD_OFDM|ZD_OFDM_PLCP_RATE_24M) | ||
75 | #define ZD_OFDM_RATE_36M (ZD_OFDM|ZD_OFDM_PLCP_RATE_36M) | ||
76 | #define ZD_OFDM_RATE_48M (ZD_OFDM|ZD_OFDM_PLCP_RATE_48M) | ||
77 | #define ZD_OFDM_RATE_54M (ZD_OFDM|ZD_OFDM_PLCP_RATE_54M) | ||
78 | |||
79 | /* The bit 5 of the zd_ctrlset modulation field controls the preamble in CCK | ||
80 | * mode or the 802.11a/802.11g selection in OFDM mode. | ||
81 | */ | ||
82 | #define ZD_CCK_PREA_LONG 0x00 | ||
83 | #define ZD_CCK_PREA_SHORT 0x20 | ||
84 | #define ZD_OFDM_MODE_11G 0x00 | ||
85 | #define ZD_OFDM_MODE_11A 0x20 | ||
86 | |||
87 | /* zd_ctrlset control field */ | ||
88 | #define ZD_CS_NEED_RANDOM_BACKOFF 0x01 | ||
89 | #define ZD_CS_NO_ACK 0x02 | ||
90 | |||
91 | #define ZD_CS_FRAME_TYPE_MASK 0x0c | ||
92 | #define ZD_CS_DATA_FRAME 0x00 | ||
93 | #define ZD_CS_PS_POLL_FRAME 0x04 | ||
94 | #define ZD_CS_MANAGEMENT_FRAME 0x08 | ||
95 | #define ZD_CS_NO_SEQUENCE_CTL_FRAME 0x0c | ||
96 | |||
97 | #define ZD_CS_WAKE_DESTINATION 0x10 | ||
98 | #define ZD_CS_RTS 0x20 | ||
99 | #define ZD_CS_ENCRYPT 0x40 | ||
100 | #define ZD_CS_SELF_CTS 0x80 | ||
101 | |||
102 | /* Incoming frames are prepended by a PLCP header */ | ||
103 | #define ZD_PLCP_HEADER_SIZE 5 | ||
104 | |||
105 | struct rx_length_info { | ||
106 | __le16 length[3]; | ||
107 | __le16 tag; | ||
108 | } __packed; | ||
109 | |||
110 | #define RX_LENGTH_INFO_TAG 0x697e | ||
111 | |||
112 | struct rx_status { | ||
113 | u8 signal_quality_cck; | ||
114 | /* rssi */ | ||
115 | u8 signal_strength; | ||
116 | u8 signal_quality_ofdm; | ||
117 | u8 decryption_type; | ||
118 | u8 frame_status; | ||
119 | } __packed; | ||
120 | |||
121 | /* rx_status field decryption_type */ | ||
122 | #define ZD_RX_NO_WEP 0 | ||
123 | #define ZD_RX_WEP64 1 | ||
124 | #define ZD_RX_TKIP 2 | ||
125 | #define ZD_RX_AES 4 | ||
126 | #define ZD_RX_WEP128 5 | ||
127 | #define ZD_RX_WEP256 6 | ||
128 | |||
129 | /* rx_status field frame_status */ | ||
130 | #define ZD_RX_FRAME_MODULATION_MASK 0x01 | ||
131 | #define ZD_RX_CCK 0x00 | ||
132 | #define ZD_RX_OFDM 0x01 | ||
133 | |||
134 | #define ZD_RX_TIMEOUT_ERROR 0x02 | ||
135 | #define ZD_RX_FIFO_OVERRUN_ERROR 0x04 | ||
136 | #define ZD_RX_DECRYPTION_ERROR 0x08 | ||
137 | #define ZD_RX_CRC32_ERROR 0x10 | ||
138 | #define ZD_RX_NO_ADDR1_MATCH_ERROR 0x20 | ||
139 | #define ZD_RX_CRC16_ERROR 0x40 | ||
140 | #define ZD_RX_ERROR 0x80 | ||
141 | |||
142 | struct tx_retry_rate { | ||
143 | int count; /* number of valid element in rate[] array */ | ||
144 | int rate[10]; /* retry rates, described by an index in zd_rates[] */ | ||
145 | }; | ||
146 | |||
147 | struct tx_status { | ||
148 | u8 type; /* must always be 0x01 : USB_INT_TYPE */ | ||
149 | u8 id; /* must always be 0xa0 : USB_INT_ID_RETRY_FAILED */ | ||
150 | u8 rate; | ||
151 | u8 pad; | ||
152 | u8 mac[ETH_ALEN]; | ||
153 | u8 retry; | ||
154 | u8 failure; | ||
155 | } __packed; | ||
156 | |||
157 | enum mac_flags { | ||
158 | MAC_FIXED_CHANNEL = 0x01, | ||
159 | }; | ||
160 | |||
161 | struct housekeeping { | ||
162 | struct delayed_work link_led_work; | ||
163 | }; | ||
164 | |||
165 | struct beacon { | ||
166 | struct delayed_work watchdog_work; | ||
167 | struct sk_buff *cur_beacon; | ||
168 | unsigned long last_update; | ||
169 | u16 interval; | ||
170 | u8 period; | ||
171 | }; | ||
172 | |||
173 | enum zd_device_flags { | ||
174 | ZD_DEVICE_RUNNING, | ||
175 | }; | ||
176 | |||
177 | #define ZD_MAC_STATS_BUFFER_SIZE 16 | ||
178 | |||
179 | #define ZD_MAC_MAX_ACK_WAITERS 50 | ||
180 | |||
181 | struct zd_mac { | ||
182 | struct zd_chip chip; | ||
183 | spinlock_t lock; | ||
184 | spinlock_t intr_lock; | ||
185 | struct ieee80211_hw *hw; | ||
186 | struct ieee80211_vif *vif; | ||
187 | struct housekeeping housekeeping; | ||
188 | struct beacon beacon; | ||
189 | struct work_struct set_rts_cts_work; | ||
190 | struct work_struct process_intr; | ||
191 | struct zd_mc_hash multicast_hash; | ||
192 | u8 intr_buffer[USB_MAX_EP_INT_BUFFER]; | ||
193 | u8 regdomain; | ||
194 | u8 default_regdomain; | ||
195 | u8 channel; | ||
196 | int type; | ||
197 | int associated; | ||
198 | unsigned long flags; | ||
199 | struct sk_buff_head ack_wait_queue; | ||
200 | struct ieee80211_channel channels[14]; | ||
201 | struct ieee80211_rate rates[12]; | ||
202 | struct ieee80211_supported_band band; | ||
203 | |||
204 | /* Short preamble (used for RTS/CTS) */ | ||
205 | unsigned int short_preamble:1; | ||
206 | |||
207 | /* whether to pass frames with CRC errors to stack */ | ||
208 | unsigned int pass_failed_fcs:1; | ||
209 | |||
210 | /* whether to pass control frames to stack */ | ||
211 | unsigned int pass_ctrl:1; | ||
212 | |||
213 | /* whether we have received a 802.11 ACK that is pending */ | ||
214 | unsigned int ack_pending:1; | ||
215 | |||
216 | /* signal strength of the last 802.11 ACK received */ | ||
217 | int ack_signal; | ||
218 | }; | ||
219 | |||
220 | #define ZD_REGDOMAIN_FCC 0x10 | ||
221 | #define ZD_REGDOMAIN_IC 0x20 | ||
222 | #define ZD_REGDOMAIN_ETSI 0x30 | ||
223 | #define ZD_REGDOMAIN_SPAIN 0x31 | ||
224 | #define ZD_REGDOMAIN_FRANCE 0x32 | ||
225 | #define ZD_REGDOMAIN_JAPAN_2 0x40 | ||
226 | #define ZD_REGDOMAIN_JAPAN 0x41 | ||
227 | #define ZD_REGDOMAIN_JAPAN_3 0x49 | ||
228 | |||
229 | enum { | ||
230 | MIN_CHANNEL24 = 1, | ||
231 | MAX_CHANNEL24 = 14, | ||
232 | }; | ||
233 | |||
234 | #define ZD_PLCP_SERVICE_LENGTH_EXTENSION 0x80 | ||
235 | |||
236 | struct ofdm_plcp_header { | ||
237 | u8 prefix[3]; | ||
238 | __le16 service; | ||
239 | } __packed; | ||
240 | |||
241 | static inline u8 zd_ofdm_plcp_header_rate(const struct ofdm_plcp_header *header) | ||
242 | { | ||
243 | return header->prefix[0] & 0xf; | ||
244 | } | ||
245 | |||
246 | /* The following defines give the encoding of the 4-bit rate field in the | ||
247 | * OFDM (802.11a/802.11g) PLCP header. Notify that these values are used to | ||
248 | * define the zd-rate values for OFDM. | ||
249 | * | ||
250 | * See the struct zd_ctrlset definition in zd_mac.h. | ||
251 | */ | ||
252 | #define ZD_OFDM_PLCP_RATE_6M 0xb | ||
253 | #define ZD_OFDM_PLCP_RATE_9M 0xf | ||
254 | #define ZD_OFDM_PLCP_RATE_12M 0xa | ||
255 | #define ZD_OFDM_PLCP_RATE_18M 0xe | ||
256 | #define ZD_OFDM_PLCP_RATE_24M 0x9 | ||
257 | #define ZD_OFDM_PLCP_RATE_36M 0xd | ||
258 | #define ZD_OFDM_PLCP_RATE_48M 0x8 | ||
259 | #define ZD_OFDM_PLCP_RATE_54M 0xc | ||
260 | |||
261 | struct cck_plcp_header { | ||
262 | u8 signal; | ||
263 | u8 service; | ||
264 | __le16 length; | ||
265 | __le16 crc16; | ||
266 | } __packed; | ||
267 | |||
268 | static inline u8 zd_cck_plcp_header_signal(const struct cck_plcp_header *header) | ||
269 | { | ||
270 | return header->signal; | ||
271 | } | ||
272 | |||
273 | /* These defines give the encodings of the signal field in the 802.11b PLCP | ||
274 | * header. The signal field gives the bit rate of the following packet. Even | ||
275 | * if technically wrong we use CCK here also for the 1 MBit/s and 2 MBit/s | ||
276 | * rate to stay consistent with Zydas and our use of the term. | ||
277 | * | ||
278 | * Notify that these values are *not* used in the zd-rates. | ||
279 | */ | ||
280 | #define ZD_CCK_PLCP_SIGNAL_1M 0x0a | ||
281 | #define ZD_CCK_PLCP_SIGNAL_2M 0x14 | ||
282 | #define ZD_CCK_PLCP_SIGNAL_5M5 0x37 | ||
283 | #define ZD_CCK_PLCP_SIGNAL_11M 0x6e | ||
284 | |||
285 | static inline struct zd_mac *zd_hw_mac(struct ieee80211_hw *hw) | ||
286 | { | ||
287 | return hw->priv; | ||
288 | } | ||
289 | |||
290 | static inline struct zd_mac *zd_chip_to_mac(struct zd_chip *chip) | ||
291 | { | ||
292 | return container_of(chip, struct zd_mac, chip); | ||
293 | } | ||
294 | |||
295 | static inline struct zd_mac *zd_usb_to_mac(struct zd_usb *usb) | ||
296 | { | ||
297 | return zd_chip_to_mac(zd_usb_to_chip(usb)); | ||
298 | } | ||
299 | |||
300 | static inline u8 *zd_mac_get_perm_addr(struct zd_mac *mac) | ||
301 | { | ||
302 | return mac->hw->wiphy->perm_addr; | ||
303 | } | ||
304 | |||
305 | #define zd_mac_dev(mac) (zd_chip_dev(&(mac)->chip)) | ||
306 | |||
307 | struct ieee80211_hw *zd_mac_alloc_hw(struct usb_interface *intf); | ||
308 | void zd_mac_clear(struct zd_mac *mac); | ||
309 | |||
310 | int zd_mac_preinit_hw(struct ieee80211_hw *hw); | ||
311 | int zd_mac_init_hw(struct ieee80211_hw *hw); | ||
312 | |||
313 | int zd_mac_rx(struct ieee80211_hw *hw, const u8 *buffer, unsigned int length); | ||
314 | void zd_mac_tx_failed(struct urb *urb); | ||
315 | void zd_mac_tx_to_dev(struct sk_buff *skb, int error); | ||
316 | |||
317 | int zd_op_start(struct ieee80211_hw *hw); | ||
318 | void zd_op_stop(struct ieee80211_hw *hw); | ||
319 | int zd_restore_settings(struct zd_mac *mac); | ||
320 | |||
321 | #ifdef DEBUG | ||
322 | void zd_dump_rx_status(const struct rx_status *status); | ||
323 | #else | ||
324 | #define zd_dump_rx_status(status) | ||
325 | #endif /* DEBUG */ | ||
326 | |||
327 | #endif /* _ZD_MAC_H */ | ||
diff --git a/drivers/net/wireless/zydas/zd1211rw/zd_rf.c b/drivers/net/wireless/zydas/zd1211rw/zd_rf.c new file mode 100644 index 000000000000..dc179c414518 --- /dev/null +++ b/drivers/net/wireless/zydas/zd1211rw/zd_rf.c | |||
@@ -0,0 +1,181 @@ | |||
1 | /* ZD1211 USB-WLAN driver for Linux | ||
2 | * | ||
3 | * Copyright (C) 2005-2007 Ulrich Kunitz <kune@deine-taler.de> | ||
4 | * Copyright (C) 2006-2007 Daniel Drake <dsd@gentoo.org> | ||
5 | * | ||
6 | * This program is free software; you can redistribute it and/or modify | ||
7 | * it under the terms of the GNU General Public License as published by | ||
8 | * the Free Software Foundation; either version 2 of the License, or | ||
9 | * (at your option) any later version. | ||
10 | * | ||
11 | * This program is distributed in the hope that it will be useful, | ||
12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
14 | * GNU General Public License for more details. | ||
15 | * | ||
16 | * You should have received a copy of the GNU General Public License | ||
17 | * along with this program; if not, see <http://www.gnu.org/licenses/>. | ||
18 | */ | ||
19 | |||
20 | #include <linux/errno.h> | ||
21 | #include <linux/string.h> | ||
22 | |||
23 | #include "zd_def.h" | ||
24 | #include "zd_rf.h" | ||
25 | #include "zd_mac.h" | ||
26 | #include "zd_chip.h" | ||
27 | |||
28 | static const char * const rfs[] = { | ||
29 | [0] = "unknown RF0", | ||
30 | [1] = "unknown RF1", | ||
31 | [UW2451_RF] = "UW2451_RF", | ||
32 | [UCHIP_RF] = "UCHIP_RF", | ||
33 | [AL2230_RF] = "AL2230_RF", | ||
34 | [AL7230B_RF] = "AL7230B_RF", | ||
35 | [THETA_RF] = "THETA_RF", | ||
36 | [AL2210_RF] = "AL2210_RF", | ||
37 | [MAXIM_NEW_RF] = "MAXIM_NEW_RF", | ||
38 | [UW2453_RF] = "UW2453_RF", | ||
39 | [AL2230S_RF] = "AL2230S_RF", | ||
40 | [RALINK_RF] = "RALINK_RF", | ||
41 | [INTERSIL_RF] = "INTERSIL_RF", | ||
42 | [RF2959_RF] = "RF2959_RF", | ||
43 | [MAXIM_NEW2_RF] = "MAXIM_NEW2_RF", | ||
44 | [PHILIPS_RF] = "PHILIPS_RF", | ||
45 | }; | ||
46 | |||
47 | const char *zd_rf_name(u8 type) | ||
48 | { | ||
49 | if (type & 0xf0) | ||
50 | type = 0; | ||
51 | return rfs[type]; | ||
52 | } | ||
53 | |||
54 | void zd_rf_init(struct zd_rf *rf) | ||
55 | { | ||
56 | memset(rf, 0, sizeof(*rf)); | ||
57 | |||
58 | /* default to update channel integration, as almost all RF's do want | ||
59 | * this */ | ||
60 | rf->update_channel_int = 1; | ||
61 | } | ||
62 | |||
63 | void zd_rf_clear(struct zd_rf *rf) | ||
64 | { | ||
65 | if (rf->clear) | ||
66 | rf->clear(rf); | ||
67 | ZD_MEMCLEAR(rf, sizeof(*rf)); | ||
68 | } | ||
69 | |||
70 | int zd_rf_init_hw(struct zd_rf *rf, u8 type) | ||
71 | { | ||
72 | int r = 0; | ||
73 | int t; | ||
74 | struct zd_chip *chip = zd_rf_to_chip(rf); | ||
75 | |||
76 | ZD_ASSERT(mutex_is_locked(&chip->mutex)); | ||
77 | switch (type) { | ||
78 | case RF2959_RF: | ||
79 | r = zd_rf_init_rf2959(rf); | ||
80 | break; | ||
81 | case AL2230_RF: | ||
82 | case AL2230S_RF: | ||
83 | r = zd_rf_init_al2230(rf); | ||
84 | break; | ||
85 | case AL7230B_RF: | ||
86 | r = zd_rf_init_al7230b(rf); | ||
87 | break; | ||
88 | case MAXIM_NEW_RF: | ||
89 | case UW2453_RF: | ||
90 | r = zd_rf_init_uw2453(rf); | ||
91 | break; | ||
92 | default: | ||
93 | dev_err(zd_chip_dev(chip), | ||
94 | "RF %s %#x is not supported\n", zd_rf_name(type), type); | ||
95 | rf->type = 0; | ||
96 | return -ENODEV; | ||
97 | } | ||
98 | |||
99 | if (r) | ||
100 | return r; | ||
101 | |||
102 | rf->type = type; | ||
103 | |||
104 | r = zd_chip_lock_phy_regs(chip); | ||
105 | if (r) | ||
106 | return r; | ||
107 | t = rf->init_hw(rf); | ||
108 | r = zd_chip_unlock_phy_regs(chip); | ||
109 | if (t) | ||
110 | r = t; | ||
111 | return r; | ||
112 | } | ||
113 | |||
114 | int zd_rf_scnprint_id(struct zd_rf *rf, char *buffer, size_t size) | ||
115 | { | ||
116 | return scnprintf(buffer, size, "%s", zd_rf_name(rf->type)); | ||
117 | } | ||
118 | |||
119 | int zd_rf_set_channel(struct zd_rf *rf, u8 channel) | ||
120 | { | ||
121 | int r; | ||
122 | |||
123 | ZD_ASSERT(mutex_is_locked(&zd_rf_to_chip(rf)->mutex)); | ||
124 | if (channel < MIN_CHANNEL24) | ||
125 | return -EINVAL; | ||
126 | if (channel > MAX_CHANNEL24) | ||
127 | return -EINVAL; | ||
128 | dev_dbg_f(zd_chip_dev(zd_rf_to_chip(rf)), "channel: %d\n", channel); | ||
129 | |||
130 | r = rf->set_channel(rf, channel); | ||
131 | if (r >= 0) | ||
132 | rf->channel = channel; | ||
133 | return r; | ||
134 | } | ||
135 | |||
136 | int zd_switch_radio_on(struct zd_rf *rf) | ||
137 | { | ||
138 | int r, t; | ||
139 | struct zd_chip *chip = zd_rf_to_chip(rf); | ||
140 | |||
141 | ZD_ASSERT(mutex_is_locked(&chip->mutex)); | ||
142 | r = zd_chip_lock_phy_regs(chip); | ||
143 | if (r) | ||
144 | return r; | ||
145 | t = rf->switch_radio_on(rf); | ||
146 | r = zd_chip_unlock_phy_regs(chip); | ||
147 | if (t) | ||
148 | r = t; | ||
149 | return r; | ||
150 | } | ||
151 | |||
152 | int zd_switch_radio_off(struct zd_rf *rf) | ||
153 | { | ||
154 | int r, t; | ||
155 | struct zd_chip *chip = zd_rf_to_chip(rf); | ||
156 | |||
157 | /* TODO: move phy regs handling to zd_chip */ | ||
158 | ZD_ASSERT(mutex_is_locked(&chip->mutex)); | ||
159 | r = zd_chip_lock_phy_regs(chip); | ||
160 | if (r) | ||
161 | return r; | ||
162 | t = rf->switch_radio_off(rf); | ||
163 | r = zd_chip_unlock_phy_regs(chip); | ||
164 | if (t) | ||
165 | r = t; | ||
166 | return r; | ||
167 | } | ||
168 | |||
169 | int zd_rf_patch_6m_band_edge(struct zd_rf *rf, u8 channel) | ||
170 | { | ||
171 | if (!rf->patch_6m_band_edge) | ||
172 | return 0; | ||
173 | |||
174 | return rf->patch_6m_band_edge(rf, channel); | ||
175 | } | ||
176 | |||
177 | int zd_rf_generic_patch_6m(struct zd_rf *rf, u8 channel) | ||
178 | { | ||
179 | return zd_chip_generic_patch_6m_band(zd_rf_to_chip(rf), channel); | ||
180 | } | ||
181 | |||
diff --git a/drivers/net/wireless/zydas/zd1211rw/zd_rf.h b/drivers/net/wireless/zydas/zd1211rw/zd_rf.h new file mode 100644 index 000000000000..8f14e25e1041 --- /dev/null +++ b/drivers/net/wireless/zydas/zd1211rw/zd_rf.h | |||
@@ -0,0 +1,110 @@ | |||
1 | /* ZD1211 USB-WLAN driver for Linux | ||
2 | * | ||
3 | * Copyright (C) 2005-2007 Ulrich Kunitz <kune@deine-taler.de> | ||
4 | * Copyright (C) 2006-2007 Daniel Drake <dsd@gentoo.org> | ||
5 | * | ||
6 | * This program is free software; you can redistribute it and/or modify | ||
7 | * it under the terms of the GNU General Public License as published by | ||
8 | * the Free Software Foundation; either version 2 of the License, or | ||
9 | * (at your option) any later version. | ||
10 | * | ||
11 | * This program is distributed in the hope that it will be useful, | ||
12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
14 | * GNU General Public License for more details. | ||
15 | * | ||
16 | * You should have received a copy of the GNU General Public License | ||
17 | * along with this program; if not, see <http://www.gnu.org/licenses/>. | ||
18 | */ | ||
19 | |||
20 | #ifndef _ZD_RF_H | ||
21 | #define _ZD_RF_H | ||
22 | |||
23 | #define UW2451_RF 0x2 | ||
24 | #define UCHIP_RF 0x3 | ||
25 | #define AL2230_RF 0x4 | ||
26 | #define AL7230B_RF 0x5 /* a,b,g */ | ||
27 | #define THETA_RF 0x6 | ||
28 | #define AL2210_RF 0x7 | ||
29 | #define MAXIM_NEW_RF 0x8 | ||
30 | #define UW2453_RF 0x9 | ||
31 | #define AL2230S_RF 0xa | ||
32 | #define RALINK_RF 0xb | ||
33 | #define INTERSIL_RF 0xc | ||
34 | #define RF2959_RF 0xd | ||
35 | #define MAXIM_NEW2_RF 0xe | ||
36 | #define PHILIPS_RF 0xf | ||
37 | |||
38 | #define RF_CHANNEL(ch) [(ch)-1] | ||
39 | |||
40 | /* Provides functions of the RF transceiver. */ | ||
41 | |||
42 | enum { | ||
43 | RF_REG_BITS = 6, | ||
44 | RF_VALUE_BITS = 18, | ||
45 | RF_RV_BITS = RF_REG_BITS + RF_VALUE_BITS, | ||
46 | }; | ||
47 | |||
48 | struct zd_rf { | ||
49 | u8 type; | ||
50 | |||
51 | u8 channel; | ||
52 | |||
53 | /* whether channel integration and calibration should be updated | ||
54 | * defaults to 1 (yes) */ | ||
55 | u8 update_channel_int:1; | ||
56 | |||
57 | /* whether ZD_CR47 should be patched from the EEPROM, if the appropriate | ||
58 | * flag is set in the POD. The vendor driver suggests that this should | ||
59 | * be done for all RF's, but a bug in their code prevents but their | ||
60 | * HW_OverWritePhyRegFromE2P() routine from ever taking effect. */ | ||
61 | u8 patch_cck_gain:1; | ||
62 | |||
63 | /* private RF driver data */ | ||
64 | void *priv; | ||
65 | |||
66 | /* RF-specific functions */ | ||
67 | int (*init_hw)(struct zd_rf *rf); | ||
68 | int (*set_channel)(struct zd_rf *rf, u8 channel); | ||
69 | int (*switch_radio_on)(struct zd_rf *rf); | ||
70 | int (*switch_radio_off)(struct zd_rf *rf); | ||
71 | int (*patch_6m_band_edge)(struct zd_rf *rf, u8 channel); | ||
72 | void (*clear)(struct zd_rf *rf); | ||
73 | }; | ||
74 | |||
75 | const char *zd_rf_name(u8 type); | ||
76 | void zd_rf_init(struct zd_rf *rf); | ||
77 | void zd_rf_clear(struct zd_rf *rf); | ||
78 | int zd_rf_init_hw(struct zd_rf *rf, u8 type); | ||
79 | |||
80 | int zd_rf_scnprint_id(struct zd_rf *rf, char *buffer, size_t size); | ||
81 | |||
82 | int zd_rf_set_channel(struct zd_rf *rf, u8 channel); | ||
83 | |||
84 | int zd_switch_radio_on(struct zd_rf *rf); | ||
85 | int zd_switch_radio_off(struct zd_rf *rf); | ||
86 | |||
87 | int zd_rf_patch_6m_band_edge(struct zd_rf *rf, u8 channel); | ||
88 | int zd_rf_generic_patch_6m(struct zd_rf *rf, u8 channel); | ||
89 | |||
90 | static inline int zd_rf_should_update_pwr_int(struct zd_rf *rf) | ||
91 | { | ||
92 | return rf->update_channel_int; | ||
93 | } | ||
94 | |||
95 | static inline int zd_rf_should_patch_cck_gain(struct zd_rf *rf) | ||
96 | { | ||
97 | return rf->patch_cck_gain; | ||
98 | } | ||
99 | |||
100 | int zd_rf_patch_6m_band_edge(struct zd_rf *rf, u8 channel); | ||
101 | int zd_rf_generic_patch_6m(struct zd_rf *rf, u8 channel); | ||
102 | |||
103 | /* Functions for individual RF chips */ | ||
104 | |||
105 | int zd_rf_init_rf2959(struct zd_rf *rf); | ||
106 | int zd_rf_init_al2230(struct zd_rf *rf); | ||
107 | int zd_rf_init_al7230b(struct zd_rf *rf); | ||
108 | int zd_rf_init_uw2453(struct zd_rf *rf); | ||
109 | |||
110 | #endif /* _ZD_RF_H */ | ||
diff --git a/drivers/net/wireless/zydas/zd1211rw/zd_rf_al2230.c b/drivers/net/wireless/zydas/zd1211rw/zd_rf_al2230.c new file mode 100644 index 000000000000..99aed7d78952 --- /dev/null +++ b/drivers/net/wireless/zydas/zd1211rw/zd_rf_al2230.c | |||
@@ -0,0 +1,443 @@ | |||
1 | /* ZD1211 USB-WLAN driver for Linux | ||
2 | * | ||
3 | * Copyright (C) 2005-2007 Ulrich Kunitz <kune@deine-taler.de> | ||
4 | * Copyright (C) 2006-2007 Daniel Drake <dsd@gentoo.org> | ||
5 | * | ||
6 | * This program is free software; you can redistribute it and/or modify | ||
7 | * it under the terms of the GNU General Public License as published by | ||
8 | * the Free Software Foundation; either version 2 of the License, or | ||
9 | * (at your option) any later version. | ||
10 | * | ||
11 | * This program is distributed in the hope that it will be useful, | ||
12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
14 | * GNU General Public License for more details. | ||
15 | * | ||
16 | * You should have received a copy of the GNU General Public License | ||
17 | * along with this program; if not, see <http://www.gnu.org/licenses/>. | ||
18 | */ | ||
19 | |||
20 | #include <linux/kernel.h> | ||
21 | |||
22 | #include "zd_rf.h" | ||
23 | #include "zd_usb.h" | ||
24 | #include "zd_chip.h" | ||
25 | |||
26 | #define IS_AL2230S(chip) ((chip)->al2230s_bit || (chip)->rf.type == AL2230S_RF) | ||
27 | |||
28 | static const u32 zd1211_al2230_table[][3] = { | ||
29 | RF_CHANNEL( 1) = { 0x03f790, 0x033331, 0x00000d, }, | ||
30 | RF_CHANNEL( 2) = { 0x03f790, 0x0b3331, 0x00000d, }, | ||
31 | RF_CHANNEL( 3) = { 0x03e790, 0x033331, 0x00000d, }, | ||
32 | RF_CHANNEL( 4) = { 0x03e790, 0x0b3331, 0x00000d, }, | ||
33 | RF_CHANNEL( 5) = { 0x03f7a0, 0x033331, 0x00000d, }, | ||
34 | RF_CHANNEL( 6) = { 0x03f7a0, 0x0b3331, 0x00000d, }, | ||
35 | RF_CHANNEL( 7) = { 0x03e7a0, 0x033331, 0x00000d, }, | ||
36 | RF_CHANNEL( 8) = { 0x03e7a0, 0x0b3331, 0x00000d, }, | ||
37 | RF_CHANNEL( 9) = { 0x03f7b0, 0x033331, 0x00000d, }, | ||
38 | RF_CHANNEL(10) = { 0x03f7b0, 0x0b3331, 0x00000d, }, | ||
39 | RF_CHANNEL(11) = { 0x03e7b0, 0x033331, 0x00000d, }, | ||
40 | RF_CHANNEL(12) = { 0x03e7b0, 0x0b3331, 0x00000d, }, | ||
41 | RF_CHANNEL(13) = { 0x03f7c0, 0x033331, 0x00000d, }, | ||
42 | RF_CHANNEL(14) = { 0x03e7c0, 0x066661, 0x00000d, }, | ||
43 | }; | ||
44 | |||
45 | static const u32 zd1211b_al2230_table[][3] = { | ||
46 | RF_CHANNEL( 1) = { 0x09efc0, 0x8cccc0, 0xb00000, }, | ||
47 | RF_CHANNEL( 2) = { 0x09efc0, 0x8cccd0, 0xb00000, }, | ||
48 | RF_CHANNEL( 3) = { 0x09e7c0, 0x8cccc0, 0xb00000, }, | ||
49 | RF_CHANNEL( 4) = { 0x09e7c0, 0x8cccd0, 0xb00000, }, | ||
50 | RF_CHANNEL( 5) = { 0x05efc0, 0x8cccc0, 0xb00000, }, | ||
51 | RF_CHANNEL( 6) = { 0x05efc0, 0x8cccd0, 0xb00000, }, | ||
52 | RF_CHANNEL( 7) = { 0x05e7c0, 0x8cccc0, 0xb00000, }, | ||
53 | RF_CHANNEL( 8) = { 0x05e7c0, 0x8cccd0, 0xb00000, }, | ||
54 | RF_CHANNEL( 9) = { 0x0defc0, 0x8cccc0, 0xb00000, }, | ||
55 | RF_CHANNEL(10) = { 0x0defc0, 0x8cccd0, 0xb00000, }, | ||
56 | RF_CHANNEL(11) = { 0x0de7c0, 0x8cccc0, 0xb00000, }, | ||
57 | RF_CHANNEL(12) = { 0x0de7c0, 0x8cccd0, 0xb00000, }, | ||
58 | RF_CHANNEL(13) = { 0x03efc0, 0x8cccc0, 0xb00000, }, | ||
59 | RF_CHANNEL(14) = { 0x03e7c0, 0x866660, 0xb00000, }, | ||
60 | }; | ||
61 | |||
62 | static const struct zd_ioreq16 zd1211b_ioreqs_shared_1[] = { | ||
63 | { ZD_CR240, 0x57 }, { ZD_CR9, 0xe0 }, | ||
64 | }; | ||
65 | |||
66 | static const struct zd_ioreq16 ioreqs_init_al2230s[] = { | ||
67 | { ZD_CR47, 0x1e }, /* MARK_002 */ | ||
68 | { ZD_CR106, 0x22 }, | ||
69 | { ZD_CR107, 0x2a }, /* MARK_002 */ | ||
70 | { ZD_CR109, 0x13 }, /* MARK_002 */ | ||
71 | { ZD_CR118, 0xf8 }, /* MARK_002 */ | ||
72 | { ZD_CR119, 0x12 }, { ZD_CR122, 0xe0 }, | ||
73 | { ZD_CR128, 0x10 }, /* MARK_001 from 0xe->0x10 */ | ||
74 | { ZD_CR129, 0x0e }, /* MARK_001 from 0xd->0x0e */ | ||
75 | { ZD_CR130, 0x10 }, /* MARK_001 from 0xb->0x0d */ | ||
76 | }; | ||
77 | |||
78 | static int zd1211b_al2230_finalize_rf(struct zd_chip *chip) | ||
79 | { | ||
80 | int r; | ||
81 | static const struct zd_ioreq16 ioreqs[] = { | ||
82 | { ZD_CR80, 0x30 }, { ZD_CR81, 0x30 }, { ZD_CR79, 0x58 }, | ||
83 | { ZD_CR12, 0xf0 }, { ZD_CR77, 0x1b }, { ZD_CR78, 0x58 }, | ||
84 | { ZD_CR203, 0x06 }, | ||
85 | { }, | ||
86 | |||
87 | { ZD_CR240, 0x80 }, | ||
88 | }; | ||
89 | |||
90 | r = zd_iowrite16a_locked(chip, ioreqs, ARRAY_SIZE(ioreqs)); | ||
91 | if (r) | ||
92 | return r; | ||
93 | |||
94 | /* related to antenna selection? */ | ||
95 | if (chip->new_phy_layout) { | ||
96 | r = zd_iowrite16_locked(chip, 0xe1, ZD_CR9); | ||
97 | if (r) | ||
98 | return r; | ||
99 | } | ||
100 | |||
101 | return zd_iowrite16_locked(chip, 0x06, ZD_CR203); | ||
102 | } | ||
103 | |||
104 | static int zd1211_al2230_init_hw(struct zd_rf *rf) | ||
105 | { | ||
106 | int r; | ||
107 | struct zd_chip *chip = zd_rf_to_chip(rf); | ||
108 | |||
109 | static const struct zd_ioreq16 ioreqs_init[] = { | ||
110 | { ZD_CR15, 0x20 }, { ZD_CR23, 0x40 }, { ZD_CR24, 0x20 }, | ||
111 | { ZD_CR26, 0x11 }, { ZD_CR28, 0x3e }, { ZD_CR29, 0x00 }, | ||
112 | { ZD_CR44, 0x33 }, { ZD_CR106, 0x2a }, { ZD_CR107, 0x1a }, | ||
113 | { ZD_CR109, 0x09 }, { ZD_CR110, 0x27 }, { ZD_CR111, 0x2b }, | ||
114 | { ZD_CR112, 0x2b }, { ZD_CR119, 0x0a }, { ZD_CR10, 0x89 }, | ||
115 | /* for newest (3rd cut) AL2300 */ | ||
116 | { ZD_CR17, 0x28 }, | ||
117 | { ZD_CR26, 0x93 }, { ZD_CR34, 0x30 }, | ||
118 | /* for newest (3rd cut) AL2300 */ | ||
119 | { ZD_CR35, 0x3e }, | ||
120 | { ZD_CR41, 0x24 }, { ZD_CR44, 0x32 }, | ||
121 | /* for newest (3rd cut) AL2300 */ | ||
122 | { ZD_CR46, 0x96 }, | ||
123 | { ZD_CR47, 0x1e }, { ZD_CR79, 0x58 }, { ZD_CR80, 0x30 }, | ||
124 | { ZD_CR81, 0x30 }, { ZD_CR87, 0x0a }, { ZD_CR89, 0x04 }, | ||
125 | { ZD_CR92, 0x0a }, { ZD_CR99, 0x28 }, { ZD_CR100, 0x00 }, | ||
126 | { ZD_CR101, 0x13 }, { ZD_CR102, 0x27 }, { ZD_CR106, 0x24 }, | ||
127 | { ZD_CR107, 0x2a }, { ZD_CR109, 0x09 }, { ZD_CR110, 0x13 }, | ||
128 | { ZD_CR111, 0x1f }, { ZD_CR112, 0x1f }, { ZD_CR113, 0x27 }, | ||
129 | { ZD_CR114, 0x27 }, | ||
130 | /* for newest (3rd cut) AL2300 */ | ||
131 | { ZD_CR115, 0x24 }, | ||
132 | { ZD_CR116, 0x24 }, { ZD_CR117, 0xf4 }, { ZD_CR118, 0xfc }, | ||
133 | { ZD_CR119, 0x10 }, { ZD_CR120, 0x4f }, { ZD_CR121, 0x77 }, | ||
134 | { ZD_CR122, 0xe0 }, { ZD_CR137, 0x88 }, { ZD_CR252, 0xff }, | ||
135 | { ZD_CR253, 0xff }, | ||
136 | }; | ||
137 | |||
138 | static const struct zd_ioreq16 ioreqs_pll[] = { | ||
139 | /* shdnb(PLL_ON)=0 */ | ||
140 | { ZD_CR251, 0x2f }, | ||
141 | /* shdnb(PLL_ON)=1 */ | ||
142 | { ZD_CR251, 0x3f }, | ||
143 | { ZD_CR138, 0x28 }, { ZD_CR203, 0x06 }, | ||
144 | }; | ||
145 | |||
146 | static const u32 rv1[] = { | ||
147 | /* Channel 1 */ | ||
148 | 0x03f790, | ||
149 | 0x033331, | ||
150 | 0x00000d, | ||
151 | |||
152 | 0x0b3331, | ||
153 | 0x03b812, | ||
154 | 0x00fff3, | ||
155 | }; | ||
156 | |||
157 | static const u32 rv2[] = { | ||
158 | 0x000da4, | ||
159 | 0x0f4dc5, /* fix freq shift, 0x04edc5 */ | ||
160 | 0x0805b6, | ||
161 | 0x011687, | ||
162 | 0x000688, | ||
163 | 0x0403b9, /* external control TX power (ZD_CR31) */ | ||
164 | 0x00dbba, | ||
165 | 0x00099b, | ||
166 | 0x0bdffc, | ||
167 | 0x00000d, | ||
168 | 0x00500f, | ||
169 | }; | ||
170 | |||
171 | static const u32 rv3[] = { | ||
172 | 0x00d00f, | ||
173 | 0x004c0f, | ||
174 | 0x00540f, | ||
175 | 0x00700f, | ||
176 | 0x00500f, | ||
177 | }; | ||
178 | |||
179 | r = zd_iowrite16a_locked(chip, ioreqs_init, ARRAY_SIZE(ioreqs_init)); | ||
180 | if (r) | ||
181 | return r; | ||
182 | |||
183 | if (IS_AL2230S(chip)) { | ||
184 | r = zd_iowrite16a_locked(chip, ioreqs_init_al2230s, | ||
185 | ARRAY_SIZE(ioreqs_init_al2230s)); | ||
186 | if (r) | ||
187 | return r; | ||
188 | } | ||
189 | |||
190 | r = zd_rfwritev_locked(chip, rv1, ARRAY_SIZE(rv1), RF_RV_BITS); | ||
191 | if (r) | ||
192 | return r; | ||
193 | |||
194 | /* improve band edge for AL2230S */ | ||
195 | if (IS_AL2230S(chip)) | ||
196 | r = zd_rfwrite_locked(chip, 0x000824, RF_RV_BITS); | ||
197 | else | ||
198 | r = zd_rfwrite_locked(chip, 0x0005a4, RF_RV_BITS); | ||
199 | if (r) | ||
200 | return r; | ||
201 | |||
202 | r = zd_rfwritev_locked(chip, rv2, ARRAY_SIZE(rv2), RF_RV_BITS); | ||
203 | if (r) | ||
204 | return r; | ||
205 | |||
206 | r = zd_iowrite16a_locked(chip, ioreqs_pll, ARRAY_SIZE(ioreqs_pll)); | ||
207 | if (r) | ||
208 | return r; | ||
209 | |||
210 | r = zd_rfwritev_locked(chip, rv3, ARRAY_SIZE(rv3), RF_RV_BITS); | ||
211 | if (r) | ||
212 | return r; | ||
213 | |||
214 | return 0; | ||
215 | } | ||
216 | |||
217 | static int zd1211b_al2230_init_hw(struct zd_rf *rf) | ||
218 | { | ||
219 | int r; | ||
220 | struct zd_chip *chip = zd_rf_to_chip(rf); | ||
221 | |||
222 | static const struct zd_ioreq16 ioreqs1[] = { | ||
223 | { ZD_CR10, 0x89 }, { ZD_CR15, 0x20 }, | ||
224 | { ZD_CR17, 0x2B }, /* for newest(3rd cut) AL2230 */ | ||
225 | { ZD_CR23, 0x40 }, { ZD_CR24, 0x20 }, { ZD_CR26, 0x93 }, | ||
226 | { ZD_CR28, 0x3e }, { ZD_CR29, 0x00 }, | ||
227 | { ZD_CR33, 0x28 }, /* 5621 */ | ||
228 | { ZD_CR34, 0x30 }, | ||
229 | { ZD_CR35, 0x3e }, /* for newest(3rd cut) AL2230 */ | ||
230 | { ZD_CR41, 0x24 }, { ZD_CR44, 0x32 }, | ||
231 | { ZD_CR46, 0x99 }, /* for newest(3rd cut) AL2230 */ | ||
232 | { ZD_CR47, 0x1e }, | ||
233 | |||
234 | /* ZD1211B 05.06.10 */ | ||
235 | { ZD_CR48, 0x06 }, { ZD_CR49, 0xf9 }, { ZD_CR51, 0x01 }, | ||
236 | { ZD_CR52, 0x80 }, { ZD_CR53, 0x7e }, { ZD_CR65, 0x00 }, | ||
237 | { ZD_CR66, 0x00 }, { ZD_CR67, 0x00 }, { ZD_CR68, 0x00 }, | ||
238 | { ZD_CR69, 0x28 }, | ||
239 | |||
240 | { ZD_CR79, 0x58 }, { ZD_CR80, 0x30 }, { ZD_CR81, 0x30 }, | ||
241 | { ZD_CR87, 0x0a }, { ZD_CR89, 0x04 }, | ||
242 | { ZD_CR91, 0x00 }, /* 5621 */ | ||
243 | { ZD_CR92, 0x0a }, | ||
244 | { ZD_CR98, 0x8d }, /* 4804, for 1212 new algorithm */ | ||
245 | { ZD_CR99, 0x00 }, /* 5621 */ | ||
246 | { ZD_CR101, 0x13 }, { ZD_CR102, 0x27 }, | ||
247 | { ZD_CR106, 0x24 }, /* for newest(3rd cut) AL2230 */ | ||
248 | { ZD_CR107, 0x2a }, | ||
249 | { ZD_CR109, 0x13 }, /* 4804, for 1212 new algorithm */ | ||
250 | { ZD_CR110, 0x1f }, /* 4804, for 1212 new algorithm */ | ||
251 | { ZD_CR111, 0x1f }, { ZD_CR112, 0x1f }, { ZD_CR113, 0x27 }, | ||
252 | { ZD_CR114, 0x27 }, | ||
253 | { ZD_CR115, 0x26 }, /* 24->26 at 4902 for newest(3rd cut) | ||
254 | * AL2230 | ||
255 | */ | ||
256 | { ZD_CR116, 0x24 }, | ||
257 | { ZD_CR117, 0xfa }, /* for 1211b */ | ||
258 | { ZD_CR118, 0xfa }, /* for 1211b */ | ||
259 | { ZD_CR119, 0x10 }, | ||
260 | { ZD_CR120, 0x4f }, | ||
261 | { ZD_CR121, 0x6c }, /* for 1211b */ | ||
262 | { ZD_CR122, 0xfc }, /* E0->FC at 4902 */ | ||
263 | { ZD_CR123, 0x57 }, /* 5623 */ | ||
264 | { ZD_CR125, 0xad }, /* 4804, for 1212 new algorithm */ | ||
265 | { ZD_CR126, 0x6c }, /* 5614 */ | ||
266 | { ZD_CR127, 0x03 }, /* 4804, for 1212 new algorithm */ | ||
267 | { ZD_CR137, 0x50 }, /* 5614 */ | ||
268 | { ZD_CR138, 0xa8 }, | ||
269 | { ZD_CR144, 0xac }, /* 5621 */ | ||
270 | { ZD_CR150, 0x0d }, { ZD_CR252, 0x34 }, { ZD_CR253, 0x34 }, | ||
271 | }; | ||
272 | |||
273 | static const u32 rv1[] = { | ||
274 | 0x8cccd0, | ||
275 | 0x481dc0, | ||
276 | 0xcfff00, | ||
277 | 0x25a000, | ||
278 | }; | ||
279 | |||
280 | static const u32 rv2[] = { | ||
281 | /* To improve AL2230 yield, improve phase noise, 4713 */ | ||
282 | 0x25a000, | ||
283 | 0xa3b2f0, | ||
284 | |||
285 | 0x6da010, /* Reg6 update for MP versio */ | ||
286 | 0xe36280, /* Modified by jxiao for Bor-Chin on 2004/08/02 */ | ||
287 | 0x116000, | ||
288 | 0x9dc020, /* External control TX power (ZD_CR31) */ | ||
289 | 0x5ddb00, /* RegA update for MP version */ | ||
290 | 0xd99000, /* RegB update for MP version */ | ||
291 | 0x3ffbd0, /* RegC update for MP version */ | ||
292 | 0xb00000, /* RegD update for MP version */ | ||
293 | |||
294 | /* improve phase noise and remove phase calibration,4713 */ | ||
295 | 0xf01a00, | ||
296 | }; | ||
297 | |||
298 | static const struct zd_ioreq16 ioreqs2[] = { | ||
299 | { ZD_CR251, 0x2f }, /* shdnb(PLL_ON)=0 */ | ||
300 | { ZD_CR251, 0x7f }, /* shdnb(PLL_ON)=1 */ | ||
301 | }; | ||
302 | |||
303 | static const u32 rv3[] = { | ||
304 | /* To improve AL2230 yield, 4713 */ | ||
305 | 0xf01b00, | ||
306 | 0xf01e00, | ||
307 | 0xf01a00, | ||
308 | }; | ||
309 | |||
310 | static const struct zd_ioreq16 ioreqs3[] = { | ||
311 | /* related to 6M band edge patching, happens unconditionally */ | ||
312 | { ZD_CR128, 0x14 }, { ZD_CR129, 0x12 }, { ZD_CR130, 0x10 }, | ||
313 | }; | ||
314 | |||
315 | r = zd_iowrite16a_locked(chip, zd1211b_ioreqs_shared_1, | ||
316 | ARRAY_SIZE(zd1211b_ioreqs_shared_1)); | ||
317 | if (r) | ||
318 | return r; | ||
319 | r = zd_iowrite16a_locked(chip, ioreqs1, ARRAY_SIZE(ioreqs1)); | ||
320 | if (r) | ||
321 | return r; | ||
322 | |||
323 | if (IS_AL2230S(chip)) { | ||
324 | r = zd_iowrite16a_locked(chip, ioreqs_init_al2230s, | ||
325 | ARRAY_SIZE(ioreqs_init_al2230s)); | ||
326 | if (r) | ||
327 | return r; | ||
328 | } | ||
329 | |||
330 | r = zd_rfwritev_cr_locked(chip, zd1211b_al2230_table[0], 3); | ||
331 | if (r) | ||
332 | return r; | ||
333 | r = zd_rfwritev_cr_locked(chip, rv1, ARRAY_SIZE(rv1)); | ||
334 | if (r) | ||
335 | return r; | ||
336 | |||
337 | if (IS_AL2230S(chip)) | ||
338 | r = zd_rfwrite_locked(chip, 0x241000, RF_RV_BITS); | ||
339 | else | ||
340 | r = zd_rfwrite_locked(chip, 0x25a000, RF_RV_BITS); | ||
341 | if (r) | ||
342 | return r; | ||
343 | |||
344 | r = zd_rfwritev_cr_locked(chip, rv2, ARRAY_SIZE(rv2)); | ||
345 | if (r) | ||
346 | return r; | ||
347 | r = zd_iowrite16a_locked(chip, ioreqs2, ARRAY_SIZE(ioreqs2)); | ||
348 | if (r) | ||
349 | return r; | ||
350 | r = zd_rfwritev_cr_locked(chip, rv3, ARRAY_SIZE(rv3)); | ||
351 | if (r) | ||
352 | return r; | ||
353 | r = zd_iowrite16a_locked(chip, ioreqs3, ARRAY_SIZE(ioreqs3)); | ||
354 | if (r) | ||
355 | return r; | ||
356 | return zd1211b_al2230_finalize_rf(chip); | ||
357 | } | ||
358 | |||
359 | static int zd1211_al2230_set_channel(struct zd_rf *rf, u8 channel) | ||
360 | { | ||
361 | int r; | ||
362 | const u32 *rv = zd1211_al2230_table[channel-1]; | ||
363 | struct zd_chip *chip = zd_rf_to_chip(rf); | ||
364 | static const struct zd_ioreq16 ioreqs[] = { | ||
365 | { ZD_CR138, 0x28 }, | ||
366 | { ZD_CR203, 0x06 }, | ||
367 | }; | ||
368 | |||
369 | r = zd_rfwritev_locked(chip, rv, 3, RF_RV_BITS); | ||
370 | if (r) | ||
371 | return r; | ||
372 | return zd_iowrite16a_locked(chip, ioreqs, ARRAY_SIZE(ioreqs)); | ||
373 | } | ||
374 | |||
375 | static int zd1211b_al2230_set_channel(struct zd_rf *rf, u8 channel) | ||
376 | { | ||
377 | int r; | ||
378 | const u32 *rv = zd1211b_al2230_table[channel-1]; | ||
379 | struct zd_chip *chip = zd_rf_to_chip(rf); | ||
380 | |||
381 | r = zd_iowrite16a_locked(chip, zd1211b_ioreqs_shared_1, | ||
382 | ARRAY_SIZE(zd1211b_ioreqs_shared_1)); | ||
383 | if (r) | ||
384 | return r; | ||
385 | |||
386 | r = zd_rfwritev_cr_locked(chip, rv, 3); | ||
387 | if (r) | ||
388 | return r; | ||
389 | |||
390 | return zd1211b_al2230_finalize_rf(chip); | ||
391 | } | ||
392 | |||
393 | static int zd1211_al2230_switch_radio_on(struct zd_rf *rf) | ||
394 | { | ||
395 | struct zd_chip *chip = zd_rf_to_chip(rf); | ||
396 | static const struct zd_ioreq16 ioreqs[] = { | ||
397 | { ZD_CR11, 0x00 }, | ||
398 | { ZD_CR251, 0x3f }, | ||
399 | }; | ||
400 | |||
401 | return zd_iowrite16a_locked(chip, ioreqs, ARRAY_SIZE(ioreqs)); | ||
402 | } | ||
403 | |||
404 | static int zd1211b_al2230_switch_radio_on(struct zd_rf *rf) | ||
405 | { | ||
406 | struct zd_chip *chip = zd_rf_to_chip(rf); | ||
407 | static const struct zd_ioreq16 ioreqs[] = { | ||
408 | { ZD_CR11, 0x00 }, | ||
409 | { ZD_CR251, 0x7f }, | ||
410 | }; | ||
411 | |||
412 | return zd_iowrite16a_locked(chip, ioreqs, ARRAY_SIZE(ioreqs)); | ||
413 | } | ||
414 | |||
415 | static int al2230_switch_radio_off(struct zd_rf *rf) | ||
416 | { | ||
417 | struct zd_chip *chip = zd_rf_to_chip(rf); | ||
418 | static const struct zd_ioreq16 ioreqs[] = { | ||
419 | { ZD_CR11, 0x04 }, | ||
420 | { ZD_CR251, 0x2f }, | ||
421 | }; | ||
422 | |||
423 | return zd_iowrite16a_locked(chip, ioreqs, ARRAY_SIZE(ioreqs)); | ||
424 | } | ||
425 | |||
426 | int zd_rf_init_al2230(struct zd_rf *rf) | ||
427 | { | ||
428 | struct zd_chip *chip = zd_rf_to_chip(rf); | ||
429 | |||
430 | rf->switch_radio_off = al2230_switch_radio_off; | ||
431 | if (zd_chip_is_zd1211b(chip)) { | ||
432 | rf->init_hw = zd1211b_al2230_init_hw; | ||
433 | rf->set_channel = zd1211b_al2230_set_channel; | ||
434 | rf->switch_radio_on = zd1211b_al2230_switch_radio_on; | ||
435 | } else { | ||
436 | rf->init_hw = zd1211_al2230_init_hw; | ||
437 | rf->set_channel = zd1211_al2230_set_channel; | ||
438 | rf->switch_radio_on = zd1211_al2230_switch_radio_on; | ||
439 | } | ||
440 | rf->patch_6m_band_edge = zd_rf_generic_patch_6m; | ||
441 | rf->patch_cck_gain = 1; | ||
442 | return 0; | ||
443 | } | ||
diff --git a/drivers/net/wireless/zydas/zd1211rw/zd_rf_al7230b.c b/drivers/net/wireless/zydas/zd1211rw/zd_rf_al7230b.c new file mode 100644 index 000000000000..5fea485be574 --- /dev/null +++ b/drivers/net/wireless/zydas/zd1211rw/zd_rf_al7230b.c | |||
@@ -0,0 +1,494 @@ | |||
1 | /* ZD1211 USB-WLAN driver for Linux | ||
2 | * | ||
3 | * Copyright (C) 2005-2007 Ulrich Kunitz <kune@deine-taler.de> | ||
4 | * Copyright (C) 2006-2007 Daniel Drake <dsd@gentoo.org> | ||
5 | * | ||
6 | * This program is free software; you can redistribute it and/or modify | ||
7 | * it under the terms of the GNU General Public License as published by | ||
8 | * the Free Software Foundation; either version 2 of the License, or | ||
9 | * (at your option) any later version. | ||
10 | * | ||
11 | * This program is distributed in the hope that it will be useful, | ||
12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
14 | * GNU General Public License for more details. | ||
15 | * | ||
16 | * You should have received a copy of the GNU General Public License | ||
17 | * along with this program; if not, see <http://www.gnu.org/licenses/>. | ||
18 | */ | ||
19 | |||
20 | #include <linux/kernel.h> | ||
21 | |||
22 | #include "zd_rf.h" | ||
23 | #include "zd_usb.h" | ||
24 | #include "zd_chip.h" | ||
25 | |||
26 | static const u32 chan_rv[][2] = { | ||
27 | RF_CHANNEL( 1) = { 0x09ec00, 0x8cccc8 }, | ||
28 | RF_CHANNEL( 2) = { 0x09ec00, 0x8cccd8 }, | ||
29 | RF_CHANNEL( 3) = { 0x09ec00, 0x8cccc0 }, | ||
30 | RF_CHANNEL( 4) = { 0x09ec00, 0x8cccd0 }, | ||
31 | RF_CHANNEL( 5) = { 0x05ec00, 0x8cccc8 }, | ||
32 | RF_CHANNEL( 6) = { 0x05ec00, 0x8cccd8 }, | ||
33 | RF_CHANNEL( 7) = { 0x05ec00, 0x8cccc0 }, | ||
34 | RF_CHANNEL( 8) = { 0x05ec00, 0x8cccd0 }, | ||
35 | RF_CHANNEL( 9) = { 0x0dec00, 0x8cccc8 }, | ||
36 | RF_CHANNEL(10) = { 0x0dec00, 0x8cccd8 }, | ||
37 | RF_CHANNEL(11) = { 0x0dec00, 0x8cccc0 }, | ||
38 | RF_CHANNEL(12) = { 0x0dec00, 0x8cccd0 }, | ||
39 | RF_CHANNEL(13) = { 0x03ec00, 0x8cccc8 }, | ||
40 | RF_CHANNEL(14) = { 0x03ec00, 0x866660 }, | ||
41 | }; | ||
42 | |||
43 | static const u32 std_rv[] = { | ||
44 | 0x4ff821, | ||
45 | 0xc5fbfc, | ||
46 | 0x21ebfe, | ||
47 | 0xafd401, /* freq shift 0xaad401 */ | ||
48 | 0x6cf56a, | ||
49 | 0xe04073, | ||
50 | 0x193d76, | ||
51 | 0x9dd844, | ||
52 | 0x500007, | ||
53 | 0xd8c010, | ||
54 | }; | ||
55 | |||
56 | static const u32 rv_init1[] = { | ||
57 | 0x3c9000, | ||
58 | 0xbfffff, | ||
59 | 0x700000, | ||
60 | 0xf15d58, | ||
61 | }; | ||
62 | |||
63 | static const u32 rv_init2[] = { | ||
64 | 0xf15d59, | ||
65 | 0xf15d5c, | ||
66 | 0xf15d58, | ||
67 | }; | ||
68 | |||
69 | static const struct zd_ioreq16 ioreqs_sw[] = { | ||
70 | { ZD_CR128, 0x14 }, { ZD_CR129, 0x12 }, { ZD_CR130, 0x10 }, | ||
71 | { ZD_CR38, 0x38 }, { ZD_CR136, 0xdf }, | ||
72 | }; | ||
73 | |||
74 | static int zd1211b_al7230b_finalize(struct zd_chip *chip) | ||
75 | { | ||
76 | int r; | ||
77 | static const struct zd_ioreq16 ioreqs[] = { | ||
78 | { ZD_CR80, 0x30 }, { ZD_CR81, 0x30 }, { ZD_CR79, 0x58 }, | ||
79 | { ZD_CR12, 0xf0 }, { ZD_CR77, 0x1b }, { ZD_CR78, 0x58 }, | ||
80 | { ZD_CR203, 0x04 }, | ||
81 | { }, | ||
82 | { ZD_CR240, 0x80 }, | ||
83 | }; | ||
84 | |||
85 | r = zd_iowrite16a_locked(chip, ioreqs, ARRAY_SIZE(ioreqs)); | ||
86 | if (r) | ||
87 | return r; | ||
88 | |||
89 | if (chip->new_phy_layout) { | ||
90 | /* antenna selection? */ | ||
91 | r = zd_iowrite16_locked(chip, 0xe5, ZD_CR9); | ||
92 | if (r) | ||
93 | return r; | ||
94 | } | ||
95 | |||
96 | return zd_iowrite16_locked(chip, 0x04, ZD_CR203); | ||
97 | } | ||
98 | |||
99 | static int zd1211_al7230b_init_hw(struct zd_rf *rf) | ||
100 | { | ||
101 | int r; | ||
102 | struct zd_chip *chip = zd_rf_to_chip(rf); | ||
103 | |||
104 | /* All of these writes are identical to AL2230 unless otherwise | ||
105 | * specified */ | ||
106 | static const struct zd_ioreq16 ioreqs_1[] = { | ||
107 | /* This one is 7230-specific, and happens before the rest */ | ||
108 | { ZD_CR240, 0x57 }, | ||
109 | { }, | ||
110 | |||
111 | { ZD_CR15, 0x20 }, { ZD_CR23, 0x40 }, { ZD_CR24, 0x20 }, | ||
112 | { ZD_CR26, 0x11 }, { ZD_CR28, 0x3e }, { ZD_CR29, 0x00 }, | ||
113 | { ZD_CR44, 0x33 }, | ||
114 | /* This value is different for 7230 (was: 0x2a) */ | ||
115 | { ZD_CR106, 0x22 }, | ||
116 | { ZD_CR107, 0x1a }, { ZD_CR109, 0x09 }, { ZD_CR110, 0x27 }, | ||
117 | { ZD_CR111, 0x2b }, { ZD_CR112, 0x2b }, { ZD_CR119, 0x0a }, | ||
118 | /* This happened further down in AL2230, | ||
119 | * and the value changed (was: 0xe0) */ | ||
120 | { ZD_CR122, 0xfc }, | ||
121 | { ZD_CR10, 0x89 }, | ||
122 | /* for newest (3rd cut) AL2300 */ | ||
123 | { ZD_CR17, 0x28 }, | ||
124 | { ZD_CR26, 0x93 }, { ZD_CR34, 0x30 }, | ||
125 | /* for newest (3rd cut) AL2300 */ | ||
126 | { ZD_CR35, 0x3e }, | ||
127 | { ZD_CR41, 0x24 }, { ZD_CR44, 0x32 }, | ||
128 | /* for newest (3rd cut) AL2300 */ | ||
129 | { ZD_CR46, 0x96 }, | ||
130 | { ZD_CR47, 0x1e }, { ZD_CR79, 0x58 }, { ZD_CR80, 0x30 }, | ||
131 | { ZD_CR81, 0x30 }, { ZD_CR87, 0x0a }, { ZD_CR89, 0x04 }, | ||
132 | { ZD_CR92, 0x0a }, { ZD_CR99, 0x28 }, | ||
133 | /* This value is different for 7230 (was: 0x00) */ | ||
134 | { ZD_CR100, 0x02 }, | ||
135 | { ZD_CR101, 0x13 }, { ZD_CR102, 0x27 }, | ||
136 | /* This value is different for 7230 (was: 0x24) */ | ||
137 | { ZD_CR106, 0x22 }, | ||
138 | /* This value is different for 7230 (was: 0x2a) */ | ||
139 | { ZD_CR107, 0x3f }, | ||
140 | { ZD_CR109, 0x09 }, | ||
141 | /* This value is different for 7230 (was: 0x13) */ | ||
142 | { ZD_CR110, 0x1f }, | ||
143 | { ZD_CR111, 0x1f }, { ZD_CR112, 0x1f }, { ZD_CR113, 0x27 }, | ||
144 | { ZD_CR114, 0x27 }, | ||
145 | /* for newest (3rd cut) AL2300 */ | ||
146 | { ZD_CR115, 0x24 }, | ||
147 | /* This value is different for 7230 (was: 0x24) */ | ||
148 | { ZD_CR116, 0x3f }, | ||
149 | /* This value is different for 7230 (was: 0xf4) */ | ||
150 | { ZD_CR117, 0xfa }, | ||
151 | { ZD_CR118, 0xfc }, { ZD_CR119, 0x10 }, { ZD_CR120, 0x4f }, | ||
152 | { ZD_CR121, 0x77 }, { ZD_CR137, 0x88 }, | ||
153 | /* This one is 7230-specific */ | ||
154 | { ZD_CR138, 0xa8 }, | ||
155 | /* This value is different for 7230 (was: 0xff) */ | ||
156 | { ZD_CR252, 0x34 }, | ||
157 | /* This value is different for 7230 (was: 0xff) */ | ||
158 | { ZD_CR253, 0x34 }, | ||
159 | |||
160 | /* PLL_OFF */ | ||
161 | { ZD_CR251, 0x2f }, | ||
162 | }; | ||
163 | |||
164 | static const struct zd_ioreq16 ioreqs_2[] = { | ||
165 | { ZD_CR251, 0x3f }, /* PLL_ON */ | ||
166 | { ZD_CR128, 0x14 }, { ZD_CR129, 0x12 }, { ZD_CR130, 0x10 }, | ||
167 | { ZD_CR38, 0x38 }, { ZD_CR136, 0xdf }, | ||
168 | }; | ||
169 | |||
170 | r = zd_iowrite16a_locked(chip, ioreqs_1, ARRAY_SIZE(ioreqs_1)); | ||
171 | if (r) | ||
172 | return r; | ||
173 | |||
174 | r = zd_rfwritev_cr_locked(chip, chan_rv[0], ARRAY_SIZE(chan_rv[0])); | ||
175 | if (r) | ||
176 | return r; | ||
177 | |||
178 | r = zd_rfwritev_cr_locked(chip, std_rv, ARRAY_SIZE(std_rv)); | ||
179 | if (r) | ||
180 | return r; | ||
181 | |||
182 | r = zd_rfwritev_cr_locked(chip, rv_init1, ARRAY_SIZE(rv_init1)); | ||
183 | if (r) | ||
184 | return r; | ||
185 | |||
186 | r = zd_iowrite16a_locked(chip, ioreqs_2, ARRAY_SIZE(ioreqs_2)); | ||
187 | if (r) | ||
188 | return r; | ||
189 | |||
190 | r = zd_rfwritev_cr_locked(chip, rv_init2, ARRAY_SIZE(rv_init2)); | ||
191 | if (r) | ||
192 | return r; | ||
193 | |||
194 | r = zd_iowrite16_locked(chip, 0x06, ZD_CR203); | ||
195 | if (r) | ||
196 | return r; | ||
197 | r = zd_iowrite16_locked(chip, 0x80, ZD_CR240); | ||
198 | if (r) | ||
199 | return r; | ||
200 | |||
201 | return 0; | ||
202 | } | ||
203 | |||
204 | static int zd1211b_al7230b_init_hw(struct zd_rf *rf) | ||
205 | { | ||
206 | int r; | ||
207 | struct zd_chip *chip = zd_rf_to_chip(rf); | ||
208 | |||
209 | static const struct zd_ioreq16 ioreqs_1[] = { | ||
210 | { ZD_CR240, 0x57 }, { ZD_CR9, 0x9 }, | ||
211 | { }, | ||
212 | { ZD_CR10, 0x8b }, { ZD_CR15, 0x20 }, | ||
213 | { ZD_CR17, 0x2B }, /* for newest (3rd cut) AL2230 */ | ||
214 | { ZD_CR20, 0x10 }, /* 4N25->Stone Request */ | ||
215 | { ZD_CR23, 0x40 }, { ZD_CR24, 0x20 }, { ZD_CR26, 0x93 }, | ||
216 | { ZD_CR28, 0x3e }, { ZD_CR29, 0x00 }, | ||
217 | { ZD_CR33, 0x28 }, /* 5613 */ | ||
218 | { ZD_CR34, 0x30 }, | ||
219 | { ZD_CR35, 0x3e }, /* for newest (3rd cut) AL2230 */ | ||
220 | { ZD_CR41, 0x24 }, { ZD_CR44, 0x32 }, | ||
221 | { ZD_CR46, 0x99 }, /* for newest (3rd cut) AL2230 */ | ||
222 | { ZD_CR47, 0x1e }, | ||
223 | |||
224 | /* ZD1215 5610 */ | ||
225 | { ZD_CR48, 0x00 }, { ZD_CR49, 0x00 }, { ZD_CR51, 0x01 }, | ||
226 | { ZD_CR52, 0x80 }, { ZD_CR53, 0x7e }, { ZD_CR65, 0x00 }, | ||
227 | { ZD_CR66, 0x00 }, { ZD_CR67, 0x00 }, { ZD_CR68, 0x00 }, | ||
228 | { ZD_CR69, 0x28 }, | ||
229 | |||
230 | { ZD_CR79, 0x58 }, { ZD_CR80, 0x30 }, { ZD_CR81, 0x30 }, | ||
231 | { ZD_CR87, 0x0A }, { ZD_CR89, 0x04 }, | ||
232 | { ZD_CR90, 0x58 }, /* 5112 */ | ||
233 | { ZD_CR91, 0x00 }, /* 5613 */ | ||
234 | { ZD_CR92, 0x0a }, | ||
235 | { ZD_CR98, 0x8d }, /* 4804, for 1212 new algorithm */ | ||
236 | { ZD_CR99, 0x00 }, { ZD_CR100, 0x02 }, { ZD_CR101, 0x13 }, | ||
237 | { ZD_CR102, 0x27 }, | ||
238 | { ZD_CR106, 0x20 }, /* change to 0x24 for AL7230B */ | ||
239 | { ZD_CR109, 0x13 }, /* 4804, for 1212 new algorithm */ | ||
240 | { ZD_CR112, 0x1f }, | ||
241 | }; | ||
242 | |||
243 | static const struct zd_ioreq16 ioreqs_new_phy[] = { | ||
244 | { ZD_CR107, 0x28 }, | ||
245 | { ZD_CR110, 0x1f }, /* 5127, 0x13->0x1f */ | ||
246 | { ZD_CR111, 0x1f }, /* 0x13 to 0x1f for AL7230B */ | ||
247 | { ZD_CR116, 0x2a }, { ZD_CR118, 0xfa }, { ZD_CR119, 0x12 }, | ||
248 | { ZD_CR121, 0x6c }, /* 5613 */ | ||
249 | }; | ||
250 | |||
251 | static const struct zd_ioreq16 ioreqs_old_phy[] = { | ||
252 | { ZD_CR107, 0x24 }, | ||
253 | { ZD_CR110, 0x13 }, /* 5127, 0x13->0x1f */ | ||
254 | { ZD_CR111, 0x13 }, /* 0x13 to 0x1f for AL7230B */ | ||
255 | { ZD_CR116, 0x24 }, { ZD_CR118, 0xfc }, { ZD_CR119, 0x11 }, | ||
256 | { ZD_CR121, 0x6a }, /* 5613 */ | ||
257 | }; | ||
258 | |||
259 | static const struct zd_ioreq16 ioreqs_2[] = { | ||
260 | { ZD_CR113, 0x27 }, { ZD_CR114, 0x27 }, { ZD_CR115, 0x24 }, | ||
261 | { ZD_CR117, 0xfa }, { ZD_CR120, 0x4f }, | ||
262 | { ZD_CR122, 0xfc }, /* E0->FCh at 4901 */ | ||
263 | { ZD_CR123, 0x57 }, /* 5613 */ | ||
264 | { ZD_CR125, 0xad }, /* 4804, for 1212 new algorithm */ | ||
265 | { ZD_CR126, 0x6c }, /* 5613 */ | ||
266 | { ZD_CR127, 0x03 }, /* 4804, for 1212 new algorithm */ | ||
267 | { ZD_CR130, 0x10 }, | ||
268 | { ZD_CR131, 0x00 }, /* 5112 */ | ||
269 | { ZD_CR137, 0x50 }, /* 5613 */ | ||
270 | { ZD_CR138, 0xa8 }, /* 5112 */ | ||
271 | { ZD_CR144, 0xac }, /* 5613 */ | ||
272 | { ZD_CR148, 0x40 }, /* 5112 */ | ||
273 | { ZD_CR149, 0x40 }, /* 4O07, 50->40 */ | ||
274 | { ZD_CR150, 0x1a }, /* 5112, 0C->1A */ | ||
275 | { ZD_CR252, 0x34 }, { ZD_CR253, 0x34 }, | ||
276 | { ZD_CR251, 0x2f }, /* PLL_OFF */ | ||
277 | }; | ||
278 | |||
279 | static const struct zd_ioreq16 ioreqs_3[] = { | ||
280 | { ZD_CR251, 0x7f }, /* PLL_ON */ | ||
281 | { ZD_CR128, 0x14 }, { ZD_CR129, 0x12 }, { ZD_CR130, 0x10 }, | ||
282 | { ZD_CR38, 0x38 }, { ZD_CR136, 0xdf }, | ||
283 | }; | ||
284 | |||
285 | r = zd_iowrite16a_locked(chip, ioreqs_1, ARRAY_SIZE(ioreqs_1)); | ||
286 | if (r) | ||
287 | return r; | ||
288 | |||
289 | if (chip->new_phy_layout) | ||
290 | r = zd_iowrite16a_locked(chip, ioreqs_new_phy, | ||
291 | ARRAY_SIZE(ioreqs_new_phy)); | ||
292 | else | ||
293 | r = zd_iowrite16a_locked(chip, ioreqs_old_phy, | ||
294 | ARRAY_SIZE(ioreqs_old_phy)); | ||
295 | if (r) | ||
296 | return r; | ||
297 | |||
298 | r = zd_iowrite16a_locked(chip, ioreqs_2, ARRAY_SIZE(ioreqs_2)); | ||
299 | if (r) | ||
300 | return r; | ||
301 | |||
302 | r = zd_rfwritev_cr_locked(chip, chan_rv[0], ARRAY_SIZE(chan_rv[0])); | ||
303 | if (r) | ||
304 | return r; | ||
305 | |||
306 | r = zd_rfwritev_cr_locked(chip, std_rv, ARRAY_SIZE(std_rv)); | ||
307 | if (r) | ||
308 | return r; | ||
309 | |||
310 | r = zd_rfwritev_cr_locked(chip, rv_init1, ARRAY_SIZE(rv_init1)); | ||
311 | if (r) | ||
312 | return r; | ||
313 | |||
314 | r = zd_iowrite16a_locked(chip, ioreqs_3, ARRAY_SIZE(ioreqs_3)); | ||
315 | if (r) | ||
316 | return r; | ||
317 | |||
318 | r = zd_rfwritev_cr_locked(chip, rv_init2, ARRAY_SIZE(rv_init2)); | ||
319 | if (r) | ||
320 | return r; | ||
321 | |||
322 | return zd1211b_al7230b_finalize(chip); | ||
323 | } | ||
324 | |||
325 | static int zd1211_al7230b_set_channel(struct zd_rf *rf, u8 channel) | ||
326 | { | ||
327 | int r; | ||
328 | const u32 *rv = chan_rv[channel-1]; | ||
329 | struct zd_chip *chip = zd_rf_to_chip(rf); | ||
330 | |||
331 | static const struct zd_ioreq16 ioreqs[] = { | ||
332 | /* PLL_ON */ | ||
333 | { ZD_CR251, 0x3f }, | ||
334 | { ZD_CR203, 0x06 }, { ZD_CR240, 0x08 }, | ||
335 | }; | ||
336 | |||
337 | r = zd_iowrite16_locked(chip, 0x57, ZD_CR240); | ||
338 | if (r) | ||
339 | return r; | ||
340 | |||
341 | /* PLL_OFF */ | ||
342 | r = zd_iowrite16_locked(chip, 0x2f, ZD_CR251); | ||
343 | if (r) | ||
344 | return r; | ||
345 | |||
346 | r = zd_rfwritev_cr_locked(chip, std_rv, ARRAY_SIZE(std_rv)); | ||
347 | if (r) | ||
348 | return r; | ||
349 | |||
350 | r = zd_rfwrite_cr_locked(chip, 0x3c9000); | ||
351 | if (r) | ||
352 | return r; | ||
353 | r = zd_rfwrite_cr_locked(chip, 0xf15d58); | ||
354 | if (r) | ||
355 | return r; | ||
356 | |||
357 | r = zd_iowrite16a_locked(chip, ioreqs_sw, ARRAY_SIZE(ioreqs_sw)); | ||
358 | if (r) | ||
359 | return r; | ||
360 | |||
361 | r = zd_rfwritev_cr_locked(chip, rv, 2); | ||
362 | if (r) | ||
363 | return r; | ||
364 | |||
365 | r = zd_rfwrite_cr_locked(chip, 0x3c9000); | ||
366 | if (r) | ||
367 | return r; | ||
368 | |||
369 | return zd_iowrite16a_locked(chip, ioreqs, ARRAY_SIZE(ioreqs)); | ||
370 | } | ||
371 | |||
372 | static int zd1211b_al7230b_set_channel(struct zd_rf *rf, u8 channel) | ||
373 | { | ||
374 | int r; | ||
375 | const u32 *rv = chan_rv[channel-1]; | ||
376 | struct zd_chip *chip = zd_rf_to_chip(rf); | ||
377 | |||
378 | r = zd_iowrite16_locked(chip, 0x57, ZD_CR240); | ||
379 | if (r) | ||
380 | return r; | ||
381 | r = zd_iowrite16_locked(chip, 0xe4, ZD_CR9); | ||
382 | if (r) | ||
383 | return r; | ||
384 | |||
385 | /* PLL_OFF */ | ||
386 | r = zd_iowrite16_locked(chip, 0x2f, ZD_CR251); | ||
387 | if (r) | ||
388 | return r; | ||
389 | r = zd_rfwritev_cr_locked(chip, std_rv, ARRAY_SIZE(std_rv)); | ||
390 | if (r) | ||
391 | return r; | ||
392 | |||
393 | r = zd_rfwrite_cr_locked(chip, 0x3c9000); | ||
394 | if (r) | ||
395 | return r; | ||
396 | r = zd_rfwrite_cr_locked(chip, 0xf15d58); | ||
397 | if (r) | ||
398 | return r; | ||
399 | |||
400 | r = zd_iowrite16a_locked(chip, ioreqs_sw, ARRAY_SIZE(ioreqs_sw)); | ||
401 | if (r) | ||
402 | return r; | ||
403 | |||
404 | r = zd_rfwritev_cr_locked(chip, rv, 2); | ||
405 | if (r) | ||
406 | return r; | ||
407 | |||
408 | r = zd_rfwrite_cr_locked(chip, 0x3c9000); | ||
409 | if (r) | ||
410 | return r; | ||
411 | |||
412 | r = zd_iowrite16_locked(chip, 0x7f, ZD_CR251); | ||
413 | if (r) | ||
414 | return r; | ||
415 | |||
416 | return zd1211b_al7230b_finalize(chip); | ||
417 | } | ||
418 | |||
419 | static int zd1211_al7230b_switch_radio_on(struct zd_rf *rf) | ||
420 | { | ||
421 | struct zd_chip *chip = zd_rf_to_chip(rf); | ||
422 | static const struct zd_ioreq16 ioreqs[] = { | ||
423 | { ZD_CR11, 0x00 }, | ||
424 | { ZD_CR251, 0x3f }, | ||
425 | }; | ||
426 | |||
427 | return zd_iowrite16a_locked(chip, ioreqs, ARRAY_SIZE(ioreqs)); | ||
428 | } | ||
429 | |||
430 | static int zd1211b_al7230b_switch_radio_on(struct zd_rf *rf) | ||
431 | { | ||
432 | struct zd_chip *chip = zd_rf_to_chip(rf); | ||
433 | static const struct zd_ioreq16 ioreqs[] = { | ||
434 | { ZD_CR11, 0x00 }, | ||
435 | { ZD_CR251, 0x7f }, | ||
436 | }; | ||
437 | |||
438 | return zd_iowrite16a_locked(chip, ioreqs, ARRAY_SIZE(ioreqs)); | ||
439 | } | ||
440 | |||
441 | static int al7230b_switch_radio_off(struct zd_rf *rf) | ||
442 | { | ||
443 | struct zd_chip *chip = zd_rf_to_chip(rf); | ||
444 | static const struct zd_ioreq16 ioreqs[] = { | ||
445 | { ZD_CR11, 0x04 }, | ||
446 | { ZD_CR251, 0x2f }, | ||
447 | }; | ||
448 | |||
449 | return zd_iowrite16a_locked(chip, ioreqs, ARRAY_SIZE(ioreqs)); | ||
450 | } | ||
451 | |||
452 | /* ZD1211B+AL7230B 6m band edge patching differs slightly from other | ||
453 | * configurations */ | ||
454 | static int zd1211b_al7230b_patch_6m(struct zd_rf *rf, u8 channel) | ||
455 | { | ||
456 | struct zd_chip *chip = zd_rf_to_chip(rf); | ||
457 | struct zd_ioreq16 ioreqs[] = { | ||
458 | { ZD_CR128, 0x14 }, { ZD_CR129, 0x12 }, | ||
459 | }; | ||
460 | |||
461 | /* FIXME: Channel 11 is not the edge for all regulatory domains. */ | ||
462 | if (channel == 1) { | ||
463 | ioreqs[0].value = 0x0e; | ||
464 | ioreqs[1].value = 0x10; | ||
465 | } else if (channel == 11) { | ||
466 | ioreqs[0].value = 0x10; | ||
467 | ioreqs[1].value = 0x10; | ||
468 | } | ||
469 | |||
470 | dev_dbg_f(zd_chip_dev(chip), "patching for channel %d\n", channel); | ||
471 | return zd_iowrite16a_locked(chip, ioreqs, ARRAY_SIZE(ioreqs)); | ||
472 | } | ||
473 | |||
474 | int zd_rf_init_al7230b(struct zd_rf *rf) | ||
475 | { | ||
476 | struct zd_chip *chip = zd_rf_to_chip(rf); | ||
477 | |||
478 | if (zd_chip_is_zd1211b(chip)) { | ||
479 | rf->init_hw = zd1211b_al7230b_init_hw; | ||
480 | rf->switch_radio_on = zd1211b_al7230b_switch_radio_on; | ||
481 | rf->set_channel = zd1211b_al7230b_set_channel; | ||
482 | rf->patch_6m_band_edge = zd1211b_al7230b_patch_6m; | ||
483 | } else { | ||
484 | rf->init_hw = zd1211_al7230b_init_hw; | ||
485 | rf->switch_radio_on = zd1211_al7230b_switch_radio_on; | ||
486 | rf->set_channel = zd1211_al7230b_set_channel; | ||
487 | rf->patch_6m_band_edge = zd_rf_generic_patch_6m; | ||
488 | rf->patch_cck_gain = 1; | ||
489 | } | ||
490 | |||
491 | rf->switch_radio_off = al7230b_switch_radio_off; | ||
492 | |||
493 | return 0; | ||
494 | } | ||
diff --git a/drivers/net/wireless/zydas/zd1211rw/zd_rf_rf2959.c b/drivers/net/wireless/zydas/zd1211rw/zd_rf_rf2959.c new file mode 100644 index 000000000000..a93f657a41c7 --- /dev/null +++ b/drivers/net/wireless/zydas/zd1211rw/zd_rf_rf2959.c | |||
@@ -0,0 +1,281 @@ | |||
1 | /* ZD1211 USB-WLAN driver for Linux | ||
2 | * | ||
3 | * Copyright (C) 2005-2007 Ulrich Kunitz <kune@deine-taler.de> | ||
4 | * Copyright (C) 2006-2007 Daniel Drake <dsd@gentoo.org> | ||
5 | * | ||
6 | * This program is free software; you can redistribute it and/or modify | ||
7 | * it under the terms of the GNU General Public License as published by | ||
8 | * the Free Software Foundation; either version 2 of the License, or | ||
9 | * (at your option) any later version. | ||
10 | * | ||
11 | * This program is distributed in the hope that it will be useful, | ||
12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
14 | * GNU General Public License for more details. | ||
15 | * | ||
16 | * You should have received a copy of the GNU General Public License | ||
17 | * along with this program; if not, see <http://www.gnu.org/licenses/>. | ||
18 | */ | ||
19 | |||
20 | #include <linux/kernel.h> | ||
21 | |||
22 | #include "zd_rf.h" | ||
23 | #include "zd_usb.h" | ||
24 | #include "zd_chip.h" | ||
25 | |||
26 | static const u32 rf2959_table[][2] = { | ||
27 | RF_CHANNEL( 1) = { 0x181979, 0x1e6666 }, | ||
28 | RF_CHANNEL( 2) = { 0x181989, 0x1e6666 }, | ||
29 | RF_CHANNEL( 3) = { 0x181999, 0x1e6666 }, | ||
30 | RF_CHANNEL( 4) = { 0x1819a9, 0x1e6666 }, | ||
31 | RF_CHANNEL( 5) = { 0x1819b9, 0x1e6666 }, | ||
32 | RF_CHANNEL( 6) = { 0x1819c9, 0x1e6666 }, | ||
33 | RF_CHANNEL( 7) = { 0x1819d9, 0x1e6666 }, | ||
34 | RF_CHANNEL( 8) = { 0x1819e9, 0x1e6666 }, | ||
35 | RF_CHANNEL( 9) = { 0x1819f9, 0x1e6666 }, | ||
36 | RF_CHANNEL(10) = { 0x181a09, 0x1e6666 }, | ||
37 | RF_CHANNEL(11) = { 0x181a19, 0x1e6666 }, | ||
38 | RF_CHANNEL(12) = { 0x181a29, 0x1e6666 }, | ||
39 | RF_CHANNEL(13) = { 0x181a39, 0x1e6666 }, | ||
40 | RF_CHANNEL(14) = { 0x181a60, 0x1c0000 }, | ||
41 | }; | ||
42 | |||
43 | #if 0 | ||
44 | static int bits(u32 rw, int from, int to) | ||
45 | { | ||
46 | rw &= ~(0xffffffffU << (to+1)); | ||
47 | rw >>= from; | ||
48 | return rw; | ||
49 | } | ||
50 | |||
51 | static int bit(u32 rw, int bit) | ||
52 | { | ||
53 | return bits(rw, bit, bit); | ||
54 | } | ||
55 | |||
56 | static void dump_regwrite(u32 rw) | ||
57 | { | ||
58 | int reg = bits(rw, 18, 22); | ||
59 | int rw_flag = bits(rw, 23, 23); | ||
60 | PDEBUG("rf2959 %#010x reg %d rw %d", rw, reg, rw_flag); | ||
61 | |||
62 | switch (reg) { | ||
63 | case 0: | ||
64 | PDEBUG("reg0 CFG1 ref_sel %d hybernate %d rf_vco_reg_en %d" | ||
65 | " if_vco_reg_en %d if_vga_en %d", | ||
66 | bits(rw, 14, 15), bit(rw, 3), bit(rw, 2), bit(rw, 1), | ||
67 | bit(rw, 0)); | ||
68 | break; | ||
69 | case 1: | ||
70 | PDEBUG("reg1 IFPLL1 pll_en1 %d kv_en1 %d vtc_en1 %d lpf1 %d" | ||
71 | " cpl1 %d pdp1 %d autocal_en1 %d ld_en1 %d ifloopr %d" | ||
72 | " ifloopc %d dac1 %d", | ||
73 | bit(rw, 17), bit(rw, 16), bit(rw, 15), bit(rw, 14), | ||
74 | bit(rw, 13), bit(rw, 12), bit(rw, 11), bit(rw, 10), | ||
75 | bits(rw, 7, 9), bits(rw, 4, 6), bits(rw, 0, 3)); | ||
76 | break; | ||
77 | case 2: | ||
78 | PDEBUG("reg2 IFPLL2 n1 %d num1 %d", | ||
79 | bits(rw, 6, 17), bits(rw, 0, 5)); | ||
80 | break; | ||
81 | case 3: | ||
82 | PDEBUG("reg3 IFPLL3 num %d", bits(rw, 0, 17)); | ||
83 | break; | ||
84 | case 4: | ||
85 | PDEBUG("reg4 IFPLL4 dn1 %#04x ct_def1 %d kv_def1 %d", | ||
86 | bits(rw, 8, 16), bits(rw, 4, 7), bits(rw, 0, 3)); | ||
87 | break; | ||
88 | case 5: | ||
89 | PDEBUG("reg5 RFPLL1 pll_en %d kv_en %d vtc_en %d lpf %d cpl %d" | ||
90 | " pdp %d autocal_en %d ld_en %d rfloopr %d rfloopc %d" | ||
91 | " dac %d", | ||
92 | bit(rw, 17), bit(rw, 16), bit(rw, 15), bit(rw, 14), | ||
93 | bit(rw, 13), bit(rw, 12), bit(rw, 11), bit(rw, 10), | ||
94 | bits(rw, 7, 9), bits(rw, 4, 6), bits(rw, 0,3)); | ||
95 | break; | ||
96 | case 6: | ||
97 | PDEBUG("reg6 RFPLL2 n %d num %d", | ||
98 | bits(rw, 6, 17), bits(rw, 0, 5)); | ||
99 | break; | ||
100 | case 7: | ||
101 | PDEBUG("reg7 RFPLL3 num2 %d", bits(rw, 0, 17)); | ||
102 | break; | ||
103 | case 8: | ||
104 | PDEBUG("reg8 RFPLL4 dn %#06x ct_def %d kv_def %d", | ||
105 | bits(rw, 8, 16), bits(rw, 4, 7), bits(rw, 0, 3)); | ||
106 | break; | ||
107 | case 9: | ||
108 | PDEBUG("reg9 CAL1 tvco %d tlock %d m_ct_value %d ld_window %d", | ||
109 | bits(rw, 13, 17), bits(rw, 8, 12), bits(rw, 3, 7), | ||
110 | bits(rw, 0, 2)); | ||
111 | break; | ||
112 | case 10: | ||
113 | PDEBUG("reg10 TXRX1 rxdcfbbyps %d pcontrol %d txvgc %d" | ||
114 | " rxlpfbw %d txlpfbw %d txdiffmode %d txenmode %d" | ||
115 | " intbiasen %d tybypass %d", | ||
116 | bit(rw, 17), bits(rw, 15, 16), bits(rw, 10, 14), | ||
117 | bits(rw, 7, 9), bits(rw, 4, 6), bit(rw, 3), bit(rw, 2), | ||
118 | bit(rw, 1), bit(rw, 0)); | ||
119 | break; | ||
120 | case 11: | ||
121 | PDEBUG("reg11 PCNT1 mid_bias %d p_desired %d pc_offset %d" | ||
122 | " tx_delay %d", | ||
123 | bits(rw, 15, 17), bits(rw, 9, 14), bits(rw, 3, 8), | ||
124 | bits(rw, 0, 2)); | ||
125 | break; | ||
126 | case 12: | ||
127 | PDEBUG("reg12 PCNT2 max_power %d mid_power %d min_power %d", | ||
128 | bits(rw, 12, 17), bits(rw, 6, 11), bits(rw, 0, 5)); | ||
129 | break; | ||
130 | case 13: | ||
131 | PDEBUG("reg13 VCOT1 rfpll vco comp %d ifpll vco comp %d" | ||
132 | " lobias %d if_biasbuf %d if_biasvco %d rf_biasbuf %d" | ||
133 | " rf_biasvco %d", | ||
134 | bit(rw, 17), bit(rw, 16), bit(rw, 15), | ||
135 | bits(rw, 8, 9), bits(rw, 5, 7), bits(rw, 3, 4), | ||
136 | bits(rw, 0, 2)); | ||
137 | break; | ||
138 | case 14: | ||
139 | PDEBUG("reg14 IQCAL rx_acal %d rx_pcal %d" | ||
140 | " tx_acal %d tx_pcal %d", | ||
141 | bits(rw, 13, 17), bits(rw, 9, 12), bits(rw, 4, 8), | ||
142 | bits(rw, 0, 3)); | ||
143 | break; | ||
144 | } | ||
145 | } | ||
146 | #endif /* 0 */ | ||
147 | |||
148 | static int rf2959_init_hw(struct zd_rf *rf) | ||
149 | { | ||
150 | int r; | ||
151 | struct zd_chip *chip = zd_rf_to_chip(rf); | ||
152 | |||
153 | static const struct zd_ioreq16 ioreqs[] = { | ||
154 | { ZD_CR2, 0x1E }, { ZD_CR9, 0x20 }, { ZD_CR10, 0x89 }, | ||
155 | { ZD_CR11, 0x00 }, { ZD_CR15, 0xD0 }, { ZD_CR17, 0x68 }, | ||
156 | { ZD_CR19, 0x4a }, { ZD_CR20, 0x0c }, { ZD_CR21, 0x0E }, | ||
157 | { ZD_CR23, 0x48 }, | ||
158 | /* normal size for cca threshold */ | ||
159 | { ZD_CR24, 0x14 }, | ||
160 | /* { ZD_CR24, 0x20 }, */ | ||
161 | { ZD_CR26, 0x90 }, { ZD_CR27, 0x30 }, { ZD_CR29, 0x20 }, | ||
162 | { ZD_CR31, 0xb2 }, { ZD_CR32, 0x43 }, { ZD_CR33, 0x28 }, | ||
163 | { ZD_CR38, 0x30 }, { ZD_CR34, 0x0f }, { ZD_CR35, 0xF0 }, | ||
164 | { ZD_CR41, 0x2a }, { ZD_CR46, 0x7F }, { ZD_CR47, 0x1E }, | ||
165 | { ZD_CR51, 0xc5 }, { ZD_CR52, 0xc5 }, { ZD_CR53, 0xc5 }, | ||
166 | { ZD_CR79, 0x58 }, { ZD_CR80, 0x30 }, { ZD_CR81, 0x30 }, | ||
167 | { ZD_CR82, 0x00 }, { ZD_CR83, 0x24 }, { ZD_CR84, 0x04 }, | ||
168 | { ZD_CR85, 0x00 }, { ZD_CR86, 0x10 }, { ZD_CR87, 0x2A }, | ||
169 | { ZD_CR88, 0x10 }, { ZD_CR89, 0x24 }, { ZD_CR90, 0x18 }, | ||
170 | /* { ZD_CR91, 0x18 }, */ | ||
171 | /* should solve continuous CTS frame problems */ | ||
172 | { ZD_CR91, 0x00 }, | ||
173 | { ZD_CR92, 0x0a }, { ZD_CR93, 0x00 }, { ZD_CR94, 0x01 }, | ||
174 | { ZD_CR95, 0x00 }, { ZD_CR96, 0x40 }, { ZD_CR97, 0x37 }, | ||
175 | { ZD_CR98, 0x05 }, { ZD_CR99, 0x28 }, { ZD_CR100, 0x00 }, | ||
176 | { ZD_CR101, 0x13 }, { ZD_CR102, 0x27 }, { ZD_CR103, 0x27 }, | ||
177 | { ZD_CR104, 0x18 }, { ZD_CR105, 0x12 }, | ||
178 | /* normal size */ | ||
179 | { ZD_CR106, 0x1a }, | ||
180 | /* { ZD_CR106, 0x22 }, */ | ||
181 | { ZD_CR107, 0x24 }, { ZD_CR108, 0x0a }, { ZD_CR109, 0x13 }, | ||
182 | { ZD_CR110, 0x2F }, { ZD_CR111, 0x27 }, { ZD_CR112, 0x27 }, | ||
183 | { ZD_CR113, 0x27 }, { ZD_CR114, 0x27 }, { ZD_CR115, 0x40 }, | ||
184 | { ZD_CR116, 0x40 }, { ZD_CR117, 0xF0 }, { ZD_CR118, 0xF0 }, | ||
185 | { ZD_CR119, 0x16 }, | ||
186 | /* no TX continuation */ | ||
187 | { ZD_CR122, 0x00 }, | ||
188 | /* { ZD_CR122, 0xff }, */ | ||
189 | { ZD_CR127, 0x03 }, { ZD_CR131, 0x08 }, { ZD_CR138, 0x28 }, | ||
190 | { ZD_CR148, 0x44 }, { ZD_CR150, 0x10 }, { ZD_CR169, 0xBB }, | ||
191 | { ZD_CR170, 0xBB }, | ||
192 | }; | ||
193 | |||
194 | static const u32 rv[] = { | ||
195 | 0x000007, /* REG0(CFG1) */ | ||
196 | 0x07dd43, /* REG1(IFPLL1) */ | ||
197 | 0x080959, /* REG2(IFPLL2) */ | ||
198 | 0x0e6666, | ||
199 | 0x116a57, /* REG4 */ | ||
200 | 0x17dd43, /* REG5 */ | ||
201 | 0x1819f9, /* REG6 */ | ||
202 | 0x1e6666, | ||
203 | 0x214554, | ||
204 | 0x25e7fa, | ||
205 | 0x27fffa, | ||
206 | /* The Zydas driver somehow forgets to set this value. It's | ||
207 | * only set for Japan. We are using internal power control | ||
208 | * for now. | ||
209 | */ | ||
210 | 0x294128, /* internal power */ | ||
211 | /* 0x28252c, */ /* External control TX power */ | ||
212 | /* ZD_CR31_CCK, ZD_CR51_6-36M, ZD_CR52_48M, ZD_CR53_54M */ | ||
213 | 0x2c0000, | ||
214 | 0x300000, | ||
215 | 0x340000, /* REG13(0xD) */ | ||
216 | 0x381e0f, /* REG14(0xE) */ | ||
217 | /* Bogus, RF2959's data sheet doesn't know register 27, which is | ||
218 | * actually referenced here. The commented 0x11 is 17. | ||
219 | */ | ||
220 | 0x6c180f, /* REG27(0x11) */ | ||
221 | }; | ||
222 | |||
223 | r = zd_iowrite16a_locked(chip, ioreqs, ARRAY_SIZE(ioreqs)); | ||
224 | if (r) | ||
225 | return r; | ||
226 | |||
227 | return zd_rfwritev_locked(chip, rv, ARRAY_SIZE(rv), RF_RV_BITS); | ||
228 | } | ||
229 | |||
230 | static int rf2959_set_channel(struct zd_rf *rf, u8 channel) | ||
231 | { | ||
232 | int i, r; | ||
233 | const u32 *rv = rf2959_table[channel-1]; | ||
234 | struct zd_chip *chip = zd_rf_to_chip(rf); | ||
235 | |||
236 | for (i = 0; i < 2; i++) { | ||
237 | r = zd_rfwrite_locked(chip, rv[i], RF_RV_BITS); | ||
238 | if (r) | ||
239 | return r; | ||
240 | } | ||
241 | return 0; | ||
242 | } | ||
243 | |||
244 | static int rf2959_switch_radio_on(struct zd_rf *rf) | ||
245 | { | ||
246 | static const struct zd_ioreq16 ioreqs[] = { | ||
247 | { ZD_CR10, 0x89 }, | ||
248 | { ZD_CR11, 0x00 }, | ||
249 | }; | ||
250 | struct zd_chip *chip = zd_rf_to_chip(rf); | ||
251 | |||
252 | return zd_iowrite16a_locked(chip, ioreqs, ARRAY_SIZE(ioreqs)); | ||
253 | } | ||
254 | |||
255 | static int rf2959_switch_radio_off(struct zd_rf *rf) | ||
256 | { | ||
257 | static const struct zd_ioreq16 ioreqs[] = { | ||
258 | { ZD_CR10, 0x15 }, | ||
259 | { ZD_CR11, 0x81 }, | ||
260 | }; | ||
261 | struct zd_chip *chip = zd_rf_to_chip(rf); | ||
262 | |||
263 | return zd_iowrite16a_locked(chip, ioreqs, ARRAY_SIZE(ioreqs)); | ||
264 | } | ||
265 | |||
266 | int zd_rf_init_rf2959(struct zd_rf *rf) | ||
267 | { | ||
268 | struct zd_chip *chip = zd_rf_to_chip(rf); | ||
269 | |||
270 | if (zd_chip_is_zd1211b(chip)) { | ||
271 | dev_err(zd_chip_dev(chip), | ||
272 | "RF2959 is currently not supported for ZD1211B" | ||
273 | " devices\n"); | ||
274 | return -ENODEV; | ||
275 | } | ||
276 | rf->init_hw = rf2959_init_hw; | ||
277 | rf->set_channel = rf2959_set_channel; | ||
278 | rf->switch_radio_on = rf2959_switch_radio_on; | ||
279 | rf->switch_radio_off = rf2959_switch_radio_off; | ||
280 | return 0; | ||
281 | } | ||
diff --git a/drivers/net/wireless/zydas/zd1211rw/zd_rf_uw2453.c b/drivers/net/wireless/zydas/zd1211rw/zd_rf_uw2453.c new file mode 100644 index 000000000000..61b924027356 --- /dev/null +++ b/drivers/net/wireless/zydas/zd1211rw/zd_rf_uw2453.c | |||
@@ -0,0 +1,539 @@ | |||
1 | /* ZD1211 USB-WLAN driver for Linux | ||
2 | * | ||
3 | * Copyright (C) 2005-2007 Ulrich Kunitz <kune@deine-taler.de> | ||
4 | * Copyright (C) 2006-2007 Daniel Drake <dsd@gentoo.org> | ||
5 | * | ||
6 | * This program is free software; you can redistribute it and/or modify | ||
7 | * it under the terms of the GNU General Public License as published by | ||
8 | * the Free Software Foundation; either version 2 of the License, or | ||
9 | * (at your option) any later version. | ||
10 | * | ||
11 | * This program is distributed in the hope that it will be useful, | ||
12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
14 | * GNU General Public License for more details. | ||
15 | * | ||
16 | * You should have received a copy of the GNU General Public License | ||
17 | * along with this program; if not, see <http://www.gnu.org/licenses/>. | ||
18 | */ | ||
19 | |||
20 | #include <linux/kernel.h> | ||
21 | #include <linux/slab.h> | ||
22 | |||
23 | #include "zd_rf.h" | ||
24 | #include "zd_usb.h" | ||
25 | #include "zd_chip.h" | ||
26 | |||
27 | /* This RF programming code is based upon the code found in v2.16.0.0 of the | ||
28 | * ZyDAS vendor driver. Unlike other RF's, Ubec publish full technical specs | ||
29 | * for this RF on their website, so we're able to understand more than | ||
30 | * usual as to what is going on. Thumbs up for Ubec for doing that. */ | ||
31 | |||
32 | /* The 3-wire serial interface provides access to 8 write-only registers. | ||
33 | * The data format is a 4 bit register address followed by a 20 bit value. */ | ||
34 | #define UW2453_REGWRITE(reg, val) ((((reg) & 0xf) << 20) | ((val) & 0xfffff)) | ||
35 | |||
36 | /* For channel tuning, we have to configure registers 1 (synthesizer), 2 (synth | ||
37 | * fractional divide ratio) and 3 (VCO config). | ||
38 | * | ||
39 | * We configure the RF to produce an interrupt when the PLL is locked onto | ||
40 | * the configured frequency. During initialization, we run through a variety | ||
41 | * of different VCO configurations on channel 1 until we detect a PLL lock. | ||
42 | * When this happens, we remember which VCO configuration produced the lock | ||
43 | * and use it later. Actually, we use the configuration *after* the one that | ||
44 | * produced the lock, which seems odd, but it works. | ||
45 | * | ||
46 | * If we do not see a PLL lock on any standard VCO config, we fall back on an | ||
47 | * autocal configuration, which has a fixed (as opposed to per-channel) VCO | ||
48 | * config and different synth values from the standard set (divide ratio | ||
49 | * is still shared with the standard set). */ | ||
50 | |||
51 | /* The per-channel synth values for all standard VCO configurations. These get | ||
52 | * written to register 1. */ | ||
53 | static const u8 uw2453_std_synth[] = { | ||
54 | RF_CHANNEL( 1) = 0x47, | ||
55 | RF_CHANNEL( 2) = 0x47, | ||
56 | RF_CHANNEL( 3) = 0x67, | ||
57 | RF_CHANNEL( 4) = 0x67, | ||
58 | RF_CHANNEL( 5) = 0x67, | ||
59 | RF_CHANNEL( 6) = 0x67, | ||
60 | RF_CHANNEL( 7) = 0x57, | ||
61 | RF_CHANNEL( 8) = 0x57, | ||
62 | RF_CHANNEL( 9) = 0x57, | ||
63 | RF_CHANNEL(10) = 0x57, | ||
64 | RF_CHANNEL(11) = 0x77, | ||
65 | RF_CHANNEL(12) = 0x77, | ||
66 | RF_CHANNEL(13) = 0x77, | ||
67 | RF_CHANNEL(14) = 0x4f, | ||
68 | }; | ||
69 | |||
70 | /* This table stores the synthesizer fractional divide ratio for *all* VCO | ||
71 | * configurations (both standard and autocal). These get written to register 2. | ||
72 | */ | ||
73 | static const u16 uw2453_synth_divide[] = { | ||
74 | RF_CHANNEL( 1) = 0x999, | ||
75 | RF_CHANNEL( 2) = 0x99b, | ||
76 | RF_CHANNEL( 3) = 0x998, | ||
77 | RF_CHANNEL( 4) = 0x99a, | ||
78 | RF_CHANNEL( 5) = 0x999, | ||
79 | RF_CHANNEL( 6) = 0x99b, | ||
80 | RF_CHANNEL( 7) = 0x998, | ||
81 | RF_CHANNEL( 8) = 0x99a, | ||
82 | RF_CHANNEL( 9) = 0x999, | ||
83 | RF_CHANNEL(10) = 0x99b, | ||
84 | RF_CHANNEL(11) = 0x998, | ||
85 | RF_CHANNEL(12) = 0x99a, | ||
86 | RF_CHANNEL(13) = 0x999, | ||
87 | RF_CHANNEL(14) = 0xccc, | ||
88 | }; | ||
89 | |||
90 | /* Here is the data for all the standard VCO configurations. We shrink our | ||
91 | * table a little by observing that both channels in a consecutive pair share | ||
92 | * the same value. We also observe that the high 4 bits ([0:3] in the specs) | ||
93 | * are all 'Reserved' and are always set to 0x4 - we chop them off in the data | ||
94 | * below. */ | ||
95 | #define CHAN_TO_PAIRIDX(a) ((a - 1) / 2) | ||
96 | #define RF_CHANPAIR(a,b) [CHAN_TO_PAIRIDX(a)] | ||
97 | static const u16 uw2453_std_vco_cfg[][7] = { | ||
98 | { /* table 1 */ | ||
99 | RF_CHANPAIR( 1, 2) = 0x664d, | ||
100 | RF_CHANPAIR( 3, 4) = 0x604d, | ||
101 | RF_CHANPAIR( 5, 6) = 0x6675, | ||
102 | RF_CHANPAIR( 7, 8) = 0x6475, | ||
103 | RF_CHANPAIR( 9, 10) = 0x6655, | ||
104 | RF_CHANPAIR(11, 12) = 0x6455, | ||
105 | RF_CHANPAIR(13, 14) = 0x6665, | ||
106 | }, | ||
107 | { /* table 2 */ | ||
108 | RF_CHANPAIR( 1, 2) = 0x666d, | ||
109 | RF_CHANPAIR( 3, 4) = 0x606d, | ||
110 | RF_CHANPAIR( 5, 6) = 0x664d, | ||
111 | RF_CHANPAIR( 7, 8) = 0x644d, | ||
112 | RF_CHANPAIR( 9, 10) = 0x6675, | ||
113 | RF_CHANPAIR(11, 12) = 0x6475, | ||
114 | RF_CHANPAIR(13, 14) = 0x6655, | ||
115 | }, | ||
116 | { /* table 3 */ | ||
117 | RF_CHANPAIR( 1, 2) = 0x665d, | ||
118 | RF_CHANPAIR( 3, 4) = 0x605d, | ||
119 | RF_CHANPAIR( 5, 6) = 0x666d, | ||
120 | RF_CHANPAIR( 7, 8) = 0x646d, | ||
121 | RF_CHANPAIR( 9, 10) = 0x664d, | ||
122 | RF_CHANPAIR(11, 12) = 0x644d, | ||
123 | RF_CHANPAIR(13, 14) = 0x6675, | ||
124 | }, | ||
125 | { /* table 4 */ | ||
126 | RF_CHANPAIR( 1, 2) = 0x667d, | ||
127 | RF_CHANPAIR( 3, 4) = 0x607d, | ||
128 | RF_CHANPAIR( 5, 6) = 0x665d, | ||
129 | RF_CHANPAIR( 7, 8) = 0x645d, | ||
130 | RF_CHANPAIR( 9, 10) = 0x666d, | ||
131 | RF_CHANPAIR(11, 12) = 0x646d, | ||
132 | RF_CHANPAIR(13, 14) = 0x664d, | ||
133 | }, | ||
134 | { /* table 5 */ | ||
135 | RF_CHANPAIR( 1, 2) = 0x6643, | ||
136 | RF_CHANPAIR( 3, 4) = 0x6043, | ||
137 | RF_CHANPAIR( 5, 6) = 0x667d, | ||
138 | RF_CHANPAIR( 7, 8) = 0x647d, | ||
139 | RF_CHANPAIR( 9, 10) = 0x665d, | ||
140 | RF_CHANPAIR(11, 12) = 0x645d, | ||
141 | RF_CHANPAIR(13, 14) = 0x666d, | ||
142 | }, | ||
143 | { /* table 6 */ | ||
144 | RF_CHANPAIR( 1, 2) = 0x6663, | ||
145 | RF_CHANPAIR( 3, 4) = 0x6063, | ||
146 | RF_CHANPAIR( 5, 6) = 0x6643, | ||
147 | RF_CHANPAIR( 7, 8) = 0x6443, | ||
148 | RF_CHANPAIR( 9, 10) = 0x667d, | ||
149 | RF_CHANPAIR(11, 12) = 0x647d, | ||
150 | RF_CHANPAIR(13, 14) = 0x665d, | ||
151 | }, | ||
152 | { /* table 7 */ | ||
153 | RF_CHANPAIR( 1, 2) = 0x6653, | ||
154 | RF_CHANPAIR( 3, 4) = 0x6053, | ||
155 | RF_CHANPAIR( 5, 6) = 0x6663, | ||
156 | RF_CHANPAIR( 7, 8) = 0x6463, | ||
157 | RF_CHANPAIR( 9, 10) = 0x6643, | ||
158 | RF_CHANPAIR(11, 12) = 0x6443, | ||
159 | RF_CHANPAIR(13, 14) = 0x667d, | ||
160 | }, | ||
161 | { /* table 8 */ | ||
162 | RF_CHANPAIR( 1, 2) = 0x6673, | ||
163 | RF_CHANPAIR( 3, 4) = 0x6073, | ||
164 | RF_CHANPAIR( 5, 6) = 0x6653, | ||
165 | RF_CHANPAIR( 7, 8) = 0x6453, | ||
166 | RF_CHANPAIR( 9, 10) = 0x6663, | ||
167 | RF_CHANPAIR(11, 12) = 0x6463, | ||
168 | RF_CHANPAIR(13, 14) = 0x6643, | ||
169 | }, | ||
170 | { /* table 9 */ | ||
171 | RF_CHANPAIR( 1, 2) = 0x664b, | ||
172 | RF_CHANPAIR( 3, 4) = 0x604b, | ||
173 | RF_CHANPAIR( 5, 6) = 0x6673, | ||
174 | RF_CHANPAIR( 7, 8) = 0x6473, | ||
175 | RF_CHANPAIR( 9, 10) = 0x6653, | ||
176 | RF_CHANPAIR(11, 12) = 0x6453, | ||
177 | RF_CHANPAIR(13, 14) = 0x6663, | ||
178 | }, | ||
179 | { /* table 10 */ | ||
180 | RF_CHANPAIR( 1, 2) = 0x666b, | ||
181 | RF_CHANPAIR( 3, 4) = 0x606b, | ||
182 | RF_CHANPAIR( 5, 6) = 0x664b, | ||
183 | RF_CHANPAIR( 7, 8) = 0x644b, | ||
184 | RF_CHANPAIR( 9, 10) = 0x6673, | ||
185 | RF_CHANPAIR(11, 12) = 0x6473, | ||
186 | RF_CHANPAIR(13, 14) = 0x6653, | ||
187 | }, | ||
188 | { /* table 11 */ | ||
189 | RF_CHANPAIR( 1, 2) = 0x665b, | ||
190 | RF_CHANPAIR( 3, 4) = 0x605b, | ||
191 | RF_CHANPAIR( 5, 6) = 0x666b, | ||
192 | RF_CHANPAIR( 7, 8) = 0x646b, | ||
193 | RF_CHANPAIR( 9, 10) = 0x664b, | ||
194 | RF_CHANPAIR(11, 12) = 0x644b, | ||
195 | RF_CHANPAIR(13, 14) = 0x6673, | ||
196 | }, | ||
197 | |||
198 | }; | ||
199 | |||
200 | /* The per-channel synth values for autocal. These get written to register 1. */ | ||
201 | static const u16 uw2453_autocal_synth[] = { | ||
202 | RF_CHANNEL( 1) = 0x6847, | ||
203 | RF_CHANNEL( 2) = 0x6847, | ||
204 | RF_CHANNEL( 3) = 0x6867, | ||
205 | RF_CHANNEL( 4) = 0x6867, | ||
206 | RF_CHANNEL( 5) = 0x6867, | ||
207 | RF_CHANNEL( 6) = 0x6867, | ||
208 | RF_CHANNEL( 7) = 0x6857, | ||
209 | RF_CHANNEL( 8) = 0x6857, | ||
210 | RF_CHANNEL( 9) = 0x6857, | ||
211 | RF_CHANNEL(10) = 0x6857, | ||
212 | RF_CHANNEL(11) = 0x6877, | ||
213 | RF_CHANNEL(12) = 0x6877, | ||
214 | RF_CHANNEL(13) = 0x6877, | ||
215 | RF_CHANNEL(14) = 0x684f, | ||
216 | }; | ||
217 | |||
218 | /* The VCO configuration for autocal (all channels) */ | ||
219 | static const u16 UW2453_AUTOCAL_VCO_CFG = 0x6662; | ||
220 | |||
221 | /* TX gain settings. The array index corresponds to the TX power integration | ||
222 | * values found in the EEPROM. The values get written to register 7. */ | ||
223 | static u32 uw2453_txgain[] = { | ||
224 | [0x00] = 0x0e313, | ||
225 | [0x01] = 0x0fb13, | ||
226 | [0x02] = 0x0e093, | ||
227 | [0x03] = 0x0f893, | ||
228 | [0x04] = 0x0ea93, | ||
229 | [0x05] = 0x1f093, | ||
230 | [0x06] = 0x1f493, | ||
231 | [0x07] = 0x1f693, | ||
232 | [0x08] = 0x1f393, | ||
233 | [0x09] = 0x1f35b, | ||
234 | [0x0a] = 0x1e6db, | ||
235 | [0x0b] = 0x1ff3f, | ||
236 | [0x0c] = 0x1ffff, | ||
237 | [0x0d] = 0x361d7, | ||
238 | [0x0e] = 0x37fbf, | ||
239 | [0x0f] = 0x3ff8b, | ||
240 | [0x10] = 0x3ff33, | ||
241 | [0x11] = 0x3fb3f, | ||
242 | [0x12] = 0x3ffff, | ||
243 | }; | ||
244 | |||
245 | /* RF-specific structure */ | ||
246 | struct uw2453_priv { | ||
247 | /* index into synth/VCO config tables where PLL lock was found | ||
248 | * -1 means autocal */ | ||
249 | int config; | ||
250 | }; | ||
251 | |||
252 | #define UW2453_PRIV(rf) ((struct uw2453_priv *) (rf)->priv) | ||
253 | |||
254 | static int uw2453_synth_set_channel(struct zd_chip *chip, int channel, | ||
255 | bool autocal) | ||
256 | { | ||
257 | int r; | ||
258 | int idx = channel - 1; | ||
259 | u32 val; | ||
260 | |||
261 | if (autocal) | ||
262 | val = UW2453_REGWRITE(1, uw2453_autocal_synth[idx]); | ||
263 | else | ||
264 | val = UW2453_REGWRITE(1, uw2453_std_synth[idx]); | ||
265 | |||
266 | r = zd_rfwrite_locked(chip, val, RF_RV_BITS); | ||
267 | if (r) | ||
268 | return r; | ||
269 | |||
270 | return zd_rfwrite_locked(chip, | ||
271 | UW2453_REGWRITE(2, uw2453_synth_divide[idx]), RF_RV_BITS); | ||
272 | } | ||
273 | |||
274 | static int uw2453_write_vco_cfg(struct zd_chip *chip, u16 value) | ||
275 | { | ||
276 | /* vendor driver always sets these upper bits even though the specs say | ||
277 | * they are reserved */ | ||
278 | u32 val = 0x40000 | value; | ||
279 | return zd_rfwrite_locked(chip, UW2453_REGWRITE(3, val), RF_RV_BITS); | ||
280 | } | ||
281 | |||
282 | static int uw2453_init_mode(struct zd_chip *chip) | ||
283 | { | ||
284 | static const u32 rv[] = { | ||
285 | UW2453_REGWRITE(0, 0x25f98), /* enter IDLE mode */ | ||
286 | UW2453_REGWRITE(0, 0x25f9a), /* enter CAL_VCO mode */ | ||
287 | UW2453_REGWRITE(0, 0x25f94), /* enter RX/TX mode */ | ||
288 | UW2453_REGWRITE(0, 0x27fd4), /* power down RSSI circuit */ | ||
289 | }; | ||
290 | |||
291 | return zd_rfwritev_locked(chip, rv, ARRAY_SIZE(rv), RF_RV_BITS); | ||
292 | } | ||
293 | |||
294 | static int uw2453_set_tx_gain_level(struct zd_chip *chip, int channel) | ||
295 | { | ||
296 | u8 int_value = chip->pwr_int_values[channel - 1]; | ||
297 | |||
298 | if (int_value >= ARRAY_SIZE(uw2453_txgain)) { | ||
299 | dev_dbg_f(zd_chip_dev(chip), "can't configure TX gain for " | ||
300 | "int value %x on channel %d\n", int_value, channel); | ||
301 | return 0; | ||
302 | } | ||
303 | |||
304 | return zd_rfwrite_locked(chip, | ||
305 | UW2453_REGWRITE(7, uw2453_txgain[int_value]), RF_RV_BITS); | ||
306 | } | ||
307 | |||
308 | static int uw2453_init_hw(struct zd_rf *rf) | ||
309 | { | ||
310 | int i, r; | ||
311 | int found_config = -1; | ||
312 | u16 intr_status; | ||
313 | struct zd_chip *chip = zd_rf_to_chip(rf); | ||
314 | |||
315 | static const struct zd_ioreq16 ioreqs[] = { | ||
316 | { ZD_CR10, 0x89 }, { ZD_CR15, 0x20 }, | ||
317 | { ZD_CR17, 0x28 }, /* 6112 no change */ | ||
318 | { ZD_CR23, 0x38 }, { ZD_CR24, 0x20 }, { ZD_CR26, 0x93 }, | ||
319 | { ZD_CR27, 0x15 }, { ZD_CR28, 0x3e }, { ZD_CR29, 0x00 }, | ||
320 | { ZD_CR33, 0x28 }, { ZD_CR34, 0x30 }, | ||
321 | { ZD_CR35, 0x43 }, /* 6112 3e->43 */ | ||
322 | { ZD_CR41, 0x24 }, { ZD_CR44, 0x32 }, | ||
323 | { ZD_CR46, 0x92 }, /* 6112 96->92 */ | ||
324 | { ZD_CR47, 0x1e }, | ||
325 | { ZD_CR48, 0x04 }, /* 5602 Roger */ | ||
326 | { ZD_CR49, 0xfa }, { ZD_CR79, 0x58 }, { ZD_CR80, 0x30 }, | ||
327 | { ZD_CR81, 0x30 }, { ZD_CR87, 0x0a }, { ZD_CR89, 0x04 }, | ||
328 | { ZD_CR91, 0x00 }, { ZD_CR92, 0x0a }, { ZD_CR98, 0x8d }, | ||
329 | { ZD_CR99, 0x28 }, { ZD_CR100, 0x02 }, | ||
330 | { ZD_CR101, 0x09 }, /* 6112 13->1f 6220 1f->13 6407 13->9 */ | ||
331 | { ZD_CR102, 0x27 }, | ||
332 | { ZD_CR106, 0x1c }, /* 5d07 5112 1f->1c 6220 1c->1f | ||
333 | * 6221 1f->1c | ||
334 | */ | ||
335 | { ZD_CR107, 0x1c }, /* 6220 1c->1a 5221 1a->1c */ | ||
336 | { ZD_CR109, 0x13 }, | ||
337 | { ZD_CR110, 0x1f }, /* 6112 13->1f 6221 1f->13 6407 13->0x09 */ | ||
338 | { ZD_CR111, 0x13 }, { ZD_CR112, 0x1f }, { ZD_CR113, 0x27 }, | ||
339 | { ZD_CR114, 0x23 }, /* 6221 27->23 */ | ||
340 | { ZD_CR115, 0x24 }, /* 6112 24->1c 6220 1c->24 */ | ||
341 | { ZD_CR116, 0x24 }, /* 6220 1c->24 */ | ||
342 | { ZD_CR117, 0xfa }, /* 6112 fa->f8 6220 f8->f4 6220 f4->fa */ | ||
343 | { ZD_CR118, 0xf0 }, /* 5d07 6112 f0->f2 6220 f2->f0 */ | ||
344 | { ZD_CR119, 0x1a }, /* 6112 1a->10 6220 10->14 6220 14->1a */ | ||
345 | { ZD_CR120, 0x4f }, | ||
346 | { ZD_CR121, 0x1f }, /* 6220 4f->1f */ | ||
347 | { ZD_CR122, 0xf0 }, { ZD_CR123, 0x57 }, { ZD_CR125, 0xad }, | ||
348 | { ZD_CR126, 0x6c }, { ZD_CR127, 0x03 }, | ||
349 | { ZD_CR128, 0x14 }, /* 6302 12->11 */ | ||
350 | { ZD_CR129, 0x12 }, /* 6301 10->0f */ | ||
351 | { ZD_CR130, 0x10 }, { ZD_CR137, 0x50 }, { ZD_CR138, 0xa8 }, | ||
352 | { ZD_CR144, 0xac }, { ZD_CR146, 0x20 }, { ZD_CR252, 0xff }, | ||
353 | { ZD_CR253, 0xff }, | ||
354 | }; | ||
355 | |||
356 | static const u32 rv[] = { | ||
357 | UW2453_REGWRITE(4, 0x2b), /* configure receiver gain */ | ||
358 | UW2453_REGWRITE(5, 0x19e4f), /* configure transmitter gain */ | ||
359 | UW2453_REGWRITE(6, 0xf81ad), /* enable RX/TX filter tuning */ | ||
360 | UW2453_REGWRITE(7, 0x3fffe), /* disable TX gain in test mode */ | ||
361 | |||
362 | /* enter CAL_FIL mode, TX gain set by registers, RX gain set by pins, | ||
363 | * RSSI circuit powered down, reduced RSSI range */ | ||
364 | UW2453_REGWRITE(0, 0x25f9c), /* 5d01 cal_fil */ | ||
365 | |||
366 | /* synthesizer configuration for channel 1 */ | ||
367 | UW2453_REGWRITE(1, 0x47), | ||
368 | UW2453_REGWRITE(2, 0x999), | ||
369 | |||
370 | /* disable manual VCO band selection */ | ||
371 | UW2453_REGWRITE(3, 0x7602), | ||
372 | |||
373 | /* enable manual VCO band selection, configure current level */ | ||
374 | UW2453_REGWRITE(3, 0x46063), | ||
375 | }; | ||
376 | |||
377 | r = zd_iowrite16a_locked(chip, ioreqs, ARRAY_SIZE(ioreqs)); | ||
378 | if (r) | ||
379 | return r; | ||
380 | |||
381 | r = zd_rfwritev_locked(chip, rv, ARRAY_SIZE(rv), RF_RV_BITS); | ||
382 | if (r) | ||
383 | return r; | ||
384 | |||
385 | r = uw2453_init_mode(chip); | ||
386 | if (r) | ||
387 | return r; | ||
388 | |||
389 | /* Try all standard VCO configuration settings on channel 1 */ | ||
390 | for (i = 0; i < ARRAY_SIZE(uw2453_std_vco_cfg) - 1; i++) { | ||
391 | /* Configure synthesizer for channel 1 */ | ||
392 | r = uw2453_synth_set_channel(chip, 1, false); | ||
393 | if (r) | ||
394 | return r; | ||
395 | |||
396 | /* Write VCO config */ | ||
397 | r = uw2453_write_vco_cfg(chip, uw2453_std_vco_cfg[i][0]); | ||
398 | if (r) | ||
399 | return r; | ||
400 | |||
401 | /* ack interrupt event */ | ||
402 | r = zd_iowrite16_locked(chip, 0x0f, UW2453_INTR_REG); | ||
403 | if (r) | ||
404 | return r; | ||
405 | |||
406 | /* check interrupt status */ | ||
407 | r = zd_ioread16_locked(chip, &intr_status, UW2453_INTR_REG); | ||
408 | if (r) | ||
409 | return r; | ||
410 | |||
411 | if (!(intr_status & 0xf)) { | ||
412 | dev_dbg_f(zd_chip_dev(chip), | ||
413 | "PLL locked on configuration %d\n", i); | ||
414 | found_config = i; | ||
415 | break; | ||
416 | } | ||
417 | } | ||
418 | |||
419 | if (found_config == -1) { | ||
420 | /* autocal */ | ||
421 | dev_dbg_f(zd_chip_dev(chip), | ||
422 | "PLL did not lock, using autocal\n"); | ||
423 | |||
424 | r = uw2453_synth_set_channel(chip, 1, true); | ||
425 | if (r) | ||
426 | return r; | ||
427 | |||
428 | r = uw2453_write_vco_cfg(chip, UW2453_AUTOCAL_VCO_CFG); | ||
429 | if (r) | ||
430 | return r; | ||
431 | } | ||
432 | |||
433 | /* To match the vendor driver behaviour, we use the configuration after | ||
434 | * the one that produced a lock. */ | ||
435 | UW2453_PRIV(rf)->config = found_config + 1; | ||
436 | |||
437 | return zd_iowrite16_locked(chip, 0x06, ZD_CR203); | ||
438 | } | ||
439 | |||
440 | static int uw2453_set_channel(struct zd_rf *rf, u8 channel) | ||
441 | { | ||
442 | int r; | ||
443 | u16 vco_cfg; | ||
444 | int config = UW2453_PRIV(rf)->config; | ||
445 | bool autocal = (config == -1); | ||
446 | struct zd_chip *chip = zd_rf_to_chip(rf); | ||
447 | |||
448 | static const struct zd_ioreq16 ioreqs[] = { | ||
449 | { ZD_CR80, 0x30 }, { ZD_CR81, 0x30 }, { ZD_CR79, 0x58 }, | ||
450 | { ZD_CR12, 0xf0 }, { ZD_CR77, 0x1b }, { ZD_CR78, 0x58 }, | ||
451 | }; | ||
452 | |||
453 | r = uw2453_synth_set_channel(chip, channel, autocal); | ||
454 | if (r) | ||
455 | return r; | ||
456 | |||
457 | if (autocal) | ||
458 | vco_cfg = UW2453_AUTOCAL_VCO_CFG; | ||
459 | else | ||
460 | vco_cfg = uw2453_std_vco_cfg[config][CHAN_TO_PAIRIDX(channel)]; | ||
461 | |||
462 | r = uw2453_write_vco_cfg(chip, vco_cfg); | ||
463 | if (r) | ||
464 | return r; | ||
465 | |||
466 | r = uw2453_init_mode(chip); | ||
467 | if (r) | ||
468 | return r; | ||
469 | |||
470 | r = zd_iowrite16a_locked(chip, ioreqs, ARRAY_SIZE(ioreqs)); | ||
471 | if (r) | ||
472 | return r; | ||
473 | |||
474 | r = uw2453_set_tx_gain_level(chip, channel); | ||
475 | if (r) | ||
476 | return r; | ||
477 | |||
478 | return zd_iowrite16_locked(chip, 0x06, ZD_CR203); | ||
479 | } | ||
480 | |||
481 | static int uw2453_switch_radio_on(struct zd_rf *rf) | ||
482 | { | ||
483 | int r; | ||
484 | struct zd_chip *chip = zd_rf_to_chip(rf); | ||
485 | struct zd_ioreq16 ioreqs[] = { | ||
486 | { ZD_CR11, 0x00 }, { ZD_CR251, 0x3f }, | ||
487 | }; | ||
488 | |||
489 | /* enter RXTX mode */ | ||
490 | r = zd_rfwrite_locked(chip, UW2453_REGWRITE(0, 0x25f94), RF_RV_BITS); | ||
491 | if (r) | ||
492 | return r; | ||
493 | |||
494 | if (zd_chip_is_zd1211b(chip)) | ||
495 | ioreqs[1].value = 0x7f; | ||
496 | |||
497 | return zd_iowrite16a_locked(chip, ioreqs, ARRAY_SIZE(ioreqs)); | ||
498 | } | ||
499 | |||
500 | static int uw2453_switch_radio_off(struct zd_rf *rf) | ||
501 | { | ||
502 | int r; | ||
503 | struct zd_chip *chip = zd_rf_to_chip(rf); | ||
504 | static const struct zd_ioreq16 ioreqs[] = { | ||
505 | { ZD_CR11, 0x04 }, { ZD_CR251, 0x2f }, | ||
506 | }; | ||
507 | |||
508 | /* enter IDLE mode */ | ||
509 | /* FIXME: shouldn't we go to SLEEP? sent email to zydas */ | ||
510 | r = zd_rfwrite_locked(chip, UW2453_REGWRITE(0, 0x25f90), RF_RV_BITS); | ||
511 | if (r) | ||
512 | return r; | ||
513 | |||
514 | return zd_iowrite16a_locked(chip, ioreqs, ARRAY_SIZE(ioreqs)); | ||
515 | } | ||
516 | |||
517 | static void uw2453_clear(struct zd_rf *rf) | ||
518 | { | ||
519 | kfree(rf->priv); | ||
520 | } | ||
521 | |||
522 | int zd_rf_init_uw2453(struct zd_rf *rf) | ||
523 | { | ||
524 | rf->init_hw = uw2453_init_hw; | ||
525 | rf->set_channel = uw2453_set_channel; | ||
526 | rf->switch_radio_on = uw2453_switch_radio_on; | ||
527 | rf->switch_radio_off = uw2453_switch_radio_off; | ||
528 | rf->patch_6m_band_edge = zd_rf_generic_patch_6m; | ||
529 | rf->clear = uw2453_clear; | ||
530 | /* we have our own TX integration code */ | ||
531 | rf->update_channel_int = 0; | ||
532 | |||
533 | rf->priv = kmalloc(sizeof(struct uw2453_priv), GFP_KERNEL); | ||
534 | if (rf->priv == NULL) | ||
535 | return -ENOMEM; | ||
536 | |||
537 | return 0; | ||
538 | } | ||
539 | |||
diff --git a/drivers/net/wireless/zydas/zd1211rw/zd_usb.c b/drivers/net/wireless/zydas/zd1211rw/zd_usb.c new file mode 100644 index 000000000000..a912dc051111 --- /dev/null +++ b/drivers/net/wireless/zydas/zd1211rw/zd_usb.c | |||
@@ -0,0 +1,2060 @@ | |||
1 | /* ZD1211 USB-WLAN driver for Linux | ||
2 | * | ||
3 | * Copyright (C) 2005-2007 Ulrich Kunitz <kune@deine-taler.de> | ||
4 | * Copyright (C) 2006-2007 Daniel Drake <dsd@gentoo.org> | ||
5 | * Copyright (C) 2006-2007 Michael Wu <flamingice@sourmilk.net> | ||
6 | * | ||
7 | * This program is free software; you can redistribute it and/or modify | ||
8 | * it under the terms of the GNU General Public License as published by | ||
9 | * the Free Software Foundation; either version 2 of the License, or | ||
10 | * (at your option) any later version. | ||
11 | * | ||
12 | * This program is distributed in the hope that it will be useful, | ||
13 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
14 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
15 | * GNU General Public License for more details. | ||
16 | * | ||
17 | * You should have received a copy of the GNU General Public License | ||
18 | * along with this program; if not, see <http://www.gnu.org/licenses/>. | ||
19 | */ | ||
20 | |||
21 | #include <linux/kernel.h> | ||
22 | #include <linux/init.h> | ||
23 | #include <linux/firmware.h> | ||
24 | #include <linux/device.h> | ||
25 | #include <linux/errno.h> | ||
26 | #include <linux/slab.h> | ||
27 | #include <linux/skbuff.h> | ||
28 | #include <linux/usb.h> | ||
29 | #include <linux/workqueue.h> | ||
30 | #include <linux/module.h> | ||
31 | #include <net/mac80211.h> | ||
32 | #include <asm/unaligned.h> | ||
33 | |||
34 | #include "zd_def.h" | ||
35 | #include "zd_mac.h" | ||
36 | #include "zd_usb.h" | ||
37 | |||
38 | static struct usb_device_id usb_ids[] = { | ||
39 | /* ZD1211 */ | ||
40 | { USB_DEVICE(0x0105, 0x145f), .driver_info = DEVICE_ZD1211 }, | ||
41 | { USB_DEVICE(0x0586, 0x3401), .driver_info = DEVICE_ZD1211 }, | ||
42 | { USB_DEVICE(0x0586, 0x3402), .driver_info = DEVICE_ZD1211 }, | ||
43 | { USB_DEVICE(0x0586, 0x3407), .driver_info = DEVICE_ZD1211 }, | ||
44 | { USB_DEVICE(0x0586, 0x3409), .driver_info = DEVICE_ZD1211 }, | ||
45 | { USB_DEVICE(0x079b, 0x004a), .driver_info = DEVICE_ZD1211 }, | ||
46 | { USB_DEVICE(0x07b8, 0x6001), .driver_info = DEVICE_ZD1211 }, | ||
47 | { USB_DEVICE(0x0ace, 0x1211), .driver_info = DEVICE_ZD1211 }, | ||
48 | { USB_DEVICE(0x0ace, 0xa211), .driver_info = DEVICE_ZD1211 }, | ||
49 | { USB_DEVICE(0x0b05, 0x170c), .driver_info = DEVICE_ZD1211 }, | ||
50 | { USB_DEVICE(0x0b3b, 0x1630), .driver_info = DEVICE_ZD1211 }, | ||
51 | { USB_DEVICE(0x0b3b, 0x5630), .driver_info = DEVICE_ZD1211 }, | ||
52 | { USB_DEVICE(0x0df6, 0x9071), .driver_info = DEVICE_ZD1211 }, | ||
53 | { USB_DEVICE(0x0df6, 0x9075), .driver_info = DEVICE_ZD1211 }, | ||
54 | { USB_DEVICE(0x126f, 0xa006), .driver_info = DEVICE_ZD1211 }, | ||
55 | { USB_DEVICE(0x129b, 0x1666), .driver_info = DEVICE_ZD1211 }, | ||
56 | { USB_DEVICE(0x13b1, 0x001e), .driver_info = DEVICE_ZD1211 }, | ||
57 | { USB_DEVICE(0x1435, 0x0711), .driver_info = DEVICE_ZD1211 }, | ||
58 | { USB_DEVICE(0x14ea, 0xab10), .driver_info = DEVICE_ZD1211 }, | ||
59 | { USB_DEVICE(0x14ea, 0xab13), .driver_info = DEVICE_ZD1211 }, | ||
60 | { USB_DEVICE(0x157e, 0x300a), .driver_info = DEVICE_ZD1211 }, | ||
61 | { USB_DEVICE(0x157e, 0x300b), .driver_info = DEVICE_ZD1211 }, | ||
62 | { USB_DEVICE(0x157e, 0x3204), .driver_info = DEVICE_ZD1211 }, | ||
63 | { USB_DEVICE(0x157e, 0x3207), .driver_info = DEVICE_ZD1211 }, | ||
64 | { USB_DEVICE(0x1740, 0x2000), .driver_info = DEVICE_ZD1211 }, | ||
65 | { USB_DEVICE(0x6891, 0xa727), .driver_info = DEVICE_ZD1211 }, | ||
66 | /* ZD1211B */ | ||
67 | { USB_DEVICE(0x0053, 0x5301), .driver_info = DEVICE_ZD1211B }, | ||
68 | { USB_DEVICE(0x0409, 0x0248), .driver_info = DEVICE_ZD1211B }, | ||
69 | { USB_DEVICE(0x0411, 0x00da), .driver_info = DEVICE_ZD1211B }, | ||
70 | { USB_DEVICE(0x0471, 0x1236), .driver_info = DEVICE_ZD1211B }, | ||
71 | { USB_DEVICE(0x0471, 0x1237), .driver_info = DEVICE_ZD1211B }, | ||
72 | { USB_DEVICE(0x050d, 0x705c), .driver_info = DEVICE_ZD1211B }, | ||
73 | { USB_DEVICE(0x054c, 0x0257), .driver_info = DEVICE_ZD1211B }, | ||
74 | { USB_DEVICE(0x0586, 0x340a), .driver_info = DEVICE_ZD1211B }, | ||
75 | { USB_DEVICE(0x0586, 0x340f), .driver_info = DEVICE_ZD1211B }, | ||
76 | { USB_DEVICE(0x0586, 0x3410), .driver_info = DEVICE_ZD1211B }, | ||
77 | { USB_DEVICE(0x0586, 0x3412), .driver_info = DEVICE_ZD1211B }, | ||
78 | { USB_DEVICE(0x0586, 0x3413), .driver_info = DEVICE_ZD1211B }, | ||
79 | { USB_DEVICE(0x079b, 0x0062), .driver_info = DEVICE_ZD1211B }, | ||
80 | { USB_DEVICE(0x07b8, 0x6001), .driver_info = DEVICE_ZD1211B }, | ||
81 | { USB_DEVICE(0x07fa, 0x1196), .driver_info = DEVICE_ZD1211B }, | ||
82 | { USB_DEVICE(0x083a, 0x4505), .driver_info = DEVICE_ZD1211B }, | ||
83 | { USB_DEVICE(0x083a, 0xe501), .driver_info = DEVICE_ZD1211B }, | ||
84 | { USB_DEVICE(0x083a, 0xe503), .driver_info = DEVICE_ZD1211B }, | ||
85 | { USB_DEVICE(0x083a, 0xe506), .driver_info = DEVICE_ZD1211B }, | ||
86 | { USB_DEVICE(0x0ace, 0x1215), .driver_info = DEVICE_ZD1211B }, | ||
87 | { USB_DEVICE(0x0ace, 0xb215), .driver_info = DEVICE_ZD1211B }, | ||
88 | { USB_DEVICE(0x0b05, 0x171b), .driver_info = DEVICE_ZD1211B }, | ||
89 | { USB_DEVICE(0x0baf, 0x0121), .driver_info = DEVICE_ZD1211B }, | ||
90 | { USB_DEVICE(0x0cde, 0x001a), .driver_info = DEVICE_ZD1211B }, | ||
91 | { USB_DEVICE(0x0df6, 0x0036), .driver_info = DEVICE_ZD1211B }, | ||
92 | { USB_DEVICE(0x129b, 0x1667), .driver_info = DEVICE_ZD1211B }, | ||
93 | { USB_DEVICE(0x13b1, 0x0024), .driver_info = DEVICE_ZD1211B }, | ||
94 | { USB_DEVICE(0x157e, 0x300d), .driver_info = DEVICE_ZD1211B }, | ||
95 | { USB_DEVICE(0x1582, 0x6003), .driver_info = DEVICE_ZD1211B }, | ||
96 | { USB_DEVICE(0x2019, 0x5303), .driver_info = DEVICE_ZD1211B }, | ||
97 | { USB_DEVICE(0x2019, 0xed01), .driver_info = DEVICE_ZD1211B }, | ||
98 | /* "Driverless" devices that need ejecting */ | ||
99 | { USB_DEVICE(0x0ace, 0x2011), .driver_info = DEVICE_INSTALLER }, | ||
100 | { USB_DEVICE(0x0ace, 0x20ff), .driver_info = DEVICE_INSTALLER }, | ||
101 | {} | ||
102 | }; | ||
103 | |||
104 | MODULE_LICENSE("GPL"); | ||
105 | MODULE_DESCRIPTION("USB driver for devices with the ZD1211 chip."); | ||
106 | MODULE_AUTHOR("Ulrich Kunitz"); | ||
107 | MODULE_AUTHOR("Daniel Drake"); | ||
108 | MODULE_VERSION("1.0"); | ||
109 | MODULE_DEVICE_TABLE(usb, usb_ids); | ||
110 | |||
111 | #define FW_ZD1211_PREFIX "zd1211/zd1211_" | ||
112 | #define FW_ZD1211B_PREFIX "zd1211/zd1211b_" | ||
113 | |||
114 | static bool check_read_regs(struct zd_usb *usb, struct usb_req_read_regs *req, | ||
115 | unsigned int count); | ||
116 | |||
117 | /* USB device initialization */ | ||
118 | static void int_urb_complete(struct urb *urb); | ||
119 | |||
120 | static int request_fw_file( | ||
121 | const struct firmware **fw, const char *name, struct device *device) | ||
122 | { | ||
123 | int r; | ||
124 | |||
125 | dev_dbg_f(device, "fw name %s\n", name); | ||
126 | |||
127 | r = request_firmware(fw, name, device); | ||
128 | if (r) | ||
129 | dev_err(device, | ||
130 | "Could not load firmware file %s. Error number %d\n", | ||
131 | name, r); | ||
132 | return r; | ||
133 | } | ||
134 | |||
135 | static inline u16 get_bcdDevice(const struct usb_device *udev) | ||
136 | { | ||
137 | return le16_to_cpu(udev->descriptor.bcdDevice); | ||
138 | } | ||
139 | |||
140 | enum upload_code_flags { | ||
141 | REBOOT = 1, | ||
142 | }; | ||
143 | |||
144 | /* Ensures that MAX_TRANSFER_SIZE is even. */ | ||
145 | #define MAX_TRANSFER_SIZE (USB_MAX_TRANSFER_SIZE & ~1) | ||
146 | |||
147 | static int upload_code(struct usb_device *udev, | ||
148 | const u8 *data, size_t size, u16 code_offset, int flags) | ||
149 | { | ||
150 | u8 *p; | ||
151 | int r; | ||
152 | |||
153 | /* USB request blocks need "kmalloced" buffers. | ||
154 | */ | ||
155 | p = kmalloc(MAX_TRANSFER_SIZE, GFP_KERNEL); | ||
156 | if (!p) { | ||
157 | r = -ENOMEM; | ||
158 | goto error; | ||
159 | } | ||
160 | |||
161 | size &= ~1; | ||
162 | while (size > 0) { | ||
163 | size_t transfer_size = size <= MAX_TRANSFER_SIZE ? | ||
164 | size : MAX_TRANSFER_SIZE; | ||
165 | |||
166 | dev_dbg_f(&udev->dev, "transfer size %zu\n", transfer_size); | ||
167 | |||
168 | memcpy(p, data, transfer_size); | ||
169 | r = usb_control_msg(udev, usb_sndctrlpipe(udev, 0), | ||
170 | USB_REQ_FIRMWARE_DOWNLOAD, | ||
171 | USB_DIR_OUT | USB_TYPE_VENDOR, | ||
172 | code_offset, 0, p, transfer_size, 1000 /* ms */); | ||
173 | if (r < 0) { | ||
174 | dev_err(&udev->dev, | ||
175 | "USB control request for firmware upload" | ||
176 | " failed. Error number %d\n", r); | ||
177 | goto error; | ||
178 | } | ||
179 | transfer_size = r & ~1; | ||
180 | |||
181 | size -= transfer_size; | ||
182 | data += transfer_size; | ||
183 | code_offset += transfer_size/sizeof(u16); | ||
184 | } | ||
185 | |||
186 | if (flags & REBOOT) { | ||
187 | u8 ret; | ||
188 | |||
189 | /* Use "DMA-aware" buffer. */ | ||
190 | r = usb_control_msg(udev, usb_rcvctrlpipe(udev, 0), | ||
191 | USB_REQ_FIRMWARE_CONFIRM, | ||
192 | USB_DIR_IN | USB_TYPE_VENDOR, | ||
193 | 0, 0, p, sizeof(ret), 5000 /* ms */); | ||
194 | if (r != sizeof(ret)) { | ||
195 | dev_err(&udev->dev, | ||
196 | "control request firmeware confirmation failed." | ||
197 | " Return value %d\n", r); | ||
198 | if (r >= 0) | ||
199 | r = -ENODEV; | ||
200 | goto error; | ||
201 | } | ||
202 | ret = p[0]; | ||
203 | if (ret & 0x80) { | ||
204 | dev_err(&udev->dev, | ||
205 | "Internal error while downloading." | ||
206 | " Firmware confirm return value %#04x\n", | ||
207 | (unsigned int)ret); | ||
208 | r = -ENODEV; | ||
209 | goto error; | ||
210 | } | ||
211 | dev_dbg_f(&udev->dev, "firmware confirm return value %#04x\n", | ||
212 | (unsigned int)ret); | ||
213 | } | ||
214 | |||
215 | r = 0; | ||
216 | error: | ||
217 | kfree(p); | ||
218 | return r; | ||
219 | } | ||
220 | |||
221 | static u16 get_word(const void *data, u16 offset) | ||
222 | { | ||
223 | const __le16 *p = data; | ||
224 | return le16_to_cpu(p[offset]); | ||
225 | } | ||
226 | |||
227 | static char *get_fw_name(struct zd_usb *usb, char *buffer, size_t size, | ||
228 | const char* postfix) | ||
229 | { | ||
230 | scnprintf(buffer, size, "%s%s", | ||
231 | usb->is_zd1211b ? | ||
232 | FW_ZD1211B_PREFIX : FW_ZD1211_PREFIX, | ||
233 | postfix); | ||
234 | return buffer; | ||
235 | } | ||
236 | |||
237 | static int handle_version_mismatch(struct zd_usb *usb, | ||
238 | const struct firmware *ub_fw) | ||
239 | { | ||
240 | struct usb_device *udev = zd_usb_to_usbdev(usb); | ||
241 | const struct firmware *ur_fw = NULL; | ||
242 | int offset; | ||
243 | int r = 0; | ||
244 | char fw_name[128]; | ||
245 | |||
246 | r = request_fw_file(&ur_fw, | ||
247 | get_fw_name(usb, fw_name, sizeof(fw_name), "ur"), | ||
248 | &udev->dev); | ||
249 | if (r) | ||
250 | goto error; | ||
251 | |||
252 | r = upload_code(udev, ur_fw->data, ur_fw->size, FW_START, REBOOT); | ||
253 | if (r) | ||
254 | goto error; | ||
255 | |||
256 | offset = (E2P_BOOT_CODE_OFFSET * sizeof(u16)); | ||
257 | r = upload_code(udev, ub_fw->data + offset, ub_fw->size - offset, | ||
258 | E2P_START + E2P_BOOT_CODE_OFFSET, REBOOT); | ||
259 | |||
260 | /* At this point, the vendor driver downloads the whole firmware | ||
261 | * image, hacks around with version IDs, and uploads it again, | ||
262 | * completely overwriting the boot code. We do not do this here as | ||
263 | * it is not required on any tested devices, and it is suspected to | ||
264 | * cause problems. */ | ||
265 | error: | ||
266 | release_firmware(ur_fw); | ||
267 | return r; | ||
268 | } | ||
269 | |||
270 | static int upload_firmware(struct zd_usb *usb) | ||
271 | { | ||
272 | int r; | ||
273 | u16 fw_bcdDevice; | ||
274 | u16 bcdDevice; | ||
275 | struct usb_device *udev = zd_usb_to_usbdev(usb); | ||
276 | const struct firmware *ub_fw = NULL; | ||
277 | const struct firmware *uph_fw = NULL; | ||
278 | char fw_name[128]; | ||
279 | |||
280 | bcdDevice = get_bcdDevice(udev); | ||
281 | |||
282 | r = request_fw_file(&ub_fw, | ||
283 | get_fw_name(usb, fw_name, sizeof(fw_name), "ub"), | ||
284 | &udev->dev); | ||
285 | if (r) | ||
286 | goto error; | ||
287 | |||
288 | fw_bcdDevice = get_word(ub_fw->data, E2P_DATA_OFFSET); | ||
289 | |||
290 | if (fw_bcdDevice != bcdDevice) { | ||
291 | dev_info(&udev->dev, | ||
292 | "firmware version %#06x and device bootcode version " | ||
293 | "%#06x differ\n", fw_bcdDevice, bcdDevice); | ||
294 | if (bcdDevice <= 0x4313) | ||
295 | dev_warn(&udev->dev, "device has old bootcode, please " | ||
296 | "report success or failure\n"); | ||
297 | |||
298 | r = handle_version_mismatch(usb, ub_fw); | ||
299 | if (r) | ||
300 | goto error; | ||
301 | } else { | ||
302 | dev_dbg_f(&udev->dev, | ||
303 | "firmware device id %#06x is equal to the " | ||
304 | "actual device id\n", fw_bcdDevice); | ||
305 | } | ||
306 | |||
307 | |||
308 | r = request_fw_file(&uph_fw, | ||
309 | get_fw_name(usb, fw_name, sizeof(fw_name), "uphr"), | ||
310 | &udev->dev); | ||
311 | if (r) | ||
312 | goto error; | ||
313 | |||
314 | r = upload_code(udev, uph_fw->data, uph_fw->size, FW_START, REBOOT); | ||
315 | if (r) { | ||
316 | dev_err(&udev->dev, | ||
317 | "Could not upload firmware code uph. Error number %d\n", | ||
318 | r); | ||
319 | } | ||
320 | |||
321 | /* FALL-THROUGH */ | ||
322 | error: | ||
323 | release_firmware(ub_fw); | ||
324 | release_firmware(uph_fw); | ||
325 | return r; | ||
326 | } | ||
327 | |||
328 | MODULE_FIRMWARE(FW_ZD1211B_PREFIX "ur"); | ||
329 | MODULE_FIRMWARE(FW_ZD1211_PREFIX "ur"); | ||
330 | MODULE_FIRMWARE(FW_ZD1211B_PREFIX "ub"); | ||
331 | MODULE_FIRMWARE(FW_ZD1211_PREFIX "ub"); | ||
332 | MODULE_FIRMWARE(FW_ZD1211B_PREFIX "uphr"); | ||
333 | MODULE_FIRMWARE(FW_ZD1211_PREFIX "uphr"); | ||
334 | |||
335 | /* Read data from device address space using "firmware interface" which does | ||
336 | * not require firmware to be loaded. */ | ||
337 | int zd_usb_read_fw(struct zd_usb *usb, zd_addr_t addr, u8 *data, u16 len) | ||
338 | { | ||
339 | int r; | ||
340 | struct usb_device *udev = zd_usb_to_usbdev(usb); | ||
341 | u8 *buf; | ||
342 | |||
343 | /* Use "DMA-aware" buffer. */ | ||
344 | buf = kmalloc(len, GFP_KERNEL); | ||
345 | if (!buf) | ||
346 | return -ENOMEM; | ||
347 | r = usb_control_msg(udev, usb_rcvctrlpipe(udev, 0), | ||
348 | USB_REQ_FIRMWARE_READ_DATA, USB_DIR_IN | 0x40, addr, 0, | ||
349 | buf, len, 5000); | ||
350 | if (r < 0) { | ||
351 | dev_err(&udev->dev, | ||
352 | "read over firmware interface failed: %d\n", r); | ||
353 | goto exit; | ||
354 | } else if (r != len) { | ||
355 | dev_err(&udev->dev, | ||
356 | "incomplete read over firmware interface: %d/%d\n", | ||
357 | r, len); | ||
358 | r = -EIO; | ||
359 | goto exit; | ||
360 | } | ||
361 | r = 0; | ||
362 | memcpy(data, buf, len); | ||
363 | exit: | ||
364 | kfree(buf); | ||
365 | return r; | ||
366 | } | ||
367 | |||
368 | #define urb_dev(urb) (&(urb)->dev->dev) | ||
369 | |||
370 | static inline void handle_regs_int_override(struct urb *urb) | ||
371 | { | ||
372 | struct zd_usb *usb = urb->context; | ||
373 | struct zd_usb_interrupt *intr = &usb->intr; | ||
374 | |||
375 | spin_lock(&intr->lock); | ||
376 | if (atomic_read(&intr->read_regs_enabled)) { | ||
377 | atomic_set(&intr->read_regs_enabled, 0); | ||
378 | intr->read_regs_int_overridden = 1; | ||
379 | complete(&intr->read_regs.completion); | ||
380 | } | ||
381 | spin_unlock(&intr->lock); | ||
382 | } | ||
383 | |||
384 | static inline void handle_regs_int(struct urb *urb) | ||
385 | { | ||
386 | struct zd_usb *usb = urb->context; | ||
387 | struct zd_usb_interrupt *intr = &usb->intr; | ||
388 | int len; | ||
389 | u16 int_num; | ||
390 | |||
391 | ZD_ASSERT(in_interrupt()); | ||
392 | spin_lock(&intr->lock); | ||
393 | |||
394 | int_num = le16_to_cpu(*(__le16 *)(urb->transfer_buffer+2)); | ||
395 | if (int_num == CR_INTERRUPT) { | ||
396 | struct zd_mac *mac = zd_hw_mac(zd_usb_to_hw(urb->context)); | ||
397 | spin_lock(&mac->lock); | ||
398 | memcpy(&mac->intr_buffer, urb->transfer_buffer, | ||
399 | USB_MAX_EP_INT_BUFFER); | ||
400 | spin_unlock(&mac->lock); | ||
401 | schedule_work(&mac->process_intr); | ||
402 | } else if (atomic_read(&intr->read_regs_enabled)) { | ||
403 | len = urb->actual_length; | ||
404 | intr->read_regs.length = urb->actual_length; | ||
405 | if (len > sizeof(intr->read_regs.buffer)) | ||
406 | len = sizeof(intr->read_regs.buffer); | ||
407 | |||
408 | memcpy(intr->read_regs.buffer, urb->transfer_buffer, len); | ||
409 | |||
410 | /* Sometimes USB_INT_ID_REGS is not overridden, but comes after | ||
411 | * USB_INT_ID_RETRY_FAILED. Read-reg retry then gets this | ||
412 | * delayed USB_INT_ID_REGS, but leaves USB_INT_ID_REGS of | ||
413 | * retry unhandled. Next read-reg command then might catch | ||
414 | * this wrong USB_INT_ID_REGS. Fix by ignoring wrong reads. | ||
415 | */ | ||
416 | if (!check_read_regs(usb, intr->read_regs.req, | ||
417 | intr->read_regs.req_count)) | ||
418 | goto out; | ||
419 | |||
420 | atomic_set(&intr->read_regs_enabled, 0); | ||
421 | intr->read_regs_int_overridden = 0; | ||
422 | complete(&intr->read_regs.completion); | ||
423 | |||
424 | goto out; | ||
425 | } | ||
426 | |||
427 | out: | ||
428 | spin_unlock(&intr->lock); | ||
429 | |||
430 | /* CR_INTERRUPT might override read_reg too. */ | ||
431 | if (int_num == CR_INTERRUPT && atomic_read(&intr->read_regs_enabled)) | ||
432 | handle_regs_int_override(urb); | ||
433 | } | ||
434 | |||
435 | static void int_urb_complete(struct urb *urb) | ||
436 | { | ||
437 | int r; | ||
438 | struct usb_int_header *hdr; | ||
439 | struct zd_usb *usb; | ||
440 | struct zd_usb_interrupt *intr; | ||
441 | |||
442 | switch (urb->status) { | ||
443 | case 0: | ||
444 | break; | ||
445 | case -ESHUTDOWN: | ||
446 | case -EINVAL: | ||
447 | case -ENODEV: | ||
448 | case -ENOENT: | ||
449 | case -ECONNRESET: | ||
450 | case -EPIPE: | ||
451 | dev_dbg_f(urb_dev(urb), "urb %p error %d\n", urb, urb->status); | ||
452 | return; | ||
453 | default: | ||
454 | dev_dbg_f(urb_dev(urb), "urb %p error %d\n", urb, urb->status); | ||
455 | goto resubmit; | ||
456 | } | ||
457 | |||
458 | if (urb->actual_length < sizeof(hdr)) { | ||
459 | dev_dbg_f(urb_dev(urb), "error: urb %p to small\n", urb); | ||
460 | goto resubmit; | ||
461 | } | ||
462 | |||
463 | hdr = urb->transfer_buffer; | ||
464 | if (hdr->type != USB_INT_TYPE) { | ||
465 | dev_dbg_f(urb_dev(urb), "error: urb %p wrong type\n", urb); | ||
466 | goto resubmit; | ||
467 | } | ||
468 | |||
469 | /* USB_INT_ID_RETRY_FAILED triggered by tx-urb submit can override | ||
470 | * pending USB_INT_ID_REGS causing read command timeout. | ||
471 | */ | ||
472 | usb = urb->context; | ||
473 | intr = &usb->intr; | ||
474 | if (hdr->id != USB_INT_ID_REGS && atomic_read(&intr->read_regs_enabled)) | ||
475 | handle_regs_int_override(urb); | ||
476 | |||
477 | switch (hdr->id) { | ||
478 | case USB_INT_ID_REGS: | ||
479 | handle_regs_int(urb); | ||
480 | break; | ||
481 | case USB_INT_ID_RETRY_FAILED: | ||
482 | zd_mac_tx_failed(urb); | ||
483 | break; | ||
484 | default: | ||
485 | dev_dbg_f(urb_dev(urb), "error: urb %p unknown id %x\n", urb, | ||
486 | (unsigned int)hdr->id); | ||
487 | goto resubmit; | ||
488 | } | ||
489 | |||
490 | resubmit: | ||
491 | r = usb_submit_urb(urb, GFP_ATOMIC); | ||
492 | if (r) { | ||
493 | dev_dbg_f(urb_dev(urb), "error: resubmit urb %p err code %d\n", | ||
494 | urb, r); | ||
495 | /* TODO: add worker to reset intr->urb */ | ||
496 | } | ||
497 | return; | ||
498 | } | ||
499 | |||
500 | static inline int int_urb_interval(struct usb_device *udev) | ||
501 | { | ||
502 | switch (udev->speed) { | ||
503 | case USB_SPEED_HIGH: | ||
504 | return 4; | ||
505 | case USB_SPEED_LOW: | ||
506 | return 10; | ||
507 | case USB_SPEED_FULL: | ||
508 | default: | ||
509 | return 1; | ||
510 | } | ||
511 | } | ||
512 | |||
513 | static inline int usb_int_enabled(struct zd_usb *usb) | ||
514 | { | ||
515 | unsigned long flags; | ||
516 | struct zd_usb_interrupt *intr = &usb->intr; | ||
517 | struct urb *urb; | ||
518 | |||
519 | spin_lock_irqsave(&intr->lock, flags); | ||
520 | urb = intr->urb; | ||
521 | spin_unlock_irqrestore(&intr->lock, flags); | ||
522 | return urb != NULL; | ||
523 | } | ||
524 | |||
525 | int zd_usb_enable_int(struct zd_usb *usb) | ||
526 | { | ||
527 | int r; | ||
528 | struct usb_device *udev = zd_usb_to_usbdev(usb); | ||
529 | struct zd_usb_interrupt *intr = &usb->intr; | ||
530 | struct urb *urb; | ||
531 | |||
532 | dev_dbg_f(zd_usb_dev(usb), "\n"); | ||
533 | |||
534 | urb = usb_alloc_urb(0, GFP_KERNEL); | ||
535 | if (!urb) { | ||
536 | r = -ENOMEM; | ||
537 | goto out; | ||
538 | } | ||
539 | |||
540 | ZD_ASSERT(!irqs_disabled()); | ||
541 | spin_lock_irq(&intr->lock); | ||
542 | if (intr->urb) { | ||
543 | spin_unlock_irq(&intr->lock); | ||
544 | r = 0; | ||
545 | goto error_free_urb; | ||
546 | } | ||
547 | intr->urb = urb; | ||
548 | spin_unlock_irq(&intr->lock); | ||
549 | |||
550 | r = -ENOMEM; | ||
551 | intr->buffer = usb_alloc_coherent(udev, USB_MAX_EP_INT_BUFFER, | ||
552 | GFP_KERNEL, &intr->buffer_dma); | ||
553 | if (!intr->buffer) { | ||
554 | dev_dbg_f(zd_usb_dev(usb), | ||
555 | "couldn't allocate transfer_buffer\n"); | ||
556 | goto error_set_urb_null; | ||
557 | } | ||
558 | |||
559 | usb_fill_int_urb(urb, udev, usb_rcvintpipe(udev, EP_INT_IN), | ||
560 | intr->buffer, USB_MAX_EP_INT_BUFFER, | ||
561 | int_urb_complete, usb, | ||
562 | intr->interval); | ||
563 | urb->transfer_dma = intr->buffer_dma; | ||
564 | urb->transfer_flags |= URB_NO_TRANSFER_DMA_MAP; | ||
565 | |||
566 | dev_dbg_f(zd_usb_dev(usb), "submit urb %p\n", intr->urb); | ||
567 | r = usb_submit_urb(urb, GFP_KERNEL); | ||
568 | if (r) { | ||
569 | dev_dbg_f(zd_usb_dev(usb), | ||
570 | "Couldn't submit urb. Error number %d\n", r); | ||
571 | goto error; | ||
572 | } | ||
573 | |||
574 | return 0; | ||
575 | error: | ||
576 | usb_free_coherent(udev, USB_MAX_EP_INT_BUFFER, | ||
577 | intr->buffer, intr->buffer_dma); | ||
578 | error_set_urb_null: | ||
579 | spin_lock_irq(&intr->lock); | ||
580 | intr->urb = NULL; | ||
581 | spin_unlock_irq(&intr->lock); | ||
582 | error_free_urb: | ||
583 | usb_free_urb(urb); | ||
584 | out: | ||
585 | return r; | ||
586 | } | ||
587 | |||
588 | void zd_usb_disable_int(struct zd_usb *usb) | ||
589 | { | ||
590 | unsigned long flags; | ||
591 | struct usb_device *udev = zd_usb_to_usbdev(usb); | ||
592 | struct zd_usb_interrupt *intr = &usb->intr; | ||
593 | struct urb *urb; | ||
594 | void *buffer; | ||
595 | dma_addr_t buffer_dma; | ||
596 | |||
597 | spin_lock_irqsave(&intr->lock, flags); | ||
598 | urb = intr->urb; | ||
599 | if (!urb) { | ||
600 | spin_unlock_irqrestore(&intr->lock, flags); | ||
601 | return; | ||
602 | } | ||
603 | intr->urb = NULL; | ||
604 | buffer = intr->buffer; | ||
605 | buffer_dma = intr->buffer_dma; | ||
606 | intr->buffer = NULL; | ||
607 | spin_unlock_irqrestore(&intr->lock, flags); | ||
608 | |||
609 | usb_kill_urb(urb); | ||
610 | dev_dbg_f(zd_usb_dev(usb), "urb %p killed\n", urb); | ||
611 | usb_free_urb(urb); | ||
612 | |||
613 | if (buffer) | ||
614 | usb_free_coherent(udev, USB_MAX_EP_INT_BUFFER, | ||
615 | buffer, buffer_dma); | ||
616 | } | ||
617 | |||
618 | static void handle_rx_packet(struct zd_usb *usb, const u8 *buffer, | ||
619 | unsigned int length) | ||
620 | { | ||
621 | int i; | ||
622 | const struct rx_length_info *length_info; | ||
623 | |||
624 | if (length < sizeof(struct rx_length_info)) { | ||
625 | /* It's not a complete packet anyhow. */ | ||
626 | dev_dbg_f(zd_usb_dev(usb), "invalid, small RX packet : %d\n", | ||
627 | length); | ||
628 | return; | ||
629 | } | ||
630 | length_info = (struct rx_length_info *) | ||
631 | (buffer + length - sizeof(struct rx_length_info)); | ||
632 | |||
633 | /* It might be that three frames are merged into a single URB | ||
634 | * transaction. We have to check for the length info tag. | ||
635 | * | ||
636 | * While testing we discovered that length_info might be unaligned, | ||
637 | * because if USB transactions are merged, the last packet will not | ||
638 | * be padded. Unaligned access might also happen if the length_info | ||
639 | * structure is not present. | ||
640 | */ | ||
641 | if (get_unaligned_le16(&length_info->tag) == RX_LENGTH_INFO_TAG) | ||
642 | { | ||
643 | unsigned int l, k, n; | ||
644 | for (i = 0, l = 0;; i++) { | ||
645 | k = get_unaligned_le16(&length_info->length[i]); | ||
646 | if (k == 0) | ||
647 | return; | ||
648 | n = l+k; | ||
649 | if (n > length) | ||
650 | return; | ||
651 | zd_mac_rx(zd_usb_to_hw(usb), buffer+l, k); | ||
652 | if (i >= 2) | ||
653 | return; | ||
654 | l = (n+3) & ~3; | ||
655 | } | ||
656 | } else { | ||
657 | zd_mac_rx(zd_usb_to_hw(usb), buffer, length); | ||
658 | } | ||
659 | } | ||
660 | |||
661 | static void rx_urb_complete(struct urb *urb) | ||
662 | { | ||
663 | int r; | ||
664 | struct zd_usb *usb; | ||
665 | struct zd_usb_rx *rx; | ||
666 | const u8 *buffer; | ||
667 | unsigned int length; | ||
668 | |||
669 | switch (urb->status) { | ||
670 | case 0: | ||
671 | break; | ||
672 | case -ESHUTDOWN: | ||
673 | case -EINVAL: | ||
674 | case -ENODEV: | ||
675 | case -ENOENT: | ||
676 | case -ECONNRESET: | ||
677 | case -EPIPE: | ||
678 | dev_dbg_f(urb_dev(urb), "urb %p error %d\n", urb, urb->status); | ||
679 | return; | ||
680 | default: | ||
681 | dev_dbg_f(urb_dev(urb), "urb %p error %d\n", urb, urb->status); | ||
682 | goto resubmit; | ||
683 | } | ||
684 | |||
685 | buffer = urb->transfer_buffer; | ||
686 | length = urb->actual_length; | ||
687 | usb = urb->context; | ||
688 | rx = &usb->rx; | ||
689 | |||
690 | tasklet_schedule(&rx->reset_timer_tasklet); | ||
691 | |||
692 | if (length%rx->usb_packet_size > rx->usb_packet_size-4) { | ||
693 | /* If there is an old first fragment, we don't care. */ | ||
694 | dev_dbg_f(urb_dev(urb), "*** first fragment ***\n"); | ||
695 | ZD_ASSERT(length <= ARRAY_SIZE(rx->fragment)); | ||
696 | spin_lock(&rx->lock); | ||
697 | memcpy(rx->fragment, buffer, length); | ||
698 | rx->fragment_length = length; | ||
699 | spin_unlock(&rx->lock); | ||
700 | goto resubmit; | ||
701 | } | ||
702 | |||
703 | spin_lock(&rx->lock); | ||
704 | if (rx->fragment_length > 0) { | ||
705 | /* We are on a second fragment, we believe */ | ||
706 | ZD_ASSERT(length + rx->fragment_length <= | ||
707 | ARRAY_SIZE(rx->fragment)); | ||
708 | dev_dbg_f(urb_dev(urb), "*** second fragment ***\n"); | ||
709 | memcpy(rx->fragment+rx->fragment_length, buffer, length); | ||
710 | handle_rx_packet(usb, rx->fragment, | ||
711 | rx->fragment_length + length); | ||
712 | rx->fragment_length = 0; | ||
713 | spin_unlock(&rx->lock); | ||
714 | } else { | ||
715 | spin_unlock(&rx->lock); | ||
716 | handle_rx_packet(usb, buffer, length); | ||
717 | } | ||
718 | |||
719 | resubmit: | ||
720 | r = usb_submit_urb(urb, GFP_ATOMIC); | ||
721 | if (r) | ||
722 | dev_dbg_f(urb_dev(urb), "urb %p resubmit error %d\n", urb, r); | ||
723 | } | ||
724 | |||
725 | static struct urb *alloc_rx_urb(struct zd_usb *usb) | ||
726 | { | ||
727 | struct usb_device *udev = zd_usb_to_usbdev(usb); | ||
728 | struct urb *urb; | ||
729 | void *buffer; | ||
730 | |||
731 | urb = usb_alloc_urb(0, GFP_KERNEL); | ||
732 | if (!urb) | ||
733 | return NULL; | ||
734 | buffer = usb_alloc_coherent(udev, USB_MAX_RX_SIZE, GFP_KERNEL, | ||
735 | &urb->transfer_dma); | ||
736 | if (!buffer) { | ||
737 | usb_free_urb(urb); | ||
738 | return NULL; | ||
739 | } | ||
740 | |||
741 | usb_fill_bulk_urb(urb, udev, usb_rcvbulkpipe(udev, EP_DATA_IN), | ||
742 | buffer, USB_MAX_RX_SIZE, | ||
743 | rx_urb_complete, usb); | ||
744 | urb->transfer_flags |= URB_NO_TRANSFER_DMA_MAP; | ||
745 | |||
746 | return urb; | ||
747 | } | ||
748 | |||
749 | static void free_rx_urb(struct urb *urb) | ||
750 | { | ||
751 | if (!urb) | ||
752 | return; | ||
753 | usb_free_coherent(urb->dev, urb->transfer_buffer_length, | ||
754 | urb->transfer_buffer, urb->transfer_dma); | ||
755 | usb_free_urb(urb); | ||
756 | } | ||
757 | |||
758 | static int __zd_usb_enable_rx(struct zd_usb *usb) | ||
759 | { | ||
760 | int i, r; | ||
761 | struct zd_usb_rx *rx = &usb->rx; | ||
762 | struct urb **urbs; | ||
763 | |||
764 | dev_dbg_f(zd_usb_dev(usb), "\n"); | ||
765 | |||
766 | r = -ENOMEM; | ||
767 | urbs = kcalloc(RX_URBS_COUNT, sizeof(struct urb *), GFP_KERNEL); | ||
768 | if (!urbs) | ||
769 | goto error; | ||
770 | for (i = 0; i < RX_URBS_COUNT; i++) { | ||
771 | urbs[i] = alloc_rx_urb(usb); | ||
772 | if (!urbs[i]) | ||
773 | goto error; | ||
774 | } | ||
775 | |||
776 | ZD_ASSERT(!irqs_disabled()); | ||
777 | spin_lock_irq(&rx->lock); | ||
778 | if (rx->urbs) { | ||
779 | spin_unlock_irq(&rx->lock); | ||
780 | r = 0; | ||
781 | goto error; | ||
782 | } | ||
783 | rx->urbs = urbs; | ||
784 | rx->urbs_count = RX_URBS_COUNT; | ||
785 | spin_unlock_irq(&rx->lock); | ||
786 | |||
787 | for (i = 0; i < RX_URBS_COUNT; i++) { | ||
788 | r = usb_submit_urb(urbs[i], GFP_KERNEL); | ||
789 | if (r) | ||
790 | goto error_submit; | ||
791 | } | ||
792 | |||
793 | return 0; | ||
794 | error_submit: | ||
795 | for (i = 0; i < RX_URBS_COUNT; i++) { | ||
796 | usb_kill_urb(urbs[i]); | ||
797 | } | ||
798 | spin_lock_irq(&rx->lock); | ||
799 | rx->urbs = NULL; | ||
800 | rx->urbs_count = 0; | ||
801 | spin_unlock_irq(&rx->lock); | ||
802 | error: | ||
803 | if (urbs) { | ||
804 | for (i = 0; i < RX_URBS_COUNT; i++) | ||
805 | free_rx_urb(urbs[i]); | ||
806 | } | ||
807 | return r; | ||
808 | } | ||
809 | |||
810 | int zd_usb_enable_rx(struct zd_usb *usb) | ||
811 | { | ||
812 | int r; | ||
813 | struct zd_usb_rx *rx = &usb->rx; | ||
814 | |||
815 | mutex_lock(&rx->setup_mutex); | ||
816 | r = __zd_usb_enable_rx(usb); | ||
817 | mutex_unlock(&rx->setup_mutex); | ||
818 | |||
819 | zd_usb_reset_rx_idle_timer(usb); | ||
820 | |||
821 | return r; | ||
822 | } | ||
823 | |||
824 | static void __zd_usb_disable_rx(struct zd_usb *usb) | ||
825 | { | ||
826 | int i; | ||
827 | unsigned long flags; | ||
828 | struct urb **urbs; | ||
829 | unsigned int count; | ||
830 | struct zd_usb_rx *rx = &usb->rx; | ||
831 | |||
832 | spin_lock_irqsave(&rx->lock, flags); | ||
833 | urbs = rx->urbs; | ||
834 | count = rx->urbs_count; | ||
835 | spin_unlock_irqrestore(&rx->lock, flags); | ||
836 | if (!urbs) | ||
837 | return; | ||
838 | |||
839 | for (i = 0; i < count; i++) { | ||
840 | usb_kill_urb(urbs[i]); | ||
841 | free_rx_urb(urbs[i]); | ||
842 | } | ||
843 | kfree(urbs); | ||
844 | |||
845 | spin_lock_irqsave(&rx->lock, flags); | ||
846 | rx->urbs = NULL; | ||
847 | rx->urbs_count = 0; | ||
848 | spin_unlock_irqrestore(&rx->lock, flags); | ||
849 | } | ||
850 | |||
851 | void zd_usb_disable_rx(struct zd_usb *usb) | ||
852 | { | ||
853 | struct zd_usb_rx *rx = &usb->rx; | ||
854 | |||
855 | mutex_lock(&rx->setup_mutex); | ||
856 | __zd_usb_disable_rx(usb); | ||
857 | mutex_unlock(&rx->setup_mutex); | ||
858 | |||
859 | tasklet_kill(&rx->reset_timer_tasklet); | ||
860 | cancel_delayed_work_sync(&rx->idle_work); | ||
861 | } | ||
862 | |||
863 | static void zd_usb_reset_rx(struct zd_usb *usb) | ||
864 | { | ||
865 | bool do_reset; | ||
866 | struct zd_usb_rx *rx = &usb->rx; | ||
867 | unsigned long flags; | ||
868 | |||
869 | mutex_lock(&rx->setup_mutex); | ||
870 | |||
871 | spin_lock_irqsave(&rx->lock, flags); | ||
872 | do_reset = rx->urbs != NULL; | ||
873 | spin_unlock_irqrestore(&rx->lock, flags); | ||
874 | |||
875 | if (do_reset) { | ||
876 | __zd_usb_disable_rx(usb); | ||
877 | __zd_usb_enable_rx(usb); | ||
878 | } | ||
879 | |||
880 | mutex_unlock(&rx->setup_mutex); | ||
881 | |||
882 | if (do_reset) | ||
883 | zd_usb_reset_rx_idle_timer(usb); | ||
884 | } | ||
885 | |||
886 | /** | ||
887 | * zd_usb_disable_tx - disable transmission | ||
888 | * @usb: the zd1211rw-private USB structure | ||
889 | * | ||
890 | * Frees all URBs in the free list and marks the transmission as disabled. | ||
891 | */ | ||
892 | void zd_usb_disable_tx(struct zd_usb *usb) | ||
893 | { | ||
894 | struct zd_usb_tx *tx = &usb->tx; | ||
895 | unsigned long flags; | ||
896 | |||
897 | atomic_set(&tx->enabled, 0); | ||
898 | |||
899 | /* kill all submitted tx-urbs */ | ||
900 | usb_kill_anchored_urbs(&tx->submitted); | ||
901 | |||
902 | spin_lock_irqsave(&tx->lock, flags); | ||
903 | WARN_ON(!skb_queue_empty(&tx->submitted_skbs)); | ||
904 | WARN_ON(tx->submitted_urbs != 0); | ||
905 | tx->submitted_urbs = 0; | ||
906 | spin_unlock_irqrestore(&tx->lock, flags); | ||
907 | |||
908 | /* The stopped state is ignored, relying on ieee80211_wake_queues() | ||
909 | * in a potentionally following zd_usb_enable_tx(). | ||
910 | */ | ||
911 | } | ||
912 | |||
913 | /** | ||
914 | * zd_usb_enable_tx - enables transmission | ||
915 | * @usb: a &struct zd_usb pointer | ||
916 | * | ||
917 | * This function enables transmission and prepares the &zd_usb_tx data | ||
918 | * structure. | ||
919 | */ | ||
920 | void zd_usb_enable_tx(struct zd_usb *usb) | ||
921 | { | ||
922 | unsigned long flags; | ||
923 | struct zd_usb_tx *tx = &usb->tx; | ||
924 | |||
925 | spin_lock_irqsave(&tx->lock, flags); | ||
926 | atomic_set(&tx->enabled, 1); | ||
927 | tx->submitted_urbs = 0; | ||
928 | ieee80211_wake_queues(zd_usb_to_hw(usb)); | ||
929 | tx->stopped = 0; | ||
930 | spin_unlock_irqrestore(&tx->lock, flags); | ||
931 | } | ||
932 | |||
933 | static void tx_dec_submitted_urbs(struct zd_usb *usb) | ||
934 | { | ||
935 | struct zd_usb_tx *tx = &usb->tx; | ||
936 | unsigned long flags; | ||
937 | |||
938 | spin_lock_irqsave(&tx->lock, flags); | ||
939 | --tx->submitted_urbs; | ||
940 | if (tx->stopped && tx->submitted_urbs <= ZD_USB_TX_LOW) { | ||
941 | ieee80211_wake_queues(zd_usb_to_hw(usb)); | ||
942 | tx->stopped = 0; | ||
943 | } | ||
944 | spin_unlock_irqrestore(&tx->lock, flags); | ||
945 | } | ||
946 | |||
947 | static void tx_inc_submitted_urbs(struct zd_usb *usb) | ||
948 | { | ||
949 | struct zd_usb_tx *tx = &usb->tx; | ||
950 | unsigned long flags; | ||
951 | |||
952 | spin_lock_irqsave(&tx->lock, flags); | ||
953 | ++tx->submitted_urbs; | ||
954 | if (!tx->stopped && tx->submitted_urbs > ZD_USB_TX_HIGH) { | ||
955 | ieee80211_stop_queues(zd_usb_to_hw(usb)); | ||
956 | tx->stopped = 1; | ||
957 | } | ||
958 | spin_unlock_irqrestore(&tx->lock, flags); | ||
959 | } | ||
960 | |||
961 | /** | ||
962 | * tx_urb_complete - completes the execution of an URB | ||
963 | * @urb: a URB | ||
964 | * | ||
965 | * This function is called if the URB has been transferred to a device or an | ||
966 | * error has happened. | ||
967 | */ | ||
968 | static void tx_urb_complete(struct urb *urb) | ||
969 | { | ||
970 | int r; | ||
971 | struct sk_buff *skb; | ||
972 | struct ieee80211_tx_info *info; | ||
973 | struct zd_usb *usb; | ||
974 | struct zd_usb_tx *tx; | ||
975 | |||
976 | skb = (struct sk_buff *)urb->context; | ||
977 | info = IEEE80211_SKB_CB(skb); | ||
978 | /* | ||
979 | * grab 'usb' pointer before handing off the skb (since | ||
980 | * it might be freed by zd_mac_tx_to_dev or mac80211) | ||
981 | */ | ||
982 | usb = &zd_hw_mac(info->rate_driver_data[0])->chip.usb; | ||
983 | tx = &usb->tx; | ||
984 | |||
985 | switch (urb->status) { | ||
986 | case 0: | ||
987 | break; | ||
988 | case -ESHUTDOWN: | ||
989 | case -EINVAL: | ||
990 | case -ENODEV: | ||
991 | case -ENOENT: | ||
992 | case -ECONNRESET: | ||
993 | case -EPIPE: | ||
994 | dev_dbg_f(urb_dev(urb), "urb %p error %d\n", urb, urb->status); | ||
995 | break; | ||
996 | default: | ||
997 | dev_dbg_f(urb_dev(urb), "urb %p error %d\n", urb, urb->status); | ||
998 | goto resubmit; | ||
999 | } | ||
1000 | free_urb: | ||
1001 | skb_unlink(skb, &usb->tx.submitted_skbs); | ||
1002 | zd_mac_tx_to_dev(skb, urb->status); | ||
1003 | usb_free_urb(urb); | ||
1004 | tx_dec_submitted_urbs(usb); | ||
1005 | return; | ||
1006 | resubmit: | ||
1007 | usb_anchor_urb(urb, &tx->submitted); | ||
1008 | r = usb_submit_urb(urb, GFP_ATOMIC); | ||
1009 | if (r) { | ||
1010 | usb_unanchor_urb(urb); | ||
1011 | dev_dbg_f(urb_dev(urb), "error resubmit urb %p %d\n", urb, r); | ||
1012 | goto free_urb; | ||
1013 | } | ||
1014 | } | ||
1015 | |||
1016 | /** | ||
1017 | * zd_usb_tx: initiates transfer of a frame of the device | ||
1018 | * | ||
1019 | * @usb: the zd1211rw-private USB structure | ||
1020 | * @skb: a &struct sk_buff pointer | ||
1021 | * | ||
1022 | * This function tranmits a frame to the device. It doesn't wait for | ||
1023 | * completion. The frame must contain the control set and have all the | ||
1024 | * control set information available. | ||
1025 | * | ||
1026 | * The function returns 0 if the transfer has been successfully initiated. | ||
1027 | */ | ||
1028 | int zd_usb_tx(struct zd_usb *usb, struct sk_buff *skb) | ||
1029 | { | ||
1030 | int r; | ||
1031 | struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb); | ||
1032 | struct usb_device *udev = zd_usb_to_usbdev(usb); | ||
1033 | struct urb *urb; | ||
1034 | struct zd_usb_tx *tx = &usb->tx; | ||
1035 | |||
1036 | if (!atomic_read(&tx->enabled)) { | ||
1037 | r = -ENOENT; | ||
1038 | goto out; | ||
1039 | } | ||
1040 | |||
1041 | urb = usb_alloc_urb(0, GFP_ATOMIC); | ||
1042 | if (!urb) { | ||
1043 | r = -ENOMEM; | ||
1044 | goto out; | ||
1045 | } | ||
1046 | |||
1047 | usb_fill_bulk_urb(urb, udev, usb_sndbulkpipe(udev, EP_DATA_OUT), | ||
1048 | skb->data, skb->len, tx_urb_complete, skb); | ||
1049 | |||
1050 | info->rate_driver_data[1] = (void *)jiffies; | ||
1051 | skb_queue_tail(&tx->submitted_skbs, skb); | ||
1052 | usb_anchor_urb(urb, &tx->submitted); | ||
1053 | |||
1054 | r = usb_submit_urb(urb, GFP_ATOMIC); | ||
1055 | if (r) { | ||
1056 | dev_dbg_f(zd_usb_dev(usb), "error submit urb %p %d\n", urb, r); | ||
1057 | usb_unanchor_urb(urb); | ||
1058 | skb_unlink(skb, &tx->submitted_skbs); | ||
1059 | goto error; | ||
1060 | } | ||
1061 | tx_inc_submitted_urbs(usb); | ||
1062 | return 0; | ||
1063 | error: | ||
1064 | usb_free_urb(urb); | ||
1065 | out: | ||
1066 | return r; | ||
1067 | } | ||
1068 | |||
1069 | static bool zd_tx_timeout(struct zd_usb *usb) | ||
1070 | { | ||
1071 | struct zd_usb_tx *tx = &usb->tx; | ||
1072 | struct sk_buff_head *q = &tx->submitted_skbs; | ||
1073 | struct sk_buff *skb, *skbnext; | ||
1074 | struct ieee80211_tx_info *info; | ||
1075 | unsigned long flags, trans_start; | ||
1076 | bool have_timedout = false; | ||
1077 | |||
1078 | spin_lock_irqsave(&q->lock, flags); | ||
1079 | skb_queue_walk_safe(q, skb, skbnext) { | ||
1080 | info = IEEE80211_SKB_CB(skb); | ||
1081 | trans_start = (unsigned long)info->rate_driver_data[1]; | ||
1082 | |||
1083 | if (time_is_before_jiffies(trans_start + ZD_TX_TIMEOUT)) { | ||
1084 | have_timedout = true; | ||
1085 | break; | ||
1086 | } | ||
1087 | } | ||
1088 | spin_unlock_irqrestore(&q->lock, flags); | ||
1089 | |||
1090 | return have_timedout; | ||
1091 | } | ||
1092 | |||
1093 | static void zd_tx_watchdog_handler(struct work_struct *work) | ||
1094 | { | ||
1095 | struct zd_usb *usb = | ||
1096 | container_of(work, struct zd_usb, tx.watchdog_work.work); | ||
1097 | struct zd_usb_tx *tx = &usb->tx; | ||
1098 | |||
1099 | if (!atomic_read(&tx->enabled) || !tx->watchdog_enabled) | ||
1100 | goto out; | ||
1101 | if (!zd_tx_timeout(usb)) | ||
1102 | goto out; | ||
1103 | |||
1104 | /* TX halted, try reset */ | ||
1105 | dev_warn(zd_usb_dev(usb), "TX-stall detected, resetting device..."); | ||
1106 | |||
1107 | usb_queue_reset_device(usb->intf); | ||
1108 | |||
1109 | /* reset will stop this worker, don't rearm */ | ||
1110 | return; | ||
1111 | out: | ||
1112 | queue_delayed_work(zd_workqueue, &tx->watchdog_work, | ||
1113 | ZD_TX_WATCHDOG_INTERVAL); | ||
1114 | } | ||
1115 | |||
1116 | void zd_tx_watchdog_enable(struct zd_usb *usb) | ||
1117 | { | ||
1118 | struct zd_usb_tx *tx = &usb->tx; | ||
1119 | |||
1120 | if (!tx->watchdog_enabled) { | ||
1121 | dev_dbg_f(zd_usb_dev(usb), "\n"); | ||
1122 | queue_delayed_work(zd_workqueue, &tx->watchdog_work, | ||
1123 | ZD_TX_WATCHDOG_INTERVAL); | ||
1124 | tx->watchdog_enabled = 1; | ||
1125 | } | ||
1126 | } | ||
1127 | |||
1128 | void zd_tx_watchdog_disable(struct zd_usb *usb) | ||
1129 | { | ||
1130 | struct zd_usb_tx *tx = &usb->tx; | ||
1131 | |||
1132 | if (tx->watchdog_enabled) { | ||
1133 | dev_dbg_f(zd_usb_dev(usb), "\n"); | ||
1134 | tx->watchdog_enabled = 0; | ||
1135 | cancel_delayed_work_sync(&tx->watchdog_work); | ||
1136 | } | ||
1137 | } | ||
1138 | |||
1139 | static void zd_rx_idle_timer_handler(struct work_struct *work) | ||
1140 | { | ||
1141 | struct zd_usb *usb = | ||
1142 | container_of(work, struct zd_usb, rx.idle_work.work); | ||
1143 | struct zd_mac *mac = zd_usb_to_mac(usb); | ||
1144 | |||
1145 | if (!test_bit(ZD_DEVICE_RUNNING, &mac->flags)) | ||
1146 | return; | ||
1147 | |||
1148 | dev_dbg_f(zd_usb_dev(usb), "\n"); | ||
1149 | |||
1150 | /* 30 seconds since last rx, reset rx */ | ||
1151 | zd_usb_reset_rx(usb); | ||
1152 | } | ||
1153 | |||
1154 | static void zd_usb_reset_rx_idle_timer_tasklet(unsigned long param) | ||
1155 | { | ||
1156 | struct zd_usb *usb = (struct zd_usb *)param; | ||
1157 | |||
1158 | zd_usb_reset_rx_idle_timer(usb); | ||
1159 | } | ||
1160 | |||
1161 | void zd_usb_reset_rx_idle_timer(struct zd_usb *usb) | ||
1162 | { | ||
1163 | struct zd_usb_rx *rx = &usb->rx; | ||
1164 | |||
1165 | mod_delayed_work(zd_workqueue, &rx->idle_work, ZD_RX_IDLE_INTERVAL); | ||
1166 | } | ||
1167 | |||
1168 | static inline void init_usb_interrupt(struct zd_usb *usb) | ||
1169 | { | ||
1170 | struct zd_usb_interrupt *intr = &usb->intr; | ||
1171 | |||
1172 | spin_lock_init(&intr->lock); | ||
1173 | intr->interval = int_urb_interval(zd_usb_to_usbdev(usb)); | ||
1174 | init_completion(&intr->read_regs.completion); | ||
1175 | atomic_set(&intr->read_regs_enabled, 0); | ||
1176 | intr->read_regs.cr_int_addr = cpu_to_le16((u16)CR_INTERRUPT); | ||
1177 | } | ||
1178 | |||
1179 | static inline void init_usb_rx(struct zd_usb *usb) | ||
1180 | { | ||
1181 | struct zd_usb_rx *rx = &usb->rx; | ||
1182 | |||
1183 | spin_lock_init(&rx->lock); | ||
1184 | mutex_init(&rx->setup_mutex); | ||
1185 | if (interface_to_usbdev(usb->intf)->speed == USB_SPEED_HIGH) { | ||
1186 | rx->usb_packet_size = 512; | ||
1187 | } else { | ||
1188 | rx->usb_packet_size = 64; | ||
1189 | } | ||
1190 | ZD_ASSERT(rx->fragment_length == 0); | ||
1191 | INIT_DELAYED_WORK(&rx->idle_work, zd_rx_idle_timer_handler); | ||
1192 | rx->reset_timer_tasklet.func = zd_usb_reset_rx_idle_timer_tasklet; | ||
1193 | rx->reset_timer_tasklet.data = (unsigned long)usb; | ||
1194 | } | ||
1195 | |||
1196 | static inline void init_usb_tx(struct zd_usb *usb) | ||
1197 | { | ||
1198 | struct zd_usb_tx *tx = &usb->tx; | ||
1199 | |||
1200 | spin_lock_init(&tx->lock); | ||
1201 | atomic_set(&tx->enabled, 0); | ||
1202 | tx->stopped = 0; | ||
1203 | skb_queue_head_init(&tx->submitted_skbs); | ||
1204 | init_usb_anchor(&tx->submitted); | ||
1205 | tx->submitted_urbs = 0; | ||
1206 | tx->watchdog_enabled = 0; | ||
1207 | INIT_DELAYED_WORK(&tx->watchdog_work, zd_tx_watchdog_handler); | ||
1208 | } | ||
1209 | |||
1210 | void zd_usb_init(struct zd_usb *usb, struct ieee80211_hw *hw, | ||
1211 | struct usb_interface *intf) | ||
1212 | { | ||
1213 | memset(usb, 0, sizeof(*usb)); | ||
1214 | usb->intf = usb_get_intf(intf); | ||
1215 | usb_set_intfdata(usb->intf, hw); | ||
1216 | init_usb_anchor(&usb->submitted_cmds); | ||
1217 | init_usb_interrupt(usb); | ||
1218 | init_usb_tx(usb); | ||
1219 | init_usb_rx(usb); | ||
1220 | } | ||
1221 | |||
1222 | void zd_usb_clear(struct zd_usb *usb) | ||
1223 | { | ||
1224 | usb_set_intfdata(usb->intf, NULL); | ||
1225 | usb_put_intf(usb->intf); | ||
1226 | ZD_MEMCLEAR(usb, sizeof(*usb)); | ||
1227 | /* FIXME: usb_interrupt, usb_tx, usb_rx? */ | ||
1228 | } | ||
1229 | |||
1230 | static const char *speed(enum usb_device_speed speed) | ||
1231 | { | ||
1232 | switch (speed) { | ||
1233 | case USB_SPEED_LOW: | ||
1234 | return "low"; | ||
1235 | case USB_SPEED_FULL: | ||
1236 | return "full"; | ||
1237 | case USB_SPEED_HIGH: | ||
1238 | return "high"; | ||
1239 | default: | ||
1240 | return "unknown speed"; | ||
1241 | } | ||
1242 | } | ||
1243 | |||
1244 | static int scnprint_id(struct usb_device *udev, char *buffer, size_t size) | ||
1245 | { | ||
1246 | return scnprintf(buffer, size, "%04hx:%04hx v%04hx %s", | ||
1247 | le16_to_cpu(udev->descriptor.idVendor), | ||
1248 | le16_to_cpu(udev->descriptor.idProduct), | ||
1249 | get_bcdDevice(udev), | ||
1250 | speed(udev->speed)); | ||
1251 | } | ||
1252 | |||
1253 | int zd_usb_scnprint_id(struct zd_usb *usb, char *buffer, size_t size) | ||
1254 | { | ||
1255 | struct usb_device *udev = interface_to_usbdev(usb->intf); | ||
1256 | return scnprint_id(udev, buffer, size); | ||
1257 | } | ||
1258 | |||
1259 | #ifdef DEBUG | ||
1260 | static void print_id(struct usb_device *udev) | ||
1261 | { | ||
1262 | char buffer[40]; | ||
1263 | |||
1264 | scnprint_id(udev, buffer, sizeof(buffer)); | ||
1265 | buffer[sizeof(buffer)-1] = 0; | ||
1266 | dev_dbg_f(&udev->dev, "%s\n", buffer); | ||
1267 | } | ||
1268 | #else | ||
1269 | #define print_id(udev) do { } while (0) | ||
1270 | #endif | ||
1271 | |||
1272 | static int eject_installer(struct usb_interface *intf) | ||
1273 | { | ||
1274 | struct usb_device *udev = interface_to_usbdev(intf); | ||
1275 | struct usb_host_interface *iface_desc = &intf->altsetting[0]; | ||
1276 | struct usb_endpoint_descriptor *endpoint; | ||
1277 | unsigned char *cmd; | ||
1278 | u8 bulk_out_ep; | ||
1279 | int r; | ||
1280 | |||
1281 | /* Find bulk out endpoint */ | ||
1282 | for (r = 1; r >= 0; r--) { | ||
1283 | endpoint = &iface_desc->endpoint[r].desc; | ||
1284 | if (usb_endpoint_dir_out(endpoint) && | ||
1285 | usb_endpoint_xfer_bulk(endpoint)) { | ||
1286 | bulk_out_ep = endpoint->bEndpointAddress; | ||
1287 | break; | ||
1288 | } | ||
1289 | } | ||
1290 | if (r == -1) { | ||
1291 | dev_err(&udev->dev, | ||
1292 | "zd1211rw: Could not find bulk out endpoint\n"); | ||
1293 | return -ENODEV; | ||
1294 | } | ||
1295 | |||
1296 | cmd = kzalloc(31, GFP_KERNEL); | ||
1297 | if (cmd == NULL) | ||
1298 | return -ENODEV; | ||
1299 | |||
1300 | /* USB bulk command block */ | ||
1301 | cmd[0] = 0x55; /* bulk command signature */ | ||
1302 | cmd[1] = 0x53; /* bulk command signature */ | ||
1303 | cmd[2] = 0x42; /* bulk command signature */ | ||
1304 | cmd[3] = 0x43; /* bulk command signature */ | ||
1305 | cmd[14] = 6; /* command length */ | ||
1306 | |||
1307 | cmd[15] = 0x1b; /* SCSI command: START STOP UNIT */ | ||
1308 | cmd[19] = 0x2; /* eject disc */ | ||
1309 | |||
1310 | dev_info(&udev->dev, "Ejecting virtual installer media...\n"); | ||
1311 | r = usb_bulk_msg(udev, usb_sndbulkpipe(udev, bulk_out_ep), | ||
1312 | cmd, 31, NULL, 2000); | ||
1313 | kfree(cmd); | ||
1314 | if (r) | ||
1315 | return r; | ||
1316 | |||
1317 | /* At this point, the device disconnects and reconnects with the real | ||
1318 | * ID numbers. */ | ||
1319 | |||
1320 | usb_set_intfdata(intf, NULL); | ||
1321 | return 0; | ||
1322 | } | ||
1323 | |||
1324 | int zd_usb_init_hw(struct zd_usb *usb) | ||
1325 | { | ||
1326 | int r; | ||
1327 | struct zd_mac *mac = zd_usb_to_mac(usb); | ||
1328 | |||
1329 | dev_dbg_f(zd_usb_dev(usb), "\n"); | ||
1330 | |||
1331 | r = upload_firmware(usb); | ||
1332 | if (r) { | ||
1333 | dev_err(zd_usb_dev(usb), | ||
1334 | "couldn't load firmware. Error number %d\n", r); | ||
1335 | return r; | ||
1336 | } | ||
1337 | |||
1338 | r = usb_reset_configuration(zd_usb_to_usbdev(usb)); | ||
1339 | if (r) { | ||
1340 | dev_dbg_f(zd_usb_dev(usb), | ||
1341 | "couldn't reset configuration. Error number %d\n", r); | ||
1342 | return r; | ||
1343 | } | ||
1344 | |||
1345 | r = zd_mac_init_hw(mac->hw); | ||
1346 | if (r) { | ||
1347 | dev_dbg_f(zd_usb_dev(usb), | ||
1348 | "couldn't initialize mac. Error number %d\n", r); | ||
1349 | return r; | ||
1350 | } | ||
1351 | |||
1352 | usb->initialized = 1; | ||
1353 | return 0; | ||
1354 | } | ||
1355 | |||
1356 | static int probe(struct usb_interface *intf, const struct usb_device_id *id) | ||
1357 | { | ||
1358 | int r; | ||
1359 | struct usb_device *udev = interface_to_usbdev(intf); | ||
1360 | struct zd_usb *usb; | ||
1361 | struct ieee80211_hw *hw = NULL; | ||
1362 | |||
1363 | print_id(udev); | ||
1364 | |||
1365 | if (id->driver_info & DEVICE_INSTALLER) | ||
1366 | return eject_installer(intf); | ||
1367 | |||
1368 | switch (udev->speed) { | ||
1369 | case USB_SPEED_LOW: | ||
1370 | case USB_SPEED_FULL: | ||
1371 | case USB_SPEED_HIGH: | ||
1372 | break; | ||
1373 | default: | ||
1374 | dev_dbg_f(&intf->dev, "Unknown USB speed\n"); | ||
1375 | r = -ENODEV; | ||
1376 | goto error; | ||
1377 | } | ||
1378 | |||
1379 | r = usb_reset_device(udev); | ||
1380 | if (r) { | ||
1381 | dev_err(&intf->dev, | ||
1382 | "couldn't reset usb device. Error number %d\n", r); | ||
1383 | goto error; | ||
1384 | } | ||
1385 | |||
1386 | hw = zd_mac_alloc_hw(intf); | ||
1387 | if (hw == NULL) { | ||
1388 | r = -ENOMEM; | ||
1389 | goto error; | ||
1390 | } | ||
1391 | |||
1392 | usb = &zd_hw_mac(hw)->chip.usb; | ||
1393 | usb->is_zd1211b = (id->driver_info == DEVICE_ZD1211B) != 0; | ||
1394 | |||
1395 | r = zd_mac_preinit_hw(hw); | ||
1396 | if (r) { | ||
1397 | dev_dbg_f(&intf->dev, | ||
1398 | "couldn't initialize mac. Error number %d\n", r); | ||
1399 | goto error; | ||
1400 | } | ||
1401 | |||
1402 | r = ieee80211_register_hw(hw); | ||
1403 | if (r) { | ||
1404 | dev_dbg_f(&intf->dev, | ||
1405 | "couldn't register device. Error number %d\n", r); | ||
1406 | goto error; | ||
1407 | } | ||
1408 | |||
1409 | dev_dbg_f(&intf->dev, "successful\n"); | ||
1410 | dev_info(&intf->dev, "%s\n", wiphy_name(hw->wiphy)); | ||
1411 | return 0; | ||
1412 | error: | ||
1413 | usb_reset_device(interface_to_usbdev(intf)); | ||
1414 | if (hw) { | ||
1415 | zd_mac_clear(zd_hw_mac(hw)); | ||
1416 | ieee80211_free_hw(hw); | ||
1417 | } | ||
1418 | return r; | ||
1419 | } | ||
1420 | |||
1421 | static void disconnect(struct usb_interface *intf) | ||
1422 | { | ||
1423 | struct ieee80211_hw *hw = zd_intf_to_hw(intf); | ||
1424 | struct zd_mac *mac; | ||
1425 | struct zd_usb *usb; | ||
1426 | |||
1427 | /* Either something really bad happened, or we're just dealing with | ||
1428 | * a DEVICE_INSTALLER. */ | ||
1429 | if (hw == NULL) | ||
1430 | return; | ||
1431 | |||
1432 | mac = zd_hw_mac(hw); | ||
1433 | usb = &mac->chip.usb; | ||
1434 | |||
1435 | dev_dbg_f(zd_usb_dev(usb), "\n"); | ||
1436 | |||
1437 | ieee80211_unregister_hw(hw); | ||
1438 | |||
1439 | /* Just in case something has gone wrong! */ | ||
1440 | zd_usb_disable_tx(usb); | ||
1441 | zd_usb_disable_rx(usb); | ||
1442 | zd_usb_disable_int(usb); | ||
1443 | |||
1444 | /* If the disconnect has been caused by a removal of the | ||
1445 | * driver module, the reset allows reloading of the driver. If the | ||
1446 | * reset will not be executed here, the upload of the firmware in the | ||
1447 | * probe function caused by the reloading of the driver will fail. | ||
1448 | */ | ||
1449 | usb_reset_device(interface_to_usbdev(intf)); | ||
1450 | |||
1451 | zd_mac_clear(mac); | ||
1452 | ieee80211_free_hw(hw); | ||
1453 | dev_dbg(&intf->dev, "disconnected\n"); | ||
1454 | } | ||
1455 | |||
1456 | static void zd_usb_resume(struct zd_usb *usb) | ||
1457 | { | ||
1458 | struct zd_mac *mac = zd_usb_to_mac(usb); | ||
1459 | int r; | ||
1460 | |||
1461 | dev_dbg_f(zd_usb_dev(usb), "\n"); | ||
1462 | |||
1463 | r = zd_op_start(zd_usb_to_hw(usb)); | ||
1464 | if (r < 0) { | ||
1465 | dev_warn(zd_usb_dev(usb), "Device resume failed " | ||
1466 | "with error code %d. Retrying...\n", r); | ||
1467 | if (usb->was_running) | ||
1468 | set_bit(ZD_DEVICE_RUNNING, &mac->flags); | ||
1469 | usb_queue_reset_device(usb->intf); | ||
1470 | return; | ||
1471 | } | ||
1472 | |||
1473 | if (mac->type != NL80211_IFTYPE_UNSPECIFIED) { | ||
1474 | r = zd_restore_settings(mac); | ||
1475 | if (r < 0) { | ||
1476 | dev_dbg(zd_usb_dev(usb), | ||
1477 | "failed to restore settings, %d\n", r); | ||
1478 | return; | ||
1479 | } | ||
1480 | } | ||
1481 | } | ||
1482 | |||
1483 | static void zd_usb_stop(struct zd_usb *usb) | ||
1484 | { | ||
1485 | dev_dbg_f(zd_usb_dev(usb), "\n"); | ||
1486 | |||
1487 | zd_op_stop(zd_usb_to_hw(usb)); | ||
1488 | |||
1489 | zd_usb_disable_tx(usb); | ||
1490 | zd_usb_disable_rx(usb); | ||
1491 | zd_usb_disable_int(usb); | ||
1492 | |||
1493 | usb->initialized = 0; | ||
1494 | } | ||
1495 | |||
1496 | static int pre_reset(struct usb_interface *intf) | ||
1497 | { | ||
1498 | struct ieee80211_hw *hw = usb_get_intfdata(intf); | ||
1499 | struct zd_mac *mac; | ||
1500 | struct zd_usb *usb; | ||
1501 | |||
1502 | if (!hw || intf->condition != USB_INTERFACE_BOUND) | ||
1503 | return 0; | ||
1504 | |||
1505 | mac = zd_hw_mac(hw); | ||
1506 | usb = &mac->chip.usb; | ||
1507 | |||
1508 | usb->was_running = test_bit(ZD_DEVICE_RUNNING, &mac->flags); | ||
1509 | |||
1510 | zd_usb_stop(usb); | ||
1511 | |||
1512 | mutex_lock(&mac->chip.mutex); | ||
1513 | return 0; | ||
1514 | } | ||
1515 | |||
1516 | static int post_reset(struct usb_interface *intf) | ||
1517 | { | ||
1518 | struct ieee80211_hw *hw = usb_get_intfdata(intf); | ||
1519 | struct zd_mac *mac; | ||
1520 | struct zd_usb *usb; | ||
1521 | |||
1522 | if (!hw || intf->condition != USB_INTERFACE_BOUND) | ||
1523 | return 0; | ||
1524 | |||
1525 | mac = zd_hw_mac(hw); | ||
1526 | usb = &mac->chip.usb; | ||
1527 | |||
1528 | mutex_unlock(&mac->chip.mutex); | ||
1529 | |||
1530 | if (usb->was_running) | ||
1531 | zd_usb_resume(usb); | ||
1532 | return 0; | ||
1533 | } | ||
1534 | |||
1535 | static struct usb_driver driver = { | ||
1536 | .name = KBUILD_MODNAME, | ||
1537 | .id_table = usb_ids, | ||
1538 | .probe = probe, | ||
1539 | .disconnect = disconnect, | ||
1540 | .pre_reset = pre_reset, | ||
1541 | .post_reset = post_reset, | ||
1542 | .disable_hub_initiated_lpm = 1, | ||
1543 | }; | ||
1544 | |||
1545 | struct workqueue_struct *zd_workqueue; | ||
1546 | |||
1547 | static int __init usb_init(void) | ||
1548 | { | ||
1549 | int r; | ||
1550 | |||
1551 | pr_debug("%s usb_init()\n", driver.name); | ||
1552 | |||
1553 | zd_workqueue = create_singlethread_workqueue(driver.name); | ||
1554 | if (zd_workqueue == NULL) { | ||
1555 | printk(KERN_ERR "%s couldn't create workqueue\n", driver.name); | ||
1556 | return -ENOMEM; | ||
1557 | } | ||
1558 | |||
1559 | r = usb_register(&driver); | ||
1560 | if (r) { | ||
1561 | destroy_workqueue(zd_workqueue); | ||
1562 | printk(KERN_ERR "%s usb_register() failed. Error number %d\n", | ||
1563 | driver.name, r); | ||
1564 | return r; | ||
1565 | } | ||
1566 | |||
1567 | pr_debug("%s initialized\n", driver.name); | ||
1568 | return 0; | ||
1569 | } | ||
1570 | |||
1571 | static void __exit usb_exit(void) | ||
1572 | { | ||
1573 | pr_debug("%s usb_exit()\n", driver.name); | ||
1574 | usb_deregister(&driver); | ||
1575 | destroy_workqueue(zd_workqueue); | ||
1576 | } | ||
1577 | |||
1578 | module_init(usb_init); | ||
1579 | module_exit(usb_exit); | ||
1580 | |||
1581 | static int zd_ep_regs_out_msg(struct usb_device *udev, void *data, int len, | ||
1582 | int *actual_length, int timeout) | ||
1583 | { | ||
1584 | /* In USB 2.0 mode EP_REGS_OUT endpoint is interrupt type. However in | ||
1585 | * USB 1.1 mode endpoint is bulk. Select correct type URB by endpoint | ||
1586 | * descriptor. | ||
1587 | */ | ||
1588 | struct usb_host_endpoint *ep; | ||
1589 | unsigned int pipe; | ||
1590 | |||
1591 | pipe = usb_sndintpipe(udev, EP_REGS_OUT); | ||
1592 | ep = usb_pipe_endpoint(udev, pipe); | ||
1593 | if (!ep) | ||
1594 | return -EINVAL; | ||
1595 | |||
1596 | if (usb_endpoint_xfer_int(&ep->desc)) { | ||
1597 | return usb_interrupt_msg(udev, pipe, data, len, | ||
1598 | actual_length, timeout); | ||
1599 | } else { | ||
1600 | pipe = usb_sndbulkpipe(udev, EP_REGS_OUT); | ||
1601 | return usb_bulk_msg(udev, pipe, data, len, actual_length, | ||
1602 | timeout); | ||
1603 | } | ||
1604 | } | ||
1605 | |||
1606 | static int usb_int_regs_length(unsigned int count) | ||
1607 | { | ||
1608 | return sizeof(struct usb_int_regs) + count * sizeof(struct reg_data); | ||
1609 | } | ||
1610 | |||
1611 | static void prepare_read_regs_int(struct zd_usb *usb, | ||
1612 | struct usb_req_read_regs *req, | ||
1613 | unsigned int count) | ||
1614 | { | ||
1615 | struct zd_usb_interrupt *intr = &usb->intr; | ||
1616 | |||
1617 | spin_lock_irq(&intr->lock); | ||
1618 | atomic_set(&intr->read_regs_enabled, 1); | ||
1619 | intr->read_regs.req = req; | ||
1620 | intr->read_regs.req_count = count; | ||
1621 | reinit_completion(&intr->read_regs.completion); | ||
1622 | spin_unlock_irq(&intr->lock); | ||
1623 | } | ||
1624 | |||
1625 | static void disable_read_regs_int(struct zd_usb *usb) | ||
1626 | { | ||
1627 | struct zd_usb_interrupt *intr = &usb->intr; | ||
1628 | |||
1629 | spin_lock_irq(&intr->lock); | ||
1630 | atomic_set(&intr->read_regs_enabled, 0); | ||
1631 | spin_unlock_irq(&intr->lock); | ||
1632 | } | ||
1633 | |||
1634 | static bool check_read_regs(struct zd_usb *usb, struct usb_req_read_regs *req, | ||
1635 | unsigned int count) | ||
1636 | { | ||
1637 | int i; | ||
1638 | struct zd_usb_interrupt *intr = &usb->intr; | ||
1639 | struct read_regs_int *rr = &intr->read_regs; | ||
1640 | struct usb_int_regs *regs = (struct usb_int_regs *)rr->buffer; | ||
1641 | |||
1642 | /* The created block size seems to be larger than expected. | ||
1643 | * However results appear to be correct. | ||
1644 | */ | ||
1645 | if (rr->length < usb_int_regs_length(count)) { | ||
1646 | dev_dbg_f(zd_usb_dev(usb), | ||
1647 | "error: actual length %d less than expected %d\n", | ||
1648 | rr->length, usb_int_regs_length(count)); | ||
1649 | return false; | ||
1650 | } | ||
1651 | |||
1652 | if (rr->length > sizeof(rr->buffer)) { | ||
1653 | dev_dbg_f(zd_usb_dev(usb), | ||
1654 | "error: actual length %d exceeds buffer size %zu\n", | ||
1655 | rr->length, sizeof(rr->buffer)); | ||
1656 | return false; | ||
1657 | } | ||
1658 | |||
1659 | for (i = 0; i < count; i++) { | ||
1660 | struct reg_data *rd = ®s->regs[i]; | ||
1661 | if (rd->addr != req->addr[i]) { | ||
1662 | dev_dbg_f(zd_usb_dev(usb), | ||
1663 | "rd[%d] addr %#06hx expected %#06hx\n", i, | ||
1664 | le16_to_cpu(rd->addr), | ||
1665 | le16_to_cpu(req->addr[i])); | ||
1666 | return false; | ||
1667 | } | ||
1668 | } | ||
1669 | |||
1670 | return true; | ||
1671 | } | ||
1672 | |||
1673 | static int get_results(struct zd_usb *usb, u16 *values, | ||
1674 | struct usb_req_read_regs *req, unsigned int count, | ||
1675 | bool *retry) | ||
1676 | { | ||
1677 | int r; | ||
1678 | int i; | ||
1679 | struct zd_usb_interrupt *intr = &usb->intr; | ||
1680 | struct read_regs_int *rr = &intr->read_regs; | ||
1681 | struct usb_int_regs *regs = (struct usb_int_regs *)rr->buffer; | ||
1682 | |||
1683 | spin_lock_irq(&intr->lock); | ||
1684 | |||
1685 | r = -EIO; | ||
1686 | |||
1687 | /* Read failed because firmware bug? */ | ||
1688 | *retry = !!intr->read_regs_int_overridden; | ||
1689 | if (*retry) | ||
1690 | goto error_unlock; | ||
1691 | |||
1692 | if (!check_read_regs(usb, req, count)) { | ||
1693 | dev_dbg_f(zd_usb_dev(usb), "error: invalid read regs\n"); | ||
1694 | goto error_unlock; | ||
1695 | } | ||
1696 | |||
1697 | for (i = 0; i < count; i++) { | ||
1698 | struct reg_data *rd = ®s->regs[i]; | ||
1699 | values[i] = le16_to_cpu(rd->value); | ||
1700 | } | ||
1701 | |||
1702 | r = 0; | ||
1703 | error_unlock: | ||
1704 | spin_unlock_irq(&intr->lock); | ||
1705 | return r; | ||
1706 | } | ||
1707 | |||
1708 | int zd_usb_ioread16v(struct zd_usb *usb, u16 *values, | ||
1709 | const zd_addr_t *addresses, unsigned int count) | ||
1710 | { | ||
1711 | int r, i, req_len, actual_req_len, try_count = 0; | ||
1712 | struct usb_device *udev; | ||
1713 | struct usb_req_read_regs *req = NULL; | ||
1714 | unsigned long timeout; | ||
1715 | bool retry = false; | ||
1716 | |||
1717 | if (count < 1) { | ||
1718 | dev_dbg_f(zd_usb_dev(usb), "error: count is zero\n"); | ||
1719 | return -EINVAL; | ||
1720 | } | ||
1721 | if (count > USB_MAX_IOREAD16_COUNT) { | ||
1722 | dev_dbg_f(zd_usb_dev(usb), | ||
1723 | "error: count %u exceeds possible max %u\n", | ||
1724 | count, USB_MAX_IOREAD16_COUNT); | ||
1725 | return -EINVAL; | ||
1726 | } | ||
1727 | if (in_atomic()) { | ||
1728 | dev_dbg_f(zd_usb_dev(usb), | ||
1729 | "error: io in atomic context not supported\n"); | ||
1730 | return -EWOULDBLOCK; | ||
1731 | } | ||
1732 | if (!usb_int_enabled(usb)) { | ||
1733 | dev_dbg_f(zd_usb_dev(usb), | ||
1734 | "error: usb interrupt not enabled\n"); | ||
1735 | return -EWOULDBLOCK; | ||
1736 | } | ||
1737 | |||
1738 | ZD_ASSERT(mutex_is_locked(&zd_usb_to_chip(usb)->mutex)); | ||
1739 | BUILD_BUG_ON(sizeof(struct usb_req_read_regs) + USB_MAX_IOREAD16_COUNT * | ||
1740 | sizeof(__le16) > sizeof(usb->req_buf)); | ||
1741 | BUG_ON(sizeof(struct usb_req_read_regs) + count * sizeof(__le16) > | ||
1742 | sizeof(usb->req_buf)); | ||
1743 | |||
1744 | req_len = sizeof(struct usb_req_read_regs) + count * sizeof(__le16); | ||
1745 | req = (void *)usb->req_buf; | ||
1746 | |||
1747 | req->id = cpu_to_le16(USB_REQ_READ_REGS); | ||
1748 | for (i = 0; i < count; i++) | ||
1749 | req->addr[i] = cpu_to_le16((u16)addresses[i]); | ||
1750 | |||
1751 | retry_read: | ||
1752 | try_count++; | ||
1753 | udev = zd_usb_to_usbdev(usb); | ||
1754 | prepare_read_regs_int(usb, req, count); | ||
1755 | r = zd_ep_regs_out_msg(udev, req, req_len, &actual_req_len, 50 /*ms*/); | ||
1756 | if (r) { | ||
1757 | dev_dbg_f(zd_usb_dev(usb), | ||
1758 | "error in zd_ep_regs_out_msg(). Error number %d\n", r); | ||
1759 | goto error; | ||
1760 | } | ||
1761 | if (req_len != actual_req_len) { | ||
1762 | dev_dbg_f(zd_usb_dev(usb), "error in zd_ep_regs_out_msg()\n" | ||
1763 | " req_len %d != actual_req_len %d\n", | ||
1764 | req_len, actual_req_len); | ||
1765 | r = -EIO; | ||
1766 | goto error; | ||
1767 | } | ||
1768 | |||
1769 | timeout = wait_for_completion_timeout(&usb->intr.read_regs.completion, | ||
1770 | msecs_to_jiffies(50)); | ||
1771 | if (!timeout) { | ||
1772 | disable_read_regs_int(usb); | ||
1773 | dev_dbg_f(zd_usb_dev(usb), "read timed out\n"); | ||
1774 | r = -ETIMEDOUT; | ||
1775 | goto error; | ||
1776 | } | ||
1777 | |||
1778 | r = get_results(usb, values, req, count, &retry); | ||
1779 | if (retry && try_count < 20) { | ||
1780 | dev_dbg_f(zd_usb_dev(usb), "read retry, tries so far: %d\n", | ||
1781 | try_count); | ||
1782 | goto retry_read; | ||
1783 | } | ||
1784 | error: | ||
1785 | return r; | ||
1786 | } | ||
1787 | |||
1788 | static void iowrite16v_urb_complete(struct urb *urb) | ||
1789 | { | ||
1790 | struct zd_usb *usb = urb->context; | ||
1791 | |||
1792 | if (urb->status && !usb->cmd_error) | ||
1793 | usb->cmd_error = urb->status; | ||
1794 | |||
1795 | if (!usb->cmd_error && | ||
1796 | urb->actual_length != urb->transfer_buffer_length) | ||
1797 | usb->cmd_error = -EIO; | ||
1798 | } | ||
1799 | |||
1800 | static int zd_submit_waiting_urb(struct zd_usb *usb, bool last) | ||
1801 | { | ||
1802 | int r = 0; | ||
1803 | struct urb *urb = usb->urb_async_waiting; | ||
1804 | |||
1805 | if (!urb) | ||
1806 | return 0; | ||
1807 | |||
1808 | usb->urb_async_waiting = NULL; | ||
1809 | |||
1810 | if (!last) | ||
1811 | urb->transfer_flags |= URB_NO_INTERRUPT; | ||
1812 | |||
1813 | usb_anchor_urb(urb, &usb->submitted_cmds); | ||
1814 | r = usb_submit_urb(urb, GFP_KERNEL); | ||
1815 | if (r) { | ||
1816 | usb_unanchor_urb(urb); | ||
1817 | dev_dbg_f(zd_usb_dev(usb), | ||
1818 | "error in usb_submit_urb(). Error number %d\n", r); | ||
1819 | goto error; | ||
1820 | } | ||
1821 | |||
1822 | /* fall-through with r == 0 */ | ||
1823 | error: | ||
1824 | usb_free_urb(urb); | ||
1825 | return r; | ||
1826 | } | ||
1827 | |||
1828 | void zd_usb_iowrite16v_async_start(struct zd_usb *usb) | ||
1829 | { | ||
1830 | ZD_ASSERT(usb_anchor_empty(&usb->submitted_cmds)); | ||
1831 | ZD_ASSERT(usb->urb_async_waiting == NULL); | ||
1832 | ZD_ASSERT(!usb->in_async); | ||
1833 | |||
1834 | ZD_ASSERT(mutex_is_locked(&zd_usb_to_chip(usb)->mutex)); | ||
1835 | |||
1836 | usb->in_async = 1; | ||
1837 | usb->cmd_error = 0; | ||
1838 | usb->urb_async_waiting = NULL; | ||
1839 | } | ||
1840 | |||
1841 | int zd_usb_iowrite16v_async_end(struct zd_usb *usb, unsigned int timeout) | ||
1842 | { | ||
1843 | int r; | ||
1844 | |||
1845 | ZD_ASSERT(mutex_is_locked(&zd_usb_to_chip(usb)->mutex)); | ||
1846 | ZD_ASSERT(usb->in_async); | ||
1847 | |||
1848 | /* Submit last iowrite16v URB */ | ||
1849 | r = zd_submit_waiting_urb(usb, true); | ||
1850 | if (r) { | ||
1851 | dev_dbg_f(zd_usb_dev(usb), | ||
1852 | "error in zd_submit_waiting_usb(). " | ||
1853 | "Error number %d\n", r); | ||
1854 | |||
1855 | usb_kill_anchored_urbs(&usb->submitted_cmds); | ||
1856 | goto error; | ||
1857 | } | ||
1858 | |||
1859 | if (timeout) | ||
1860 | timeout = usb_wait_anchor_empty_timeout(&usb->submitted_cmds, | ||
1861 | timeout); | ||
1862 | if (!timeout) { | ||
1863 | usb_kill_anchored_urbs(&usb->submitted_cmds); | ||
1864 | if (usb->cmd_error == -ENOENT) { | ||
1865 | dev_dbg_f(zd_usb_dev(usb), "timed out"); | ||
1866 | r = -ETIMEDOUT; | ||
1867 | goto error; | ||
1868 | } | ||
1869 | } | ||
1870 | |||
1871 | r = usb->cmd_error; | ||
1872 | error: | ||
1873 | usb->in_async = 0; | ||
1874 | return r; | ||
1875 | } | ||
1876 | |||
1877 | int zd_usb_iowrite16v_async(struct zd_usb *usb, const struct zd_ioreq16 *ioreqs, | ||
1878 | unsigned int count) | ||
1879 | { | ||
1880 | int r; | ||
1881 | struct usb_device *udev; | ||
1882 | struct usb_req_write_regs *req = NULL; | ||
1883 | int i, req_len; | ||
1884 | struct urb *urb; | ||
1885 | struct usb_host_endpoint *ep; | ||
1886 | |||
1887 | ZD_ASSERT(mutex_is_locked(&zd_usb_to_chip(usb)->mutex)); | ||
1888 | ZD_ASSERT(usb->in_async); | ||
1889 | |||
1890 | if (count == 0) | ||
1891 | return 0; | ||
1892 | if (count > USB_MAX_IOWRITE16_COUNT) { | ||
1893 | dev_dbg_f(zd_usb_dev(usb), | ||
1894 | "error: count %u exceeds possible max %u\n", | ||
1895 | count, USB_MAX_IOWRITE16_COUNT); | ||
1896 | return -EINVAL; | ||
1897 | } | ||
1898 | if (in_atomic()) { | ||
1899 | dev_dbg_f(zd_usb_dev(usb), | ||
1900 | "error: io in atomic context not supported\n"); | ||
1901 | return -EWOULDBLOCK; | ||
1902 | } | ||
1903 | |||
1904 | udev = zd_usb_to_usbdev(usb); | ||
1905 | |||
1906 | ep = usb_pipe_endpoint(udev, usb_sndintpipe(udev, EP_REGS_OUT)); | ||
1907 | if (!ep) | ||
1908 | return -ENOENT; | ||
1909 | |||
1910 | urb = usb_alloc_urb(0, GFP_KERNEL); | ||
1911 | if (!urb) | ||
1912 | return -ENOMEM; | ||
1913 | |||
1914 | req_len = sizeof(struct usb_req_write_regs) + | ||
1915 | count * sizeof(struct reg_data); | ||
1916 | req = kmalloc(req_len, GFP_KERNEL); | ||
1917 | if (!req) { | ||
1918 | r = -ENOMEM; | ||
1919 | goto error; | ||
1920 | } | ||
1921 | |||
1922 | req->id = cpu_to_le16(USB_REQ_WRITE_REGS); | ||
1923 | for (i = 0; i < count; i++) { | ||
1924 | struct reg_data *rw = &req->reg_writes[i]; | ||
1925 | rw->addr = cpu_to_le16((u16)ioreqs[i].addr); | ||
1926 | rw->value = cpu_to_le16(ioreqs[i].value); | ||
1927 | } | ||
1928 | |||
1929 | /* In USB 2.0 mode endpoint is interrupt type. However in USB 1.1 mode | ||
1930 | * endpoint is bulk. Select correct type URB by endpoint descriptor. | ||
1931 | */ | ||
1932 | if (usb_endpoint_xfer_int(&ep->desc)) | ||
1933 | usb_fill_int_urb(urb, udev, usb_sndintpipe(udev, EP_REGS_OUT), | ||
1934 | req, req_len, iowrite16v_urb_complete, usb, | ||
1935 | ep->desc.bInterval); | ||
1936 | else | ||
1937 | usb_fill_bulk_urb(urb, udev, usb_sndbulkpipe(udev, EP_REGS_OUT), | ||
1938 | req, req_len, iowrite16v_urb_complete, usb); | ||
1939 | |||
1940 | urb->transfer_flags |= URB_FREE_BUFFER; | ||
1941 | |||
1942 | /* Submit previous URB */ | ||
1943 | r = zd_submit_waiting_urb(usb, false); | ||
1944 | if (r) { | ||
1945 | dev_dbg_f(zd_usb_dev(usb), | ||
1946 | "error in zd_submit_waiting_usb(). " | ||
1947 | "Error number %d\n", r); | ||
1948 | goto error; | ||
1949 | } | ||
1950 | |||
1951 | /* Delay submit so that URB_NO_INTERRUPT flag can be set for all URBs | ||
1952 | * of currect batch except for very last. | ||
1953 | */ | ||
1954 | usb->urb_async_waiting = urb; | ||
1955 | return 0; | ||
1956 | error: | ||
1957 | usb_free_urb(urb); | ||
1958 | return r; | ||
1959 | } | ||
1960 | |||
1961 | int zd_usb_iowrite16v(struct zd_usb *usb, const struct zd_ioreq16 *ioreqs, | ||
1962 | unsigned int count) | ||
1963 | { | ||
1964 | int r; | ||
1965 | |||
1966 | zd_usb_iowrite16v_async_start(usb); | ||
1967 | r = zd_usb_iowrite16v_async(usb, ioreqs, count); | ||
1968 | if (r) { | ||
1969 | zd_usb_iowrite16v_async_end(usb, 0); | ||
1970 | return r; | ||
1971 | } | ||
1972 | return zd_usb_iowrite16v_async_end(usb, 50 /* ms */); | ||
1973 | } | ||
1974 | |||
1975 | int zd_usb_rfwrite(struct zd_usb *usb, u32 value, u8 bits) | ||
1976 | { | ||
1977 | int r; | ||
1978 | struct usb_device *udev; | ||
1979 | struct usb_req_rfwrite *req = NULL; | ||
1980 | int i, req_len, actual_req_len; | ||
1981 | u16 bit_value_template; | ||
1982 | |||
1983 | if (in_atomic()) { | ||
1984 | dev_dbg_f(zd_usb_dev(usb), | ||
1985 | "error: io in atomic context not supported\n"); | ||
1986 | return -EWOULDBLOCK; | ||
1987 | } | ||
1988 | if (bits < USB_MIN_RFWRITE_BIT_COUNT) { | ||
1989 | dev_dbg_f(zd_usb_dev(usb), | ||
1990 | "error: bits %d are smaller than" | ||
1991 | " USB_MIN_RFWRITE_BIT_COUNT %d\n", | ||
1992 | bits, USB_MIN_RFWRITE_BIT_COUNT); | ||
1993 | return -EINVAL; | ||
1994 | } | ||
1995 | if (bits > USB_MAX_RFWRITE_BIT_COUNT) { | ||
1996 | dev_dbg_f(zd_usb_dev(usb), | ||
1997 | "error: bits %d exceed USB_MAX_RFWRITE_BIT_COUNT %d\n", | ||
1998 | bits, USB_MAX_RFWRITE_BIT_COUNT); | ||
1999 | return -EINVAL; | ||
2000 | } | ||
2001 | #ifdef DEBUG | ||
2002 | if (value & (~0UL << bits)) { | ||
2003 | dev_dbg_f(zd_usb_dev(usb), | ||
2004 | "error: value %#09x has bits >= %d set\n", | ||
2005 | value, bits); | ||
2006 | return -EINVAL; | ||
2007 | } | ||
2008 | #endif /* DEBUG */ | ||
2009 | |||
2010 | dev_dbg_f(zd_usb_dev(usb), "value %#09x bits %d\n", value, bits); | ||
2011 | |||
2012 | r = zd_usb_ioread16(usb, &bit_value_template, ZD_CR203); | ||
2013 | if (r) { | ||
2014 | dev_dbg_f(zd_usb_dev(usb), | ||
2015 | "error %d: Couldn't read ZD_CR203\n", r); | ||
2016 | return r; | ||
2017 | } | ||
2018 | bit_value_template &= ~(RF_IF_LE|RF_CLK|RF_DATA); | ||
2019 | |||
2020 | ZD_ASSERT(mutex_is_locked(&zd_usb_to_chip(usb)->mutex)); | ||
2021 | BUILD_BUG_ON(sizeof(struct usb_req_rfwrite) + | ||
2022 | USB_MAX_RFWRITE_BIT_COUNT * sizeof(__le16) > | ||
2023 | sizeof(usb->req_buf)); | ||
2024 | BUG_ON(sizeof(struct usb_req_rfwrite) + bits * sizeof(__le16) > | ||
2025 | sizeof(usb->req_buf)); | ||
2026 | |||
2027 | req_len = sizeof(struct usb_req_rfwrite) + bits * sizeof(__le16); | ||
2028 | req = (void *)usb->req_buf; | ||
2029 | |||
2030 | req->id = cpu_to_le16(USB_REQ_WRITE_RF); | ||
2031 | /* 1: 3683a, but not used in ZYDAS driver */ | ||
2032 | req->value = cpu_to_le16(2); | ||
2033 | req->bits = cpu_to_le16(bits); | ||
2034 | |||
2035 | for (i = 0; i < bits; i++) { | ||
2036 | u16 bv = bit_value_template; | ||
2037 | if (value & (1 << (bits-1-i))) | ||
2038 | bv |= RF_DATA; | ||
2039 | req->bit_values[i] = cpu_to_le16(bv); | ||
2040 | } | ||
2041 | |||
2042 | udev = zd_usb_to_usbdev(usb); | ||
2043 | r = zd_ep_regs_out_msg(udev, req, req_len, &actual_req_len, 50 /*ms*/); | ||
2044 | if (r) { | ||
2045 | dev_dbg_f(zd_usb_dev(usb), | ||
2046 | "error in zd_ep_regs_out_msg(). Error number %d\n", r); | ||
2047 | goto out; | ||
2048 | } | ||
2049 | if (req_len != actual_req_len) { | ||
2050 | dev_dbg_f(zd_usb_dev(usb), "error in zd_ep_regs_out_msg()" | ||
2051 | " req_len %d != actual_req_len %d\n", | ||
2052 | req_len, actual_req_len); | ||
2053 | r = -EIO; | ||
2054 | goto out; | ||
2055 | } | ||
2056 | |||
2057 | /* FALL-THROUGH with r == 0 */ | ||
2058 | out: | ||
2059 | return r; | ||
2060 | } | ||
diff --git a/drivers/net/wireless/zydas/zd1211rw/zd_usb.h b/drivers/net/wireless/zydas/zd1211rw/zd_usb.h new file mode 100644 index 000000000000..a9075f225178 --- /dev/null +++ b/drivers/net/wireless/zydas/zd1211rw/zd_usb.h | |||
@@ -0,0 +1,292 @@ | |||
1 | /* ZD1211 USB-WLAN driver for Linux | ||
2 | * | ||
3 | * Copyright (C) 2005-2007 Ulrich Kunitz <kune@deine-taler.de> | ||
4 | * Copyright (C) 2006-2007 Daniel Drake <dsd@gentoo.org> | ||
5 | * | ||
6 | * This program is free software; you can redistribute it and/or modify | ||
7 | * it under the terms of the GNU General Public License as published by | ||
8 | * the Free Software Foundation; either version 2 of the License, or | ||
9 | * (at your option) any later version. | ||
10 | * | ||
11 | * This program is distributed in the hope that it will be useful, | ||
12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
14 | * GNU General Public License for more details. | ||
15 | * | ||
16 | * You should have received a copy of the GNU General Public License | ||
17 | * along with this program; if not, see <http://www.gnu.org/licenses/>. | ||
18 | */ | ||
19 | |||
20 | #ifndef _ZD_USB_H | ||
21 | #define _ZD_USB_H | ||
22 | |||
23 | #include <linux/completion.h> | ||
24 | #include <linux/netdevice.h> | ||
25 | #include <linux/spinlock.h> | ||
26 | #include <linux/skbuff.h> | ||
27 | #include <linux/usb.h> | ||
28 | |||
29 | #include "zd_def.h" | ||
30 | |||
31 | #define ZD_USB_TX_HIGH 5 | ||
32 | #define ZD_USB_TX_LOW 2 | ||
33 | |||
34 | #define ZD_TX_TIMEOUT (HZ * 5) | ||
35 | #define ZD_TX_WATCHDOG_INTERVAL round_jiffies_relative(HZ) | ||
36 | #define ZD_RX_IDLE_INTERVAL round_jiffies_relative(30 * HZ) | ||
37 | |||
38 | enum devicetype { | ||
39 | DEVICE_ZD1211 = 0, | ||
40 | DEVICE_ZD1211B = 1, | ||
41 | DEVICE_INSTALLER = 2, | ||
42 | }; | ||
43 | |||
44 | enum endpoints { | ||
45 | EP_CTRL = 0, | ||
46 | EP_DATA_OUT = 1, | ||
47 | EP_DATA_IN = 2, | ||
48 | EP_INT_IN = 3, | ||
49 | EP_REGS_OUT = 4, | ||
50 | }; | ||
51 | |||
52 | enum { | ||
53 | USB_MAX_TRANSFER_SIZE = 4096, /* bytes */ | ||
54 | /* FIXME: The original driver uses this value. We have to check, | ||
55 | * whether the MAX_TRANSFER_SIZE is sufficient and this needs only be | ||
56 | * used if one combined frame is split over two USB transactions. | ||
57 | */ | ||
58 | USB_MAX_RX_SIZE = 4800, /* bytes */ | ||
59 | USB_MAX_IOWRITE16_COUNT = 15, | ||
60 | USB_MAX_IOWRITE32_COUNT = USB_MAX_IOWRITE16_COUNT/2, | ||
61 | USB_MAX_IOREAD16_COUNT = 15, | ||
62 | USB_MAX_IOREAD32_COUNT = USB_MAX_IOREAD16_COUNT/2, | ||
63 | USB_MIN_RFWRITE_BIT_COUNT = 16, | ||
64 | USB_MAX_RFWRITE_BIT_COUNT = 28, | ||
65 | USB_MAX_EP_INT_BUFFER = 64, | ||
66 | USB_ZD1211B_BCD_DEVICE = 0x4810, | ||
67 | }; | ||
68 | |||
69 | enum control_requests { | ||
70 | USB_REQ_WRITE_REGS = 0x21, | ||
71 | USB_REQ_READ_REGS = 0x22, | ||
72 | USB_REQ_WRITE_RF = 0x23, | ||
73 | USB_REQ_PROG_FLASH = 0x24, | ||
74 | USB_REQ_EEPROM_START = 0x0128, /* ? request is a byte */ | ||
75 | USB_REQ_EEPROM_MID = 0x28, | ||
76 | USB_REQ_EEPROM_END = 0x0228, /* ? request is a byte */ | ||
77 | USB_REQ_FIRMWARE_DOWNLOAD = 0x30, | ||
78 | USB_REQ_FIRMWARE_CONFIRM = 0x31, | ||
79 | USB_REQ_FIRMWARE_READ_DATA = 0x32, | ||
80 | }; | ||
81 | |||
82 | struct usb_req_read_regs { | ||
83 | __le16 id; | ||
84 | __le16 addr[0]; | ||
85 | } __packed; | ||
86 | |||
87 | struct reg_data { | ||
88 | __le16 addr; | ||
89 | __le16 value; | ||
90 | } __packed; | ||
91 | |||
92 | struct usb_req_write_regs { | ||
93 | __le16 id; | ||
94 | struct reg_data reg_writes[0]; | ||
95 | } __packed; | ||
96 | |||
97 | enum { | ||
98 | RF_IF_LE = 0x02, | ||
99 | RF_CLK = 0x04, | ||
100 | RF_DATA = 0x08, | ||
101 | }; | ||
102 | |||
103 | struct usb_req_rfwrite { | ||
104 | __le16 id; | ||
105 | __le16 value; | ||
106 | /* 1: 3683a */ | ||
107 | /* 2: other (default) */ | ||
108 | __le16 bits; | ||
109 | /* RF2595: 24 */ | ||
110 | __le16 bit_values[0]; | ||
111 | /* (ZD_CR203 & ~(RF_IF_LE | RF_CLK | RF_DATA)) | (bit ? RF_DATA : 0) */ | ||
112 | } __packed; | ||
113 | |||
114 | /* USB interrupt */ | ||
115 | |||
116 | enum usb_int_id { | ||
117 | USB_INT_TYPE = 0x01, | ||
118 | USB_INT_ID_REGS = 0x90, | ||
119 | USB_INT_ID_RETRY_FAILED = 0xa0, | ||
120 | }; | ||
121 | |||
122 | enum usb_int_flags { | ||
123 | USB_INT_READ_REGS_EN = 0x01, | ||
124 | }; | ||
125 | |||
126 | struct usb_int_header { | ||
127 | u8 type; /* must always be 1 */ | ||
128 | u8 id; | ||
129 | } __packed; | ||
130 | |||
131 | struct usb_int_regs { | ||
132 | struct usb_int_header hdr; | ||
133 | struct reg_data regs[0]; | ||
134 | } __packed; | ||
135 | |||
136 | struct usb_int_retry_fail { | ||
137 | struct usb_int_header hdr; | ||
138 | u8 new_rate; | ||
139 | u8 _dummy; | ||
140 | u8 addr[ETH_ALEN]; | ||
141 | u8 ibss_wakeup_dest; | ||
142 | } __packed; | ||
143 | |||
144 | struct read_regs_int { | ||
145 | struct completion completion; | ||
146 | struct usb_req_read_regs *req; | ||
147 | unsigned int req_count; | ||
148 | /* Stores the USB int structure and contains the USB address of the | ||
149 | * first requested register before request. | ||
150 | */ | ||
151 | u8 buffer[USB_MAX_EP_INT_BUFFER]; | ||
152 | int length; | ||
153 | __le16 cr_int_addr; | ||
154 | }; | ||
155 | |||
156 | struct zd_ioreq16 { | ||
157 | zd_addr_t addr; | ||
158 | u16 value; | ||
159 | }; | ||
160 | |||
161 | struct zd_ioreq32 { | ||
162 | zd_addr_t addr; | ||
163 | u32 value; | ||
164 | }; | ||
165 | |||
166 | struct zd_usb_interrupt { | ||
167 | struct read_regs_int read_regs; | ||
168 | spinlock_t lock; | ||
169 | struct urb *urb; | ||
170 | void *buffer; | ||
171 | dma_addr_t buffer_dma; | ||
172 | int interval; | ||
173 | atomic_t read_regs_enabled; | ||
174 | u8 read_regs_int_overridden:1; | ||
175 | }; | ||
176 | |||
177 | static inline struct usb_int_regs *get_read_regs(struct zd_usb_interrupt *intr) | ||
178 | { | ||
179 | return (struct usb_int_regs *)intr->read_regs.buffer; | ||
180 | } | ||
181 | |||
182 | #define RX_URBS_COUNT 5 | ||
183 | |||
184 | struct zd_usb_rx { | ||
185 | spinlock_t lock; | ||
186 | struct mutex setup_mutex; | ||
187 | struct delayed_work idle_work; | ||
188 | struct tasklet_struct reset_timer_tasklet; | ||
189 | u8 fragment[2 * USB_MAX_RX_SIZE]; | ||
190 | unsigned int fragment_length; | ||
191 | unsigned int usb_packet_size; | ||
192 | struct urb **urbs; | ||
193 | int urbs_count; | ||
194 | }; | ||
195 | |||
196 | /** | ||
197 | * struct zd_usb_tx - structure used for transmitting frames | ||
198 | * @enabled: atomic enabled flag, indicates whether tx is enabled | ||
199 | * @lock: lock for transmission | ||
200 | * @submitted: anchor for URBs sent to device | ||
201 | * @submitted_urbs: atomic integer that counts the URBs having sent to the | ||
202 | * device, which haven't been completed | ||
203 | * @stopped: indicates whether higher level tx queues are stopped | ||
204 | */ | ||
205 | struct zd_usb_tx { | ||
206 | atomic_t enabled; | ||
207 | spinlock_t lock; | ||
208 | struct delayed_work watchdog_work; | ||
209 | struct sk_buff_head submitted_skbs; | ||
210 | struct usb_anchor submitted; | ||
211 | int submitted_urbs; | ||
212 | u8 stopped:1, watchdog_enabled:1; | ||
213 | }; | ||
214 | |||
215 | /* Contains the usb parts. The structure doesn't require a lock because intf | ||
216 | * will not be changed after initialization. | ||
217 | */ | ||
218 | struct zd_usb { | ||
219 | struct zd_usb_interrupt intr; | ||
220 | struct zd_usb_rx rx; | ||
221 | struct zd_usb_tx tx; | ||
222 | struct usb_interface *intf; | ||
223 | struct usb_anchor submitted_cmds; | ||
224 | struct urb *urb_async_waiting; | ||
225 | int cmd_error; | ||
226 | u8 req_buf[64]; /* zd_usb_iowrite16v needs 62 bytes */ | ||
227 | u8 is_zd1211b:1, initialized:1, was_running:1, in_async:1; | ||
228 | }; | ||
229 | |||
230 | #define zd_usb_dev(usb) (&usb->intf->dev) | ||
231 | |||
232 | static inline struct usb_device *zd_usb_to_usbdev(struct zd_usb *usb) | ||
233 | { | ||
234 | return interface_to_usbdev(usb->intf); | ||
235 | } | ||
236 | |||
237 | static inline struct ieee80211_hw *zd_intf_to_hw(struct usb_interface *intf) | ||
238 | { | ||
239 | return usb_get_intfdata(intf); | ||
240 | } | ||
241 | |||
242 | static inline struct ieee80211_hw *zd_usb_to_hw(struct zd_usb *usb) | ||
243 | { | ||
244 | return zd_intf_to_hw(usb->intf); | ||
245 | } | ||
246 | |||
247 | void zd_usb_init(struct zd_usb *usb, struct ieee80211_hw *hw, | ||
248 | struct usb_interface *intf); | ||
249 | int zd_usb_init_hw(struct zd_usb *usb); | ||
250 | void zd_usb_clear(struct zd_usb *usb); | ||
251 | |||
252 | int zd_usb_scnprint_id(struct zd_usb *usb, char *buffer, size_t size); | ||
253 | |||
254 | void zd_tx_watchdog_enable(struct zd_usb *usb); | ||
255 | void zd_tx_watchdog_disable(struct zd_usb *usb); | ||
256 | |||
257 | int zd_usb_enable_int(struct zd_usb *usb); | ||
258 | void zd_usb_disable_int(struct zd_usb *usb); | ||
259 | |||
260 | int zd_usb_enable_rx(struct zd_usb *usb); | ||
261 | void zd_usb_disable_rx(struct zd_usb *usb); | ||
262 | |||
263 | void zd_usb_reset_rx_idle_timer(struct zd_usb *usb); | ||
264 | |||
265 | void zd_usb_enable_tx(struct zd_usb *usb); | ||
266 | void zd_usb_disable_tx(struct zd_usb *usb); | ||
267 | |||
268 | int zd_usb_tx(struct zd_usb *usb, struct sk_buff *skb); | ||
269 | |||
270 | int zd_usb_ioread16v(struct zd_usb *usb, u16 *values, | ||
271 | const zd_addr_t *addresses, unsigned int count); | ||
272 | |||
273 | static inline int zd_usb_ioread16(struct zd_usb *usb, u16 *value, | ||
274 | const zd_addr_t addr) | ||
275 | { | ||
276 | return zd_usb_ioread16v(usb, value, &addr, 1); | ||
277 | } | ||
278 | |||
279 | void zd_usb_iowrite16v_async_start(struct zd_usb *usb); | ||
280 | int zd_usb_iowrite16v_async_end(struct zd_usb *usb, unsigned int timeout); | ||
281 | int zd_usb_iowrite16v_async(struct zd_usb *usb, const struct zd_ioreq16 *ioreqs, | ||
282 | unsigned int count); | ||
283 | int zd_usb_iowrite16v(struct zd_usb *usb, const struct zd_ioreq16 *ioreqs, | ||
284 | unsigned int count); | ||
285 | |||
286 | int zd_usb_rfwrite(struct zd_usb *usb, u32 value, u8 bits); | ||
287 | |||
288 | int zd_usb_read_fw(struct zd_usb *usb, zd_addr_t addr, u8 *data, u16 len); | ||
289 | |||
290 | extern struct workqueue_struct *zd_workqueue; | ||
291 | |||
292 | #endif /* _ZD_USB_H */ | ||