Source-Changes-HG archive
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]
[src/trunk]: src/sys/net80211 Pull in net80211/ from FreeBSD. This contains S...
details: https://anonhg.NetBSD.org/src/rev/4cb138050e3e
branches: trunk
changeset: 551159:4cb138050e3e
user: dyoung <dyoung%NetBSD.org@localhost>
date: Sat Aug 30 21:26:03 2003 +0000
description:
Pull in net80211/ from FreeBSD. This contains Sam Leffler's
enhancements to the 802.11 layer, which are necessary for ath(4),
the Atheros-chipset driver.
diffstat:
sys/net80211/ieee80211.c | 875 +++++++++++++++++++++++++++++++
sys/net80211/ieee80211.h | 332 ++++++++++++
sys/net80211/ieee80211_crypto.c | 307 +++++++++++
sys/net80211/ieee80211_crypto.h | 50 +
sys/net80211/ieee80211_input.c | 1078 +++++++++++++++++++++++++++++++++++++++
sys/net80211/ieee80211_ioctl.c | 988 +++++++++++++++++++++++++++++++++++
sys/net80211/ieee80211_ioctl.h | 84 +++
sys/net80211/ieee80211_node.c | 570 ++++++++++++++++++++
sys/net80211/ieee80211_node.h | 147 +++++
sys/net80211/ieee80211_output.c | 551 +++++++++++++++++++
sys/net80211/ieee80211_proto.c | 503 ++++++++++++++++++
sys/net80211/ieee80211_proto.h | 78 ++
sys/net80211/ieee80211_var.h | 265 +++++++++
13 files changed, 5828 insertions(+), 0 deletions(-)
diffs (truncated from 5880 to 300 lines):
diff -r b0e3a780fba9 -r 4cb138050e3e sys/net80211/ieee80211.c
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/sys/net80211/ieee80211.c Sat Aug 30 21:26:03 2003 +0000
@@ -0,0 +1,875 @@
+/*-
+ * Copyright (c) 2001 Atsushi Onoe
+ * Copyright (c) 2002, 2003 Sam Leffler, Errno Consulting
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. The name of the author may not be used to endorse or promote products
+ * derived from this software without specific prior written permission.
+ *
+ * Alternatively, this software may be distributed under the terms of the
+ * GNU General Public License ("GPL") version 2 as published by the Free
+ * Software Foundation.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include <sys/cdefs.h>
+__FBSDID("$FreeBSD: src/sys/net80211/ieee80211.c,v 1.7 2003/08/13 22:09:44 sam Exp $");
+
+/*
+ * IEEE 802.11 generic handler
+ */
+
+#include "opt_inet.h"
+
+#include <sys/param.h>
+#include <sys/systm.h>
+#include <sys/mbuf.h>
+#include <sys/malloc.h>
+#include <sys/kernel.h>
+#include <sys/socket.h>
+#include <sys/sockio.h>
+#include <sys/endian.h>
+#include <sys/errno.h>
+#include <sys/bus.h>
+#include <sys/proc.h>
+#include <sys/sysctl.h>
+
+#include <machine/atomic.h>
+
+#include <net/if.h>
+#include <net/if_dl.h>
+#include <net/if_media.h>
+#include <net/if_arp.h>
+#include <net/ethernet.h>
+#include <net/if_llc.h>
+
+#include <net80211/ieee80211_var.h>
+
+#include <net/bpf.h>
+
+#ifdef INET
+#include <netinet/in.h>
+#include <netinet/if_ether.h>
+#endif
+
+#ifdef IEEE80211_DEBUG
+int ieee80211_debug = 0;
+SYSCTL_INT(_debug, OID_AUTO, ieee80211, CTLFLAG_RW, &ieee80211_debug,
+ 0, "IEEE 802.11 media debugging printfs");
+#endif
+
+static void ieee80211_set11gbasicrates(struct ieee80211_rateset *,
+ enum ieee80211_phymode);
+
+static const char *ieee80211_phymode_name[] = {
+ "auto", /* IEEE80211_MODE_AUTO */
+ "11a", /* IEEE80211_MODE_11A */
+ "11b", /* IEEE80211_MODE_11B */
+ "11g", /* IEEE80211_MODE_11G */
+ "turbo", /* IEEE80211_MODE_TURBO */
+};
+
+void
+ieee80211_ifattach(struct ifnet *ifp)
+{
+ struct ieee80211com *ic = (void *)ifp;
+ struct ieee80211_channel *c;
+ int i;
+
+ ether_ifattach(ifp, ic->ic_myaddr);
+ bpfattach2(ifp, DLT_IEEE802_11,
+ sizeof(struct ieee80211_frame_addr4), &ic->ic_rawbpf);
+ ieee80211_crypto_attach(ifp);
+
+ /*
+ * Fill in 802.11 available channel set, mark
+ * all available channels as active, and pick
+ * a default channel if not already specified.
+ */
+ memset(ic->ic_chan_avail, 0, sizeof(ic->ic_chan_avail));
+ ic->ic_modecaps |= 1<<IEEE80211_MODE_AUTO;
+ for (i = 0; i <= IEEE80211_CHAN_MAX; i++) {
+ c = &ic->ic_channels[i];
+ if (c->ic_flags) {
+ /*
+ * Verify driver passed us valid data.
+ */
+ if (i != ieee80211_chan2ieee(ic, c)) {
+ if_printf(ifp, "bad channel ignored; "
+ "freq %u flags %x number %u\n",
+ c->ic_freq, c->ic_flags, i);
+ c->ic_flags = 0; /* NB: remove */
+ continue;
+ }
+ setbit(ic->ic_chan_avail, i);
+ /*
+ * Identify mode capabilities.
+ */
+ if (IEEE80211_IS_CHAN_A(c))
+ ic->ic_modecaps |= 1<<IEEE80211_MODE_11A;
+ if (IEEE80211_IS_CHAN_B(c))
+ ic->ic_modecaps |= 1<<IEEE80211_MODE_11B;
+ if (IEEE80211_IS_CHAN_PUREG(c))
+ ic->ic_modecaps |= 1<<IEEE80211_MODE_11G;
+ if (IEEE80211_IS_CHAN_T(c))
+ ic->ic_modecaps |= 1<<IEEE80211_MODE_TURBO;
+ }
+ }
+ /* validate ic->ic_curmode */
+ if ((ic->ic_modecaps & (1<<ic->ic_curmode)) == 0)
+ ic->ic_curmode = IEEE80211_MODE_AUTO;
+
+ (void) ieee80211_setmode(ic, ic->ic_curmode);
+
+ ic->ic_des_chan = IEEE80211_CHAN_ANYC; /* any channel is ok */
+ if (ic->ic_lintval == 0)
+ ic->ic_lintval = 100; /* default sleep */
+ ic->ic_bmisstimeout = 7*ic->ic_lintval; /* default 7 beacons */
+
+ ieee80211_node_attach(ifp);
+ ieee80211_proto_attach(ifp);
+}
+
+void
+ieee80211_ifdetach(struct ifnet *ifp)
+{
+ struct ieee80211com *ic = (void *)ifp;
+
+ ieee80211_proto_detach(ifp);
+ ieee80211_crypto_detach(ifp);
+ ieee80211_node_detach(ifp);
+ ifmedia_removeall(&ic->ic_media);
+ bpfdetach(ifp);
+ ether_ifdetach(ifp);
+}
+
+/*
+ * Convert MHz frequency to IEEE channel number.
+ */
+u_int
+ieee80211_mhz2ieee(u_int freq, u_int flags)
+{
+ if (flags & IEEE80211_CHAN_2GHZ) { /* 2GHz band */
+ if (freq == 2484)
+ return 14;
+ if (freq < 2484)
+ return (freq - 2407) / 5;
+ else
+ return 15 + ((freq - 2512) / 20);
+ } else if (flags & IEEE80211_CHAN_5GHZ) { /* 5Ghz band */
+ return (freq - 5000) / 5;
+ } else { /* either, guess */
+ if (freq == 2484)
+ return 14;
+ if (freq < 2484)
+ return (freq - 2407) / 5;
+ if (freq < 5000)
+ return 15 + ((freq - 2512) / 20);
+ return (freq - 5000) / 5;
+ }
+}
+
+/*
+ * Convert channel to IEEE channel number.
+ */
+u_int
+ieee80211_chan2ieee(struct ieee80211com *ic, struct ieee80211_channel *c)
+{
+ if (ic->ic_channels <= c && c <= &ic->ic_channels[IEEE80211_CHAN_MAX])
+ return c - ic->ic_channels;
+ else if (c == IEEE80211_CHAN_ANYC)
+ return IEEE80211_CHAN_ANY;
+ else if (c != NULL) {
+ if_printf(&ic->ic_if, "invalid channel freq %u flags %x\n",
+ c->ic_freq, c->ic_flags);
+ return 0; /* XXX */
+ } else {
+ if_printf(&ic->ic_if, "invalid channel (NULL)\n");
+ return 0; /* XXX */
+ }
+}
+
+/*
+ * Convert IEEE channel number to MHz frequency.
+ */
+u_int
+ieee80211_ieee2mhz(u_int chan, u_int flags)
+{
+ if (flags & IEEE80211_CHAN_2GHZ) { /* 2GHz band */
+ if (chan == 14)
+ return 2484;
+ if (chan < 14)
+ return 2407 + chan*5;
+ else
+ return 2512 + ((chan-15)*20);
+ } else if (flags & IEEE80211_CHAN_5GHZ) {/* 5Ghz band */
+ return 5000 + (chan*5);
+ } else { /* either, guess */
+ if (chan == 14)
+ return 2484;
+ if (chan < 14) /* 0-13 */
+ return 2407 + chan*5;
+ if (chan < 27) /* 15-26 */
+ return 2512 + ((chan-15)*20);
+ return 5000 + (chan*5);
+ }
+}
+
+/*
+ * Setup the media data structures according to the channel and
+ * rate tables. This must be called by the driver after
+ * ieee80211_attach and before most anything else.
+ */
+void
+ieee80211_media_init(struct ifnet *ifp,
+ ifm_change_cb_t media_change, ifm_stat_cb_t media_stat)
+{
+#define ADD(_ic, _s, _o) \
+ ifmedia_add(&(_ic)->ic_media, \
+ IFM_MAKEWORD(IFM_IEEE80211, (_s), (_o), 0), 0, NULL)
+ struct ieee80211com *ic = (void *)ifp;
+ struct ifmediareq imr;
+ int i, j, mode, rate, maxrate, mword, mopt, r;
+ struct ieee80211_rateset *rs;
+ struct ieee80211_rateset allrates;
+
+ /*
+ * Do late attach work that must wait for any subclass
+ * (i.e. driver) work such as overriding methods.
+ */
+ ieee80211_node_lateattach(ifp);
+
+ /*
+ * Fill in media characteristics.
+ */
+ ifmedia_init(&ic->ic_media, 0, media_change, media_stat);
+ maxrate = 0;
+ memset(&allrates, 0, sizeof(allrates));
+ for (mode = IEEE80211_MODE_AUTO; mode < IEEE80211_MODE_MAX; mode++) {
+ static const u_int mopts[] = {
+ IFM_AUTO,
+ IFM_MAKEMODE(IFM_IEEE80211_11A),
+ IFM_MAKEMODE(IFM_IEEE80211_11B),
+ IFM_MAKEMODE(IFM_IEEE80211_11G),
+ IFM_MAKEMODE(IFM_IEEE80211_11A) | IFM_IEEE80211_TURBO,
+ };
+ if ((ic->ic_modecaps & (1<<mode)) == 0)
+ continue;
+ mopt = mopts[mode];
+ ADD(ic, IFM_AUTO, mopt); /* e.g. 11a auto */
+ if (ic->ic_caps & IEEE80211_C_IBSS)
+ ADD(ic, IFM_AUTO, mopt | IFM_IEEE80211_ADHOC);
+ if (ic->ic_caps & IEEE80211_C_HOSTAP)
+ ADD(ic, IFM_AUTO, mopt | IFM_IEEE80211_HOSTAP);
+ if (ic->ic_caps & IEEE80211_C_AHDEMO)
+ ADD(ic, IFM_AUTO, mopt | IFM_IEEE80211_ADHOC | IFM_FLAG0);
+ if (ic->ic_caps & IEEE80211_C_MONITOR)
+ ADD(ic, IFM_AUTO, mopt | IFM_IEEE80211_MONITOR);
+ if (mode == IEEE80211_MODE_AUTO)
+ continue;
+ if_printf(ifp, "%s rates: ", ieee80211_phymode_name[mode]);
+ rs = &ic->ic_sup_rates[mode];
+ for (i = 0; i < rs->rs_nrates; i++) {
+ rate = rs->rs_rates[i];
+ mword = ieee80211_rate2media(ic, rate, mode);
+ if (mword == 0)
+ continue;
+ printf("%s%d%sMbps", (i != 0 ? " " : ""),
+ (rate & IEEE80211_RATE_VAL) / 2,
Home |
Main Index |
Thread Index |
Old Index