Deleted Added
sdiff udiff text old ( 203087 ) new ( 206358 )
full compact
1/*-
2 * Copyright (c) 2008 Weongyo Jeong <weongyo@FreeBSD.org>
3 *
4 * Permission to use, copy, modify, and distribute this software for any
5 * purpose with or without fee is hereby granted, provided that the above
6 * copyright notice and this permission notice appear in all copies.
7 *
8 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
9 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
10 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
11 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
12 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
13 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
14 * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
15 */
16
17#include <sys/cdefs.h>
18__FBSDID("$FreeBSD: head/sys/dev/usb/wlan/if_urtw.c 203087 2010-01-27 19:43:14Z weongyo $");
19#include <sys/param.h>
20#include <sys/sockio.h>
21#include <sys/sysctl.h>
22#include <sys/lock.h>
23#include <sys/mutex.h>
24#include <sys/mbuf.h>
25#include <sys/kernel.h>
26#include <sys/socket.h>
27#include <sys/systm.h>
28#include <sys/malloc.h>
29#include <sys/module.h>
30#include <sys/bus.h>
31#include <sys/endian.h>
32#include <sys/kdb.h>
33
34#include <machine/bus.h>
35#include <machine/resource.h>
36#include <sys/rman.h>
37
38#include <net/if.h>
39#include <net/if_arp.h>
40#include <net/ethernet.h>
41#include <net/if_dl.h>
42#include <net/if_media.h>
43#include <net/if_types.h>
44
45#ifdef INET
46#include <netinet/in.h>
47#include <netinet/in_systm.h>
48#include <netinet/in_var.h>
49#include <netinet/if_ether.h>
50#include <netinet/ip.h>
51#endif
52
53#include <net80211/ieee80211_var.h>
54#include <net80211/ieee80211_regdomain.h>
55#include <net80211/ieee80211_radiotap.h>
56
57#include <dev/usb/usb.h>
58#include <dev/usb/usbdi.h>
59#include "usbdevs.h"
60
61#include <dev/usb/wlan/if_urtwreg.h>
62#include <dev/usb/wlan/if_urtwvar.h>
63
64SYSCTL_NODE(_hw_usb, OID_AUTO, urtw, CTLFLAG_RW, 0, "USB Realtek 8187L");
65#ifdef URTW_DEBUG
66int urtw_debug = 0;
67SYSCTL_INT(_hw_usb_urtw, OID_AUTO, debug, CTLFLAG_RW, &urtw_debug, 0,
68 "control debugging printfs");
69TUNABLE_INT("hw.usb.urtw.debug", &urtw_debug);
70enum {
71 URTW_DEBUG_XMIT = 0x00000001, /* basic xmit operation */
72 URTW_DEBUG_RECV = 0x00000002, /* basic recv operation */
73 URTW_DEBUG_RESET = 0x00000004, /* reset processing */
74 URTW_DEBUG_TX_PROC = 0x00000008, /* tx ISR proc */
75 URTW_DEBUG_RX_PROC = 0x00000010, /* rx ISR proc */
76 URTW_DEBUG_STATE = 0x00000020, /* 802.11 state transitions */
77 URTW_DEBUG_STAT = 0x00000040, /* statistic */
78 URTW_DEBUG_INIT = 0x00000080, /* initialization of dev */
79 URTW_DEBUG_TXSTATUS = 0x00000100, /* tx status */
80 URTW_DEBUG_ANY = 0xffffffff
81};
82#define DPRINTF(sc, m, fmt, ...) do { \
83 if (sc->sc_debug & (m)) \
84 printf(fmt, __VA_ARGS__); \
85} while (0)
86#else
87#define DPRINTF(sc, m, fmt, ...) do { \
88 (void) sc; \
89} while (0)
90#endif
91static int urtw_preamble_mode = URTW_PREAMBLE_MODE_LONG;
92SYSCTL_INT(_hw_usb_urtw, OID_AUTO, preamble_mode, CTLFLAG_RW,
93 &urtw_preamble_mode, 0, "set the preable mode (long or short)");
94TUNABLE_INT("hw.usb.urtw.preamble_mode", &urtw_preamble_mode);
95
96/* recognized device vendors/products */
97#define urtw_lookup(v, p) \
98 ((const struct urtw_type *)usb_lookup(urtw_devs, v, p))
99#define URTW_DEV_B(v,p) \
100 { USB_VPI(USB_VENDOR_##v, USB_PRODUCT_##v##_##p, URTW_REV_RTL8187B) }
101#define URTW_DEV_L(v,p) \
102 { USB_VPI(USB_VENDOR_##v, USB_PRODUCT_##v##_##p, URTW_REV_RTL8187L) }
103#define URTW_REV_RTL8187B 0
104#define URTW_REV_RTL8187L 1
105static const struct usb_device_id urtw_devs[] = {
106 URTW_DEV_B(NETGEAR, WG111V3),
107 URTW_DEV_B(REALTEK, RTL8187B_0),
108 URTW_DEV_B(REALTEK, RTL8187B_1),
109 URTW_DEV_B(REALTEK, RTL8187B_2),
110 URTW_DEV_B(SITECOMEU, WL168V4),
111 URTW_DEV_L(ASUS, P5B_WIFI),
112 URTW_DEV_L(BELKIN, F5D7050E),
113 URTW_DEV_L(LINKSYS4, WUSB54GCV2),
114 URTW_DEV_L(NETGEAR, WG111V2),
115 URTW_DEV_L(REALTEK, RTL8187),
116 URTW_DEV_L(SITECOMEU, WL168V1),
117 URTW_DEV_L(SURECOM, EP9001G2A),
118 { USB_VPI(0x1b75, 0x8187, URTW_REV_RTL8187L) },
119 { USB_VPI(USB_VENDOR_DICKSMITH, 0x9401, URTW_REV_RTL8187L) },
120 { USB_VPI(USB_VENDOR_HP, 0xca02, URTW_REV_RTL8187L) },
121 { USB_VPI(USB_VENDOR_LOGITEC, 0x010c, URTW_REV_RTL8187L) },
122 { USB_VPI(USB_VENDOR_NETGEAR, 0x6100, URTW_REV_RTL8187L) },
123 { USB_VPI(USB_VENDOR_SPHAIRON, 0x0150, URTW_REV_RTL8187L) },
124 { USB_VPI(USB_VENDOR_QCOM, 0x6232, URTW_REV_RTL8187L) },
125#undef URTW_DEV_L
126#undef URTW_DEV_B
127};
128
129#define urtw_read8_m(sc, val, data) do { \
130 error = urtw_read8_c(sc, val, data); \
131 if (error != 0) \
132 goto fail; \
133} while (0)
134#define urtw_write8_m(sc, val, data) do { \
135 error = urtw_write8_c(sc, val, data); \
136 if (error != 0) \
137 goto fail; \
138} while (0)
139#define urtw_read16_m(sc, val, data) do { \
140 error = urtw_read16_c(sc, val, data); \
141 if (error != 0) \
142 goto fail; \
143} while (0)
144#define urtw_write16_m(sc, val, data) do { \
145 error = urtw_write16_c(sc, val, data); \
146 if (error != 0) \
147 goto fail; \
148} while (0)
149#define urtw_read32_m(sc, val, data) do { \
150 error = urtw_read32_c(sc, val, data); \
151 if (error != 0) \
152 goto fail; \
153} while (0)
154#define urtw_write32_m(sc, val, data) do { \
155 error = urtw_write32_c(sc, val, data); \
156 if (error != 0) \
157 goto fail; \
158} while (0)
159#define urtw_8187_write_phy_ofdm(sc, val, data) do { \
160 error = urtw_8187_write_phy_ofdm_c(sc, val, data); \
161 if (error != 0) \
162 goto fail; \
163} while (0)
164#define urtw_8187_write_phy_cck(sc, val, data) do { \
165 error = urtw_8187_write_phy_cck_c(sc, val, data); \
166 if (error != 0) \
167 goto fail; \
168} while (0)
169#define urtw_8225_write(sc, val, data) do { \
170 error = urtw_8225_write_c(sc, val, data); \
171 if (error != 0) \
172 goto fail; \
173} while (0)
174
175struct urtw_pair {
176 uint32_t reg;
177 uint32_t val;
178};
179
180static uint8_t urtw_8225_agc[] = {
181 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9d, 0x9c, 0x9b,
182 0x9a, 0x99, 0x98, 0x97, 0x96, 0x95, 0x94, 0x93, 0x92, 0x91, 0x90,
183 0x8f, 0x8e, 0x8d, 0x8c, 0x8b, 0x8a, 0x89, 0x88, 0x87, 0x86, 0x85,
184 0x84, 0x83, 0x82, 0x81, 0x80, 0x3f, 0x3e, 0x3d, 0x3c, 0x3b, 0x3a,
185 0x39, 0x38, 0x37, 0x36, 0x35, 0x34, 0x33, 0x32, 0x31, 0x30, 0x2f,
186 0x2e, 0x2d, 0x2c, 0x2b, 0x2a, 0x29, 0x28, 0x27, 0x26, 0x25, 0x24,
187 0x23, 0x22, 0x21, 0x20, 0x1f, 0x1e, 0x1d, 0x1c, 0x1b, 0x1a, 0x19,
188 0x18, 0x17, 0x16, 0x15, 0x14, 0x13, 0x12, 0x11, 0x10, 0x0f, 0x0e,
189 0x0d, 0x0c, 0x0b, 0x0a, 0x09, 0x08, 0x07, 0x06, 0x05, 0x04, 0x03,
190 0x02, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01,
191 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01,
192 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01
193};
194
195static uint8_t urtw_8225z2_agc[] = {
196 0x5e, 0x5e, 0x5e, 0x5e, 0x5d, 0x5b, 0x59, 0x57, 0x55, 0x53, 0x51,
197 0x4f, 0x4d, 0x4b, 0x49, 0x47, 0x45, 0x43, 0x41, 0x3f, 0x3d, 0x3b,
198 0x39, 0x37, 0x35, 0x33, 0x31, 0x2f, 0x2d, 0x2b, 0x29, 0x27, 0x25,
199 0x23, 0x21, 0x1f, 0x1d, 0x1b, 0x19, 0x17, 0x15, 0x13, 0x11, 0x0f,
200 0x0d, 0x0b, 0x09, 0x07, 0x05, 0x03, 0x01, 0x01, 0x01, 0x01, 0x01,
201 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x19, 0x19,
202 0x19, 0x19, 0x19, 0x19, 0x19, 0x19, 0x19, 0x20, 0x21, 0x22, 0x23,
203 0x24, 0x25, 0x26, 0x26, 0x27, 0x27, 0x28, 0x28, 0x29, 0x2a, 0x2a,
204 0x2a, 0x2b, 0x2b, 0x2b, 0x2c, 0x2c, 0x2c, 0x2d, 0x2d, 0x2d, 0x2d,
205 0x2e, 0x2e, 0x2e, 0x2e, 0x2f, 0x2f, 0x2f, 0x30, 0x30, 0x31, 0x31,
206 0x31, 0x31, 0x31, 0x31, 0x31, 0x31, 0x31, 0x31, 0x31, 0x31, 0x31,
207 0x31, 0x31, 0x31, 0x31, 0x31, 0x31, 0x31
208};
209
210static uint32_t urtw_8225_channel[] = {
211 0x0000, /* dummy channel 0 */
212 0x085c, /* 1 */
213 0x08dc, /* 2 */
214 0x095c, /* 3 */
215 0x09dc, /* 4 */
216 0x0a5c, /* 5 */
217 0x0adc, /* 6 */
218 0x0b5c, /* 7 */
219 0x0bdc, /* 8 */
220 0x0c5c, /* 9 */
221 0x0cdc, /* 10 */
222 0x0d5c, /* 11 */
223 0x0ddc, /* 12 */
224 0x0e5c, /* 13 */
225 0x0f72, /* 14 */
226};
227
228static uint8_t urtw_8225_gain[] = {
229 0x23, 0x88, 0x7c, 0xa5, /* -82dbm */
230 0x23, 0x88, 0x7c, 0xb5, /* -82dbm */
231 0x23, 0x88, 0x7c, 0xc5, /* -82dbm */
232 0x33, 0x80, 0x79, 0xc5, /* -78dbm */
233 0x43, 0x78, 0x76, 0xc5, /* -74dbm */
234 0x53, 0x60, 0x73, 0xc5, /* -70dbm */
235 0x63, 0x58, 0x70, 0xc5, /* -66dbm */
236};
237
238static struct urtw_pair urtw_8225_rf_part1[] = {
239 { 0x00, 0x0067 }, { 0x01, 0x0fe0 }, { 0x02, 0x044d }, { 0x03, 0x0441 },
240 { 0x04, 0x0486 }, { 0x05, 0x0bc0 }, { 0x06, 0x0ae6 }, { 0x07, 0x082a },
241 { 0x08, 0x001f }, { 0x09, 0x0334 }, { 0x0a, 0x0fd4 }, { 0x0b, 0x0391 },
242 { 0x0c, 0x0050 }, { 0x0d, 0x06db }, { 0x0e, 0x0029 }, { 0x0f, 0x0914 },
243};
244
245static struct urtw_pair urtw_8225_rf_part2[] = {
246 { 0x00, 0x01 }, { 0x01, 0x02 }, { 0x02, 0x42 }, { 0x03, 0x00 },
247 { 0x04, 0x00 }, { 0x05, 0x00 }, { 0x06, 0x40 }, { 0x07, 0x00 },
248 { 0x08, 0x40 }, { 0x09, 0xfe }, { 0x0a, 0x09 }, { 0x0b, 0x80 },
249 { 0x0c, 0x01 }, { 0x0e, 0xd3 }, { 0x0f, 0x38 }, { 0x10, 0x84 },
250 { 0x11, 0x06 }, { 0x12, 0x20 }, { 0x13, 0x20 }, { 0x14, 0x00 },
251 { 0x15, 0x40 }, { 0x16, 0x00 }, { 0x17, 0x40 }, { 0x18, 0xef },
252 { 0x19, 0x19 }, { 0x1a, 0x20 }, { 0x1b, 0x76 }, { 0x1c, 0x04 },
253 { 0x1e, 0x95 }, { 0x1f, 0x75 }, { 0x20, 0x1f }, { 0x21, 0x27 },
254 { 0x22, 0x16 }, { 0x24, 0x46 }, { 0x25, 0x20 }, { 0x26, 0x90 },
255 { 0x27, 0x88 }
256};
257
258static struct urtw_pair urtw_8225_rf_part3[] = {
259 { 0x00, 0x98 }, { 0x03, 0x20 }, { 0x04, 0x7e }, { 0x05, 0x12 },
260 { 0x06, 0xfc }, { 0x07, 0x78 }, { 0x08, 0x2e }, { 0x10, 0x9b },
261 { 0x11, 0x88 }, { 0x12, 0x47 }, { 0x13, 0xd0 }, { 0x19, 0x00 },
262 { 0x1a, 0xa0 }, { 0x1b, 0x08 }, { 0x40, 0x86 }, { 0x41, 0x8d },
263 { 0x42, 0x15 }, { 0x43, 0x18 }, { 0x44, 0x1f }, { 0x45, 0x1e },
264 { 0x46, 0x1a }, { 0x47, 0x15 }, { 0x48, 0x10 }, { 0x49, 0x0a },
265 { 0x4a, 0x05 }, { 0x4b, 0x02 }, { 0x4c, 0x05 }
266};
267
268static uint16_t urtw_8225_rxgain[] = {
269 0x0400, 0x0401, 0x0402, 0x0403, 0x0404, 0x0405, 0x0408, 0x0409,
270 0x040a, 0x040b, 0x0502, 0x0503, 0x0504, 0x0505, 0x0540, 0x0541,
271 0x0542, 0x0543, 0x0544, 0x0545, 0x0580, 0x0581, 0x0582, 0x0583,
272 0x0584, 0x0585, 0x0588, 0x0589, 0x058a, 0x058b, 0x0643, 0x0644,
273 0x0645, 0x0680, 0x0681, 0x0682, 0x0683, 0x0684, 0x0685, 0x0688,
274 0x0689, 0x068a, 0x068b, 0x068c, 0x0742, 0x0743, 0x0744, 0x0745,
275 0x0780, 0x0781, 0x0782, 0x0783, 0x0784, 0x0785, 0x0788, 0x0789,
276 0x078a, 0x078b, 0x078c, 0x078d, 0x0790, 0x0791, 0x0792, 0x0793,
277 0x0794, 0x0795, 0x0798, 0x0799, 0x079a, 0x079b, 0x079c, 0x079d,
278 0x07a0, 0x07a1, 0x07a2, 0x07a3, 0x07a4, 0x07a5, 0x07a8, 0x07a9,
279 0x07aa, 0x07ab, 0x07ac, 0x07ad, 0x07b0, 0x07b1, 0x07b2, 0x07b3,
280 0x07b4, 0x07b5, 0x07b8, 0x07b9, 0x07ba, 0x07bb, 0x07bb
281};
282
283static uint8_t urtw_8225_threshold[] = {
284 0x8d, 0x8d, 0x8d, 0x8d, 0x9d, 0xad, 0xbd,
285};
286
287static uint8_t urtw_8225_tx_gain_cck_ofdm[] = {
288 0x02, 0x06, 0x0e, 0x1e, 0x3e, 0x7e
289};
290
291static uint8_t urtw_8225_txpwr_cck[] = {
292 0x18, 0x17, 0x15, 0x11, 0x0c, 0x08, 0x04, 0x02,
293 0x1b, 0x1a, 0x17, 0x13, 0x0e, 0x09, 0x04, 0x02,
294 0x1f, 0x1e, 0x1a, 0x15, 0x10, 0x0a, 0x05, 0x02,
295 0x22, 0x21, 0x1d, 0x18, 0x11, 0x0b, 0x06, 0x02,
296 0x26, 0x25, 0x21, 0x1b, 0x14, 0x0d, 0x06, 0x03,
297 0x2b, 0x2a, 0x25, 0x1e, 0x16, 0x0e, 0x07, 0x03
298};
299
300static uint8_t urtw_8225_txpwr_cck_ch14[] = {
301 0x18, 0x17, 0x15, 0x0c, 0x00, 0x00, 0x00, 0x00,
302 0x1b, 0x1a, 0x17, 0x0e, 0x00, 0x00, 0x00, 0x00,
303 0x1f, 0x1e, 0x1a, 0x0f, 0x00, 0x00, 0x00, 0x00,
304 0x22, 0x21, 0x1d, 0x11, 0x00, 0x00, 0x00, 0x00,
305 0x26, 0x25, 0x21, 0x13, 0x00, 0x00, 0x00, 0x00,
306 0x2b, 0x2a, 0x25, 0x15, 0x00, 0x00, 0x00, 0x00
307};
308
309static uint8_t urtw_8225_txpwr_ofdm[]={
310 0x80, 0x90, 0xa2, 0xb5, 0xcb, 0xe4
311};
312
313static uint8_t urtw_8225v2_gain_bg[]={
314 0x23, 0x15, 0xa5, /* -82-1dbm */
315 0x23, 0x15, 0xb5, /* -82-2dbm */
316 0x23, 0x15, 0xc5, /* -82-3dbm */
317 0x33, 0x15, 0xc5, /* -78dbm */
318 0x43, 0x15, 0xc5, /* -74dbm */
319 0x53, 0x15, 0xc5, /* -70dbm */
320 0x63, 0x15, 0xc5, /* -66dbm */
321};
322
323static struct urtw_pair urtw_8225v2_rf_part1[] = {
324 { 0x00, 0x02bf }, { 0x01, 0x0ee0 }, { 0x02, 0x044d }, { 0x03, 0x0441 },
325 { 0x04, 0x08c3 }, { 0x05, 0x0c72 }, { 0x06, 0x00e6 }, { 0x07, 0x082a },
326 { 0x08, 0x003f }, { 0x09, 0x0335 }, { 0x0a, 0x09d4 }, { 0x0b, 0x07bb },
327 { 0x0c, 0x0850 }, { 0x0d, 0x0cdf }, { 0x0e, 0x002b }, { 0x0f, 0x0114 }
328};
329
330static struct urtw_pair urtw_8225v2b_rf_part0[] = {
331 { 0x00, 0x00b7 }, { 0x01, 0x0ee0 }, { 0x02, 0x044d }, { 0x03, 0x0441 },
332 { 0x04, 0x08c3 }, { 0x05, 0x0c72 }, { 0x06, 0x00e6 }, { 0x07, 0x082a },
333 { 0x08, 0x003f }, { 0x09, 0x0335 }, { 0x0a, 0x09d4 }, { 0x0b, 0x07bb },
334 { 0x0c, 0x0850 }, { 0x0d, 0x0cdf }, { 0x0e, 0x002b }, { 0x0f, 0x0114 }
335};
336
337static struct urtw_pair urtw_8225v2b_rf_part1[] = {
338 {0x0f0, 0x32}, {0x0f1, 0x32}, {0x0f2, 0x00},
339 {0x0f3, 0x00}, {0x0f4, 0x32}, {0x0f5, 0x43},
340 {0x0f6, 0x00}, {0x0f7, 0x00}, {0x0f8, 0x46},
341 {0x0f9, 0xa4}, {0x0fa, 0x00}, {0x0fb, 0x00},
342 {0x0fc, 0x96}, {0x0fd, 0xa4}, {0x0fe, 0x00},
343 {0x0ff, 0x00}, {0x158, 0x4b}, {0x159, 0x00},
344 {0x15a, 0x4b}, {0x15b, 0x00}, {0x160, 0x4b},
345 {0x161, 0x09}, {0x162, 0x4b}, {0x163, 0x09},
346 {0x1ce, 0x0f}, {0x1cf, 0x00}, {0x1e0, 0xff},
347 {0x1e1, 0x0f}, {0x1e2, 0x00}, {0x1f0, 0x4e},
348 {0x1f1, 0x01}, {0x1f2, 0x02}, {0x1f3, 0x03},
349 {0x1f4, 0x04}, {0x1f5, 0x05}, {0x1f6, 0x06},
350 {0x1f7, 0x07}, {0x1f8, 0x08}, {0x24e, 0x00},
351 {0x20c, 0x04}, {0x221, 0x61}, {0x222, 0x68},
352 {0x223, 0x6f}, {0x224, 0x76}, {0x225, 0x7d},
353 {0x226, 0x84}, {0x227, 0x8d}, {0x24d, 0x08},
354 {0x250, 0x05}, {0x251, 0xf5}, {0x252, 0x04},
355 {0x253, 0xa0}, {0x254, 0x1f}, {0x255, 0x23},
356 {0x256, 0x45}, {0x257, 0x67}, {0x258, 0x08},
357 {0x259, 0x08}, {0x25a, 0x08}, {0x25b, 0x08},
358 {0x260, 0x08}, {0x261, 0x08}, {0x262, 0x08},
359 {0x263, 0x08}, {0x264, 0xcf}, {0x272, 0x56},
360 {0x273, 0x9a}, {0x034, 0xf0}, {0x035, 0x0f},
361 {0x05b, 0x40}, {0x084, 0x88}, {0x085, 0x24},
362 {0x088, 0x54}, {0x08b, 0xb8}, {0x08c, 0x07},
363 {0x08d, 0x00}, {0x094, 0x1b}, {0x095, 0x12},
364 {0x096, 0x00}, {0x097, 0x06}, {0x09d, 0x1a},
365 {0x09f, 0x10}, {0x0b4, 0x22}, {0x0be, 0x80},
366 {0x0db, 0x00}, {0x0ee, 0x00}, {0x091, 0x03},
367 {0x24c, 0x00}, {0x39f, 0x00}, {0x08c, 0x01},
368 {0x08d, 0x10}, {0x08e, 0x08}, {0x08f, 0x00}
369};
370
371static struct urtw_pair urtw_8225v2_rf_part2[] = {
372 { 0x00, 0x01 }, { 0x01, 0x02 }, { 0x02, 0x42 }, { 0x03, 0x00 },
373 { 0x04, 0x00 }, { 0x05, 0x00 }, { 0x06, 0x40 }, { 0x07, 0x00 },
374 { 0x08, 0x40 }, { 0x09, 0xfe }, { 0x0a, 0x08 }, { 0x0b, 0x80 },
375 { 0x0c, 0x01 }, { 0x0d, 0x43 }, { 0x0e, 0xd3 }, { 0x0f, 0x38 },
376 { 0x10, 0x84 }, { 0x11, 0x07 }, { 0x12, 0x20 }, { 0x13, 0x20 },
377 { 0x14, 0x00 }, { 0x15, 0x40 }, { 0x16, 0x00 }, { 0x17, 0x40 },
378 { 0x18, 0xef }, { 0x19, 0x19 }, { 0x1a, 0x20 }, { 0x1b, 0x15 },
379 { 0x1c, 0x04 }, { 0x1d, 0xc5 }, { 0x1e, 0x95 }, { 0x1f, 0x75 },
380 { 0x20, 0x1f }, { 0x21, 0x17 }, { 0x22, 0x16 }, { 0x23, 0x80 },
381 { 0x24, 0x46 }, { 0x25, 0x00 }, { 0x26, 0x90 }, { 0x27, 0x88 }
382};
383
384static struct urtw_pair urtw_8225v2b_rf_part2[] = {
385 { 0x00, 0x10 }, { 0x01, 0x0d }, { 0x02, 0x01 }, { 0x03, 0x00 },
386 { 0x04, 0x14 }, { 0x05, 0xfb }, { 0x06, 0xfb }, { 0x07, 0x60 },
387 { 0x08, 0x00 }, { 0x09, 0x60 }, { 0x0a, 0x00 }, { 0x0b, 0x00 },
388 { 0x0c, 0x00 }, { 0x0d, 0x5c }, { 0x0e, 0x00 }, { 0x0f, 0x00 },
389 { 0x10, 0x40 }, { 0x11, 0x00 }, { 0x12, 0x40 }, { 0x13, 0x00 },
390 { 0x14, 0x00 }, { 0x15, 0x00 }, { 0x16, 0xa8 }, { 0x17, 0x26 },
391 { 0x18, 0x32 }, { 0x19, 0x33 }, { 0x1a, 0x07 }, { 0x1b, 0xa5 },
392 { 0x1c, 0x6f }, { 0x1d, 0x55 }, { 0x1e, 0xc8 }, { 0x1f, 0xb3 },
393 { 0x20, 0x0a }, { 0x21, 0xe1 }, { 0x22, 0x2C }, { 0x23, 0x8a },
394 { 0x24, 0x86 }, { 0x25, 0x83 }, { 0x26, 0x34 }, { 0x27, 0x0f },
395 { 0x28, 0x4f }, { 0x29, 0x24 }, { 0x2a, 0x6f }, { 0x2b, 0xc2 },
396 { 0x2c, 0x6b }, { 0x2d, 0x40 }, { 0x2e, 0x80 }, { 0x2f, 0x00 },
397 { 0x30, 0xc0 }, { 0x31, 0xc1 }, { 0x32, 0x58 }, { 0x33, 0xf1 },
398 { 0x34, 0x00 }, { 0x35, 0xe4 }, { 0x36, 0x90 }, { 0x37, 0x3e },
399 { 0x38, 0x6d }, { 0x39, 0x3c }, { 0x3a, 0xfb }, { 0x3b, 0x07 }
400};
401
402static struct urtw_pair urtw_8225v2_rf_part3[] = {
403 { 0x00, 0x98 }, { 0x03, 0x20 }, { 0x04, 0x7e }, { 0x05, 0x12 },
404 { 0x06, 0xfc }, { 0x07, 0x78 }, { 0x08, 0x2e }, { 0x09, 0x11 },
405 { 0x0a, 0x17 }, { 0x0b, 0x11 }, { 0x10, 0x9b }, { 0x11, 0x88 },
406 { 0x12, 0x47 }, { 0x13, 0xd0 }, { 0x19, 0x00 }, { 0x1a, 0xa0 },
407 { 0x1b, 0x08 }, { 0x1d, 0x00 }, { 0x40, 0x86 }, { 0x41, 0x9d },
408 { 0x42, 0x15 }, { 0x43, 0x18 }, { 0x44, 0x36 }, { 0x45, 0x35 },
409 { 0x46, 0x2e }, { 0x47, 0x25 }, { 0x48, 0x1c }, { 0x49, 0x12 },
410 { 0x4a, 0x09 }, { 0x4b, 0x04 }, { 0x4c, 0x05 }
411};
412
413static uint16_t urtw_8225v2_rxgain[] = {
414 0x0000, 0x0001, 0x0002, 0x0003, 0x0004, 0x0005, 0x0008, 0x0009,
415 0x000a, 0x000b, 0x0102, 0x0103, 0x0104, 0x0105, 0x0140, 0x0141,
416 0x0142, 0x0143, 0x0144, 0x0145, 0x0180, 0x0181, 0x0182, 0x0183,
417 0x0184, 0x0185, 0x0188, 0x0189, 0x018a, 0x018b, 0x0243, 0x0244,
418 0x0245, 0x0280, 0x0281, 0x0282, 0x0283, 0x0284, 0x0285, 0x0288,
419 0x0289, 0x028a, 0x028b, 0x028c, 0x0342, 0x0343, 0x0344, 0x0345,
420 0x0380, 0x0381, 0x0382, 0x0383, 0x0384, 0x0385, 0x0388, 0x0389,
421 0x038a, 0x038b, 0x038c, 0x038d, 0x0390, 0x0391, 0x0392, 0x0393,
422 0x0394, 0x0395, 0x0398, 0x0399, 0x039a, 0x039b, 0x039c, 0x039d,
423 0x03a0, 0x03a1, 0x03a2, 0x03a3, 0x03a4, 0x03a5, 0x03a8, 0x03a9,
424 0x03aa, 0x03ab, 0x03ac, 0x03ad, 0x03b0, 0x03b1, 0x03b2, 0x03b3,
425 0x03b4, 0x03b5, 0x03b8, 0x03b9, 0x03ba, 0x03bb, 0x03bb
426};
427
428static uint16_t urtw_8225v2b_rxgain[] = {
429 0x0400, 0x0401, 0x0402, 0x0403, 0x0404, 0x0405, 0x0408, 0x0409,
430 0x040a, 0x040b, 0x0502, 0x0503, 0x0504, 0x0505, 0x0540, 0x0541,
431 0x0542, 0x0543, 0x0544, 0x0545, 0x0580, 0x0581, 0x0582, 0x0583,
432 0x0584, 0x0585, 0x0588, 0x0589, 0x058a, 0x058b, 0x0643, 0x0644,
433 0x0645, 0x0680, 0x0681, 0x0682, 0x0683, 0x0684, 0x0685, 0x0688,
434 0x0689, 0x068a, 0x068b, 0x068c, 0x0742, 0x0743, 0x0744, 0x0745,
435 0x0780, 0x0781, 0x0782, 0x0783, 0x0784, 0x0785, 0x0788, 0x0789,
436 0x078a, 0x078b, 0x078c, 0x078d, 0x0790, 0x0791, 0x0792, 0x0793,
437 0x0794, 0x0795, 0x0798, 0x0799, 0x079a, 0x079b, 0x079c, 0x079d,
438 0x07a0, 0x07a1, 0x07a2, 0x07a3, 0x07a4, 0x07a5, 0x07a8, 0x07a9,
439 0x03aa, 0x03ab, 0x03ac, 0x03ad, 0x03b0, 0x03b1, 0x03b2, 0x03b3,
440 0x03b4, 0x03b5, 0x03b8, 0x03b9, 0x03ba, 0x03bb, 0x03bb
441};
442
443static uint8_t urtw_8225v2_tx_gain_cck_ofdm[] = {
444 0x00, 0x01, 0x02, 0x03, 0x04, 0x05,
445 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b,
446 0x0c, 0x0d, 0x0e, 0x0f, 0x10, 0x11,
447 0x12, 0x13, 0x14, 0x15, 0x16, 0x17,
448 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d,
449 0x1e, 0x1f, 0x20, 0x21, 0x22, 0x23,
450};
451
452static uint8_t urtw_8225v2_txpwr_cck[] = {
453 0x36, 0x35, 0x2e, 0x25, 0x1c, 0x12, 0x09, 0x04
454};
455
456static uint8_t urtw_8225v2_txpwr_cck_ch14[] = {
457 0x36, 0x35, 0x2e, 0x1b, 0x00, 0x00, 0x00, 0x00
458};
459
460static uint8_t urtw_8225v2b_txpwr_cck[] = {
461 0x36, 0x35, 0x2e, 0x25, 0x1c, 0x12, 0x09, 0x04,
462 0x30, 0x2f, 0x29, 0x21, 0x19, 0x10, 0x08, 0x03,
463 0x2b, 0x2a, 0x25, 0x1e, 0x16, 0x0e, 0x07, 0x03,
464 0x26, 0x25, 0x21, 0x1b, 0x14, 0x0d, 0x06, 0x03
465};
466
467static uint8_t urtw_8225v2b_txpwr_cck_ch14[] = {
468 0x36, 0x35, 0x2e, 0x1b, 0x00, 0x00, 0x00, 0x00,
469 0x30, 0x2f, 0x29, 0x15, 0x00, 0x00, 0x00, 0x00,
470 0x30, 0x2f, 0x29, 0x15, 0x00, 0x00, 0x00, 0x00,
471 0x30, 0x2f, 0x29, 0x15, 0x00, 0x00, 0x00, 0x00
472};
473
474static struct urtw_pair urtw_ratetable[] = {
475 { 2, 0 }, { 4, 1 }, { 11, 2 }, { 12, 4 }, { 18, 5 },
476 { 22, 3 }, { 24, 6 }, { 36, 7 }, { 48, 8 }, { 72, 9 },
477 { 96, 10 }, { 108, 11 }
478};
479
480static const uint8_t urtw_8187b_reg_table[][3] = {
481 { 0xf0, 0x32, 0 }, { 0xf1, 0x32, 0 }, { 0xf2, 0x00, 0 },
482 { 0xf3, 0x00, 0 }, { 0xf4, 0x32, 0 }, { 0xf5, 0x43, 0 },
483 { 0xf6, 0x00, 0 }, { 0xf7, 0x00, 0 }, { 0xf8, 0x46, 0 },
484 { 0xf9, 0xa4, 0 }, { 0xfa, 0x00, 0 }, { 0xfb, 0x00, 0 },
485 { 0xfc, 0x96, 0 }, { 0xfd, 0xa4, 0 }, { 0xfe, 0x00, 0 },
486 { 0xff, 0x00, 0 }, { 0x58, 0x4b, 1 }, { 0x59, 0x00, 1 },
487 { 0x5a, 0x4b, 1 }, { 0x5b, 0x00, 1 }, { 0x60, 0x4b, 1 },
488 { 0x61, 0x09, 1 }, { 0x62, 0x4b, 1 }, { 0x63, 0x09, 1 },
489 { 0xce, 0x0f, 1 }, { 0xcf, 0x00, 1 }, { 0xe0, 0xff, 1 },
490 { 0xe1, 0x0f, 1 }, { 0xe2, 0x00, 1 }, { 0xf0, 0x4e, 1 },
491 { 0xf1, 0x01, 1 }, { 0xf2, 0x02, 1 }, { 0xf3, 0x03, 1 },
492 { 0xf4, 0x04, 1 }, { 0xf5, 0x05, 1 }, { 0xf6, 0x06, 1 },
493 { 0xf7, 0x07, 1 }, { 0xf8, 0x08, 1 }, { 0x4e, 0x00, 2 },
494 { 0x0c, 0x04, 2 }, { 0x21, 0x61, 2 }, { 0x22, 0x68, 2 },
495 { 0x23, 0x6f, 2 }, { 0x24, 0x76, 2 }, { 0x25, 0x7d, 2 },
496 { 0x26, 0x84, 2 }, { 0x27, 0x8d, 2 }, { 0x4d, 0x08, 2 },
497 { 0x50, 0x05, 2 }, { 0x51, 0xf5, 2 }, { 0x52, 0x04, 2 },
498 { 0x53, 0xa0, 2 }, { 0x54, 0x1f, 2 }, { 0x55, 0x23, 2 },
499 { 0x56, 0x45, 2 }, { 0x57, 0x67, 2 }, { 0x58, 0x08, 2 },
500 { 0x59, 0x08, 2 }, { 0x5a, 0x08, 2 }, { 0x5b, 0x08, 2 },
501 { 0x60, 0x08, 2 }, { 0x61, 0x08, 2 }, { 0x62, 0x08, 2 },
502 { 0x63, 0x08, 2 }, { 0x64, 0xcf, 2 }, { 0x72, 0x56, 2 },
503 { 0x73, 0x9a, 2 }, { 0x34, 0xf0, 0 }, { 0x35, 0x0f, 0 },
504 { 0x5b, 0x40, 0 }, { 0x84, 0x88, 0 }, { 0x85, 0x24, 0 },
505 { 0x88, 0x54, 0 }, { 0x8b, 0xb8, 0 }, { 0x8c, 0x07, 0 },
506 { 0x8d, 0x00, 0 }, { 0x94, 0x1b, 0 }, { 0x95, 0x12, 0 },
507 { 0x96, 0x00, 0 }, { 0x97, 0x06, 0 }, { 0x9d, 0x1a, 0 },
508 { 0x9f, 0x10, 0 }, { 0xb4, 0x22, 0 }, { 0xbe, 0x80, 0 },
509 { 0xdb, 0x00, 0 }, { 0xee, 0x00, 0 }, { 0x91, 0x03, 0 },
510 { 0x4c, 0x00, 2 }, { 0x9f, 0x00, 3 }, { 0x8c, 0x01, 0 },
511 { 0x8d, 0x10, 0 }, { 0x8e, 0x08, 0 }, { 0x8f, 0x00, 0 }
512};
513
514static usb_callback_t urtw_bulk_rx_callback;
515static usb_callback_t urtw_bulk_tx_callback;
516static usb_callback_t urtw_bulk_tx_status_callback;
517
518static const struct usb_config urtw_8187b_usbconfig[URTW_8187B_N_XFERS] = {
519 [URTW_8187B_BULK_RX] = {
520 .type = UE_BULK,
521 .endpoint = 0x83,
522 .direction = UE_DIR_IN,
523 .bufsize = MCLBYTES,
524 .flags = {
525 .ext_buffer = 1,
526 .pipe_bof = 1,
527 .short_xfer_ok = 1
528 },
529 .callback = urtw_bulk_rx_callback
530 },
531 [URTW_8187B_BULK_TX_STATUS] = {
532 .type = UE_BULK,
533 .endpoint = 0x89,
534 .direction = UE_DIR_IN,
535 .bufsize = MCLBYTES,
536 .flags = {
537 .ext_buffer = 1,
538 .pipe_bof = 1,
539 .short_xfer_ok = 1
540 },
541 .callback = urtw_bulk_tx_status_callback
542 },
543 [URTW_8187B_BULK_TX_BE] = {
544 .type = UE_BULK,
545 .endpoint = URTW_8187B_TXPIPE_BE,
546 .direction = UE_DIR_OUT,
547 .bufsize = URTW_TX_MAXSIZE,
548 .flags = {
549 .ext_buffer = 1,
550 .force_short_xfer = 1,
551 .pipe_bof = 1,
552 },
553 .callback = urtw_bulk_tx_callback,
554 .timeout = URTW_DATA_TIMEOUT
555 },
556 [URTW_8187B_BULK_TX_BK] = {
557 .type = UE_BULK,
558 .endpoint = URTW_8187B_TXPIPE_BK,
559 .direction = UE_DIR_OUT,
560 .bufsize = URTW_TX_MAXSIZE,
561 .flags = {
562 .ext_buffer = 1,
563 .force_short_xfer = 1,
564 .pipe_bof = 1,
565 },
566 .callback = urtw_bulk_tx_callback,
567 .timeout = URTW_DATA_TIMEOUT
568 },
569 [URTW_8187B_BULK_TX_VI] = {
570 .type = UE_BULK,
571 .endpoint = URTW_8187B_TXPIPE_VI,
572 .direction = UE_DIR_OUT,
573 .bufsize = URTW_TX_MAXSIZE,
574 .flags = {
575 .ext_buffer = 1,
576 .force_short_xfer = 1,
577 .pipe_bof = 1,
578 },
579 .callback = urtw_bulk_tx_callback,
580 .timeout = URTW_DATA_TIMEOUT
581 },
582 [URTW_8187B_BULK_TX_VO] = {
583 .type = UE_BULK,
584 .endpoint = URTW_8187B_TXPIPE_VO,
585 .direction = UE_DIR_OUT,
586 .bufsize = URTW_TX_MAXSIZE,
587 .flags = {
588 .ext_buffer = 1,
589 .force_short_xfer = 1,
590 .pipe_bof = 1,
591 },
592 .callback = urtw_bulk_tx_callback,
593 .timeout = URTW_DATA_TIMEOUT
594 },
595 [URTW_8187B_BULK_TX_EP12] = {
596 .type = UE_BULK,
597 .endpoint = 0xc,
598 .direction = UE_DIR_OUT,
599 .bufsize = URTW_TX_MAXSIZE,
600 .flags = {
601 .ext_buffer = 1,
602 .force_short_xfer = 1,
603 .pipe_bof = 1,
604 },
605 .callback = urtw_bulk_tx_callback,
606 .timeout = URTW_DATA_TIMEOUT
607 }
608};
609
610static const struct usb_config urtw_8187l_usbconfig[URTW_8187L_N_XFERS] = {
611 [URTW_8187L_BULK_RX] = {
612 .type = UE_BULK,
613 .endpoint = 0x81,
614 .direction = UE_DIR_IN,
615 .bufsize = MCLBYTES,
616 .flags = {
617 .ext_buffer = 1,
618 .pipe_bof = 1,
619 .short_xfer_ok = 1
620 },
621 .callback = urtw_bulk_rx_callback
622 },
623 [URTW_8187L_BULK_TX_LOW] = {
624 .type = UE_BULK,
625 .endpoint = 0x2,
626 .direction = UE_DIR_OUT,
627 .bufsize = URTW_TX_MAXSIZE,
628 .flags = {
629 .ext_buffer = 1,
630 .force_short_xfer = 1,
631 .pipe_bof = 1,
632 },
633 .callback = urtw_bulk_tx_callback,
634 .timeout = URTW_DATA_TIMEOUT
635 },
636 [URTW_8187L_BULK_TX_NORMAL] = {
637 .type = UE_BULK,
638 .endpoint = 0x3,
639 .direction = UE_DIR_OUT,
640 .bufsize = URTW_TX_MAXSIZE,
641 .flags = {
642 .ext_buffer = 1,
643 .force_short_xfer = 1,
644 .pipe_bof = 1,
645 },
646 .callback = urtw_bulk_tx_callback,
647 .timeout = URTW_DATA_TIMEOUT
648 },
649};
650
651static struct ieee80211vap *urtw_vap_create(struct ieee80211com *,
652 const char name[IFNAMSIZ], int unit, int opmode,
653 int flags, const uint8_t bssid[IEEE80211_ADDR_LEN],
654 const uint8_t mac[IEEE80211_ADDR_LEN]);
655static void urtw_vap_delete(struct ieee80211vap *);
656static void urtw_init(void *);
657static void urtw_stop(struct ifnet *, int);
658static void urtw_stop_locked(struct ifnet *, int);
659static int urtw_ioctl(struct ifnet *, u_long, caddr_t);
660static void urtw_start(struct ifnet *);
661static int urtw_alloc_rx_data_list(struct urtw_softc *);
662static int urtw_alloc_tx_data_list(struct urtw_softc *);
663static int urtw_raw_xmit(struct ieee80211_node *, struct mbuf *,
664 const struct ieee80211_bpf_params *);
665static void urtw_scan_start(struct ieee80211com *);
666static void urtw_scan_end(struct ieee80211com *);
667static void urtw_set_channel(struct ieee80211com *);
668static void urtw_update_mcast(struct ifnet *);
669static int urtw_tx_start(struct urtw_softc *,
670 struct ieee80211_node *, struct mbuf *,
671 struct urtw_data *, int);
672static int urtw_newstate(struct ieee80211vap *,
673 enum ieee80211_state, int);
674static void urtw_led_ch(void *);
675static void urtw_ledtask(void *, int);
676static void urtw_watchdog(void *);
677static void urtw_set_multi(void *);
678static int urtw_isbmode(uint16_t);
679static uint16_t urtw_rate2rtl(int);
680static uint16_t urtw_rtl2rate(int);
681static usb_error_t urtw_set_rate(struct urtw_softc *);
682static usb_error_t urtw_update_msr(struct urtw_softc *);
683static usb_error_t urtw_read8_c(struct urtw_softc *, int, uint8_t *);
684static usb_error_t urtw_read16_c(struct urtw_softc *, int, uint16_t *);
685static usb_error_t urtw_read32_c(struct urtw_softc *, int, uint32_t *);
686static usb_error_t urtw_write8_c(struct urtw_softc *, int, uint8_t);
687static usb_error_t urtw_write16_c(struct urtw_softc *, int, uint16_t);
688static usb_error_t urtw_write32_c(struct urtw_softc *, int, uint32_t);
689static usb_error_t urtw_eprom_cs(struct urtw_softc *, int);
690static usb_error_t urtw_eprom_ck(struct urtw_softc *);
691static usb_error_t urtw_eprom_sendbits(struct urtw_softc *, int16_t *,
692 int);
693static usb_error_t urtw_eprom_read32(struct urtw_softc *, uint32_t,
694 uint32_t *);
695static usb_error_t urtw_eprom_readbit(struct urtw_softc *, int16_t *);
696static usb_error_t urtw_eprom_writebit(struct urtw_softc *, int16_t);
697static usb_error_t urtw_get_macaddr(struct urtw_softc *);
698static usb_error_t urtw_get_txpwr(struct urtw_softc *);
699static usb_error_t urtw_get_rfchip(struct urtw_softc *);
700static usb_error_t urtw_led_init(struct urtw_softc *);
701static usb_error_t urtw_8185_rf_pins_enable(struct urtw_softc *);
702static usb_error_t urtw_8185_tx_antenna(struct urtw_softc *, uint8_t);
703static usb_error_t urtw_8187_write_phy(struct urtw_softc *, uint8_t,
704 uint32_t);
705static usb_error_t urtw_8187_write_phy_ofdm_c(struct urtw_softc *,
706 uint8_t, uint32_t);
707static usb_error_t urtw_8187_write_phy_cck_c(struct urtw_softc *, uint8_t,
708 uint32_t);
709static usb_error_t urtw_8225_setgain(struct urtw_softc *, int16_t);
710static usb_error_t urtw_8225_usb_init(struct urtw_softc *);
711static usb_error_t urtw_8225_write_c(struct urtw_softc *, uint8_t,
712 uint16_t);
713static usb_error_t urtw_8225_write_s16(struct urtw_softc *, uint8_t, int,
714 uint16_t *);
715static usb_error_t urtw_8225_read(struct urtw_softc *, uint8_t,
716 uint32_t *);
717static usb_error_t urtw_8225_rf_init(struct urtw_softc *);
718static usb_error_t urtw_8225_rf_set_chan(struct urtw_softc *, int);
719static usb_error_t urtw_8225_rf_set_sens(struct urtw_softc *, int);
720static usb_error_t urtw_8225_set_txpwrlvl(struct urtw_softc *, int);
721static usb_error_t urtw_8225_rf_stop(struct urtw_softc *);
722static usb_error_t urtw_8225v2_rf_init(struct urtw_softc *);
723static usb_error_t urtw_8225v2_rf_set_chan(struct urtw_softc *, int);
724static usb_error_t urtw_8225v2_set_txpwrlvl(struct urtw_softc *, int);
725static usb_error_t urtw_8225v2_setgain(struct urtw_softc *, int16_t);
726static usb_error_t urtw_8225_isv2(struct urtw_softc *, int *);
727static usb_error_t urtw_8225v2b_rf_init(struct urtw_softc *);
728static usb_error_t urtw_8225v2b_rf_set_chan(struct urtw_softc *, int);
729static usb_error_t urtw_read8e(struct urtw_softc *, int, uint8_t *);
730static usb_error_t urtw_write8e(struct urtw_softc *, int, uint8_t);
731static usb_error_t urtw_8180_set_anaparam(struct urtw_softc *, uint32_t);
732static usb_error_t urtw_8185_set_anaparam2(struct urtw_softc *, uint32_t);
733static usb_error_t urtw_intr_enable(struct urtw_softc *);
734static usb_error_t urtw_intr_disable(struct urtw_softc *);
735static usb_error_t urtw_reset(struct urtw_softc *);
736static usb_error_t urtw_led_on(struct urtw_softc *, int);
737static usb_error_t urtw_led_ctl(struct urtw_softc *, int);
738static usb_error_t urtw_led_blink(struct urtw_softc *);
739static usb_error_t urtw_led_mode0(struct urtw_softc *, int);
740static usb_error_t urtw_led_mode1(struct urtw_softc *, int);
741static usb_error_t urtw_led_mode2(struct urtw_softc *, int);
742static usb_error_t urtw_led_mode3(struct urtw_softc *, int);
743static usb_error_t urtw_rx_setconf(struct urtw_softc *);
744static usb_error_t urtw_rx_enable(struct urtw_softc *);
745static usb_error_t urtw_tx_enable(struct urtw_softc *sc);
746static void urtw_free_tx_data_list(struct urtw_softc *);
747static void urtw_free_rx_data_list(struct urtw_softc *);
748static void urtw_free_data_list(struct urtw_softc *,
749 struct urtw_data data[], int, int);
750static usb_error_t urtw_adapter_start(struct urtw_softc *);
751static usb_error_t urtw_adapter_start_b(struct urtw_softc *);
752static usb_error_t urtw_set_mode(struct urtw_softc *, uint32_t);
753static usb_error_t urtw_8187b_cmd_reset(struct urtw_softc *);
754static usb_error_t urtw_do_request(struct urtw_softc *,
755 struct usb_device_request *, void *);
756static usb_error_t urtw_8225v2b_set_txpwrlvl(struct urtw_softc *, int);
757static usb_error_t urtw_led_off(struct urtw_softc *, int);
758static void urtw_abort_xfers(struct urtw_softc *);
759static struct urtw_data *
760 urtw_getbuf(struct urtw_softc *sc);
761static int urtw_compute_txtime(uint16_t, uint16_t, uint8_t,
762 uint8_t);
763static void urtw_updateslot(struct ifnet *);
764static void urtw_updateslottask(void *, int);
765static void urtw_sysctl_node(struct urtw_softc *);
766
767static int
768urtw_match(device_t dev)
769{
770 struct usb_attach_arg *uaa = device_get_ivars(dev);
771
772 if (uaa->usb_mode != USB_MODE_HOST)
773 return (ENXIO);
774 if (uaa->info.bConfigIndex != URTW_CONFIG_INDEX)
775 return (ENXIO);
776 if (uaa->info.bIfaceIndex != URTW_IFACE_INDEX)
777 return (ENXIO);
778
779 return (usbd_lookup_id_by_uaa(urtw_devs, sizeof(urtw_devs), uaa));
780}
781
782static int
783urtw_attach(device_t dev)
784{
785 const struct usb_config *setup_start;
786 int ret = ENXIO;
787 struct urtw_softc *sc = device_get_softc(dev);
788 struct usb_attach_arg *uaa = device_get_ivars(dev);
789 struct ieee80211com *ic;
790 struct ifnet *ifp;
791 uint8_t bands, iface_index = URTW_IFACE_INDEX; /* XXX */
792 uint16_t n_setup;
793 uint32_t data;
794 usb_error_t error;
795
796 device_set_usb_desc(dev);
797
798 sc->sc_dev = dev;
799 sc->sc_udev = uaa->device;
800 if (USB_GET_DRIVER_INFO(uaa) == URTW_REV_RTL8187B)
801 sc->sc_flags |= URTW_RTL8187B;
802#ifdef URTW_DEBUG
803 sc->sc_debug = urtw_debug;
804#endif
805
806 mtx_init(&sc->sc_mtx, device_get_nameunit(sc->sc_dev), MTX_NETWORK_LOCK,
807 MTX_DEF);
808 usb_callout_init_mtx(&sc->sc_led_ch, &sc->sc_mtx, 0);
809 TASK_INIT(&sc->sc_led_task, 0, urtw_ledtask, sc);
810 TASK_INIT(&sc->sc_updateslot_task, 0, urtw_updateslottask, sc);
811 callout_init(&sc->sc_watchdog_ch, 0);
812
813 if (sc->sc_flags & URTW_RTL8187B) {
814 setup_start = urtw_8187b_usbconfig;
815 n_setup = URTW_8187B_N_XFERS;
816 } else {
817 setup_start = urtw_8187l_usbconfig;
818 n_setup = URTW_8187L_N_XFERS;
819 }
820
821 error = usbd_transfer_setup(uaa->device, &iface_index, sc->sc_xfer,
822 setup_start, n_setup, sc, &sc->sc_mtx);
823 if (error) {
824 device_printf(dev, "could not allocate USB transfers, "
825 "err=%s\n", usbd_errstr(error));
826 ret = ENXIO;
827 goto fail0;
828 }
829
830 URTW_LOCK(sc);
831
832 urtw_read32_m(sc, URTW_RX, &data);
833 sc->sc_epromtype = (data & URTW_RX_9356SEL) ? URTW_EEPROM_93C56 :
834 URTW_EEPROM_93C46;
835
836 error = urtw_get_rfchip(sc);
837 if (error != 0)
838 goto fail;
839 error = urtw_get_macaddr(sc);
840 if (error != 0)
841 goto fail;
842 error = urtw_get_txpwr(sc);
843 if (error != 0)
844 goto fail;
845 error = urtw_led_init(sc);
846 if (error != 0)
847 goto fail;
848
849 URTW_UNLOCK(sc);
850
851 sc->sc_rts_retry = URTW_DEFAULT_RTS_RETRY;
852 sc->sc_tx_retry = URTW_DEFAULT_TX_RETRY;
853 sc->sc_currate = 3;
854 sc->sc_preamble_mode = urtw_preamble_mode;
855
856 ifp = sc->sc_ifp = if_alloc(IFT_IEEE80211);
857 if (ifp == NULL) {
858 device_printf(sc->sc_dev, "can not allocate ifnet\n");
859 ret = ENOMEM;
860 goto fail1;
861 }
862
863 ifp->if_softc = sc;
864 if_initname(ifp, "urtw", device_get_unit(sc->sc_dev));
865 ifp->if_flags = IFF_BROADCAST | IFF_SIMPLEX | IFF_MULTICAST;
866 ifp->if_init = urtw_init;
867 ifp->if_ioctl = urtw_ioctl;
868 ifp->if_start = urtw_start;
869 /* XXX URTW_TX_DATA_LIST_COUNT */
870 IFQ_SET_MAXLEN(&ifp->if_snd, IFQ_MAXLEN);
871 ifp->if_snd.ifq_drv_maxlen = IFQ_MAXLEN;
872 IFQ_SET_READY(&ifp->if_snd);
873
874 ic = ifp->if_l2com;
875 ic->ic_ifp = ifp;
876 ic->ic_phytype = IEEE80211_T_OFDM; /* not only, but not used */
877 ic->ic_opmode = IEEE80211_M_STA; /* default to BSS mode */
878
879 /* set device capabilities */
880 ic->ic_caps =
881 IEEE80211_C_STA | /* station mode */
882 IEEE80211_C_MONITOR | /* monitor mode supported */
883 IEEE80211_C_TXPMGT | /* tx power management */
884 IEEE80211_C_SHPREAMBLE | /* short preamble supported */
885 IEEE80211_C_SHSLOT | /* short slot time supported */
886 IEEE80211_C_BGSCAN | /* capable of bg scanning */
887 IEEE80211_C_WPA; /* 802.11i */
888
889 bands = 0;
890 setbit(&bands, IEEE80211_MODE_11B);
891 setbit(&bands, IEEE80211_MODE_11G);
892 ieee80211_init_channels(ic, NULL, &bands);
893
894 ieee80211_ifattach(ic, sc->sc_bssid);
895 ic->ic_raw_xmit = urtw_raw_xmit;
896 ic->ic_scan_start = urtw_scan_start;
897 ic->ic_scan_end = urtw_scan_end;
898 ic->ic_set_channel = urtw_set_channel;
899 ic->ic_updateslot = urtw_updateslot;
900 ic->ic_vap_create = urtw_vap_create;
901 ic->ic_vap_delete = urtw_vap_delete;
902 ic->ic_update_mcast = urtw_update_mcast;
903
904 ieee80211_radiotap_attach(ic,
905 &sc->sc_txtap.wt_ihdr, sizeof(sc->sc_txtap),
906 URTW_TX_RADIOTAP_PRESENT,
907 &sc->sc_rxtap.wr_ihdr, sizeof(sc->sc_rxtap),
908 URTW_RX_RADIOTAP_PRESENT);
909
910 urtw_sysctl_node(sc);
911
912 if (bootverbose)
913 ieee80211_announce(ic);
914 return (0);
915
916fail: URTW_UNLOCK(sc);
917fail1: usbd_transfer_unsetup(sc->sc_xfer, (sc->sc_flags & URTW_RTL8187B) ?
918 URTW_8187B_N_XFERS : URTW_8187L_N_XFERS);
919fail0:
920 return (ret);
921}
922
923static int
924urtw_detach(device_t dev)
925{
926 struct urtw_softc *sc = device_get_softc(dev);
927 struct ifnet *ifp = sc->sc_ifp;
928 struct ieee80211com *ic = ifp->if_l2com;
929
930 if (!device_is_attached(dev))
931 return (0);
932
933 urtw_stop(ifp, 1);
934 ieee80211_draintask(ic, &sc->sc_updateslot_task);
935 ieee80211_draintask(ic, &sc->sc_led_task);
936
937 usb_callout_drain(&sc->sc_led_ch);
938 callout_drain(&sc->sc_watchdog_ch);
939
940 usbd_transfer_unsetup(sc->sc_xfer, (sc->sc_flags & URTW_RTL8187B) ?
941 URTW_8187B_N_XFERS : URTW_8187L_N_XFERS);
942 ieee80211_ifdetach(ic);
943
944 urtw_free_tx_data_list(sc);
945 urtw_free_rx_data_list(sc);
946
947 if_free(ifp);
948 mtx_destroy(&sc->sc_mtx);
949
950 return (0);
951}
952
953static void
954urtw_free_tx_data_list(struct urtw_softc *sc)
955{
956
957 urtw_free_data_list(sc, sc->sc_tx, URTW_TX_DATA_LIST_COUNT, 0);
958}
959
960static void
961urtw_free_rx_data_list(struct urtw_softc *sc)
962{
963
964 urtw_free_data_list(sc, sc->sc_rx, URTW_RX_DATA_LIST_COUNT, 1);
965}
966
967static void
968urtw_free_data_list(struct urtw_softc *sc, struct urtw_data data[], int ndata,
969 int fillmbuf)
970{
971 int i;
972
973 for (i = 0; i < ndata; i++) {
974 struct urtw_data *dp = &data[i];
975
976 if (fillmbuf == 1) {
977 if (dp->m != NULL) {
978 m_freem(dp->m);
979 dp->m = NULL;
980 dp->buf = NULL;
981 }
982 } else {
983 if (dp->buf != NULL) {
984 free(dp->buf, M_USBDEV);
985 dp->buf = NULL;
986 }
987 }
988 if (dp->ni != NULL) {
989 ieee80211_free_node(dp->ni);
990 dp->ni = NULL;
991 }
992 }
993}
994
995static struct ieee80211vap *
996urtw_vap_create(struct ieee80211com *ic,
997 const char name[IFNAMSIZ], int unit, int opmode, int flags,
998 const uint8_t bssid[IEEE80211_ADDR_LEN],
999 const uint8_t mac[IEEE80211_ADDR_LEN])
1000{
1001 struct urtw_vap *uvp;
1002 struct ieee80211vap *vap;
1003
1004 if (!TAILQ_EMPTY(&ic->ic_vaps)) /* only one at a time */
1005 return (NULL);
1006 uvp = (struct urtw_vap *) malloc(sizeof(struct urtw_vap),
1007 M_80211_VAP, M_NOWAIT | M_ZERO);
1008 if (uvp == NULL)
1009 return (NULL);
1010 vap = &uvp->vap;
1011 /* enable s/w bmiss handling for sta mode */
1012 ieee80211_vap_setup(ic, vap, name, unit, opmode,
1013 flags | IEEE80211_CLONE_NOBEACONS, bssid, mac);
1014
1015 /* override state transition machine */
1016 uvp->newstate = vap->iv_newstate;
1017 vap->iv_newstate = urtw_newstate;
1018
1019 /* complete setup */
1020 ieee80211_vap_attach(vap, ieee80211_media_change,
1021 ieee80211_media_status);
1022 ic->ic_opmode = opmode;
1023 return (vap);
1024}
1025
1026static void
1027urtw_vap_delete(struct ieee80211vap *vap)
1028{
1029 struct urtw_vap *uvp = URTW_VAP(vap);
1030
1031 ieee80211_vap_detach(vap);
1032 free(uvp, M_80211_VAP);
1033}
1034
1035static void
1036urtw_init_locked(void *arg)
1037{
1038 int ret;
1039 struct urtw_softc *sc = arg;
1040 struct ifnet *ifp = sc->sc_ifp;
1041 usb_error_t error;
1042
1043 if (ifp->if_drv_flags & IFF_DRV_RUNNING)
1044 urtw_stop_locked(ifp, 0);
1045
1046 error = (sc->sc_flags & URTW_RTL8187B) ? urtw_adapter_start_b(sc) :
1047 urtw_adapter_start(sc);
1048 if (error != 0)
1049 goto fail;
1050
1051 /* reset softc variables */
1052 sc->sc_txtimer = 0;
1053
1054 if (!(sc->sc_flags & URTW_INIT_ONCE)) {
1055 ret = urtw_alloc_rx_data_list(sc);
1056 if (error != 0)
1057 goto fail;
1058 ret = urtw_alloc_tx_data_list(sc);
1059 if (error != 0)
1060 goto fail;
1061 sc->sc_flags |= URTW_INIT_ONCE;
1062 }
1063
1064 error = urtw_rx_enable(sc);
1065 if (error != 0)
1066 goto fail;
1067 error = urtw_tx_enable(sc);
1068 if (error != 0)
1069 goto fail;
1070
1071 if (sc->sc_flags & URTW_RTL8187B)
1072 usbd_transfer_start(sc->sc_xfer[URTW_8187B_BULK_TX_STATUS]);
1073
1074 ifp->if_drv_flags &= ~IFF_DRV_OACTIVE;
1075 ifp->if_drv_flags |= IFF_DRV_RUNNING;
1076
1077 callout_reset(&sc->sc_watchdog_ch, hz, urtw_watchdog, sc);
1078fail:
1079 return;
1080}
1081
1082static void
1083urtw_init(void *arg)
1084{
1085 struct urtw_softc *sc = arg;
1086
1087 URTW_LOCK(sc);
1088 urtw_init_locked(arg);
1089 URTW_UNLOCK(sc);
1090}
1091
1092static usb_error_t
1093urtw_adapter_start_b(struct urtw_softc *sc)
1094{
1095#define N(a) (sizeof(a) / sizeof((a)[0]))
1096 uint8_t data8;
1097 usb_error_t error;
1098
1099 error = urtw_set_mode(sc, URTW_EPROM_CMD_CONFIG);
1100 if (error)
1101 goto fail;
1102
1103 urtw_read8_m(sc, URTW_CONFIG3, &data8);
1104 urtw_write8_m(sc, URTW_CONFIG3,
1105 data8 | URTW_CONFIG3_ANAPARAM_WRITE | URTW_CONFIG3_GNT_SELECT);
1106 urtw_write32_m(sc, URTW_ANAPARAM2, URTW_8187B_8225_ANAPARAM2_ON);
1107 urtw_write32_m(sc, URTW_ANAPARAM, URTW_8187B_8225_ANAPARAM_ON);
1108 urtw_write8_m(sc, URTW_ANAPARAM3, URTW_8187B_8225_ANAPARAM3_ON);
1109
1110 urtw_write8_m(sc, 0x61, 0x10);
1111 urtw_read8_m(sc, 0x62, &data8);
1112 urtw_write8_m(sc, 0x62, data8 & ~(1 << 5));
1113 urtw_write8_m(sc, 0x62, data8 | (1 << 5));
1114
1115 urtw_read8_m(sc, URTW_CONFIG3, &data8);
1116 data8 &= ~URTW_CONFIG3_ANAPARAM_WRITE;
1117 urtw_write8_m(sc, URTW_CONFIG3, data8);
1118
1119 error = urtw_set_mode(sc, URTW_EPROM_CMD_NORMAL);
1120 if (error)
1121 goto fail;
1122
1123 error = urtw_8187b_cmd_reset(sc);
1124 if (error)
1125 goto fail;
1126
1127 error = sc->sc_rf_init(sc);
1128 if (error != 0)
1129 goto fail;
1130 urtw_write8_m(sc, URTW_CMD, URTW_CMD_RX_ENABLE | URTW_CMD_TX_ENABLE);
1131
1132 /* fix RTL8187B RX stall */
1133 error = urtw_intr_enable(sc);
1134 if (error)
1135 goto fail;
1136
1137 error = urtw_write8e(sc, 0x41, 0xf4);
1138 if (error)
1139 goto fail;
1140 error = urtw_write8e(sc, 0x40, 0x00);
1141 if (error)
1142 goto fail;
1143 error = urtw_write8e(sc, 0x42, 0x00);
1144 if (error)
1145 goto fail;
1146 error = urtw_write8e(sc, 0x42, 0x01);
1147 if (error)
1148 goto fail;
1149 error = urtw_write8e(sc, 0x40, 0x0f);
1150 if (error)
1151 goto fail;
1152 error = urtw_write8e(sc, 0x42, 0x00);
1153 if (error)
1154 goto fail;
1155 error = urtw_write8e(sc, 0x42, 0x01);
1156 if (error)
1157 goto fail;
1158
1159 urtw_read8_m(sc, 0xdb, &data8);
1160 urtw_write8_m(sc, 0xdb, data8 | (1 << 2));
1161 urtw_write16_m(sc, 0x372, 0x59fa);
1162 urtw_write16_m(sc, 0x374, 0x59d2);
1163 urtw_write16_m(sc, 0x376, 0x59d2);
1164 urtw_write16_m(sc, 0x378, 0x19fa);
1165 urtw_write16_m(sc, 0x37a, 0x19fa);
1166 urtw_write16_m(sc, 0x37c, 0x00d0);
1167 urtw_write8_m(sc, 0x61, 0);
1168
1169 urtw_write8_m(sc, 0x180, 0x0f);
1170 urtw_write8_m(sc, 0x183, 0x03);
1171 urtw_write8_m(sc, 0xda, 0x10);
1172 urtw_write8_m(sc, 0x24d, 0x08);
1173 urtw_write32_m(sc, URTW_HSSI_PARA, 0x0600321b);
1174
1175 urtw_write16_m(sc, 0x1ec, 0x800); /* RX MAX SIZE */
1176fail:
1177 return (error);
1178#undef N
1179}
1180
1181static usb_error_t
1182urtw_adapter_start(struct urtw_softc *sc)
1183{
1184 usb_error_t error;
1185
1186 error = urtw_reset(sc);
1187 if (error)
1188 goto fail;
1189
1190 urtw_write8_m(sc, URTW_ADDR_MAGIC1, 0);
1191 urtw_write8_m(sc, URTW_GPIO, 0);
1192
1193 /* for led */
1194 urtw_write8_m(sc, URTW_ADDR_MAGIC1, 4);
1195 error = urtw_led_ctl(sc, URTW_LED_CTL_POWER_ON);
1196 if (error != 0)
1197 goto fail;
1198
1199 error = urtw_set_mode(sc, URTW_EPROM_CMD_CONFIG);
1200 if (error)
1201 goto fail;
1202 /* applying MAC address again. */
1203 urtw_write32_m(sc, URTW_MAC0, ((uint32_t *)sc->sc_bssid)[0]);
1204 urtw_write16_m(sc, URTW_MAC4, ((uint32_t *)sc->sc_bssid)[1] & 0xffff);
1205 error = urtw_set_mode(sc, URTW_EPROM_CMD_NORMAL);
1206 if (error)
1207 goto fail;
1208
1209 error = urtw_update_msr(sc);
1210 if (error)
1211 goto fail;
1212
1213 urtw_write32_m(sc, URTW_INT_TIMEOUT, 0);
1214 urtw_write8_m(sc, URTW_WPA_CONFIG, 0);
1215 urtw_write8_m(sc, URTW_RATE_FALLBACK, URTW_RATE_FALLBACK_ENABLE | 0x1);
1216 error = urtw_set_rate(sc);
1217 if (error != 0)
1218 goto fail;
1219
1220 error = sc->sc_rf_init(sc);
1221 if (error != 0)
1222 goto fail;
1223 if (sc->sc_rf_set_sens != NULL)
1224 sc->sc_rf_set_sens(sc, sc->sc_sens);
1225
1226 /* XXX correct? to call write16 */
1227 urtw_write16_m(sc, URTW_PSR, 1);
1228 urtw_write16_m(sc, URTW_ADDR_MAGIC2, 0x10);
1229 urtw_write8_m(sc, URTW_TALLY_SEL, 0x80);
1230 urtw_write8_m(sc, URTW_ADDR_MAGIC3, 0x60);
1231 /* XXX correct? to call write16 */
1232 urtw_write16_m(sc, URTW_PSR, 0);
1233 urtw_write8_m(sc, URTW_ADDR_MAGIC1, 4);
1234
1235 error = urtw_intr_enable(sc);
1236 if (error != 0)
1237 goto fail;
1238
1239fail:
1240 return (error);
1241}
1242
1243static usb_error_t
1244urtw_set_mode(struct urtw_softc *sc, uint32_t mode)
1245{
1246 uint8_t data;
1247 usb_error_t error;
1248
1249 urtw_read8_m(sc, URTW_EPROM_CMD, &data);
1250 data = (data & ~URTW_EPROM_CMD_MASK) | (mode << URTW_EPROM_CMD_SHIFT);
1251 data = data & ~(URTW_EPROM_CS | URTW_EPROM_CK);
1252 urtw_write8_m(sc, URTW_EPROM_CMD, data);
1253fail:
1254 return (error);
1255}
1256
1257static usb_error_t
1258urtw_8187b_cmd_reset(struct urtw_softc *sc)
1259{
1260 int i;
1261 uint8_t data8;
1262 usb_error_t error;
1263
1264 /* XXX the code can be duplicate with urtw_reset(). */
1265 urtw_read8_m(sc, URTW_CMD, &data8);
1266 data8 = (data8 & 0x2) | URTW_CMD_RST;
1267 urtw_write8_m(sc, URTW_CMD, data8);
1268
1269 for (i = 0; i < 20; i++) {
1270 usb_pause_mtx(&sc->sc_mtx, 2);
1271 urtw_read8_m(sc, URTW_CMD, &data8);
1272 if (!(data8 & URTW_CMD_RST))
1273 break;
1274 }
1275 if (i >= 20) {
1276 device_printf(sc->sc_dev, "reset timeout\n");
1277 goto fail;
1278 }
1279fail:
1280 return (error);
1281}
1282
1283static usb_error_t
1284urtw_do_request(struct urtw_softc *sc,
1285 struct usb_device_request *req, void *data)
1286{
1287 usb_error_t err;
1288 int ntries = 10;
1289
1290 URTW_ASSERT_LOCKED(sc);
1291
1292 while (ntries--) {
1293 err = usbd_do_request_flags(sc->sc_udev, &sc->sc_mtx,
1294 req, data, 0, NULL, 250 /* ms */);
1295 if (err == 0)
1296 break;
1297
1298 DPRINTF(sc, URTW_DEBUG_INIT,
1299 "Control request failed, %s (retrying)\n",
1300 usbd_errstr(err));
1301 usb_pause_mtx(&sc->sc_mtx, hz / 100);
1302 }
1303 return (err);
1304}
1305
1306static void
1307urtw_stop_locked(struct ifnet *ifp, int disable)
1308{
1309 struct urtw_softc *sc = ifp->if_softc;
1310 uint8_t data8;
1311 usb_error_t error;
1312
1313 (void)disable;
1314 ifp->if_drv_flags &= ~(IFF_DRV_RUNNING | IFF_DRV_OACTIVE);
1315
1316 error = urtw_intr_disable(sc);
1317 if (error)
1318 goto fail;
1319 urtw_read8_m(sc, URTW_CMD, &data8);
1320 data8 &= ~(URTW_CMD_RX_ENABLE | URTW_CMD_TX_ENABLE);
1321 urtw_write8_m(sc, URTW_CMD, data8);
1322
1323 error = sc->sc_rf_stop(sc);
1324 if (error != 0)
1325 goto fail;
1326
1327 error = urtw_set_mode(sc, URTW_EPROM_CMD_CONFIG);
1328 if (error)
1329 goto fail;
1330 urtw_read8_m(sc, URTW_CONFIG4, &data8);
1331 urtw_write8_m(sc, URTW_CONFIG4, data8 | URTW_CONFIG4_VCOOFF);
1332 error = urtw_set_mode(sc, URTW_EPROM_CMD_NORMAL);
1333 if (error)
1334 goto fail;
1335fail:
1336 if (error)
1337 device_printf(sc->sc_dev, "failed to stop (%s)\n",
1338 usbd_errstr(error));
1339
1340 usb_callout_stop(&sc->sc_led_ch);
1341 callout_stop(&sc->sc_watchdog_ch);
1342
1343 urtw_abort_xfers(sc);
1344}
1345
1346static void
1347urtw_stop(struct ifnet *ifp, int disable)
1348{
1349 struct urtw_softc *sc = ifp->if_softc;
1350
1351 URTW_LOCK(sc);
1352 urtw_stop_locked(ifp, disable);
1353 URTW_UNLOCK(sc);
1354}
1355
1356static void
1357urtw_abort_xfers(struct urtw_softc *sc)
1358{
1359 int i, max;
1360
1361 URTW_ASSERT_LOCKED(sc);
1362
1363 max = (sc->sc_flags & URTW_RTL8187B) ? URTW_8187B_N_XFERS :
1364 URTW_8187L_N_XFERS;
1365
1366 /* abort any pending transfers */
1367 for (i = 0; i < max; i++)
1368 usbd_transfer_stop(sc->sc_xfer[i]);
1369}
1370
1371static int
1372urtw_ioctl(struct ifnet *ifp, u_long cmd, caddr_t data)
1373{
1374 struct urtw_softc *sc = ifp->if_softc;
1375 struct ieee80211com *ic = ifp->if_l2com;
1376 struct ifreq *ifr = (struct ifreq *) data;
1377 int error = 0, startall = 0;
1378
1379 switch (cmd) {
1380 case SIOCSIFFLAGS:
1381 if (ifp->if_flags & IFF_UP) {
1382 if (ifp->if_drv_flags & IFF_DRV_RUNNING) {
1383 if ((ifp->if_flags ^ sc->sc_if_flags) &
1384 (IFF_ALLMULTI | IFF_PROMISC))
1385 urtw_set_multi(sc);
1386 } else {
1387 urtw_init(ifp->if_softc);
1388 startall = 1;
1389 }
1390 } else {
1391 if (ifp->if_drv_flags & IFF_DRV_RUNNING)
1392 urtw_stop(ifp, 1);
1393 }
1394 sc->sc_if_flags = ifp->if_flags;
1395 if (startall)
1396 ieee80211_start_all(ic);
1397 break;
1398 case SIOCGIFMEDIA:
1399 error = ifmedia_ioctl(ifp, ifr, &ic->ic_media, cmd);
1400 break;
1401 case SIOCGIFADDR:
1402 error = ether_ioctl(ifp, cmd, data);
1403 break;
1404 default:
1405 error = EINVAL;
1406 break;
1407 }
1408
1409 return (error);
1410}
1411
1412static void
1413urtw_start(struct ifnet *ifp)
1414{
1415 struct urtw_data *bf;
1416 struct urtw_softc *sc = ifp->if_softc;
1417 struct ieee80211_node *ni;
1418 struct mbuf *m;
1419
1420 if ((ifp->if_drv_flags & IFF_DRV_RUNNING) == 0)
1421 return;
1422
1423 URTW_LOCK(sc);
1424 for (;;) {
1425 IFQ_DRV_DEQUEUE(&ifp->if_snd, m);
1426 if (m == NULL)
1427 break;
1428 bf = urtw_getbuf(sc);
1429 if (bf == NULL) {
1430 IFQ_DRV_PREPEND(&ifp->if_snd, m);
1431 break;
1432 }
1433
1434 ni = (struct ieee80211_node *)m->m_pkthdr.rcvif;
1435 m->m_pkthdr.rcvif = NULL;
1436
1437 if (urtw_tx_start(sc, ni, m, bf, URTW_PRIORITY_NORMAL) != 0) {
1438 ifp->if_oerrors++;
1439 STAILQ_INSERT_HEAD(&sc->sc_tx_inactive, bf, next);
1440 ieee80211_free_node(ni);
1441 break;
1442 }
1443
1444 sc->sc_txtimer = 5;
1445 callout_reset(&sc->sc_watchdog_ch, hz, urtw_watchdog, sc);
1446 }
1447 URTW_UNLOCK(sc);
1448}
1449
1450static int
1451urtw_alloc_data_list(struct urtw_softc *sc, struct urtw_data data[],
1452 int ndata, int maxsz, int fillmbuf)
1453{
1454 int i, error;
1455
1456 for (i = 0; i < ndata; i++) {
1457 struct urtw_data *dp = &data[i];
1458
1459 dp->sc = sc;
1460 if (fillmbuf) {
1461 dp->m = m_getcl(M_DONTWAIT, MT_DATA, M_PKTHDR);
1462 if (dp->m == NULL) {
1463 device_printf(sc->sc_dev,
1464 "could not allocate rx mbuf\n");
1465 error = ENOMEM;
1466 goto fail;
1467 }
1468 dp->buf = mtod(dp->m, uint8_t *);
1469 } else {
1470 dp->m = NULL;
1471 dp->buf = malloc(maxsz, M_USBDEV, M_NOWAIT);
1472 if (dp->buf == NULL) {
1473 device_printf(sc->sc_dev,
1474 "could not allocate buffer\n");
1475 error = ENOMEM;
1476 goto fail;
1477 }
1478 if (((unsigned long)dp->buf) % 4)
1479 device_printf(sc->sc_dev,
1480 "warn: unaligned buffer %p\n", dp->buf);
1481 }
1482 dp->ni = NULL;
1483 }
1484
1485 return 0;
1486
1487fail: urtw_free_data_list(sc, data, ndata, fillmbuf);
1488 return error;
1489}
1490
1491static int
1492urtw_alloc_rx_data_list(struct urtw_softc *sc)
1493{
1494 int error, i;
1495
1496 error = urtw_alloc_data_list(sc,
1497 sc->sc_rx, URTW_RX_DATA_LIST_COUNT, MCLBYTES, 1 /* mbufs */);
1498 if (error != 0)
1499 return (error);
1500
1501 STAILQ_INIT(&sc->sc_rx_active);
1502 STAILQ_INIT(&sc->sc_rx_inactive);
1503
1504 for (i = 0; i < URTW_RX_DATA_LIST_COUNT; i++)
1505 STAILQ_INSERT_HEAD(&sc->sc_rx_inactive, &sc->sc_rx[i], next);
1506
1507 return (0);
1508}
1509
1510static int
1511urtw_alloc_tx_data_list(struct urtw_softc *sc)
1512{
1513 int error, i;
1514
1515 error = urtw_alloc_data_list(sc,
1516 sc->sc_tx, URTW_TX_DATA_LIST_COUNT, URTW_TX_MAXSIZE,
1517 0 /* no mbufs */);
1518 if (error != 0)
1519 return (error);
1520
1521 STAILQ_INIT(&sc->sc_tx_active);
1522 STAILQ_INIT(&sc->sc_tx_inactive);
1523 STAILQ_INIT(&sc->sc_tx_pending);
1524
1525 for (i = 0; i < URTW_TX_DATA_LIST_COUNT; i++)
1526 STAILQ_INSERT_HEAD(&sc->sc_tx_inactive, &sc->sc_tx[i],
1527 next);
1528
1529 return (0);
1530}
1531
1532static int
1533urtw_raw_xmit(struct ieee80211_node *ni, struct mbuf *m,
1534 const struct ieee80211_bpf_params *params)
1535{
1536 struct ieee80211com *ic = ni->ni_ic;
1537 struct ifnet *ifp = ic->ic_ifp;
1538 struct urtw_data *bf;
1539 struct urtw_softc *sc = ifp->if_softc;
1540
1541 /* prevent management frames from being sent if we're not ready */
1542 if (!(ifp->if_drv_flags & IFF_DRV_RUNNING)) {
1543 m_freem(m);
1544 ieee80211_free_node(ni);
1545 return ENETDOWN;
1546 }
1547 URTW_LOCK(sc);
1548 bf = urtw_getbuf(sc);
1549 if (bf == NULL) {
1550 ieee80211_free_node(ni);
1551 m_freem(m);
1552 URTW_UNLOCK(sc);
1553 return (ENOBUFS); /* XXX */
1554 }
1555
1556 ifp->if_opackets++;
1557 if (urtw_tx_start(sc, ni, m, bf, URTW_PRIORITY_LOW) != 0) {
1558 ieee80211_free_node(ni);
1559 ifp->if_oerrors++;
1560 STAILQ_INSERT_HEAD(&sc->sc_tx_inactive, bf, next);
1561 URTW_UNLOCK(sc);
1562 return (EIO);
1563 }
1564 URTW_UNLOCK(sc);
1565
1566 sc->sc_txtimer = 5;
1567 return (0);
1568}
1569
1570static void
1571urtw_scan_start(struct ieee80211com *ic)
1572{
1573
1574 /* XXX do nothing? */
1575}
1576
1577static void
1578urtw_scan_end(struct ieee80211com *ic)
1579{
1580
1581 /* XXX do nothing? */
1582}
1583
1584static void
1585urtw_set_channel(struct ieee80211com *ic)
1586{
1587 struct urtw_softc *sc = ic->ic_ifp->if_softc;
1588 struct ifnet *ifp = sc->sc_ifp;
1589 uint32_t data, orig;
1590 usb_error_t error;
1591
1592 /*
1593 * if the user set a channel explicitly using ifconfig(8) this function
1594 * can be called earlier than we're expected that in some cases the
1595 * initialization would be failed if setting a channel is called before
1596 * the init have done.
1597 */
1598 if (!(ifp->if_drv_flags & IFF_DRV_RUNNING))
1599 return;
1600
1601 if (sc->sc_curchan != NULL && sc->sc_curchan == ic->ic_curchan)
1602 return;
1603
1604 URTW_LOCK(sc);
1605
1606 /*
1607 * during changing th channel we need to temporarily be disable
1608 * TX.
1609 */
1610 urtw_read32_m(sc, URTW_TX_CONF, &orig);
1611 data = orig & ~URTW_TX_LOOPBACK_MASK;
1612 urtw_write32_m(sc, URTW_TX_CONF, data | URTW_TX_LOOPBACK_MAC);
1613
1614 error = sc->sc_rf_set_chan(sc, ieee80211_chan2ieee(ic, ic->ic_curchan));
1615 if (error != 0)
1616 goto fail;
1617 usb_pause_mtx(&sc->sc_mtx, 10);
1618 urtw_write32_m(sc, URTW_TX_CONF, orig);
1619
1620 urtw_write16_m(sc, URTW_ATIM_WND, 2);
1621 urtw_write16_m(sc, URTW_ATIM_TR_ITV, 100);
1622 urtw_write16_m(sc, URTW_BEACON_INTERVAL, 100);
1623 urtw_write16_m(sc, URTW_BEACON_INTERVAL_TIME, 100);
1624
1625fail:
1626 URTW_UNLOCK(sc);
1627
1628 sc->sc_curchan = ic->ic_curchan;
1629
1630 if (error != 0)
1631 device_printf(sc->sc_dev, "could not change the channel\n");
1632}
1633
1634static void
1635urtw_update_mcast(struct ifnet *ifp)
1636{
1637
1638 /* XXX do nothing? */
1639}
1640
1641static int
1642urtw_tx_start(struct urtw_softc *sc, struct ieee80211_node *ni, struct mbuf *m0,
1643 struct urtw_data *data, int prior)
1644{
1645 struct ifnet *ifp = sc->sc_ifp;
1646 struct ieee80211_frame *wh = mtod(m0, struct ieee80211_frame *);
1647 struct ieee80211_key *k;
1648 const struct ieee80211_txparam *tp;
1649 struct ieee80211com *ic = ifp->if_l2com;
1650 struct ieee80211vap *vap = ni->ni_vap;
1651 struct usb_xfer *rtl8187b_pipes[URTW_8187B_TXPIPE_MAX] = {
1652 sc->sc_xfer[URTW_8187B_BULK_TX_BE],
1653 sc->sc_xfer[URTW_8187B_BULK_TX_BK],
1654 sc->sc_xfer[URTW_8187B_BULK_TX_VI],
1655 sc->sc_xfer[URTW_8187B_BULK_TX_VO]
1656 };
1657 struct usb_xfer *xfer;
1658 int dur = 0, rtsdur = 0, rtsenable = 0, ctsenable = 0, rate,
1659 pkttime = 0, txdur = 0, isshort = 0, xferlen;
1660 uint16_t acktime, rtstime, ctstime;
1661 uint32_t flags;
1662 usb_error_t error;
1663
1664 URTW_ASSERT_LOCKED(sc);
1665
1666 /*
1667 * Software crypto.
1668 */
1669 if (wh->i_fc[1] & IEEE80211_FC1_WEP) {
1670 k = ieee80211_crypto_encap(ni, m0);
1671 if (k == NULL) {
1672 device_printf(sc->sc_dev,
1673 "ieee80211_crypto_encap returns NULL.\n");
1674 /* XXX we don't expect the fragmented frames */
1675 m_freem(m0);
1676 return (ENOBUFS);
1677 }
1678
1679 /* in case packet header moved, reset pointer */
1680 wh = mtod(m0, struct ieee80211_frame *);
1681 }
1682
1683 if (ieee80211_radiotap_active_vap(vap)) {
1684 struct urtw_tx_radiotap_header *tap = &sc->sc_txtap;
1685
1686 /* XXX Are variables correct? */
1687 tap->wt_flags = 0;
1688 tap->wt_chan_freq = htole16(ic->ic_curchan->ic_freq);
1689 tap->wt_chan_flags = htole16(ic->ic_curchan->ic_flags);
1690
1691 ieee80211_radiotap_tx(vap, m0);
1692 }
1693
1694 if ((wh->i_fc[0] & IEEE80211_FC0_TYPE_MASK) == IEEE80211_FC0_TYPE_MGT ||
1695 (wh->i_fc[0] & IEEE80211_FC0_TYPE_MASK) == IEEE80211_FC0_TYPE_CTL) {
1696 tp = &vap->iv_txparms[ieee80211_chan2mode(ic->ic_curchan)];
1697 rate = tp->mgmtrate;
1698 } else {
1699 tp = &vap->iv_txparms[ieee80211_chan2mode(ni->ni_chan)];
1700 /* for data frames */
1701 if (IEEE80211_IS_MULTICAST(wh->i_addr1))
1702 rate = tp->mcastrate;
1703 else if (tp->ucastrate != IEEE80211_FIXED_RATE_NONE)
1704 rate = tp->ucastrate;
1705 else
1706 rate = urtw_rtl2rate(sc->sc_currate);
1707 }
1708
1709 sc->sc_stats.txrates[sc->sc_currate]++;
1710
1711 if (IEEE80211_IS_MULTICAST(wh->i_addr1))
1712 txdur = pkttime = urtw_compute_txtime(m0->m_pkthdr.len +
1713 IEEE80211_CRC_LEN, rate, 0, 0);
1714 else {
1715 acktime = urtw_compute_txtime(14, 2,0, 0);
1716 if ((m0->m_pkthdr.len + 4) > vap->iv_rtsthreshold) {
1717 rtsenable = 1;
1718 ctsenable = 0;
1719 rtstime = urtw_compute_txtime(URTW_ACKCTS_LEN, 2, 0, 0);
1720 ctstime = urtw_compute_txtime(14, 2, 0, 0);
1721 pkttime = urtw_compute_txtime(m0->m_pkthdr.len +
1722 IEEE80211_CRC_LEN, rate, 0, isshort);
1723 rtsdur = ctstime + pkttime + acktime +
1724 3 * URTW_ASIFS_TIME;
1725 txdur = rtstime + rtsdur;
1726 } else {
1727 rtsenable = ctsenable = rtsdur = 0;
1728 pkttime = urtw_compute_txtime(m0->m_pkthdr.len +
1729 IEEE80211_CRC_LEN, rate, 0, isshort);
1730 txdur = pkttime + URTW_ASIFS_TIME + acktime;
1731 }
1732
1733 if (wh->i_fc[1] & IEEE80211_FC1_MORE_FRAG)
1734 dur = urtw_compute_txtime(m0->m_pkthdr.len +
1735 IEEE80211_CRC_LEN, rate, 0, isshort) +
1736 3 * URTW_ASIFS_TIME +
1737 2 * acktime;
1738 else
1739 dur = URTW_ASIFS_TIME + acktime;
1740 }
1741 *(uint16_t *)wh->i_dur = htole16(dur);
1742
1743 xferlen = m0->m_pkthdr.len;
1744 xferlen += (sc->sc_flags & URTW_RTL8187B) ? (4 * 8) : (4 * 3);
1745 if ((0 == xferlen % 64) || (0 == xferlen % 512))
1746 xferlen += 1;
1747
1748 bzero(data->buf, URTW_TX_MAXSIZE);
1749 flags = m0->m_pkthdr.len & 0xfff;
1750 flags |= URTW_TX_FLAG_NO_ENC;
1751 if ((ic->ic_flags & IEEE80211_F_SHPREAMBLE) &&
1752 (ni->ni_capinfo & IEEE80211_CAPINFO_SHORT_PREAMBLE) &&
1753 (sc->sc_preamble_mode == URTW_PREAMBLE_MODE_SHORT) &&
1754 (sc->sc_currate != 0))
1755 flags |= URTW_TX_FLAG_SPLCP;
1756 if (wh->i_fc[1] & IEEE80211_FC1_MORE_FRAG)
1757 flags |= URTW_TX_FLAG_MOREFRAG;
1758
1759 flags |= (sc->sc_currate & 0xf) << URTW_TX_FLAG_TXRATE_SHIFT;
1760
1761 if (sc->sc_flags & URTW_RTL8187B) {
1762 struct urtw_8187b_txhdr *tx;
1763
1764 tx = (struct urtw_8187b_txhdr *)data->buf;
1765 if (ctsenable)
1766 flags |= URTW_TX_FLAG_CTS;
1767 if (rtsenable) {
1768 flags |= URTW_TX_FLAG_RTS;
1769 flags |= (urtw_rate2rtl(11) & 0xf) <<
1770 URTW_TX_FLAG_RTSRATE_SHIFT;
1771 tx->rtsdur = rtsdur;
1772 }
1773 tx->flag = htole32(flags);
1774 tx->txdur = txdur;
1775 if ((wh->i_fc[0] & IEEE80211_FC0_TYPE_MASK) ==
1776 IEEE80211_FC0_TYPE_MGT &&
1777 (wh->i_fc[0] & IEEE80211_FC0_SUBTYPE_MASK) ==
1778 IEEE80211_FC0_SUBTYPE_PROBE_RESP)
1779 tx->retry = 1;
1780 else
1781 tx->retry = URTW_TX_MAXRETRY;
1782 m_copydata(m0, 0, m0->m_pkthdr.len, (uint8_t *)(tx + 1));
1783 } else {
1784 struct urtw_8187l_txhdr *tx;
1785
1786 tx = (struct urtw_8187l_txhdr *)data->buf;
1787 if (rtsenable) {
1788 flags |= URTW_TX_FLAG_RTS;
1789 tx->rtsdur = rtsdur;
1790 }
1791 flags |= (urtw_rate2rtl(11) & 0xf) << URTW_TX_FLAG_RTSRATE_SHIFT;
1792 tx->flag = htole32(flags);
1793 tx->retry = 3; /* CW minimum */
1794 tx->retry = 7 << 4; /* CW maximum */
1795 tx->retry = URTW_TX_MAXRETRY << 8; /* retry limitation */
1796 m_copydata(m0, 0, m0->m_pkthdr.len, (uint8_t *)(tx + 1));
1797 }
1798
1799 data->buflen = xferlen;
1800 data->ni = ni;
1801 data->m = m0;
1802
1803 if (sc->sc_flags & URTW_RTL8187B) {
1804 switch (wh->i_fc[0] & IEEE80211_FC0_TYPE_MASK) {
1805 case IEEE80211_FC0_TYPE_CTL:
1806 case IEEE80211_FC0_TYPE_MGT:
1807 xfer = sc->sc_xfer[URTW_8187B_BULK_TX_EP12];
1808 break;
1809 default:
1810 KASSERT(M_WME_GETAC(m0) < URTW_8187B_TXPIPE_MAX,
1811 ("unsupported WME pipe %d", M_WME_GETAC(m0)));
1812 xfer = rtl8187b_pipes[M_WME_GETAC(m0)];
1813 break;
1814 }
1815 } else
1816 xfer = (prior == URTW_PRIORITY_LOW) ?
1817 sc->sc_xfer[URTW_8187L_BULK_TX_LOW] :
1818 sc->sc_xfer[URTW_8187L_BULK_TX_NORMAL];
1819
1820 STAILQ_INSERT_TAIL(&sc->sc_tx_pending, data, next);
1821 usbd_transfer_start(xfer);
1822
1823 error = urtw_led_ctl(sc, URTW_LED_CTL_TX);
1824 if (error != 0)
1825 device_printf(sc->sc_dev, "could not control LED (%d)\n",
1826 error);
1827 return (0);
1828}
1829
1830static int
1831urtw_newstate(struct ieee80211vap *vap, enum ieee80211_state nstate, int arg)
1832{
1833 struct ieee80211_node *ni = vap->iv_bss;
1834 struct ieee80211com *ic = vap->iv_ic;
1835 struct urtw_softc *sc = ic->ic_ifp->if_softc;
1836 struct urtw_vap *uvp = URTW_VAP(vap);
1837 usb_error_t error = 0;
1838
1839 DPRINTF(sc, URTW_DEBUG_STATE, "%s: %s -> %s\n", __func__,
1840 ieee80211_state_name[vap->iv_state],
1841 ieee80211_state_name[nstate]);
1842
1843 sc->sc_state = nstate;
1844
1845 IEEE80211_UNLOCK(ic);
1846 URTW_LOCK(sc);
1847 usb_callout_stop(&sc->sc_led_ch);
1848 callout_stop(&sc->sc_watchdog_ch);
1849
1850 switch (nstate) {
1851 case IEEE80211_S_INIT:
1852 case IEEE80211_S_SCAN:
1853 case IEEE80211_S_AUTH:
1854 case IEEE80211_S_ASSOC:
1855 break;
1856 case IEEE80211_S_RUN:
1857 /* setting bssid. */
1858 urtw_write32_m(sc, URTW_BSSID, ((uint32_t *)ni->ni_bssid)[0]);
1859 urtw_write16_m(sc, URTW_BSSID + 4,
1860 ((uint16_t *)ni->ni_bssid)[2]);
1861 urtw_update_msr(sc);
1862 /* XXX maybe the below would be incorrect. */
1863 urtw_write16_m(sc, URTW_ATIM_WND, 2);
1864 urtw_write16_m(sc, URTW_ATIM_TR_ITV, 100);
1865 urtw_write16_m(sc, URTW_BEACON_INTERVAL, 0x64);
1866 urtw_write16_m(sc, URTW_BEACON_INTERVAL_TIME, 100);
1867 error = urtw_led_ctl(sc, URTW_LED_CTL_LINK);
1868 if (error != 0)
1869 device_printf(sc->sc_dev,
1870 "could not control LED (%d)\n", error);
1871 break;
1872 default:
1873 break;
1874 }
1875fail:
1876 URTW_UNLOCK(sc);
1877 IEEE80211_LOCK(ic);
1878 return (uvp->newstate(vap, nstate, arg));
1879}
1880
1881static void
1882urtw_watchdog(void *arg)
1883{
1884 struct urtw_softc *sc = arg;
1885 struct ifnet *ifp = sc->sc_ifp;
1886
1887 if (sc->sc_txtimer > 0) {
1888 if (--sc->sc_txtimer == 0) {
1889 device_printf(sc->sc_dev, "device timeout\n");
1890 ifp->if_oerrors++;
1891 return;
1892 }
1893 callout_reset(&sc->sc_watchdog_ch, hz, urtw_watchdog, sc);
1894 }
1895}
1896
1897static void
1898urtw_set_multi(void *arg)
1899{
1900 struct urtw_softc *sc = arg;
1901 struct ifnet *ifp = sc->sc_ifp;
1902
1903 if (!(ifp->if_flags & IFF_UP))
1904 return;
1905
1906 /*
1907 * XXX don't know how to set a device. Lack of docs. Just try to set
1908 * IFF_ALLMULTI flag here.
1909 */
1910 ifp->if_flags |= IFF_ALLMULTI;
1911}
1912
1913static usb_error_t
1914urtw_set_rate(struct urtw_softc *sc)
1915{
1916 int i, basic_rate, min_rr_rate, max_rr_rate;
1917 uint16_t data;
1918 usb_error_t error;
1919
1920 basic_rate = urtw_rate2rtl(48);
1921 min_rr_rate = urtw_rate2rtl(12);
1922 max_rr_rate = urtw_rate2rtl(48);
1923
1924 urtw_write8_m(sc, URTW_RESP_RATE,
1925 max_rr_rate << URTW_RESP_MAX_RATE_SHIFT |
1926 min_rr_rate << URTW_RESP_MIN_RATE_SHIFT);
1927
1928 urtw_read16_m(sc, URTW_BRSR, &data);
1929 data &= ~URTW_BRSR_MBR_8185;
1930
1931 for (i = 0; i <= basic_rate; i++)
1932 data |= (1 << i);
1933
1934 urtw_write16_m(sc, URTW_BRSR, data);
1935fail:
1936 return (error);
1937}
1938
1939static uint16_t
1940urtw_rate2rtl(int rate)
1941{
1942#define N(a) (sizeof(a) / sizeof((a)[0]))
1943 int i;
1944
1945 for (i = 0; i < N(urtw_ratetable); i++) {
1946 if (rate == urtw_ratetable[i].reg)
1947 return urtw_ratetable[i].val;
1948 }
1949
1950 return (3);
1951#undef N
1952}
1953
1954static uint16_t
1955urtw_rtl2rate(int rate)
1956{
1957#define N(a) (sizeof(a) / sizeof((a)[0]))
1958 int i;
1959
1960 for (i = 0; i < N(urtw_ratetable); i++) {
1961 if (rate == urtw_ratetable[i].val)
1962 return urtw_ratetable[i].reg;
1963 }
1964
1965 return (0);
1966#undef N
1967}
1968
1969static usb_error_t
1970urtw_update_msr(struct urtw_softc *sc)
1971{
1972 struct ifnet *ifp = sc->sc_ifp;
1973 struct ieee80211com *ic = ifp->if_l2com;
1974 uint8_t data;
1975 usb_error_t error;
1976
1977 urtw_read8_m(sc, URTW_MSR, &data);
1978 data &= ~URTW_MSR_LINK_MASK;
1979
1980 if (sc->sc_state == IEEE80211_S_RUN) {
1981 switch (ic->ic_opmode) {
1982 case IEEE80211_M_STA:
1983 case IEEE80211_M_MONITOR:
1984 data |= URTW_MSR_LINK_STA;
1985 if (sc->sc_flags & URTW_RTL8187B)
1986 data |= URTW_MSR_LINK_ENEDCA;
1987 break;
1988 case IEEE80211_M_IBSS:
1989 data |= URTW_MSR_LINK_ADHOC;
1990 break;
1991 case IEEE80211_M_HOSTAP:
1992 data |= URTW_MSR_LINK_HOSTAP;
1993 break;
1994 default:
1995 panic("unsupported operation mode 0x%x\n",
1996 ic->ic_opmode);
1997 /* never reach */
1998 }
1999 } else
2000 data |= URTW_MSR_LINK_NONE;
2001
2002 urtw_write8_m(sc, URTW_MSR, data);
2003fail:
2004 return (error);
2005}
2006
2007static usb_error_t
2008urtw_read8_c(struct urtw_softc *sc, int val, uint8_t *data)
2009{
2010 struct usb_device_request req;
2011 usb_error_t error;
2012
2013 URTW_ASSERT_LOCKED(sc);
2014
2015 req.bmRequestType = UT_READ_VENDOR_DEVICE;
2016 req.bRequest = URTW_8187_GETREGS_REQ;
2017 USETW(req.wValue, (val & 0xff) | 0xff00);
2018 USETW(req.wIndex, (val >> 8) & 0x3);
2019 USETW(req.wLength, sizeof(uint8_t));
2020
2021 error = urtw_do_request(sc, &req, data);
2022 return (error);
2023}
2024
2025static usb_error_t
2026urtw_read16_c(struct urtw_softc *sc, int val, uint16_t *data)
2027{
2028 struct usb_device_request req;
2029 usb_error_t error;
2030
2031 URTW_ASSERT_LOCKED(sc);
2032
2033 req.bmRequestType = UT_READ_VENDOR_DEVICE;
2034 req.bRequest = URTW_8187_GETREGS_REQ;
2035 USETW(req.wValue, (val & 0xff) | 0xff00);
2036 USETW(req.wIndex, (val >> 8) & 0x3);
2037 USETW(req.wLength, sizeof(uint16_t));
2038
2039 error = urtw_do_request(sc, &req, data);
2040 return (error);
2041}
2042
2043static usb_error_t
2044urtw_read32_c(struct urtw_softc *sc, int val, uint32_t *data)
2045{
2046 struct usb_device_request req;
2047 usb_error_t error;
2048
2049 URTW_ASSERT_LOCKED(sc);
2050
2051 req.bmRequestType = UT_READ_VENDOR_DEVICE;
2052 req.bRequest = URTW_8187_GETREGS_REQ;
2053 USETW(req.wValue, (val & 0xff) | 0xff00);
2054 USETW(req.wIndex, (val >> 8) & 0x3);
2055 USETW(req.wLength, sizeof(uint32_t));
2056
2057 error = urtw_do_request(sc, &req, data);
2058 return (error);
2059}
2060
2061static usb_error_t
2062urtw_write8_c(struct urtw_softc *sc, int val, uint8_t data)
2063{
2064 struct usb_device_request req;
2065
2066 URTW_ASSERT_LOCKED(sc);
2067
2068 req.bmRequestType = UT_WRITE_VENDOR_DEVICE;
2069 req.bRequest = URTW_8187_SETREGS_REQ;
2070 USETW(req.wValue, (val & 0xff) | 0xff00);
2071 USETW(req.wIndex, (val >> 8) & 0x3);
2072 USETW(req.wLength, sizeof(uint8_t));
2073
2074 return (urtw_do_request(sc, &req, &data));
2075}
2076
2077static usb_error_t
2078urtw_write16_c(struct urtw_softc *sc, int val, uint16_t data)
2079{
2080 struct usb_device_request req;
2081
2082 URTW_ASSERT_LOCKED(sc);
2083
2084 req.bmRequestType = UT_WRITE_VENDOR_DEVICE;
2085 req.bRequest = URTW_8187_SETREGS_REQ;
2086 USETW(req.wValue, (val & 0xff) | 0xff00);
2087 USETW(req.wIndex, (val >> 8) & 0x3);
2088 USETW(req.wLength, sizeof(uint16_t));
2089
2090 return (urtw_do_request(sc, &req, &data));
2091}
2092
2093static usb_error_t
2094urtw_write32_c(struct urtw_softc *sc, int val, uint32_t data)
2095{
2096 struct usb_device_request req;
2097
2098 URTW_ASSERT_LOCKED(sc);
2099
2100 req.bmRequestType = UT_WRITE_VENDOR_DEVICE;
2101 req.bRequest = URTW_8187_SETREGS_REQ;
2102 USETW(req.wValue, (val & 0xff) | 0xff00);
2103 USETW(req.wIndex, (val >> 8) & 0x3);
2104 USETW(req.wLength, sizeof(uint32_t));
2105
2106 return (urtw_do_request(sc, &req, &data));
2107}
2108
2109static usb_error_t
2110urtw_get_macaddr(struct urtw_softc *sc)
2111{
2112 uint32_t data;
2113 usb_error_t error;
2114
2115 error = urtw_eprom_read32(sc, URTW_EPROM_MACADDR, &data);
2116 if (error != 0)
2117 goto fail;
2118 sc->sc_bssid[0] = data & 0xff;
2119 sc->sc_bssid[1] = (data & 0xff00) >> 8;
2120 error = urtw_eprom_read32(sc, URTW_EPROM_MACADDR + 1, &data);
2121 if (error != 0)
2122 goto fail;
2123 sc->sc_bssid[2] = data & 0xff;
2124 sc->sc_bssid[3] = (data & 0xff00) >> 8;
2125 error = urtw_eprom_read32(sc, URTW_EPROM_MACADDR + 2, &data);
2126 if (error != 0)
2127 goto fail;
2128 sc->sc_bssid[4] = data & 0xff;
2129 sc->sc_bssid[5] = (data & 0xff00) >> 8;
2130fail:
2131 return (error);
2132}
2133
2134static usb_error_t
2135urtw_eprom_read32(struct urtw_softc *sc, uint32_t addr, uint32_t *data)
2136{
2137#define URTW_READCMD_LEN 3
2138 int addrlen, i;
2139 int16_t addrstr[8], data16, readcmd[] = { 1, 1, 0 };
2140 usb_error_t error;
2141
2142 /* NB: make sure the buffer is initialized */
2143 *data = 0;
2144
2145 /* enable EPROM programming */
2146 urtw_write8_m(sc, URTW_EPROM_CMD, URTW_EPROM_CMD_PROGRAM_MODE);
2147 DELAY(URTW_EPROM_DELAY);
2148
2149 error = urtw_eprom_cs(sc, URTW_EPROM_ENABLE);
2150 if (error != 0)
2151 goto fail;
2152 error = urtw_eprom_ck(sc);
2153 if (error != 0)
2154 goto fail;
2155 error = urtw_eprom_sendbits(sc, readcmd, URTW_READCMD_LEN);
2156 if (error != 0)
2157 goto fail;
2158 if (sc->sc_epromtype == URTW_EEPROM_93C56) {
2159 addrlen = 8;
2160 addrstr[0] = addr & (1 << 7);
2161 addrstr[1] = addr & (1 << 6);
2162 addrstr[2] = addr & (1 << 5);
2163 addrstr[3] = addr & (1 << 4);
2164 addrstr[4] = addr & (1 << 3);
2165 addrstr[5] = addr & (1 << 2);
2166 addrstr[6] = addr & (1 << 1);
2167 addrstr[7] = addr & (1 << 0);
2168 } else {
2169 addrlen=6;
2170 addrstr[0] = addr & (1 << 5);
2171 addrstr[1] = addr & (1 << 4);
2172 addrstr[2] = addr & (1 << 3);
2173 addrstr[3] = addr & (1 << 2);
2174 addrstr[4] = addr & (1 << 1);
2175 addrstr[5] = addr & (1 << 0);
2176 }
2177 error = urtw_eprom_sendbits(sc, addrstr, addrlen);
2178 if (error != 0)
2179 goto fail;
2180
2181 error = urtw_eprom_writebit(sc, 0);
2182 if (error != 0)
2183 goto fail;
2184
2185 for (i = 0; i < 16; i++) {
2186 error = urtw_eprom_ck(sc);
2187 if (error != 0)
2188 goto fail;
2189 error = urtw_eprom_readbit(sc, &data16);
2190 if (error != 0)
2191 goto fail;
2192
2193 (*data) |= (data16 << (15 - i));
2194 }
2195
2196 error = urtw_eprom_cs(sc, URTW_EPROM_DISABLE);
2197 if (error != 0)
2198 goto fail;
2199 error = urtw_eprom_ck(sc);
2200 if (error != 0)
2201 goto fail;
2202
2203 /* now disable EPROM programming */
2204 urtw_write8_m(sc, URTW_EPROM_CMD, URTW_EPROM_CMD_NORMAL_MODE);
2205fail:
2206 return (error);
2207#undef URTW_READCMD_LEN
2208}
2209
2210static usb_error_t
2211urtw_eprom_cs(struct urtw_softc *sc, int able)
2212{
2213 uint8_t data;
2214 usb_error_t error;
2215
2216 urtw_read8_m(sc, URTW_EPROM_CMD, &data);
2217 if (able == URTW_EPROM_ENABLE)
2218 urtw_write8_m(sc, URTW_EPROM_CMD, data | URTW_EPROM_CS);
2219 else
2220 urtw_write8_m(sc, URTW_EPROM_CMD, data & ~URTW_EPROM_CS);
2221 DELAY(URTW_EPROM_DELAY);
2222fail:
2223 return (error);
2224}
2225
2226static usb_error_t
2227urtw_eprom_ck(struct urtw_softc *sc)
2228{
2229 uint8_t data;
2230 usb_error_t error;
2231
2232 /* masking */
2233 urtw_read8_m(sc, URTW_EPROM_CMD, &data);
2234 urtw_write8_m(sc, URTW_EPROM_CMD, data | URTW_EPROM_CK);
2235 DELAY(URTW_EPROM_DELAY);
2236 /* unmasking */
2237 urtw_read8_m(sc, URTW_EPROM_CMD, &data);
2238 urtw_write8_m(sc, URTW_EPROM_CMD, data & ~URTW_EPROM_CK);
2239 DELAY(URTW_EPROM_DELAY);
2240fail:
2241 return (error);
2242}
2243
2244static usb_error_t
2245urtw_eprom_readbit(struct urtw_softc *sc, int16_t *data)
2246{
2247 uint8_t data8;
2248 usb_error_t error;
2249
2250 urtw_read8_m(sc, URTW_EPROM_CMD, &data8);
2251 *data = (data8 & URTW_EPROM_READBIT) ? 1 : 0;
2252 DELAY(URTW_EPROM_DELAY);
2253
2254fail:
2255 return (error);
2256}
2257
2258static usb_error_t
2259urtw_eprom_writebit(struct urtw_softc *sc, int16_t bit)
2260{
2261 uint8_t data;
2262 usb_error_t error;
2263
2264 urtw_read8_m(sc, URTW_EPROM_CMD, &data);
2265 if (bit != 0)
2266 urtw_write8_m(sc, URTW_EPROM_CMD, data | URTW_EPROM_WRITEBIT);
2267 else
2268 urtw_write8_m(sc, URTW_EPROM_CMD, data & ~URTW_EPROM_WRITEBIT);
2269 DELAY(URTW_EPROM_DELAY);
2270fail:
2271 return (error);
2272}
2273
2274static usb_error_t
2275urtw_eprom_sendbits(struct urtw_softc *sc, int16_t *buf, int buflen)
2276{
2277 int i = 0;
2278 usb_error_t error = 0;
2279
2280 for (i = 0; i < buflen; i++) {
2281 error = urtw_eprom_writebit(sc, buf[i]);
2282 if (error != 0)
2283 goto fail;
2284 error = urtw_eprom_ck(sc);
2285 if (error != 0)
2286 goto fail;
2287 }
2288fail:
2289 return (error);
2290}
2291
2292
2293static usb_error_t
2294urtw_get_txpwr(struct urtw_softc *sc)
2295{
2296 int i, j;
2297 uint32_t data;
2298 usb_error_t error;
2299
2300 error = urtw_eprom_read32(sc, URTW_EPROM_TXPW_BASE, &data);
2301 if (error != 0)
2302 goto fail;
2303 sc->sc_txpwr_cck_base = data & 0xf;
2304 sc->sc_txpwr_ofdm_base = (data >> 4) & 0xf;
2305
2306 for (i = 1, j = 0; i < 6; i += 2, j++) {
2307 error = urtw_eprom_read32(sc, URTW_EPROM_TXPW0 + j, &data);
2308 if (error != 0)
2309 goto fail;
2310 sc->sc_txpwr_cck[i] = data & 0xf;
2311 sc->sc_txpwr_cck[i + 1] = (data & 0xf00) >> 8;
2312 sc->sc_txpwr_ofdm[i] = (data & 0xf0) >> 4;
2313 sc->sc_txpwr_ofdm[i + 1] = (data & 0xf000) >> 12;
2314 }
2315 for (i = 1, j = 0; i < 4; i += 2, j++) {
2316 error = urtw_eprom_read32(sc, URTW_EPROM_TXPW1 + j, &data);
2317 if (error != 0)
2318 goto fail;
2319 sc->sc_txpwr_cck[i + 6] = data & 0xf;
2320 sc->sc_txpwr_cck[i + 6 + 1] = (data & 0xf00) >> 8;
2321 sc->sc_txpwr_ofdm[i + 6] = (data & 0xf0) >> 4;
2322 sc->sc_txpwr_ofdm[i + 6 + 1] = (data & 0xf000) >> 12;
2323 }
2324 if (sc->sc_flags & URTW_RTL8187B) {
2325 error = urtw_eprom_read32(sc, URTW_EPROM_TXPW2, &data);
2326 if (error != 0)
2327 goto fail;
2328 sc->sc_txpwr_cck[1 + 6 + 4] = data & 0xf;
2329 sc->sc_txpwr_ofdm[1 + 6 + 4] = (data & 0xf0) >> 4;
2330 error = urtw_eprom_read32(sc, 0x0a, &data);
2331 if (error != 0)
2332 goto fail;
2333 sc->sc_txpwr_cck[2 + 6 + 4] = data & 0xf;
2334 sc->sc_txpwr_ofdm[2 + 6 + 4] = (data & 0xf0) >> 4;
2335 error = urtw_eprom_read32(sc, 0x1c, &data);
2336 if (error != 0)
2337 goto fail;
2338 sc->sc_txpwr_cck[3 + 6 + 4] = data & 0xf;
2339 sc->sc_txpwr_cck[3 + 6 + 4 + 1] = (data & 0xf00) >> 8;
2340 sc->sc_txpwr_ofdm[3 + 6 + 4] = (data & 0xf0) >> 4;
2341 sc->sc_txpwr_ofdm[3 + 6 + 4 + 1] = (data & 0xf000) >> 12;
2342 } else {
2343 for (i = 1, j = 0; i < 4; i += 2, j++) {
2344 error = urtw_eprom_read32(sc, URTW_EPROM_TXPW2 + j,
2345 &data);
2346 if (error != 0)
2347 goto fail;
2348 sc->sc_txpwr_cck[i + 6 + 4] = data & 0xf;
2349 sc->sc_txpwr_cck[i + 6 + 4 + 1] = (data & 0xf00) >> 8;
2350 sc->sc_txpwr_ofdm[i + 6 + 4] = (data & 0xf0) >> 4;
2351 sc->sc_txpwr_ofdm[i + 6 + 4 + 1] = (data & 0xf000) >> 12;
2352 }
2353 }
2354fail:
2355 return (error);
2356}
2357
2358
2359static usb_error_t
2360urtw_get_rfchip(struct urtw_softc *sc)
2361{
2362 int ret;
2363 uint8_t data8;
2364 uint32_t data;
2365 usb_error_t error;
2366
2367 if (sc->sc_flags & URTW_RTL8187B) {
2368 urtw_read8_m(sc, 0xe1, &data8);
2369 switch (data8) {
2370 case 0:
2371 sc->sc_flags |= URTW_RTL8187B_REV_B;
2372 break;
2373 case 1:
2374 sc->sc_flags |= URTW_RTL8187B_REV_D;
2375 break;
2376 case 2:
2377 sc->sc_flags |= URTW_RTL8187B_REV_E;
2378 break;
2379 default:
2380 device_printf(sc->sc_dev, "unknown type: %#x\n", data8);
2381 sc->sc_flags |= URTW_RTL8187B_REV_B;
2382 break;
2383 }
2384 } else {
2385 urtw_read32_m(sc, URTW_TX_CONF, &data);
2386 switch (data & URTW_TX_HWMASK) {
2387 case URTW_TX_R8187vD_B:
2388 sc->sc_flags |= URTW_RTL8187B;
2389 break;
2390 case URTW_TX_R8187vD:
2391 break;
2392 default:
2393 device_printf(sc->sc_dev, "unknown RTL8187L type: %#x\n",
2394 data & URTW_TX_HWMASK);
2395 break;
2396 }
2397 }
2398
2399 error = urtw_eprom_read32(sc, URTW_EPROM_RFCHIPID, &data);
2400 if (error != 0)
2401 goto fail;
2402 switch (data & 0xff) {
2403 case URTW_EPROM_RFCHIPID_RTL8225U:
2404 error = urtw_8225_isv2(sc, &ret);
2405 if (error != 0)
2406 goto fail;
2407 if (ret == 0) {
2408 sc->sc_rf_init = urtw_8225_rf_init;
2409 sc->sc_rf_set_sens = urtw_8225_rf_set_sens;
2410 sc->sc_rf_set_chan = urtw_8225_rf_set_chan;
2411 sc->sc_rf_stop = urtw_8225_rf_stop;
2412 } else {
2413 sc->sc_rf_init = urtw_8225v2_rf_init;
2414 sc->sc_rf_set_chan = urtw_8225v2_rf_set_chan;
2415 sc->sc_rf_stop = urtw_8225_rf_stop;
2416 }
2417 sc->sc_max_sens = URTW_8225_RF_MAX_SENS;
2418 sc->sc_sens = URTW_8225_RF_DEF_SENS;
2419 break;
2420 case URTW_EPROM_RFCHIPID_RTL8225Z2:
2421 sc->sc_rf_init = urtw_8225v2b_rf_init;
2422 sc->sc_rf_set_chan = urtw_8225v2b_rf_set_chan;
2423 sc->sc_max_sens = URTW_8225_RF_MAX_SENS;
2424 sc->sc_sens = URTW_8225_RF_DEF_SENS;
2425 sc->sc_rf_stop = urtw_8225_rf_stop;
2426 break;
2427 default:
2428 panic("unsupported RF chip %d\n", data & 0xff);
2429 /* never reach */
2430 }
2431
2432 device_printf(sc->sc_dev, "%s rf %s hwrev %s\n",
2433 (sc->sc_flags & URTW_RTL8187B) ? "rtl8187b" : "rtl8187l",
2434 ((data & 0xff) == URTW_EPROM_RFCHIPID_RTL8225U) ? "rtl8225u" :
2435 "rtl8225z2",
2436 (sc->sc_flags & URTW_RTL8187B) ? ((data8 == 0) ? "b" :
2437 (data8 == 1) ? "d" : "e") : "none");
2438
2439fail:
2440 return (error);
2441}
2442
2443
2444static usb_error_t
2445urtw_led_init(struct urtw_softc *sc)
2446{
2447 uint32_t rev;
2448 usb_error_t error;
2449
2450 urtw_read8_m(sc, URTW_PSR, &sc->sc_psr);
2451 error = urtw_eprom_read32(sc, URTW_EPROM_SWREV, &rev);
2452 if (error != 0)
2453 goto fail;
2454
2455 switch (rev & URTW_EPROM_CID_MASK) {
2456 case URTW_EPROM_CID_ALPHA0:
2457 sc->sc_strategy = URTW_SW_LED_MODE1;
2458 break;
2459 case URTW_EPROM_CID_SERCOMM_PS:
2460 sc->sc_strategy = URTW_SW_LED_MODE3;
2461 break;
2462 case URTW_EPROM_CID_HW_LED:
2463 sc->sc_strategy = URTW_HW_LED;
2464 break;
2465 case URTW_EPROM_CID_RSVD0:
2466 case URTW_EPROM_CID_RSVD1:
2467 default:
2468 sc->sc_strategy = URTW_SW_LED_MODE0;
2469 break;
2470 }
2471
2472 sc->sc_gpio_ledpin = URTW_LED_PIN_GPIO0;
2473
2474fail:
2475 return (error);
2476}
2477
2478
2479static usb_error_t
2480urtw_8225_rf_init(struct urtw_softc *sc)
2481{
2482#define N(a) (sizeof(a) / sizeof((a)[0]))
2483 int i;
2484 uint16_t data;
2485 usb_error_t error;
2486
2487 error = urtw_8180_set_anaparam(sc, URTW_8225_ANAPARAM_ON);
2488 if (error)
2489 goto fail;
2490
2491 error = urtw_8225_usb_init(sc);
2492 if (error)
2493 goto fail;
2494
2495 urtw_write32_m(sc, URTW_RF_TIMING, 0x000a8008);
2496 urtw_read16_m(sc, URTW_BRSR, &data); /* XXX ??? */
2497 urtw_write16_m(sc, URTW_BRSR, 0xffff);
2498 urtw_write32_m(sc, URTW_RF_PARA, 0x100044);
2499
2500 error = urtw_set_mode(sc, URTW_EPROM_CMD_CONFIG);
2501 if (error)
2502 goto fail;
2503 urtw_write8_m(sc, URTW_CONFIG3, 0x44);
2504 error = urtw_set_mode(sc, URTW_EPROM_CMD_NORMAL);
2505 if (error)
2506 goto fail;
2507
2508 error = urtw_8185_rf_pins_enable(sc);
2509 if (error)
2510 goto fail;
2511 usb_pause_mtx(&sc->sc_mtx, 1000);
2512
2513 for (i = 0; i < N(urtw_8225_rf_part1); i++) {
2514 urtw_8225_write(sc, urtw_8225_rf_part1[i].reg,
2515 urtw_8225_rf_part1[i].val);
2516 usb_pause_mtx(&sc->sc_mtx, 1);
2517 }
2518 usb_pause_mtx(&sc->sc_mtx, 100);
2519 urtw_8225_write(sc,
2520 URTW_8225_ADDR_2_MAGIC, URTW_8225_ADDR_2_DATA_MAGIC1);
2521 usb_pause_mtx(&sc->sc_mtx, 200);
2522 urtw_8225_write(sc,
2523 URTW_8225_ADDR_2_MAGIC, URTW_8225_ADDR_2_DATA_MAGIC2);
2524 usb_pause_mtx(&sc->sc_mtx, 200);
2525 urtw_8225_write(sc,
2526 URTW_8225_ADDR_0_MAGIC, URTW_8225_ADDR_0_DATA_MAGIC3);
2527
2528 for (i = 0; i < 95; i++) {
2529 urtw_8225_write(sc, URTW_8225_ADDR_1_MAGIC, (uint8_t)(i + 1));
2530 urtw_8225_write(sc, URTW_8225_ADDR_2_MAGIC, urtw_8225_rxgain[i]);
2531 }
2532
2533 urtw_8225_write(sc,
2534 URTW_8225_ADDR_0_MAGIC, URTW_8225_ADDR_0_DATA_MAGIC4);
2535 urtw_8225_write(sc,
2536 URTW_8225_ADDR_0_MAGIC, URTW_8225_ADDR_0_DATA_MAGIC5);
2537
2538 for (i = 0; i < 128; i++) {
2539 urtw_8187_write_phy_ofdm(sc, 0xb, urtw_8225_agc[i]);
2540 usb_pause_mtx(&sc->sc_mtx, 1);
2541 urtw_8187_write_phy_ofdm(sc, 0xa, (uint8_t)i + 0x80);
2542 usb_pause_mtx(&sc->sc_mtx, 1);
2543 }
2544
2545 for (i = 0; i < N(urtw_8225_rf_part2); i++) {
2546 urtw_8187_write_phy_ofdm(sc, urtw_8225_rf_part2[i].reg,
2547 urtw_8225_rf_part2[i].val);
2548 usb_pause_mtx(&sc->sc_mtx, 1);
2549 }
2550
2551 error = urtw_8225_setgain(sc, 4);
2552 if (error)
2553 goto fail;
2554
2555 for (i = 0; i < N(urtw_8225_rf_part3); i++) {
2556 urtw_8187_write_phy_cck(sc, urtw_8225_rf_part3[i].reg,
2557 urtw_8225_rf_part3[i].val);
2558 usb_pause_mtx(&sc->sc_mtx, 1);
2559 }
2560
2561 urtw_write8_m(sc, URTW_TESTR, 0x0d);
2562
2563 error = urtw_8225_set_txpwrlvl(sc, 1);
2564 if (error)
2565 goto fail;
2566
2567 urtw_8187_write_phy_cck(sc, 0x10, 0x9b);
2568 usb_pause_mtx(&sc->sc_mtx, 1);
2569 urtw_8187_write_phy_ofdm(sc, 0x26, 0x90);
2570 usb_pause_mtx(&sc->sc_mtx, 1);
2571
2572 /* TX ant A, 0x0 for B */
2573 error = urtw_8185_tx_antenna(sc, 0x3);
2574 if (error)
2575 goto fail;
2576 urtw_write32_m(sc, URTW_HSSI_PARA, 0x3dc00002);
2577
2578 error = urtw_8225_rf_set_chan(sc, 1);
2579fail:
2580 return (error);
2581#undef N
2582}
2583
2584static usb_error_t
2585urtw_8185_rf_pins_enable(struct urtw_softc *sc)
2586{
2587 usb_error_t error = 0;
2588
2589 urtw_write16_m(sc, URTW_RF_PINS_ENABLE, 0x1ff7);
2590fail:
2591 return (error);
2592}
2593
2594static usb_error_t
2595urtw_8185_tx_antenna(struct urtw_softc *sc, uint8_t ant)
2596{
2597 usb_error_t error;
2598
2599 urtw_write8_m(sc, URTW_TX_ANTENNA, ant);
2600 usb_pause_mtx(&sc->sc_mtx, 1);
2601fail:
2602 return (error);
2603}
2604
2605static usb_error_t
2606urtw_8187_write_phy_ofdm_c(struct urtw_softc *sc, uint8_t addr, uint32_t data)
2607{
2608
2609 data = data & 0xff;
2610 return urtw_8187_write_phy(sc, addr, data);
2611}
2612
2613static usb_error_t
2614urtw_8187_write_phy_cck_c(struct urtw_softc *sc, uint8_t addr, uint32_t data)
2615{
2616
2617 data = data & 0xff;
2618 return urtw_8187_write_phy(sc, addr, data | 0x10000);
2619}
2620
2621static usb_error_t
2622urtw_8187_write_phy(struct urtw_softc *sc, uint8_t addr, uint32_t data)
2623{
2624 uint32_t phyw;
2625 usb_error_t error;
2626
2627 phyw = ((data << 8) | (addr | 0x80));
2628 urtw_write8_m(sc, URTW_PHY_MAGIC4, ((phyw & 0xff000000) >> 24));
2629 urtw_write8_m(sc, URTW_PHY_MAGIC3, ((phyw & 0x00ff0000) >> 16));
2630 urtw_write8_m(sc, URTW_PHY_MAGIC2, ((phyw & 0x0000ff00) >> 8));
2631 urtw_write8_m(sc, URTW_PHY_MAGIC1, ((phyw & 0x000000ff)));
2632 usb_pause_mtx(&sc->sc_mtx, 1);
2633fail:
2634 return (error);
2635}
2636
2637static usb_error_t
2638urtw_8225_setgain(struct urtw_softc *sc, int16_t gain)
2639{
2640 usb_error_t error;
2641
2642 urtw_8187_write_phy_ofdm(sc, 0x0d, urtw_8225_gain[gain * 4]);
2643 urtw_8187_write_phy_ofdm(sc, 0x1b, urtw_8225_gain[gain * 4 + 2]);
2644 urtw_8187_write_phy_ofdm(sc, 0x1d, urtw_8225_gain[gain * 4 + 3]);
2645 urtw_8187_write_phy_ofdm(sc, 0x23, urtw_8225_gain[gain * 4 + 1]);
2646fail:
2647 return (error);
2648}
2649
2650static usb_error_t
2651urtw_8225_usb_init(struct urtw_softc *sc)
2652{
2653 uint8_t data;
2654 usb_error_t error;
2655
2656 urtw_write8_m(sc, URTW_RF_PINS_SELECT + 1, 0);
2657 urtw_write8_m(sc, URTW_GPIO, 0);
2658 error = urtw_read8e(sc, 0x53, &data);
2659 if (error)
2660 goto fail;
2661 error = urtw_write8e(sc, 0x53, data | (1 << 7));
2662 if (error)
2663 goto fail;
2664 urtw_write8_m(sc, URTW_RF_PINS_SELECT + 1, 4);
2665 urtw_write8_m(sc, URTW_GPIO, 0x20);
2666 urtw_write8_m(sc, URTW_GP_ENABLE, 0);
2667
2668 urtw_write16_m(sc, URTW_RF_PINS_OUTPUT, 0x80);
2669 urtw_write16_m(sc, URTW_RF_PINS_SELECT, 0x80);
2670 urtw_write16_m(sc, URTW_RF_PINS_ENABLE, 0x80);
2671
2672 usb_pause_mtx(&sc->sc_mtx, 500);
2673fail:
2674 return (error);
2675}
2676
2677static usb_error_t
2678urtw_8225_write_c(struct urtw_softc *sc, uint8_t addr, uint16_t data)
2679{
2680 uint16_t d80, d82, d84;
2681 usb_error_t error;
2682
2683 urtw_read16_m(sc, URTW_RF_PINS_OUTPUT, &d80);
2684 d80 &= URTW_RF_PINS_MAGIC1;
2685 urtw_read16_m(sc, URTW_RF_PINS_ENABLE, &d82);
2686 urtw_read16_m(sc, URTW_RF_PINS_SELECT, &d84);
2687 d84 &= URTW_RF_PINS_MAGIC2;
2688 urtw_write16_m(sc, URTW_RF_PINS_ENABLE, d82 | URTW_RF_PINS_MAGIC3);
2689 urtw_write16_m(sc, URTW_RF_PINS_SELECT, d84 | URTW_RF_PINS_MAGIC3);
2690 DELAY(10);
2691
2692 urtw_write16_m(sc, URTW_RF_PINS_OUTPUT, d80 | URTW_BB_HOST_BANG_EN);
2693 DELAY(2);
2694 urtw_write16_m(sc, URTW_RF_PINS_OUTPUT, d80);
2695 DELAY(10);
2696
2697 error = urtw_8225_write_s16(sc, addr, 0x8225, &data);
2698 if (error != 0)
2699 goto fail;
2700
2701 urtw_write16_m(sc, URTW_RF_PINS_OUTPUT, d80 | URTW_BB_HOST_BANG_EN);
2702 DELAY(10);
2703 urtw_write16_m(sc, URTW_RF_PINS_OUTPUT, d80 | URTW_BB_HOST_BANG_EN);
2704 urtw_write16_m(sc, URTW_RF_PINS_SELECT, d84);
2705 usb_pause_mtx(&sc->sc_mtx, 2);
2706fail:
2707 return (error);
2708}
2709
2710/* XXX why we should allocalte memory buffer instead of using memory stack? */
2711static usb_error_t
2712urtw_8225_write_s16(struct urtw_softc *sc, uint8_t addr, int index,
2713 uint16_t *data)
2714{
2715 uint8_t *buf;
2716 uint16_t data16;
2717 struct usb_device_request *req;
2718 usb_error_t error = 0;
2719
2720 data16 = *data;
2721 req = (usb_device_request_t *)malloc(sizeof(usb_device_request_t),
2722 M_80211_VAP, M_NOWAIT | M_ZERO);
2723 if (req == NULL) {
2724 device_printf(sc->sc_dev, "could not allocate a memory\n");
2725 goto fail0;
2726 }
2727 buf = (uint8_t *)malloc(2, M_80211_VAP, M_NOWAIT | M_ZERO);
2728 if (req == NULL) {
2729 device_printf(sc->sc_dev, "could not allocate a memory\n");
2730 goto fail1;
2731 }
2732
2733 req->bmRequestType = UT_WRITE_VENDOR_DEVICE;
2734 req->bRequest = URTW_8187_SETREGS_REQ;
2735 USETW(req->wValue, addr);
2736 USETW(req->wIndex, index);
2737 USETW(req->wLength, sizeof(uint16_t));
2738 buf[0] = (data16 & 0x00ff);
2739 buf[1] = (data16 & 0xff00) >> 8;
2740
2741 error = urtw_do_request(sc, req, buf);
2742
2743 free(buf, M_80211_VAP);
2744fail1: free(req, M_80211_VAP);
2745fail0: return (error);
2746}
2747
2748static usb_error_t
2749urtw_8225_rf_set_chan(struct urtw_softc *sc, int chan)
2750{
2751 usb_error_t error;
2752
2753 error = urtw_8225_set_txpwrlvl(sc, chan);
2754 if (error)
2755 goto fail;
2756 urtw_8225_write(sc, URTW_8225_ADDR_7_MAGIC, urtw_8225_channel[chan]);
2757 usb_pause_mtx(&sc->sc_mtx, 10);
2758fail:
2759 return (error);
2760}
2761
2762static usb_error_t
2763urtw_8225_rf_set_sens(struct urtw_softc *sc, int sens)
2764{
2765 usb_error_t error;
2766
2767 if (sens < 0 || sens > 6)
2768 return -1;
2769
2770 if (sens > 4)
2771 urtw_8225_write(sc,
2772 URTW_8225_ADDR_C_MAGIC, URTW_8225_ADDR_C_DATA_MAGIC1);
2773 else
2774 urtw_8225_write(sc,
2775 URTW_8225_ADDR_C_MAGIC, URTW_8225_ADDR_C_DATA_MAGIC2);
2776
2777 sens = 6 - sens;
2778 error = urtw_8225_setgain(sc, sens);
2779 if (error)
2780 goto fail;
2781
2782 urtw_8187_write_phy_cck(sc, 0x41, urtw_8225_threshold[sens]);
2783
2784fail:
2785 return (error);
2786}
2787
2788static usb_error_t
2789urtw_8225_set_txpwrlvl(struct urtw_softc *sc, int chan)
2790{
2791 int i, idx, set;
2792 uint8_t *cck_pwltable;
2793 uint8_t cck_pwrlvl_max, ofdm_pwrlvl_min, ofdm_pwrlvl_max;
2794 uint8_t cck_pwrlvl = sc->sc_txpwr_cck[chan] & 0xff;
2795 uint8_t ofdm_pwrlvl = sc->sc_txpwr_ofdm[chan] & 0xff;
2796 usb_error_t error;
2797
2798 cck_pwrlvl_max = 11;
2799 ofdm_pwrlvl_max = 25; /* 12 -> 25 */
2800 ofdm_pwrlvl_min = 10;
2801
2802 /* CCK power setting */
2803 cck_pwrlvl = (cck_pwrlvl > cck_pwrlvl_max) ? cck_pwrlvl_max : cck_pwrlvl;
2804 idx = cck_pwrlvl % 6;
2805 set = cck_pwrlvl / 6;
2806 cck_pwltable = (chan == 14) ? urtw_8225_txpwr_cck_ch14 :
2807 urtw_8225_txpwr_cck;
2808
2809 urtw_write8_m(sc, URTW_TX_GAIN_CCK,
2810 urtw_8225_tx_gain_cck_ofdm[set] >> 1);
2811 for (i = 0; i < 8; i++) {
2812 urtw_8187_write_phy_cck(sc, 0x44 + i,
2813 cck_pwltable[idx * 8 + i]);
2814 }
2815 usb_pause_mtx(&sc->sc_mtx, 1);
2816
2817 /* OFDM power setting */
2818 ofdm_pwrlvl = (ofdm_pwrlvl > (ofdm_pwrlvl_max - ofdm_pwrlvl_min)) ?
2819 ofdm_pwrlvl_max : ofdm_pwrlvl + ofdm_pwrlvl_min;
2820 ofdm_pwrlvl = (ofdm_pwrlvl > 35) ? 35 : ofdm_pwrlvl;
2821
2822 idx = ofdm_pwrlvl % 6;
2823 set = ofdm_pwrlvl / 6;
2824
2825 error = urtw_8185_set_anaparam2(sc, URTW_8225_ANAPARAM2_ON);
2826 if (error)
2827 goto fail;
2828 urtw_8187_write_phy_ofdm(sc, 2, 0x42);
2829 urtw_8187_write_phy_ofdm(sc, 6, 0);
2830 urtw_8187_write_phy_ofdm(sc, 8, 0);
2831
2832 urtw_write8_m(sc, URTW_TX_GAIN_OFDM,
2833 urtw_8225_tx_gain_cck_ofdm[set] >> 1);
2834 urtw_8187_write_phy_ofdm(sc, 0x5, urtw_8225_txpwr_ofdm[idx]);
2835 urtw_8187_write_phy_ofdm(sc, 0x7, urtw_8225_txpwr_ofdm[idx]);
2836 usb_pause_mtx(&sc->sc_mtx, 1);
2837fail:
2838 return (error);
2839}
2840
2841
2842static usb_error_t
2843urtw_8225_rf_stop(struct urtw_softc *sc)
2844{
2845 uint8_t data;
2846 usb_error_t error;
2847
2848 urtw_8225_write(sc, 0x4, 0x1f);
2849
2850 error = urtw_set_mode(sc, URTW_EPROM_CMD_CONFIG);
2851 if (error)
2852 goto fail;
2853
2854 urtw_read8_m(sc, URTW_CONFIG3, &data);
2855 urtw_write8_m(sc, URTW_CONFIG3, data | URTW_CONFIG3_ANAPARAM_WRITE);
2856 if (sc->sc_flags & URTW_RTL8187B) {
2857 urtw_write32_m(sc, URTW_ANAPARAM2,
2858 URTW_8187B_8225_ANAPARAM2_OFF);
2859 urtw_write32_m(sc, URTW_ANAPARAM, URTW_8187B_8225_ANAPARAM_OFF);
2860 urtw_write32_m(sc, URTW_ANAPARAM3,
2861 URTW_8187B_8225_ANAPARAM3_OFF);
2862 } else {
2863 urtw_write32_m(sc, URTW_ANAPARAM2, URTW_8225_ANAPARAM2_OFF);
2864 urtw_write32_m(sc, URTW_ANAPARAM, URTW_8225_ANAPARAM_OFF);
2865 }
2866
2867 urtw_write8_m(sc, URTW_CONFIG3, data & ~URTW_CONFIG3_ANAPARAM_WRITE);
2868 error = urtw_set_mode(sc, URTW_EPROM_CMD_NORMAL);
2869 if (error)
2870 goto fail;
2871
2872fail:
2873 return (error);
2874}
2875
2876static usb_error_t
2877urtw_8225v2_rf_init(struct urtw_softc *sc)
2878{
2879#define N(a) (sizeof(a) / sizeof((a)[0]))
2880 int i;
2881 uint16_t data;
2882 uint32_t data32;
2883 usb_error_t error;
2884
2885 error = urtw_8180_set_anaparam(sc, URTW_8225_ANAPARAM_ON);
2886 if (error)
2887 goto fail;
2888
2889 error = urtw_8225_usb_init(sc);
2890 if (error)
2891 goto fail;
2892
2893 urtw_write32_m(sc, URTW_RF_TIMING, 0x000a8008);
2894 urtw_read16_m(sc, URTW_BRSR, &data); /* XXX ??? */
2895 urtw_write16_m(sc, URTW_BRSR, 0xffff);
2896 urtw_write32_m(sc, URTW_RF_PARA, 0x100044);
2897
2898 error = urtw_set_mode(sc, URTW_EPROM_CMD_CONFIG);
2899 if (error)
2900 goto fail;
2901 urtw_write8_m(sc, URTW_CONFIG3, 0x44);
2902 error = urtw_set_mode(sc, URTW_EPROM_CMD_NORMAL);
2903 if (error)
2904 goto fail;
2905
2906 error = urtw_8185_rf_pins_enable(sc);
2907 if (error)
2908 goto fail;
2909
2910 usb_pause_mtx(&sc->sc_mtx, 500);
2911
2912 for (i = 0; i < N(urtw_8225v2_rf_part1); i++) {
2913 urtw_8225_write(sc, urtw_8225v2_rf_part1[i].reg,
2914 urtw_8225v2_rf_part1[i].val);
2915 }
2916 usb_pause_mtx(&sc->sc_mtx, 50);
2917
2918 urtw_8225_write(sc,
2919 URTW_8225_ADDR_0_MAGIC, URTW_8225_ADDR_0_DATA_MAGIC1);
2920
2921 for (i = 0; i < 95; i++) {
2922 urtw_8225_write(sc, URTW_8225_ADDR_1_MAGIC, (uint8_t)(i + 1));
2923 urtw_8225_write(sc, URTW_8225_ADDR_2_MAGIC,
2924 urtw_8225v2_rxgain[i]);
2925 }
2926
2927 urtw_8225_write(sc,
2928 URTW_8225_ADDR_3_MAGIC, URTW_8225_ADDR_3_DATA_MAGIC1);
2929 urtw_8225_write(sc,
2930 URTW_8225_ADDR_5_MAGIC, URTW_8225_ADDR_5_DATA_MAGIC1);
2931 urtw_8225_write(sc,
2932 URTW_8225_ADDR_0_MAGIC, URTW_8225_ADDR_0_DATA_MAGIC2);
2933 urtw_8225_write(sc,
2934 URTW_8225_ADDR_2_MAGIC, URTW_8225_ADDR_2_DATA_MAGIC1);
2935 usb_pause_mtx(&sc->sc_mtx, 100);
2936 urtw_8225_write(sc,
2937 URTW_8225_ADDR_2_MAGIC, URTW_8225_ADDR_2_DATA_MAGIC2);
2938 usb_pause_mtx(&sc->sc_mtx, 100);
2939
2940 error = urtw_8225_read(sc, URTW_8225_ADDR_6_MAGIC, &data32);
2941 if (error != 0)
2942 goto fail;
2943 if (data32 != URTW_8225_ADDR_6_DATA_MAGIC1)
2944 device_printf(sc->sc_dev, "expect 0xe6!! (0x%x)\n", data32);
2945 if (!(data32 & URTW_8225_ADDR_6_DATA_MAGIC2)) {
2946 urtw_8225_write(sc,
2947 URTW_8225_ADDR_2_MAGIC, URTW_8225_ADDR_2_DATA_MAGIC1);
2948 usb_pause_mtx(&sc->sc_mtx, 100);
2949 urtw_8225_write(sc,
2950 URTW_8225_ADDR_2_MAGIC, URTW_8225_ADDR_2_DATA_MAGIC2);
2951 usb_pause_mtx(&sc->sc_mtx, 50);
2952 error = urtw_8225_read(sc, URTW_8225_ADDR_6_MAGIC, &data32);
2953 if (error != 0)
2954 goto fail;
2955 if (!(data32 & URTW_8225_ADDR_6_DATA_MAGIC2))
2956 device_printf(sc->sc_dev, "RF calibration failed\n");
2957 }
2958 usb_pause_mtx(&sc->sc_mtx, 100);
2959
2960 urtw_8225_write(sc,
2961 URTW_8225_ADDR_0_MAGIC, URTW_8225_ADDR_0_DATA_MAGIC6);
2962 for (i = 0; i < 128; i++) {
2963 urtw_8187_write_phy_ofdm(sc, 0xb, urtw_8225_agc[i]);
2964 urtw_8187_write_phy_ofdm(sc, 0xa, (uint8_t)i + 0x80);
2965 }
2966
2967 for (i = 0; i < N(urtw_8225v2_rf_part2); i++) {
2968 urtw_8187_write_phy_ofdm(sc, urtw_8225v2_rf_part2[i].reg,
2969 urtw_8225v2_rf_part2[i].val);
2970 }
2971
2972 error = urtw_8225v2_setgain(sc, 4);
2973 if (error)
2974 goto fail;
2975
2976 for (i = 0; i < N(urtw_8225v2_rf_part3); i++) {
2977 urtw_8187_write_phy_cck(sc, urtw_8225v2_rf_part3[i].reg,
2978 urtw_8225v2_rf_part3[i].val);
2979 }
2980
2981 urtw_write8_m(sc, URTW_TESTR, 0x0d);
2982
2983 error = urtw_8225v2_set_txpwrlvl(sc, 1);
2984 if (error)
2985 goto fail;
2986
2987 urtw_8187_write_phy_cck(sc, 0x10, 0x9b);
2988 urtw_8187_write_phy_ofdm(sc, 0x26, 0x90);
2989
2990 /* TX ant A, 0x0 for B */
2991 error = urtw_8185_tx_antenna(sc, 0x3);
2992 if (error)
2993 goto fail;
2994 urtw_write32_m(sc, URTW_HSSI_PARA, 0x3dc00002);
2995
2996 error = urtw_8225_rf_set_chan(sc, 1);
2997fail:
2998 return (error);
2999#undef N
3000}
3001
3002static usb_error_t
3003urtw_8225v2_rf_set_chan(struct urtw_softc *sc, int chan)
3004{
3005 usb_error_t error;
3006
3007 error = urtw_8225v2_set_txpwrlvl(sc, chan);
3008 if (error)
3009 goto fail;
3010
3011 urtw_8225_write(sc, URTW_8225_ADDR_7_MAGIC, urtw_8225_channel[chan]);
3012 usb_pause_mtx(&sc->sc_mtx, 10);
3013fail:
3014 return (error);
3015}
3016
3017static usb_error_t
3018urtw_8225_read(struct urtw_softc *sc, uint8_t addr, uint32_t *data)
3019{
3020 int i;
3021 int16_t bit;
3022 uint8_t rlen = 12, wlen = 6;
3023 uint16_t o1, o2, o3, tmp;
3024 uint32_t d2w = ((uint32_t)(addr & 0x1f)) << 27;
3025 uint32_t mask = 0x80000000, value = 0;
3026 usb_error_t error;
3027
3028 urtw_read16_m(sc, URTW_RF_PINS_OUTPUT, &o1);
3029 urtw_read16_m(sc, URTW_RF_PINS_ENABLE, &o2);
3030 urtw_read16_m(sc, URTW_RF_PINS_SELECT, &o3);
3031 urtw_write16_m(sc, URTW_RF_PINS_ENABLE, o2 | URTW_RF_PINS_MAGIC4);
3032 urtw_write16_m(sc, URTW_RF_PINS_SELECT, o3 | URTW_RF_PINS_MAGIC4);
3033 o1 &= ~URTW_RF_PINS_MAGIC4;
3034 urtw_write16_m(sc, URTW_RF_PINS_OUTPUT, o1 | URTW_BB_HOST_BANG_EN);
3035 DELAY(5);
3036 urtw_write16_m(sc, URTW_RF_PINS_OUTPUT, o1);
3037 DELAY(5);
3038
3039 for (i = 0; i < (wlen / 2); i++, mask = mask >> 1) {
3040 bit = ((d2w & mask) != 0) ? 1 : 0;
3041
3042 urtw_write16_m(sc, URTW_RF_PINS_OUTPUT, bit | o1);
3043 DELAY(2);
3044 urtw_write16_m(sc, URTW_RF_PINS_OUTPUT, bit | o1 |
3045 URTW_BB_HOST_BANG_CLK);
3046 DELAY(2);
3047 urtw_write16_m(sc, URTW_RF_PINS_OUTPUT, bit | o1 |
3048 URTW_BB_HOST_BANG_CLK);
3049 DELAY(2);
3050 mask = mask >> 1;
3051 if (i == 2)
3052 break;
3053 bit = ((d2w & mask) != 0) ? 1 : 0;
3054 urtw_write16_m(sc, URTW_RF_PINS_OUTPUT, bit | o1 |
3055 URTW_BB_HOST_BANG_CLK);
3056 DELAY(2);
3057 urtw_write16_m(sc, URTW_RF_PINS_OUTPUT, bit | o1 |
3058 URTW_BB_HOST_BANG_CLK);
3059 DELAY(2);
3060 urtw_write16_m(sc, URTW_RF_PINS_OUTPUT, bit | o1);
3061 DELAY(1);
3062 }
3063 urtw_write16_m(sc, URTW_RF_PINS_OUTPUT, bit | o1 | URTW_BB_HOST_BANG_RW |
3064 URTW_BB_HOST_BANG_CLK);
3065 DELAY(2);
3066 urtw_write16_m(sc, URTW_RF_PINS_OUTPUT, bit | o1 | URTW_BB_HOST_BANG_RW);
3067 DELAY(2);
3068 urtw_write16_m(sc, URTW_RF_PINS_OUTPUT, o1 | URTW_BB_HOST_BANG_RW);
3069 DELAY(2);
3070
3071 mask = 0x800;
3072 for (i = 0; i < rlen; i++, mask = mask >> 1) {
3073 urtw_write16_m(sc, URTW_RF_PINS_OUTPUT,
3074 o1 | URTW_BB_HOST_BANG_RW);
3075 DELAY(2);
3076 urtw_write16_m(sc, URTW_RF_PINS_OUTPUT,
3077 o1 | URTW_BB_HOST_BANG_RW | URTW_BB_HOST_BANG_CLK);
3078 DELAY(2);
3079 urtw_write16_m(sc, URTW_RF_PINS_OUTPUT,
3080 o1 | URTW_BB_HOST_BANG_RW | URTW_BB_HOST_BANG_CLK);
3081 DELAY(2);
3082 urtw_write16_m(sc, URTW_RF_PINS_OUTPUT,
3083 o1 | URTW_BB_HOST_BANG_RW | URTW_BB_HOST_BANG_CLK);
3084 DELAY(2);
3085
3086 urtw_read16_m(sc, URTW_RF_PINS_INPUT, &tmp);
3087 value |= ((tmp & URTW_BB_HOST_BANG_CLK) ? mask : 0);
3088 urtw_write16_m(sc, URTW_RF_PINS_OUTPUT,
3089 o1 | URTW_BB_HOST_BANG_RW);
3090 DELAY(2);
3091 }
3092
3093 urtw_write16_m(sc, URTW_RF_PINS_OUTPUT, o1 | URTW_BB_HOST_BANG_EN |
3094 URTW_BB_HOST_BANG_RW);
3095 DELAY(2);
3096
3097 urtw_write16_m(sc, URTW_RF_PINS_ENABLE, o2);
3098 urtw_write16_m(sc, URTW_RF_PINS_SELECT, o3);
3099 urtw_write16_m(sc, URTW_RF_PINS_OUTPUT, URTW_RF_PINS_OUTPUT_MAGIC1);
3100
3101 if (data != NULL)
3102 *data = value;
3103fail:
3104 return (error);
3105}
3106
3107
3108static usb_error_t
3109urtw_8225v2_set_txpwrlvl(struct urtw_softc *sc, int chan)
3110{
3111 int i;
3112 uint8_t *cck_pwrtable;
3113 uint8_t cck_pwrlvl_max = 15, ofdm_pwrlvl_max = 25, ofdm_pwrlvl_min = 10;
3114 uint8_t cck_pwrlvl = sc->sc_txpwr_cck[chan] & 0xff;
3115 uint8_t ofdm_pwrlvl = sc->sc_txpwr_ofdm[chan] & 0xff;
3116 usb_error_t error;
3117
3118 /* CCK power setting */
3119 cck_pwrlvl = (cck_pwrlvl > cck_pwrlvl_max) ? cck_pwrlvl_max : cck_pwrlvl;
3120 cck_pwrlvl += sc->sc_txpwr_cck_base;
3121 cck_pwrlvl = (cck_pwrlvl > 35) ? 35 : cck_pwrlvl;
3122 cck_pwrtable = (chan == 14) ? urtw_8225v2_txpwr_cck_ch14 :
3123 urtw_8225v2_txpwr_cck;
3124
3125 for (i = 0; i < 8; i++)
3126 urtw_8187_write_phy_cck(sc, 0x44 + i, cck_pwrtable[i]);
3127
3128 urtw_write8_m(sc, URTW_TX_GAIN_CCK,
3129 urtw_8225v2_tx_gain_cck_ofdm[cck_pwrlvl]);
3130 usb_pause_mtx(&sc->sc_mtx, 1);
3131
3132 /* OFDM power setting */
3133 ofdm_pwrlvl = (ofdm_pwrlvl > (ofdm_pwrlvl_max - ofdm_pwrlvl_min)) ?
3134 ofdm_pwrlvl_max : ofdm_pwrlvl + ofdm_pwrlvl_min;
3135 ofdm_pwrlvl += sc->sc_txpwr_ofdm_base;
3136 ofdm_pwrlvl = (ofdm_pwrlvl > 35) ? 35 : ofdm_pwrlvl;
3137
3138 error = urtw_8185_set_anaparam2(sc, URTW_8225_ANAPARAM2_ON);
3139 if (error)
3140 goto fail;
3141
3142 urtw_8187_write_phy_ofdm(sc, 2, 0x42);
3143 urtw_8187_write_phy_ofdm(sc, 5, 0x0);
3144 urtw_8187_write_phy_ofdm(sc, 6, 0x40);
3145 urtw_8187_write_phy_ofdm(sc, 7, 0x0);
3146 urtw_8187_write_phy_ofdm(sc, 8, 0x40);
3147
3148 urtw_write8_m(sc, URTW_TX_GAIN_OFDM,
3149 urtw_8225v2_tx_gain_cck_ofdm[ofdm_pwrlvl]);
3150 usb_pause_mtx(&sc->sc_mtx, 1);
3151fail:
3152 return (error);
3153}
3154
3155static usb_error_t
3156urtw_8225v2_setgain(struct urtw_softc *sc, int16_t gain)
3157{
3158 uint8_t *gainp;
3159 usb_error_t error;
3160
3161 /* XXX for A? */
3162 gainp = urtw_8225v2_gain_bg;
3163 urtw_8187_write_phy_ofdm(sc, 0x0d, gainp[gain * 3]);
3164 usb_pause_mtx(&sc->sc_mtx, 1);
3165 urtw_8187_write_phy_ofdm(sc, 0x1b, gainp[gain * 3 + 1]);
3166 usb_pause_mtx(&sc->sc_mtx, 1);
3167 urtw_8187_write_phy_ofdm(sc, 0x1d, gainp[gain * 3 + 2]);
3168 usb_pause_mtx(&sc->sc_mtx, 1);
3169 urtw_8187_write_phy_ofdm(sc, 0x21, 0x17);
3170 usb_pause_mtx(&sc->sc_mtx, 1);
3171fail:
3172 return (error);
3173}
3174
3175static usb_error_t
3176urtw_8225_isv2(struct urtw_softc *sc, int *ret)
3177{
3178 uint32_t data;
3179 usb_error_t error;
3180
3181 *ret = 1;
3182
3183 urtw_write16_m(sc, URTW_RF_PINS_OUTPUT, URTW_RF_PINS_MAGIC5);
3184 urtw_write16_m(sc, URTW_RF_PINS_SELECT, URTW_RF_PINS_MAGIC5);
3185 urtw_write16_m(sc, URTW_RF_PINS_ENABLE, URTW_RF_PINS_MAGIC5);
3186 usb_pause_mtx(&sc->sc_mtx, 500);
3187
3188 urtw_8225_write(sc, URTW_8225_ADDR_0_MAGIC,
3189 URTW_8225_ADDR_0_DATA_MAGIC1);
3190
3191 error = urtw_8225_read(sc, URTW_8225_ADDR_8_MAGIC, &data);
3192 if (error != 0)
3193 goto fail;
3194 if (data != URTW_8225_ADDR_8_DATA_MAGIC1)
3195 *ret = 0;
3196 else {
3197 error = urtw_8225_read(sc, URTW_8225_ADDR_9_MAGIC, &data);
3198 if (error != 0)
3199 goto fail;
3200 if (data != URTW_8225_ADDR_9_DATA_MAGIC1)
3201 *ret = 0;
3202 }
3203
3204 urtw_8225_write(sc, URTW_8225_ADDR_0_MAGIC,
3205 URTW_8225_ADDR_0_DATA_MAGIC2);
3206fail:
3207 return (error);
3208}
3209
3210static usb_error_t
3211urtw_8225v2b_rf_init(struct urtw_softc *sc)
3212{
3213#define N(a) (sizeof(a) / sizeof((a)[0]))
3214 int i;
3215 uint8_t data8;
3216 usb_error_t error;
3217
3218 error = urtw_set_mode(sc, URTW_EPROM_CMD_CONFIG);
3219 if (error)
3220 goto fail;
3221
3222 /*
3223 * initialize extra registers on 8187
3224 */
3225 urtw_write16_m(sc, URTW_BRSR_8187B, 0xfff);
3226
3227 /* retry limit */
3228 urtw_read8_m(sc, URTW_CW_CONF, &data8);
3229 data8 |= URTW_CW_CONF_PERPACKET_RETRY;
3230 urtw_write8_m(sc, URTW_CW_CONF, data8);
3231
3232 /* TX AGC */
3233 urtw_read8_m(sc, URTW_TX_AGC_CTL, &data8);
3234 data8 |= URTW_TX_AGC_CTL_PERPACKET_GAIN;
3235 urtw_write8_m(sc, URTW_TX_AGC_CTL, data8);
3236
3237 /* Auto Rate Fallback Control */
3238#define URTW_ARFR 0x1e0
3239 urtw_write16_m(sc, URTW_ARFR, 0xfff);
3240 urtw_read8_m(sc, URTW_RATE_FALLBACK, &data8);
3241 urtw_write8_m(sc, URTW_RATE_FALLBACK,
3242 data8 | URTW_RATE_FALLBACK_ENABLE);
3243
3244 urtw_read8_m(sc, URTW_MSR, &data8);
3245 urtw_write8_m(sc, URTW_MSR, data8 & 0xf3);
3246 urtw_read8_m(sc, URTW_MSR, &data8);
3247 urtw_write8_m(sc, URTW_MSR, data8 | URTW_MSR_LINK_ENEDCA);
3248 urtw_write8_m(sc, URTW_ACM_CONTROL, sc->sc_acmctl);
3249
3250 urtw_write16_m(sc, URTW_ATIM_WND, 2);
3251 urtw_write16_m(sc, URTW_BEACON_INTERVAL, 100);
3252#define URTW_FEMR_FOR_8187B 0x1d4
3253 urtw_write16_m(sc, URTW_FEMR_FOR_8187B, 0xffff);
3254
3255 /* led type */
3256 urtw_read8_m(sc, URTW_CONFIG1, &data8);
3257 data8 = (data8 & 0x3f) | 0x80;
3258 urtw_write8_m(sc, URTW_CONFIG1, data8);
3259
3260 /* applying MAC address again. */
3261 urtw_write32_m(sc, URTW_MAC0, ((uint32_t *)sc->sc_bssid)[0]);
3262 urtw_write16_m(sc, URTW_MAC4, ((uint32_t *)sc->sc_bssid)[1] & 0xffff);
3263
3264 error = urtw_set_mode(sc, URTW_EPROM_CMD_NORMAL);
3265 if (error)
3266 goto fail;
3267
3268 urtw_write8_m(sc, URTW_WPA_CONFIG, 0);
3269
3270 /*
3271 * MAC configuration
3272 */
3273 for (i = 0; i < N(urtw_8225v2b_rf_part1); i++)
3274 urtw_write8_m(sc, urtw_8225v2b_rf_part1[i].reg,
3275 urtw_8225v2b_rf_part1[i].val);
3276 urtw_write16_m(sc, URTW_TID_AC_MAP, 0xfa50);
3277 urtw_write16_m(sc, URTW_INT_MIG, 0x0000);
3278 urtw_write32_m(sc, 0x1f0, 0);
3279 urtw_write32_m(sc, 0x1f4, 0);
3280 urtw_write8_m(sc, 0x1f8, 0);
3281 urtw_write32_m(sc, URTW_RF_TIMING, 0x4001);
3282
3283#define URTW_RFSW_CTRL 0x272
3284 urtw_write16_m(sc, URTW_RFSW_CTRL, 0x569a);
3285
3286 /*
3287 * initialize PHY
3288 */
3289 error = urtw_set_mode(sc, URTW_EPROM_CMD_CONFIG);
3290 if (error)
3291 goto fail;
3292 urtw_read8_m(sc, URTW_CONFIG3, &data8);
3293 urtw_write8_m(sc, URTW_CONFIG3,
3294 data8 | URTW_CONFIG3_ANAPARAM_WRITE);
3295
3296 error = urtw_set_mode(sc, URTW_EPROM_CMD_NORMAL);
3297 if (error)
3298 goto fail;
3299
3300 /* setup RFE initial timing */
3301 urtw_write16_m(sc, URTW_RF_PINS_OUTPUT, 0x0480);
3302 urtw_write16_m(sc, URTW_RF_PINS_SELECT, 0x2488);
3303 urtw_write16_m(sc, URTW_RF_PINS_ENABLE, 0x1fff);
3304 usb_pause_mtx(&sc->sc_mtx, 1100);
3305
3306 for (i = 0; i < N(urtw_8225v2b_rf_part0); i++) {
3307 urtw_8225_write(sc, urtw_8225v2b_rf_part0[i].reg,
3308 urtw_8225v2b_rf_part0[i].val);
3309 usb_pause_mtx(&sc->sc_mtx, 1);
3310 }
3311 urtw_8225_write(sc, 0x00, 0x01b7);
3312
3313 for (i = 0; i < 95; i++) {
3314 urtw_8225_write(sc, URTW_8225_ADDR_1_MAGIC, (uint8_t)(i + 1));
3315 usb_pause_mtx(&sc->sc_mtx, 1);
3316 urtw_8225_write(sc, URTW_8225_ADDR_2_MAGIC,
3317 urtw_8225v2b_rxgain[i]);
3318 usb_pause_mtx(&sc->sc_mtx, 1);
3319 }
3320
3321 urtw_8225_write(sc, URTW_8225_ADDR_3_MAGIC, 0x080);
3322 usb_pause_mtx(&sc->sc_mtx, 1);
3323 urtw_8225_write(sc, URTW_8225_ADDR_5_MAGIC, 0x004);
3324 usb_pause_mtx(&sc->sc_mtx, 1);
3325 urtw_8225_write(sc, URTW_8225_ADDR_0_MAGIC, 0x0b7);
3326 usb_pause_mtx(&sc->sc_mtx, 1);
3327 usb_pause_mtx(&sc->sc_mtx, 3000);
3328 urtw_8225_write(sc, URTW_8225_ADDR_2_MAGIC, 0xc4d);
3329 usb_pause_mtx(&sc->sc_mtx, 2000);
3330 urtw_8225_write(sc, URTW_8225_ADDR_2_MAGIC, 0x44d);
3331 usb_pause_mtx(&sc->sc_mtx, 1);
3332 urtw_8225_write(sc, URTW_8225_ADDR_0_MAGIC, 0x2bf);
3333 usb_pause_mtx(&sc->sc_mtx, 1);
3334
3335 urtw_write8_m(sc, URTW_TX_GAIN_CCK, 0x03);
3336 urtw_write8_m(sc, URTW_TX_GAIN_OFDM, 0x07);
3337 urtw_write8_m(sc, URTW_TX_ANTENNA, 0x03);
3338
3339 urtw_8187_write_phy_ofdm(sc, 0x80, 0x12);
3340 for (i = 0; i < 128; i++) {
3341 uint32_t addr, data;
3342
3343 data = (urtw_8225z2_agc[i] << 8) | 0x0000008f;
3344 addr = ((i + 0x80) << 8) | 0x0000008e;
3345
3346 urtw_8187_write_phy_ofdm(sc, data & 0x7f, (data >> 8) & 0xff);
3347 urtw_8187_write_phy_ofdm(sc, addr & 0x7f, (addr >> 8) & 0xff);
3348 urtw_8187_write_phy_ofdm(sc, 0x0e, 0x00);
3349 }
3350 urtw_8187_write_phy_ofdm(sc, 0x80, 0x10);
3351
3352 for (i = 0; i < N(urtw_8225v2b_rf_part2); i++)
3353 urtw_8187_write_phy_ofdm(sc, i, urtw_8225v2b_rf_part2[i].val);
3354
3355 urtw_write32_m(sc, URTW_8187B_AC_VO, (7 << 12) | (3 << 8) | 0x1c);
3356 urtw_write32_m(sc, URTW_8187B_AC_VI, (7 << 12) | (3 << 8) | 0x1c);
3357 urtw_write32_m(sc, URTW_8187B_AC_BE, (7 << 12) | (3 << 8) | 0x1c);
3358 urtw_write32_m(sc, URTW_8187B_AC_BK, (7 << 12) | (3 << 8) | 0x1c);
3359
3360 urtw_8187_write_phy_ofdm(sc, 0x97, 0x46);
3361 urtw_8187_write_phy_ofdm(sc, 0xa4, 0xb6);
3362 urtw_8187_write_phy_ofdm(sc, 0x85, 0xfc);
3363 urtw_8187_write_phy_cck(sc, 0xc1, 0x88);
3364
3365fail:
3366 return (error);
3367#undef N
3368}
3369
3370static usb_error_t
3371urtw_8225v2b_rf_set_chan(struct urtw_softc *sc, int chan)
3372{
3373 usb_error_t error;
3374
3375 error = urtw_8225v2b_set_txpwrlvl(sc, chan);
3376 if (error)
3377 goto fail;
3378
3379 urtw_8225_write(sc, URTW_8225_ADDR_7_MAGIC, urtw_8225_channel[chan]);
3380 usb_pause_mtx(&sc->sc_mtx, 10);
3381fail:
3382 return (error);
3383}
3384
3385static usb_error_t
3386urtw_8225v2b_set_txpwrlvl(struct urtw_softc *sc, int chan)
3387{
3388 int i;
3389 uint8_t *cck_pwrtable;
3390 uint8_t cck_pwrlvl_max = 15;
3391 uint8_t cck_pwrlvl = sc->sc_txpwr_cck[chan] & 0xff;
3392 uint8_t ofdm_pwrlvl = sc->sc_txpwr_ofdm[chan] & 0xff;
3393 usb_error_t error;
3394
3395 /* CCK power setting */
3396 cck_pwrlvl = (cck_pwrlvl > cck_pwrlvl_max) ?
3397 ((sc->sc_flags & URTW_RTL8187B_REV_B) ? cck_pwrlvl_max : 22) :
3398 (cck_pwrlvl + ((sc->sc_flags & URTW_RTL8187B_REV_B) ? 0 : 7));
3399 cck_pwrlvl += sc->sc_txpwr_cck_base;
3400 cck_pwrlvl = (cck_pwrlvl > 35) ? 35 : cck_pwrlvl;
3401 cck_pwrtable = (chan == 14) ? urtw_8225v2b_txpwr_cck_ch14 :
3402 urtw_8225v2b_txpwr_cck;
3403
3404 if (sc->sc_flags & URTW_RTL8187B_REV_B)
3405 cck_pwrtable += (cck_pwrlvl <= 6) ? 0 :
3406 ((cck_pwrlvl <= 11) ? 8 : 16);
3407 else
3408 cck_pwrtable += (cck_pwrlvl <= 5) ? 0 :
3409 ((cck_pwrlvl <= 11) ? 8 : ((cck_pwrlvl <= 17) ? 16 : 24));
3410
3411 for (i = 0; i < 8; i++)
3412 urtw_8187_write_phy_cck(sc, 0x44 + i, cck_pwrtable[i]);
3413
3414 urtw_write8_m(sc, URTW_TX_GAIN_CCK,
3415 urtw_8225v2_tx_gain_cck_ofdm[cck_pwrlvl] << 1);
3416 usb_pause_mtx(&sc->sc_mtx, 1);
3417
3418 /* OFDM power setting */
3419 ofdm_pwrlvl = (ofdm_pwrlvl > 15) ?
3420 ((sc->sc_flags & URTW_RTL8187B_REV_B) ? 17 : 25) :
3421 (ofdm_pwrlvl + ((sc->sc_flags & URTW_RTL8187B_REV_B) ? 2 : 10));
3422 ofdm_pwrlvl += sc->sc_txpwr_ofdm_base;
3423 ofdm_pwrlvl = (ofdm_pwrlvl > 35) ? 35 : ofdm_pwrlvl;
3424
3425 urtw_write8_m(sc, URTW_TX_GAIN_OFDM,
3426 urtw_8225v2_tx_gain_cck_ofdm[ofdm_pwrlvl] << 1);
3427
3428 if (sc->sc_flags & URTW_RTL8187B_REV_B) {
3429 if (ofdm_pwrlvl <= 11) {
3430 urtw_8187_write_phy_ofdm(sc, 0x87, 0x60);
3431 urtw_8187_write_phy_ofdm(sc, 0x89, 0x60);
3432 } else {
3433 urtw_8187_write_phy_ofdm(sc, 0x87, 0x5c);
3434 urtw_8187_write_phy_ofdm(sc, 0x89, 0x5c);
3435 }
3436 } else {
3437 if (ofdm_pwrlvl <= 11) {
3438 urtw_8187_write_phy_ofdm(sc, 0x87, 0x5c);
3439 urtw_8187_write_phy_ofdm(sc, 0x89, 0x5c);
3440 } else if (ofdm_pwrlvl <= 17) {
3441 urtw_8187_write_phy_ofdm(sc, 0x87, 0x54);
3442 urtw_8187_write_phy_ofdm(sc, 0x89, 0x54);
3443 } else {
3444 urtw_8187_write_phy_ofdm(sc, 0x87, 0x50);
3445 urtw_8187_write_phy_ofdm(sc, 0x89, 0x50);
3446 }
3447 }
3448 usb_pause_mtx(&sc->sc_mtx, 1);
3449fail:
3450 return (error);
3451}
3452
3453static usb_error_t
3454urtw_read8e(struct urtw_softc *sc, int val, uint8_t *data)
3455{
3456 struct usb_device_request req;
3457 usb_error_t error;
3458
3459 req.bmRequestType = UT_READ_VENDOR_DEVICE;
3460 req.bRequest = URTW_8187_GETREGS_REQ;
3461 USETW(req.wValue, val | 0xfe00);
3462 USETW(req.wIndex, 0);
3463 USETW(req.wLength, sizeof(uint8_t));
3464
3465 error = urtw_do_request(sc, &req, data);
3466 return (error);
3467}
3468
3469static usb_error_t
3470urtw_write8e(struct urtw_softc *sc, int val, uint8_t data)
3471{
3472 struct usb_device_request req;
3473
3474 req.bmRequestType = UT_WRITE_VENDOR_DEVICE;
3475 req.bRequest = URTW_8187_SETREGS_REQ;
3476 USETW(req.wValue, val | 0xfe00);
3477 USETW(req.wIndex, 0);
3478 USETW(req.wLength, sizeof(uint8_t));
3479
3480 return (urtw_do_request(sc, &req, &data));
3481}
3482
3483static usb_error_t
3484urtw_8180_set_anaparam(struct urtw_softc *sc, uint32_t val)
3485{
3486 uint8_t data;
3487 usb_error_t error;
3488
3489 error = urtw_set_mode(sc, URTW_EPROM_CMD_CONFIG);
3490 if (error)
3491 goto fail;
3492
3493 urtw_read8_m(sc, URTW_CONFIG3, &data);
3494 urtw_write8_m(sc, URTW_CONFIG3, data | URTW_CONFIG3_ANAPARAM_WRITE);
3495 urtw_write32_m(sc, URTW_ANAPARAM, val);
3496 urtw_read8_m(sc, URTW_CONFIG3, &data);
3497 urtw_write8_m(sc, URTW_CONFIG3, data & ~URTW_CONFIG3_ANAPARAM_WRITE);
3498
3499 error = urtw_set_mode(sc, URTW_EPROM_CMD_NORMAL);
3500 if (error)
3501 goto fail;
3502fail:
3503 return (error);
3504}
3505
3506static usb_error_t
3507urtw_8185_set_anaparam2(struct urtw_softc *sc, uint32_t val)
3508{
3509 uint8_t data;
3510 usb_error_t error;
3511
3512 error = urtw_set_mode(sc, URTW_EPROM_CMD_CONFIG);
3513 if (error)
3514 goto fail;
3515
3516 urtw_read8_m(sc, URTW_CONFIG3, &data);
3517 urtw_write8_m(sc, URTW_CONFIG3, data | URTW_CONFIG3_ANAPARAM_WRITE);
3518 urtw_write32_m(sc, URTW_ANAPARAM2, val);
3519 urtw_read8_m(sc, URTW_CONFIG3, &data);
3520 urtw_write8_m(sc, URTW_CONFIG3, data & ~URTW_CONFIG3_ANAPARAM_WRITE);
3521
3522 error = urtw_set_mode(sc, URTW_EPROM_CMD_NORMAL);
3523 if (error)
3524 goto fail;
3525fail:
3526 return (error);
3527}
3528
3529static usb_error_t
3530urtw_intr_enable(struct urtw_softc *sc)
3531{
3532 usb_error_t error;
3533
3534 urtw_write16_m(sc, URTW_INTR_MASK, 0xffff);
3535fail:
3536 return (error);
3537}
3538
3539static usb_error_t
3540urtw_intr_disable(struct urtw_softc *sc)
3541{
3542 usb_error_t error;
3543
3544 urtw_write16_m(sc, URTW_INTR_MASK, 0);
3545fail:
3546 return (error);
3547}
3548
3549static usb_error_t
3550urtw_reset(struct urtw_softc *sc)
3551{
3552 uint8_t data;
3553 usb_error_t error;
3554
3555 error = urtw_8180_set_anaparam(sc, URTW_8225_ANAPARAM_ON);
3556 if (error)
3557 goto fail;
3558 error = urtw_8185_set_anaparam2(sc, URTW_8225_ANAPARAM2_ON);
3559 if (error)
3560 goto fail;
3561
3562 error = urtw_intr_disable(sc);
3563 if (error)
3564 goto fail;
3565 usb_pause_mtx(&sc->sc_mtx, 100);
3566
3567 error = urtw_write8e(sc, 0x18, 0x10);
3568 if (error != 0)
3569 goto fail;
3570 error = urtw_write8e(sc, 0x18, 0x11);
3571 if (error != 0)
3572 goto fail;
3573 error = urtw_write8e(sc, 0x18, 0x00);
3574 if (error != 0)
3575 goto fail;
3576 usb_pause_mtx(&sc->sc_mtx, 100);
3577
3578 urtw_read8_m(sc, URTW_CMD, &data);
3579 data = (data & 0x2) | URTW_CMD_RST;
3580 urtw_write8_m(sc, URTW_CMD, data);
3581 usb_pause_mtx(&sc->sc_mtx, 100);
3582
3583 urtw_read8_m(sc, URTW_CMD, &data);
3584 if (data & URTW_CMD_RST) {
3585 device_printf(sc->sc_dev, "reset timeout\n");
3586 goto fail;
3587 }
3588
3589 error = urtw_set_mode(sc, URTW_EPROM_CMD_LOAD);
3590 if (error)
3591 goto fail;
3592 usb_pause_mtx(&sc->sc_mtx, 100);
3593
3594 error = urtw_8180_set_anaparam(sc, URTW_8225_ANAPARAM_ON);
3595 if (error)
3596 goto fail;
3597 error = urtw_8185_set_anaparam2(sc, URTW_8225_ANAPARAM2_ON);
3598 if (error)
3599 goto fail;
3600fail:
3601 return (error);
3602}
3603
3604static usb_error_t
3605urtw_led_ctl(struct urtw_softc *sc, int mode)
3606{
3607 usb_error_t error = 0;
3608
3609 switch (sc->sc_strategy) {
3610 case URTW_SW_LED_MODE0:
3611 error = urtw_led_mode0(sc, mode);
3612 break;
3613 case URTW_SW_LED_MODE1:
3614 error = urtw_led_mode1(sc, mode);
3615 break;
3616 case URTW_SW_LED_MODE2:
3617 error = urtw_led_mode2(sc, mode);
3618 break;
3619 case URTW_SW_LED_MODE3:
3620 error = urtw_led_mode3(sc, mode);
3621 break;
3622 default:
3623 panic("unsupported LED mode %d\n", sc->sc_strategy);
3624 /* never reach */
3625 }
3626
3627 return (error);
3628}
3629
3630static usb_error_t
3631urtw_led_mode0(struct urtw_softc *sc, int mode)
3632{
3633
3634 switch (mode) {
3635 case URTW_LED_CTL_POWER_ON:
3636 sc->sc_gpio_ledstate = URTW_LED_POWER_ON_BLINK;
3637 break;
3638 case URTW_LED_CTL_TX:
3639 if (sc->sc_gpio_ledinprogress == 1)
3640 return (0);
3641
3642 sc->sc_gpio_ledstate = URTW_LED_BLINK_NORMAL;
3643 sc->sc_gpio_blinktime = 2;
3644 break;
3645 case URTW_LED_CTL_LINK:
3646 sc->sc_gpio_ledstate = URTW_LED_ON;
3647 break;
3648 default:
3649 panic("unsupported LED mode 0x%x", mode);
3650 /* never reach */
3651 }
3652
3653 switch (sc->sc_gpio_ledstate) {
3654 case URTW_LED_ON:
3655 if (sc->sc_gpio_ledinprogress != 0)
3656 break;
3657 urtw_led_on(sc, URTW_LED_GPIO);
3658 break;
3659 case URTW_LED_BLINK_NORMAL:
3660 if (sc->sc_gpio_ledinprogress != 0)
3661 break;
3662 sc->sc_gpio_ledinprogress = 1;
3663 sc->sc_gpio_blinkstate = (sc->sc_gpio_ledon != 0) ?
3664 URTW_LED_OFF : URTW_LED_ON;
3665 usb_callout_reset(&sc->sc_led_ch, hz, urtw_led_ch, sc);
3666 break;
3667 case URTW_LED_POWER_ON_BLINK:
3668 urtw_led_on(sc, URTW_LED_GPIO);
3669 usb_pause_mtx(&sc->sc_mtx, 100);
3670 urtw_led_off(sc, URTW_LED_GPIO);
3671 break;
3672 default:
3673 panic("unknown LED status 0x%x", sc->sc_gpio_ledstate);
3674 /* never reach */
3675 }
3676 return (0);
3677}
3678
3679static usb_error_t
3680urtw_led_mode1(struct urtw_softc *sc, int mode)
3681{
3682
3683 return (USB_ERR_INVAL);
3684}
3685
3686static usb_error_t
3687urtw_led_mode2(struct urtw_softc *sc, int mode)
3688{
3689
3690 return (USB_ERR_INVAL);
3691}
3692
3693static usb_error_t
3694urtw_led_mode3(struct urtw_softc *sc, int mode)
3695{
3696
3697 return (USB_ERR_INVAL);
3698}
3699
3700static usb_error_t
3701urtw_led_on(struct urtw_softc *sc, int type)
3702{
3703 usb_error_t error;
3704
3705 if (type == URTW_LED_GPIO) {
3706 switch (sc->sc_gpio_ledpin) {
3707 case URTW_LED_PIN_GPIO0:
3708 urtw_write8_m(sc, URTW_GPIO, 0x01);
3709 urtw_write8_m(sc, URTW_GP_ENABLE, 0x00);
3710 break;
3711 default:
3712 panic("unsupported LED PIN type 0x%x",
3713 sc->sc_gpio_ledpin);
3714 /* never reach */
3715 }
3716 } else {
3717 panic("unsupported LED type 0x%x", type);
3718 /* never reach */
3719 }
3720
3721 sc->sc_gpio_ledon = 1;
3722fail:
3723 return (error);
3724}
3725
3726static usb_error_t
3727urtw_led_off(struct urtw_softc *sc, int type)
3728{
3729 usb_error_t error;
3730
3731 if (type == URTW_LED_GPIO) {
3732 switch (sc->sc_gpio_ledpin) {
3733 case URTW_LED_PIN_GPIO0:
3734 urtw_write8_m(sc, URTW_GPIO, URTW_GPIO_DATA_MAGIC1);
3735 urtw_write8_m(sc,
3736 URTW_GP_ENABLE, URTW_GP_ENABLE_DATA_MAGIC1);
3737 break;
3738 default:
3739 panic("unsupported LED PIN type 0x%x",
3740 sc->sc_gpio_ledpin);
3741 /* never reach */
3742 }
3743 } else {
3744 panic("unsupported LED type 0x%x", type);
3745 /* never reach */
3746 }
3747
3748 sc->sc_gpio_ledon = 0;
3749
3750fail:
3751 return (error);
3752}
3753
3754static void
3755urtw_led_ch(void *arg)
3756{
3757 struct urtw_softc *sc = arg;
3758 struct ifnet *ifp = sc->sc_ifp;
3759 struct ieee80211com *ic = ifp->if_l2com;
3760
3761 ieee80211_runtask(ic, &sc->sc_led_task);
3762}
3763
3764static void
3765urtw_ledtask(void *arg, int pending)
3766{
3767 struct urtw_softc *sc = arg;
3768
3769 if (sc->sc_strategy != URTW_SW_LED_MODE0)
3770 panic("could not process a LED strategy 0x%x", sc->sc_strategy);
3771
3772 URTW_LOCK(sc);
3773 urtw_led_blink(sc);
3774 URTW_UNLOCK(sc);
3775}
3776
3777static usb_error_t
3778urtw_led_blink(struct urtw_softc *sc)
3779{
3780 uint8_t ing = 0;
3781 usb_error_t error;
3782
3783 if (sc->sc_gpio_blinkstate == URTW_LED_ON)
3784 error = urtw_led_on(sc, URTW_LED_GPIO);
3785 else
3786 error = urtw_led_off(sc, URTW_LED_GPIO);
3787 sc->sc_gpio_blinktime--;
3788 if (sc->sc_gpio_blinktime == 0)
3789 ing = 1;
3790 else {
3791 if (sc->sc_gpio_ledstate != URTW_LED_BLINK_NORMAL &&
3792 sc->sc_gpio_ledstate != URTW_LED_BLINK_SLOWLY &&
3793 sc->sc_gpio_ledstate != URTW_LED_BLINK_CM3)
3794 ing = 1;
3795 }
3796 if (ing == 1) {
3797 if (sc->sc_gpio_ledstate == URTW_LED_ON &&
3798 sc->sc_gpio_ledon == 0)
3799 error = urtw_led_on(sc, URTW_LED_GPIO);
3800 else if (sc->sc_gpio_ledstate == URTW_LED_OFF &&
3801 sc->sc_gpio_ledon == 1)
3802 error = urtw_led_off(sc, URTW_LED_GPIO);
3803
3804 sc->sc_gpio_blinktime = 0;
3805 sc->sc_gpio_ledinprogress = 0;
3806 return (0);
3807 }
3808
3809 sc->sc_gpio_blinkstate = (sc->sc_gpio_blinkstate != URTW_LED_ON) ?
3810 URTW_LED_ON : URTW_LED_OFF;
3811
3812 switch (sc->sc_gpio_ledstate) {
3813 case URTW_LED_BLINK_NORMAL:
3814 usb_callout_reset(&sc->sc_led_ch, hz, urtw_led_ch, sc);
3815 break;
3816 default:
3817 panic("unknown LED status 0x%x", sc->sc_gpio_ledstate);
3818 /* never reach */
3819 }
3820 return (0);
3821}
3822
3823static usb_error_t
3824urtw_rx_enable(struct urtw_softc *sc)
3825{
3826 uint8_t data;
3827 usb_error_t error;
3828
3829 usbd_transfer_start((sc->sc_flags & URTW_RTL8187B) ?
3830 sc->sc_xfer[URTW_8187B_BULK_RX] : sc->sc_xfer[URTW_8187L_BULK_RX]);
3831
3832 error = urtw_rx_setconf(sc);
3833 if (error != 0)
3834 goto fail;
3835
3836 if ((sc->sc_flags & URTW_RTL8187B) == 0) {
3837 urtw_read8_m(sc, URTW_CMD, &data);
3838 urtw_write8_m(sc, URTW_CMD, data | URTW_CMD_RX_ENABLE);
3839 }
3840fail:
3841 return (error);
3842}
3843
3844static usb_error_t
3845urtw_tx_enable(struct urtw_softc *sc)
3846{
3847 uint8_t data8;
3848 uint32_t data;
3849 usb_error_t error;
3850
3851 if (sc->sc_flags & URTW_RTL8187B) {
3852 urtw_read32_m(sc, URTW_TX_CONF, &data);
3853 data &= ~URTW_TX_LOOPBACK_MASK;
3854 data &= ~(URTW_TX_DPRETRY_MASK | URTW_TX_RTSRETRY_MASK);
3855 data &= ~(URTW_TX_NOCRC | URTW_TX_MXDMA_MASK);
3856 data &= ~URTW_TX_SWPLCPLEN;
3857 data |= URTW_TX_HW_SEQNUM | URTW_TX_DISREQQSIZE |
3858 (7 << 8) | /* short retry limit */
3859 (7 << 0) | /* long retry limit */
3860 (7 << 21); /* MAX TX DMA */
3861 urtw_write32_m(sc, URTW_TX_CONF, data);
3862
3863 urtw_read8_m(sc, URTW_MSR, &data8);
3864 data8 |= URTW_MSR_LINK_ENEDCA;
3865 urtw_write8_m(sc, URTW_MSR, data8);
3866 return (error);
3867 }
3868
3869 urtw_read8_m(sc, URTW_CW_CONF, &data8);
3870 data8 &= ~(URTW_CW_CONF_PERPACKET_CW | URTW_CW_CONF_PERPACKET_RETRY);
3871 urtw_write8_m(sc, URTW_CW_CONF, data8);
3872
3873 urtw_read8_m(sc, URTW_TX_AGC_CTL, &data8);
3874 data8 &= ~URTW_TX_AGC_CTL_PERPACKET_GAIN;
3875 data8 &= ~URTW_TX_AGC_CTL_PERPACKET_ANTSEL;
3876 data8 &= ~URTW_TX_AGC_CTL_FEEDBACK_ANT;
3877 urtw_write8_m(sc, URTW_TX_AGC_CTL, data8);
3878
3879 urtw_read32_m(sc, URTW_TX_CONF, &data);
3880 data &= ~URTW_TX_LOOPBACK_MASK;
3881 data |= URTW_TX_LOOPBACK_NONE;
3882 data &= ~(URTW_TX_DPRETRY_MASK | URTW_TX_RTSRETRY_MASK);
3883 data |= sc->sc_tx_retry << URTW_TX_DPRETRY_SHIFT;
3884 data |= sc->sc_rts_retry << URTW_TX_RTSRETRY_SHIFT;
3885 data &= ~(URTW_TX_NOCRC | URTW_TX_MXDMA_MASK);
3886 data |= URTW_TX_MXDMA_2048 | URTW_TX_CWMIN | URTW_TX_DISCW;
3887 data &= ~URTW_TX_SWPLCPLEN;
3888 data |= URTW_TX_NOICV;
3889 urtw_write32_m(sc, URTW_TX_CONF, data);
3890
3891 urtw_read8_m(sc, URTW_CMD, &data8);
3892 urtw_write8_m(sc, URTW_CMD, data8 | URTW_CMD_TX_ENABLE);
3893fail:
3894 return (error);
3895}
3896
3897static usb_error_t
3898urtw_rx_setconf(struct urtw_softc *sc)
3899{
3900 struct ifnet *ifp = sc->sc_ifp;
3901 struct ieee80211com *ic = ifp->if_l2com;
3902 uint32_t data;
3903 usb_error_t error;
3904
3905 urtw_read32_m(sc, URTW_RX, &data);
3906 data = data &~ URTW_RX_FILTER_MASK;
3907 if (sc->sc_flags & URTW_RTL8187B) {
3908 data = data | URTW_RX_FILTER_MNG | URTW_RX_FILTER_DATA |
3909 URTW_RX_FILTER_MCAST | URTW_RX_FILTER_BCAST |
3910 URTW_RX_FILTER_NICMAC | URTW_RX_CHECK_BSSID |
3911 URTW_RX_FIFO_THRESHOLD_NONE |
3912 URTW_MAX_RX_DMA_2048 |
3913 URTW_RX_AUTORESETPHY | URTW_RCR_ONLYERLPKT;
3914 } else {
3915 data = data | URTW_RX_FILTER_MNG | URTW_RX_FILTER_DATA;
3916 data = data | URTW_RX_FILTER_BCAST | URTW_RX_FILTER_MCAST;
3917
3918 if (ic->ic_opmode == IEEE80211_M_MONITOR) {
3919 data = data | URTW_RX_FILTER_ICVERR;
3920 data = data | URTW_RX_FILTER_PWR;
3921 }
3922 if (sc->sc_crcmon == 1 && ic->ic_opmode == IEEE80211_M_MONITOR)
3923 data = data | URTW_RX_FILTER_CRCERR;
3924
3925 if (ic->ic_opmode == IEEE80211_M_MONITOR ||
3926 (ifp->if_flags & (IFF_ALLMULTI | IFF_PROMISC))) {
3927 data = data | URTW_RX_FILTER_ALLMAC;
3928 } else {
3929 data = data | URTW_RX_FILTER_NICMAC;
3930 data = data | URTW_RX_CHECK_BSSID;
3931 }
3932
3933 data = data &~ URTW_RX_FIFO_THRESHOLD_MASK;
3934 data = data | URTW_RX_FIFO_THRESHOLD_NONE |
3935 URTW_RX_AUTORESETPHY;
3936 data = data &~ URTW_MAX_RX_DMA_MASK;
3937 data = data | URTW_MAX_RX_DMA_2048 | URTW_RCR_ONLYERLPKT;
3938 }
3939
3940 urtw_write32_m(sc, URTW_RX, data);
3941fail:
3942 return (error);
3943}
3944
3945static struct mbuf *
3946urtw_rxeof(struct usb_xfer *xfer, struct urtw_data *data, int *rssi_p,
3947 int8_t *nf_p)
3948{
3949 int actlen, flen, rssi;
3950 struct ieee80211_frame *wh;
3951 struct mbuf *m, *mnew;
3952 struct urtw_softc *sc = data->sc;
3953 struct ifnet *ifp = sc->sc_ifp;
3954 struct ieee80211com *ic = ifp->if_l2com;
3955 uint8_t noise = 0, rate;
3956
3957 usbd_xfer_status(xfer, &actlen, NULL, NULL, NULL);
3958
3959 if (actlen < URTW_MIN_RXBUFSZ) {
3960 ifp->if_ierrors++;
3961 return (NULL);
3962 }
3963
3964 if (sc->sc_flags & URTW_RTL8187B) {
3965 struct urtw_8187b_rxhdr *rx;
3966
3967 rx = (struct urtw_8187b_rxhdr *)(data->buf +
3968 (actlen - (sizeof(struct urtw_8187b_rxhdr))));
3969 flen = le32toh(rx->flag) & 0xfff;
3970 if (flen > actlen) {
3971 ifp->if_ierrors++;
3972 return (NULL);
3973 }
3974 rate = (le32toh(rx->flag) >> URTW_RX_FLAG_RXRATE_SHIFT) & 0xf;
3975 /* XXX correct? */
3976 rssi = rx->rssi & URTW_RX_RSSI_MASK;
3977 noise = rx->noise;
3978 } else {
3979 struct urtw_8187l_rxhdr *rx;
3980
3981 rx = (struct urtw_8187l_rxhdr *)(data->buf +
3982 (actlen - (sizeof(struct urtw_8187l_rxhdr))));
3983 flen = le32toh(rx->flag) & 0xfff;
3984 if (flen > actlen) {
3985 ifp->if_ierrors++;
3986 return (NULL);
3987 }
3988
3989 rate = (le32toh(rx->flag) >> URTW_RX_FLAG_RXRATE_SHIFT) & 0xf;
3990 /* XXX correct? */
3991 rssi = rx->rssi & URTW_RX_8187L_RSSI_MASK;
3992 noise = rx->noise;
3993 }
3994
3995 mnew = m_getcl(M_DONTWAIT, MT_DATA, M_PKTHDR);
3996 if (mnew == NULL) {
3997 ifp->if_ierrors++;
3998 return (NULL);
3999 }
4000
4001 m = data->m;
4002 data->m = mnew;
4003 data->buf = mtod(mnew, uint8_t *);
4004
4005 /* finalize mbuf */
4006 m->m_pkthdr.rcvif = ifp;
4007 m->m_pkthdr.len = m->m_len = flen - IEEE80211_CRC_LEN;
4008
4009 if (ieee80211_radiotap_active(ic)) {
4010 struct urtw_rx_radiotap_header *tap = &sc->sc_rxtap;
4011
4012 /* XXX Are variables correct? */
4013 tap->wr_chan_freq = htole16(ic->ic_curchan->ic_freq);
4014 tap->wr_chan_flags = htole16(ic->ic_curchan->ic_flags);
4015 tap->wr_dbm_antsignal = (int8_t)rssi;
4016 }
4017
4018 wh = mtod(m, struct ieee80211_frame *);
4019 if ((wh->i_fc[0] & IEEE80211_FC0_TYPE_MASK) == IEEE80211_FC0_TYPE_DATA)
4020 sc->sc_currate = (rate > 0) ? rate : sc->sc_currate;
4021
4022 *rssi_p = rssi;
4023 *nf_p = noise; /* XXX correct? */
4024
4025 return (m);
4026}
4027
4028static void
4029urtw_bulk_rx_callback(struct usb_xfer *xfer, usb_error_t error)
4030{
4031 struct urtw_softc *sc = usbd_xfer_softc(xfer);
4032 struct ifnet *ifp = sc->sc_ifp;
4033 struct ieee80211com *ic = ifp->if_l2com;
4034 struct ieee80211_frame *wh;
4035 struct ieee80211_node *ni;
4036 struct mbuf *m = NULL;
4037 struct urtw_data *data;
4038 int8_t nf = -95;
4039 int rssi = 1;
4040
4041 URTW_ASSERT_LOCKED(sc);
4042
4043 switch (USB_GET_STATE(xfer)) {
4044 case USB_ST_TRANSFERRED:
4045 data = STAILQ_FIRST(&sc->sc_rx_active);
4046 if (data == NULL)
4047 goto setup;
4048 STAILQ_REMOVE_HEAD(&sc->sc_rx_active, next);
4049 m = urtw_rxeof(xfer, data, &rssi, &nf);
4050 STAILQ_INSERT_TAIL(&sc->sc_rx_inactive, data, next);
4051 /* FALLTHROUGH */
4052 case USB_ST_SETUP:
4053setup:
4054 data = STAILQ_FIRST(&sc->sc_rx_inactive);
4055 if (data == NULL) {
4056 KASSERT(m == NULL, ("mbuf isn't NULL"));
4057 return;
4058 }
4059 STAILQ_REMOVE_HEAD(&sc->sc_rx_inactive, next);
4060 STAILQ_INSERT_TAIL(&sc->sc_rx_active, data, next);
4061 usbd_xfer_set_frame_data(xfer, 0, data->buf,
4062 usbd_xfer_max_len(xfer));
4063 usbd_transfer_submit(xfer);
4064
4065 /*
4066 * To avoid LOR we should unlock our private mutex here to call
4067 * ieee80211_input() because here is at the end of a USB
4068 * callback and safe to unlock.
4069 */
4070 URTW_UNLOCK(sc);
4071 if (m != NULL) {
4072 wh = mtod(m, struct ieee80211_frame *);
4073 ni = ieee80211_find_rxnode(ic,
4074 (struct ieee80211_frame_min *)wh);
4075 if (ni != NULL) {
4076 (void) ieee80211_input(ni, m, rssi, nf);
4077 /* node is no longer needed */
4078 ieee80211_free_node(ni);
4079 } else
4080 (void) ieee80211_input_all(ic, m, rssi, nf);
4081 m = NULL;
4082 }
4083 URTW_LOCK(sc);
4084 break;
4085 default:
4086 /* needs it to the inactive queue due to a error. */
4087 data = STAILQ_FIRST(&sc->sc_rx_active);
4088 if (data != NULL) {
4089 STAILQ_REMOVE_HEAD(&sc->sc_rx_active, next);
4090 STAILQ_INSERT_TAIL(&sc->sc_rx_inactive, data, next);
4091 }
4092 if (error != USB_ERR_CANCELLED) {
4093 usbd_xfer_set_stall(xfer);
4094 ifp->if_ierrors++;
4095 goto setup;
4096 }
4097 break;
4098 }
4099}
4100
4101#define URTW_STATUS_TYPE_TXCLOSE 1
4102#define URTW_STATUS_TYPE_BEACON_INTR 0
4103
4104static void
4105urtw_txstatus_eof(struct usb_xfer *xfer)
4106{
4107 struct urtw_softc *sc = usbd_xfer_softc(xfer);
4108 struct ifnet *ifp = sc->sc_ifp;
4109 int actlen, type, pktretry, seq;
4110 uint64_t val;
4111
4112 usbd_xfer_status(xfer, &actlen, NULL, NULL, NULL);
4113
4114 if (actlen != sizeof(uint64_t))
4115 return;
4116
4117 val = le64toh(sc->sc_txstatus);
4118 type = (val >> 30) & 0x3;
4119 if (type == URTW_STATUS_TYPE_TXCLOSE) {
4120 pktretry = val & 0xff;
4121 seq = (val >> 16) & 0xff;
4122 if (pktretry == URTW_TX_MAXRETRY)
4123 ifp->if_oerrors++;
4124 DPRINTF(sc, URTW_DEBUG_TXSTATUS, "pktretry %d seq %#x\n",
4125 pktretry, seq);
4126 }
4127}
4128
4129static void
4130urtw_bulk_tx_status_callback(struct usb_xfer *xfer, usb_error_t error)
4131{
4132 struct urtw_softc *sc = usbd_xfer_softc(xfer);
4133 struct ifnet *ifp = sc->sc_ifp;
4134
4135 URTW_ASSERT_LOCKED(sc);
4136
4137 switch (USB_GET_STATE(xfer)) {
4138 case USB_ST_TRANSFERRED:
4139 urtw_txstatus_eof(xfer);
4140 /* FALLTHROUGH */
4141 case USB_ST_SETUP:
4142setup:
4143 usbd_xfer_set_frame_data(xfer, 0, &sc->sc_txstatus,
4144 sizeof(int64_t));
4145 usbd_transfer_submit(xfer);
4146 break;
4147 default:
4148 if (error != USB_ERR_CANCELLED) {
4149 usbd_xfer_set_stall(xfer);
4150 ifp->if_ierrors++;
4151 goto setup;
4152 }
4153 break;
4154 }
4155}
4156
4157static void
4158urtw_txeof(struct usb_xfer *xfer, struct urtw_data *data)
4159{
4160 struct urtw_softc *sc = usbd_xfer_softc(xfer);
4161 struct ifnet *ifp = sc->sc_ifp;
4162 struct mbuf *m;
4163
4164 URTW_ASSERT_LOCKED(sc);
4165
4166 /*
4167 * Do any tx complete callback. Note this must be done before releasing
4168 * the node reference.
4169 */
4170 if (data->m) {
4171 m = data->m;
4172 if (m->m_flags & M_TXCB) {
4173 /* XXX status? */
4174 ieee80211_process_callback(data->ni, m, 0);
4175 }
4176 m_freem(m);
4177 data->m = NULL;
4178 }
4179 if (data->ni) {
4180 ieee80211_free_node(data->ni);
4181 data->ni = NULL;
4182 }
4183 sc->sc_txtimer = 0;
4184 ifp->if_opackets++;
4185 ifp->if_drv_flags &= ~IFF_DRV_OACTIVE;
4186}
4187
4188static void
4189urtw_bulk_tx_callback(struct usb_xfer *xfer, usb_error_t error)
4190{
4191 struct urtw_softc *sc = usbd_xfer_softc(xfer);
4192 struct ifnet *ifp = sc->sc_ifp;
4193 struct urtw_data *data;
4194
4195 URTW_ASSERT_LOCKED(sc);
4196
4197 switch (USB_GET_STATE(xfer)) {
4198 case USB_ST_TRANSFERRED:
4199 data = STAILQ_FIRST(&sc->sc_tx_active);
4200 if (data == NULL)
4201 goto setup;
4202 STAILQ_REMOVE_HEAD(&sc->sc_tx_active, next);
4203 urtw_txeof(xfer, data);
4204 STAILQ_INSERT_TAIL(&sc->sc_tx_inactive, data, next);
4205 /* FALLTHROUGH */
4206 case USB_ST_SETUP:
4207setup:
4208 data = STAILQ_FIRST(&sc->sc_tx_pending);
4209 if (data == NULL) {
4210 DPRINTF(sc, URTW_DEBUG_XMIT,
4211 "%s: empty pending queue\n", __func__);
4212 return;
4213 }
4214 STAILQ_REMOVE_HEAD(&sc->sc_tx_pending, next);
4215 STAILQ_INSERT_TAIL(&sc->sc_tx_active, data, next);
4216
4217 usbd_xfer_set_frame_data(xfer, 0, data->buf, data->buflen);
4218 usbd_transfer_submit(xfer);
4219
4220 URTW_UNLOCK(sc);
4221 urtw_start(ifp);
4222 URTW_LOCK(sc);
4223 break;
4224 default:
4225 data = STAILQ_FIRST(&sc->sc_tx_active);
4226 if (data == NULL)
4227 goto setup;
4228 if (data->ni != NULL) {
4229 ieee80211_free_node(data->ni);
4230 data->ni = NULL;
4231 ifp->if_oerrors++;
4232 }
4233 if (error != USB_ERR_CANCELLED) {
4234 usbd_xfer_set_stall(xfer);
4235 goto setup;
4236 }
4237 break;
4238 }
4239}
4240
4241static struct urtw_data *
4242_urtw_getbuf(struct urtw_softc *sc)
4243{
4244 struct urtw_data *bf;
4245
4246 bf = STAILQ_FIRST(&sc->sc_tx_inactive);
4247 if (bf != NULL)
4248 STAILQ_REMOVE_HEAD(&sc->sc_tx_inactive, next);
4249 else
4250 bf = NULL;
4251 if (bf == NULL)
4252 DPRINTF(sc, URTW_DEBUG_XMIT, "%s: %s\n", __func__,
4253 "out of xmit buffers");
4254 return (bf);
4255}
4256
4257static struct urtw_data *
4258urtw_getbuf(struct urtw_softc *sc)
4259{
4260 struct urtw_data *bf;
4261
4262 URTW_ASSERT_LOCKED(sc);
4263
4264 bf = _urtw_getbuf(sc);
4265 if (bf == NULL) {
4266 struct ifnet *ifp = sc->sc_ifp;
4267
4268 DPRINTF(sc, URTW_DEBUG_XMIT, "%s: stop queue\n", __func__);
4269 ifp->if_drv_flags |= IFF_DRV_OACTIVE;
4270 }
4271 return (bf);
4272}
4273
4274static int
4275urtw_isbmode(uint16_t rate)
4276{
4277
4278 return ((rate <= 22 && rate != 12 && rate != 18) ||
4279 rate == 44) ? (1) : (0);
4280}
4281
4282static uint16_t
4283urtw_rate2dbps(uint16_t rate)
4284{
4285
4286 switch(rate) {
4287 case 12:
4288 case 18:
4289 case 24:
4290 case 36:
4291 case 48:
4292 case 72:
4293 case 96:
4294 case 108:
4295 return (rate * 2);
4296 default:
4297 break;
4298 }
4299 return (24);
4300}
4301
4302static int
4303urtw_compute_txtime(uint16_t framelen, uint16_t rate,
4304 uint8_t ismgt, uint8_t isshort)
4305{
4306 uint16_t ceiling, frametime, n_dbps;
4307
4308 if (urtw_isbmode(rate)) {
4309 if (ismgt || !isshort || rate == 2)
4310 frametime = (uint16_t)(144 + 48 +
4311 (framelen * 8 / (rate / 2)));
4312 else
4313 frametime = (uint16_t)(72 + 24 +
4314 (framelen * 8 / (rate / 2)));
4315 if ((framelen * 8 % (rate / 2)) != 0)
4316 frametime++;
4317 } else {
4318 n_dbps = urtw_rate2dbps(rate);
4319 ceiling = (16 + 8 * framelen + 6) / n_dbps
4320 + (((16 + 8 * framelen + 6) % n_dbps) ? 1 : 0);
4321 frametime = (uint16_t)(16 + 4 + 4 * ceiling + 6);
4322 }
4323 return (frametime);
4324}
4325
4326/*
4327 * Callback from the 802.11 layer to update the
4328 * slot time based on the current setting.
4329 */
4330static void
4331urtw_updateslot(struct ifnet *ifp)
4332{
4333 struct urtw_softc *sc = ifp->if_softc;
4334 struct ieee80211com *ic = ifp->if_l2com;
4335
4336 ieee80211_runtask(ic, &sc->sc_updateslot_task);
4337}
4338
4339static void
4340urtw_updateslottask(void *arg, int pending)
4341{
4342 struct urtw_softc *sc = arg;
4343 struct ifnet *ifp = sc->sc_ifp;
4344 struct ieee80211com *ic = ifp->if_l2com;
4345 int error;
4346
4347 if ((ifp->if_drv_flags & IFF_DRV_RUNNING) == 0)
4348 return;
4349
4350 URTW_LOCK(sc);
4351 if (sc->sc_flags & URTW_RTL8187B) {
4352 urtw_write8_m(sc, URTW_SIFS, 0x22);
4353 if (IEEE80211_IS_CHAN_ANYG(ic->ic_curchan))
4354 urtw_write8_m(sc, URTW_SLOT, 0x9);
4355 else
4356 urtw_write8_m(sc, URTW_SLOT, 0x14);
4357 urtw_write8_m(sc, URTW_8187B_EIFS, 0x5b);
4358 urtw_write8_m(sc, URTW_CARRIER_SCOUNT, 0x5b);
4359 } else {
4360 urtw_write8_m(sc, URTW_SIFS, 0x22);
4361 if (sc->sc_state == IEEE80211_S_ASSOC &&
4362 ic->ic_flags & IEEE80211_F_SHSLOT)
4363 urtw_write8_m(sc, URTW_SLOT, 0x9);
4364 else
4365 urtw_write8_m(sc, URTW_SLOT, 0x14);
4366 if (IEEE80211_IS_CHAN_ANYG(ic->ic_curchan)) {
4367 urtw_write8_m(sc, URTW_DIFS, 0x14);
4368 urtw_write8_m(sc, URTW_EIFS, 0x5b - 0x14);
4369 urtw_write8_m(sc, URTW_CW_VAL, 0x73);
4370 } else {
4371 urtw_write8_m(sc, URTW_DIFS, 0x24);
4372 urtw_write8_m(sc, URTW_EIFS, 0x5b - 0x24);
4373 urtw_write8_m(sc, URTW_CW_VAL, 0xa5);
4374 }
4375 }
4376fail:
4377 URTW_UNLOCK(sc);
4378}
4379
4380static void
4381urtw_sysctl_node(struct urtw_softc *sc)
4382{
4383#define URTW_SYSCTL_STAT_ADD32(c, h, n, p, d) \
4384 SYSCTL_ADD_UINT(c, h, OID_AUTO, n, CTLFLAG_RD, p, 0, d)
4385 struct sysctl_ctx_list *ctx;
4386 struct sysctl_oid_list *child, *parent;
4387 struct sysctl_oid *tree;
4388 struct urtw_stats *stats = &sc->sc_stats;
4389
4390 ctx = device_get_sysctl_ctx(sc->sc_dev);
4391 child = SYSCTL_CHILDREN(device_get_sysctl_tree(sc->sc_dev));
4392
4393 tree = SYSCTL_ADD_NODE(ctx, child, OID_AUTO, "stats", CTLFLAG_RD,
4394 NULL, "URTW statistics");
4395 parent = SYSCTL_CHILDREN(tree);
4396
4397 /* Tx statistics. */
4398 tree = SYSCTL_ADD_NODE(ctx, parent, OID_AUTO, "tx", CTLFLAG_RD,
4399 NULL, "Tx MAC statistics");
4400 child = SYSCTL_CHILDREN(tree);
4401 URTW_SYSCTL_STAT_ADD32(ctx, child, "1m", &stats->txrates[0],
4402 "1 Mbit/s");
4403 URTW_SYSCTL_STAT_ADD32(ctx, child, "2m", &stats->txrates[1],
4404 "2 Mbit/s");
4405 URTW_SYSCTL_STAT_ADD32(ctx, child, "5.5m", &stats->txrates[2],
4406 "5.5 Mbit/s");
4407 URTW_SYSCTL_STAT_ADD32(ctx, child, "6m", &stats->txrates[4],
4408 "6 Mbit/s");
4409 URTW_SYSCTL_STAT_ADD32(ctx, child, "9m", &stats->txrates[5],
4410 "9 Mbit/s");
4411 URTW_SYSCTL_STAT_ADD32(ctx, child, "11m", &stats->txrates[3],
4412 "11 Mbit/s");
4413 URTW_SYSCTL_STAT_ADD32(ctx, child, "12m", &stats->txrates[6],
4414 "12 Mbit/s");
4415 URTW_SYSCTL_STAT_ADD32(ctx, child, "18m", &stats->txrates[7],
4416 "18 Mbit/s");
4417 URTW_SYSCTL_STAT_ADD32(ctx, child, "24m", &stats->txrates[8],
4418 "24 Mbit/s");
4419 URTW_SYSCTL_STAT_ADD32(ctx, child, "36m", &stats->txrates[9],
4420 "36 Mbit/s");
4421 URTW_SYSCTL_STAT_ADD32(ctx, child, "48m", &stats->txrates[10],
4422 "48 Mbit/s");
4423 URTW_SYSCTL_STAT_ADD32(ctx, child, "54m", &stats->txrates[11],
4424 "54 Mbit/s");
4425#undef URTW_SYSCTL_STAT_ADD32
4426}
4427
4428static device_method_t urtw_methods[] = {
4429 DEVMETHOD(device_probe, urtw_match),
4430 DEVMETHOD(device_attach, urtw_attach),
4431 DEVMETHOD(device_detach, urtw_detach),
4432 { 0, 0 }
4433};
4434static driver_t urtw_driver = {
4435 "urtw",
4436 urtw_methods,
4437 sizeof(struct urtw_softc)
4438};
4439static devclass_t urtw_devclass;
4440
4441DRIVER_MODULE(urtw, uhub, urtw_driver, urtw_devclass, NULL, 0);
4442MODULE_DEPEND(urtw, wlan, 1, 1, 1);
4443MODULE_DEPEND(urtw, usb, 1, 1, 1);