if_rsu.c (286950) | if_rsu.c (287197) |
---|---|
1/* $OpenBSD: if_rsu.c,v 1.17 2013/04/15 09:23:01 mglocker Exp $ */ 2 3/*- 4 * Copyright (c) 2010 Damien Bergamini <damien.bergamini@free.fr> 5 * 6 * Permission to use, copy, modify, and distribute this software for any 7 * purpose with or without fee is hereby granted, provided that the above 8 * copyright notice and this permission notice appear in all copies. 9 * 10 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 11 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 12 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 13 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 14 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 15 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 16 * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 17 */ 18#include <sys/cdefs.h> | 1/* $OpenBSD: if_rsu.c,v 1.17 2013/04/15 09:23:01 mglocker Exp $ */ 2 3/*- 4 * Copyright (c) 2010 Damien Bergamini <damien.bergamini@free.fr> 5 * 6 * Permission to use, copy, modify, and distribute this software for any 7 * purpose with or without fee is hereby granted, provided that the above 8 * copyright notice and this permission notice appear in all copies. 9 * 10 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 11 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 12 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 13 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 14 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 15 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 16 * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 17 */ 18#include <sys/cdefs.h> |
19__FBSDID("$FreeBSD: head/sys/dev/usb/wlan/if_rsu.c 286950 2015-08-20 05:13:54Z adrian $"); | 19__FBSDID("$FreeBSD: head/sys/dev/usb/wlan/if_rsu.c 287197 2015-08-27 08:56:39Z glebius $"); |
20 21/* 22 * Driver for Realtek RTL8188SU/RTL8191SU/RTL8192SU. 23 * 24 * TODO: 25 * o 11n support 26 * o h/w crypto 27 * o hostap / ibss / mesh --- 154 unchanged lines hidden (view full) --- 182 rsu_rx_frame(struct rsu_softc *, uint8_t *, int, int *); 183static struct mbuf * 184 rsu_rx_multi_frame(struct rsu_softc *, uint8_t *, int, int *); 185static struct mbuf * 186 rsu_rxeof(struct usb_xfer *, struct rsu_data *, int *); 187static void rsu_txeof(struct usb_xfer *, struct rsu_data *); 188static int rsu_raw_xmit(struct ieee80211_node *, struct mbuf *, 189 const struct ieee80211_bpf_params *); | 20 21/* 22 * Driver for Realtek RTL8188SU/RTL8191SU/RTL8192SU. 23 * 24 * TODO: 25 * o 11n support 26 * o h/w crypto 27 * o hostap / ibss / mesh --- 154 unchanged lines hidden (view full) --- 182 rsu_rx_frame(struct rsu_softc *, uint8_t *, int, int *); 183static struct mbuf * 184 rsu_rx_multi_frame(struct rsu_softc *, uint8_t *, int, int *); 185static struct mbuf * 186 rsu_rxeof(struct usb_xfer *, struct rsu_data *, int *); 187static void rsu_txeof(struct usb_xfer *, struct rsu_data *); 188static int rsu_raw_xmit(struct ieee80211_node *, struct mbuf *, 189 const struct ieee80211_bpf_params *); |
190static void rsu_init(void *); 191static void rsu_init_locked(struct rsu_softc *); | 190static void rsu_init(struct rsu_softc *); |
192static int rsu_tx_start(struct rsu_softc *, struct ieee80211_node *, 193 struct mbuf *, struct rsu_data *); | 191static int rsu_tx_start(struct rsu_softc *, struct ieee80211_node *, 192 struct mbuf *, struct rsu_data *); |
194static void rsu_start(struct ifnet *); 195static void rsu_start_locked(struct ifnet *); 196static int rsu_ioctl(struct ifnet *, u_long, caddr_t); 197static void rsu_stop(struct ifnet *, int); 198static void rsu_stop_locked(struct ifnet *, int); | 193static int rsu_transmit(struct ieee80211com *, struct mbuf *); 194static void rsu_start(struct rsu_softc *); 195static void rsu_parent(struct ieee80211com *); 196static void rsu_stop(struct rsu_softc *); |
199static void rsu_ms_delay(struct rsu_softc *); 200 201static device_method_t rsu_methods[] = { 202 DEVMETHOD(device_probe, rsu_match), 203 DEVMETHOD(device_attach, rsu_attach), 204 DEVMETHOD(device_detach, rsu_detach), 205 206 DEVMETHOD_END --- 73 unchanged lines hidden (view full) --- 280 return (usbd_lookup_id_by_uaa(rsu_devs, sizeof(rsu_devs), uaa)); 281} 282 283static int 284rsu_attach(device_t self) 285{ 286 struct usb_attach_arg *uaa = device_get_ivars(self); 287 struct rsu_softc *sc = device_get_softc(self); | 197static void rsu_ms_delay(struct rsu_softc *); 198 199static device_method_t rsu_methods[] = { 200 DEVMETHOD(device_probe, rsu_match), 201 DEVMETHOD(device_attach, rsu_attach), 202 DEVMETHOD(device_detach, rsu_detach), 203 204 DEVMETHOD_END --- 73 unchanged lines hidden (view full) --- 278 return (usbd_lookup_id_by_uaa(rsu_devs, sizeof(rsu_devs), uaa)); 279} 280 281static int 282rsu_attach(device_t self) 283{ 284 struct usb_attach_arg *uaa = device_get_ivars(self); 285 struct rsu_softc *sc = device_get_softc(self); |
288 struct ifnet *ifp; 289 struct ieee80211com *ic; | 286 struct ieee80211com *ic = &sc->sc_ic; |
290 int error; 291 uint8_t iface_index, bands; 292 293 device_set_usb_desc(self); 294 sc->sc_udev = uaa->device; 295 sc->sc_dev = self; 296 297 mtx_init(&sc->sc_mtx, device_get_nameunit(self), MTX_NETWORK_LOCK, 298 MTX_DEF); 299 TIMEOUT_TASK_INIT(taskqueue_thread, &sc->calib_task, 0, 300 rsu_calib_task, sc); | 287 int error; 288 uint8_t iface_index, bands; 289 290 device_set_usb_desc(self); 291 sc->sc_udev = uaa->device; 292 sc->sc_dev = self; 293 294 mtx_init(&sc->sc_mtx, device_get_nameunit(self), MTX_NETWORK_LOCK, 295 MTX_DEF); 296 TIMEOUT_TASK_INIT(taskqueue_thread, &sc->calib_task, 0, 297 rsu_calib_task, sc); |
298 mbufq_init(&sc->sc_snd, ifqmaxlen); |
|
301 302 /* Allocate Tx/Rx buffers. */ 303 error = rsu_alloc_rx_list(sc); 304 if (error != 0) { 305 device_printf(sc->sc_dev, "could not allocate Rx buffers\n"); 306 goto fail_usb; 307 } 308 --- 19 unchanged lines hidden (view full) --- 328 if (sc->cut != 3) 329 sc->cut = (sc->cut >> 1) + 1; 330 error = rsu_read_rom(sc); 331 RSU_UNLOCK(sc); 332 if (error != 0) { 333 device_printf(self, "could not read ROM\n"); 334 goto fail_rom; 335 } | 299 300 /* Allocate Tx/Rx buffers. */ 301 error = rsu_alloc_rx_list(sc); 302 if (error != 0) { 303 device_printf(sc->sc_dev, "could not allocate Rx buffers\n"); 304 goto fail_usb; 305 } 306 --- 19 unchanged lines hidden (view full) --- 326 if (sc->cut != 3) 327 sc->cut = (sc->cut >> 1) + 1; 328 error = rsu_read_rom(sc); 329 RSU_UNLOCK(sc); 330 if (error != 0) { 331 device_printf(self, "could not read ROM\n"); 332 goto fail_rom; 333 } |
336 IEEE80211_ADDR_COPY(sc->sc_bssid, &sc->rom[0x12]); | 334 IEEE80211_ADDR_COPY(ic->ic_macaddr, &sc->rom[0x12]); |
337 device_printf(self, "MAC/BB RTL8712 cut %d\n", sc->cut); | 335 device_printf(self, "MAC/BB RTL8712 cut %d\n", sc->cut); |
338 ifp = sc->sc_ifp = if_alloc(IFT_IEEE80211); 339 if (ifp == NULL) { 340 device_printf(self, "cannot allocate interface\n"); 341 goto fail_ifalloc; 342 } 343 ic = ifp->if_l2com; 344 ifp->if_softc = sc; 345 if_initname(ifp, "rsu", device_get_unit(self)); 346 ifp->if_flags = IFF_BROADCAST | IFF_SIMPLEX | IFF_MULTICAST; 347 ifp->if_init = rsu_init; 348 ifp->if_ioctl = rsu_ioctl; 349 ifp->if_start = rsu_start; 350 IFQ_SET_MAXLEN(&ifp->if_snd, ifqmaxlen); 351 ifp->if_snd.ifq_drv_maxlen = ifqmaxlen; 352 IFQ_SET_READY(&ifp->if_snd); 353 ifp->if_capabilities |= IFCAP_RXCSUM; 354 ifp->if_capenable |= IFCAP_RXCSUM; 355 ifp->if_hwassist = CSUM_TCP; | |
356 | 336 |
357 ic->ic_ifp = ifp; | |
358 ic->ic_softc = sc; 359 ic->ic_name = device_get_nameunit(self); 360 ic->ic_phytype = IEEE80211_T_OFDM; /* Not only, but not used. */ 361 ic->ic_opmode = IEEE80211_M_STA; /* Default to BSS mode. */ 362 363 /* Set device capabilities. */ 364 ic->ic_caps = 365 IEEE80211_C_STA | /* station mode */ --- 16 unchanged lines hidden (view full) --- 382#endif 383 384 /* Set supported .11b and .11g rates. */ 385 bands = 0; 386 setbit(&bands, IEEE80211_MODE_11B); 387 setbit(&bands, IEEE80211_MODE_11G); 388 ieee80211_init_channels(ic, NULL, &bands); 389 | 337 ic->ic_softc = sc; 338 ic->ic_name = device_get_nameunit(self); 339 ic->ic_phytype = IEEE80211_T_OFDM; /* Not only, but not used. */ 340 ic->ic_opmode = IEEE80211_M_STA; /* Default to BSS mode. */ 341 342 /* Set device capabilities. */ 343 ic->ic_caps = 344 IEEE80211_C_STA | /* station mode */ --- 16 unchanged lines hidden (view full) --- 361#endif 362 363 /* Set supported .11b and .11g rates. */ 364 bands = 0; 365 setbit(&bands, IEEE80211_MODE_11B); 366 setbit(&bands, IEEE80211_MODE_11G); 367 ieee80211_init_channels(ic, NULL, &bands); 368 |
390 ieee80211_ifattach(ic, sc->sc_bssid); | 369 ieee80211_ifattach(ic); |
391 ic->ic_raw_xmit = rsu_raw_xmit; 392 ic->ic_scan_start = rsu_scan_start; 393 ic->ic_scan_end = rsu_scan_end; 394 ic->ic_set_channel = rsu_set_channel; 395 ic->ic_vap_create = rsu_vap_create; 396 ic->ic_vap_delete = rsu_vap_delete; 397 ic->ic_update_mcast = rsu_update_mcast; | 370 ic->ic_raw_xmit = rsu_raw_xmit; 371 ic->ic_scan_start = rsu_scan_start; 372 ic->ic_scan_end = rsu_scan_end; 373 ic->ic_set_channel = rsu_set_channel; 374 ic->ic_vap_create = rsu_vap_create; 375 ic->ic_vap_delete = rsu_vap_delete; 376 ic->ic_update_mcast = rsu_update_mcast; |
377 ic->ic_parent = rsu_parent; 378 ic->ic_transmit = rsu_transmit; |
|
398 399 ieee80211_radiotap_attach(ic, &sc->sc_txtap.wt_ihdr, 400 sizeof(sc->sc_txtap), RSU_TX_RADIOTAP_PRESENT, 401 &sc->sc_rxtap.wr_ihdr, sizeof(sc->sc_rxtap), 402 RSU_RX_RADIOTAP_PRESENT); 403 404 if (bootverbose) 405 ieee80211_announce(ic); 406 407 return (0); 408 | 379 380 ieee80211_radiotap_attach(ic, &sc->sc_txtap.wt_ihdr, 381 sizeof(sc->sc_txtap), RSU_TX_RADIOTAP_PRESENT, 382 &sc->sc_rxtap.wr_ihdr, sizeof(sc->sc_rxtap), 383 RSU_RX_RADIOTAP_PRESENT); 384 385 if (bootverbose) 386 ieee80211_announce(ic); 387 388 return (0); 389 |
409fail_ifalloc: | |
410fail_rom: 411 usbd_transfer_unsetup(sc->sc_xfer, RSU_N_TRANSFER); 412fail_usb: 413 mtx_destroy(&sc->sc_mtx); 414 return (ENXIO); 415} 416 417static int 418rsu_detach(device_t self) 419{ 420 struct rsu_softc *sc = device_get_softc(self); | 390fail_rom: 391 usbd_transfer_unsetup(sc->sc_xfer, RSU_N_TRANSFER); 392fail_usb: 393 mtx_destroy(&sc->sc_mtx); 394 return (ENXIO); 395} 396 397static int 398rsu_detach(device_t self) 399{ 400 struct rsu_softc *sc = device_get_softc(self); |
421 struct ifnet *ifp = sc->sc_ifp; 422 struct ieee80211com *ic = ifp->if_l2com; | 401 struct ieee80211com *ic = &sc->sc_ic; |
423 | 402 |
424 rsu_stop(ifp, 1); | 403 RSU_LOCK(sc); 404 rsu_stop(sc); 405 RSU_UNLOCK(sc); |
425 usbd_transfer_unsetup(sc->sc_xfer, RSU_N_TRANSFER); 426 ieee80211_ifdetach(ic); 427 428 taskqueue_drain_timeout(taskqueue_thread, &sc->calib_task); 429 430 /* Free Tx/Rx buffers. */ 431 rsu_free_tx_list(sc); 432 rsu_free_rx_list(sc); 433 | 406 usbd_transfer_unsetup(sc->sc_xfer, RSU_N_TRANSFER); 407 ieee80211_ifdetach(ic); 408 409 taskqueue_drain_timeout(taskqueue_thread, &sc->calib_task); 410 411 /* Free Tx/Rx buffers. */ 412 rsu_free_tx_list(sc); 413 rsu_free_rx_list(sc); 414 |
434 if_free(ifp); | 415 mbufq_drain(&sc->sc_snd); |
435 mtx_destroy(&sc->sc_mtx); 436 437 return (0); 438} 439 440static usb_error_t 441rsu_do_request(struct rsu_softc *sc, struct usb_device_request *req, 442 void *data) --- 23 unchanged lines hidden (view full) --- 466 const uint8_t mac[IEEE80211_ADDR_LEN]) 467{ 468 struct rsu_vap *uvp; 469 struct ieee80211vap *vap; 470 471 if (!TAILQ_EMPTY(&ic->ic_vaps)) /* only one at a time */ 472 return (NULL); 473 | 416 mtx_destroy(&sc->sc_mtx); 417 418 return (0); 419} 420 421static usb_error_t 422rsu_do_request(struct rsu_softc *sc, struct usb_device_request *req, 423 void *data) --- 23 unchanged lines hidden (view full) --- 447 const uint8_t mac[IEEE80211_ADDR_LEN]) 448{ 449 struct rsu_vap *uvp; 450 struct ieee80211vap *vap; 451 452 if (!TAILQ_EMPTY(&ic->ic_vaps)) /* only one at a time */ 453 return (NULL); 454 |
474 uvp = (struct rsu_vap *) malloc(sizeof(struct rsu_vap), 475 M_80211_VAP, M_NOWAIT | M_ZERO); 476 if (uvp == NULL) 477 return (NULL); | 455 uvp = malloc(sizeof(struct rsu_vap), M_80211_VAP, M_WAITOK | M_ZERO); |
478 vap = &uvp->vap; 479 480 if (ieee80211_vap_setup(ic, vap, name, unit, opmode, | 456 vap = &uvp->vap; 457 458 if (ieee80211_vap_setup(ic, vap, name, unit, opmode, |
481 flags, bssid, mac) != 0) { | 459 flags, bssid) != 0) { |
482 /* out of memory */ 483 free(uvp, M_80211_VAP); 484 return (NULL); 485 } 486 487 /* override state transition machine */ 488 uvp->newstate = vap->iv_newstate; 489 vap->iv_newstate = rsu_newstate; 490 491 /* complete setup */ 492 ieee80211_vap_attach(vap, ieee80211_media_change, | 460 /* out of memory */ 461 free(uvp, M_80211_VAP); 462 return (NULL); 463 } 464 465 /* override state transition machine */ 466 uvp->newstate = vap->iv_newstate; 467 vap->iv_newstate = rsu_newstate; 468 469 /* complete setup */ 470 ieee80211_vap_attach(vap, ieee80211_media_change, |
493 ieee80211_media_status); | 471 ieee80211_media_status, mac); |
494 ic->ic_opmode = opmode; 495 496 return (vap); 497} 498 499static void 500rsu_vap_delete(struct ieee80211vap *vap) 501{ 502 struct rsu_vap *uvp = RSU_VAP(vap); 503 504 ieee80211_vap_detach(vap); 505 free(uvp, M_80211_VAP); 506} 507 508static void 509rsu_scan_start(struct ieee80211com *ic) 510{ | 472 ic->ic_opmode = opmode; 473 474 return (vap); 475} 476 477static void 478rsu_vap_delete(struct ieee80211vap *vap) 479{ 480 struct rsu_vap *uvp = RSU_VAP(vap); 481 482 ieee80211_vap_detach(vap); 483 free(uvp, M_80211_VAP); 484} 485 486static void 487rsu_scan_start(struct ieee80211com *ic) 488{ |
511 int error; | |
512 struct rsu_softc *sc = ic->ic_softc; | 489 struct rsu_softc *sc = ic->ic_softc; |
490 int error; |
|
513 514 /* Scanning is done by the firmware. */ 515 RSU_LOCK(sc); 516 error = rsu_site_survey(sc, TAILQ_FIRST(&ic->ic_vaps)); 517 RSU_UNLOCK(sc); 518 if (error != 0) 519 device_printf(sc->sc_dev, 520 "could not send site survey command\n"); --- 149 unchanged lines hidden (view full) --- 670static struct rsu_data * 671rsu_getbuf(struct rsu_softc *sc) 672{ 673 struct rsu_data *bf; 674 675 RSU_ASSERT_LOCKED(sc); 676 677 bf = _rsu_getbuf(sc); | 491 492 /* Scanning is done by the firmware. */ 493 RSU_LOCK(sc); 494 error = rsu_site_survey(sc, TAILQ_FIRST(&ic->ic_vaps)); 495 RSU_UNLOCK(sc); 496 if (error != 0) 497 device_printf(sc->sc_dev, 498 "could not send site survey command\n"); --- 149 unchanged lines hidden (view full) --- 648static struct rsu_data * 649rsu_getbuf(struct rsu_softc *sc) 650{ 651 struct rsu_data *bf; 652 653 RSU_ASSERT_LOCKED(sc); 654 655 bf = _rsu_getbuf(sc); |
678 if (bf == NULL) { 679 struct ifnet *ifp = sc->sc_ifp; | 656 if (bf == NULL) |
680 DPRINTF("stop queue\n"); | 657 DPRINTF("stop queue\n"); |
681 ifp->if_drv_flags |= IFF_DRV_OACTIVE; 682 } | |
683 return (bf); 684} 685 686static int 687rsu_write_region_1(struct rsu_softc *sc, uint16_t addr, uint8_t *buf, 688 int len) 689{ 690 usb_device_request_t req; --- 336 unchanged lines hidden (view full) --- 1027 (void)rsu_fw_cmd(sc, R92S_CMD_SET_KEY, &key, sizeof(key)); 1028} 1029#endif 1030 1031static int 1032rsu_site_survey(struct rsu_softc *sc, struct ieee80211vap *vap) 1033{ 1034 struct r92s_fw_cmd_sitesurvey cmd; | 658 return (bf); 659} 660 661static int 662rsu_write_region_1(struct rsu_softc *sc, uint16_t addr, uint8_t *buf, 663 int len) 664{ 665 usb_device_request_t req; --- 336 unchanged lines hidden (view full) --- 1002 (void)rsu_fw_cmd(sc, R92S_CMD_SET_KEY, &key, sizeof(key)); 1003} 1004#endif 1005 1006static int 1007rsu_site_survey(struct rsu_softc *sc, struct ieee80211vap *vap) 1008{ 1009 struct r92s_fw_cmd_sitesurvey cmd; |
1035 struct ifnet *ifp = sc->sc_ifp; 1036 struct ieee80211com *ic = ifp->if_l2com; | 1010 struct ieee80211com *ic = &sc->sc_ic; |
1037 1038 memset(&cmd, 0, sizeof(cmd)); | 1011 1012 memset(&cmd, 0, sizeof(cmd)); |
1039 if ((ic->ic_flags & IEEE80211_F_ASCAN) || sc->scan_pass == 1) | 1013 if ((ic->ic_flags & IEEE80211_F_ASCAN) || sc->sc_scan_pass == 1) |
1040 cmd.active = htole32(1); 1041 cmd.limit = htole32(48); | 1014 cmd.active = htole32(1); 1015 cmd.limit = htole32(48); |
1042 if (sc->scan_pass == 1 && vap->iv_des_nssid > 0) { | 1016 if (sc->sc_scan_pass == 1 && vap->iv_des_nssid > 0) { |
1043 /* Do a directed scan for second pass. */ 1044 cmd.ssidlen = htole32(vap->iv_des_ssid[0].len); 1045 memcpy(cmd.ssid, vap->iv_des_ssid[0].ssid, 1046 vap->iv_des_ssid[0].len); 1047 1048 } | 1017 /* Do a directed scan for second pass. */ 1018 cmd.ssidlen = htole32(vap->iv_des_ssid[0].len); 1019 memcpy(cmd.ssid, vap->iv_des_ssid[0].ssid, 1020 vap->iv_des_ssid[0].len); 1021 1022 } |
1049 DPRINTF("sending site survey command, pass=%d\n", sc->scan_pass); | 1023 DPRINTF("sending site survey command, pass=%d\n", sc->sc_scan_pass); |
1050 return (rsu_fw_cmd(sc, R92S_CMD_SITE_SURVEY, &cmd, sizeof(cmd))); 1051} 1052 1053static int 1054rsu_join_bss(struct rsu_softc *sc, struct ieee80211_node *ni) 1055{ | 1024 return (rsu_fw_cmd(sc, R92S_CMD_SITE_SURVEY, &cmd, sizeof(cmd))); 1025} 1026 1027static int 1028rsu_join_bss(struct rsu_softc *sc, struct ieee80211_node *ni) 1029{ |
1056 struct ifnet *ifp = sc->sc_ifp; 1057 struct ieee80211com *ic = ifp->if_l2com; | 1030 struct ieee80211com *ic = &sc->sc_ic; |
1058 struct ieee80211vap *vap = ni->ni_vap; 1059 struct ndis_wlan_bssid_ex *bss; 1060 struct ndis_802_11_fixed_ies *fixed; 1061 struct r92s_fw_cmd_auth auth; 1062 uint8_t buf[sizeof(*bss) + 128] __aligned(4); 1063 uint8_t *frm; 1064 uint8_t opmode; 1065 int error; --- 61 unchanged lines hidden (view full) --- 1127 /* Disassociate from our current BSS. */ 1128 DPRINTF("sending disconnect command\n"); 1129 return (rsu_fw_cmd(sc, R92S_CMD_DISCONNECT, &zero, sizeof(zero))); 1130} 1131 1132static void 1133rsu_event_survey(struct rsu_softc *sc, uint8_t *buf, int len) 1134{ | 1031 struct ieee80211vap *vap = ni->ni_vap; 1032 struct ndis_wlan_bssid_ex *bss; 1033 struct ndis_802_11_fixed_ies *fixed; 1034 struct r92s_fw_cmd_auth auth; 1035 uint8_t buf[sizeof(*bss) + 128] __aligned(4); 1036 uint8_t *frm; 1037 uint8_t opmode; 1038 int error; --- 61 unchanged lines hidden (view full) --- 1100 /* Disassociate from our current BSS. */ 1101 DPRINTF("sending disconnect command\n"); 1102 return (rsu_fw_cmd(sc, R92S_CMD_DISCONNECT, &zero, sizeof(zero))); 1103} 1104 1105static void 1106rsu_event_survey(struct rsu_softc *sc, uint8_t *buf, int len) 1107{ |
1135 struct ifnet *ifp = sc->sc_ifp; 1136 struct ieee80211com *ic = ifp->if_l2com; | 1108 struct ieee80211com *ic = &sc->sc_ic; |
1137 struct ieee80211_frame *wh; 1138 struct ieee80211_channel *c; 1139 struct ndis_wlan_bssid_ex *bss; 1140 struct mbuf *m; 1141 int pktlen; 1142 1143 if (__predict_false(len < sizeof(*bss))) 1144 return; --- 14 unchanged lines hidden (view full) --- 1159 m = m_get2(pktlen, M_NOWAIT, MT_DATA, M_PKTHDR); 1160 if (__predict_false(m == NULL)) 1161 return; 1162 wh = mtod(m, struct ieee80211_frame *); 1163 wh->i_fc[0] = IEEE80211_FC0_VERSION_0 | IEEE80211_FC0_TYPE_MGT | 1164 IEEE80211_FC0_SUBTYPE_BEACON; 1165 wh->i_fc[1] = IEEE80211_FC1_DIR_NODS; 1166 USETW(wh->i_dur, 0); | 1109 struct ieee80211_frame *wh; 1110 struct ieee80211_channel *c; 1111 struct ndis_wlan_bssid_ex *bss; 1112 struct mbuf *m; 1113 int pktlen; 1114 1115 if (__predict_false(len < sizeof(*bss))) 1116 return; --- 14 unchanged lines hidden (view full) --- 1131 m = m_get2(pktlen, M_NOWAIT, MT_DATA, M_PKTHDR); 1132 if (__predict_false(m == NULL)) 1133 return; 1134 wh = mtod(m, struct ieee80211_frame *); 1135 wh->i_fc[0] = IEEE80211_FC0_VERSION_0 | IEEE80211_FC0_TYPE_MGT | 1136 IEEE80211_FC0_SUBTYPE_BEACON; 1137 wh->i_fc[1] = IEEE80211_FC1_DIR_NODS; 1138 USETW(wh->i_dur, 0); |
1167 IEEE80211_ADDR_COPY(wh->i_addr1, ifp->if_broadcastaddr); | 1139 IEEE80211_ADDR_COPY(wh->i_addr1, ieee80211broadcastaddr); |
1168 IEEE80211_ADDR_COPY(wh->i_addr2, bss->macaddr); 1169 IEEE80211_ADDR_COPY(wh->i_addr3, bss->macaddr); 1170 *(uint16_t *)wh->i_seq = 0; 1171 memcpy(&wh[1], (uint8_t *)&bss[1], le32toh(bss->ieslen)); 1172 1173 /* Finalize mbuf. */ 1174 m->m_pkthdr.len = m->m_len = pktlen; | 1140 IEEE80211_ADDR_COPY(wh->i_addr2, bss->macaddr); 1141 IEEE80211_ADDR_COPY(wh->i_addr3, bss->macaddr); 1142 *(uint16_t *)wh->i_seq = 0; 1143 memcpy(&wh[1], (uint8_t *)&bss[1], le32toh(bss->ieslen)); 1144 1145 /* Finalize mbuf. */ 1146 m->m_pkthdr.len = m->m_len = pktlen; |
1175 m->m_pkthdr.rcvif = ifp; | |
1176 /* Fix the channel. */ 1177 c = ieee80211_find_channel_byieee(ic, 1178 le32toh(bss->config.dsconfig), 1179 IEEE80211_CHAN_G); 1180 if (c) { 1181 ic->ic_curchan = c; 1182 ieee80211_radiotap_chan_change(ic); 1183 } 1184 /* XXX avoid a LOR */ 1185 RSU_UNLOCK(sc); 1186 ieee80211_input_all(ic, m, le32toh(bss->rssi), 0); 1187 RSU_LOCK(sc); 1188} 1189 1190static void 1191rsu_event_join_bss(struct rsu_softc *sc, uint8_t *buf, int len) 1192{ | 1147 /* Fix the channel. */ 1148 c = ieee80211_find_channel_byieee(ic, 1149 le32toh(bss->config.dsconfig), 1150 IEEE80211_CHAN_G); 1151 if (c) { 1152 ic->ic_curchan = c; 1153 ieee80211_radiotap_chan_change(ic); 1154 } 1155 /* XXX avoid a LOR */ 1156 RSU_UNLOCK(sc); 1157 ieee80211_input_all(ic, m, le32toh(bss->rssi), 0); 1158 RSU_LOCK(sc); 1159} 1160 1161static void 1162rsu_event_join_bss(struct rsu_softc *sc, uint8_t *buf, int len) 1163{ |
1193 struct ifnet *ifp = sc->sc_ifp; 1194 struct ieee80211com *ic = ifp->if_l2com; | 1164 struct ieee80211com *ic = &sc->sc_ic; |
1195 struct ieee80211vap *vap = TAILQ_FIRST(&ic->ic_vaps); 1196 struct ieee80211_node *ni = vap->iv_bss; 1197 struct r92s_event_join_bss *rsp; 1198 uint32_t tmp; 1199 int res; 1200 1201 if (__predict_false(len < sizeof(*rsp))) 1202 return; --- 19 unchanged lines hidden (view full) --- 1222 ieee80211_new_state(vap, IEEE80211_S_RUN, 1223 IEEE80211_FC0_SUBTYPE_ASSOC_RESP); 1224 RSU_LOCK(sc); 1225} 1226 1227static void 1228rsu_rx_event(struct rsu_softc *sc, uint8_t code, uint8_t *buf, int len) 1229{ | 1165 struct ieee80211vap *vap = TAILQ_FIRST(&ic->ic_vaps); 1166 struct ieee80211_node *ni = vap->iv_bss; 1167 struct r92s_event_join_bss *rsp; 1168 uint32_t tmp; 1169 int res; 1170 1171 if (__predict_false(len < sizeof(*rsp))) 1172 return; --- 19 unchanged lines hidden (view full) --- 1192 ieee80211_new_state(vap, IEEE80211_S_RUN, 1193 IEEE80211_FC0_SUBTYPE_ASSOC_RESP); 1194 RSU_LOCK(sc); 1195} 1196 1197static void 1198rsu_rx_event(struct rsu_softc *sc, uint8_t code, uint8_t *buf, int len) 1199{ |
1230 struct ifnet *ifp = sc->sc_ifp; 1231 struct ieee80211com *ic = ifp->if_l2com; | 1200 struct ieee80211com *ic = &sc->sc_ic; |
1232 struct ieee80211vap *vap = TAILQ_FIRST(&ic->ic_vaps); 1233 1234 DPRINTFN(4, "Rx event code=%d len=%d\n", code, len); 1235 switch (code) { 1236 case R92S_EVT_SURVEY: 1237 if (vap->iv_state == IEEE80211_S_SCAN) 1238 rsu_event_survey(sc, buf, len); 1239 break; 1240 case R92S_EVT_SURVEY_DONE: 1241 DPRINTF("site survey pass %d done, found %d BSS\n", | 1201 struct ieee80211vap *vap = TAILQ_FIRST(&ic->ic_vaps); 1202 1203 DPRINTFN(4, "Rx event code=%d len=%d\n", code, len); 1204 switch (code) { 1205 case R92S_EVT_SURVEY: 1206 if (vap->iv_state == IEEE80211_S_SCAN) 1207 rsu_event_survey(sc, buf, len); 1208 break; 1209 case R92S_EVT_SURVEY_DONE: 1210 DPRINTF("site survey pass %d done, found %d BSS\n", |
1242 sc->scan_pass, le32toh(*(uint32_t *)buf)); | 1211 sc->sc_scan_pass, le32toh(*(uint32_t *)buf)); |
1243 if (vap->iv_state != IEEE80211_S_SCAN) 1244 break; /* Ignore if not scanning. */ | 1212 if (vap->iv_state != IEEE80211_S_SCAN) 1213 break; /* Ignore if not scanning. */ |
1245 if (sc->scan_pass == 0 && vap->iv_des_nssid != 0) { | 1214 if (sc->sc_scan_pass == 0 && vap->iv_des_nssid != 0) { |
1246 /* Schedule a directed scan for hidden APs. */ | 1215 /* Schedule a directed scan for hidden APs. */ |
1247 sc->scan_pass = 1; | 1216 sc->sc_scan_pass = 1; |
1248 RSU_UNLOCK(sc); 1249 ieee80211_new_state(vap, IEEE80211_S_SCAN, -1); 1250 RSU_LOCK(sc); 1251 break; 1252 } | 1217 RSU_UNLOCK(sc); 1218 ieee80211_new_state(vap, IEEE80211_S_SCAN, -1); 1219 RSU_LOCK(sc); 1220 break; 1221 } |
1253 sc->scan_pass = 0; | 1222 sc->sc_scan_pass = 0; |
1254 break; 1255 case R92S_EVT_JOIN_BSS: 1256 if (vap->iv_state == IEEE80211_S_AUTH) 1257 rsu_event_join_bss(sc, buf, len); 1258 break; 1259#if 0 1260XXX This event is occurring regularly, possibly due to some power saving event 1261XXX and disrupts the WLAN traffic. Disable for now. --- 6 unchanged lines hidden (view full) --- 1268 RSU_LOCK(sc); 1269 } 1270 break; 1271#endif 1272 case R92S_EVT_WPS_PBC: 1273 DPRINTF("WPS PBC pushed.\n"); 1274 break; 1275 case R92S_EVT_FWDBG: | 1223 break; 1224 case R92S_EVT_JOIN_BSS: 1225 if (vap->iv_state == IEEE80211_S_AUTH) 1226 rsu_event_join_bss(sc, buf, len); 1227 break; 1228#if 0 1229XXX This event is occurring regularly, possibly due to some power saving event 1230XXX and disrupts the WLAN traffic. Disable for now. --- 6 unchanged lines hidden (view full) --- 1237 RSU_LOCK(sc); 1238 } 1239 break; 1240#endif 1241 case R92S_EVT_WPS_PBC: 1242 DPRINTF("WPS PBC pushed.\n"); 1243 break; 1244 case R92S_EVT_FWDBG: |
1276 if (ifp->if_flags & IFF_DEBUG) { | 1245 if (vap->iv_ifp->if_flags & IFF_DEBUG) { |
1277 buf[60] = '\0'; 1278 printf("FWDBG: %s\n", (char *)buf); 1279 } 1280 break; 1281 default: 1282 break; 1283 } 1284} --- 50 unchanged lines hidden (view full) --- 1335 rssi = ((le32toh(phy->phydw1) >> 1) & 0x7f) - 106; 1336 } 1337 return (rssi); 1338} 1339 1340static struct mbuf * 1341rsu_rx_frame(struct rsu_softc *sc, uint8_t *buf, int pktlen, int *rssi) 1342{ | 1246 buf[60] = '\0'; 1247 printf("FWDBG: %s\n", (char *)buf); 1248 } 1249 break; 1250 default: 1251 break; 1252 } 1253} --- 50 unchanged lines hidden (view full) --- 1304 rssi = ((le32toh(phy->phydw1) >> 1) & 0x7f) - 106; 1305 } 1306 return (rssi); 1307} 1308 1309static struct mbuf * 1310rsu_rx_frame(struct rsu_softc *sc, uint8_t *buf, int pktlen, int *rssi) 1311{ |
1343 struct ifnet *ifp = sc->sc_ifp; 1344 struct ieee80211com *ic = ifp->if_l2com; | 1312 struct ieee80211com *ic = &sc->sc_ic; |
1345 struct ieee80211_frame *wh; 1346 struct r92s_rx_stat *stat; 1347 uint32_t rxdw0, rxdw3; 1348 struct mbuf *m; 1349 uint8_t rate; 1350 int infosz; 1351 1352 stat = (struct r92s_rx_stat *)buf; 1353 rxdw0 = le32toh(stat->rxdw0); 1354 rxdw3 = le32toh(stat->rxdw3); 1355 1356 if (__predict_false(rxdw0 & R92S_RXDW0_CRCERR)) { | 1313 struct ieee80211_frame *wh; 1314 struct r92s_rx_stat *stat; 1315 uint32_t rxdw0, rxdw3; 1316 struct mbuf *m; 1317 uint8_t rate; 1318 int infosz; 1319 1320 stat = (struct r92s_rx_stat *)buf; 1321 rxdw0 = le32toh(stat->rxdw0); 1322 rxdw3 = le32toh(stat->rxdw3); 1323 1324 if (__predict_false(rxdw0 & R92S_RXDW0_CRCERR)) { |
1357 if_inc_counter(ifp, IFCOUNTER_IERRORS, 1); | 1325 counter_u64_add(ic->ic_ierrors, 1); |
1358 return NULL; 1359 } 1360 if (__predict_false(pktlen < sizeof(*wh) || pktlen > MCLBYTES)) { | 1326 return NULL; 1327 } 1328 if (__predict_false(pktlen < sizeof(*wh) || pktlen > MCLBYTES)) { |
1361 if_inc_counter(ifp, IFCOUNTER_IERRORS, 1); | 1329 counter_u64_add(ic->ic_ierrors, 1); |
1362 return NULL; 1363 } 1364 1365 rate = MS(rxdw3, R92S_RXDW3_RATE); 1366 infosz = MS(rxdw0, R92S_RXDW0_INFOSZ) * 8; 1367 1368 /* Get RSSI from PHY status descriptor if present. */ 1369 if (infosz != 0) 1370 *rssi = rsu_get_rssi(sc, rate, &stat[1]); 1371 else 1372 *rssi = 0; 1373 1374 DPRINTFN(5, "Rx frame len=%d rate=%d infosz=%d rssi=%d\n", 1375 pktlen, rate, infosz, *rssi); 1376 1377 m = m_get2(pktlen, M_NOWAIT, MT_DATA, M_PKTHDR); 1378 if (__predict_false(m == NULL)) { | 1330 return NULL; 1331 } 1332 1333 rate = MS(rxdw3, R92S_RXDW3_RATE); 1334 infosz = MS(rxdw0, R92S_RXDW0_INFOSZ) * 8; 1335 1336 /* Get RSSI from PHY status descriptor if present. */ 1337 if (infosz != 0) 1338 *rssi = rsu_get_rssi(sc, rate, &stat[1]); 1339 else 1340 *rssi = 0; 1341 1342 DPRINTFN(5, "Rx frame len=%d rate=%d infosz=%d rssi=%d\n", 1343 pktlen, rate, infosz, *rssi); 1344 1345 m = m_get2(pktlen, M_NOWAIT, MT_DATA, M_PKTHDR); 1346 if (__predict_false(m == NULL)) { |
1379 if_inc_counter(ifp, IFCOUNTER_IERRORS, 1); | 1347 counter_u64_add(ic->ic_ierrors, 1); |
1380 return NULL; 1381 } | 1348 return NULL; 1349 } |
1382 /* Finalize mbuf. */ 1383 m->m_pkthdr.rcvif = ifp; | |
1384 /* Hardware does Rx TCP checksum offload. */ 1385 if (rxdw3 & R92S_RXDW3_TCPCHKVALID) { 1386 if (__predict_true(rxdw3 & R92S_RXDW3_TCPCHKRPT)) 1387 m->m_pkthdr.csum_flags |= CSUM_DATA_VALID; 1388 } 1389 wh = (struct ieee80211_frame *)((uint8_t *)&stat[1] + infosz); 1390 memcpy(mtod(m, uint8_t *), wh, pktlen); 1391 m->m_pkthdr.len = m->m_len = pktlen; --- 81 unchanged lines hidden (view full) --- 1473 1474 return (m0); 1475} 1476 1477static struct mbuf * 1478rsu_rxeof(struct usb_xfer *xfer, struct rsu_data *data, int *rssi) 1479{ 1480 struct rsu_softc *sc = data->sc; | 1350 /* Hardware does Rx TCP checksum offload. */ 1351 if (rxdw3 & R92S_RXDW3_TCPCHKVALID) { 1352 if (__predict_true(rxdw3 & R92S_RXDW3_TCPCHKRPT)) 1353 m->m_pkthdr.csum_flags |= CSUM_DATA_VALID; 1354 } 1355 wh = (struct ieee80211_frame *)((uint8_t *)&stat[1] + infosz); 1356 memcpy(mtod(m, uint8_t *), wh, pktlen); 1357 m->m_pkthdr.len = m->m_len = pktlen; --- 81 unchanged lines hidden (view full) --- 1439 1440 return (m0); 1441} 1442 1443static struct mbuf * 1444rsu_rxeof(struct usb_xfer *xfer, struct rsu_data *data, int *rssi) 1445{ 1446 struct rsu_softc *sc = data->sc; |
1447 struct ieee80211com *ic = &sc->sc_ic; |
|
1481 struct r92s_rx_stat *stat; 1482 int len; 1483 1484 usbd_xfer_status(xfer, &len, NULL, NULL, NULL); 1485 1486 if (__predict_false(len < sizeof(*stat))) { 1487 DPRINTF("xfer too short %d\n", len); | 1448 struct r92s_rx_stat *stat; 1449 int len; 1450 1451 usbd_xfer_status(xfer, &len, NULL, NULL, NULL); 1452 1453 if (__predict_false(len < sizeof(*stat))) { 1454 DPRINTF("xfer too short %d\n", len); |
1488 if_inc_counter(sc->sc_ifp, IFCOUNTER_IERRORS, 1); | 1455 counter_u64_add(ic->ic_ierrors, 1); |
1489 return (NULL); 1490 } 1491 /* Determine if it is a firmware C2H event or an 802.11 frame. */ 1492 stat = (struct r92s_rx_stat *)data->buf; 1493 if ((le32toh(stat->rxdw1) & 0x1ff) == 0x1ff) { 1494 rsu_rx_multi_event(sc, data->buf, len); 1495 /* No packets to process. */ 1496 return (NULL); 1497 } else 1498 return (rsu_rx_multi_frame(sc, data->buf, len, rssi)); 1499} 1500 1501static void 1502rsu_bulk_rx_callback(struct usb_xfer *xfer, usb_error_t error) 1503{ 1504 struct rsu_softc *sc = usbd_xfer_softc(xfer); | 1456 return (NULL); 1457 } 1458 /* Determine if it is a firmware C2H event or an 802.11 frame. */ 1459 stat = (struct r92s_rx_stat *)data->buf; 1460 if ((le32toh(stat->rxdw1) & 0x1ff) == 0x1ff) { 1461 rsu_rx_multi_event(sc, data->buf, len); 1462 /* No packets to process. */ 1463 return (NULL); 1464 } else 1465 return (rsu_rx_multi_frame(sc, data->buf, len, rssi)); 1466} 1467 1468static void 1469rsu_bulk_rx_callback(struct usb_xfer *xfer, usb_error_t error) 1470{ 1471 struct rsu_softc *sc = usbd_xfer_softc(xfer); |
1505 struct ifnet *ifp = sc->sc_ifp; 1506 struct ieee80211com *ic = ifp->if_l2com; | 1472 struct ieee80211com *ic = &sc->sc_ic; |
1507 struct ieee80211_frame *wh; 1508 struct ieee80211_node *ni; 1509 struct mbuf *m = NULL, *next; 1510 struct rsu_data *data; 1511 int rssi = 1; 1512 1513 RSU_ASSERT_LOCKED(sc); 1514 --- 43 unchanged lines hidden (view full) --- 1558 /* needs it to the inactive queue due to a error. */ 1559 data = STAILQ_FIRST(&sc->sc_rx_active); 1560 if (data != NULL) { 1561 STAILQ_REMOVE_HEAD(&sc->sc_rx_active, next); 1562 STAILQ_INSERT_TAIL(&sc->sc_rx_inactive, data, next); 1563 } 1564 if (error != USB_ERR_CANCELLED) { 1565 usbd_xfer_set_stall(xfer); | 1473 struct ieee80211_frame *wh; 1474 struct ieee80211_node *ni; 1475 struct mbuf *m = NULL, *next; 1476 struct rsu_data *data; 1477 int rssi = 1; 1478 1479 RSU_ASSERT_LOCKED(sc); 1480 --- 43 unchanged lines hidden (view full) --- 1524 /* needs it to the inactive queue due to a error. */ 1525 data = STAILQ_FIRST(&sc->sc_rx_active); 1526 if (data != NULL) { 1527 STAILQ_REMOVE_HEAD(&sc->sc_rx_active, next); 1528 STAILQ_INSERT_TAIL(&sc->sc_rx_inactive, data, next); 1529 } 1530 if (error != USB_ERR_CANCELLED) { 1531 usbd_xfer_set_stall(xfer); |
1566 if_inc_counter(ifp, IFCOUNTER_IERRORS, 1); | 1532 counter_u64_add(ic->ic_ierrors, 1); |
1567 goto tr_setup; 1568 } 1569 break; 1570 } 1571 1572} 1573 | 1533 goto tr_setup; 1534 } 1535 break; 1536 } 1537 1538} 1539 |
1574 | |
1575static void 1576rsu_txeof(struct usb_xfer *xfer, struct rsu_data *data) 1577{ | 1540static void 1541rsu_txeof(struct usb_xfer *xfer, struct rsu_data *data) 1542{ |
1578 struct rsu_softc *sc = usbd_xfer_softc(xfer); 1579 struct ifnet *ifp = sc->sc_ifp; 1580 struct mbuf *m; | |
1581 | 1543 |
1582 RSU_ASSERT_LOCKED(sc); 1583 1584 /* 1585 * Do any tx complete callback. Note this must be done before releasing 1586 * the node reference. 1587 */ | |
1588 if (data->m) { | 1544 if (data->m) { |
1589 m = data->m; 1590 if (m->m_flags & M_TXCB) { 1591 /* XXX status? */ 1592 ieee80211_process_callback(data->ni, m, 0); 1593 } 1594 m_freem(m); | 1545 /* XXX status? */ 1546 ieee80211_tx_complete(data->ni, data->m, 0); |
1595 data->m = NULL; | 1547 data->m = NULL; |
1596 } 1597 if (data->ni) { 1598 ieee80211_free_node(data->ni); | |
1599 data->ni = NULL; 1600 } | 1548 data->ni = NULL; 1549 } |
1601 if_inc_counter(ifp, IFCOUNTER_OPACKETS, 1); 1602 ifp->if_drv_flags &= ~IFF_DRV_OACTIVE; | |
1603} 1604 1605static void 1606rsu_bulk_tx_callback_sub(struct usb_xfer *xfer, usb_error_t error, 1607 uint8_t which) 1608{ 1609 struct rsu_softc *sc = usbd_xfer_softc(xfer); | 1550} 1551 1552static void 1553rsu_bulk_tx_callback_sub(struct usb_xfer *xfer, usb_error_t error, 1554 uint8_t which) 1555{ 1556 struct rsu_softc *sc = usbd_xfer_softc(xfer); |
1610 struct ifnet *ifp = sc->sc_ifp; | 1557 struct ieee80211com *ic = &sc->sc_ic; |
1611 struct rsu_data *data; 1612 1613 RSU_ASSERT_LOCKED(sc); 1614 1615 switch (USB_GET_STATE(xfer)) { 1616 case USB_ST_TRANSFERRED: 1617 data = STAILQ_FIRST(&sc->sc_tx_active[which]); 1618 if (data == NULL) --- 18 unchanged lines hidden (view full) --- 1637 break; 1638 default: 1639 data = STAILQ_FIRST(&sc->sc_tx_active[which]); 1640 if (data != NULL) { 1641 STAILQ_REMOVE_HEAD(&sc->sc_tx_active[which], next); 1642 rsu_txeof(xfer, data); 1643 STAILQ_INSERT_TAIL(&sc->sc_tx_inactive, data, next); 1644 } | 1558 struct rsu_data *data; 1559 1560 RSU_ASSERT_LOCKED(sc); 1561 1562 switch (USB_GET_STATE(xfer)) { 1563 case USB_ST_TRANSFERRED: 1564 data = STAILQ_FIRST(&sc->sc_tx_active[which]); 1565 if (data == NULL) --- 18 unchanged lines hidden (view full) --- 1584 break; 1585 default: 1586 data = STAILQ_FIRST(&sc->sc_tx_active[which]); 1587 if (data != NULL) { 1588 STAILQ_REMOVE_HEAD(&sc->sc_tx_active[which], next); 1589 rsu_txeof(xfer, data); 1590 STAILQ_INSERT_TAIL(&sc->sc_tx_inactive, data, next); 1591 } |
1645 if_inc_counter(ifp, IFCOUNTER_OERRORS, 1); | 1592 counter_u64_add(ic->ic_oerrors, 1); |
1646 1647 if (error != USB_ERR_CANCELLED) { 1648 usbd_xfer_set_stall(xfer); 1649 goto tr_setup; 1650 } 1651 break; 1652 } 1653} --- 9 unchanged lines hidden (view full) --- 1663{ 1664 rsu_bulk_tx_callback_sub(xfer, error, RSU_BULK_TX_VI_VO); 1665} 1666 1667static int 1668rsu_tx_start(struct rsu_softc *sc, struct ieee80211_node *ni, 1669 struct mbuf *m0, struct rsu_data *data) 1670{ | 1593 1594 if (error != USB_ERR_CANCELLED) { 1595 usbd_xfer_set_stall(xfer); 1596 goto tr_setup; 1597 } 1598 break; 1599 } 1600} --- 9 unchanged lines hidden (view full) --- 1610{ 1611 rsu_bulk_tx_callback_sub(xfer, error, RSU_BULK_TX_VI_VO); 1612} 1613 1614static int 1615rsu_tx_start(struct rsu_softc *sc, struct ieee80211_node *ni, 1616 struct mbuf *m0, struct rsu_data *data) 1617{ |
1671 struct ifnet *ifp = sc->sc_ifp; 1672 struct ieee80211com *ic = ifp->if_l2com; | 1618 struct ieee80211com *ic = &sc->sc_ic; |
1673 struct ieee80211vap *vap = ni->ni_vap; 1674 struct ieee80211_frame *wh; 1675 struct ieee80211_key *k = NULL; 1676 struct r92s_tx_desc *txd; 1677 uint8_t type; 1678 uint8_t tid = 0; 1679 uint8_t which; 1680 int hasqos; --- 85 unchanged lines hidden (view full) --- 1766 data->m = m0; 1767 STAILQ_INSERT_TAIL(&sc->sc_tx_pending[which], data, next); 1768 1769 /* start transfer, if any */ 1770 usbd_transfer_start(sc->sc_xfer[which]); 1771 return (0); 1772} 1773 | 1619 struct ieee80211vap *vap = ni->ni_vap; 1620 struct ieee80211_frame *wh; 1621 struct ieee80211_key *k = NULL; 1622 struct r92s_tx_desc *txd; 1623 uint8_t type; 1624 uint8_t tid = 0; 1625 uint8_t which; 1626 int hasqos; --- 85 unchanged lines hidden (view full) --- 1712 data->m = m0; 1713 STAILQ_INSERT_TAIL(&sc->sc_tx_pending[which], data, next); 1714 1715 /* start transfer, if any */ 1716 usbd_transfer_start(sc->sc_xfer[which]); 1717 return (0); 1718} 1719 |
1774static void 1775rsu_start(struct ifnet *ifp) | 1720static int 1721rsu_transmit(struct ieee80211com *ic, struct mbuf *m) |
1776{ | 1722{ |
1777 struct rsu_softc *sc = ifp->if_softc; | 1723 struct rsu_softc *sc = ic->ic_softc; 1724 int error; |
1778 | 1725 |
1779 if ((ifp->if_drv_flags & IFF_DRV_RUNNING) == 0) 1780 return; 1781 | |
1782 RSU_LOCK(sc); | 1726 RSU_LOCK(sc); |
1783 rsu_start_locked(ifp); | 1727 if (!sc->sc_running) { 1728 RSU_UNLOCK(sc); 1729 return (ENXIO); 1730 } 1731 error = mbufq_enqueue(&sc->sc_snd, m); 1732 if (error) { 1733 RSU_UNLOCK(sc); 1734 return (error); 1735 } 1736 rsu_start(sc); |
1784 RSU_UNLOCK(sc); | 1737 RSU_UNLOCK(sc); |
1738 1739 return (0); |
|
1785} 1786 1787static void | 1740} 1741 1742static void |
1788rsu_start_locked(struct ifnet *ifp) | 1743rsu_start(struct rsu_softc *sc) |
1789{ | 1744{ |
1790 struct rsu_softc *sc = ifp->if_softc; | |
1791 struct ieee80211_node *ni; 1792 struct rsu_data *bf; 1793 struct mbuf *m; 1794 1795 RSU_ASSERT_LOCKED(sc); 1796 | 1745 struct ieee80211_node *ni; 1746 struct rsu_data *bf; 1747 struct mbuf *m; 1748 1749 RSU_ASSERT_LOCKED(sc); 1750 |
1797 for (;;) { 1798 IFQ_DRV_DEQUEUE(&ifp->if_snd, m); 1799 if (m == NULL) | 1751 while ((m = mbufq_dequeue(&sc->sc_snd)) != NULL) { 1752 bf = rsu_getbuf(sc); 1753 if (bf == NULL) { 1754 mbufq_prepend(&sc->sc_snd, m); |
1800 break; | 1755 break; |
1756 } 1757 |
|
1801 ni = (struct ieee80211_node *)m->m_pkthdr.rcvif; 1802 m->m_pkthdr.rcvif = NULL; 1803 | 1758 ni = (struct ieee80211_node *)m->m_pkthdr.rcvif; 1759 m->m_pkthdr.rcvif = NULL; 1760 |
1804 bf = rsu_getbuf(sc); 1805 if (bf == NULL) { 1806 if_inc_counter(ifp, IFCOUNTER_IQDROPS, 1); 1807 m_freem(m); 1808 ieee80211_free_node(ni); 1809 } else if (rsu_tx_start(sc, ni, m, bf) != 0) { 1810 if_inc_counter(ifp, IFCOUNTER_OERRORS, 1); | 1761 if (rsu_tx_start(sc, ni, m, bf) != 0) { 1762 if_inc_counter(ni->ni_vap->iv_ifp, 1763 IFCOUNTER_OERRORS, 1); |
1811 STAILQ_INSERT_HEAD(&sc->sc_tx_inactive, bf, next); 1812 ieee80211_free_node(ni); | 1764 STAILQ_INSERT_HEAD(&sc->sc_tx_inactive, bf, next); 1765 ieee80211_free_node(ni); |
1766 break; |
|
1813 } 1814 } 1815} 1816 | 1767 } 1768 } 1769} 1770 |
1817static int 1818rsu_ioctl(struct ifnet *ifp, u_long cmd, caddr_t data) | 1771static void 1772rsu_parent(struct ieee80211com *ic) |
1819{ | 1773{ |
1820 struct ieee80211com *ic = ifp->if_l2com; | |
1821 struct rsu_softc *sc = ic->ic_softc; | 1774 struct rsu_softc *sc = ic->ic_softc; |
1822 struct ifreq *ifr = (struct ifreq *) data; 1823 int error = 0, startall = 0; | 1775 int startall = 0; |
1824 | 1776 |
1825 switch (cmd) { 1826 case SIOCSIFFLAGS: 1827 if (ifp->if_flags & IFF_UP) { 1828 if ((ifp->if_drv_flags & IFF_DRV_RUNNING) == 0) { 1829 rsu_init(sc); 1830 startall = 1; 1831 } 1832 } else { 1833 if (ifp->if_drv_flags & IFF_DRV_RUNNING) 1834 rsu_stop(ifp, 1); | 1777 RSU_LOCK(sc); 1778 if (ic->ic_nrunning > 0) { 1779 if (!sc->sc_running) { 1780 rsu_init(sc); 1781 startall = 1; |
1835 } | 1782 } |
1836 if (startall) 1837 ieee80211_start_all(ic); 1838 break; 1839 case SIOCGIFMEDIA: 1840 error = ifmedia_ioctl(ifp, ifr, &ic->ic_media, cmd); 1841 break; 1842 case SIOCGIFADDR: 1843 error = ether_ioctl(ifp, cmd, data); 1844 break; 1845 default: 1846 error = EINVAL; 1847 break; 1848 } | 1783 } else if (sc->sc_running) 1784 rsu_stop(sc); 1785 RSU_UNLOCK(sc); |
1849 | 1786 |
1850 return (error); | 1787 if (startall) 1788 ieee80211_start_all(ic); |
1851} 1852 1853/* 1854 * Power on sequence for A-cut adapters. 1855 */ 1856static void 1857rsu_power_on_acut(struct rsu_softc *sc) 1858{ --- 432 unchanged lines hidden (view full) --- 2291} 2292 2293 2294static int 2295rsu_raw_xmit(struct ieee80211_node *ni, struct mbuf *m, 2296 const struct ieee80211_bpf_params *params) 2297{ 2298 struct ieee80211com *ic = ni->ni_ic; | 1789} 1790 1791/* 1792 * Power on sequence for A-cut adapters. 1793 */ 1794static void 1795rsu_power_on_acut(struct rsu_softc *sc) 1796{ --- 432 unchanged lines hidden (view full) --- 2229} 2230 2231 2232static int 2233rsu_raw_xmit(struct ieee80211_node *ni, struct mbuf *m, 2234 const struct ieee80211_bpf_params *params) 2235{ 2236 struct ieee80211com *ic = ni->ni_ic; |
2299 struct ifnet *ifp = ic->ic_ifp; | |
2300 struct rsu_softc *sc = ic->ic_softc; 2301 struct rsu_data *bf; 2302 2303 /* prevent management frames from being sent if we're not ready */ | 2237 struct rsu_softc *sc = ic->ic_softc; 2238 struct rsu_data *bf; 2239 2240 /* prevent management frames from being sent if we're not ready */ |
2304 if (!(ifp->if_drv_flags & IFF_DRV_RUNNING)) { | 2241 if (!sc->sc_running) { |
2305 m_freem(m); 2306 ieee80211_free_node(ni); 2307 return (ENETDOWN); 2308 } 2309 RSU_LOCK(sc); 2310 bf = rsu_getbuf(sc); 2311 if (bf == NULL) { 2312 ieee80211_free_node(ni); 2313 m_freem(m); 2314 RSU_UNLOCK(sc); 2315 return (ENOBUFS); 2316 } | 2242 m_freem(m); 2243 ieee80211_free_node(ni); 2244 return (ENETDOWN); 2245 } 2246 RSU_LOCK(sc); 2247 bf = rsu_getbuf(sc); 2248 if (bf == NULL) { 2249 ieee80211_free_node(ni); 2250 m_freem(m); 2251 RSU_UNLOCK(sc); 2252 return (ENOBUFS); 2253 } |
2317 if_inc_counter(ifp, IFCOUNTER_OPACKETS, 1); | |
2318 if (rsu_tx_start(sc, ni, m, bf) != 0) { 2319 ieee80211_free_node(ni); | 2254 if (rsu_tx_start(sc, ni, m, bf) != 0) { 2255 ieee80211_free_node(ni); |
2320 if_inc_counter(ifp, IFCOUNTER_OERRORS, 1); | |
2321 STAILQ_INSERT_HEAD(&sc->sc_tx_inactive, bf, next); 2322 RSU_UNLOCK(sc); 2323 return (EIO); 2324 } 2325 RSU_UNLOCK(sc); 2326 2327 return (0); 2328} 2329 2330static void | 2256 STAILQ_INSERT_HEAD(&sc->sc_tx_inactive, bf, next); 2257 RSU_UNLOCK(sc); 2258 return (EIO); 2259 } 2260 RSU_UNLOCK(sc); 2261 2262 return (0); 2263} 2264 2265static void |
2331rsu_init(void *arg) | 2266rsu_init(struct rsu_softc *sc) |
2332{ | 2267{ |
2333 struct rsu_softc *sc = arg; 2334 2335 RSU_LOCK(sc); 2336 rsu_init_locked(arg); 2337 RSU_UNLOCK(sc); 2338} 2339 2340static void 2341rsu_init_locked(struct rsu_softc *sc) 2342{ 2343 struct ifnet *ifp = sc->sc_ifp; | 2268 struct ieee80211com *ic = &sc->sc_ic; 2269 struct ieee80211vap *vap = TAILQ_FIRST(&ic->ic_vaps); 2270 uint8_t macaddr[IEEE80211_ADDR_LEN]; |
2344 struct r92s_set_pwr_mode cmd; 2345 int error; 2346 int i; 2347 | 2271 struct r92s_set_pwr_mode cmd; 2272 int error; 2273 int i; 2274 |
2275 RSU_ASSERT_LOCKED(sc); 2276 |
|
2348 /* Init host async commands ring. */ 2349 sc->cmdq.cur = sc->cmdq.next = sc->cmdq.queued = 0; 2350 2351 /* Power on adapter. */ 2352 if (sc->cut == 1) 2353 rsu_power_on_acut(sc); 2354 else 2355 rsu_power_on_bcut(sc); --- 23 unchanged lines hidden (view full) --- 2379 rsu_write_1(sc, 0x00d9, 0x01); 2380 /* Set USB Rx aggregation timeout (1.7ms/4). */ 2381 rsu_write_1(sc, 0xfe5b, 0x04); 2382 /* Fix USB Rx FIFO issue. */ 2383 rsu_write_1(sc, 0xfe5c, 2384 rsu_read_1(sc, 0xfe5c) | 0x80); 2385 2386 /* Set MAC address. */ | 2277 /* Init host async commands ring. */ 2278 sc->cmdq.cur = sc->cmdq.next = sc->cmdq.queued = 0; 2279 2280 /* Power on adapter. */ 2281 if (sc->cut == 1) 2282 rsu_power_on_acut(sc); 2283 else 2284 rsu_power_on_bcut(sc); --- 23 unchanged lines hidden (view full) --- 2308 rsu_write_1(sc, 0x00d9, 0x01); 2309 /* Set USB Rx aggregation timeout (1.7ms/4). */ 2310 rsu_write_1(sc, 0xfe5b, 0x04); 2311 /* Fix USB Rx FIFO issue. */ 2312 rsu_write_1(sc, 0xfe5c, 2313 rsu_read_1(sc, 0xfe5c) | 0x80); 2314 2315 /* Set MAC address. */ |
2387 rsu_write_region_1(sc, R92S_MACID, IF_LLADDR(ifp), 2388 IEEE80211_ADDR_LEN); | 2316 IEEE80211_ADDR_COPY(macaddr, vap ? vap->iv_myaddr : ic->ic_macaddr); 2317 rsu_write_region_1(sc, R92S_MACID, macaddr, IEEE80211_ADDR_LEN); |
2389 2390 /* It really takes 1.5 seconds for the firmware to boot: */ 2391 usb_pause_mtx(&sc->sc_mtx, (3 * hz) / 2); 2392 | 2318 2319 /* It really takes 1.5 seconds for the firmware to boot: */ 2320 usb_pause_mtx(&sc->sc_mtx, (3 * hz) / 2); 2321 |
2393 DPRINTF("setting MAC address to %s\n", ether_sprintf(IF_LLADDR(ifp))); 2394 error = rsu_fw_cmd(sc, R92S_CMD_SET_MAC_ADDRESS, IF_LLADDR(ifp), | 2322 DPRINTF("setting MAC address to %s\n", ether_sprintf(macaddr)); 2323 error = rsu_fw_cmd(sc, R92S_CMD_SET_MAC_ADDRESS, macaddr, |
2395 IEEE80211_ADDR_LEN); 2396 if (error != 0) { 2397 device_printf(sc->sc_dev, "could not set MAC address\n"); 2398 goto fail; 2399 } 2400 2401 rsu_write_1(sc, R92S_USB_HRPWM, 2402 R92S_USB_HRPWM_PS_ST_ACTIVE | R92S_USB_HRPWM_PS_ALL_ON); --- 19 unchanged lines hidden (view full) --- 2422 "could not enable 40MHz mode\n"); 2423 goto fail; 2424 } 2425 } 2426 2427 /* Set default channel. */ 2428 ic->ic_bss->ni_chan = ic->ic_ibss_chan; 2429#endif | 2324 IEEE80211_ADDR_LEN); 2325 if (error != 0) { 2326 device_printf(sc->sc_dev, "could not set MAC address\n"); 2327 goto fail; 2328 } 2329 2330 rsu_write_1(sc, R92S_USB_HRPWM, 2331 R92S_USB_HRPWM_PS_ST_ACTIVE | R92S_USB_HRPWM_PS_ALL_ON); --- 19 unchanged lines hidden (view full) --- 2351 "could not enable 40MHz mode\n"); 2352 goto fail; 2353 } 2354 } 2355 2356 /* Set default channel. */ 2357 ic->ic_bss->ni_chan = ic->ic_ibss_chan; 2358#endif |
2430 sc->scan_pass = 0; | 2359 sc->sc_scan_pass = 0; |
2431 usbd_transfer_start(sc->sc_xfer[RSU_BULK_RX]); 2432 2433 /* We're ready to go. */ | 2360 usbd_transfer_start(sc->sc_xfer[RSU_BULK_RX]); 2361 2362 /* We're ready to go. */ |
2434 ifp->if_drv_flags &= ~IFF_DRV_OACTIVE; 2435 ifp->if_drv_flags |= IFF_DRV_RUNNING; | 2363 sc->sc_running = 1; |
2436 return; 2437fail: 2438 /* Need to stop all failed transfers, if any */ 2439 for (i = 0; i != RSU_N_TRANSFER; i++) 2440 usbd_transfer_stop(sc->sc_xfer[i]); 2441} 2442 2443static void | 2364 return; 2365fail: 2366 /* Need to stop all failed transfers, if any */ 2367 for (i = 0; i != RSU_N_TRANSFER; i++) 2368 usbd_transfer_stop(sc->sc_xfer[i]); 2369} 2370 2371static void |
2444rsu_stop(struct ifnet *ifp, int disable) | 2372rsu_stop(struct rsu_softc *sc) |
2445{ | 2373{ |
2446 struct rsu_softc *sc = ifp->if_softc; 2447 2448 RSU_LOCK(sc); 2449 rsu_stop_locked(ifp, disable); 2450 RSU_UNLOCK(sc); 2451} 2452 2453static void 2454rsu_stop_locked(struct ifnet *ifp, int disable __unused) 2455{ 2456 struct rsu_softc *sc = ifp->if_softc; | |
2457 int i; 2458 | 2374 int i; 2375 |
2459 ifp->if_drv_flags &= ~(IFF_DRV_RUNNING | IFF_DRV_OACTIVE); | 2376 sc->sc_running = 0; |
2460 sc->sc_calibrating = 0; 2461 taskqueue_cancel_timeout(taskqueue_thread, &sc->calib_task, NULL); 2462 2463 /* Power off adapter. */ 2464 rsu_power_off(sc); 2465 2466 for (i = 0; i < RSU_N_TRANSFER; i++) 2467 usbd_transfer_stop(sc->sc_xfer[i]); 2468} 2469 2470static void 2471rsu_ms_delay(struct rsu_softc *sc) 2472{ 2473 usb_pause_mtx(&sc->sc_mtx, hz / 1000); 2474} | 2377 sc->sc_calibrating = 0; 2378 taskqueue_cancel_timeout(taskqueue_thread, &sc->calib_task, NULL); 2379 2380 /* Power off adapter. */ 2381 rsu_power_off(sc); 2382 2383 for (i = 0; i < RSU_N_TRANSFER; i++) 2384 usbd_transfer_stop(sc->sc_xfer[i]); 2385} 2386 2387static void 2388rsu_ms_delay(struct rsu_softc *sc) 2389{ 2390 usb_pause_mtx(&sc->sc_mtx, hz / 1000); 2391} |