PERFORCE change 132808 for review
Sam Leffler
sam at FreeBSD.org
Tue Jan 8 12:45:18 PST 2008
http://perforce.freebsd.org/chv.cgi?CH=132808
Change 132808 by sam at sam_ebb on 2008/01/08 20:44:38
blindly convert some legacy drivers: compile-tested only
and likely wrong; need to understand the best way to handle
legacy drivers (e.g. w/ common support in net80211)
Affected files ...
.. //depot/projects/vap/sys/dev/ipw/if_ipw.c#5 edit
.. //depot/projects/vap/sys/dev/ipw/if_ipwvar.h#5 edit
.. //depot/projects/vap/sys/dev/iwi/if_iwi.c#9 edit
.. //depot/projects/vap/sys/dev/iwi/if_iwivar.h#7 edit
.. //depot/projects/vap/sys/dev/ral/if_ralrate.c#3 edit
.. //depot/projects/vap/sys/dev/ral/if_ralrate.h#3 edit
.. //depot/projects/vap/sys/dev/ral/rt2560.c#3 edit
.. //depot/projects/vap/sys/dev/ral/rt2560var.h#3 edit
.. //depot/projects/vap/sys/dev/ral/rt2661.c#3 edit
.. //depot/projects/vap/sys/dev/ral/rt2661var.h#3 edit
.. //depot/projects/vap/sys/dev/usb/if_rum.c#3 edit
.. //depot/projects/vap/sys/dev/usb/if_rumvar.h#3 edit
.. //depot/projects/vap/sys/dev/usb/if_ural.c#5 edit
.. //depot/projects/vap/sys/dev/usb/if_uralvar.h#5 edit
.. //depot/projects/vap/sys/dev/usb/if_zyd.c#3 edit
.. //depot/projects/vap/sys/dev/usb/if_zydreg.h#3 edit
.. //depot/projects/vap/sys/dev/wpi/if_wpi.c#3 edit
.. //depot/projects/vap/sys/dev/wpi/if_wpivar.h#3 edit
Differences ...
==== //depot/projects/vap/sys/dev/ipw/if_ipw.c#5 (text+ko) ====
@@ -107,11 +107,14 @@
{ 0, 0, NULL }
};
+static struct ieee80211vap *ipw_vap_create(struct ieee80211com *,
+ const char name[IFNAMSIZ], int unit, int opmode, int flags,
+ const uint8_t bssid[IEEE80211_ADDR_LEN]);
+static void ipw_vap_delete(struct ieee80211vap *);
static int ipw_dma_alloc(struct ipw_softc *);
static void ipw_release(struct ipw_softc *);
-static int ipw_media_change(struct ifnet *);
static void ipw_media_status(struct ifnet *, struct ifmediareq *);
-static int ipw_newstate(struct ieee80211com *, enum ieee80211_state, int);
+static int ipw_newstate(struct ieee80211vap *, enum ieee80211_state, int);
static uint16_t ipw_read_prom_word(struct ipw_softc *, uint8_t);
static void ipw_rx_cmd_intr(struct ipw_softc *, struct ipw_soft_buf *);
static void ipw_rx_newstate_intr(struct ipw_softc *, struct ipw_soft_buf *);
@@ -163,8 +166,9 @@
static void ipw_scan_start(struct ieee80211com *);
static void ipw_scan_end(struct ieee80211com *);
static void ipw_set_channel(struct ieee80211com *);
-static void ipw_scan_curchan(struct ieee80211com *, unsigned long maxdwell);
-static void ipw_scan_mindwell(struct ieee80211com *);
+static void ipw_scan_curchan(struct ieee80211_scan_state *,
+ unsigned long maxdwell);
+static void ipw_scan_mindwell(struct ieee80211_scan_state *);
static int ipw_probe(device_t);
static int ipw_attach(device_t);
@@ -293,8 +297,6 @@
ic->ic_ifp = ifp;
ic->ic_phytype = IEEE80211_T_DS;
- ic->ic_opmode = IEEE80211_M_STA;
- ic->ic_state = IEEE80211_S_INIT;
/* set device capabilities */
ic->ic_caps = IEEE80211_C_IBSS /* IBSS mode supported */
@@ -333,17 +335,15 @@
sc->flags |= IPW_FLAG_HAS_RADIO_SWITCH;
ieee80211_ifattach(ic);
- /* override state transition machine */
- sc->sc_newstate = ic->ic_newstate;
- ic->ic_newstate = ipw_newstate;
- ieee80211_media_init(ic, ipw_media_change, ipw_media_status);
-
ic->ic_scan_start = ipw_scan_start;
ic->ic_scan_end = ipw_scan_end;
ic->ic_set_channel = ipw_set_channel;
ic->ic_scan_curchan = ipw_scan_curchan;
ic->ic_scan_mindwell = ipw_scan_mindwell;
+ ic->ic_vap_create = ipw_vap_create;
+ ic->ic_vap_delete = ipw_vap_delete;
+
bpfattach2(ifp, DLT_IEEE802_11_RADIO,
sizeof (struct ieee80211_frame) + sizeof (sc->sc_txtap),
&sc->sc_drvbpf);
@@ -359,8 +359,6 @@
/*
* Add a few sysctl knobs.
*/
- sc->dwelltime = 100;
-
SYSCTL_ADD_PROC(device_get_sysctl_ctx(dev),
SYSCTL_CHILDREN(device_get_sysctl_tree(dev)), OID_AUTO, "radio",
CTLTYPE_INT | CTLFLAG_RD, sc, 0, ipw_sysctl_radio, "I",
@@ -371,11 +369,6 @@
CTLTYPE_OPAQUE | CTLFLAG_RD, sc, 0, ipw_sysctl_stats, "S",
"statistics");
- SYSCTL_ADD_INT(device_get_sysctl_ctx(dev),
- SYSCTL_CHILDREN(device_get_sysctl_tree(dev)), OID_AUTO, "dwell",
- CTLFLAG_RW, &sc->dwelltime, 0,
- "channel dwell time (ms) for AP/station scanning");
-
/*
* Hook our interrupt after all initialization is complete.
*/
@@ -437,6 +430,41 @@
return 0;
}
+static struct ieee80211vap *
+ipw_vap_create(struct ieee80211com *ic,
+ const char name[IFNAMSIZ], int unit, int opmode, int flags,
+ const uint8_t bssid[IEEE80211_ADDR_LEN])
+{
+ struct ipw_vap *ivp;
+ struct ieee80211vap *vap;
+
+ if (!TAILQ_EMPTY(&ic->ic_vaps)) /* only one at a time */
+ return NULL;
+ ivp = (struct ipw_vap *) malloc(sizeof(struct ipw_vap),
+ M_80211_VAP, M_NOWAIT | M_ZERO);
+ if (ivp == NULL)
+ return NULL;
+ vap = &ivp->vap;
+ ieee80211_vap_setup(ic, vap, name, unit, opmode, flags, bssid);
+ /* override with driver methods */
+ ivp->newstate = vap->iv_newstate;
+ vap->iv_newstate = ipw_newstate;
+
+ /* complete setup */
+ ieee80211_vap_attach(vap, ieee80211_media_change, ipw_media_status);
+ ic->ic_opmode = opmode;
+ return vap;
+}
+
+static void
+ipw_vap_delete(struct ieee80211vap *vap)
+{
+ struct ipw_vap *ivp = IPW_VAP(vap);
+
+ ieee80211_vap_detach(vap);
+ free(ivp, M_80211_VAP);
+}
+
static int
ipw_dma_alloc(struct ipw_softc *sc)
{
@@ -767,26 +795,6 @@
}
static int
-ipw_media_change(struct ifnet *ifp)
-{
- struct ipw_softc *sc = ifp->if_softc;
- int error;
- IPW_LOCK_DECL;
-
- IPW_LOCK(sc);
- error = ieee80211_media_change(ifp);
- if (error == ENETRESET) {
- if ((ifp->if_flags & IFF_UP) &&
- (ifp->if_drv_flags & IFF_DRV_RUNNING))
- ipw_init_locked(sc, 0);
- error = 0;
- }
- IPW_UNLOCK(sc);
-
- return (error);
-}
-
-static int
ipw_cvtrate(int ipwrate)
{
switch (ipwrate) {
@@ -805,47 +813,26 @@
static void
ipw_media_status(struct ifnet *ifp, struct ifmediareq *imr)
{
- struct ipw_softc *sc = ifp->if_softc;
- struct ieee80211com *ic = &sc->sc_ic;
- int rate;
+ struct ieee80211vap *vap = ifp->if_softc;
+ struct ieee80211com *ic = vap->iv_ic;
+ struct ipw_softc *sc = ic->ic_ifp->if_softc;
- imr->ifm_status = IFM_AVALID;
- imr->ifm_active = IFM_IEEE80211;
- if (ic->ic_state == IEEE80211_S_RUN)
- imr->ifm_status |= IFM_ACTIVE;
-
/* read current transmission rate from adapter */
- rate = ipw_cvtrate(ipw_read_table1(sc, IPW_INFO_CURRENT_TX_RATE) & 0xf);
- imr->ifm_active |= ieee80211_rate2media(ic, rate, IEEE80211_MODE_11B);
-
- switch (ic->ic_opmode) {
- case IEEE80211_M_STA:
- break;
-
- case IEEE80211_M_IBSS:
- imr->ifm_active |= IFM_IEEE80211_IBSS;
- break;
-
- case IEEE80211_M_MONITOR:
- imr->ifm_active |= IFM_IEEE80211_MONITOR;
- break;
-
- case IEEE80211_M_AHDEMO:
- case IEEE80211_M_HOSTAP:
- case IEEE80211_M_WDS:
- /* should not get there */
- break;
- }
+ vap->iv_bss->ni_txrate = ipw_cvtrate(
+ ipw_read_table1(sc, IPW_INFO_CURRENT_TX_RATE) & 0xf);
+ ieee80211_media_status(ifp, imr);
}
static int
-ipw_newstate(struct ieee80211com *ic, enum ieee80211_state nstate, int arg)
+ipw_newstate(struct ieee80211vap *vap, enum ieee80211_state nstate, int arg)
{
+ struct ipw_vap *ivp = IPW_VAP(vap);
+ struct ieee80211com *ic = vap->iv_ic;
struct ifnet *ifp = ic->ic_ifp;
struct ipw_softc *sc = ifp->if_softc;
DPRINTF(("%s: %s -> %s flags 0x%x\n", __func__,
- ieee80211_state_name[ic->ic_state],
+ ieee80211_state_name[vap->iv_state],
ieee80211_state_name[nstate], sc->flags));
switch (nstate) {
@@ -859,7 +846,7 @@
* AUTH -> RUN transition and we want to do nothing.
* This is all totally bogus and needs to be redone.
*/
- if (ic->ic_state == IEEE80211_S_SCAN)
+ if (vap->iv_state == IEEE80211_S_SCAN)
taskqueue_enqueue_fast(taskqueue_fast,
&sc->sc_assoc_task);
}
@@ -880,7 +867,7 @@
* If we are not transitioning from AUTH the resend the
* association request.
*/
- if (ic->ic_state != IEEE80211_S_AUTH)
+ if (vap->iv_state != IEEE80211_S_AUTH)
taskqueue_enqueue_fast(taskqueue_fast,
&sc->sc_assoc_task);
break;
@@ -888,7 +875,7 @@
default:
break;
}
- return (*sc->sc_newstate)(ic, nstate, arg);
+ return ivp->newstate(vap, nstate, arg);
}
/*
@@ -967,8 +954,9 @@
static void
ipw_rx_newstate_intr(struct ipw_softc *sc, struct ipw_soft_buf *sbuf)
{
-#define IEEESTATE(ic) ieee80211_state_name[ic->ic_state]
+#define IEEESTATE(vap) ieee80211_state_name[vap->iv_state]
struct ieee80211com *ic = &sc->sc_ic;
+ struct ieee80211vap *vap = TAILQ_FIRST(&ic->ic_vaps);
uint32_t state;
bus_dmamap_sync(sc->rxbuf_dmat, sbuf->map, BUS_DMASYNC_POSTREAD);
@@ -978,19 +966,19 @@
switch (state) {
case IPW_STATE_ASSOCIATED:
DPRINTFN(2, ("Association succeeded (%s flags 0x%x)\n",
- IEEESTATE(ic), sc->flags));
+ IEEESTATE(vap), sc->flags));
sc->flags |= IPW_FLAG_ASSOCIATED;
/* XXX suppress state change in case the fw auto-associates */
- if (ic->ic_state != IEEE80211_S_ASSOC) {
+ if (vap->iv_state != IEEE80211_S_ASSOC) {
DPRINTF(("Unexpected association (state %u)\n",
- ic->ic_state));
+ vap->iv_state));
} else
- ieee80211_new_state(ic, IEEE80211_S_RUN, -1);
+ ieee80211_new_state(vap, IEEE80211_S_RUN, -1);
break;
case IPW_STATE_SCANNING:
DPRINTFN(3, ("Scanning (%s flags 0x%x)\n",
- IEEESTATE(ic), sc->flags));
+ IEEESTATE(vap), sc->flags));
/*
* NB: Check driver state for association on assoc
* loss as the firmware will immediately start to
@@ -1014,9 +1002,9 @@
break;
}
DPRINTFN(3, ("Scan complete (%s flags 0x%x)\n",
- IEEESTATE(ic), sc->flags));
+ IEEESTATE(vap), sc->flags));
if (sc->flags & IPW_FLAG_SCANNING) {
- ieee80211_scan_done(ic);
+ ieee80211_scan_done(vap);
sc->flags &= ~IPW_FLAG_SCANNING;
sc->sc_scan_timer = 0;
}
@@ -1024,27 +1012,27 @@
case IPW_STATE_ASSOCIATION_LOST:
DPRINTFN(2, ("Association lost (%s flags 0x%x)\n",
- IEEESTATE(ic), sc->flags));
+ IEEESTATE(vap), sc->flags));
sc->flags &= ~IPW_FLAG_ASSOCIATED;
- if (ic->ic_state == IEEE80211_S_RUN)
- ieee80211_new_state(ic, IEEE80211_S_SCAN, -1);
+ if (vap->iv_state == IEEE80211_S_RUN)
+ ieee80211_new_state(vap, IEEE80211_S_SCAN, -1);
break;
case IPW_STATE_DISABLED:
DPRINTFN(2, ("Firmware disabled (%s flags 0x%x)\n",
- IEEESTATE(ic), sc->flags));
+ IEEESTATE(vap), sc->flags));
break;
case IPW_STATE_RADIO_DISABLED:
DPRINTFN(2, ("Radio off (%s flags 0x%x)\n",
- IEEESTATE(ic), sc->flags));
- ic->ic_ifp->if_flags &= ~IFF_UP;
+ IEEESTATE(vap), sc->flags));
+ vap->iv_ifp->if_flags &= ~IFF_UP; /* XXX */
ipw_stop_locked(sc);
break;
default:
DPRINTFN(2, ("%s: unhandled state %u %s flags 0x%x\n",
- __func__, state, IEEESTATE(ic), sc->flags));
+ __func__, state, IEEESTATE(vap), sc->flags));
break;
}
#undef IEEESTATE
@@ -1089,6 +1077,7 @@
subtype != IEEE80211_FC0_SUBTYPE_PROBE_RESP)
return;
+ /* XXX use ieee80211_parse_beacon */
frm = (uint8_t *)(wh + 1);
efrm = mtod(m, uint8_t *) + m->m_len;
@@ -1119,7 +1108,6 @@
struct ieee80211com *ic = &sc->sc_ic;
struct ifnet *ifp = ic->ic_ifp;
struct mbuf *mnew, *m;
- struct ieee80211_frame *wh;
struct ieee80211_node *ni;
bus_addr_t physaddr;
int error;
@@ -1191,15 +1179,13 @@
if (sc->flags & IPW_FLAG_SCANNING)
ipw_fix_channel(sc, m);
- wh = mtod(m, struct ieee80211_frame *);
IPW_UNLOCK(sc);
- ni = ieee80211_find_rxnode(ic, (struct ieee80211_frame_min *)wh);
-
- /* send the frame to the 802.11 layer */
- ieee80211_input(ic, m, ni, status->rssi, -95/*XXX*/, 0);
-
- /* node is no longer needed */
- ieee80211_free_node(ni);
+ ni = ieee80211_find_rxnode(ic, mtod(m, struct ieee80211_frame_min *));
+ if (ni != NULL) {
+ (void) ieee80211_input(ni, m, status->rssi, -95, 0);
+ ieee80211_free_node(ni);
+ } else
+ (void) ieee80211_input_all(ic, m, status->rssi, -95, 0);
IPW_LOCK(sc);
bus_dmamap_sync(sc->rbd_dmat, sc->rbd_map, BUS_DMASYNC_PREWRITE);
@@ -1209,6 +1195,7 @@
ipw_rx_intr(struct ipw_softc *sc)
{
struct ieee80211com *ic = &sc->sc_ic;
+ struct ieee80211vap *vap = TAILQ_FIRST(&ic->ic_vaps);
struct ipw_status *status;
struct ipw_soft_bd *sbd;
struct ipw_soft_buf *sbuf;
@@ -1243,10 +1230,10 @@
case IPW_STATUS_CODE_NOTIFICATION:
DPRINTFN(2, ("notification status, len %u flags 0x%x\n",
le32toh(status->len), status->flags));
- if (ic->ic_state == IEEE80211_S_AUTH) {
+ if (vap->iv_state == IEEE80211_S_AUTH) {
/* XXX assume auth notification */
- ieee80211_node_authorize(ic->ic_bss);
- ieee80211_new_state(ic, IEEE80211_S_ASSOC, -1);
+ ieee80211_node_authorize(vap->iv_bss);
+ ieee80211_new_state(vap, IEEE80211_S_ASSOC, -1);
}
break;
@@ -1528,12 +1515,11 @@
wh = mtod(m0, struct ieee80211_frame *);
if (wh->i_fc[1] & IEEE80211_FC1_WEP) {
- k = ieee80211_crypto_encap(ic, ni, m0);
+ k = ieee80211_crypto_encap(ni, m0);
if (k == NULL) {
m_freem(m0);
return ENOBUFS;
}
-
/* packet header may have moved, reset our local pointer */
wh = mtod(m0, struct ieee80211_frame *);
}
@@ -1675,54 +1661,31 @@
ipw_start_locked(struct ifnet *ifp)
{
struct ipw_softc *sc = ifp->if_softc;
- struct ieee80211com *ic = &sc->sc_ic;
- struct mbuf *m0;
- struct ether_header *eh;
struct ieee80211_node *ni;
+ struct mbuf *m;
IPW_LOCK_ASSERT(sc);
- if (ic->ic_state != IEEE80211_S_RUN)
- return;
-
for (;;) {
- IFQ_DRV_DEQUEUE(&ifp->if_snd, m0);
- if (m0 == NULL)
+ IFQ_DRV_DEQUEUE(&ifp->if_snd, m);
+ if (m == NULL)
break;
-
if (sc->txfree < 1 + IPW_MAX_NSEG) {
- IFQ_DRV_PREPEND(&ifp->if_snd, m0);
+ IFQ_DRV_PREPEND(&ifp->if_snd, m);
ifp->if_drv_flags |= IFF_DRV_OACTIVE;
break;
}
-
- if (m0->m_len < sizeof (struct ether_header) &&
- (m0 = m_pullup(m0, sizeof (struct ether_header))) == NULL)
- continue;
-
- eh = mtod(m0, struct ether_header *);
- ni = ieee80211_find_txnode(ic, eh->ether_dhost);
- if (ni == NULL) {
- m_freem(m0);
- continue;
- }
- BPF_MTAP(ifp, m0);
-
- m0 = ieee80211_encap(ic, m0, ni);
- if (m0 == NULL) {
+ ni = (struct ieee80211_node *) m->m_pkthdr.rcvif;
+ m = ieee80211_encap(ni, m);
+ if (m == NULL) {
ieee80211_free_node(ni);
continue;
}
-
- if (bpf_peers_present(ic->ic_rawbpf))
- bpf_mtap(ic->ic_rawbpf, m0);
-
- if (ipw_tx_start(ifp, m0, ni) != 0) {
+ if (ipw_tx_start(ifp, m, ni) != 0) {
ieee80211_free_node(ni);
ifp->if_oerrors++;
break;
}
-
/* start watchdog timer */
sc->sc_tx_timer = 5;
}
@@ -1750,7 +1713,7 @@
DPRINTFN(3, ("Scan timeout\n"));
/* End the scan */
if (sc->flags & IPW_FLAG_SCANNING) {
- ieee80211_scan_done(ic);
+ ieee80211_scan_done(TAILQ_FIRST(&ic->ic_vaps));
sc->flags &= ~IPW_FLAG_SCANNING;
}
}
@@ -1763,7 +1726,6 @@
ipw_ioctl(struct ifnet *ifp, u_long cmd, caddr_t data)
{
struct ipw_softc *sc = ifp->if_softc;
- struct ieee80211com *ic = &sc->sc_ic;
int error = 0;
IPW_LOCK_DECL;
@@ -1781,15 +1743,7 @@
break;
default:
- error = ieee80211_ioctl(ic, cmd, data);
- }
-
- if (error == ENETRESET) {
- if ((ifp->if_flags & IFF_UP) &&
- (ifp->if_drv_flags & IFF_DRV_RUNNING) &&
- (ic->ic_roaming != IEEE80211_ROAMING_MANUAL))
- ipw_init_locked(sc, 0);
- error = 0;
+ error = ether_ioctl(ifp, cmd, data);
}
IPW_UNLOCK(sc);
@@ -2011,12 +1965,13 @@
ipw_setwepkeys(struct ipw_softc *sc)
{
struct ieee80211com *ic = &sc->sc_ic;
+ struct ieee80211vap *vap = TAILQ_FIRST(&ic->ic_vaps);
struct ipw_wep_key wepkey;
struct ieee80211_key *wk;
int error, i;
for (i = 0; i < IEEE80211_WEP_NKID; i++) {
- wk = &ic->ic_crypto.cs_nw_keys[i];
+ wk = &vap->iv_nw_keys[i];
if (wk->wk_cipher == NULL ||
wk->wk_cipher->ic_cipher != IEEE80211_CIPHER_WEP)
@@ -2182,6 +2137,7 @@
ipw_config(struct ipw_softc *sc)
{
struct ieee80211com *ic = &sc->sc_ic;
+ struct ieee80211vap *vap = TAILQ_FIRST(&ic->ic_vaps);
struct ifnet *ifp = ic->ic_ifp;
struct ipw_security security;
struct ipw_configuration config;
@@ -2221,9 +2177,9 @@
if (ic->ic_opmode == IEEE80211_M_MONITOR)
return ipw_enable(sc);
- IEEE80211_ADDR_COPY(ic->ic_myaddr, IF_LLADDR(ifp));
- DPRINTF(("Setting MAC address to %6D\n", ic->ic_myaddr, ":"));
- error = ipw_cmd(sc, IPW_CMD_SET_MAC_ADDRESS, ic->ic_myaddr,
+ IEEE80211_ADDR_COPY(vap->iv_myaddr, IF_LLADDR(ifp));
+ DPRINTF(("Setting MAC address to %6D\n", vap->iv_myaddr, ":"));
+ error = ipw_cmd(sc, IPW_CMD_SET_MAC_ADDRESS, vap->iv_myaddr,
IEEE80211_ADDR_LEN);
if (error != 0)
return error;
@@ -2274,19 +2230,19 @@
return error;
}
- data = htole32(ic->ic_rtsthreshold);
+ data = htole32(vap->iv_rtsthreshold);
DPRINTF(("Setting RTS threshold to %u\n", le32toh(data)));
error = ipw_cmd(sc, IPW_CMD_SET_RTS_THRESHOLD, &data, sizeof data);
if (error != 0)
return error;
- data = htole32(ic->ic_fragthreshold);
+ data = htole32(vap->iv_fragthreshold);
DPRINTF(("Setting frag threshold to %u\n", le32toh(data)));
error = ipw_cmd(sc, IPW_CMD_SET_FRAG_THRESHOLD, &data, sizeof data);
if (error != 0)
return error;
- error = ipw_setssid(sc, ic->ic_des_ssid[0].ssid, ic->ic_des_ssid[0].len);
+ error = ipw_setssid(sc, vap->iv_des_ssid[0].ssid, vap->iv_des_ssid[0].len);
if (error != 0)
return error;
@@ -2294,17 +2250,17 @@
if (error != 0)
return error;
- if (ic->ic_flags & IEEE80211_F_DESBSSID) {
- DPRINTF(("Setting desired BSSID to %6D\n", ic->ic_des_bssid,
+ if (vap->iv_flags & IEEE80211_F_DESBSSID) {
+ DPRINTF(("Setting desired BSSID to %6D\n", vap->iv_des_bssid,
":"));
error = ipw_cmd(sc, IPW_CMD_SET_DESIRED_BSSID,
- ic->ic_des_bssid, IEEE80211_ADDR_LEN);
+ vap->iv_des_bssid, IEEE80211_ADDR_LEN);
if (error != 0)
return error;
}
memset(&security, 0, sizeof security);
- security.authmode = (ic->ic_bss->ni_authmode == IEEE80211_AUTH_SHARED) ?
+ security.authmode = (vap->iv_bss->ni_authmode == IEEE80211_AUTH_SHARED) ?
IPW_AUTH_SHARED : IPW_AUTH_OPEN;
security.ciphers = htole32(IPW_CIPHER_NONE);
DPRINTF(("Setting authmode to %u\n", security.authmode));
@@ -2313,13 +2269,13 @@
if (error != 0)
return error;
- if (ic->ic_flags & IEEE80211_F_PRIVACY) {
+ if (vap->iv_flags & IEEE80211_F_PRIVACY) {
error = ipw_setwepkeys(sc);
if (error != 0)
return error;
- if (ic->ic_crypto.cs_def_txkey != IEEE80211_KEYIX_NONE) {
- data = htole32(ic->ic_crypto.cs_def_txkey);
+ if (vap->iv_def_txkey != IEEE80211_KEYIX_NONE) {
+ data = htole32(vap->iv_def_txkey);
DPRINTF(("Setting wep tx key index to %u\n",
le32toh(data)));
error = ipw_cmd(sc, IPW_CMD_SET_WEP_KEY_INDEX, &data,
@@ -2329,14 +2285,15 @@
}
}
- data = htole32((ic->ic_flags & IEEE80211_F_PRIVACY) ? IPW_WEPON : 0);
+ data = htole32((vap->iv_flags & IEEE80211_F_PRIVACY) ? IPW_WEPON : 0);
DPRINTF(("Setting wep flags to 0x%x\n", le32toh(data)));
error = ipw_cmd(sc, IPW_CMD_SET_WEP_FLAGS, &data, sizeof data);
if (error != 0)
return error;
- if (ic->ic_opt_ie != NULL) {
- error = ipw_setwpaie(sc, ic->ic_opt_ie, ic->ic_opt_ie_len);
+ if (vap->iv_appie_assocreq != NULL) {
+ struct ieee80211_appie *ie = vap->iv_appie_assocreq;
+ error = ipw_setwpaie(sc, ie->ie_data, ie->ie_len);
if (error != 0)
return error;
}
@@ -2376,7 +2333,8 @@
ipw_auth_and_assoc(struct ipw_softc *sc)
{
struct ieee80211com *ic = &sc->sc_ic;
- struct ieee80211_node *ni = ic->ic_bss;
+ struct ieee80211vap *vap = TAILQ_FIRST(&ic->ic_vaps);
+ struct ieee80211_node *ni = vap->iv_bss;
struct ipw_security security;
uint32_t data;
int error;
@@ -2395,13 +2353,13 @@
if (error != 0)
return (error);
- if (ic->ic_flags & IEEE80211_F_PRIVACY) {
+ if (vap->iv_flags & IEEE80211_F_PRIVACY) {
error = ipw_setwepkeys(sc);
if (error != 0)
return error;
- if (ic->ic_crypto.cs_def_txkey != IEEE80211_KEYIX_NONE) {
- data = htole32(ic->ic_crypto.cs_def_txkey);
+ if (vap->iv_def_txkey != IEEE80211_KEYIX_NONE) {
+ data = htole32(vap->iv_def_txkey);
DPRINTF(("Setting wep tx key index to %u\n",
le32toh(data)));
error = ipw_cmd(sc, IPW_CMD_SET_WEP_KEY_INDEX, &data,
@@ -2411,7 +2369,7 @@
}
}
- data = htole32((ic->ic_flags & IEEE80211_F_PRIVACY) ? IPW_WEPON : 0);
+ data = htole32((vap->iv_flags & IEEE80211_F_PRIVACY) ? IPW_WEPON : 0);
DPRINTF(("Setting wep flags to 0x%x\n", le32toh(data)));
error = ipw_cmd(sc, IPW_CMD_SET_WEP_FLAGS, &data, sizeof data);
if (error != 0)
@@ -2425,8 +2383,9 @@
if (error != 0)
return (error);
- if (ic->ic_opt_ie != NULL) {
- error = ipw_setwpaie(sc, ic->ic_opt_ie, ic->ic_opt_ie_len);
+ if (vap->iv_appie_assocreq != NULL) {
+ struct ieee80211_appie *ie = vap->iv_appie_assocreq;
+ error = ipw_setwpaie(sc, ie->ie_data, ie->ie_len);
if (error != 0)
return error;
}
@@ -2462,7 +2421,8 @@
ipw_disassociate(struct ipw_softc *sc)
{
struct ieee80211com *ic = &sc->sc_ic;
- struct ieee80211_node *ni = ic->ic_bss;
+ struct ieee80211vap *vap = TAILQ_FIRST(&ic->ic_vaps);
+ struct ieee80211_node *ni = vap->iv_bss;
DPRINTF(("Disassociate from %6D\n", ni->ni_bssid, ":"));
@@ -2507,6 +2467,7 @@
ipw_init_locked(struct ipw_softc *sc, int force)
{
struct ieee80211com *ic = &sc->sc_ic;
+ struct ieee80211vap *vap = TAILQ_FIRST(&ic->ic_vaps);
struct ifnet *ifp = ic->ic_ifp;
const struct firmware *fp;
const struct ipw_firmware_hdr *hdr;
@@ -2516,7 +2477,7 @@
IPW_LOCK_ASSERT(sc);
DPRINTF(("%s: state %s flags 0x%x\n", __func__,
- ieee80211_state_name[ic->ic_state], sc->flags));
+ ieee80211_state_name[vap->iv_state], sc->flags));
/*
* Avoid re-entrant calls. We need to release the mutex in ipw_init()
@@ -2631,22 +2592,13 @@
goto fail1;
}
- if (ic->ic_opmode != IEEE80211_M_MONITOR) {
- /*
- * NB: When restarting the adapter clock the state
- * machine regardless of the roaming mode; otherwise
- * we need to notify user apps so they can manually
- * get us going again.
- */
- if (ic->ic_roaming != IEEE80211_ROAMING_MANUAL || force)
- ieee80211_new_state(ic, IEEE80211_S_SCAN, 0);
- } else
- ieee80211_new_state(ic, IEEE80211_S_RUN, -1);
-
callout_reset(&sc->sc_wdtimer, hz, ipw_watchdog, sc);
ifp->if_drv_flags &= ~IFF_DRV_OACTIVE;
ifp->if_drv_flags |= IFF_DRV_RUNNING;
+ /* XXX force handling */
+ ieee80211_start_all(ic); /* start all vap's */
+
sc->flags &=~ IPW_FLAG_INIT_LOCKED;
return;
@@ -2677,8 +2629,6 @@
IPW_LOCK_ASSERT(sc);
- ieee80211_new_state(ic, IEEE80211_S_INIT, -1);
-
callout_stop(&sc->sc_wdtimer);
ipw_stop_master(sc);
@@ -2816,13 +2766,13 @@
}
static void
-ipw_scan_curchan(struct ieee80211com *ic, unsigned long maxdwell)
+ipw_scan_curchan(struct ieee80211_scan_state *ss, unsigned long maxdwell)
{
/* NB: all channels are scanned at once */
}
static void
-ipw_scan_mindwell(struct ieee80211com *ic)
+ipw_scan_mindwell(struct ieee80211_scan_state *ss)
{
/* NB: don't try to abort scan; wait for firmware to finish */
}
==== //depot/projects/vap/sys/dev/ipw/if_ipwvar.h#5 (text+ko) ====
@@ -76,11 +76,17 @@
((1 << IEEE80211_RADIOTAP_FLAGS) | \
(1 << IEEE80211_RADIOTAP_CHANNEL))
+struct ipw_vap {
+ struct ieee80211vap vap;
+
+ int (*newstate)(struct ieee80211vap *,
+ enum ieee80211_state, int);
+};
+#define IPW_VAP(vap) ((struct ipw_vap *)(vap))
+
struct ipw_softc {
struct ifnet *sc_ifp;
struct ieee80211com sc_ic;
- int (*sc_newstate)(struct ieee80211com *,
- enum ieee80211_state, int);
device_t sc_dev;
struct mtx sc_mtx;
@@ -152,22 +158,12 @@
uint32_t rxcur;
int txfree;
- int dwelltime;
-
struct bpf_if *sc_drvbpf;
- union {
- struct ipw_rx_radiotap_header th;
- uint8_t pad[64];
- } sc_rxtapu;
-#define sc_rxtap sc_rxtapu.th
+ struct ipw_rx_radiotap_header sc_rxtap;
int sc_rxtap_len;
- union {
- struct ipw_tx_radiotap_header th;
- uint8_t pad[64];
- } sc_txtapu;
-#define sc_txtap sc_txtapu.th
+ struct ipw_tx_radiotap_header sc_txtap;
int sc_txtap_len;
};
==== //depot/projects/vap/sys/dev/iwi/if_iwi.c#9 (text+ko) ====
@@ -73,6 +73,7 @@
#include <net80211/ieee80211_var.h>
#include <net80211/ieee80211_radiotap.h>
+#include <net80211/ieee80211_input.h>
#include <net80211/ieee80211_regdomain.h>
#include <netinet/in.h>
@@ -120,6 +121,10 @@
{ 0, 0, NULL }
};
+static struct ieee80211vap *iwi_vap_create(struct ieee80211com *,
+ const char name[IFNAMSIZ], int unit, int opmode, int flags,
+ const uint8_t bssid[IEEE80211_ADDR_LEN]);
+static void iwi_vap_delete(struct ieee80211vap *);
static void iwi_dma_map_addr(void *, bus_dma_segment_t *, int, int);
static int iwi_alloc_cmd_ring(struct iwi_softc *, struct iwi_cmd_ring *,
int);
@@ -135,9 +140,8 @@
static void iwi_free_rx_ring(struct iwi_softc *, struct iwi_rx_ring *);
static struct ieee80211_node *iwi_node_alloc(struct ieee80211_node_table *);
static void iwi_node_free(struct ieee80211_node *);
-static int iwi_media_change(struct ifnet *);
static void iwi_media_status(struct ifnet *, struct ifmediareq *);
-static int iwi_newstate(struct ieee80211com *, enum ieee80211_state, int);
+static int iwi_newstate(struct ieee80211vap *, enum ieee80211_state, int);
static void iwi_wme_init(struct iwi_softc *);
static int iwi_wme_setparams(struct iwi_softc *);
static int iwi_wme_update(struct ieee80211com *);
@@ -168,16 +172,16 @@
static void iwi_scan_end(struct ieee80211com *);
static void iwi_scanabort(void *, int);
static void iwi_set_channel(struct ieee80211com *);
-static void iwi_scan_curchan(struct ieee80211com *, unsigned long maxdwell);
+static void iwi_scan_curchan(struct ieee80211_scan_state *, unsigned long maxdwell);
#if 0
static void iwi_scan_allchan(struct ieee80211com *, unsigned long maxdwell);
#endif
-static void iwi_scan_mindwell(struct ieee80211com *);
-static void iwi_assoc(struct ieee80211com *ic);
-static void iwi_disassoc(struct ieee80211com *);
+static void iwi_scan_mindwell(struct ieee80211_scan_state *);
+static void iwi_assoc(struct ieee80211vap *);
+static void iwi_disassoc(struct ieee80211vap *);
static void iwi_ops(void *, int);
static int iwi_queue_cmd(struct iwi_softc *, int);
-static int iwi_auth_and_assoc(struct iwi_softc *);
+static int iwi_auth_and_assoc(struct iwi_softc *, struct ieee80211vap *);
static int iwi_disassociate(struct iwi_softc *, int quiet);
static void iwi_init(void *);
static void iwi_init_locked(void *, int);
@@ -258,7 +262,8 @@
struct ifnet *ifp;
struct ieee80211com *ic = &sc->sc_ic;
uint16_t val;
- int i, error, bands;
+ int i, error;
+ uint8_t bands;
sc->sc_dev = dev;
@@ -267,7 +272,6 @@
sc->sc_unr = new_unrhdr(1, IWI_MAX_IBSSNODE-1, &sc->sc_mtx);
-#if __FreeBSD_version >= 700000
sc->sc_tq = taskqueue_create("iwi_taskq", M_NOWAIT | M_ZERO,
taskqueue_thread_enqueue, &sc->sc_tq);
taskqueue_start_threads(&sc->sc_tq, 1, PI_NET, "%s taskq",
@@ -276,16 +280,7 @@
taskqueue_thread_enqueue, &sc->sc_tq2);
taskqueue_start_threads(&sc->sc_tq2, 1, PI_NET, "%s taskq2",
device_get_nameunit(dev));
-#else
- sc->sc_tq = taskqueue_create("iwi_taskq", M_NOWAIT | M_ZERO,
- taskqueue_thread_enqueue, &sc->sc_tq, &sc->sc_tqproc);
- kproc_create(taskqueue_thread_loop, &sc->sc_tq, &sc->sc_tqproc,
- 0, 0, "%s taskq", device_get_nameunit(dev));
- sc->sc_tq2 = taskqueue_create("iwi_taskq2", M_NOWAIT | M_ZERO,
- taskqueue_thread_enqueue, &sc->sc_tq2, &sc->sc_tqproc);
- kproc_create(taskqueue_thread_loop, &sc->sc_tq2, &sc->sc_tqproc,
- 0, 0, "%s taskq2", device_get_nameunit(dev));
-#endif
+
TASK_INIT(&sc->sc_radiontask, 0, iwi_radio_on, sc);
TASK_INIT(&sc->sc_radiofftask, 0, iwi_radio_off, sc);
TASK_INIT(&sc->sc_restarttask, 0, iwi_restart, sc);
@@ -370,10 +365,7 @@
ifp->if_snd.ifq_drv_maxlen = IFQ_MAXLEN;
IFQ_SET_READY(&ifp->if_snd);
- ic->ic_wme.wme_update = iwi_wme_update;
ic->ic_phytype = IEEE80211_T_OFDM; /* not only, but not used */
- ic->ic_opmode = IEEE80211_M_STA; /* default to BSS mode */
- ic->ic_state = IEEE80211_S_INIT;
/* set device capabilities */
ic->ic_caps =
@@ -402,10 +394,9 @@
setbit(&bands, IEEE80211_MODE_11G);
if (pci_get_device(dev) >= 0x4223)
setbit(&bands, IEEE80211_MODE_11A);
- ieee80211_init_channels(ic, 0, CTRY_DEFAULT, bands, 0, 1);
+ ieee80211_init_channels(ic, NULL, &bands);
ieee80211_ifattach(ic);
- ic->ic_bmissthreshold = 10; /* override default */
/* override default methods */
ic->ic_node_alloc = iwi_node_alloc;
sc->sc_node_free = ic->ic_node_free;
@@ -415,11 +406,10 @@
ic->ic_set_channel = iwi_set_channel;
ic->ic_scan_curchan = iwi_scan_curchan;
ic->ic_scan_mindwell = iwi_scan_mindwell;
+ ic->ic_wme.wme_update = iwi_wme_update;
- /* override state transition machine */
- sc->sc_newstate = ic->ic_newstate;
- ic->ic_newstate = iwi_newstate;
- ieee80211_media_init(ic, iwi_media_change, iwi_media_status);
+ ic->ic_vap_create = iwi_vap_create;
+ ic->ic_vap_delete = iwi_vap_delete;
bpfattach2(ifp, DLT_IEEE802_11_RADIO,
sizeof (struct ieee80211_frame) + sizeof (sc->sc_txtap),
@@ -505,6 +495,42 @@
return 0;
}
+static struct ieee80211vap *
+iwi_vap_create(struct ieee80211com *ic,
+ const char name[IFNAMSIZ], int unit, int opmode, int flags,
+ const uint8_t bssid[IEEE80211_ADDR_LEN])
+{
+ struct iwi_vap *ivp;
+ struct ieee80211vap *vap;
+
+ if (!TAILQ_EMPTY(&ic->ic_vaps)) /* only one at a time */
+ return NULL;
+ ivp = (struct iwi_vap *) malloc(sizeof(struct iwi_vap),
+ M_80211_VAP, M_NOWAIT | M_ZERO);
+ if (ivp == NULL)
+ return NULL;
+ vap = &ivp->iwi_vap;
+ ieee80211_vap_setup(ic, vap, name, unit, opmode, flags, bssid);
+ vap->iv_bmissthreshold = 10; /* override default */
+ /* override with driver methods */
+ ivp->iwi_newstate = vap->iv_newstate;
+ vap->iv_newstate = iwi_newstate;
+
+ /* complete setup */
+ ieee80211_vap_attach(vap, ieee80211_media_change, iwi_media_status);
+ ic->ic_opmode = opmode;
+ return vap;
+}
+
+static void
+iwi_vap_delete(struct ieee80211vap *vap)
+{
+ struct iwi_vap *ivp = IWI_VAP(vap);
+
+ ieee80211_vap_detach(vap);
+ free(ivp, M_80211_VAP);
+}
+
static void
iwi_dma_map_addr(void *arg, bus_dma_segment_t *segs, int nseg, int error)
{
@@ -882,25 +908,6 @@
sc->sc_node_free(ni);
}
-static int
-iwi_media_change(struct ifnet *ifp)
-{
- struct iwi_softc *sc = ifp->if_softc;
- int error;
- IWI_LOCK_DECL;
-
- IWI_LOCK(sc);
-
- error = ieee80211_media_change(ifp);
- if (error == ENETRESET &&
- (ifp->if_flags & IFF_UP) && (ifp->if_drv_flags & IFF_DRV_RUNNING))
- iwi_init_locked(sc, 0);
-
>>> TRUNCATED FOR MAIL (1000 lines) <<<
More information about the p4-projects
mailing list