This source file includes following definitions.
- uath_match
- uath_attachhook
- uath_attach
- uath_detach
- uath_open_pipes
- uath_close_pipes
- uath_alloc_tx_data_list
- uath_free_tx_data_list
- uath_alloc_rx_data_list
- uath_free_rx_data_list
- uath_free_rx_data
- uath_alloc_tx_cmd_list
- uath_free_tx_cmd_list
- uath_alloc_rx_cmd_list
- uath_free_rx_cmd_list
- uath_media_change
- uath_stat
- uath_next_scan
- uath_task
- uath_newstate
- uath_dump_cmd
- uath_cmd
- uath_cmd_write
- uath_cmd_read
- uath_write_reg
- uath_write_multi
- uath_read_reg
- uath_read_eeprom
- uath_cmd_rxeof
- uath_data_rxeof
- uath_tx_null
- uath_data_txeof
- uath_tx_data
- uath_start
- uath_watchdog
- uath_ioctl
- uath_query_eeprom
- uath_reset
- uath_reset_tx_queues
- uath_wme_init
- uath_set_chan
- uath_set_key
- uath_set_keys
- uath_set_rates
- uath_set_rxfilter
- uath_set_led
- uath_switch_channel
- uath_init
- uath_stop
- uath_loadfirmware
- uath_activate
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31 #include "bpfilter.h"
32
33 #include <sys/param.h>
34 #include <sys/sockio.h>
35 #include <sys/sysctl.h>
36 #include <sys/mbuf.h>
37 #include <sys/kernel.h>
38 #include <sys/socket.h>
39 #include <sys/systm.h>
40 #include <sys/malloc.h>
41 #include <sys/timeout.h>
42 #include <sys/conf.h>
43 #include <sys/device.h>
44
45 #include <machine/bus.h>
46 #include <machine/endian.h>
47 #include <machine/intr.h>
48
49 #if NBPFILTER > 0
50 #include <net/bpf.h>
51 #endif
52 #include <net/if.h>
53 #include <net/if_arp.h>
54 #include <net/if_dl.h>
55 #include <net/if_media.h>
56 #include <net/if_types.h>
57
58 #include <netinet/in.h>
59 #include <netinet/in_systm.h>
60 #include <netinet/in_var.h>
61 #include <netinet/if_ether.h>
62 #include <netinet/ip.h>
63
64 #include <net80211/ieee80211_var.h>
65 #include <net80211/ieee80211_radiotap.h>
66
67 #include <dev/rndvar.h>
68 #include <crypto/arc4.h>
69
70 #include <dev/usb/usb.h>
71 #include <dev/usb/usbdi.h>
72 #include <dev/usb/usbdivar.h>
73 #include <dev/usb/usbdi_util.h>
74 #include <dev/usb/usbdevs.h>
75
76 #include <dev/usb/if_uathreg.h>
77 #include <dev/usb/if_uathvar.h>
78
79 #ifdef USB_DEBUG
80 #define UATH_DEBUG
81 #endif
82
83 #ifdef UATH_DEBUG
84 #define DPRINTF(x) do { if (uath_debug) printf x; } while (0)
85 #define DPRINTFN(n, x) do { if (uath_debug >= (n)) printf x; } while (0)
86 int uath_debug = 1;
87 #else
88 #define DPRINTF(x)
89 #define DPRINTFN(n, x)
90 #endif
91
92
93
94
95
96 #define UATH_DEV(v, p, f) \
97 { { USB_VENDOR_##v, USB_PRODUCT_##v##_##p }, (f) }, \
98 { { USB_VENDOR_##v, USB_PRODUCT_##v##_##p##_NF }, \
99 (f) | UATH_FLAG_PRE_FIRMWARE }
100 #define UATH_DEV_UG(v, p) UATH_DEV(v, p, 0)
101 #define UATH_DEV_UX(v, p) UATH_DEV(v, p, UATH_FLAG_ABG)
102 static const struct uath_type {
103 struct usb_devno dev;
104 unsigned int flags;
105 #define UATH_FLAG_PRE_FIRMWARE (1 << 0)
106 #define UATH_FLAG_ABG (1 << 1)
107 } uath_devs[] = {
108 UATH_DEV_UG(ATHEROS, AR5523),
109 UATH_DEV_UG(ATHEROS2, AR5523_1),
110 UATH_DEV_UG(ATHEROS2, AR5523_2),
111 UATH_DEV_UX(ATHEROS2, AR5523_3),
112 UATH_DEV_UG(CONCEPTRONIC, AR5523_1),
113 UATH_DEV_UX(CONCEPTRONIC, AR5523_2),
114 UATH_DEV_UX(DLINK, DWLAG122),
115 UATH_DEV_UX(DLINK, DWLAG132),
116 UATH_DEV_UG(DLINK, DWLG132),
117 UATH_DEV_UG(GIGASET, AR5523),
118 UATH_DEV_UG(GIGASET, SMCWUSBTG),
119 UATH_DEV_UG(GLOBALSUN, AR5523_1),
120 UATH_DEV_UX(GLOBALSUN, AR5523_2),
121 UATH_DEV_UX(NETGEAR, WG111U),
122 UATH_DEV_UG(NETGEAR3, WG111T),
123 UATH_DEV_UG(NETGEAR3, WPN111),
124 UATH_DEV_UG(UMEDIA, AR5523_1),
125 UATH_DEV_UX(UMEDIA, AR5523_2),
126 UATH_DEV_UG(UMEDIA, TEW444UBEU),
127 UATH_DEV_UG(WISTRONNEWEB, AR5523_1),
128 UATH_DEV_UX(WISTRONNEWEB, AR5523_2),
129 UATH_DEV_UG(ZCOM, AR5523)
130 };
131 #define uath_lookup(v, p) \
132 ((const struct uath_type *)usb_lookup(uath_devs, v, p))
133
134 void uath_attachhook(void *);
135 int uath_open_pipes(struct uath_softc *);
136 void uath_close_pipes(struct uath_softc *);
137 int uath_alloc_tx_data_list(struct uath_softc *);
138 void uath_free_tx_data_list(struct uath_softc *);
139 int uath_alloc_rx_data_list(struct uath_softc *);
140 void uath_free_rx_data_list(struct uath_softc *);
141 void uath_free_rx_data(caddr_t, u_int, void *);
142 int uath_alloc_tx_cmd_list(struct uath_softc *);
143 void uath_free_tx_cmd_list(struct uath_softc *);
144 int uath_alloc_rx_cmd_list(struct uath_softc *);
145 void uath_free_rx_cmd_list(struct uath_softc *);
146 int uath_media_change(struct ifnet *);
147 void uath_stat(void *);
148 void uath_next_scan(void *);
149 void uath_task(void *);
150 int uath_newstate(struct ieee80211com *, enum ieee80211_state, int);
151 #ifdef UATH_DEBUG
152 void uath_dump_cmd(const uint8_t *, int, char);
153 #endif
154 int uath_cmd(struct uath_softc *, uint32_t, const void *, int, void *,
155 int);
156 int uath_cmd_write(struct uath_softc *, uint32_t, const void *, int, int);
157 int uath_cmd_read(struct uath_softc *, uint32_t, const void *, int, void *,
158 int);
159 int uath_write_reg(struct uath_softc *, uint32_t, uint32_t);
160 int uath_write_multi(struct uath_softc *, uint32_t, const void *, int);
161 int uath_read_reg(struct uath_softc *, uint32_t, uint32_t *);
162 int uath_read_eeprom(struct uath_softc *, uint32_t, void *);
163 void uath_cmd_rxeof(usbd_xfer_handle, usbd_private_handle, usbd_status);
164 void uath_data_rxeof(usbd_xfer_handle, usbd_private_handle, usbd_status);
165 void uath_data_txeof(usbd_xfer_handle, usbd_private_handle, usbd_status);
166 int uath_tx_null(struct uath_softc *);
167 int uath_tx_data(struct uath_softc *, struct mbuf *,
168 struct ieee80211_node *);
169 void uath_start(struct ifnet *);
170 void uath_watchdog(struct ifnet *);
171 int uath_ioctl(struct ifnet *, u_long, caddr_t);
172 int uath_query_eeprom(struct uath_softc *);
173 int uath_reset(struct uath_softc *);
174 int uath_reset_tx_queues(struct uath_softc *);
175 int uath_wme_init(struct uath_softc *);
176 int uath_set_chan(struct uath_softc *, struct ieee80211_channel *);
177 int uath_set_key(struct uath_softc *, const struct ieee80211_key *, int);
178 int uath_set_keys(struct uath_softc *);
179 int uath_set_rates(struct uath_softc *, const struct ieee80211_rateset *);
180 int uath_set_rxfilter(struct uath_softc *, uint32_t, uint32_t);
181 int uath_set_led(struct uath_softc *, int, int);
182 int uath_switch_channel(struct uath_softc *, struct ieee80211_channel *);
183 int uath_init(struct ifnet *);
184 void uath_stop(struct ifnet *, int);
185 int uath_loadfirmware(struct uath_softc *, const u_char *, int);
186 int uath_activate(struct device *, enum devact);
187
188 int uath_match(struct device *, void *, void *);
189 void uath_attach(struct device *, struct device *, void *);
190 int uath_detach(struct device *, int);
191 int uath_activate(struct device *, enum devact);
192
193 struct cfdriver uath_cd = {
194 NULL, "uath", DV_DULL
195 };
196
197 const struct cfattach uath_ca = {
198 sizeof(struct uath_softc),
199 uath_match,
200 uath_attach,
201 uath_detach,
202 uath_activate,
203 };
204
205 int
206 uath_match(struct device *parent, void *match, void *aux)
207 {
208 struct usb_attach_arg *uaa = aux;
209
210 if (uaa->iface != NULL)
211 return UMATCH_NONE;
212
213 return (uath_lookup(uaa->vendor, uaa->product) != NULL) ?
214 UMATCH_VENDOR_PRODUCT : UMATCH_NONE;
215 }
216
217 void
218 uath_attachhook(void *xsc)
219 {
220 struct uath_softc *sc = xsc;
221 u_char *fw;
222 size_t size;
223 int error;
224
225 if ((error = loadfirmware("uath-ar5523", &fw, &size)) != 0) {
226 printf("%s: could not read firmware (error=%d)\n",
227 sc->sc_dev.dv_xname, error);
228 return;
229 }
230
231 error = uath_loadfirmware(sc, fw, size);
232 free(fw, M_DEVBUF);
233
234 if (error == 0) {
235 usb_port_status_t status;
236
237
238
239
240
241
242 usbd_reset_port(sc->sc_uhub, sc->sc_port, &status);
243 usb_needs_reattach(sc->sc_udev);
244 } else {
245 printf("%s: could not load firmware (error=%s)\n",
246 sc->sc_dev.dv_xname, usbd_errstr(error));
247 }
248 }
249
250 void
251 uath_attach(struct device *parent, struct device *self, void *aux)
252 {
253 struct uath_softc *sc = (struct uath_softc *)self;
254 struct usb_attach_arg *uaa = aux;
255 struct ieee80211com *ic = &sc->sc_ic;
256 struct ifnet *ifp = &ic->ic_if;
257 usbd_status error;
258 char *devinfop;
259 int i;
260
261 sc->sc_udev = uaa->device;
262 sc->sc_uhub = uaa->device->myhub;
263 sc->sc_port = uaa->port;
264
265 devinfop = usbd_devinfo_alloc(uaa->device, 0);
266 printf("\n%s: %s\n", sc->sc_dev.dv_xname, devinfop);
267 usbd_devinfo_free(devinfop);
268
269 sc->sc_flags = uath_lookup(uaa->vendor, uaa->product)->flags;
270
271 if (usbd_set_config_no(sc->sc_udev, UATH_CONFIG_NO, 0) != 0) {
272 printf("%s: could not set configuration no\n",
273 sc->sc_dev.dv_xname);
274 return;
275 }
276
277
278 error = usbd_device2interface_handle(sc->sc_udev, UATH_IFACE_INDEX,
279 &sc->sc_iface);
280 if (error != 0) {
281 printf("%s: could not get interface handle\n",
282 sc->sc_dev.dv_xname);
283 return;
284 }
285
286
287
288
289
290 if (uath_open_pipes(sc) != 0) {
291 printf("%s: could not open pipes\n", sc->sc_dev.dv_xname);
292 return;
293 }
294
295 if (sc->sc_flags & UATH_FLAG_PRE_FIRMWARE) {
296 if (rootvp == NULL)
297 mountroothook_establish(uath_attachhook, sc);
298 else
299 uath_attachhook(sc);
300 return;
301 }
302
303
304
305
306 usb_init_task(&sc->sc_task, uath_task, sc);
307 timeout_set(&sc->scan_to, uath_next_scan, sc);
308 timeout_set(&sc->stat_to, uath_stat, sc);
309
310
311
312
313 if (uath_alloc_tx_cmd_list(sc) != 0) {
314 printf("%s: could not allocate Tx command list\n",
315 sc->sc_dev.dv_xname);
316 goto fail1;
317 }
318 if (uath_alloc_rx_cmd_list(sc) != 0) {
319 printf("%s: could not allocate Rx command list\n",
320 sc->sc_dev.dv_xname);
321 goto fail2;
322 }
323
324
325
326
327 for (i = 0; i < UATH_RX_CMD_LIST_COUNT; i++) {
328 struct uath_rx_cmd *cmd = &sc->rx_cmd[i];
329
330 usbd_setup_xfer(cmd->xfer, sc->cmd_rx_pipe, cmd, cmd->buf,
331 UATH_MAX_RXCMDSZ, USBD_SHORT_XFER_OK | USBD_NO_COPY,
332 USBD_NO_TIMEOUT, uath_cmd_rxeof);
333 error = usbd_transfer(cmd->xfer);
334 if (error != USBD_IN_PROGRESS && error != 0) {
335 printf("%s: could not queue Rx command xfer\n",
336 sc->sc_dev.dv_xname);
337 goto fail3;
338 }
339 }
340
341
342
343
344 if (uath_reset(sc) != 0) {
345 printf("%s: could not initialize adapter\n",
346 sc->sc_dev.dv_xname);
347 goto fail3;
348 }
349 if (uath_query_eeprom(sc) != 0) {
350 printf("%s: could not read EEPROM\n", sc->sc_dev.dv_xname);
351 goto fail3;
352 }
353
354 printf("%s: MAC/BBP AR5523, RF AR%c112, address %s\n",
355 sc->sc_dev.dv_xname, (sc->sc_flags & UATH_FLAG_ABG) ? '5': '2',
356 ether_sprintf(ic->ic_myaddr));
357
358
359
360
361 if (uath_alloc_tx_data_list(sc) != 0) {
362 printf("%s: could not allocate Tx data list\n",
363 sc->sc_dev.dv_xname);
364 goto fail3;
365 }
366 if (uath_alloc_rx_data_list(sc) != 0) {
367 printf("%s: could not allocate Rx data list\n",
368 sc->sc_dev.dv_xname);
369 goto fail4;
370 }
371
372 ic->ic_phytype = IEEE80211_T_OFDM;
373 ic->ic_opmode = IEEE80211_M_STA;
374 ic->ic_state = IEEE80211_S_INIT;
375
376
377 ic->ic_caps =
378 IEEE80211_C_TXPMGT |
379 IEEE80211_C_SHPREAMBLE |
380 IEEE80211_C_SHSLOT |
381 IEEE80211_C_WEP;
382
383
384 ic->ic_sup_rates[IEEE80211_MODE_11B] = ieee80211_std_rateset_11b;
385 ic->ic_sup_rates[IEEE80211_MODE_11G] = ieee80211_std_rateset_11g;
386
387
388 for (i = 1; i <= 14; i++) {
389 ic->ic_channels[i].ic_freq =
390 ieee80211_ieee2mhz(i, IEEE80211_CHAN_2GHZ);
391 ic->ic_channels[i].ic_flags =
392 IEEE80211_CHAN_CCK | IEEE80211_CHAN_OFDM |
393 IEEE80211_CHAN_DYN | IEEE80211_CHAN_2GHZ;
394 }
395
396 ifp->if_softc = sc;
397 ifp->if_flags = IFF_BROADCAST | IFF_SIMPLEX | IFF_MULTICAST;
398 ifp->if_init = uath_init;
399 ifp->if_ioctl = uath_ioctl;
400 ifp->if_start = uath_start;
401 ifp->if_watchdog = uath_watchdog;
402 IFQ_SET_READY(&ifp->if_snd);
403 memcpy(ifp->if_xname, sc->sc_dev.dv_xname, IFNAMSIZ);
404
405 if_attach(ifp);
406 ieee80211_ifattach(ifp);
407
408
409 sc->sc_newstate = ic->ic_newstate;
410 ic->ic_newstate = uath_newstate;
411 ieee80211_media_init(ifp, uath_media_change, ieee80211_media_status);
412
413 #if NBPFILTER > 0
414 bpfattach(&sc->sc_drvbpf, ifp, DLT_IEEE802_11_RADIO,
415 sizeof (struct ieee80211_frame) + IEEE80211_RADIOTAP_HDRLEN);
416
417 sc->sc_rxtap_len = sizeof sc->sc_rxtapu;
418 sc->sc_rxtap.wr_ihdr.it_len = htole16(sc->sc_rxtap_len);
419 sc->sc_rxtap.wr_ihdr.it_present = htole32(UATH_RX_RADIOTAP_PRESENT);
420
421 sc->sc_txtap_len = sizeof sc->sc_txtapu;
422 sc->sc_txtap.wt_ihdr.it_len = htole16(sc->sc_txtap_len);
423 sc->sc_txtap.wt_ihdr.it_present = htole32(UATH_TX_RADIOTAP_PRESENT);
424 #endif
425
426 usbd_add_drv_event(USB_EVENT_DRIVER_ATTACH, sc->sc_udev,
427 &sc->sc_dev);
428
429 return;
430
431 fail4: uath_free_tx_data_list(sc);
432 fail3: uath_free_rx_cmd_list(sc);
433 fail2: uath_free_tx_cmd_list(sc);
434 fail1: uath_close_pipes(sc);
435 }
436
437 int
438 uath_detach(struct device *self, int flags)
439 {
440 struct uath_softc *sc = (struct uath_softc *)self;
441 struct ifnet *ifp = &sc->sc_ic.ic_if;
442 int s;
443
444 s = splnet();
445
446 if (sc->sc_flags & UATH_FLAG_PRE_FIRMWARE) {
447 uath_close_pipes(sc);
448 splx(s);
449 return 0;
450 }
451
452
453
454 usb_rem_task(sc->sc_udev, &sc->sc_task);
455 timeout_del(&sc->scan_to);
456 timeout_del(&sc->stat_to);
457
458 ieee80211_ifdetach(ifp);
459 if_detach(ifp);
460
461 sc->sc_dying = 1;
462 DPRINTF(("reclaiming %d references\n", sc->sc_refcnt));
463 while (sc->sc_refcnt > 0)
464 (void)tsleep(UATH_COND_NOREF(sc), 0, "uathdet", 0);
465 DPRINTF(("all references reclaimed\n"));
466
467
468 uath_free_tx_data_list(sc);
469 uath_free_rx_data_list(sc);
470 uath_free_tx_cmd_list(sc);
471 uath_free_rx_cmd_list(sc);
472
473
474 uath_close_pipes(sc);
475
476 splx(s);
477
478 usbd_add_drv_event(USB_EVENT_DRIVER_DETACH, sc->sc_udev,
479 &sc->sc_dev);
480
481 return 0;
482 }
483
484 int
485 uath_open_pipes(struct uath_softc *sc)
486 {
487 int error;
488
489
490
491
492
493
494 error = usbd_open_pipe(sc->sc_iface, 0x01, USBD_EXCLUSIVE_USE,
495 &sc->cmd_tx_pipe);
496 if (error != 0) {
497 printf("%s: could not open Tx command pipe: %s\n",
498 sc->sc_dev.dv_xname, usbd_errstr(error));
499 goto fail;
500 }
501
502 error = usbd_open_pipe(sc->sc_iface, 0x02, USBD_EXCLUSIVE_USE,
503 &sc->data_tx_pipe);
504 if (error != 0) {
505 printf("%s: could not open Tx data pipe: %s\n",
506 sc->sc_dev.dv_xname, usbd_errstr(error));
507 goto fail;
508 }
509
510 error = usbd_open_pipe(sc->sc_iface, 0x81, USBD_EXCLUSIVE_USE,
511 &sc->cmd_rx_pipe);
512 if (error != 0) {
513 printf("%s: could not open Rx command pipe: %s\n",
514 sc->sc_dev.dv_xname, usbd_errstr(error));
515 goto fail;
516 }
517
518 error = usbd_open_pipe(sc->sc_iface, 0x82, USBD_EXCLUSIVE_USE,
519 &sc->data_rx_pipe);
520 if (error != 0) {
521 printf("%s: could not open Rx data pipe: %s\n",
522 sc->sc_dev.dv_xname, usbd_errstr(error));
523 goto fail;
524 }
525
526 return 0;
527
528 fail: uath_close_pipes(sc);
529 return error;
530 }
531
532 void
533 uath_close_pipes(struct uath_softc *sc)
534 {
535
536
537 if (sc->data_tx_pipe != NULL)
538 usbd_close_pipe(sc->data_tx_pipe);
539
540 if (sc->data_rx_pipe != NULL)
541 usbd_close_pipe(sc->data_rx_pipe);
542
543 if (sc->cmd_tx_pipe != NULL)
544 usbd_close_pipe(sc->cmd_tx_pipe);
545
546 if (sc->cmd_rx_pipe != NULL)
547 usbd_close_pipe(sc->cmd_rx_pipe);
548 }
549
550 int
551 uath_alloc_tx_data_list(struct uath_softc *sc)
552 {
553 int i, error;
554
555 for (i = 0; i < UATH_TX_DATA_LIST_COUNT; i++) {
556 struct uath_tx_data *data = &sc->tx_data[i];
557
558 data->sc = sc;
559
560 data->xfer = usbd_alloc_xfer(sc->sc_udev);
561 if (data->xfer == NULL) {
562 printf("%s: could not allocate xfer\n",
563 sc->sc_dev.dv_xname);
564 error = ENOMEM;
565 goto fail;
566 }
567 data->buf = usbd_alloc_buffer(data->xfer, UATH_MAX_TXBUFSZ);
568 if (data->buf == NULL) {
569 printf("%s: could not allocate xfer buffer\n",
570 sc->sc_dev.dv_xname);
571 error = ENOMEM;
572 goto fail;
573 }
574 }
575 return 0;
576
577 fail: uath_free_tx_data_list(sc);
578 return error;
579 }
580
581 void
582 uath_free_tx_data_list(struct uath_softc *sc)
583 {
584 int i;
585
586
587 usbd_abort_pipe(sc->data_tx_pipe);
588
589 for (i = 0; i < UATH_TX_DATA_LIST_COUNT; i++)
590 if (sc->tx_data[i].xfer != NULL)
591 usbd_free_xfer(sc->tx_data[i].xfer);
592 }
593
594 int
595 uath_alloc_rx_data_list(struct uath_softc *sc)
596 {
597 int i, error;
598
599 SLIST_INIT(&sc->rx_freelist);
600 for (i = 0; i < UATH_RX_DATA_POOL_COUNT; i++) {
601 struct uath_rx_data *data = &sc->rx_data[i];
602
603 data->sc = sc;
604
605 data->xfer = usbd_alloc_xfer(sc->sc_udev);
606 if (data->xfer == NULL) {
607 printf("%s: could not allocate xfer\n",
608 sc->sc_dev.dv_xname);
609 error = ENOMEM;
610 goto fail;
611 }
612 data->buf = usbd_alloc_buffer(data->xfer, sc->rxbufsz);
613 if (data->buf == NULL) {
614 printf("%s: could not allocate xfer buffer\n",
615 sc->sc_dev.dv_xname);
616 error = ENOMEM;
617 goto fail;
618 }
619 SLIST_INSERT_HEAD(&sc->rx_freelist, data, next);
620 }
621 return 0;
622
623 fail: uath_free_rx_data_list(sc);
624 return error;
625 }
626
627 void
628 uath_free_rx_data_list(struct uath_softc *sc)
629 {
630 int i;
631
632
633 usbd_abort_pipe(sc->data_rx_pipe);
634
635 for (i = 0; i < UATH_RX_DATA_POOL_COUNT; i++)
636 if (sc->rx_data[i].xfer != NULL)
637 usbd_free_xfer(sc->rx_data[i].xfer);
638 }
639
640 void
641 uath_free_rx_data(caddr_t buf, u_int size, void *arg)
642 {
643 struct uath_rx_data *data = arg;
644 struct uath_softc *sc = data->sc;
645
646
647 SLIST_INSERT_HEAD(&sc->rx_freelist, data, next);
648
649
650 if (--sc->sc_refcnt == 0 && sc->sc_dying)
651 wakeup(UATH_COND_NOREF(sc));
652 }
653
654 int
655 uath_alloc_tx_cmd_list(struct uath_softc *sc)
656 {
657 int i, error;
658
659 for (i = 0; i < UATH_TX_CMD_LIST_COUNT; i++) {
660 struct uath_tx_cmd *cmd = &sc->tx_cmd[i];
661
662 cmd->sc = sc;
663
664 cmd->xfer = usbd_alloc_xfer(sc->sc_udev);
665 if (cmd->xfer == NULL) {
666 printf("%s: could not allocate xfer\n",
667 sc->sc_dev.dv_xname);
668 error = ENOMEM;
669 goto fail;
670 }
671 cmd->buf = usbd_alloc_buffer(cmd->xfer, UATH_MAX_TXCMDSZ);
672 if (cmd->buf == NULL) {
673 printf("%s: could not allocate xfer buffer\n",
674 sc->sc_dev.dv_xname);
675 error = ENOMEM;
676 goto fail;
677 }
678 }
679 return 0;
680
681 fail: uath_free_tx_cmd_list(sc);
682 return error;
683 }
684
685 void
686 uath_free_tx_cmd_list(struct uath_softc *sc)
687 {
688 int i;
689
690
691 usbd_abort_pipe(sc->cmd_tx_pipe);
692
693 for (i = 0; i < UATH_TX_CMD_LIST_COUNT; i++)
694 if (sc->tx_cmd[i].xfer != NULL)
695 usbd_free_xfer(sc->tx_cmd[i].xfer);
696 }
697
698 int
699 uath_alloc_rx_cmd_list(struct uath_softc *sc)
700 {
701 int i, error;
702
703 for (i = 0; i < UATH_RX_CMD_LIST_COUNT; i++) {
704 struct uath_rx_cmd *cmd = &sc->rx_cmd[i];
705
706 cmd->sc = sc;
707
708 cmd->xfer = usbd_alloc_xfer(sc->sc_udev);
709 if (cmd->xfer == NULL) {
710 printf("%s: could not allocate xfer\n",
711 sc->sc_dev.dv_xname);
712 error = ENOMEM;
713 goto fail;
714 }
715 cmd->buf = usbd_alloc_buffer(cmd->xfer, UATH_MAX_RXCMDSZ);
716 if (cmd->buf == NULL) {
717 printf("%s: could not allocate xfer buffer\n",
718 sc->sc_dev.dv_xname);
719 error = ENOMEM;
720 goto fail;
721 }
722 }
723 return 0;
724
725 fail: uath_free_rx_cmd_list(sc);
726 return error;
727 }
728
729 void
730 uath_free_rx_cmd_list(struct uath_softc *sc)
731 {
732 int i;
733
734
735 usbd_abort_pipe(sc->cmd_rx_pipe);
736
737 for (i = 0; i < UATH_RX_CMD_LIST_COUNT; i++)
738 if (sc->rx_cmd[i].xfer != NULL)
739 usbd_free_xfer(sc->rx_cmd[i].xfer);
740 }
741
742 int
743 uath_media_change(struct ifnet *ifp)
744 {
745 int error;
746
747 error = ieee80211_media_change(ifp);
748 if (error != ENETRESET)
749 return error;
750
751 if ((ifp->if_flags & (IFF_UP | IFF_RUNNING)) == (IFF_UP | IFF_RUNNING))
752 uath_init(ifp);
753
754 return 0;
755 }
756
757
758
759
760
761 void
762 uath_stat(void *arg)
763 {
764 struct uath_softc *sc = arg;
765 int error;
766
767
768
769
770
771 error = uath_cmd_write(sc, UATH_CMD_STATS, NULL, 0,
772 UATH_CMD_FLAG_ASYNC);
773 if (error != 0) {
774 printf("%s: could not query statistics (error=%d)\n",
775 sc->sc_dev.dv_xname, error);
776 }
777 }
778
779
780
781
782
783 void
784 uath_next_scan(void *arg)
785 {
786 struct uath_softc *sc = arg;
787 struct ieee80211com *ic = &sc->sc_ic;
788 struct ifnet *ifp = &ic->ic_if;
789
790 if (ic->ic_state == IEEE80211_S_SCAN)
791 ieee80211_next_scan(ifp);
792 }
793
794 void
795 uath_task(void *arg)
796 {
797 struct uath_softc *sc = arg;
798 struct ieee80211com *ic = &sc->sc_ic;
799 enum ieee80211_state ostate;
800
801 ostate = ic->ic_state;
802
803 switch (sc->sc_state) {
804 case IEEE80211_S_INIT:
805 if (ostate == IEEE80211_S_RUN) {
806
807 (void)uath_set_led(sc, UATH_LED_LINK, 0);
808 (void)uath_set_led(sc, UATH_LED_ACTIVITY, 0);
809 }
810 break;
811
812 case IEEE80211_S_SCAN:
813 if (uath_switch_channel(sc, ic->ic_bss->ni_chan) != 0) {
814 printf("%s: could not switch channel\n",
815 sc->sc_dev.dv_xname);
816 break;
817 }
818 timeout_add(&sc->scan_to, hz / 4);
819 break;
820
821 case IEEE80211_S_AUTH:
822 {
823 struct ieee80211_node *ni = ic->ic_bss;
824 struct uath_cmd_bssid bssid;
825 struct uath_cmd_0b cmd0b;
826 struct uath_cmd_0c cmd0c;
827
828 if (uath_switch_channel(sc, ni->ni_chan) != 0) {
829 printf("%s: could not switch channel\n",
830 sc->sc_dev.dv_xname);
831 break;
832 }
833
834 (void)uath_cmd_write(sc, UATH_CMD_24, NULL, 0, 0);
835
836 bzero(&bssid, sizeof bssid);
837 bssid.len = htobe32(IEEE80211_ADDR_LEN);
838 IEEE80211_ADDR_COPY(bssid.bssid, ni->ni_bssid);
839 (void)uath_cmd_write(sc, UATH_CMD_SET_BSSID, &bssid,
840 sizeof bssid, 0);
841
842 bzero(&cmd0b, sizeof cmd0b);
843 cmd0b.code = htobe32(2);
844 cmd0b.size = htobe32(sizeof (cmd0b.data));
845 (void)uath_cmd_write(sc, UATH_CMD_0B, &cmd0b, sizeof cmd0b, 0);
846
847 bzero(&cmd0c, sizeof cmd0c);
848 cmd0c.magic1 = htobe32(2);
849 cmd0c.magic2 = htobe32(7);
850 cmd0c.magic3 = htobe32(1);
851 (void)uath_cmd_write(sc, UATH_CMD_0C, &cmd0c, sizeof cmd0c, 0);
852
853 if (uath_set_rates(sc, &ni->ni_rates) != 0) {
854 printf("%s: could not set negotiated rate set\n",
855 sc->sc_dev.dv_xname);
856 break;
857 }
858 break;
859 }
860
861 case IEEE80211_S_ASSOC:
862 break;
863
864 case IEEE80211_S_RUN:
865 {
866 struct ieee80211_node *ni = ic->ic_bss;
867 struct uath_cmd_bssid bssid;
868 struct uath_cmd_xled xled;
869 uint32_t val;
870
871 if (ic->ic_opmode == IEEE80211_M_MONITOR) {
872
873 bzero(&xled, sizeof xled);
874 xled.which = htobe32(0);
875 xled.rate = htobe32(1);
876 xled.mode = htobe32(2);
877 (void)uath_cmd_write(sc, UATH_CMD_SET_XLED, &xled,
878 sizeof xled, 0);
879 break;
880 }
881
882
883
884
885
886 ni->ni_txrate = ni->ni_rates.rs_nrates - 1;
887
888 val = htobe32(1);
889 (void)uath_cmd_write(sc, UATH_CMD_2E, &val, sizeof val, 0);
890
891 bzero(&bssid, sizeof bssid);
892 bssid.flags1 = htobe32(0xc004);
893 bssid.flags2 = htobe32(0x003b);
894 bssid.len = htobe32(IEEE80211_ADDR_LEN);
895 IEEE80211_ADDR_COPY(bssid.bssid, ni->ni_bssid);
896 (void)uath_cmd_write(sc, UATH_CMD_SET_BSSID, &bssid,
897 sizeof bssid, 0);
898
899
900 (void)uath_set_led(sc, UATH_LED_LINK, 1);
901
902
903 bzero(&xled, sizeof xled);
904 xled.which = htobe32(1);
905 xled.rate = htobe32(1);
906 xled.mode = htobe32(2);
907 (void)uath_cmd_write(sc, UATH_CMD_SET_XLED, &xled, sizeof xled,
908 0);
909
910
911 val = htobe32(1);
912 (void)uath_cmd_write(sc, UATH_CMD_SET_STATE, &val, sizeof val,
913 0);
914
915
916 timeout_add(&sc->stat_to, hz);
917 break;
918 }
919 }
920 sc->sc_newstate(ic, sc->sc_state, sc->sc_arg);
921 }
922
923 int
924 uath_newstate(struct ieee80211com *ic, enum ieee80211_state nstate, int arg)
925 {
926 struct uath_softc *sc = ic->ic_softc;
927
928 usb_rem_task(sc->sc_udev, &sc->sc_task);
929 timeout_del(&sc->scan_to);
930 timeout_del(&sc->stat_to);
931
932
933 sc->sc_state = nstate;
934 sc->sc_arg = arg;
935 usb_add_task(sc->sc_udev, &sc->sc_task);
936 return 0;
937 }
938
939 #ifdef UATH_DEBUG
940 void
941 uath_dump_cmd(const uint8_t *buf, int len, char prefix)
942 {
943 int i;
944
945 for (i = 0; i < len; i++) {
946 if ((i % 16) == 0)
947 printf("\n%c ", prefix);
948 else if ((i % 4) == 0)
949 printf(" ");
950 printf("%02x", buf[i]);
951 }
952 printf("\n");
953 }
954 #endif
955
956
957
958
959 int
960 uath_cmd(struct uath_softc *sc, uint32_t code, const void *idata, int ilen,
961 void *odata, int flags)
962 {
963 struct uath_cmd_hdr *hdr;
964 struct uath_tx_cmd *cmd;
965 uint16_t xferflags;
966 int s, xferlen, error;
967
968
969 cmd = &sc->tx_cmd[sc->cmd_idx];
970
971
972 xferlen = (sizeof (struct uath_cmd_hdr) + ilen + 3) & ~3;
973
974 hdr = (struct uath_cmd_hdr *)cmd->buf;
975 bzero(hdr, sizeof (struct uath_cmd_hdr));
976 hdr->len = htobe32(xferlen);
977 hdr->code = htobe32(code);
978 hdr->priv = sc->cmd_idx;
979 hdr->magic = htobe32((flags & UATH_CMD_FLAG_MAGIC) ? 1 << 24 : 0);
980 bcopy(idata, (uint8_t *)(hdr + 1), ilen);
981
982 #ifdef UATH_DEBUG
983 if (uath_debug >= 5) {
984 printf("sending command code=0x%02x flags=0x%x index=%u",
985 code, flags, sc->cmd_idx);
986 uath_dump_cmd(cmd->buf, xferlen, '+');
987 }
988 #endif
989 xferflags = USBD_FORCE_SHORT_XFER | USBD_NO_COPY;
990 if (!(flags & UATH_CMD_FLAG_READ)) {
991 if (!(flags & UATH_CMD_FLAG_ASYNC))
992 xferflags |= USBD_SYNCHRONOUS;
993 } else
994 s = splusb();
995
996 cmd->odata = odata;
997
998 usbd_setup_xfer(cmd->xfer, sc->cmd_tx_pipe, cmd, cmd->buf, xferlen,
999 xferflags, UATH_CMD_TIMEOUT, NULL);
1000 error = usbd_transfer(cmd->xfer);
1001 if (error != USBD_IN_PROGRESS && error != 0) {
1002 if (flags & UATH_CMD_FLAG_READ)
1003 splx(s);
1004 printf("%s: could not send command 0x%x (error=%s)\n",
1005 sc->sc_dev.dv_xname, code, usbd_errstr(error));
1006 return error;
1007 }
1008 sc->cmd_idx = (sc->cmd_idx + 1) % UATH_TX_CMD_LIST_COUNT;
1009
1010 if (!(flags & UATH_CMD_FLAG_READ))
1011 return 0;
1012
1013
1014 error = tsleep(cmd, PCATCH, "uathcmd", 2 * hz);
1015 cmd->odata = NULL;
1016 splx(s);
1017 if (error != 0) {
1018 printf("%s: timeout waiting for command reply\n",
1019 sc->sc_dev.dv_xname);
1020 }
1021 return error;
1022 }
1023
1024 int
1025 uath_cmd_write(struct uath_softc *sc, uint32_t code, const void *data, int len,
1026 int flags)
1027 {
1028 flags &= ~UATH_CMD_FLAG_READ;
1029 return uath_cmd(sc, code, data, len, NULL, flags);
1030 }
1031
1032 int
1033 uath_cmd_read(struct uath_softc *sc, uint32_t code, const void *idata,
1034 int ilen, void *odata, int flags)
1035 {
1036 flags |= UATH_CMD_FLAG_READ;
1037 return uath_cmd(sc, code, idata, ilen, odata, flags);
1038 }
1039
1040 int
1041 uath_write_reg(struct uath_softc *sc, uint32_t reg, uint32_t val)
1042 {
1043 struct uath_write_mac write;
1044 int error;
1045
1046 write.reg = htobe32(reg);
1047 write.len = htobe32(0);
1048 *(uint32_t *)write.data = htobe32(val);
1049
1050 error = uath_cmd_write(sc, UATH_CMD_WRITE_MAC, &write,
1051 3 * sizeof (uint32_t), 0);
1052 if (error != 0) {
1053 printf("%s: could not write register 0x%02x\n",
1054 sc->sc_dev.dv_xname, reg);
1055 }
1056 return error;
1057 }
1058
1059 int
1060 uath_write_multi(struct uath_softc *sc, uint32_t reg, const void *data,
1061 int len)
1062 {
1063 struct uath_write_mac write;
1064 int error;
1065
1066 write.reg = htobe32(reg);
1067 write.len = htobe32(len);
1068 bcopy(data, write.data, len);
1069
1070
1071 error = uath_cmd_write(sc, UATH_CMD_WRITE_MAC, &write,
1072 (len == 0) ? sizeof (uint32_t) : 2 * sizeof (uint32_t) + len, 0);
1073 if (error != 0) {
1074 printf("%s: could not write %d bytes to register 0x%02x\n",
1075 sc->sc_dev.dv_xname, len, reg);
1076 }
1077 return error;
1078 }
1079
1080 int
1081 uath_read_reg(struct uath_softc *sc, uint32_t reg, uint32_t *val)
1082 {
1083 struct uath_read_mac read;
1084 int error;
1085
1086 reg = htobe32(reg);
1087 error = uath_cmd_read(sc, UATH_CMD_READ_MAC, ®, sizeof reg, &read,
1088 0);
1089 if (error != 0) {
1090 printf("%s: could not read register 0x%02x\n",
1091 sc->sc_dev.dv_xname, betoh32(reg));
1092 return error;
1093 }
1094 *val = betoh32(*(uint32_t *)read.data);
1095 return error;
1096 }
1097
1098 int
1099 uath_read_eeprom(struct uath_softc *sc, uint32_t reg, void *odata)
1100 {
1101 struct uath_read_mac read;
1102 int len, error;
1103
1104 reg = htobe32(reg);
1105 error = uath_cmd_read(sc, UATH_CMD_READ_EEPROM, ®, sizeof reg,
1106 &read, 0);
1107 if (error != 0) {
1108 printf("%s: could not read EEPROM offset 0x%02x\n",
1109 sc->sc_dev.dv_xname, betoh32(reg));
1110 return error;
1111 }
1112 len = betoh32(read.len);
1113 bcopy(read.data, odata, (len == 0) ? sizeof (uint32_t) : len);
1114 return error;
1115 }
1116
1117 void
1118 uath_cmd_rxeof(usbd_xfer_handle xfer, usbd_private_handle priv,
1119 usbd_status status)
1120 {
1121 struct uath_rx_cmd *cmd = priv;
1122 struct uath_softc *sc = cmd->sc;
1123 struct uath_cmd_hdr *hdr;
1124
1125 if (status != USBD_NORMAL_COMPLETION) {
1126 if (status == USBD_STALLED)
1127 usbd_clear_endpoint_stall_async(sc->cmd_rx_pipe);
1128 return;
1129 }
1130
1131 hdr = (struct uath_cmd_hdr *)cmd->buf;
1132
1133 #ifdef UATH_DEBUG
1134 if (uath_debug >= 5) {
1135 printf("received command code=0x%x index=%u len=%u",
1136 betoh32(hdr->code), hdr->priv, betoh32(hdr->len));
1137 uath_dump_cmd(cmd->buf, betoh32(hdr->len), '-');
1138 }
1139 #endif
1140
1141 switch (betoh32(hdr->code) & 0xff) {
1142
1143 default:
1144 {
1145 struct uath_tx_cmd *txcmd = &sc->tx_cmd[hdr->priv];
1146
1147 if (txcmd->odata != NULL) {
1148
1149 bcopy((uint8_t *)(hdr + 1), txcmd->odata,
1150 betoh32(hdr->len) - sizeof (struct uath_cmd_hdr));
1151 }
1152 wakeup(txcmd);
1153 break;
1154 }
1155
1156 case UATH_NOTIF_READY:
1157 DPRINTF(("received device ready notification\n"));
1158 wakeup(UATH_COND_INIT(sc));
1159 break;
1160
1161 case UATH_NOTIF_TX:
1162
1163 DPRINTF(("received Tx notification\n"));
1164 break;
1165
1166 case UATH_NOTIF_STATS:
1167 DPRINTFN(2, ("received device statistics\n"));
1168 timeout_add(&sc->stat_to, hz);
1169 break;
1170 }
1171
1172
1173 usbd_setup_xfer(xfer, sc->cmd_rx_pipe, cmd, cmd->buf, UATH_MAX_RXCMDSZ,
1174 USBD_SHORT_XFER_OK | USBD_NO_COPY, USBD_NO_TIMEOUT,
1175 uath_cmd_rxeof);
1176 (void)usbd_transfer(xfer);
1177 }
1178
1179 void
1180 uath_data_rxeof(usbd_xfer_handle xfer, usbd_private_handle priv,
1181 usbd_status status)
1182 {
1183 struct uath_rx_data *data = priv;
1184 struct uath_softc *sc = data->sc;
1185 struct ieee80211com *ic = &sc->sc_ic;
1186 struct ifnet *ifp = &ic->ic_if;
1187 struct ieee80211_frame *wh;
1188 struct ieee80211_node *ni;
1189 struct uath_rx_data *ndata;
1190 struct uath_rx_desc *desc;
1191 struct mbuf *m;
1192 uint32_t hdr;
1193 int s, len;
1194
1195 if (status != USBD_NORMAL_COMPLETION) {
1196 if (status == USBD_NOT_STARTED || status == USBD_CANCELLED)
1197 return;
1198
1199 if (status == USBD_STALLED)
1200 usbd_clear_endpoint_stall_async(sc->data_rx_pipe);
1201
1202 ifp->if_ierrors++;
1203 return;
1204 }
1205 usbd_get_xfer_status(xfer, NULL, NULL, &len, NULL);
1206
1207 if (len < UATH_MIN_RXBUFSZ) {
1208 DPRINTF(("wrong xfer size (len=%d)\n", len));
1209 ifp->if_ierrors++;
1210 goto skip;
1211 }
1212
1213 hdr = betoh32(*(uint32_t *)data->buf);
1214
1215
1216 desc = (struct uath_rx_desc *)
1217 (data->buf + len - sizeof (struct uath_rx_desc));
1218
1219 if (betoh32(desc->len) > sc->rxbufsz) {
1220 DPRINTF(("bad descriptor (len=%d)\n", betoh32(desc->len)));
1221 ifp->if_ierrors++;
1222 goto skip;
1223 }
1224
1225
1226
1227 MGETHDR(m, M_DONTWAIT, MT_DATA);
1228 if (m == NULL) {
1229 ifp->if_ierrors++;
1230 goto skip;
1231 }
1232
1233
1234 ndata = SLIST_FIRST(&sc->rx_freelist);
1235 if (ndata == NULL) {
1236 printf("%s: could not allocate Rx buffer\n",
1237 sc->sc_dev.dv_xname);
1238 m_freem(m);
1239 ifp->if_ierrors++;
1240 goto skip;
1241 }
1242 SLIST_REMOVE_HEAD(&sc->rx_freelist, next);
1243
1244 MEXTADD(m, data->buf, sc->rxbufsz, 0, uath_free_rx_data, data);
1245
1246
1247 m->m_pkthdr.rcvif = ifp;
1248 m->m_data = data->buf + sizeof (uint32_t);
1249 m->m_pkthdr.len = m->m_len = betoh32(desc->len) -
1250 sizeof (struct uath_rx_desc) - IEEE80211_CRC_LEN;
1251
1252 data = ndata;
1253
1254 wh = mtod(m, struct ieee80211_frame *);
1255 if ((wh->i_fc[1] & IEEE80211_FC1_WEP) &&
1256 ic->ic_opmode != IEEE80211_M_MONITOR) {
1257
1258
1259
1260
1261
1262 wh->i_fc[1] &= ~IEEE80211_FC1_WEP;
1263 ovbcopy(wh, (caddr_t)wh + IEEE80211_WEP_IVLEN +
1264 IEEE80211_WEP_KIDLEN, sizeof (struct ieee80211_frame));
1265 m_adj(m, IEEE80211_WEP_IVLEN + IEEE80211_WEP_KIDLEN);
1266 m_adj(m, -IEEE80211_WEP_CRCLEN);
1267 wh = mtod(m, struct ieee80211_frame *);
1268 }
1269
1270 #if NBPFILTER > 0
1271
1272 if (sc->sc_drvbpf != NULL) {
1273 struct mbuf mb;
1274 struct uath_rx_radiotap_header *tap = &sc->sc_rxtap;
1275
1276 tap->wr_flags = 0;
1277 tap->wr_chan_freq = htole16(betoh32(desc->freq));
1278 tap->wr_chan_flags = htole16(ic->ic_bss->ni_chan->ic_flags);
1279 tap->wr_dbm_antsignal = (int8_t)betoh32(desc->rssi);
1280
1281 mb.m_data = (caddr_t)tap;
1282 mb.m_len = sc->sc_rxtap_len;
1283 mb.m_next = m;
1284 mb.m_nextpkt = NULL;
1285 mb.m_type = 0;
1286 mb.m_flags = 0;
1287 bpf_mtap(sc->sc_drvbpf, &mb, BPF_DIRECTION_IN);
1288 }
1289 #endif
1290
1291 s = splnet();
1292 sc->sc_refcnt++;
1293 ni = ieee80211_find_rxnode(ic, wh);
1294 ieee80211_input(ifp, m, ni, (int)betoh32(desc->rssi), 0);
1295
1296
1297 ieee80211_release_node(ic, ni);
1298 splx(s);
1299
1300 skip:
1301 usbd_setup_xfer(data->xfer, sc->data_rx_pipe, data, data->buf,
1302 sc->rxbufsz, USBD_SHORT_XFER_OK | USBD_NO_COPY, USBD_NO_TIMEOUT,
1303 uath_data_rxeof);
1304 (void)usbd_transfer(data->xfer);
1305 }
1306
1307 int
1308 uath_tx_null(struct uath_softc *sc)
1309 {
1310 struct uath_tx_data *data;
1311 struct uath_tx_desc *desc;
1312
1313 data = &sc->tx_data[sc->data_idx];
1314
1315 data->ni = NULL;
1316
1317 *(uint32_t *)data->buf = UATH_MAKECTL(1, sizeof (struct uath_tx_desc));
1318 desc = (struct uath_tx_desc *)(data->buf + sizeof (uint32_t));
1319
1320 bzero(desc, sizeof (struct uath_tx_desc));
1321 desc->len = htobe32(sizeof (struct uath_tx_desc));
1322 desc->type = htobe32(UATH_TX_NULL);
1323
1324 usbd_setup_xfer(data->xfer, sc->data_tx_pipe, data, data->buf,
1325 sizeof (uint32_t) + sizeof (struct uath_tx_desc), USBD_NO_COPY |
1326 USBD_FORCE_SHORT_XFER, UATH_DATA_TIMEOUT, NULL);
1327 if (usbd_sync_transfer(data->xfer) != 0)
1328 return EIO;
1329
1330 sc->data_idx = (sc->data_idx + 1) % UATH_TX_DATA_LIST_COUNT;
1331
1332 return uath_cmd_write(sc, UATH_CMD_0F, NULL, 0, UATH_CMD_FLAG_ASYNC);
1333 }
1334
1335 void
1336 uath_data_txeof(usbd_xfer_handle xfer, usbd_private_handle priv,
1337 usbd_status status)
1338 {
1339 struct uath_tx_data *data = priv;
1340 struct uath_softc *sc = data->sc;
1341 struct ieee80211com *ic = &sc->sc_ic;
1342 struct ifnet *ifp = &ic->ic_if;
1343 int s;
1344
1345 if (status != USBD_NORMAL_COMPLETION) {
1346 if (status == USBD_NOT_STARTED || status == USBD_CANCELLED)
1347 return;
1348
1349 printf("%s: could not transmit buffer: %s\n",
1350 sc->sc_dev.dv_xname, usbd_errstr(status));
1351
1352 if (status == USBD_STALLED)
1353 usbd_clear_endpoint_stall_async(sc->data_tx_pipe);
1354
1355 ifp->if_oerrors++;
1356 return;
1357 }
1358
1359 s = splnet();
1360
1361 ieee80211_release_node(ic, data->ni);
1362 data->ni = NULL;
1363
1364 sc->tx_queued--;
1365 ifp->if_opackets++;
1366
1367 sc->sc_tx_timer = 0;
1368 ifp->if_flags &= ~IFF_OACTIVE;
1369 uath_start(ifp);
1370
1371 splx(s);
1372 }
1373
1374 int
1375 uath_tx_data(struct uath_softc *sc, struct mbuf *m0, struct ieee80211_node *ni)
1376 {
1377 struct ieee80211com *ic = &sc->sc_ic;
1378 struct uath_tx_data *data;
1379 struct uath_tx_desc *desc;
1380 const struct ieee80211_frame *wh;
1381 int paylen, totlen, xferlen, error;
1382
1383 data = &sc->tx_data[sc->data_idx];
1384 desc = (struct uath_tx_desc *)(data->buf + sizeof (uint32_t));
1385
1386 data->ni = ni;
1387
1388 #if NBPFILTER > 0
1389 if (sc->sc_drvbpf != NULL) {
1390 struct mbuf mb;
1391 struct uath_tx_radiotap_header *tap = &sc->sc_txtap;
1392
1393 tap->wt_flags = 0;
1394 tap->wt_chan_freq = htole16(ic->ic_bss->ni_chan->ic_freq);
1395 tap->wt_chan_flags = htole16(ic->ic_bss->ni_chan->ic_flags);
1396
1397 mb.m_data = (caddr_t)tap;
1398 mb.m_len = sc->sc_txtap_len;
1399 mb.m_next = m0;
1400 mb.m_nextpkt = NULL;
1401 mb.m_type = 0;
1402 mb.m_flags = 0;
1403 bpf_mtap(sc->sc_drvbpf, &mb, BPF_DIRECTION_OUT);
1404 }
1405 #endif
1406
1407 paylen = m0->m_pkthdr.len;
1408 xferlen = sizeof (uint32_t) + sizeof (struct uath_tx_desc) + paylen;
1409
1410 wh = mtod(m0, struct ieee80211_frame *);
1411 if (wh->i_fc[1] & IEEE80211_FC1_WEP) {
1412 uint8_t *frm = (uint8_t *)(desc + 1);
1413 uint32_t iv;
1414
1415
1416 bcopy(wh, frm, sizeof (struct ieee80211_frame));
1417 frm += sizeof (struct ieee80211_frame);
1418
1419
1420 iv = (ic->ic_iv != 0) ? ic->ic_iv : arc4random();
1421 if (iv >= 0x03ff00 && (iv & 0xf8ff00) == 0x00ff00)
1422 iv += 0x000100;
1423 ic->ic_iv = iv + 1;
1424
1425 *frm++ = iv & 0xff;
1426 *frm++ = (iv >> 8) & 0xff;
1427 *frm++ = (iv >> 16) & 0xff;
1428 *frm++ = ic->ic_wep_txkey << 6;
1429
1430 m_copydata(m0, sizeof (struct ieee80211_frame),
1431 m0->m_pkthdr.len - sizeof (struct ieee80211_frame), frm);
1432
1433 paylen += IEEE80211_WEP_IVLEN + IEEE80211_WEP_KIDLEN;
1434 xferlen += IEEE80211_WEP_IVLEN + IEEE80211_WEP_KIDLEN;
1435 totlen = xferlen + IEEE80211_WEP_CRCLEN;
1436 } else {
1437 m_copydata(m0, 0, m0->m_pkthdr.len, (uint8_t *)(desc + 1));
1438 totlen = xferlen;
1439 }
1440
1441
1442 *(uint32_t *)data->buf = UATH_MAKECTL(1, xferlen - sizeof (uint32_t));
1443
1444 desc->len = htobe32(totlen);
1445 desc->priv = sc->data_idx;
1446 desc->paylen = htobe32(paylen);
1447 desc->type = htobe32(UATH_TX_DATA);
1448 desc->flags = htobe32(0);
1449 if (IEEE80211_IS_MULTICAST(wh->i_addr1)) {
1450 desc->dest = htobe32(UATH_ID_BROADCAST);
1451 desc->magic = htobe32(3);
1452 } else {
1453 desc->dest = htobe32(UATH_ID_BSS);
1454 desc->magic = htobe32(1);
1455 }
1456
1457 m_freem(m0);
1458
1459 #ifdef UATH_DEBUG
1460 if (uath_debug >= 6) {
1461 printf("sending frame index=%u len=%d xferlen=%d",
1462 sc->data_idx, paylen, xferlen);
1463 uath_dump_cmd(data->buf, xferlen, '+');
1464 }
1465 #endif
1466 usbd_setup_xfer(data->xfer, sc->data_tx_pipe, data, data->buf, xferlen,
1467 USBD_FORCE_SHORT_XFER | USBD_NO_COPY, UATH_DATA_TIMEOUT,
1468 uath_data_txeof);
1469 error = usbd_transfer(data->xfer);
1470 if (error != USBD_IN_PROGRESS && error != 0) {
1471 ic->ic_if.if_oerrors++;
1472 return error;
1473 }
1474 sc->data_idx = (sc->data_idx + 1) % UATH_TX_DATA_LIST_COUNT;
1475 sc->tx_queued++;
1476
1477 return 0;
1478 }
1479
1480 void
1481 uath_start(struct ifnet *ifp)
1482 {
1483 struct uath_softc *sc = ifp->if_softc;
1484 struct ieee80211com *ic = &sc->sc_ic;
1485 struct ieee80211_node *ni;
1486 struct mbuf *m0;
1487
1488
1489
1490
1491
1492 if ((ifp->if_flags & (IFF_RUNNING | IFF_OACTIVE)) != IFF_RUNNING)
1493 return;
1494
1495 for (;;) {
1496 IF_POLL(&ic->ic_mgtq, m0);
1497 if (m0 != NULL) {
1498 if (sc->tx_queued >= UATH_TX_DATA_LIST_COUNT) {
1499 ifp->if_flags |= IFF_OACTIVE;
1500 break;
1501 }
1502 IF_DEQUEUE(&ic->ic_mgtq, m0);
1503
1504 ni = (struct ieee80211_node *)m0->m_pkthdr.rcvif;
1505 m0->m_pkthdr.rcvif = NULL;
1506 #if NBPFILTER > 0
1507 if (ic->ic_rawbpf != NULL)
1508 bpf_mtap(ic->ic_rawbpf, m0, BPF_DIRECTION_OUT);
1509 #endif
1510 if (uath_tx_data(sc, m0, ni) != 0)
1511 break;
1512 } else {
1513 if (ic->ic_state != IEEE80211_S_RUN)
1514 break;
1515 IFQ_POLL(&ifp->if_snd, m0);
1516 if (m0 == NULL)
1517 break;
1518 if (sc->tx_queued >= UATH_TX_DATA_LIST_COUNT) {
1519 ifp->if_flags |= IFF_OACTIVE;
1520 break;
1521 }
1522 IFQ_DEQUEUE(&ifp->if_snd, m0);
1523 #if NBPFILTER > 0
1524 if (ifp->if_bpf != NULL)
1525 bpf_mtap(ifp->if_bpf, m0, BPF_DIRECTION_OUT);
1526 #endif
1527 m0 = ieee80211_encap(ifp, m0, &ni);
1528 if (m0 == NULL)
1529 continue;
1530 #if NBPFILTER > 0
1531 if (ic->ic_rawbpf != NULL)
1532 bpf_mtap(ic->ic_rawbpf, m0, BPF_DIRECTION_OUT);
1533 #endif
1534 if (uath_tx_data(sc, m0, ni) != 0) {
1535 if (ni != NULL)
1536 ieee80211_release_node(ic, ni);
1537 ifp->if_oerrors++;
1538 break;
1539 }
1540 }
1541
1542 sc->sc_tx_timer = 5;
1543 ifp->if_timer = 1;
1544 }
1545 }
1546
1547 void
1548 uath_watchdog(struct ifnet *ifp)
1549 {
1550 struct uath_softc *sc = ifp->if_softc;
1551
1552 ifp->if_timer = 0;
1553
1554 if (sc->sc_tx_timer > 0) {
1555 if (--sc->sc_tx_timer == 0) {
1556 printf("%s: device timeout\n", sc->sc_dev.dv_xname);
1557
1558 ifp->if_oerrors++;
1559 return;
1560 }
1561 ifp->if_timer = 1;
1562 }
1563
1564 ieee80211_watchdog(ifp);
1565 }
1566
1567 int
1568 uath_ioctl(struct ifnet *ifp, u_long cmd, caddr_t data)
1569 {
1570 struct uath_softc *sc = ifp->if_softc;
1571 struct ieee80211com *ic = &sc->sc_ic;
1572 struct ifaddr *ifa;
1573 struct ifreq *ifr;
1574 int s, error = 0;
1575
1576 s = splnet();
1577
1578 switch (cmd) {
1579 case SIOCSIFADDR:
1580 ifa = (struct ifaddr *)data;
1581 ifp->if_flags |= IFF_UP;
1582 #ifdef INET
1583 if (ifa->ifa_addr->sa_family == AF_INET)
1584 arp_ifinit(&ic->ic_ac, ifa);
1585 #endif
1586
1587 case SIOCSIFFLAGS:
1588 if (ifp->if_flags & IFF_UP) {
1589 if (!(ifp->if_flags & IFF_RUNNING))
1590 uath_init(ifp);
1591 } else {
1592 if (ifp->if_flags & IFF_RUNNING)
1593 uath_stop(ifp, 1);
1594 }
1595 break;
1596
1597 case SIOCADDMULTI:
1598 case SIOCDELMULTI:
1599 ifr = (struct ifreq *)data;
1600 error = (cmd == SIOCADDMULTI) ?
1601 ether_addmulti(ifr, &ic->ic_ac) :
1602 ether_delmulti(ifr, &ic->ic_ac);
1603 if (error == ENETRESET)
1604 error = 0;
1605 break;
1606
1607 default:
1608 error = ieee80211_ioctl(ifp, cmd, data);
1609 }
1610
1611 if (error == ENETRESET) {
1612 if ((ifp->if_flags & (IFF_UP | IFF_RUNNING)) ==
1613 (IFF_UP | IFF_RUNNING))
1614 uath_init(ifp);
1615 error = 0;
1616 }
1617
1618 splx(s);
1619
1620 return error;
1621 }
1622
1623 int
1624 uath_query_eeprom(struct uath_softc *sc)
1625 {
1626 uint32_t tmp;
1627 int error;
1628
1629
1630 error = uath_read_eeprom(sc, UATH_EEPROM_MACADDR, sc->sc_ic.ic_myaddr);
1631 if (error != 0) {
1632 printf("%s: could not read MAC address\n",
1633 sc->sc_dev.dv_xname);
1634 return error;
1635 }
1636
1637
1638 error = uath_read_eeprom(sc, UATH_EEPROM_RXBUFSZ, &tmp);
1639 if (error != 0) {
1640 printf("%s: could not read maximum Rx buffer size\n",
1641 sc->sc_dev.dv_xname);
1642 return error;
1643 }
1644 sc->rxbufsz = betoh32(tmp) & 0xfff;
1645 DPRINTF(("maximum Rx buffer size %d\n", sc->rxbufsz));
1646 return 0;
1647 }
1648
1649 int
1650 uath_reset(struct uath_softc *sc)
1651 {
1652 struct uath_cmd_setup setup;
1653 uint32_t reg, val;
1654 int s, error;
1655
1656
1657 setup.magic1 = htobe32(1);
1658 setup.magic2 = htobe32(5);
1659 setup.magic3 = htobe32(200);
1660 setup.magic4 = htobe32(27);
1661 s = splusb();
1662 error = uath_cmd_write(sc, UATH_CMD_SETUP, &setup, sizeof setup,
1663 UATH_CMD_FLAG_ASYNC);
1664
1665 if (error == 0)
1666 error = tsleep(UATH_COND_INIT(sc), PCATCH, "uathinit", 5 * hz);
1667 splx(s);
1668 if (error != 0)
1669 return error;
1670
1671
1672 for (reg = 0x09; reg <= 0x24; reg++) {
1673 if (reg == 0x0b || reg == 0x0c)
1674 continue;
1675 DELAY(100);
1676 if ((error = uath_read_reg(sc, reg, &val)) != 0)
1677 return error;
1678 DPRINTFN(2, ("reg 0x%02x=0x%08x\n", reg, val));
1679 }
1680 return error;
1681 }
1682
1683 int
1684 uath_reset_tx_queues(struct uath_softc *sc)
1685 {
1686 int ac, error;
1687
1688 for (ac = 0; ac < 4; ac++) {
1689 const uint32_t qid = htobe32(UATH_AC_TO_QID(ac));
1690
1691 DPRINTF(("resetting Tx queue %d\n", UATH_AC_TO_QID(ac)));
1692 error = uath_cmd_write(sc, UATH_CMD_RESET_QUEUE, &qid,
1693 sizeof qid, 0);
1694 if (error != 0)
1695 break;
1696 }
1697 return error;
1698 }
1699
1700 int
1701 uath_wme_init(struct uath_softc *sc)
1702 {
1703 struct uath_qinfo qinfo;
1704 int ac, error;
1705 static const struct uath_wme_settings uath_wme_11g[4] = {
1706 { 7, 4, 10, 0, 0 },
1707 { 3, 4, 10, 0, 0 },
1708 { 3, 3, 4, 26, 0 },
1709 { 2, 2, 3, 47, 0 }
1710 };
1711
1712 bzero(&qinfo, sizeof qinfo);
1713 qinfo.size = htobe32(32);
1714 qinfo.magic1 = htobe32(1);
1715 qinfo.magic2 = htobe32(1);
1716 for (ac = 0; ac < 4; ac++) {
1717 qinfo.qid = htobe32(UATH_AC_TO_QID(ac));
1718 qinfo.ac = htobe32(ac);
1719 qinfo.aifsn = htobe32(uath_wme_11g[ac].aifsn);
1720 qinfo.logcwmin = htobe32(uath_wme_11g[ac].logcwmin);
1721 qinfo.logcwmax = htobe32(uath_wme_11g[ac].logcwmax);
1722 qinfo.txop = htobe32(UATH_TXOP_TO_US(
1723 uath_wme_11g[ac].txop));
1724 qinfo.acm = htobe32(uath_wme_11g[ac].acm);
1725
1726 DPRINTF(("setting up Tx queue %d\n", UATH_AC_TO_QID(ac)));
1727 error = uath_cmd_write(sc, UATH_CMD_SET_QUEUE, &qinfo,
1728 sizeof qinfo, 0);
1729 if (error != 0)
1730 break;
1731 }
1732 return error;
1733 }
1734
1735 int
1736 uath_set_chan(struct uath_softc *sc, struct ieee80211_channel *c)
1737 {
1738 struct uath_set_chan chan;
1739
1740 bzero(&chan, sizeof chan);
1741 chan.flags = htobe32(0x1400);
1742 chan.freq = htobe32(c->ic_freq);
1743 chan.magic1 = htobe32(20);
1744 chan.magic2 = htobe32(50);
1745 chan.magic3 = htobe32(1);
1746
1747 DPRINTF(("switching to channel %d\n",
1748 ieee80211_chan2ieee(&sc->sc_ic, c)));
1749 return uath_cmd_write(sc, UATH_CMD_SET_CHAN, &chan, sizeof chan, 0);
1750 }
1751
1752 int
1753 uath_set_key(struct uath_softc *sc, const struct ieee80211_key *k, int index)
1754 {
1755 struct uath_cmd_crypto crypto;
1756 int i;
1757
1758 bzero(&crypto, sizeof crypto);
1759 crypto.keyidx = htobe32(index);
1760 crypto.magic1 = htobe32(1);
1761 crypto.size = htobe32(368);
1762 crypto.mask = htobe32(0xffff);
1763 crypto.flags = htobe32(0x80000068);
1764 if (index != UATH_DEFAULT_KEY)
1765 crypto.flags |= htobe32(index << 16);
1766 memset(crypto.magic2, 0xff, sizeof crypto.magic2);
1767
1768
1769
1770
1771
1772 for (i = 0; i < k->k_len; i++)
1773 crypto.key[i] = k->k_key[i] ^ 0xaa;
1774
1775 DPRINTF(("setting crypto key index=%d len=%d\n", index, k->k_len));
1776 return uath_cmd_write(sc, UATH_CMD_CRYPTO, &crypto, sizeof crypto, 0);
1777 }
1778
1779 int
1780 uath_set_keys(struct uath_softc *sc)
1781 {
1782 const struct ieee80211com *ic = &sc->sc_ic;
1783 int i, error;
1784
1785 for (i = 0; i < IEEE80211_WEP_NKID; i++) {
1786 const struct ieee80211_key *k = &ic->ic_nw_keys[i];
1787
1788 if (k->k_len > 0 && (error = uath_set_key(sc, k, i)) != 0)
1789 return error;
1790 }
1791 return uath_set_key(sc, &ic->ic_nw_keys[ic->ic_wep_txkey],
1792 UATH_DEFAULT_KEY);
1793 }
1794
1795 int
1796 uath_set_rates(struct uath_softc *sc, const struct ieee80211_rateset *rs)
1797 {
1798 struct uath_cmd_rates rates;
1799
1800 bzero(&rates, sizeof rates);
1801 rates.magic1 = htobe32(0x02);
1802 rates.size = htobe32(1 + sizeof rates.rates);
1803 rates.nrates = rs->rs_nrates;
1804 bcopy(rs->rs_rates, rates.rates, rs->rs_nrates);
1805
1806 DPRINTF(("setting supported rates nrates=%d\n", rs->rs_nrates));
1807 return uath_cmd_write(sc, UATH_CMD_SET_RATES, &rates, sizeof rates, 0);
1808 }
1809
1810 int
1811 uath_set_rxfilter(struct uath_softc *sc, uint32_t filter, uint32_t flags)
1812 {
1813 struct uath_cmd_filter rxfilter;
1814
1815 rxfilter.filter = htobe32(filter);
1816 rxfilter.flags = htobe32(flags);
1817
1818 DPRINTF(("setting Rx filter=0x%x flags=0x%x\n", filter, flags));
1819 return uath_cmd_write(sc, UATH_CMD_SET_FILTER, &rxfilter,
1820 sizeof rxfilter, 0);
1821 }
1822
1823 int
1824 uath_set_led(struct uath_softc *sc, int which, int on)
1825 {
1826 struct uath_cmd_led led;
1827
1828 led.which = htobe32(which);
1829 led.state = htobe32(on ? UATH_LED_ON : UATH_LED_OFF);
1830
1831 DPRINTFN(2, ("switching %s led %s\n",
1832 (which == UATH_LED_LINK) ? "link" : "activity",
1833 on ? "on" : "off"));
1834 return uath_cmd_write(sc, UATH_CMD_SET_LED, &led, sizeof led, 0);
1835 }
1836
1837 int
1838 uath_switch_channel(struct uath_softc *sc, struct ieee80211_channel *c)
1839 {
1840 uint32_t val;
1841 int error;
1842
1843
1844 if ((error = uath_set_chan(sc, c)) != 0) {
1845 printf("%s: could not set channel\n", sc->sc_dev.dv_xname);
1846 return error;
1847 }
1848
1849
1850 if ((error = uath_reset_tx_queues(sc)) != 0) {
1851 printf("%s: could not reset Tx queues\n",
1852 sc->sc_dev.dv_xname);
1853 return error;
1854 }
1855
1856
1857 if ((error = uath_wme_init(sc)) != 0) {
1858 printf("%s: could not init Tx queues\n",
1859 sc->sc_dev.dv_xname);
1860 return error;
1861 }
1862
1863 val = htobe32(0);
1864 error = uath_cmd_write(sc, UATH_CMD_SET_STATE, &val, sizeof val, 0);
1865 if (error != 0) {
1866 printf("%s: could not set state\n", sc->sc_dev.dv_xname);
1867 return error;
1868 }
1869
1870 return uath_tx_null(sc);
1871 }
1872
1873 int
1874 uath_init(struct ifnet *ifp)
1875 {
1876 struct uath_softc *sc = ifp->if_softc;
1877 struct ieee80211com *ic = &sc->sc_ic;
1878 struct uath_cmd_31 cmd31;
1879 uint32_t val;
1880 int i, error;
1881
1882
1883 sc->tx_queued = sc->data_idx = sc->cmd_idx = 0;
1884
1885 val = htobe32(0);
1886 (void)uath_cmd_write(sc, UATH_CMD_02, &val, sizeof val, 0);
1887
1888
1889 IEEE80211_ADDR_COPY(ic->ic_myaddr, LLADDR(ifp->if_sadl));
1890 (void)uath_write_multi(sc, 0x13, ic->ic_myaddr, IEEE80211_ADDR_LEN);
1891
1892 (void)uath_write_reg(sc, 0x02, 0x00000001);
1893 (void)uath_write_reg(sc, 0x0e, 0x0000003f);
1894 (void)uath_write_reg(sc, 0x10, 0x00000001);
1895 (void)uath_write_reg(sc, 0x06, 0x0000001e);
1896
1897
1898
1899
1900 for (i = 0; i < UATH_RX_DATA_LIST_COUNT; i++) {
1901 struct uath_rx_data *data = SLIST_FIRST(&sc->rx_freelist);
1902
1903 usbd_setup_xfer(data->xfer, sc->data_rx_pipe, data, data->buf,
1904 sc->rxbufsz, USBD_SHORT_XFER_OK | USBD_NO_COPY,
1905 USBD_NO_TIMEOUT, uath_data_rxeof);
1906 error = usbd_transfer(data->xfer);
1907 if (error != USBD_IN_PROGRESS && error != 0) {
1908 printf("%s: could not queue Rx transfer\n",
1909 sc->sc_dev.dv_xname);
1910 goto fail;
1911 }
1912 SLIST_REMOVE_HEAD(&sc->rx_freelist, next);
1913 }
1914
1915 error = uath_cmd_read(sc, UATH_CMD_07, 0, NULL, &val,
1916 UATH_CMD_FLAG_MAGIC);
1917 if (error != 0) {
1918 printf("%s: could not send read command 07h\n",
1919 sc->sc_dev.dv_xname);
1920 goto fail;
1921 }
1922 DPRINTF(("command 07h return code: %x\n", betoh32(val)));
1923
1924
1925 ic->ic_bss->ni_chan = ic->ic_ibss_chan;
1926 if ((error = uath_set_chan(sc, ic->ic_bss->ni_chan)) != 0) {
1927 printf("%s: could not set channel\n", sc->sc_dev.dv_xname);
1928 goto fail;
1929 }
1930
1931 if ((error = uath_wme_init(sc)) != 0) {
1932 printf("%s: could not setup WME parameters\n",
1933 sc->sc_dev.dv_xname);
1934 goto fail;
1935 }
1936
1937
1938 (void)uath_write_reg(sc, 0x19, 0x00000000);
1939 (void)uath_write_reg(sc, 0x1a, 0x0000003c);
1940 (void)uath_write_reg(sc, 0x1b, 0x0000003c);
1941 (void)uath_write_reg(sc, 0x1c, 0x00000000);
1942 (void)uath_write_reg(sc, 0x1e, 0x00000000);
1943 (void)uath_write_reg(sc, 0x1f, 0x00000003);
1944 (void)uath_write_reg(sc, 0x0c, 0x00000000);
1945 (void)uath_write_reg(sc, 0x0f, 0x00000002);
1946 (void)uath_write_reg(sc, 0x0a, 0x00000007);
1947 (void)uath_write_reg(sc, 0x09, ic->ic_rtsthreshold);
1948
1949 val = htobe32(4);
1950 (void)uath_cmd_write(sc, UATH_CMD_27, &val, sizeof val, 0);
1951 (void)uath_cmd_write(sc, UATH_CMD_27, &val, sizeof val, 0);
1952 (void)uath_cmd_write(sc, UATH_CMD_1B, NULL, 0, 0);
1953
1954 if ((error = uath_set_keys(sc)) != 0) {
1955 printf("%s: could not set crypto keys\n",
1956 sc->sc_dev.dv_xname);
1957 goto fail;
1958 }
1959
1960
1961 (void)uath_set_rxfilter(sc, 0x0000, 4);
1962 (void)uath_set_rxfilter(sc, 0x0817, 1);
1963
1964 cmd31.magic1 = htobe32(0xffffffff);
1965 cmd31.magic2 = htobe32(0xffffffff);
1966 (void)uath_cmd_write(sc, UATH_CMD_31, &cmd31, sizeof cmd31, 0);
1967
1968 ifp->if_flags &= ~IFF_OACTIVE;
1969 ifp->if_flags |= IFF_RUNNING;
1970
1971 if (ic->ic_opmode == IEEE80211_M_MONITOR)
1972 ieee80211_new_state(ic, IEEE80211_S_RUN, -1);
1973 else
1974 ieee80211_new_state(ic, IEEE80211_S_SCAN, -1);
1975
1976 return 0;
1977
1978 fail: uath_stop(ifp, 1);
1979 return error;
1980 }
1981
1982 void
1983 uath_stop(struct ifnet *ifp, int disable)
1984 {
1985 struct uath_softc *sc = ifp->if_softc;
1986 struct ieee80211com *ic = &sc->sc_ic;
1987 uint32_t val;
1988 int s;
1989
1990 s = splusb();
1991
1992 sc->sc_tx_timer = 0;
1993 ifp->if_timer = 0;
1994 ifp->if_flags &= ~(IFF_RUNNING | IFF_OACTIVE);
1995
1996 ieee80211_new_state(ic, IEEE80211_S_INIT, -1);
1997
1998 val = htobe32(0);
1999 (void)uath_cmd_write(sc, UATH_CMD_SET_STATE, &val, sizeof val, 0);
2000 (void)uath_cmd_write(sc, UATH_CMD_RESET, NULL, 0, 0);
2001
2002 val = htobe32(0);
2003 (void)uath_cmd_write(sc, UATH_CMD_15, &val, sizeof val, 0);
2004
2005 #if 0
2006 (void)uath_cmd_read(sc, UATH_CMD_SHUTDOWN, NULL, 0, NULL,
2007 UATH_CMD_FLAG_MAGIC);
2008 #endif
2009
2010
2011 usbd_abort_pipe(sc->data_tx_pipe);
2012 usbd_abort_pipe(sc->data_rx_pipe);
2013 usbd_abort_pipe(sc->cmd_tx_pipe);
2014
2015 splx(s);
2016 }
2017
2018
2019
2020
2021
2022
2023
2024 int
2025 uath_loadfirmware(struct uath_softc *sc, const u_char *fw, int len)
2026 {
2027 usbd_xfer_handle ctlxfer, txxfer, rxxfer;
2028 struct uath_fwblock *txblock, *rxblock;
2029 uint8_t *txdata;
2030 int error = 0;
2031
2032 if ((ctlxfer = usbd_alloc_xfer(sc->sc_udev)) == NULL) {
2033 printf("%s: could not allocate Tx control xfer\n",
2034 sc->sc_dev.dv_xname);
2035 error = USBD_NOMEM;
2036 goto fail1;
2037 }
2038 txblock = usbd_alloc_buffer(ctlxfer, sizeof (struct uath_fwblock));
2039 if (txblock == NULL) {
2040 printf("%s: could not allocate Tx control block\n",
2041 sc->sc_dev.dv_xname);
2042 error = USBD_NOMEM;
2043 goto fail2;
2044 }
2045
2046 if ((txxfer = usbd_alloc_xfer(sc->sc_udev)) == NULL) {
2047 printf("%s: could not allocate Tx xfer\n",
2048 sc->sc_dev.dv_xname);
2049 error = USBD_NOMEM;
2050 goto fail2;
2051 }
2052 txdata = usbd_alloc_buffer(txxfer, UATH_MAX_FWBLOCK_SIZE);
2053 if (txdata == NULL) {
2054 printf("%s: could not allocate Tx buffer\n",
2055 sc->sc_dev.dv_xname);
2056 error = USBD_NOMEM;
2057 goto fail3;
2058 }
2059
2060 if ((rxxfer = usbd_alloc_xfer(sc->sc_udev)) == NULL) {
2061 printf("%s: could not allocate Rx control xfer\n",
2062 sc->sc_dev.dv_xname);
2063 error = USBD_NOMEM;
2064 goto fail3;
2065 }
2066 rxblock = usbd_alloc_buffer(rxxfer, sizeof (struct uath_fwblock));
2067 if (rxblock == NULL) {
2068 printf("%s: could not allocate Rx control block\n",
2069 sc->sc_dev.dv_xname);
2070 error = USBD_NOMEM;
2071 goto fail4;
2072 }
2073
2074 bzero(txblock, sizeof (struct uath_fwblock));
2075 txblock->flags = htobe32(UATH_WRITE_BLOCK);
2076 txblock->total = htobe32(len);
2077
2078 while (len > 0) {
2079 int mlen = min(len, UATH_MAX_FWBLOCK_SIZE);
2080
2081 txblock->remain = htobe32(len - mlen);
2082 txblock->len = htobe32(mlen);
2083
2084 DPRINTF(("sending firmware block: %d bytes remaining\n",
2085 len - mlen));
2086
2087
2088 usbd_setup_xfer(ctlxfer, sc->cmd_tx_pipe, sc, txblock,
2089 sizeof (struct uath_fwblock), USBD_NO_COPY,
2090 UATH_CMD_TIMEOUT, NULL);
2091 if ((error = usbd_sync_transfer(ctlxfer)) != 0) {
2092 printf("%s: could not send firmware block info\n",
2093 sc->sc_dev.dv_xname);
2094 break;
2095 }
2096
2097
2098 bcopy(fw, txdata, mlen);
2099 usbd_setup_xfer(txxfer, sc->data_tx_pipe, sc, txdata, mlen,
2100 USBD_NO_COPY, UATH_DATA_TIMEOUT, NULL);
2101 if ((error = usbd_sync_transfer(txxfer)) != 0) {
2102 printf("%s: could not send firmware block data\n",
2103 sc->sc_dev.dv_xname);
2104 break;
2105 }
2106
2107
2108 usbd_setup_xfer(rxxfer, sc->cmd_rx_pipe, sc, rxblock,
2109 sizeof (struct uath_fwblock), USBD_SHORT_XFER_OK |
2110 USBD_NO_COPY, UATH_CMD_TIMEOUT, NULL);
2111 if ((error = usbd_sync_transfer(rxxfer)) != 0) {
2112 printf("%s: could not read firmware answer\n",
2113 sc->sc_dev.dv_xname);
2114 break;
2115 }
2116
2117 DPRINTFN(2, ("rxblock flags=0x%x total=%d\n",
2118 betoh32(rxblock->flags), betoh32(rxblock->rxtotal)));
2119 fw += mlen;
2120 len -= mlen;
2121 }
2122
2123 fail4: usbd_free_xfer(rxxfer);
2124 fail3: usbd_free_xfer(txxfer);
2125 fail2: usbd_free_xfer(ctlxfer);
2126 fail1: return error;
2127 }
2128
2129 int
2130 uath_activate(struct device *self, enum devact act)
2131 {
2132 switch (act) {
2133 case DVACT_ACTIVATE:
2134 break;
2135
2136 case DVACT_DEACTIVATE:
2137 break;
2138 }
2139 return 0;
2140 }