PERFORCE change 73944 for review
Sam Leffler
sam at FreeBSD.org
Sun Mar 27 17:47:30 PST 2005
http://perforce.freebsd.org/chv.cgi?CH=73944
Change 73944 by sam at sam_ebb on 2005/03/28 01:46:29
o IFC
o resurrect ff support lost in a previous merge
o forward merge some stuff from the vap branch to simplify
ifconfig sharing
Affected files ...
.. //depot/projects/wifi/sys/net80211/_ieee80211.h#5 edit
.. //depot/projects/wifi/sys/net80211/ieee80211.c#22 edit
.. //depot/projects/wifi/sys/net80211/ieee80211_input.c#45 edit
.. //depot/projects/wifi/sys/net80211/ieee80211_ioctl.h#23 edit
.. //depot/projects/wifi/sys/net80211/ieee80211_output.c#40 edit
Differences ...
==== //depot/projects/wifi/sys/net80211/_ieee80211.h#5 (text+ko) ====
@@ -59,7 +59,8 @@
IEEE80211_M_IBSS = 0, /* IBSS (adhoc) station */
IEEE80211_M_AHDEMO = 3, /* Old lucent compatible adhoc demo */
IEEE80211_M_HOSTAP = 6, /* Software Access Point */
- IEEE80211_M_MONITOR = 8 /* Monitor mode */
+ IEEE80211_M_MONITOR = 8, /* Monitor mode */
+ IEEE80211_M_WDS = 2 /* WDS link */
};
/*
==== //depot/projects/wifi/sys/net80211/ieee80211.c#22 (text+ko) ====
@@ -625,6 +625,7 @@
case IEEE80211_M_HOSTAP:
case IEEE80211_M_STA:
case IEEE80211_M_MONITOR:
+ case IEEE80211_M_WDS:
ic->ic_flags &= ~IEEE80211_F_IBSSON;
break;
case IEEE80211_M_IBSS:
@@ -696,6 +697,11 @@
case IEEE80211_M_MONITOR:
imr->ifm_active |= IFM_IEEE80211_MONITOR;
break;
+ case IEEE80211_M_WDS:
+#if 0
+ imr->ifm_active |= IFM_IEEE80211_WDS;
+#endif
+ break;
}
switch (ic->ic_curmode) {
case IEEE80211_MODE_11A:
==== //depot/projects/wifi/sys/net80211/ieee80211_input.c#45 (text+ko) ====
@@ -31,7 +31,7 @@
*/
#include <sys/cdefs.h>
-__FBSDID("$FreeBSD: src/sys/net80211/ieee80211_input.c,v 1.33 2005/02/23 04:52:30 sam Exp $");
+__FBSDID("$FreeBSD: src/sys/net80211/ieee80211_input.c,v 1.35 2005/03/16 20:39:05 sam Exp $");
#include <sys/param.h>
#include <sys/systm.h>
@@ -109,7 +109,11 @@
static struct mbuf *ieee80211_defrag(struct ieee80211com *,
struct ieee80211_node *, struct mbuf *);
+static void ieee80211_deliver_data(struct ieee80211com *,
+ struct ieee80211_node *, struct mbuf *);
static struct mbuf *ieee80211_decap(struct ieee80211com *, struct mbuf *);
+static struct mbuf *ieee80211_decap_fastframe(struct ieee80211com *,
+ struct ieee80211_node *, struct mbuf *);
static void ieee80211_node_pwrsave(struct ieee80211_node *, int enable);
static void ieee80211_recv_pspoll(struct ieee80211com *,
struct ieee80211_node *, struct mbuf *);
@@ -134,7 +138,7 @@
struct ieee80211_frame *wh;
struct ieee80211_key *key;
struct ether_header *eh;
- int len, hdrsize, off;
+ int hdrsize, off;
u_int8_t dir, type, subtype;
u_int8_t *bssid;
u_int16_t rxseq;
@@ -237,8 +241,7 @@
* discovered member of the IBSS.
*/
ni = ieee80211_fakeup_adhoc_node(&ic->ic_sta,
- type == IEEE80211_FC0_TYPE_CTL ?
- wh->i_addr1 : wh->i_addr2);
+ wh->i_addr2);
if (ni == NULL) {
/* NB: stat kept for alloc failure */
goto err;
@@ -289,9 +292,9 @@
hdrsize = roundup(hdrsize, sizeof(u_int32_t));
if (m->m_len < hdrsize &&
(m = m_pullup(m, hdrsize)) == NULL) {
- IEEE80211_DISCARD(ic, IEEE80211_MSG_ANY,
- wh, "data", "too short: len %u, expecting %u",
- m->m_pkthdr.len, hdrsize);
+ IEEE80211_DISCARD_MAC(ic, IEEE80211_MSG_ANY,
+ ni->ni_macaddr, NULL,
+ "data too short: expecting %u", hdrsize);
ic->ic_stats.is_rx_tooshort++;
goto out; /* XXX */
}
@@ -493,49 +496,32 @@
IEEE80211_NODE_STAT(ni, rx_data);
IEEE80211_NODE_STAT_ADD(ni, rx_bytes, m->m_pkthdr.len);
- /* perform as a bridge within the AP */
- if (ic->ic_opmode == IEEE80211_M_HOSTAP &&
- (ic->ic_flags & IEEE80211_F_NOBRIDGE) == 0) {
- struct mbuf *m1 = NULL;
+#define FF_LLC_SIZE (sizeof(struct ether_header) + sizeof(struct llc))
+ if ((ni->ni_flags & IEEE80211_NODE_FF) &&
+ m->m_pkthdr.len >= 3*FF_LLC_SIZE) {
+ struct llc *llc;
- if (ETHER_IS_MULTICAST(eh->ether_dhost)) {
- m1 = m_copypacket(m, M_DONTWAIT);
- if (m1 == NULL)
- ifp->if_oerrors++;
- else
- m1->m_flags |= M_MCAST;
- } else {
- /* XXX this dups work done in ieee80211_encap */
- /* check if destination is associated */
- struct ieee80211_node *ni1 =
- ieee80211_find_node(&ic->ic_sta,
- eh->ether_dhost);
- if (ni1 != NULL) {
- /* XXX check if authorized */
- if (ni1->ni_associd != 0) {
- m1 = m;
- m = NULL;
- }
- /* XXX statistic? */
- ieee80211_free_node(ni1);
- }
+ /*
+ * Check for fast-frame tunnel encapsulation.
+ */
+ if (m->m_len < FF_LLC_SIZE &&
+ (m = m_pullup(m, FF_LLC_SIZE)) == NULL) {
+ IEEE80211_DISCARD_MAC(ic, IEEE80211_MSG_ANY,
+ ni->ni_macaddr, "fast-frame",
+ "%s", "m_pullup(llc) failed");
+ ic->ic_stats.is_rx_tooshort++;
}
- if (m1 != NULL) {
- len = m1->m_pkthdr.len;
- IF_ENQUEUE(&ifp->if_snd, m1);
- if (m != NULL)
- ifp->if_omcasts++;
- ifp->if_obytes += len;
+ llc = (struct llc *)(mtod(m, u_int8_t *) +
+ sizeof(struct ether_header));
+ if (llc->llc_snap.ether_type == htons(ATH_FF_ETH_TYPE)) {
+ m_adj(m, FF_LLC_SIZE);
+ m = ieee80211_decap_fastframe(ic, ni, m);
+ if (m == NULL)
+ return;
}
}
- if (m != NULL) {
- if (ni->ni_vlan != 0) {
- /* attach vlan tag */
- /* XXX goto err? */
- VLAN_INPUT_TAG(ifp, m, ni->ni_vlan, goto out);
- }
- (*ifp->if_input)(ifp, m);
- }
+#undef FF_LLC_SIZE
+ ieee80211_deliver_data(ic, ni, m);
return;
case IEEE80211_FC0_TYPE_MGT:
@@ -706,13 +692,72 @@
*(u_int16_t *) lwh->i_seq = *(u_int16_t *) wh->i_seq;
}
if (more_frag) { /* more to come, save */
- ni->ni_rxfragstamp = ticks;
ni->ni_rxfrag[0] = mfrag;
mfrag = NULL;
}
return mfrag;
}
+static void
+ieee80211_deliver_data(struct ieee80211com *ic,
+ struct ieee80211_node *ni, struct mbuf *m)
+{
+ struct ether_header *eh = mtod(m, struct ether_header *);
+ struct ifnet *ifp = ic->ic_ifp;
+ int len;
+
+ /* perform as a bridge within the AP */
+ if (ic->ic_opmode == IEEE80211_M_HOSTAP &&
+ (ic->ic_flags & IEEE80211_F_NOBRIDGE) == 0) {
+ struct mbuf *m1 = NULL;
+
+ if (ETHER_IS_MULTICAST(eh->ether_dhost)) {
+ m1 = m_copypacket(m, M_DONTWAIT);
+ if (m1 == NULL)
+ ifp->if_oerrors++;
+ else
+ m1->m_flags |= M_MCAST;
+ } else {
+ /* XXX this dups work done in ieee80211_encap */
+ /* check if destination is associated */
+ struct ieee80211_node *ni1 =
+ ieee80211_find_node(&ic->ic_sta,
+ eh->ether_dhost);
+ if (ni1 != NULL) {
+ /* XXX check if authorized */
+ if (ni1->ni_associd != 0) {
+ m1 = m;
+ m = NULL;
+ }
+ /* XXX statistic? */
+ ieee80211_free_node(ni1);
+ }
+ }
+ if (m1 != NULL) {
+ len = m1->m_pkthdr.len;
+ IF_ENQUEUE(&ifp->if_snd, m1);
+ if (m != NULL)
+ ifp->if_omcasts++;
+ ifp->if_obytes += len;
+ }
+ }
+ if (m != NULL) {
+ if (ni->ni_vlan != 0) {
+ /* attach vlan tag */
+ /* XXX goto err? */
+ VLAN_INPUT_TAG(ifp, m, ni->ni_vlan, goto out);
+ }
+ (*ifp->if_input)(ifp, m);
+ }
+ return;
+ out:
+ if (m != NULL) {
+ if (ic->ic_rawbpf)
+ bpf_mtap(ic->ic_rawbpf, m);
+ m_freem(m);
+ }
+}
+
static struct mbuf *
ieee80211_decap(struct ieee80211com *ic, struct mbuf *m)
{
@@ -815,6 +860,104 @@
}
/*
+ * Decap a frame encapsulated in a fast-frame.
+ */
+static struct mbuf *
+ieee80211_decap1(struct mbuf *m, int *framelen)
+{
+#define FF_LLC_SIZE (sizeof(struct ether_header) + sizeof(struct llc))
+ struct ether_header *eh;
+ struct llc *llc;
+
+ /*
+ * The frame has an 802.3 header followed by an 802.2
+ * LLC header. The encapsulated frame length is in the
+ * first header type field; save that and overwrite it
+ * with the true type field found in the second. Then
+ * copy the 802.3 header up to where it belongs and
+ * adjust the mbuf contents to remove the void.
+ */
+ if (m->m_len < FF_LLC_SIZE && (m = m_pullup(m, FF_LLC_SIZE)) == NULL)
+ return NULL;
+ eh = mtod(m, struct ether_header *); /* 802.3 header is first */
+ llc = (struct llc *)&eh[1]; /* 802.2 header follows */
+ *framelen = ntohs(eh->ether_type) /* encap'd frame size */
+ + sizeof(struct ether_header) - sizeof(struct llc);
+ eh->ether_type = llc->llc_un.type_snap.ether_type;
+ ovbcopy(eh, mtod(m, u_int8_t *) + sizeof(struct llc),
+ sizeof(struct ether_header));
+ m_adj(m, sizeof(struct llc));
+ return m;
+#undef FF_LLC_SIZE
+}
+
+/*
+ * Decap the encapsulated frame pair and dispatch the first
+ * for delivery. The second frame is returned for delivery
+ * via the normal path.
+ */
+static struct mbuf *
+ieee80211_decap_fastframe(struct ieee80211com *ic,
+ struct ieee80211_node *ni, struct mbuf *m)
+{
+#define MS(x,f) (((x) & f) >> f##_S)
+ u_int32_t ath;
+ struct mbuf *n;
+ int framelen;
+
+ m_copydata(m, 0, sizeof(u_int32_t), (caddr_t) &ath);
+ if (MS(ath, ATH_FF_PROTO) != ATH_FF_PROTO_L2TUNNEL) {
+ IEEE80211_DISCARD_MAC(ic, IEEE80211_MSG_ANY,
+ ni->ni_macaddr, "fast-frame",
+ "unsupport tunnel protocol, header 0x%x", ath);
+ ic->ic_stats.is_ff_badhdr++;
+ m_freem(m);
+ return NULL;
+ }
+ /* NB: skip header and alignment padding */
+ m_adj(m, roundup(sizeof(u_int32_t) - 2, 4) + 2);
+
+ ic->ic_stats.is_ff_decap++;
+
+ /*
+ * Decap the first frame, bust it apart from the
+ * second and deliver; then decap the second frame
+ * and return it to the caller for normal delivery.
+ */
+ m = ieee80211_decap1(m, &framelen);
+ if (m == NULL) {
+ IEEE80211_DISCARD_MAC(ic, IEEE80211_MSG_ANY,
+ ni->ni_macaddr, "fast-frame", "%s", "first decap failed");
+ ic->ic_stats.is_ff_tooshort++;
+ return NULL;
+ }
+ n = m_split(m, framelen, M_NOWAIT);
+ if (n == NULL) {
+ IEEE80211_DISCARD_MAC(ic, IEEE80211_MSG_ANY,
+ ni->ni_macaddr, "fast-frame",
+ "%s", "unable to split encapsulated frames");
+ ic->ic_stats.is_ff_split++;
+ m_freem(m); /* NB: must reclaim */
+ return NULL;
+ }
+ ieee80211_deliver_data(ic, ni, m); /* 1st of pair */
+
+ /*
+ * Decap second frame.
+ */
+ m_adj(n, roundup2(framelen, 4) - framelen); /* padding */
+ n = ieee80211_decap1(n, &framelen);
+ if (n == NULL) {
+ IEEE80211_DISCARD_MAC(ic, IEEE80211_MSG_ANY,
+ ni->ni_macaddr, "fast-frame", "%s", "second decap failed");
+ ic->ic_stats.is_ff_tooshort++;
+ }
+ /* XXX verify framelen against mbuf contents */
+ return n; /* 2nd delivered by caller */
+#undef MS
+}
+
+/*
* Install received rate set information in the node's state block.
*/
static int
@@ -864,6 +1007,7 @@
break;
case IEEE80211_M_AHDEMO:
+ case IEEE80211_M_WDS:
/* should not come here */
break;
@@ -1007,6 +1151,7 @@
case IEEE80211_M_MONITOR:
case IEEE80211_M_AHDEMO:
case IEEE80211_M_IBSS:
+ case IEEE80211_M_WDS:
IEEE80211_DISCARD_MAC(ic, IEEE80211_MSG_AUTH,
ni->ni_macaddr, "shared key auth",
"bad operating mode %u", ic->ic_opmode);
@@ -1613,6 +1758,40 @@
#undef MS
}
+static int
+ieee80211_parse_athparams(struct ieee80211_node *ni, u_int8_t *frm,
+ const struct ieee80211_frame *wh)
+{
+ struct ieee80211com *ic = ni->ni_ic;
+ const struct ieee80211_ath_ie *ath;
+ u_int len = frm[1];
+ int caps;
+
+ if (len < sizeof(struct ieee80211_ath_ie)-2) {
+ IEEE80211_DISCARD_IE(ic,
+ IEEE80211_MSG_ELEMID | IEEE80211_MSG_SUPERG,
+ wh, "Atheros", "too short, len %u", len);
+ return -1;
+ }
+ ath = (const struct ieee80211_ath_ie *)frm;
+ caps = 0;
+ if ((ath->ath_capability & ATHEROS_CAP_TURBO_PRIME) &&
+ (ic->ic_flags & IEEE80211_F_TURBOP))
+ caps |= IEEE80211_NODE_TURBOP;
+ if ((ath->ath_capability & ATHEROS_CAP_FAST_FRAME) &&
+ (ic->ic_flags & IEEE80211_F_FF))
+ caps |= IEEE80211_NODE_FF;
+ if ((ni->ni_flags ^ caps) & IEEE80211_NODE_ATH) {
+ IEEE80211_DPRINTF(ic, IEEE80211_MSG_SUPERG,
+ "[%s] ath ie: caps 0x%x defkeyix 0x%x, use 0x%x\n",
+ ether_sprintf(ni->ni_macaddr),
+ ath->ath_capability, LE_READ_2(ath->ath_defkeyix), caps);
+ ni->ni_flags = (ni->ni_flags &~ IEEE80211_NODE_ATH) | caps;
+ return 1;
+ } else
+ return 0; /* NB: no change */
+}
+
static void
ieee80211_saveie(u_int8_t **iep, const u_int8_t *ie)
{
@@ -1671,7 +1850,7 @@
#define ISREASSOC(_st) ((_st) == IEEE80211_FC0_SUBTYPE_REASSOC_RESP)
struct ieee80211_frame *wh;
u_int8_t *frm, *efrm;
- u_int8_t *ssid, *rates, *xrates, *wpa, *wme;
+ u_int8_t *ssid, *rates, *xrates, *wpa, *wme, *ath;
int reassoc, resp, allocbs;
wh = mtod(m0, struct ieee80211_frame *);
@@ -1712,12 +1891,13 @@
* [tlv] extended supported rates
* [tlv] WME
* [tlv] WPA or RSN
+ * [tlv] Atheros capabilities
*/
IEEE80211_VERIFY_LENGTH(efrm - frm, 12);
tstamp = frm; frm += 8;
bintval = le16toh(*(u_int16_t *)frm); frm += 2;
capinfo = le16toh(*(u_int16_t *)frm); frm += 2;
- ssid = rates = xrates = country = wpa = wme = NULL;
+ ssid = rates = xrates = country = wpa = wme = ath = NULL;
bchan = ieee80211_chan2ieee(ic, ic->ic_bss->ni_chan);
chan = bchan;
fhdwell = 0;
@@ -1777,7 +1957,8 @@
wpa = frm;
else if (iswmeparam(frm) || iswmeinfo(frm))
wme = frm;
- /* XXX Atheros OUI support */
+ else if (isatherosoui(frm))
+ ath = frm;
break;
default:
IEEE80211_DISCARD_IE(ic, IEEE80211_MSG_ELEMID,
@@ -1870,6 +2051,8 @@
if (wme != NULL &&
ieee80211_parse_wmeparams(ic, wme, wh) > 0)
ieee80211_wme_updateparams(ic);
+ if (ath != NULL)
+ ieee80211_parse_athparams(ni, ath, wh);
/* NB: don't need the rest of this */
if ((ic->ic_flags & IEEE80211_F_SCAN) == 0)
return;
@@ -1945,6 +2128,10 @@
ieee80211_saveie(&ni->ni_wme_ie, wme);
if (wpa != NULL)
ieee80211_saveie(&ni->ni_wpa_ie, wpa);
+ if (ath != NULL) {
+ ieee80211_saveie(&ni->ni_ath_ie, ath);
+ (void) ieee80211_parse_athparams(ni, ath, wh);
+ }
/* NB: must be after ni_chan is setup */
ieee80211_setup_rates(ic, ni, rates, xrates, IEEE80211_F_DOSORT);
break;
@@ -1969,8 +2156,9 @@
* [tlv] ssid
* [tlv] supported rates
* [tlv] extended supported rates
+ * [tlv] Atheros capabilities
*/
- ssid = rates = xrates = NULL;
+ ssid = rates = xrates = ath = NULL;
while (frm < efrm) {
switch (*frm) {
case IEEE80211_ELEMID_SSID:
@@ -1982,20 +2170,16 @@
case IEEE80211_ELEMID_XRATES:
xrates = frm;
break;
+ case IEEE80211_ELEMID_VENDOR:
+ if (isatherosoui(frm))
+ ath = frm;
+ break;
}
frm += frm[1] + 2;
}
IEEE80211_VERIFY_ELEMENT(rates, IEEE80211_RATE_MAXSIZE);
IEEE80211_VERIFY_ELEMENT(ssid, IEEE80211_NWID_LEN);
IEEE80211_VERIFY_SSID(ic->ic_bss, ssid);
- if ((ic->ic_flags & IEEE80211_F_HIDESSID) && ssid[1] == 0) {
- IEEE80211_DISCARD(ic, IEEE80211_MSG_INPUT,
- wh, ieee80211_mgt_subtype_name[subtype >>
- IEEE80211_FC0_SUBTYPE_SHIFT],
- "%s", "no ssid with ssid suppression enabled");
- ic->ic_stats.is_rx_ssidmismatch++; /*XXX*/
- return;
- }
if (ni == ic->ic_bss) {
if (ic->ic_opmode == IEEE80211_M_IBSS) {
@@ -2018,6 +2202,10 @@
"[%s] recv probe req\n", ether_sprintf(wh->i_addr2));
ni->ni_rssi = rssi;
ni->ni_rstamp = rstamp;
+ if (ath != NULL) {
+ ieee80211_saveie(&ni->ni_ath_ie, ath);
+ (void) ieee80211_parse_athparams(ni, ath, wh);
+ }
rate = ieee80211_setup_rates(ic, ni, rates, xrates,
IEEE80211_F_DOSORT | IEEE80211_F_DOFRATE
| IEEE80211_F_DONEGO | IEEE80211_F_DODEL);
@@ -2124,6 +2312,7 @@
* [tlv] supported rates
* [tlv] extended supported rates
* [tlv] WPA or RSN
+ * [tlv] Atheros capabilities
*/
IEEE80211_VERIFY_LENGTH(efrm - frm, (reassoc ? 10 : 4));
if (!IEEE80211_ADDR_EQ(wh->i_addr3, ic->ic_bss->ni_bssid)) {
@@ -2138,7 +2327,7 @@
bintval = le16toh(*(u_int16_t *)frm); frm += 2;
if (reassoc)
frm += 6; /* ignore current AP info */
- ssid = rates = xrates = wpa = wme = NULL;
+ ssid = rates = xrates = wpa = wme = ath = NULL;
while (frm < efrm) {
switch (*frm) {
case IEEE80211_ELEMID_SSID:
@@ -2160,7 +2349,8 @@
wpa = frm;
} else if (iswmeinfo(frm))
wme = frm;
- /* XXX Atheros OUI support */
+ else if (isatherosoui(frm))
+ ath = frm;
break;
}
frm += frm[1] + 2;
@@ -2184,6 +2374,20 @@
ic->ic_stats.is_rx_assoc_notauth++;
return;
}
+ /* assert right associstion security credentials */
+ if (wpa == NULL && (ic->ic_flags & IEEE80211_F_WPA)) {
+ IEEE80211_DPRINTF(ic,
+ IEEE80211_MSG_ASSOC | IEEE80211_MSG_WPA,
+ "[%s] no WPA/RSN IE in association request\n",
+ ether_sprintf(wh->i_addr2));
+ IEEE80211_SEND_MGMT(ic, ni,
+ IEEE80211_FC0_SUBTYPE_DEAUTH,
+ IEEE80211_REASON_RSN_REQUIRED);
+ ieee80211_node_leave(ic, ni);
+ /* XXX distinguish WPA/RSN? */
+ ic->ic_stats.is_rx_assoc_badwpaie++;
+ return;
+ }
if (wpa != NULL) {
/*
* Parse WPA information element. Note that
@@ -2287,6 +2491,23 @@
ni->ni_wme_ie = NULL;
ni->ni_flags &= ~IEEE80211_NODE_QOS;
}
+ if (ath != NULL) {
+ /*
+ * Record ATH parameters for station, mark
+ * node with appropriate capabilities, and
+ * record the information element for
+ * applications that require it.
+ */
+ ieee80211_saveie(&ni->ni_ath_ie, ath);
+ (void) ieee80211_parse_athparams(ni, ath, wh);
+ } else if (ni->ni_ath_ie != NULL) {
+ /*
+ * Flush any state from a previous association.
+ */
+ FREE(ni->ni_ath_ie, M_DEVBUF);
+ ni->ni_ath_ie = NULL;
+ ni->ni_flags &= ~IEEE80211_NODE_ATH;
+ }
ieee80211_node_join(ic, ni, resp);
break;
}
@@ -2330,7 +2551,7 @@
associd = le16toh(*(u_int16_t *)frm);
frm += 2;
- rates = xrates = wpa = wme = NULL;
+ rates = xrates = wme = NULL;
while (frm < efrm) {
switch (*frm) {
case IEEE80211_ELEMID_RATES:
@@ -2398,13 +2619,15 @@
else
ic->ic_flags &= ~IEEE80211_F_USEPROT;
IEEE80211_DPRINTF(ic, IEEE80211_MSG_ASSOC,
- "[%s] %sassoc success: %s preamble, %s slot time%s%s\n",
+ "[%s] %sassoc success: %s preamble, %s slot time%s%s%s%s\n",
ether_sprintf(wh->i_addr2),
ISREASSOC(subtype) ? "re" : "",
ic->ic_flags&IEEE80211_F_SHPREAMBLE ? "short" : "long",
ic->ic_flags&IEEE80211_F_SHSLOT ? "short" : "long",
ic->ic_flags&IEEE80211_F_USEPROT ? ", protection" : "",
- ni->ni_flags & IEEE80211_NODE_QOS ? ", QoS" : ""
+ ni->ni_flags & IEEE80211_NODE_QOS ? ", QoS" : "",
+ ni->ni_flags & IEEE80211_NODE_FF ? ", fast-frames" : "",
+ ni->ni_flags & IEEE80211_NODE_TURBOP ? ", turbo'" : ""
);
ieee80211_new_state(ic, IEEE80211_S_RUN, subtype);
break;
==== //depot/projects/wifi/sys/net80211/ieee80211_ioctl.h#23 (text+ko) ====
@@ -360,6 +360,7 @@
};
#define SIOCS80211 _IOW('i', 234, struct ieee80211req)
#define SIOCG80211 _IOWR('i', 235, struct ieee80211req)
+#define SIOCG80211STATS _IOWR('i', 236, struct ifreq)
#define IEEE80211_IOC_SSID 1
#define IEEE80211_IOC_NUMSSIDS 2
@@ -453,7 +454,10 @@
/* variable length SSID followed by IE data */
};
-#define SIOCG80211STATS _IOWR('i', 236, struct ifreq)
+struct ieee80211_clone_params {
+ char icp_parent[IFNAMSIZ]; /* parent device */
+ int icp_opmode; /* operating mode */
+};
#endif /* __FreeBSD__ */
#endif /* _NET80211_IEEE80211_IOCTL_H_ */
==== //depot/projects/wifi/sys/net80211/ieee80211_output.c#40 (text+ko) ====
@@ -31,7 +31,7 @@
*/
#include <sys/cdefs.h>
-__FBSDID("$FreeBSD: src/sys/net80211/ieee80211_output.c,v 1.20 2005/02/10 17:00:48 sam Exp $");
+__FBSDID("$FreeBSD: src/sys/net80211/ieee80211_output.c,v 1.21 2005/03/16 20:42:00 sam Exp $");
#include "opt_inet.h"
@@ -233,7 +233,7 @@
v_wme_ac = 0;
if (ni->ni_vlan != 0) {
struct m_tag *mtag = VLAN_OUTPUT_TAG(ic->ic_ifp, m);
- if (mtag != NULL) {
+ if (mtag == NULL) {
IEEE80211_NODE_STAT(ni, tx_novlantag);
return 1;
}
@@ -593,6 +593,7 @@
IEEE80211_ADDR_COPY(wh->i_addr3, eh.ether_shost);
break;
case IEEE80211_M_MONITOR:
+ case IEEE80211_M_WDS:
goto bad;
}
if (addqos) {
More information about the p4-projects
mailing list