diff options
| author | Gleb Smirnoff <glebius@FreeBSD.org> | 2015-08-27 08:56:39 +0000 |
|---|---|---|
| committer | Gleb Smirnoff <glebius@FreeBSD.org> | 2015-08-27 08:56:39 +0000 |
| commit | 7a79cebfbac5e1de4648e0385b828bd161e05874 (patch) | |
| tree | 7898977af912b148a68c6e102a888b4316ea1fb5 /sys/dev/ral | |
| parent | 0cfae4b4bc88d749cf22ad377bac77b09eb31422 (diff) | |
Notes
Diffstat (limited to 'sys/dev/ral')
| -rw-r--r-- | sys/dev/ral/if_ral_pci.c | 1 | ||||
| -rw-r--r-- | sys/dev/ral/rt2560.c | 305 | ||||
| -rw-r--r-- | sys/dev/ral/rt2560var.h | 9 | ||||
| -rw-r--r-- | sys/dev/ral/rt2661.c | 289 | ||||
| -rw-r--r-- | sys/dev/ral/rt2661var.h | 7 | ||||
| -rw-r--r-- | sys/dev/ral/rt2860.c | 274 | ||||
| -rw-r--r-- | sys/dev/ral/rt2860var.h | 7 |
7 files changed, 349 insertions, 543 deletions
diff --git a/sys/dev/ral/if_ral_pci.c b/sys/dev/ral/if_ral_pci.c index 519b4ca30d78..42ec03424bdf 100644 --- a/sys/dev/ral/if_ral_pci.c +++ b/sys/dev/ral/if_ral_pci.c @@ -28,6 +28,7 @@ __FBSDID("$FreeBSD$"); #include <sys/kernel.h> #include <sys/lock.h> #include <sys/malloc.h> +#include <sys/mbuf.h> #include <sys/module.h> #include <sys/mutex.h> #include <sys/rman.h> diff --git a/sys/dev/ral/rt2560.c b/sys/dev/ral/rt2560.c index 29ce8cbf8014..ea9c4162b8f8 100644 --- a/sys/dev/ral/rt2560.c +++ b/sys/dev/ral/rt2560.c @@ -127,10 +127,10 @@ static int rt2560_tx_mgt(struct rt2560_softc *, struct mbuf *, struct ieee80211_node *); static int rt2560_tx_data(struct rt2560_softc *, struct mbuf *, struct ieee80211_node *); -static void rt2560_start_locked(struct ifnet *); -static void rt2560_start(struct ifnet *); +static int rt2560_transmit(struct ieee80211com *, struct mbuf *); +static void rt2560_start(struct rt2560_softc *); static void rt2560_watchdog(void *); -static int rt2560_ioctl(struct ifnet *, u_long, caddr_t); +static void rt2560_parent(struct ieee80211com *); static void rt2560_bbp_write(struct rt2560_softc *, uint8_t, uint8_t); static uint8_t rt2560_bbp_read(struct rt2560_softc *, uint8_t); @@ -149,7 +149,8 @@ static void rt2560_set_basicrates(struct rt2560_softc *, const struct ieee80211_rateset *); static void rt2560_update_led(struct rt2560_softc *, int, int); static void rt2560_set_bssid(struct rt2560_softc *, const uint8_t *); -static void rt2560_set_macaddr(struct rt2560_softc *, uint8_t *); +static void rt2560_set_macaddr(struct rt2560_softc *, + const uint8_t *); static void rt2560_get_macaddr(struct rt2560_softc *, uint8_t *); static void rt2560_update_promisc(struct ieee80211com *); static const char *rt2560_get_rf(int); @@ -197,11 +198,9 @@ int rt2560_attach(device_t dev, int id) { struct rt2560_softc *sc = device_get_softc(dev); - struct ieee80211com *ic; - struct ifnet *ifp; - int error; + struct ieee80211com *ic = &sc->sc_ic; uint8_t bands; - uint8_t macaddr[IEEE80211_ADDR_LEN]; + int error; sc->sc_dev = dev; @@ -209,6 +208,7 @@ rt2560_attach(device_t dev, int id) MTX_DEF | MTX_RECURSE); callout_init_mtx(&sc->watchdog_ch, &sc->sc_mtx, 0); + mbufq_init(&sc->sc_snd, ifqmaxlen); /* retrieve RT2560 rev. no */ sc->asic_rev = RAL_READ(sc, RT2560_CSR0); @@ -252,27 +252,9 @@ rt2560_attach(device_t dev, int id) goto fail5; } - ifp = sc->sc_ifp = if_alloc(IFT_IEEE80211); - if (ifp == NULL) { - device_printf(sc->sc_dev, "can not if_alloc()\n"); - goto fail6; - } - ic = ifp->if_l2com; - /* retrieve MAC address */ - rt2560_get_macaddr(sc, macaddr); - - ifp->if_softc = sc; - if_initname(ifp, device_get_name(dev), device_get_unit(dev)); - ifp->if_flags = IFF_BROADCAST | IFF_SIMPLEX | IFF_MULTICAST; - ifp->if_init = rt2560_init; - ifp->if_ioctl = rt2560_ioctl; - ifp->if_start = rt2560_start; - IFQ_SET_MAXLEN(&ifp->if_snd, ifqmaxlen); - ifp->if_snd.ifq_drv_maxlen = ifqmaxlen; - IFQ_SET_READY(&ifp->if_snd); + rt2560_get_macaddr(sc, ic->ic_macaddr); - ic->ic_ifp = ifp; ic->ic_softc = sc; ic->ic_name = device_get_nameunit(dev); ic->ic_opmode = IEEE80211_M_STA; @@ -303,7 +285,7 @@ rt2560_attach(device_t dev, int id) setbit(&bands, IEEE80211_MODE_11A); ieee80211_init_channels(ic, NULL, &bands); - ieee80211_ifattach(ic, macaddr); + ieee80211_ifattach(ic); ic->ic_raw_xmit = rt2560_raw_xmit; ic->ic_updateslot = rt2560_update_slot; ic->ic_update_promisc = rt2560_update_promisc; @@ -313,6 +295,8 @@ rt2560_attach(device_t dev, int id) ic->ic_vap_create = rt2560_vap_create; ic->ic_vap_delete = rt2560_vap_delete; + ic->ic_parent = rt2560_parent; + ic->ic_transmit = rt2560_transmit; ieee80211_radiotap_attach(ic, &sc->sc_txtap.wt_ihdr, sizeof(sc->sc_txtap), @@ -341,7 +325,6 @@ rt2560_attach(device_t dev, int id) return 0; -fail6: rt2560_free_rx_ring(sc, &sc->rxq); fail5: rt2560_free_tx_ring(sc, &sc->bcnq); fail4: rt2560_free_tx_ring(sc, &sc->prioq); fail3: rt2560_free_tx_ring(sc, &sc->atimq); @@ -355,12 +338,12 @@ int rt2560_detach(void *xsc) { struct rt2560_softc *sc = xsc; - struct ifnet *ifp = sc->sc_ifp; - struct ieee80211com *ic = ifp->if_l2com; + struct ieee80211com *ic = &sc->sc_ic; rt2560_stop(sc); ieee80211_ifdetach(ic); + mbufq_drain(&sc->sc_snd); rt2560_free_tx_ring(sc, &sc->txq); rt2560_free_tx_ring(sc, &sc->atimq); @@ -368,8 +351,6 @@ rt2560_detach(void *xsc) rt2560_free_tx_ring(sc, &sc->bcnq); rt2560_free_rx_ring(sc, &sc->rxq); - if_free(ifp); - mtx_destroy(&sc->sc_mtx); return 0; @@ -381,7 +362,7 @@ rt2560_vap_create(struct ieee80211com *ic, const char name[IFNAMSIZ], int unit, const uint8_t bssid[IEEE80211_ADDR_LEN], const uint8_t mac[IEEE80211_ADDR_LEN]) { - struct ifnet *ifp = ic->ic_ifp; + struct rt2560_softc *sc = ic->ic_softc; struct rt2560_vap *rvp; struct ieee80211vap *vap; @@ -394,7 +375,7 @@ rt2560_vap_create(struct ieee80211com *ic, const char name[IFNAMSIZ], int unit, case IEEE80211_M_MBSS: /* XXXRP: TBD */ if (!TAILQ_EMPTY(&ic->ic_vaps)) { - if_printf(ifp, "only 1 vap supported\n"); + device_printf(sc->sc_dev, "only 1 vap supported\n"); return NULL; } if (opmode == IEEE80211_M_STA) @@ -403,7 +384,8 @@ rt2560_vap_create(struct ieee80211com *ic, const char name[IFNAMSIZ], int unit, case IEEE80211_M_WDS: if (TAILQ_EMPTY(&ic->ic_vaps) || ic->ic_opmode != IEEE80211_M_HOSTAP) { - if_printf(ifp, "wds only supported in ap mode\n"); + device_printf(sc->sc_dev, + "wds only supported in ap mode\n"); return NULL; } /* @@ -414,15 +396,12 @@ rt2560_vap_create(struct ieee80211com *ic, const char name[IFNAMSIZ], int unit, flags &= ~IEEE80211_CLONE_BSSID; break; default: - if_printf(ifp, "unknown opmode %d\n", opmode); + device_printf(sc->sc_dev, "unknown opmode %d\n", opmode); return NULL; } - rvp = (struct rt2560_vap *) malloc(sizeof(struct rt2560_vap), - M_80211_VAP, M_NOWAIT | M_ZERO); - if (rvp == NULL) - return NULL; + rvp = malloc(sizeof(struct rt2560_vap), M_80211_VAP, M_WAITOK | M_ZERO); vap = &rvp->ral_vap; - ieee80211_vap_setup(ic, vap, name, unit, opmode, flags, bssid, mac); + ieee80211_vap_setup(ic, vap, name, unit, opmode, flags, bssid); /* override state transition machine */ rvp->ral_newstate = vap->iv_newstate; @@ -431,7 +410,8 @@ rt2560_vap_create(struct ieee80211com *ic, const char name[IFNAMSIZ], int unit, ieee80211_ratectl_init(vap); /* complete setup */ - ieee80211_vap_attach(vap, ieee80211_media_change, ieee80211_media_status); + ieee80211_vap_attach(vap, ieee80211_media_change, + ieee80211_media_status, mac); if (TAILQ_FIRST(&ic->ic_vaps) == vap) ic->ic_opmode = opmode; return vap; @@ -451,9 +431,8 @@ void rt2560_resume(void *xsc) { struct rt2560_softc *sc = xsc; - struct ifnet *ifp = sc->sc_ifp; - if (ifp->if_flags & IFF_UP) + if (sc->sc_ic.ic_nrunning > 0) rt2560_init(sc); } @@ -763,8 +742,7 @@ static int rt2560_newstate(struct ieee80211vap *vap, enum ieee80211_state nstate, int arg) { struct rt2560_vap *rvp = RT2560_VAP(vap); - struct ifnet *ifp = vap->iv_ic->ic_ifp; - struct rt2560_softc *sc = ifp->if_softc; + struct rt2560_softc *sc = vap->iv_ic->ic_softc; int error; if (nstate == IEEE80211_S_INIT && vap->iv_state == IEEE80211_S_RUN) { @@ -792,7 +770,8 @@ rt2560_newstate(struct ieee80211vap *vap, enum ieee80211_state nstate, int arg) vap->iv_opmode == IEEE80211_M_MBSS) { m = ieee80211_beacon_alloc(ni, &rvp->ral_bo); if (m == NULL) { - if_printf(ifp, "could not allocate beacon\n"); + device_printf(sc->sc_dev, + "could not allocate beacon\n"); return ENOBUFS; } ieee80211_ref_node(ni); @@ -926,14 +905,13 @@ rt2560_encryption_intr(struct rt2560_softc *sc) static void rt2560_tx_intr(struct rt2560_softc *sc) { - struct ifnet *ifp = sc->sc_ifp; struct rt2560_tx_desc *desc; struct rt2560_tx_data *data; struct mbuf *m; - uint32_t flags; - int retrycnt; struct ieee80211vap *vap; struct ieee80211_node *ni; + uint32_t flags; + int retrycnt, status; bus_dmamap_sync(sc->txq.desc_dmat, sc->txq.desc_map, BUS_DMASYNC_POSTREAD); @@ -961,7 +939,7 @@ rt2560_tx_intr(struct rt2560_softc *sc) ieee80211_ratectl_tx_complete(vap, ni, IEEE80211_RATECTL_TX_SUCCESS, &retrycnt, NULL); - if_inc_counter(ifp, IFCOUNTER_OPACKETS, 1); + status = 0; break; case RT2560_TX_SUCCESS_RETRY: @@ -973,7 +951,7 @@ rt2560_tx_intr(struct rt2560_softc *sc) ieee80211_ratectl_tx_complete(vap, ni, IEEE80211_RATECTL_TX_SUCCESS, &retrycnt, NULL); - if_inc_counter(ifp, IFCOUNTER_OPACKETS, 1); + status = 0; break; case RT2560_TX_FAIL_RETRY: @@ -985,7 +963,7 @@ rt2560_tx_intr(struct rt2560_softc *sc) ieee80211_ratectl_tx_complete(vap, ni, IEEE80211_RATECTL_TX_FAILURE, &retrycnt, NULL); - if_inc_counter(ifp, IFCOUNTER_OERRORS, 1); + status = 1; break; case RT2560_TX_FAIL_INVALID: @@ -993,16 +971,16 @@ rt2560_tx_intr(struct rt2560_softc *sc) default: device_printf(sc->sc_dev, "sending data frame failed " "0x%08x\n", flags); - if_inc_counter(ifp, IFCOUNTER_OERRORS, 1); + status = 1; } bus_dmamap_sync(sc->txq.data_dmat, data->map, BUS_DMASYNC_POSTWRITE); bus_dmamap_unload(sc->txq.data_dmat, data->map); - m_freem(m); - data->m = NULL; - ieee80211_free_node(data->ni); + + ieee80211_tx_complete(ni, m, status); data->ni = NULL; + data->m = NULL; /* descriptor is no longer valid */ desc->flags &= ~htole32(RT2560_TX_VALID); @@ -1019,19 +997,13 @@ rt2560_tx_intr(struct rt2560_softc *sc) if (sc->prioq.queued == 0 && sc->txq.queued == 0) sc->sc_tx_timer = 0; - if (sc->txq.queued < RT2560_TX_RING_COUNT - 1) { - sc->sc_flags &= ~RT2560_F_DATA_OACTIVE; - if ((sc->sc_flags & - (RT2560_F_DATA_OACTIVE | RT2560_F_PRIO_OACTIVE)) == 0) - ifp->if_drv_flags &= ~IFF_DRV_OACTIVE; - rt2560_start_locked(ifp); - } + if (sc->txq.queued < RT2560_TX_RING_COUNT - 1) + rt2560_start(sc); } static void rt2560_prio_intr(struct rt2560_softc *sc) { - struct ifnet *ifp = sc->sc_ifp; struct rt2560_tx_desc *desc; struct rt2560_tx_data *data; struct ieee80211_node *ni; @@ -1103,13 +1075,8 @@ rt2560_prio_intr(struct rt2560_softc *sc) if (sc->prioq.queued == 0 && sc->txq.queued == 0) sc->sc_tx_timer = 0; - if (sc->prioq.queued < RT2560_PRIO_RING_COUNT) { - sc->sc_flags &= ~RT2560_F_PRIO_OACTIVE; - if ((sc->sc_flags & - (RT2560_F_DATA_OACTIVE | RT2560_F_PRIO_OACTIVE)) == 0) - ifp->if_drv_flags &= ~IFF_DRV_OACTIVE; - rt2560_start_locked(ifp); - } + if (sc->prioq.queued < RT2560_PRIO_RING_COUNT) + rt2560_start(sc); } /* @@ -1119,8 +1086,7 @@ rt2560_prio_intr(struct rt2560_softc *sc) static void rt2560_decryption_intr(struct rt2560_softc *sc) { - struct ifnet *ifp = sc->sc_ifp; - struct ieee80211com *ic = ifp->if_l2com; + struct ieee80211com *ic = &sc->sc_ic; struct rt2560_rx_desc *desc; struct rt2560_rx_data *data; bus_addr_t physaddr; @@ -1146,13 +1112,13 @@ rt2560_decryption_intr(struct rt2560_softc *sc) break; if (data->drop) { - if_inc_counter(ifp, IFCOUNTER_IERRORS, 1); + counter_u64_add(ic->ic_ierrors, 1); goto skip; } if ((le32toh(desc->flags) & RT2560_RX_CIPHER_MASK) != 0 && (le32toh(desc->flags) & RT2560_RX_ICV_ERROR)) { - if_inc_counter(ifp, IFCOUNTER_IERRORS, 1); + counter_u64_add(ic->ic_ierrors, 1); goto skip; } @@ -1165,7 +1131,7 @@ rt2560_decryption_intr(struct rt2560_softc *sc) */ mnew = m_getcl(M_NOWAIT, MT_DATA, M_PKTHDR); if (mnew == NULL) { - if_inc_counter(ifp, IFCOUNTER_IERRORS, 1); + counter_u64_add(ic->ic_ierrors, 1); goto skip; } @@ -1188,7 +1154,7 @@ rt2560_decryption_intr(struct rt2560_softc *sc) panic("%s: could not load old rx mbuf", device_get_name(sc->sc_dev)); } - if_inc_counter(ifp, IFCOUNTER_IERRORS, 1); + counter_u64_add(ic->ic_ierrors, 1); goto skip; } @@ -1201,7 +1167,6 @@ rt2560_decryption_intr(struct rt2560_softc *sc) desc->physaddr = htole32(physaddr); /* finalize mbuf */ - m->m_pkthdr.rcvif = ifp; m->m_pkthdr.len = m->m_len = (le32toh(desc->flags) >> 16) & 0xfff; @@ -1321,8 +1286,7 @@ rt2560_beacon_update(struct ieee80211vap *vap, int item) static void rt2560_beacon_expire(struct rt2560_softc *sc) { - struct ifnet *ifp = sc->sc_ifp; - struct ieee80211com *ic = ifp->if_l2com; + struct ieee80211com *ic = &sc->sc_ic; struct ieee80211vap *vap = TAILQ_FIRST(&ic->ic_vaps); struct rt2560_vap *rvp = RT2560_VAP(vap); struct rt2560_tx_data *data; @@ -1363,7 +1327,6 @@ void rt2560_intr(void *arg) { struct rt2560_softc *sc = arg; - struct ifnet *ifp = sc->sc_ifp; uint32_t r; RAL_LOCK(sc); @@ -1372,7 +1335,7 @@ rt2560_intr(void *arg) RAL_WRITE(sc, RT2560_CSR8, 0xffffffff); /* don't re-enable interrupts if we're shutting down */ - if (!(ifp->if_drv_flags & IFF_DRV_RUNNING)) { + if (!(sc->sc_flags & RT2560_F_RUNNING)) { RAL_UNLOCK(sc); return; } @@ -1440,8 +1403,7 @@ static void rt2560_setup_tx_desc(struct rt2560_softc *sc, struct rt2560_tx_desc *desc, uint32_t flags, int len, int rate, int encrypt, bus_addr_t physaddr) { - struct ifnet *ifp = sc->sc_ifp; - struct ieee80211com *ic = ifp->if_l2com; + struct ieee80211com *ic = &sc->sc_ic; uint16_t plcp_length; int remainder; @@ -1916,55 +1878,57 @@ rt2560_tx_data(struct rt2560_softc *sc, struct mbuf *m0, return 0; } +static int +rt2560_transmit(struct ieee80211com *ic, struct mbuf *m) +{ + struct rt2560_softc *sc = ic->ic_softc; + int error; + + RAL_LOCK(sc); + if ((sc->sc_flags & RT2560_F_RUNNING) == 0) { + RAL_UNLOCK(sc); + return (ENXIO); + } + error = mbufq_enqueue(&sc->sc_snd, m); + if (error) { + RAL_UNLOCK(sc); + return (error); + } + rt2560_start(sc); + RAL_UNLOCK(sc); + + return (0); +} + static void -rt2560_start_locked(struct ifnet *ifp) +rt2560_start(struct rt2560_softc *sc) { - struct rt2560_softc *sc = ifp->if_softc; - struct mbuf *m; struct ieee80211_node *ni; + struct mbuf *m; RAL_LOCK_ASSERT(sc); - for (;;) { - IFQ_DRV_DEQUEUE(&ifp->if_snd, m); - if (m == NULL) - break; - if (sc->txq.queued >= RT2560_TX_RING_COUNT - 1) { - IFQ_DRV_PREPEND(&ifp->if_snd, m); - ifp->if_drv_flags |= IFF_DRV_OACTIVE; - sc->sc_flags |= RT2560_F_DATA_OACTIVE; - break; - } + while (sc->txq.queued < RT2560_TX_RING_COUNT - 1 && + (m = mbufq_dequeue(&sc->sc_snd)) != NULL) { ni = (struct ieee80211_node *) m->m_pkthdr.rcvif; if (rt2560_tx_data(sc, m, ni) != 0) { + if_inc_counter(ni->ni_vap->iv_ifp, + IFCOUNTER_OERRORS, 1); ieee80211_free_node(ni); - if_inc_counter(ifp, IFCOUNTER_OERRORS, 1); break; } - sc->sc_tx_timer = 5; } } static void -rt2560_start(struct ifnet *ifp) -{ - struct rt2560_softc *sc = ifp->if_softc; - - RAL_LOCK(sc); - rt2560_start_locked(ifp); - RAL_UNLOCK(sc); -} - -static void rt2560_watchdog(void *arg) { struct rt2560_softc *sc = arg; - struct ifnet *ifp = sc->sc_ifp; RAL_LOCK_ASSERT(sc); - KASSERT(ifp->if_drv_flags & IFF_DRV_RUNNING, ("not running")); + KASSERT(sc->sc_flags & RT2560_F_RUNNING, ("not running")); if (sc->sc_invalid) /* card ejected */ return; @@ -1973,51 +1937,33 @@ rt2560_watchdog(void *arg) rt2560_tx_intr(sc); if (sc->sc_tx_timer > 0 && --sc->sc_tx_timer == 0) { - if_printf(ifp, "device timeout\n"); + device_printf(sc->sc_dev, "device timeout\n"); rt2560_init_locked(sc); - if_inc_counter(ifp, IFCOUNTER_OERRORS, 1); + counter_u64_add(sc->sc_ic.ic_oerrors, 1); /* NB: callout is reset in rt2560_init() */ return; } callout_reset(&sc->watchdog_ch, hz, rt2560_watchdog, sc); } -static int -rt2560_ioctl(struct ifnet *ifp, u_long cmd, caddr_t data) +static void +rt2560_parent(struct ieee80211com *ic) { - struct rt2560_softc *sc = ifp->if_softc; - struct ieee80211com *ic = ifp->if_l2com; - struct ifreq *ifr = (struct ifreq *) data; - int error = 0, startall = 0; + struct rt2560_softc *sc = ic->ic_softc; + int startall = 0; - switch (cmd) { - case SIOCSIFFLAGS: - RAL_LOCK(sc); - if (ifp->if_flags & IFF_UP) { - if ((ifp->if_drv_flags & IFF_DRV_RUNNING) == 0) { - rt2560_init_locked(sc); - startall = 1; - } else - rt2560_update_promisc(ic); - } else { - if (ifp->if_drv_flags & IFF_DRV_RUNNING) - rt2560_stop_locked(sc); - } - RAL_UNLOCK(sc); - if (startall) - ieee80211_start_all(ic); - break; - case SIOCGIFMEDIA: - error = ifmedia_ioctl(ifp, ifr, &ic->ic_media, cmd); - break; - case SIOCGIFADDR: - error = ether_ioctl(ifp, cmd, data); - break; - default: - error = EINVAL; - break; - } - return error; + RAL_LOCK(sc); + if (ic->ic_nrunning > 0) { + if ((sc->sc_flags & RT2560_F_RUNNING) == 0) { + rt2560_init_locked(sc); + startall = 1; + } else + rt2560_update_promisc(ic); + } else if (sc->sc_flags & RT2560_F_RUNNING) + rt2560_stop_locked(sc); + RAL_UNLOCK(sc); + if (startall) + ieee80211_start_all(ic); } static void @@ -2101,8 +2047,7 @@ rt2560_rf_write(struct rt2560_softc *sc, uint8_t reg, uint32_t val) static void rt2560_set_chan(struct rt2560_softc *sc, struct ieee80211_channel *c) { - struct ifnet *ifp = sc->sc_ifp; - struct ieee80211com *ic = ifp->if_l2com; + struct ieee80211com *ic = &sc->sc_ic; uint8_t power, tmp; u_int i, chan; @@ -2201,8 +2146,7 @@ rt2560_set_chan(struct rt2560_softc *sc, struct ieee80211_channel *c) static void rt2560_set_channel(struct ieee80211com *ic) { - struct ifnet *ifp = ic->ic_ifp; - struct rt2560_softc *sc = ifp->if_softc; + struct rt2560_softc *sc = ic->ic_softc; RAL_LOCK(sc); rt2560_set_chan(sc, ic->ic_curchan); @@ -2238,8 +2182,7 @@ rt2560_disable_rf_tune(struct rt2560_softc *sc) static void rt2560_enable_tsf_sync(struct rt2560_softc *sc) { - struct ifnet *ifp = sc->sc_ifp; - struct ieee80211com *ic = ifp->if_l2com; + struct ieee80211com *ic = &sc->sc_ic; struct ieee80211vap *vap = TAILQ_FIRST(&ic->ic_vaps); uint16_t logcwmin, preload; uint32_t tmp; @@ -2280,8 +2223,7 @@ rt2560_enable_tsf(struct rt2560_softc *sc) static void rt2560_update_plcp(struct rt2560_softc *sc) { - struct ifnet *ifp = sc->sc_ifp; - struct ieee80211com *ic = ifp->if_l2com; + struct ieee80211com *ic = &sc->sc_ic; /* no short preamble for 1Mbps */ RAL_WRITE(sc, RT2560_PLCP1MCSR, 0x00700400); @@ -2360,8 +2302,7 @@ rt2560_set_basicrates(struct rt2560_softc *sc, const struct ieee80211_rateset *rs) { #define RV(r) ((r) & IEEE80211_RATE_VAL) - struct ifnet *ifp = sc->sc_ifp; - struct ieee80211com *ic = ifp->if_l2com; + struct ieee80211com *ic = &sc->sc_ic; uint32_t mask = 0; uint8_t rate; int i; @@ -2406,7 +2347,7 @@ rt2560_set_bssid(struct rt2560_softc *sc, const uint8_t *bssid) } static void -rt2560_set_macaddr(struct rt2560_softc *sc, uint8_t *addr) +rt2560_set_macaddr(struct rt2560_softc *sc, const uint8_t *addr) { uint32_t tmp; @@ -2444,13 +2385,13 @@ rt2560_update_promisc(struct ieee80211com *ic) tmp = RAL_READ(sc, RT2560_RXCSR0); tmp &= ~RT2560_DROP_NOT_TO_ME; - if (!(ic->ic_ifp->if_flags & IFF_PROMISC)) + if (ic->ic_promisc == 0) tmp |= RT2560_DROP_NOT_TO_ME; RAL_WRITE(sc, RT2560_RXCSR0, tmp); DPRINTF(sc, "%s promiscuous mode\n", - (ic->ic_ifp->if_flags & IFF_PROMISC) ? "entering" : "leaving"); + (ic->ic_promisc > 0) ? "entering" : "leaving"); } static const char * @@ -2516,19 +2457,17 @@ rt2560_read_config(struct rt2560_softc *sc) static void rt2560_scan_start(struct ieee80211com *ic) { - struct ifnet *ifp = ic->ic_ifp; - struct rt2560_softc *sc = ifp->if_softc; + struct rt2560_softc *sc = ic->ic_softc; /* abort TSF synchronization */ RAL_WRITE(sc, RT2560_CSR14, 0); - rt2560_set_bssid(sc, ifp->if_broadcastaddr); + rt2560_set_bssid(sc, ieee80211broadcastaddr); } static void rt2560_scan_end(struct ieee80211com *ic) { - struct ifnet *ifp = ic->ic_ifp; - struct rt2560_softc *sc = ifp->if_softc; + struct rt2560_softc *sc = ic->ic_softc; struct ieee80211vap *vap = ic->ic_scan->ss_vap; rt2560_enable_tsf_sync(sc); @@ -2622,8 +2561,8 @@ static void rt2560_init_locked(struct rt2560_softc *sc) { #define N(a) (sizeof (a) / sizeof ((a)[0])) - struct ifnet *ifp = sc->sc_ifp; - struct ieee80211com *ic = ifp->if_l2com; + struct ieee80211com *ic = &sc->sc_ic; + struct ieee80211vap *vap = TAILQ_FIRST(&ic->ic_vaps); uint32_t tmp; int i; @@ -2654,7 +2593,7 @@ rt2560_init_locked(struct rt2560_softc *sc) for (i = 0; i < N(rt2560_def_mac); i++) RAL_WRITE(sc, rt2560_def_mac[i].reg, rt2560_def_mac[i].val); - rt2560_set_macaddr(sc, IF_LLADDR(ifp)); + rt2560_set_macaddr(sc, vap ? vap->iv_myaddr : ic->ic_macaddr); /* set basic rate set (will be updated later) */ RAL_WRITE(sc, RT2560_ARSP_PLCP_1, 0x153); @@ -2684,7 +2623,7 @@ rt2560_init_locked(struct rt2560_softc *sc) if (ic->ic_opmode != IEEE80211_M_HOSTAP && ic->ic_opmode != IEEE80211_M_MBSS) tmp |= RT2560_DROP_TODS; - if (!(ifp->if_flags & IFF_PROMISC)) + if (ic->ic_promisc == 0) tmp |= RT2560_DROP_NOT_TO_ME; } RAL_WRITE(sc, RT2560_RXCSR0, tmp); @@ -2699,8 +2638,7 @@ rt2560_init_locked(struct rt2560_softc *sc) /* enable interrupts */ RAL_WRITE(sc, RT2560_CSR8, RT2560_INTR_MASK); - ifp->if_drv_flags &= ~IFF_DRV_OACTIVE; - ifp->if_drv_flags |= IFF_DRV_RUNNING; + sc->sc_flags |= RT2560_F_RUNNING; callout_reset(&sc->watchdog_ch, hz, rt2560_watchdog, sc); #undef N @@ -2710,21 +2648,19 @@ static void rt2560_init(void *priv) { struct rt2560_softc *sc = priv; - struct ifnet *ifp = sc->sc_ifp; - struct ieee80211com *ic = ifp->if_l2com; + struct ieee80211com *ic = &sc->sc_ic; RAL_LOCK(sc); rt2560_init_locked(sc); RAL_UNLOCK(sc); - if (ifp->if_drv_flags & IFF_DRV_RUNNING) + if (sc->sc_flags & RT2560_F_RUNNING) ieee80211_start_all(ic); /* start all vap's */ } static void rt2560_stop_locked(struct rt2560_softc *sc) { - struct ifnet *ifp = sc->sc_ifp; volatile int *flags = &sc->sc_flags; RAL_LOCK_ASSERT(sc); @@ -2735,8 +2671,8 @@ rt2560_stop_locked(struct rt2560_softc *sc) callout_stop(&sc->watchdog_ch); sc->sc_tx_timer = 0; - if (ifp->if_drv_flags & IFF_DRV_RUNNING) { - ifp->if_drv_flags &= ~(IFF_DRV_RUNNING | IFF_DRV_OACTIVE); + if (sc->sc_flags & RT2560_F_RUNNING) { + sc->sc_flags &= ~RT2560_F_RUNNING; /* abort Tx */ RAL_WRITE(sc, RT2560_TXCSR0, RT2560_ABORT_TX); @@ -2758,7 +2694,6 @@ rt2560_stop_locked(struct rt2560_softc *sc) rt2560_reset_tx_ring(sc, &sc->bcnq); rt2560_reset_rx_ring(sc, &sc->rxq); } - sc->sc_flags &= ~(RT2560_F_PRIO_OACTIVE | RT2560_F_DATA_OACTIVE); } void @@ -2776,29 +2711,24 @@ rt2560_raw_xmit(struct ieee80211_node *ni, struct mbuf *m, const struct ieee80211_bpf_params *params) { struct ieee80211com *ic = ni->ni_ic; - struct ifnet *ifp = ic->ic_ifp; - struct rt2560_softc *sc = ifp->if_softc; + struct rt2560_softc *sc = ic->ic_softc; RAL_LOCK(sc); /* prevent management frames from being sent if we're not ready */ - if (!(ifp->if_drv_flags & IFF_DRV_RUNNING)) { + if (!(sc->sc_flags & RT2560_F_RUNNING)) { RAL_UNLOCK(sc); m_freem(m); ieee80211_free_node(ni); return ENETDOWN; } if (sc->prioq.queued >= RT2560_PRIO_RING_COUNT) { - ifp->if_drv_flags |= IFF_DRV_OACTIVE; - sc->sc_flags |= RT2560_F_PRIO_OACTIVE; RAL_UNLOCK(sc); m_freem(m); ieee80211_free_node(ni); return ENOBUFS; /* XXX */ } - if_inc_counter(ifp, IFCOUNTER_OPACKETS, 1); - if (params == NULL) { /* * Legacy path; interpret frame contents to decide @@ -2820,7 +2750,6 @@ rt2560_raw_xmit(struct ieee80211_node *ni, struct mbuf *m, return 0; bad: - if_inc_counter(ifp, IFCOUNTER_OERRORS, 1); ieee80211_free_node(ni); RAL_UNLOCK(sc); return EIO; /* XXX */ diff --git a/sys/dev/ral/rt2560var.h b/sys/dev/ral/rt2560var.h index b6a8d68e9236..3a5fef981080 100644 --- a/sys/dev/ral/rt2560var.h +++ b/sys/dev/ral/rt2560var.h @@ -105,13 +105,13 @@ struct rt2560_vap { #define RT2560_VAP(vap) ((struct rt2560_vap *)(vap)) struct rt2560_softc { - struct ifnet *sc_ifp; + struct ieee80211com sc_ic; + struct mtx sc_mtx; + struct mbufq sc_snd; device_t sc_dev; bus_space_tag_t sc_st; bus_space_handle_t sc_sh; - struct mtx sc_mtx; - struct callout watchdog_ch; int sc_tx_timer; @@ -152,8 +152,7 @@ struct rt2560_softc { struct rt2560_tx_radiotap_header sc_txtap; int sc_txtap_len; #define RT2560_F_INPUT_RUNNING 0x1 -#define RT2560_F_PRIO_OACTIVE 0x2 -#define RT2560_F_DATA_OACTIVE 0x4 +#define RT2560_F_RUNNING 0x2 int sc_flags; }; diff --git a/sys/dev/ral/rt2661.c b/sys/dev/ral/rt2661.c index 15a2364a2c74..c77d4f88df76 100644 --- a/sys/dev/ral/rt2661.c +++ b/sys/dev/ral/rt2661.c @@ -121,12 +121,12 @@ static int rt2661_tx_data(struct rt2661_softc *, struct mbuf *, struct ieee80211_node *, int); static int rt2661_tx_mgt(struct rt2661_softc *, struct mbuf *, struct ieee80211_node *); -static void rt2661_start_locked(struct ifnet *); -static void rt2661_start(struct ifnet *); +static int rt2661_transmit(struct ieee80211com *, struct mbuf *); +static void rt2661_start(struct rt2661_softc *); static int rt2661_raw_xmit(struct ieee80211_node *, struct mbuf *, const struct ieee80211_bpf_params *); static void rt2661_watchdog(void *); -static int rt2661_ioctl(struct ifnet *, u_long, caddr_t); +static void rt2661_parent(struct ieee80211com *); static void rt2661_bbp_write(struct rt2661_softc *, uint8_t, uint8_t); static uint8_t rt2661_bbp_read(struct rt2661_softc *, uint8_t); @@ -197,27 +197,19 @@ int rt2661_attach(device_t dev, int id) { struct rt2661_softc *sc = device_get_softc(dev); - struct ieee80211com *ic; - struct ifnet *ifp; + struct ieee80211com *ic = &sc->sc_ic; uint32_t val; int error, ac, ntries; uint8_t bands; - uint8_t macaddr[IEEE80211_ADDR_LEN]; sc->sc_id = id; sc->sc_dev = dev; - ifp = sc->sc_ifp = if_alloc(IFT_IEEE80211); - if (ifp == NULL) { - device_printf(sc->sc_dev, "can not if_alloc()\n"); - return ENOMEM; - } - ic = ifp->if_l2com; - mtx_init(&sc->sc_mtx, device_get_nameunit(dev), MTX_NETWORK_LOCK, MTX_DEF | MTX_RECURSE); callout_init_mtx(&sc->watchdog_ch, &sc->sc_mtx, 0); + mbufq_init(&sc->sc_snd, ifqmaxlen); /* wait for NIC to initialize */ for (ntries = 0; ntries < 1000; ntries++) { @@ -233,7 +225,7 @@ rt2661_attach(device_t dev, int id) } /* retrieve RF rev. no and various other things from EEPROM */ - rt2661_read_eeprom(sc, macaddr); + rt2661_read_eeprom(sc, ic->ic_macaddr); device_printf(dev, "MAC/BBP RT%X, RF %s\n", val, rt2661_get_rf(sc->rf_rev)); @@ -263,17 +255,6 @@ rt2661_attach(device_t dev, int id) goto fail3; } - ifp->if_softc = sc; - if_initname(ifp, device_get_name(dev), device_get_unit(dev)); - ifp->if_flags = IFF_BROADCAST | IFF_SIMPLEX | IFF_MULTICAST; - ifp->if_init = rt2661_init; - ifp->if_ioctl = rt2661_ioctl; - ifp->if_start = rt2661_start; - IFQ_SET_MAXLEN(&ifp->if_snd, ifqmaxlen); - ifp->if_snd.ifq_drv_maxlen = ifqmaxlen; - IFQ_SET_READY(&ifp->if_snd); - - ic->ic_ifp = ifp; ic->ic_softc = sc; ic->ic_name = device_get_nameunit(dev); ic->ic_opmode = IEEE80211_M_STA; @@ -305,7 +286,7 @@ rt2661_attach(device_t dev, int id) setbit(&bands, IEEE80211_MODE_11A); ieee80211_init_channels(ic, NULL, &bands); - ieee80211_ifattach(ic, macaddr); + ieee80211_ifattach(ic); #if 0 ic->ic_wme.wme_update = rt2661_wme_update; #endif @@ -315,7 +296,8 @@ rt2661_attach(device_t dev, int id) ic->ic_updateslot = rt2661_update_slot; ic->ic_update_promisc = rt2661_update_promisc; ic->ic_raw_xmit = rt2661_raw_xmit; - + ic->ic_transmit = rt2661_transmit; + ic->ic_parent = rt2661_parent; ic->ic_vap_create = rt2661_vap_create; ic->ic_vap_delete = rt2661_vap_delete; @@ -339,7 +321,6 @@ fail3: rt2661_free_tx_ring(sc, &sc->mgtq); fail2: while (--ac >= 0) rt2661_free_tx_ring(sc, &sc->txq[ac]); fail1: mtx_destroy(&sc->sc_mtx); - if_free(ifp); return error; } @@ -347,14 +328,14 @@ int rt2661_detach(void *xsc) { struct rt2661_softc *sc = xsc; - struct ifnet *ifp = sc->sc_ifp; - struct ieee80211com *ic = ifp->if_l2com; + struct ieee80211com *ic = &sc->sc_ic; RAL_LOCK(sc); rt2661_stop_locked(sc); RAL_UNLOCK(sc); ieee80211_ifdetach(ic); + mbufq_drain(&sc->sc_snd); rt2661_free_tx_ring(sc, &sc->txq[0]); rt2661_free_tx_ring(sc, &sc->txq[1]); @@ -363,8 +344,6 @@ rt2661_detach(void *xsc) rt2661_free_tx_ring(sc, &sc->mgtq); rt2661_free_rx_ring(sc, &sc->rxq); - if_free(ifp); - mtx_destroy(&sc->sc_mtx); return 0; @@ -376,7 +355,7 @@ rt2661_vap_create(struct ieee80211com *ic, const char name[IFNAMSIZ], int unit, const uint8_t bssid[IEEE80211_ADDR_LEN], const uint8_t mac[IEEE80211_ADDR_LEN]) { - struct ifnet *ifp = ic->ic_ifp; + struct rt2661_softc *sc = ic->ic_softc; struct rt2661_vap *rvp; struct ieee80211vap *vap; @@ -389,7 +368,7 @@ rt2661_vap_create(struct ieee80211com *ic, const char name[IFNAMSIZ], int unit, case IEEE80211_M_MBSS: /* XXXRP: TBD */ if (!TAILQ_EMPTY(&ic->ic_vaps)) { - if_printf(ifp, "only 1 vap supported\n"); + device_printf(sc->sc_dev, "only 1 vap supported\n"); return NULL; } if (opmode == IEEE80211_M_STA) @@ -398,7 +377,8 @@ rt2661_vap_create(struct ieee80211com *ic, const char name[IFNAMSIZ], int unit, case IEEE80211_M_WDS: if (TAILQ_EMPTY(&ic->ic_vaps) || ic->ic_opmode != IEEE80211_M_HOSTAP) { - if_printf(ifp, "wds only supported in ap mode\n"); + device_printf(sc->sc_dev, + "wds only supported in ap mode\n"); return NULL; } /* @@ -409,15 +389,12 @@ rt2661_vap_create(struct ieee80211com *ic, const char name[IFNAMSIZ], int unit, flags &= ~IEEE80211_CLONE_BSSID; break; default: - if_printf(ifp, "unknown opmode %d\n", opmode); + device_printf(sc->sc_dev, "unknown opmode %d\n", opmode); return NULL; } - rvp = (struct rt2661_vap *) malloc(sizeof(struct rt2661_vap), - M_80211_VAP, M_NOWAIT | M_ZERO); - if (rvp == NULL) - return NULL; + rvp = malloc(sizeof(struct rt2661_vap), M_80211_VAP, M_WAITOK | M_ZERO); vap = &rvp->ral_vap; - ieee80211_vap_setup(ic, vap, name, unit, opmode, flags, bssid, mac); + ieee80211_vap_setup(ic, vap, name, unit, opmode, flags, bssid); /* override state transition machine */ rvp->ral_newstate = vap->iv_newstate; @@ -428,7 +405,8 @@ rt2661_vap_create(struct ieee80211com *ic, const char name[IFNAMSIZ], int unit, ieee80211_ratectl_init(vap); /* complete setup */ - ieee80211_vap_attach(vap, ieee80211_media_change, ieee80211_media_status); + ieee80211_vap_attach(vap, ieee80211_media_change, + ieee80211_media_status, mac); if (TAILQ_FIRST(&ic->ic_vaps) == vap) ic->ic_opmode = opmode; return vap; @@ -464,9 +442,8 @@ void rt2661_resume(void *xsc) { struct rt2661_softc *sc = xsc; - struct ifnet *ifp = sc->sc_ifp; - if (ifp->if_flags & IFF_UP) + if (sc->sc_ic.ic_nrunning > 0) rt2661_init(sc); } @@ -770,7 +747,7 @@ rt2661_newstate(struct ieee80211vap *vap, enum ieee80211_state nstate, int arg) { struct rt2661_vap *rvp = RT2661_VAP(vap); struct ieee80211com *ic = vap->iv_ic; - struct rt2661_softc *sc = ic->ic_ifp->if_softc; + struct rt2661_softc *sc = ic->ic_softc; int error; if (nstate == IEEE80211_S_INIT && vap->iv_state == IEEE80211_S_RUN) { @@ -869,11 +846,10 @@ rt2661_eeprom_read(struct rt2661_softc *sc, uint8_t addr) static void rt2661_tx_intr(struct rt2661_softc *sc) { - struct ifnet *ifp = sc->sc_ifp; struct rt2661_tx_ring *txq; struct rt2661_tx_data *data; uint32_t val; - int qid, retrycnt; + int error, qid, retrycnt; struct ieee80211vap *vap; for (;;) { @@ -911,7 +887,7 @@ rt2661_tx_intr(struct rt2661_softc *sc) ieee80211_ratectl_tx_complete(vap, ni, IEEE80211_RATECTL_TX_SUCCESS, &retrycnt, NULL); - if_inc_counter(ifp, IFCOUNTER_OPACKETS, 1); + error = 0; break; case RT2661_TX_RETRY_FAIL: @@ -923,14 +899,14 @@ rt2661_tx_intr(struct rt2661_softc *sc) ieee80211_ratectl_tx_complete(vap, ni, IEEE80211_RATECTL_TX_FAILURE, &retrycnt, NULL); - if_inc_counter(ifp, IFCOUNTER_OERRORS, 1); + error = 1; break; default: /* other failure */ device_printf(sc->sc_dev, "sending data frame failed 0x%08x\n", val); - if_inc_counter(ifp, IFCOUNTER_OERRORS, 1); + error = 1; } DPRINTFN(sc, 15, "tx done q=%d idx=%u\n", qid, txq->stat); @@ -939,17 +915,12 @@ rt2661_tx_intr(struct rt2661_softc *sc) if (++txq->stat >= txq->count) /* faster than % count */ txq->stat = 0; - if (m->m_flags & M_TXCB) - ieee80211_process_callback(ni, m, - RT2661_TX_RESULT(val) != RT2661_TX_SUCCESS); - m_freem(m); - ieee80211_free_node(ni); + ieee80211_tx_complete(ni, m, error); } sc->sc_tx_timer = 0; - ifp->if_drv_flags &= ~IFF_DRV_OACTIVE; - rt2661_start_locked(ifp); + rt2661_start(sc); } static void @@ -987,8 +958,7 @@ rt2661_tx_dma_intr(struct rt2661_softc *sc, struct rt2661_tx_ring *txq) static void rt2661_rx_intr(struct rt2661_softc *sc) { - struct ifnet *ifp = sc->sc_ifp; - struct ieee80211com *ic = ifp->if_l2com; + struct ieee80211com *ic = &sc->sc_ic; struct rt2661_rx_desc *desc; struct rt2661_rx_data *data; bus_addr_t physaddr; @@ -1017,12 +987,12 @@ rt2661_rx_intr(struct rt2661_softc *sc) */ DPRINTFN(sc, 5, "PHY or CRC error flags 0x%08x\n", le32toh(desc->flags)); - if_inc_counter(ifp, IFCOUNTER_IERRORS, 1); + counter_u64_add(ic->ic_ierrors, 1); goto skip; } if ((le32toh(desc->flags) & RT2661_RX_CIPHER_MASK) != 0) { - if_inc_counter(ifp, IFCOUNTER_IERRORS, 1); + counter_u64_add(ic->ic_ierrors, 1); goto skip; } @@ -1035,7 +1005,7 @@ rt2661_rx_intr(struct rt2661_softc *sc) */ mnew = m_getcl(M_NOWAIT, MT_DATA, M_PKTHDR); if (mnew == NULL) { - if_inc_counter(ifp, IFCOUNTER_IERRORS, 1); + counter_u64_add(ic->ic_ierrors, 1); goto skip; } @@ -1058,7 +1028,7 @@ rt2661_rx_intr(struct rt2661_softc *sc) panic("%s: could not load old rx mbuf", device_get_name(sc->sc_dev)); } - if_inc_counter(ifp, IFCOUNTER_IERRORS, 1); + counter_u64_add(ic->ic_ierrors, 1); goto skip; } @@ -1071,7 +1041,6 @@ rt2661_rx_intr(struct rt2661_softc *sc) desc->physaddr = htole32(physaddr); /* finalize mbuf */ - m->m_pkthdr.rcvif = ifp; m->m_pkthdr.len = m->m_len = (le32toh(desc->flags) >> 16) & 0xfff; @@ -1156,7 +1125,6 @@ void rt2661_intr(void *arg) { struct rt2661_softc *sc = arg; - struct ifnet *ifp = sc->sc_ifp; uint32_t r1, r2; RAL_LOCK(sc); @@ -1166,7 +1134,7 @@ rt2661_intr(void *arg) RAL_WRITE(sc, RT2661_MCU_INT_MASK_CSR, 0xffffffff); /* don't re-enable interrupts if we're shutting down */ - if (!(ifp->if_drv_flags & IFF_DRV_RUNNING)) { + if (!(sc->sc_flags & RAL_RUNNING)) { RAL_UNLOCK(sc); return; } @@ -1242,8 +1210,7 @@ rt2661_setup_tx_desc(struct rt2661_softc *sc, struct rt2661_tx_desc *desc, uint32_t flags, uint16_t xflags, int len, int rate, const bus_dma_segment_t *segs, int nsegs, int ac) { - struct ifnet *ifp = sc->sc_ifp; - struct ieee80211com *ic = ifp->if_l2com; + struct ieee80211com *ic = &sc->sc_ic; uint16_t plcp_length; int i, remainder; @@ -1461,8 +1428,7 @@ rt2661_tx_data(struct rt2661_softc *sc, struct mbuf *m0, struct ieee80211_node *ni, int ac) { struct ieee80211vap *vap = ni->ni_vap; - struct ifnet *ifp = sc->sc_ifp; - struct ieee80211com *ic = ifp->if_l2com; + struct ieee80211com *ic = &sc->sc_ic; struct rt2661_tx_ring *txq = &sc->txq[ac]; struct rt2661_tx_desc *desc; struct rt2661_tx_data *data; @@ -1604,10 +1570,31 @@ rt2661_tx_data(struct rt2661_softc *sc, struct mbuf *m0, return 0; } +static int +rt2661_transmit(struct ieee80211com *ic, struct mbuf *m) +{ + struct rt2661_softc *sc = ic->ic_softc; + int error; + + RAL_LOCK(sc); + if ((sc->sc_flags & RAL_RUNNING) == 0) { + RAL_UNLOCK(sc); + return (ENXIO); + } + error = mbufq_enqueue(&sc->sc_snd, m); + if (error) { + RAL_UNLOCK(sc); + return (error); + } + rt2661_start(sc); + RAL_UNLOCK(sc); + + return (0); +} + static void -rt2661_start_locked(struct ifnet *ifp) +rt2661_start(struct rt2661_softc *sc) { - struct rt2661_softc *sc = ifp->if_softc; struct mbuf *m; struct ieee80211_node *ni; int ac; @@ -1615,69 +1602,50 @@ rt2661_start_locked(struct ifnet *ifp) RAL_LOCK_ASSERT(sc); /* prevent management frames from being sent if we're not ready */ - if (!(ifp->if_drv_flags & IFF_DRV_RUNNING) || sc->sc_invalid) + if (!(sc->sc_flags & RAL_RUNNING) || sc->sc_invalid) return; - for (;;) { - IFQ_DRV_DEQUEUE(&ifp->if_snd, m); - if (m == NULL) - break; - + while ((m = mbufq_dequeue(&sc->sc_snd)) != NULL) { ac = M_WME_GETAC(m); if (sc->txq[ac].queued >= RT2661_TX_RING_COUNT - 1) { /* there is no place left in this ring */ - IFQ_DRV_PREPEND(&ifp->if_snd, m); - ifp->if_drv_flags |= IFF_DRV_OACTIVE; + mbufq_prepend(&sc->sc_snd, m); break; } ni = (struct ieee80211_node *) m->m_pkthdr.rcvif; if (rt2661_tx_data(sc, m, ni, ac) != 0) { ieee80211_free_node(ni); - if_inc_counter(ifp, IFCOUNTER_OERRORS, 1); + if_inc_counter(ni->ni_vap->iv_ifp, + IFCOUNTER_OERRORS, 1); break; } - sc->sc_tx_timer = 5; } } -static void -rt2661_start(struct ifnet *ifp) -{ - struct rt2661_softc *sc = ifp->if_softc; - - RAL_LOCK(sc); - rt2661_start_locked(ifp); - RAL_UNLOCK(sc); -} - static int rt2661_raw_xmit(struct ieee80211_node *ni, struct mbuf *m, const struct ieee80211_bpf_params *params) { struct ieee80211com *ic = ni->ni_ic; - struct ifnet *ifp = ic->ic_ifp; - struct rt2661_softc *sc = ifp->if_softc; + struct rt2661_softc *sc = ic->ic_softc; RAL_LOCK(sc); /* prevent management frames from being sent if we're not ready */ - if (!(ifp->if_drv_flags & IFF_DRV_RUNNING)) { + if (!(sc->sc_flags & RAL_RUNNING)) { RAL_UNLOCK(sc); m_freem(m); ieee80211_free_node(ni); return ENETDOWN; } if (sc->mgtq.queued >= RT2661_MGT_RING_COUNT) { - ifp->if_drv_flags |= IFF_DRV_OACTIVE; RAL_UNLOCK(sc); m_freem(m); ieee80211_free_node(ni); return ENOBUFS; /* XXX */ } - if_inc_counter(ifp, IFCOUNTER_OPACKETS, 1); - /* * Legacy path; interpret frame contents to decide * precisely how to send the frame. @@ -1691,7 +1659,6 @@ rt2661_raw_xmit(struct ieee80211_node *ni, struct mbuf *m, return 0; bad: - if_inc_counter(ifp, IFCOUNTER_OERRORS, 1); ieee80211_free_node(ni); RAL_UNLOCK(sc); return EIO; /* XXX */ @@ -1701,61 +1668,42 @@ static void rt2661_watchdog(void *arg) { struct rt2661_softc *sc = (struct rt2661_softc *)arg; - struct ifnet *ifp = sc->sc_ifp; RAL_LOCK_ASSERT(sc); - KASSERT(ifp->if_drv_flags & IFF_DRV_RUNNING, ("not running")); + KASSERT(sc->sc_flags & RAL_RUNNING, ("not running")); if (sc->sc_invalid) /* card ejected */ return; if (sc->sc_tx_timer > 0 && --sc->sc_tx_timer == 0) { - if_printf(ifp, "device timeout\n"); + device_printf(sc->sc_dev, "device timeout\n"); rt2661_init_locked(sc); - if_inc_counter(ifp, IFCOUNTER_OERRORS, 1); + counter_u64_add(sc->sc_ic.ic_oerrors, 1); /* NB: callout is reset in rt2661_init() */ return; } callout_reset(&sc->watchdog_ch, hz, rt2661_watchdog, sc); } -static int -rt2661_ioctl(struct ifnet *ifp, u_long cmd, caddr_t data) +static void +rt2661_parent(struct ieee80211com *ic) { - struct rt2661_softc *sc = ifp->if_softc; - struct ieee80211com *ic = ifp->if_l2com; - struct ifreq *ifr = (struct ifreq *) data; - int error = 0, startall = 0; + struct rt2661_softc *sc = ic->ic_softc; + int startall = 0; - switch (cmd) { - case SIOCSIFFLAGS: - RAL_LOCK(sc); - if (ifp->if_flags & IFF_UP) { - if ((ifp->if_drv_flags & IFF_DRV_RUNNING) == 0) { - rt2661_init_locked(sc); - startall = 1; - } else - rt2661_update_promisc(ic); - } else { - if (ifp->if_drv_flags & IFF_DRV_RUNNING) - rt2661_stop_locked(sc); - } - RAL_UNLOCK(sc); - if (startall) - ieee80211_start_all(ic); - break; - case SIOCGIFMEDIA: - error = ifmedia_ioctl(ifp, ifr, &ic->ic_media, cmd); - break; - case SIOCGIFADDR: - error = ether_ioctl(ifp, cmd, data); - break; - default: - error = EINVAL; - break; - } - return error; + RAL_LOCK(sc); + if (ic->ic_nrunning > 0) { + if ((sc->sc_flags & RAL_RUNNING) == 0) { + rt2661_init_locked(sc); + startall = 1; + } else + rt2661_update_promisc(ic); + } else if (sc->sc_flags & RAL_RUNNING) + rt2661_stop_locked(sc); + RAL_UNLOCK(sc); + if (startall) + ieee80211_start_all(ic); } static void @@ -1879,8 +1827,7 @@ rt2661_select_antenna(struct rt2661_softc *sc) static void rt2661_enable_mrr(struct rt2661_softc *sc) { - struct ifnet *ifp = sc->sc_ifp; - struct ieee80211com *ic = ifp->if_l2com; + struct ieee80211com *ic = &sc->sc_ic; uint32_t tmp; tmp = RAL_READ(sc, RT2661_TXRX_CSR4); @@ -1896,8 +1843,7 @@ rt2661_enable_mrr(struct rt2661_softc *sc) static void rt2661_set_txpreamble(struct rt2661_softc *sc) { - struct ifnet *ifp = sc->sc_ifp; - struct ieee80211com *ic = ifp->if_l2com; + struct ieee80211com *ic = &sc->sc_ic; uint32_t tmp; tmp = RAL_READ(sc, RT2661_TXRX_CSR4); @@ -1914,8 +1860,7 @@ rt2661_set_basicrates(struct rt2661_softc *sc, const struct ieee80211_rateset *rs) { #define RV(r) ((r) & IEEE80211_RATE_VAL) - struct ifnet *ifp = sc->sc_ifp; - struct ieee80211com *ic = ifp->if_l2com; + struct ieee80211com *ic = &sc->sc_ic; uint32_t mask = 0; uint8_t rate; int i; @@ -1984,8 +1929,7 @@ rt2661_select_band(struct rt2661_softc *sc, struct ieee80211_channel *c) static void rt2661_set_chan(struct rt2661_softc *sc, struct ieee80211_channel *c) { - struct ifnet *ifp = sc->sc_ifp; - struct ieee80211com *ic = ifp->if_l2com; + struct ieee80211com *ic = &sc->sc_ic; const struct rfprog *rfprog; uint8_t bbp3, bbp94 = RT2661_BBPR94_DEFAULT; int8_t power; @@ -2088,13 +2032,13 @@ rt2661_update_promisc(struct ieee80211com *ic) tmp = RAL_READ(sc, RT2661_TXRX_CSR0); tmp &= ~RT2661_DROP_NOT_TO_ME; - if (!(ic->ic_ifp->if_flags & IFF_PROMISC)) + if (ic->ic_promisc == 0) tmp |= RT2661_DROP_NOT_TO_ME; RAL_WRITE(sc, RT2661_TXRX_CSR0, tmp); DPRINTF(sc, "%s promiscuous mode\n", - (ic->ic_ifp->if_flags & IFF_PROMISC) ? "entering" : "leaving"); + (ic->ic_promisc > 0) ? "entering" : "leaving"); } /* @@ -2103,7 +2047,7 @@ rt2661_update_promisc(struct ieee80211com *ic) static int rt2661_wme_update(struct ieee80211com *ic) { - struct rt2661_softc *sc = ic->ic_ifp->if_softc; + struct rt2661_softc *sc = ic->ic_softc; const struct wmeParams *wmep; wmep = ic->ic_wme.wme_chanParams.cap_wmeParams; @@ -2301,8 +2245,8 @@ static void rt2661_init_locked(struct rt2661_softc *sc) { #define N(a) (sizeof (a) / sizeof ((a)[0])) - struct ifnet *ifp = sc->sc_ifp; - struct ieee80211com *ic = ifp->if_l2com; + struct ieee80211com *ic = &sc->sc_ic; + struct ieee80211vap *vap = TAILQ_FIRST(&ic->ic_vaps); uint32_t tmp, sta[3]; int i, error, ntries; @@ -2311,7 +2255,7 @@ rt2661_init_locked(struct rt2661_softc *sc) if ((sc->sc_flags & RAL_FW_LOADED) == 0) { error = rt2661_load_microcode(sc); if (error != 0) { - if_printf(ifp, + device_printf(sc->sc_dev, "%s: could not load 8051 microcode, error %d\n", __func__, error); return; @@ -2364,7 +2308,7 @@ rt2661_init_locked(struct rt2661_softc *sc) for (i = 0; i < N(rt2661_def_mac); i++) RAL_WRITE(sc, rt2661_def_mac[i].reg, rt2661_def_mac[i].val); - rt2661_set_macaddr(sc, IF_LLADDR(ifp)); + rt2661_set_macaddr(sc, vap ? vap->iv_myaddr : ic->ic_macaddr); /* set host ready */ RAL_WRITE(sc, RT2661_MAC_CSR1, 3); @@ -2403,7 +2347,7 @@ rt2661_init_locked(struct rt2661_softc *sc) if (ic->ic_opmode != IEEE80211_M_HOSTAP && ic->ic_opmode != IEEE80211_M_MBSS) tmp |= RT2661_DROP_TODS; - if (!(ifp->if_flags & IFF_PROMISC)) + if (ic->ic_promisc == 0) tmp |= RT2661_DROP_NOT_TO_ME; } @@ -2425,8 +2369,7 @@ rt2661_init_locked(struct rt2661_softc *sc) /* kick Rx */ RAL_WRITE(sc, RT2661_RX_CNTL_CSR, 1); - ifp->if_drv_flags &= ~IFF_DRV_OACTIVE; - ifp->if_drv_flags |= IFF_DRV_RUNNING; + sc->sc_flags |= RAL_RUNNING; callout_reset(&sc->watchdog_ch, hz, rt2661_watchdog, sc); #undef N @@ -2436,23 +2379,21 @@ static void rt2661_init(void *priv) { struct rt2661_softc *sc = priv; - struct ifnet *ifp = sc->sc_ifp; - struct ieee80211com *ic = ifp->if_l2com; + struct ieee80211com *ic = &sc->sc_ic; RAL_LOCK(sc); rt2661_init_locked(sc); RAL_UNLOCK(sc); - if (ifp->if_drv_flags & IFF_DRV_RUNNING) + if (sc->sc_flags & RAL_RUNNING) ieee80211_start_all(ic); /* start all vap's */ } void rt2661_stop_locked(struct rt2661_softc *sc) { - struct ifnet *ifp = sc->sc_ifp; - uint32_t tmp; volatile int *flags = &sc->sc_flags; + uint32_t tmp; while (*flags & RAL_INPUT_RUNNING) msleep(sc, &sc->sc_mtx, 0, "ralrunning", hz/10); @@ -2460,8 +2401,8 @@ rt2661_stop_locked(struct rt2661_softc *sc) callout_stop(&sc->watchdog_ch); sc->sc_tx_timer = 0; - if (ifp->if_drv_flags & IFF_DRV_RUNNING) { - ifp->if_drv_flags &= ~(IFF_DRV_RUNNING | IFF_DRV_OACTIVE); + if (sc->sc_flags & RAL_RUNNING) { + sc->sc_flags &= ~RAL_RUNNING; /* abort Tx (for all 5 Tx rings) */ RAL_WRITE(sc, RT2661_TX_CNTL_CSR, 0x1f << 16); @@ -2505,7 +2446,6 @@ rt2661_stop(void *priv) static int rt2661_load_microcode(struct rt2661_softc *sc) { - struct ifnet *ifp = sc->sc_ifp; const struct firmware *fp; const char *imagename; int ntries, error; @@ -2517,7 +2457,7 @@ rt2661_load_microcode(struct rt2661_softc *sc) case 0x0302: imagename = "rt2561fw"; break; case 0x0401: imagename = "rt2661fw"; break; default: - if_printf(ifp, "%s: unexpected pci device id 0x%x, " + device_printf(sc->sc_dev, "%s: unexpected pci device id 0x%x, " "don't know how to retrieve firmware\n", __func__, sc->sc_id); return EINVAL; @@ -2526,7 +2466,8 @@ rt2661_load_microcode(struct rt2661_softc *sc) fp = firmware_get(imagename); RAL_LOCK(sc); if (fp == NULL) { - if_printf(ifp, "%s: unable to retrieve firmware image %s\n", + device_printf(sc->sc_dev, + "%s: unable to retrieve firmware image %s\n", __func__, imagename); return EINVAL; } @@ -2557,8 +2498,8 @@ rt2661_load_microcode(struct rt2661_softc *sc) DELAY(100); } if (ntries == 500) { - if_printf(ifp, "%s: timeout waiting for MCU to initialize\n", - __func__); + device_printf(sc->sc_dev, + "%s: timeout waiting for MCU to initialize\n", __func__); error = EIO; } else error = 0; @@ -2726,8 +2667,7 @@ rt2661_prepare_beacon(struct rt2661_softc *sc, struct ieee80211vap *vap) static void rt2661_enable_tsf_sync(struct rt2661_softc *sc) { - struct ifnet *ifp = sc->sc_ifp; - struct ieee80211com *ic = ifp->if_l2com; + struct ieee80211com *ic = &sc->sc_ic; struct ieee80211vap *vap = TAILQ_FIRST(&ic->ic_vaps); uint32_t tmp; @@ -2811,21 +2751,19 @@ rt2661_get_rssi(struct rt2661_softc *sc, uint8_t raw) static void rt2661_scan_start(struct ieee80211com *ic) { - struct ifnet *ifp = ic->ic_ifp; - struct rt2661_softc *sc = ifp->if_softc; + struct rt2661_softc *sc = ic->ic_softc; uint32_t tmp; /* abort TSF synchronization */ tmp = RAL_READ(sc, RT2661_TXRX_CSR9); RAL_WRITE(sc, RT2661_TXRX_CSR9, tmp & ~0xffffff); - rt2661_set_bssid(sc, ifp->if_broadcastaddr); + rt2661_set_bssid(sc, ieee80211broadcastaddr); } static void rt2661_scan_end(struct ieee80211com *ic) { - struct ifnet *ifp = ic->ic_ifp; - struct rt2661_softc *sc = ifp->if_softc; + struct rt2661_softc *sc = ic->ic_softc; struct ieee80211vap *vap = TAILQ_FIRST(&ic->ic_vaps); rt2661_enable_tsf_sync(sc); @@ -2836,8 +2774,7 @@ rt2661_scan_end(struct ieee80211com *ic) static void rt2661_set_channel(struct ieee80211com *ic) { - struct ifnet *ifp = ic->ic_ifp; - struct rt2661_softc *sc = ifp->if_softc; + struct rt2661_softc *sc = ic->ic_softc; RAL_LOCK(sc); rt2661_set_chan(sc, ic->ic_curchan); diff --git a/sys/dev/ral/rt2661var.h b/sys/dev/ral/rt2661var.h index 9927d138fa71..7ea16f623d57 100644 --- a/sys/dev/ral/rt2661var.h +++ b/sys/dev/ral/rt2661var.h @@ -97,13 +97,13 @@ struct rt2661_vap { #define RT2661_VAP(vap) ((struct rt2661_vap *)(vap)) struct rt2661_softc { - struct ifnet *sc_ifp; + struct ieee80211com sc_ic; + struct mtx sc_mtx; + struct mbufq sc_snd; device_t sc_dev; bus_space_tag_t sc_st; bus_space_handle_t sc_sh; - struct mtx sc_mtx; - struct callout watchdog_ch; int sc_tx_timer; @@ -117,6 +117,7 @@ struct rt2661_softc { int sc_flags; #define RAL_FW_LOADED 0x1 #define RAL_INPUT_RUNNING 0x2 +#define RAL_RUNNING 0x4 int sc_id; struct ieee80211_channel *sc_curchan; diff --git a/sys/dev/ral/rt2860.c b/sys/dev/ral/rt2860.c index 782fa1f9780b..b3c737d67c66 100644 --- a/sys/dev/ral/rt2860.c +++ b/sys/dev/ral/rt2860.c @@ -122,10 +122,10 @@ static int rt2860_raw_xmit(struct ieee80211_node *, struct mbuf *, static int rt2860_tx_raw(struct rt2860_softc *, struct mbuf *, struct ieee80211_node *, const struct ieee80211_bpf_params *params); -static void rt2860_start(struct ifnet *); -static void rt2860_start_locked(struct ifnet *); +static int rt2860_transmit(struct ieee80211com *, struct mbuf *); +static void rt2860_start(struct rt2860_softc *); static void rt2860_watchdog(void *); -static int rt2860_ioctl(struct ifnet *, u_long, caddr_t); +static void rt2860_parent(struct ieee80211com *); static void rt2860_mcu_bbp_write(struct rt2860_softc *, uint8_t, uint8_t); static uint8_t rt2860_mcu_bbp_read(struct rt2860_softc *, uint8_t); static void rt2860_rf_write(struct rt2860_softc *, uint8_t, uint32_t); @@ -156,7 +156,7 @@ static void rt2860_set_bssid(struct rt2860_softc *, const uint8_t *); static void rt2860_set_macaddr(struct rt2860_softc *, const uint8_t *); static void rt2860_update_promisc(struct ieee80211com *); static void rt2860_updateslot(struct ieee80211com *); -static void rt2860_updateprot(struct ifnet *); +static void rt2860_updateprot(struct rt2860_softc *); static int rt2860_updateedca(struct ieee80211com *); #ifdef HW_CRYPTO static int rt2860_set_key(struct ieee80211com *, struct ieee80211_node *, @@ -230,27 +230,19 @@ int rt2860_attach(device_t dev, int id) { struct rt2860_softc *sc = device_get_softc(dev); - struct ieee80211com *ic; - struct ifnet *ifp; + struct ieee80211com *ic = &sc->sc_ic; uint32_t tmp; int error, ntries, qid; uint8_t bands; - uint8_t macaddr[IEEE80211_ADDR_LEN]; sc->sc_dev = dev; sc->sc_debug = 0; - ifp = sc->sc_ifp = if_alloc(IFT_IEEE80211); - if (ifp == NULL) { - device_printf(sc->sc_dev, "can not if_alloc()\n"); - return ENOMEM; - } - ic = ifp->if_l2com; - mtx_init(&sc->sc_mtx, device_get_nameunit(dev), MTX_NETWORK_LOCK, MTX_DEF | MTX_RECURSE); callout_init_mtx(&sc->watchdog_ch, &sc->sc_mtx, 0); + mbufq_init(&sc->sc_snd, ifqmaxlen); /* wait for NIC to initialize */ for (ntries = 0; ntries < 100; ntries++) { @@ -273,11 +265,11 @@ rt2860_attach(device_t dev, int id) sc->sc_flags |= RT2860_ADVANCED_PS; /* retrieve RF rev. no and various other things from EEPROM */ - rt2860_read_eeprom(sc, macaddr); + rt2860_read_eeprom(sc, ic->ic_macaddr); device_printf(sc->sc_dev, "MAC/BBP RT%X (rev 0x%04X), " "RF %s (MIMO %dT%dR), address %6D\n", sc->mac_ver, sc->mac_rev, rt2860_get_rf(sc->rf_rev), - sc->ntxchains, sc->nrxchains, macaddr, ":"); + sc->ntxchains, sc->nrxchains, ic->ic_macaddr, ":"); /* * Allocate Tx (4 EDCAs + HCCA + Mgt) and Rx rings. @@ -304,17 +296,6 @@ rt2860_attach(device_t dev, int id) sc->mgtqid = (sc->mac_ver == 0x2860 && sc->mac_rev == 0x0100) ? WME_AC_VO : 5; - ifp->if_softc = sc; - if_initname(ifp, device_get_name(dev), device_get_unit(dev)); - ifp->if_flags = IFF_BROADCAST | IFF_SIMPLEX | IFF_MULTICAST; - ifp->if_init = rt2860_init; - ifp->if_ioctl = rt2860_ioctl; - ifp->if_start = rt2860_start; - IFQ_SET_MAXLEN(&ifp->if_snd, ifqmaxlen); - ifp->if_snd.ifq_drv_maxlen = ifqmaxlen; - IFQ_SET_READY(&ifp->if_snd); - - ic->ic_ifp = ifp; ic->ic_softc = sc; ic->ic_name = device_get_nameunit(dev); ic->ic_opmode = IEEE80211_M_STA; @@ -345,7 +326,7 @@ rt2860_attach(device_t dev, int id) setbit(&bands, IEEE80211_MODE_11A); ieee80211_init_channels(ic, NULL, &bands); - ieee80211_ifattach(ic, macaddr); + ieee80211_ifattach(ic); ic->ic_wme.wme_update = rt2860_updateedca; ic->ic_scan_start = rt2860_scan_start; @@ -357,7 +338,8 @@ rt2860_attach(device_t dev, int id) sc->sc_node_free = ic->ic_node_free; ic->ic_node_free = rt2860_node_free; ic->ic_newassoc = rt2860_newassoc; - + ic->ic_transmit = rt2860_transmit; + ic->ic_parent = rt2860_parent; ic->ic_vap_create = rt2860_vap_create; ic->ic_vap_delete = rt2860_vap_delete; @@ -381,7 +363,6 @@ fail3: rt2860_free_rx_ring(sc, &sc->rxq); fail2: while (--qid >= 0) rt2860_free_tx_ring(sc, &sc->txq[qid]); fail1: mtx_destroy(&sc->sc_mtx); - if_free(ifp); return error; } @@ -389,8 +370,7 @@ int rt2860_detach(void *xsc) { struct rt2860_softc *sc = xsc; - struct ifnet *ifp = sc->sc_ifp; - struct ieee80211com *ic = ifp->if_l2com; + struct ieee80211com *ic = &sc->sc_ic; int qid; RAL_LOCK(sc); @@ -398,14 +378,12 @@ rt2860_detach(void *xsc) RAL_UNLOCK(sc); ieee80211_ifdetach(ic); - + mbufq_drain(&sc->sc_snd); for (qid = 0; qid < 6; qid++) rt2860_free_tx_ring(sc, &sc->txq[qid]); rt2860_free_rx_ring(sc, &sc->rxq); rt2860_free_tx_pool(sc); - if_free(ifp); - mtx_destroy(&sc->sc_mtx); return 0; @@ -431,9 +409,8 @@ void rt2860_resume(void *xsc) { struct rt2860_softc *sc = xsc; - struct ifnet *ifp = sc->sc_ifp; - if (ifp->if_flags & IFF_UP) + if (sc->sc_ic.ic_nrunning > 0) rt2860_init(sc); } @@ -443,7 +420,7 @@ rt2860_vap_create(struct ieee80211com *ic, const char name[IFNAMSIZ], int unit, const uint8_t bssid[IEEE80211_ADDR_LEN], const uint8_t mac[IEEE80211_ADDR_LEN]) { - struct ifnet *ifp = ic->ic_ifp; + struct rt2860_softc *sc = ic->ic_softc; struct rt2860_vap *rvp; struct ieee80211vap *vap; @@ -456,7 +433,7 @@ rt2860_vap_create(struct ieee80211com *ic, const char name[IFNAMSIZ], int unit, case IEEE80211_M_MBSS: /* XXXRP: TBD */ if (!TAILQ_EMPTY(&ic->ic_vaps)) { - if_printf(ifp, "only 1 vap supported\n"); + device_printf(sc->sc_dev, "only 1 vap supported\n"); return NULL; } if (opmode == IEEE80211_M_STA) @@ -465,7 +442,8 @@ rt2860_vap_create(struct ieee80211com *ic, const char name[IFNAMSIZ], int unit, case IEEE80211_M_WDS: if (TAILQ_EMPTY(&ic->ic_vaps) || ic->ic_opmode != IEEE80211_M_HOSTAP) { - if_printf(ifp, "wds only supported in ap mode\n"); + device_printf(sc->sc_dev, + "wds only supported in ap mode\n"); return NULL; } /* @@ -476,14 +454,12 @@ rt2860_vap_create(struct ieee80211com *ic, const char name[IFNAMSIZ], int unit, flags &= ~IEEE80211_CLONE_BSSID; break; default: - if_printf(ifp, "unknown opmode %d\n", opmode); + device_printf(sc->sc_dev, "unknown opmode %d\n", opmode); return NULL; } - rvp = malloc(sizeof(struct rt2860_vap), M_80211_VAP, M_NOWAIT | M_ZERO); - if (rvp == NULL) - return NULL; + rvp = malloc(sizeof(struct rt2860_vap), M_80211_VAP, M_WAITOK | M_ZERO); vap = &rvp->ral_vap; - ieee80211_vap_setup(ic, vap, name, unit, opmode, flags, bssid, mac); + ieee80211_vap_setup(ic, vap, name, unit, opmode, flags, bssid); /* override state transition machine */ rvp->ral_newstate = vap->iv_newstate; @@ -497,7 +473,8 @@ rt2860_vap_create(struct ieee80211com *ic, const char name[IFNAMSIZ], int unit, ieee80211_ratectl_init(vap); /* complete setup */ - ieee80211_vap_attach(vap, ieee80211_media_change, ieee80211_media_status); + ieee80211_vap_attach(vap, ieee80211_media_change, + ieee80211_media_status, mac); if (TAILQ_FIRST(&ic->ic_vaps) == vap) ic->ic_opmode = opmode; return vap; @@ -829,7 +806,7 @@ rt2860_free_rx_ring(struct rt2860_softc *sc, struct rt2860_rx_ring *ring) static void rt2860_updatestats(struct rt2860_softc *sc) { - struct ieee80211com *ic = sc->sc_ifp->if_l2com; + struct ieee80211com *ic = &sc->sc_ic; /* * In IBSS or HostAP modes (when the hardware sends beacons), the @@ -856,7 +833,7 @@ static void rt2860_newassoc(struct ieee80211_node *ni, int isnew) { struct ieee80211com *ic = ni->ni_ic; - struct rt2860_softc *sc = ic->ic_ifp->if_softc; + struct rt2860_softc *sc = ic->ic_softc; uint8_t wcid; wcid = IEEE80211_AID(ni->ni_associd); @@ -875,7 +852,7 @@ static void rt2860_node_free(struct ieee80211_node *ni) { struct ieee80211com *ic = ni->ni_ic; - struct rt2860_softc *sc = ic->ic_ifp->if_softc; + struct rt2860_softc *sc = ic->ic_softc; uint8_t wcid; if (ni->ni_associd != 0) { @@ -923,7 +900,7 @@ rt2860_newstate(struct ieee80211vap *vap, enum ieee80211_state nstate, int arg) { struct rt2860_vap *rvp = RT2860_VAP(vap); struct ieee80211com *ic = vap->iv_ic; - struct rt2860_softc *sc = ic->ic_ifp->if_softc; + struct rt2860_softc *sc = ic->ic_softc; uint32_t tmp; int error; @@ -1101,7 +1078,6 @@ rt2860_intr_coherent(struct rt2860_softc *sc) static void rt2860_drain_stats_fifo(struct rt2860_softc *sc) { - struct ifnet *ifp = sc->sc_ifp; struct ieee80211_node *ni; uint32_t stat; int retrycnt; @@ -1137,7 +1113,8 @@ rt2860_drain_stats_fifo(struct rt2860_softc *sc) } else { ieee80211_ratectl_tx_complete(ni->ni_vap, ni, IEEE80211_RATECTL_TX_FAILURE, &retrycnt, NULL); - if_inc_counter(ifp, IFCOUNTER_OERRORS, 1); + if_inc_counter(ni->ni_vap->iv_ifp, + IFCOUNTER_OERRORS, 1); } } } @@ -1145,7 +1122,6 @@ rt2860_drain_stats_fifo(struct rt2860_softc *sc) static void rt2860_tx_intr(struct rt2860_softc *sc, int qid) { - struct ifnet *ifp = sc->sc_ifp; struct rt2860_tx_ring *ring = &sc->txq[qid]; uint32_t hw; @@ -1163,15 +1139,11 @@ rt2860_tx_intr(struct rt2860_softc *sc, int qid) ieee80211_process_callback(data->ni, data->m, 0); } - m_freem(data->m); - ieee80211_free_node(data->ni); - data->m = NULL; + ieee80211_tx_complete(data->ni, data->m, 0); data->ni = NULL; - + data->m = NULL; SLIST_INSERT_HEAD(&sc->data_pool, data, next); ring->data[ring->next] = NULL; - - if_inc_counter(ifp, IFCOUNTER_OPACKETS, 1); } ring->queued--; ring->next = (ring->next + 1) % RT2860_TX_RING_COUNT; @@ -1180,8 +1152,7 @@ rt2860_tx_intr(struct rt2860_softc *sc, int qid) sc->sc_tx_timer = 0; if (ring->queued < RT2860_TX_RING_COUNT) sc->qfullmsk &= ~(1 << qid); - ifp->if_drv_flags &= ~IFF_DRV_OACTIVE; - rt2860_start_locked(ifp); + rt2860_start(sc); } /* @@ -1206,8 +1177,7 @@ static void rt2860_rx_intr(struct rt2860_softc *sc) { struct rt2860_rx_radiotap_header *tap; - struct ifnet *ifp = sc->sc_ifp; - struct ieee80211com *ic = ifp->if_l2com; + struct ieee80211com *ic = &sc->sc_ic; struct ieee80211_frame *wh; struct ieee80211_node *ni; struct mbuf *m, *m1; @@ -1234,7 +1204,7 @@ rt2860_rx_intr(struct rt2860_softc *sc) if (__predict_false(rxd->flags & htole32(RT2860_RX_CRCERR | RT2860_RX_ICVERR))) { - if_inc_counter(ifp, IFCOUNTER_IERRORS, 1); + counter_u64_add(ic->ic_ierrors, 1); goto skip; } @@ -1243,14 +1213,14 @@ rt2860_rx_intr(struct rt2860_softc *sc) /* report MIC failures to net80211 for TKIP */ ic->ic_stats.is_rx_locmicfail++; ieee80211_michael_mic_failure(ic, 0/* XXX */); - if_inc_counter(ifp, IFCOUNTER_IERRORS, 1); + counter_u64_add(ic->ic_ierrors, 1); goto skip; } #endif m1 = m_getcl(M_NOWAIT, MT_DATA, M_PKTHDR); if (__predict_false(m1 == NULL)) { - if_inc_counter(ifp, IFCOUNTER_IERRORS, 1); + counter_u64_add(ic->ic_ierrors, 1); goto skip; } @@ -1274,7 +1244,7 @@ rt2860_rx_intr(struct rt2860_softc *sc) } /* physical address may have changed */ rxd->sdp0 = htole32(physaddr); - if_inc_counter(ifp, IFCOUNTER_IERRORS, 1); + counter_u64_add(ic->ic_ierrors, 1); goto skip; } @@ -1289,7 +1259,6 @@ rt2860_rx_intr(struct rt2860_softc *sc) rxwi = mtod(m, struct rt2860_rxwi *); /* finalize mbuf */ - m->m_pkthdr.rcvif = ifp; m->m_data = (caddr_t)(rxwi + 1); m->m_pkthdr.len = m->m_len = le16toh(rxwi->len) & 0xfff; @@ -1399,7 +1368,7 @@ rt2860_tbtt_intr(struct rt2860_softc *sc) #endif /* check if protection mode has changed */ if ((sc->sc_ic_flags ^ ic->ic_flags) & IEEE80211_F_USEPROT) { - rt2860_updateprot(ic); + rt2860_updateprot(sc); sc->sc_ic_flags = ic->ic_flags; } #endif @@ -1408,7 +1377,7 @@ rt2860_tbtt_intr(struct rt2860_softc *sc) static void rt2860_gp_intr(struct rt2860_softc *sc) { - struct ieee80211com *ic = sc->sc_ifp->if_l2com; + struct ieee80211com *ic = &sc->sc_ic; struct ieee80211vap *vap = TAILQ_FIRST(&ic->ic_vaps); DPRINTFN(2, ("GP timeout state=%d\n", vap->iv_state)); @@ -1480,8 +1449,7 @@ rt2860_intr(void *arg) static int rt2860_tx(struct rt2860_softc *sc, struct mbuf *m, struct ieee80211_node *ni) { - struct ifnet *ifp = sc->sc_ifp; - struct ieee80211com *ic = ifp->if_l2com; + struct ieee80211com *ic = &sc->sc_ic; struct ieee80211vap *vap = ni->ni_vap; struct rt2860_tx_ring *ring; struct rt2860_tx_data *data; @@ -1725,14 +1693,13 @@ rt2860_raw_xmit(struct ieee80211_node *ni, struct mbuf *m, const struct ieee80211_bpf_params *params) { struct ieee80211com *ic = ni->ni_ic; - struct ifnet *ifp = ic->ic_ifp; - struct rt2860_softc *sc = ifp->if_softc; + struct rt2860_softc *sc = ic->ic_softc; int error; RAL_LOCK(sc); /* prevent management frames from being sent if we're not ready */ - if (!(ifp->if_drv_flags & IFF_DRV_RUNNING)) { + if (!(sc->sc_flags & RT2860_RUNNNING)) { RAL_UNLOCK(sc); m_freem(m); ieee80211_free_node(ni); @@ -1754,7 +1721,6 @@ rt2860_raw_xmit(struct ieee80211_node *ni, struct mbuf *m, if (error != 0) { /* NB: m is reclaimed on tx failure */ ieee80211_free_node(ni); - if_inc_counter(ifp, IFCOUNTER_OERRORS, 1); } sc->sc_tx_timer = 5; RAL_UNLOCK(sc); @@ -1765,8 +1731,7 @@ static int rt2860_tx_raw(struct rt2860_softc *sc, struct mbuf *m, struct ieee80211_node *ni, const struct ieee80211_bpf_params *params) { - struct ifnet *ifp = sc->sc_ifp; - struct ieee80211com *ic = ifp->if_l2com; + struct ieee80211com *ic = &sc->sc_ic; struct ieee80211vap *vap = ni->ni_vap; struct rt2860_tx_ring *ring; struct rt2860_tx_data *data; @@ -1973,41 +1938,46 @@ rt2860_tx_raw(struct rt2860_softc *sc, struct mbuf *m, return 0; } -static void -rt2860_start(struct ifnet *ifp) +static int +rt2860_transmit(struct ieee80211com *ic, struct mbuf *m) { - struct rt2860_softc *sc = ifp->if_softc; + struct rt2860_softc *sc = ic->ic_softc; + int error; RAL_LOCK(sc); - rt2860_start_locked(ifp); + if ((sc->sc_flags & RT2860_RUNNNING) == 0) { + RAL_UNLOCK(sc); + return (ENXIO); + } + error = mbufq_enqueue(&sc->sc_snd, m); + if (error) { + RAL_UNLOCK(sc); + return (error); + } + rt2860_start(sc); RAL_UNLOCK(sc); + + return (0); } static void -rt2860_start_locked(struct ifnet *ifp) +rt2860_start(struct rt2860_softc *sc) { - struct rt2860_softc *sc = ifp->if_softc; struct ieee80211_node *ni; struct mbuf *m; RAL_LOCK_ASSERT(sc); - if ((ifp->if_drv_flags & IFF_DRV_RUNNING) == 0 || - (ifp->if_drv_flags & IFF_DRV_OACTIVE)) + if ((sc->sc_flags & RT2860_RUNNNING) == 0) return; - for (;;) { - if (SLIST_EMPTY(&sc->data_pool) || sc->qfullmsk != 0) { - ifp->if_drv_flags |= IFF_DRV_OACTIVE; - break; - } - IFQ_DRV_DEQUEUE(&ifp->if_snd, m); - if (m == NULL) - break; + while (!SLIST_EMPTY(&sc->data_pool) && sc->qfullmsk == 0 && + (m = mbufq_dequeue(&sc->sc_snd)) != NULL) { ni = (struct ieee80211_node *)m->m_pkthdr.rcvif; if (rt2860_tx(sc, m, ni) != 0) { + if_inc_counter(ni->ni_vap->iv_ifp, + IFCOUNTER_OERRORS, 1); ieee80211_free_node(ni); - if_inc_counter(ifp, IFCOUNTER_OERRORS, 1); continue; } sc->sc_tx_timer = 5; @@ -2018,61 +1988,42 @@ static void rt2860_watchdog(void *arg) { struct rt2860_softc *sc = arg; - struct ifnet *ifp = sc->sc_ifp; RAL_LOCK_ASSERT(sc); - KASSERT(ifp->if_drv_flags & IFF_DRV_RUNNING, ("not running")); + KASSERT(sc->sc_flags & RT2860_RUNNNING, ("not running")); if (sc->sc_invalid) /* card ejected */ return; if (sc->sc_tx_timer > 0 && --sc->sc_tx_timer == 0) { - if_printf(ifp, "device timeout\n"); + device_printf(sc->sc_dev, "device timeout\n"); rt2860_stop_locked(sc); rt2860_init_locked(sc); - if_inc_counter(ifp, IFCOUNTER_OERRORS, 1); + counter_u64_add(sc->sc_ic.ic_oerrors, 1); return; } callout_reset(&sc->watchdog_ch, hz, rt2860_watchdog, sc); } -static int -rt2860_ioctl(struct ifnet *ifp, u_long cmd, caddr_t data) +static void +rt2860_parent(struct ieee80211com *ic) { - struct rt2860_softc *sc = ifp->if_softc; - struct ieee80211com *ic = ifp->if_l2com; - struct ifreq *ifr = (struct ifreq *)data; - int error = 0, startall = 0; + struct rt2860_softc *sc = ic->ic_softc; + int startall = 0; - switch (cmd) { - case SIOCSIFFLAGS: - RAL_LOCK(sc); - if (ifp->if_flags & IFF_UP) { - if (!(ifp->if_drv_flags & IFF_DRV_RUNNING)) { - rt2860_init_locked(sc); - startall = 1; - } else - rt2860_update_promisc(ic); - } else { - if (ifp->if_drv_flags & IFF_DRV_RUNNING) - rt2860_stop_locked(sc); - } - RAL_UNLOCK(sc); - if (startall) - ieee80211_start_all(ic); - break; - case SIOCGIFMEDIA: - error = ifmedia_ioctl(ifp, ifr, &ic->ic_media, cmd); - break; - case SIOCSIFADDR: - error = ether_ioctl(ifp, cmd, data); - break; - default: - error = EINVAL; - break; - } - return error; + RAL_LOCK(sc); + if (ic->ic_nrunning> 0) { + if (!(sc->sc_flags & RT2860_RUNNNING)) { + rt2860_init_locked(sc); + startall = 1; + } else + rt2860_update_promisc(ic); + } else if (sc->sc_flags & RT2860_RUNNNING) + rt2860_stop_locked(sc); + RAL_UNLOCK(sc); + if (startall) + ieee80211_start_all(ic); } /* @@ -2295,8 +2246,7 @@ rt2860_enable_mrr(struct rt2860_softc *sc) static void rt2860_set_txpreamble(struct rt2860_softc *sc) { - struct ifnet *ifp = sc->sc_ifp; - struct ieee80211com *ic = ifp->if_l2com; + struct ieee80211com *ic = &sc->sc_ic; uint32_t tmp; tmp = RAL_READ(sc, RT2860_AUTO_RSP_CFG); @@ -2311,8 +2261,7 @@ rt2860_set_basicrates(struct rt2860_softc *sc, const struct ieee80211_rateset *rs) { #define RV(r) ((r) & IEEE80211_RATE_VAL) - struct ifnet *ifp = sc->sc_ifp; - struct ieee80211com *ic = ifp->if_l2com; + struct ieee80211com *ic = &sc->sc_ic; uint32_t mask = 0; uint8_t rate; int i; @@ -2333,8 +2282,7 @@ rt2860_set_basicrates(struct rt2860_softc *sc, static void rt2860_scan_start(struct ieee80211com *ic) { - struct ifnet *ifp = ic->ic_ifp; - struct rt2860_softc *sc = ifp->if_softc; + struct rt2860_softc *sc = ic->ic_softc; uint32_t tmp; tmp = RAL_READ(sc, RT2860_BCN_TIME_CFG); @@ -2347,8 +2295,7 @@ rt2860_scan_start(struct ieee80211com *ic) static void rt2860_scan_end(struct ieee80211com *ic) { - struct ifnet *ifp = ic->ic_ifp; - struct rt2860_softc *sc = ifp->if_softc; + struct rt2860_softc *sc = ic->ic_softc; struct ieee80211vap *vap = TAILQ_FIRST(&ic->ic_vaps); if (vap->iv_state == IEEE80211_S_RUN) { @@ -2360,8 +2307,7 @@ rt2860_scan_end(struct ieee80211com *ic) static void rt2860_set_channel(struct ieee80211com *ic) { - struct ifnet *ifp = ic->ic_ifp; - struct rt2860_softc *sc = ifp->if_softc; + struct rt2860_softc *sc = ic->ic_softc; RAL_LOCK(sc); rt2860_switch_chan(sc, ic->ic_curchan); @@ -3113,10 +3059,9 @@ rt2860_updateslot(struct ieee80211com *ic) } static void -rt2860_updateprot(struct ifnet *ifp) +rt2860_updateprot(struct rt2860_softc *sc) { - struct rt2860_softc *sc = ifp->if_softc; - struct ieee80211com *ic = ifp->if_l2com; + struct ieee80211com *ic = &sc->sc_ic; uint32_t tmp; tmp = RT2860_RTSTH_EN | RT2860_PROT_NAV_SHORT | RT2860_TXOP_ALLOW_ALL; @@ -3145,7 +3090,7 @@ rt2860_update_promisc(struct ieee80211com *ic) tmp = RAL_READ(sc, RT2860_RX_FILTR_CFG); tmp &= ~RT2860_DROP_NOT_MYBSS; - if (!(ic->ic_ifp->if_flags & IFF_PROMISC)) + if (ic->ic_promisc == 0) tmp |= RT2860_DROP_NOT_MYBSS; RAL_WRITE(sc, RT2860_RX_FILTR_CFG, tmp); } @@ -3153,7 +3098,7 @@ rt2860_update_promisc(struct ieee80211com *ic) static int rt2860_updateedca(struct ieee80211com *ic) { - struct rt2860_softc *sc = ic->ic_ifp->if_softc; + struct rt2860_softc *sc = ic->ic_softc; const struct wmeParams *wmep; int aci; @@ -3325,8 +3270,7 @@ rt2860_delete_key(struct ieee80211com *ic, struct ieee80211_node *ni, static int8_t rt2860_rssi2dbm(struct rt2860_softc *sc, uint8_t rssi, uint8_t rxchain) { - struct ifnet *ifp = sc->sc_ifp; - struct ieee80211com *ic = ifp->if_l2com; + struct ieee80211com *ic = &sc->sc_ic; struct ieee80211_channel *c = ic->ic_curchan; int delta; @@ -3801,8 +3745,7 @@ rt5390_bbp_init(struct rt2860_softc *sc) static int rt2860_txrx_enable(struct rt2860_softc *sc) { - struct ifnet *ifp = sc->sc_ifp; - struct ieee80211com *ic = ifp->if_l2com; + struct ieee80211com *ic = &sc->sc_ic; uint32_t tmp; int ntries; @@ -3848,22 +3791,21 @@ static void rt2860_init(void *arg) { struct rt2860_softc *sc = arg; - struct ifnet *ifp = sc->sc_ifp; - struct ieee80211com *ic = ifp->if_l2com; + struct ieee80211com *ic = &sc->sc_ic; RAL_LOCK(sc); rt2860_init_locked(sc); RAL_UNLOCK(sc); - if (ifp->if_drv_flags & IFF_DRV_RUNNING) + if (sc->sc_flags & RT2860_RUNNNING) ieee80211_start_all(ic); } static void rt2860_init_locked(struct rt2860_softc *sc) { - struct ifnet *ifp = sc->sc_ifp; - struct ieee80211com *ic = ifp->if_l2com; + struct ieee80211com *ic = &sc->sc_ic; + struct ieee80211vap *vap = TAILQ_FIRST(&ic->ic_vaps); uint32_t tmp; uint8_t bbp1, bbp3; int i, qid, ridx, ntries, error; @@ -3899,7 +3841,7 @@ rt2860_init_locked(struct rt2860_softc *sc) return; } - rt2860_set_macaddr(sc, IF_LLADDR(ifp)); + rt2860_set_macaddr(sc, vap ? vap->iv_myaddr : ic->ic_macaddr); /* init Tx power for all Tx rates (from EEPROM) */ for (ridx = 0; ridx < 5; ridx++) { @@ -4096,7 +4038,7 @@ rt2860_init_locked(struct rt2860_softc *sc) RAL_WRITE(sc, RT2860_TX_RTS_CFG, tmp); /* setup initial protection mode */ - rt2860_updateprot(ifp); + rt2860_updateprot(sc); /* turn radio LED on */ rt2860_set_leds(sc, RT2860_LED_RADIO); @@ -4115,8 +4057,7 @@ rt2860_init_locked(struct rt2860_softc *sc) if (sc->sc_flags & RT2860_ADVANCED_PS) rt2860_mcu_cmd(sc, RT2860_MCU_CMD_PSLEVEL, sc->pslevel, 0); - ifp->if_drv_flags &= ~IFF_DRV_OACTIVE; - ifp->if_drv_flags |= IFF_DRV_RUNNING; + sc->sc_flags |= RT2860_RUNNNING; callout_reset(&sc->watchdog_ch, hz, rt2860_watchdog, sc); } @@ -4134,16 +4075,15 @@ rt2860_stop(void *arg) static void rt2860_stop_locked(struct rt2860_softc *sc) { - struct ifnet *ifp = sc->sc_ifp; uint32_t tmp; int qid; - if (ifp->if_drv_flags & IFF_DRV_RUNNING) + if (sc->sc_flags & RT2860_RUNNNING) rt2860_set_leds(sc, 0); /* turn all LEDs off */ callout_stop(&sc->watchdog_ch); sc->sc_tx_timer = 0; - ifp->if_drv_flags &= ~(IFF_DRV_RUNNING | IFF_DRV_OACTIVE); + sc->sc_flags &= ~RT2860_RUNNNING; /* disable interrupts */ RAL_WRITE(sc, RT2860_INT_MASK, 0); @@ -4294,8 +4234,7 @@ rt3090_set_rx_antenna(struct rt2860_softc *sc, int aux) static void rt2860_switch_chan(struct rt2860_softc *sc, struct ieee80211_channel *c) { - struct ifnet *ifp = sc->sc_ifp; - struct ieee80211com *ic = ifp->if_l2com; + struct ieee80211com *ic = &sc->sc_ic; u_int chan, group; chan = ieee80211_chan2ieee(ic, c); @@ -4364,8 +4303,7 @@ rt2860_setup_beacon(struct rt2860_softc *sc, struct ieee80211vap *vap) static void rt2860_enable_tsf_sync(struct rt2860_softc *sc) { - struct ifnet *ifp = sc->sc_ifp; - struct ieee80211com *ic = ifp->if_l2com; + struct ieee80211com *ic = &sc->sc_ic; struct ieee80211vap *vap = TAILQ_FIRST(&ic->ic_vaps); uint32_t tmp; diff --git a/sys/dev/ral/rt2860var.h b/sys/dev/ral/rt2860var.h index 28a3d59b8263..3779e5beb1d1 100644 --- a/sys/dev/ral/rt2860var.h +++ b/sys/dev/ral/rt2860var.h @@ -115,13 +115,13 @@ struct rt2860_vap { #define RT2860_VAP(vap) ((struct rt2860_vap *)(vap)) struct rt2860_softc { - struct ifnet *sc_ifp; + struct ieee80211com sc_ic; + struct mbufq sc_snd; + struct mtx sc_mtx; device_t sc_dev; bus_space_tag_t sc_st; bus_space_handle_t sc_sh; - struct mtx sc_mtx; - struct callout watchdog_ch; int sc_invalid; @@ -139,6 +139,7 @@ struct rt2860_softc { #define RT2860_ENABLED (1 << 0) #define RT2860_ADVANCED_PS (1 << 1) #define RT2860_PCIE (1 << 2) +#define RT2860_RUNNNING (1 << 3) struct ieee80211_node *wcid2ni[RT2860_WCID_MAX]; |
