summaryrefslogtreecommitdiff
path: root/orinoco
diff options
context:
space:
mode:
authorChris Larson <clarson@kergoth.com>2004-11-09 00:36:47 +0000
committerChris Larson <clarson@kergoth.com>2004-11-09 00:36:47 +0000
commitf96441b9faf769c9ecdd4d338b605ea3d0cc4010 (patch)
treeedb17ec2c4ea13c5acb1c7350957a249a820e28d /orinoco
parentb6588aa6851fb220cedc387d21c51513ef8d67f4 (diff)
Disable bk EOLN_NATIVE conversions on all files in packages FILESPATHs, to prevent it screwing up patches.
BKrev: 4190111fA4MuVozAqwE7xOSL9fr-TA
Diffstat (limited to 'orinoco')
-rw-r--r--orinoco/orinoco-modules-0.13e/crosscompile.patch48
-rw-r--r--orinoco/orinoco-modules-0.13e/monitor-0.13e.patch758
-rw-r--r--orinoco/orinoco-modules-0.13e/shmoo-monitor-0.13e.patch797
-rw-r--r--orinoco/orinoco-modules-0.13e/spectrum_cs.c1212
-rw-r--r--orinoco/orinoco-modules-0.13e/spectrum_fw.h4569
-rw-r--r--orinoco/orinoco-modules-0.15rc1/list-move.patch22
-rw-r--r--orinoco/orinoco-modules-0.15rc1/spectrum-firmware.patch16
-rw-r--r--orinoco/orinoco-modules-0.15rc1/spectrum_fw.h4569
-rw-r--r--orinoco/orinoco-modules-0.15rc2/list-move.patch22
-rw-r--r--orinoco/orinoco-modules-0.15rc2/spectrum-firmware.patch16
-rw-r--r--orinoco/orinoco-modules-0.15rc2/spectrum_fw.h4569
11 files changed, 16598 insertions, 0 deletions
diff --git a/orinoco/orinoco-modules-0.13e/crosscompile.patch b/orinoco/orinoco-modules-0.13e/crosscompile.patch
index e69de29bb2..5963e931c2 100644
--- a/orinoco/orinoco-modules-0.13e/crosscompile.patch
+++ b/orinoco/orinoco-modules-0.13e/crosscompile.patch
@@ -0,0 +1,48 @@
+--- orinoco-0.13e/Makefile~crosscompile 2003-05-12 08:22:27.000000000 +0200
++++ orinoco-0.13e/Makefile 2003-06-15 18:17:21.000000000 +0200
+@@ -19,7 +19,7 @@
+ endif
+ endif
+
+-MODULES = hermes.o orinoco.o orinoco_cs.o orinoco_plx.o orinoco_tmd.o orinoco_pci.o
++MODULES = hermes.o orinoco.o orinoco_cs.o orinoco_plx.o orinoco_tmd.o orinoco_pci.o spectrum_cs.o
+ ifeq ($(shell uname -m),ppc)
+ MODULES += airport.o
+ endif
+@@ -27,9 +27,9 @@
+ SRCS = hermes.c \
+ orinoco.c \
+ airport.c orinoco_cs.c orinoco_plx.c orinoco_tmd.c orinoco_pci.c \
+- userhermes.c
++ userhermes.c spectrum_cs.c
+ HDRS = hermes.h hermes_rid.h ieee802_11.h orinoco.h
+-CONF = hermes.conf
++CONF = hermes.conf spectrum.conf
+ TAR = tar
+
+ DISTFILES = $(SRCS) $(HDRS) $(CONF) Makefile README.orinoco
+@@ -41,7 +41,7 @@
+ all: modules
+
+ installconf:
+- if [ -d $(CONF_DIR) ]; then install -m 644 -o 0 -g 0 $(CONF) $(CONF_DIR)/$(CONF); fi
++ if [ -d $(CONF_DIR) ]; then install -m 644 $(CONF) $(CONF_DIR)/; fi
+
+
+ userhermes: userhermes.c
+@@ -118,12 +118,12 @@
+ mkdir -p $(MODULE_DIR_WIRELESS)
+ for f in $(MODULES); do \
+ if test -e $(MODULE_DIR_PCMCIA)/$$f; then \
+- install -m 644 -o 0 -g 0 $$f $(MODULE_DIR_PCMCIA)/$$f; \
++ install -m 644 $$f $(MODULE_DIR_PCMCIA)/$$f; \
+ else \
+- install -m 644 -o 0 -g 0 $$f $(MODULE_DIR_WIRELESS)/$$f; \
++ install -m 644 $$f $(MODULE_DIR_WIRELESS)/$$f; \
+ fi; \
+ done
+- depmod -a
++ #depmod -a
+
+ %.o: %.c
+ $(CC) -MD $(CFLAGS) $(CPPFLAGS) $(MFLAG) -c $<
diff --git a/orinoco/orinoco-modules-0.13e/monitor-0.13e.patch b/orinoco/orinoco-modules-0.13e/monitor-0.13e.patch
index e69de29bb2..cfffced893 100644
--- a/orinoco/orinoco-modules-0.13e/monitor-0.13e.patch
+++ b/orinoco/orinoco-modules-0.13e/monitor-0.13e.patch
@@ -0,0 +1,758 @@
+diff -urN dist/orinoco-0.13e/hermes.c orinoco-monitor/hermes.c
+--- dist/orinoco-0.13e/hermes.c 2003-05-12 16:22:27.000000000 +1000
++++ orinoco-monitor/hermes.c 2003-05-13 13:26:02.000000000 +1000
+@@ -183,6 +183,10 @@
+ if (err)
+ return err;
+
++ for (k = 0; k < HERMES_NUMPORTS_MAX; k++) {
++ hw->port_enabled[k] = 0;
++ }
++
+ reg = hermes_read_regn(hw, EVSTAT);
+ k = CMD_INIT_TIMEOUT;
+ while ( (! (reg & HERMES_EV_CMD)) && k) {
+diff -urN dist/orinoco-0.13e/hermes.h orinoco-monitor/hermes.h
+--- dist/orinoco-0.13e/hermes.h 2003-05-12 16:22:27.000000000 +1000
++++ orinoco-monitor/hermes.h 2003-05-07 16:54:45.000000000 +1000
+@@ -33,6 +33,10 @@
+ #include <linux/if_ether.h>
+ #include <asm/byteorder.h>
+
++#define HFA384x_PORTTYPE_IBSS ((uint16_t)3)
++#define HFA384x_WEPFLAGS_DISABLE_TXCRYPT (0x10)
++#define HFA384x_WEPFLAGS_DISABLE_RXCRYPT (0x80)
++
+ /*
+ * Limits and constants
+ */
+@@ -148,6 +152,14 @@
+ #define HERMES_MONITOR_ENABLE (0x000b)
+ #define HERMES_MONITOR_DISABLE (0x000f)
+
++/*--------------------------------------------------------------------
++Communication Frames: Field Masks for Receive Frames
++--------------------------------------------------------------------*/
++/*-- Offsets --------*/
++#define HERMES_RX_DATA_LEN_OFF (44)
++#define HERMES_RX_80211HDR_OFF (14)
++#define HERMES_RX_DATA_OFF (60)
++
+ /*
+ * Frame structures and constants
+ */
+@@ -171,6 +183,7 @@
+ #define HERMES_RXSTAT_BADCRC (0x0001)
+ #define HERMES_RXSTAT_UNDECRYPTABLE (0x0002)
+ #define HERMES_RXSTAT_MACPORT (0x0700)
++#define HERMES_RXSTAT_GET_MACPORT(s) (((s) & HERMES_RXSTAT_MACPORT) >> 8)
+ #define HERMES_RXSTAT_PCF (0x1000) /* Frame was received in CF period */
+ #define HERMES_RXSTAT_MSGTYPE (0xE000)
+ #define HERMES_RXSTAT_1042 (0x2000) /* RFC-1042 frame */
+@@ -286,6 +299,7 @@
+ #define HERMES_32BIT_REGSPACING 1
+
+ u16 inten; /* Which interrupts should be enabled? */
++ u8 port_enabled[HERMES_NUMPORTS_MAX];
+
+ #ifdef HERMES_DEBUG_BUFFER
+ struct hermes_debug_entry dbuf[HERMES_DEBUG_BUFSIZE];
+@@ -339,12 +353,14 @@
+
+ static inline int hermes_enable_port(hermes_t *hw, int port)
+ {
++ hw->port_enabled[port] = 1;
+ return hermes_docmd_wait(hw, HERMES_CMD_ENABLE | (port << 8),
+ 0, NULL);
+ }
+
+ static inline int hermes_disable_port(hermes_t *hw, int port)
+ {
++ hw->port_enabled[port] = 0;
+ return hermes_docmd_wait(hw, HERMES_CMD_DISABLE | (port << 8),
+ 0, NULL);
+ }
+diff -urN dist/orinoco-0.13e/orinoco.c orinoco-monitor/orinoco.c
+--- dist/orinoco-0.13e/orinoco.c 2003-05-12 16:22:27.000000000 +1000
++++ orinoco-monitor/orinoco.c 2003-05-13 13:27:31.000000000 +1000
+@@ -1673,6 +1673,7 @@
+ struct header_struct hdr;
+ struct ethhdr *eh;
+ int err;
++ struct ieee802_11_hdr hdr80211;
+
+ rxfid = hermes_read_regn(hw, RXFID);
+
+@@ -1689,6 +1690,8 @@
+
+ if (status & HERMES_RXSTAT_ERR) {
+ if (status & HERMES_RXSTAT_UNDECRYPTABLE) {
++ if (dev->type != ARPHRD_ETHER)
++ goto sniffing;
+ wstats->discard.code++;
+ DEBUG(1, "%s: Undecryptable frame on Rx. Frame dropped.\n",
+ dev->name);
+@@ -1699,7 +1702,7 @@
+ stats->rx_errors++;
+ goto drop;
+ }
+-
++sniffing:
+ /* For now we ignore the 802.11 header completely, assuming
+ that the card's firmware has handled anything vital */
+
+@@ -1729,81 +1732,111 @@
+ stats->rx_errors++;
+ goto drop;
+ }
++ /* Now handle frame based on port# */
++ switch (HERMES_RXSTAT_GET_MACPORT(status)) {
++ case 0:
++ /* We need space for the packet data itself, plus an
++ * ethernet header, plus 2 bytes so we can align the
++ * IP header on a 32bit boundary, plus 1 byte so we
++ * can read in odd length packets from the card, which
++ * has an IO granularity of 16 bits */
++ skb = dev_alloc_skb(length+ETH_HLEN+2+1);
++ if (!skb) {
++ printk(KERN_WARNING "%s: Can't allocate skb for Rx\n",
++ dev->name);
++ goto drop;
++ }
+
+- /* We need space for the packet data itself, plus an ethernet
+- header, plus 2 bytes so we can align the IP header on a
+- 32bit boundary, plus 1 byte so we can read in odd length
+- packets from the card, which has an IO granularity of 16
+- bits */
+- skb = dev_alloc_skb(length+ETH_HLEN+2+1);
+- if (!skb) {
+- printk(KERN_WARNING "%s: Can't allocate skb for Rx\n",
+- dev->name);
+- goto drop;
+- }
+-
+- skb_reserve(skb, 2); /* This way the IP header is aligned */
+-
+- /* Handle decapsulation
+- * In most cases, the firmware tell us about SNAP frames.
+- * For some reason, the SNAP frames sent by LinkSys APs
+- * are not properly recognised by most firmwares.
+- * So, check ourselves */
+- if(((status & HERMES_RXSTAT_MSGTYPE) == HERMES_RXSTAT_1042) ||
+- ((status & HERMES_RXSTAT_MSGTYPE) == HERMES_RXSTAT_TUNNEL) ||
+- is_ethersnap(&hdr)) {
+- /* These indicate a SNAP within 802.2 LLC within
+- 802.11 frame which we'll need to de-encapsulate to
+- the original EthernetII frame. */
++ skb_reserve(skb, 2); /* This way the IP header is aligned */
+
+- if (length < ENCAPS_OVERHEAD) { /* No room for full LLC+SNAP */
+- stats->rx_length_errors++;
++ /* Handle decapsulation In most cases, the firmware
++ * tell us about SNAP frames. For some reason, the
++ * SNAP frames sent by LinkSys APs are not properly
++ * recognised by most firmwares. So, check ourselves
++ * */
++ if (((status & HERMES_RXSTAT_MSGTYPE) == HERMES_RXSTAT_1042) ||
++ ((status & HERMES_RXSTAT_MSGTYPE) == HERMES_RXSTAT_TUNNEL) ||
++ is_ethersnap(&hdr)) {
++ /* These indicate a SNAP within 802.2 LLC
++ * within 802.11 frame which we'll need to
++ * de-encapsulate to the original EthernetII
++ * frame. */
++
++ if (length < ENCAPS_OVERHEAD) { /* No room for full LLC+SNAP */
++ stats->rx_length_errors++;
++ goto drop;
++ }
++
++ /* Remove SNAP header, reconstruct EthernetII frame */
++ data_len = length - ENCAPS_OVERHEAD;
++ data_off = HERMES_802_3_OFFSET + sizeof(hdr);
++
++ eh = (struct ethhdr *)skb_put(skb, ETH_HLEN);
++
++ memcpy(eh, &hdr, 2 * ETH_ALEN);
++ eh->h_proto = hdr.ethertype;
++ } else {
++ /* All other cases indicate a genuine 802.3 frame. No
++ decapsulation needed. We just throw the whole
++ thing in, and hope the protocol layer can deal with
++ it as 802.3 */
++ data_len = length;
++ data_off = HERMES_802_3_OFFSET;
++ /* FIXME: we re-read from the card data we already read here */
++ }
++
++ p = skb_put(skb, data_len);
++ err = hermes_bap_pread(hw, IRQ_BAP, p, RUP_EVEN(data_len),
++ rxfid, data_off);
++ if (err) {
++ printk(KERN_ERR "%s: error %d reading frame. "
++ "Frame dropped.\n", dev->name, err);
++ stats->rx_errors++;
++ goto drop;
++ }
++
++ dev->last_rx = jiffies;
++ skb->dev = dev;
++ skb->protocol = eth_type_trans(skb, dev);
++ skb->ip_summed = CHECKSUM_NONE;
++
++ /* Process the wireless stats if needed */
++ orinoco_stat_gather(dev, skb, &desc);
++
++ /* Pass the packet to the networking stack */
++ netif_rx(skb);
++ stats->rx_packets++;
++ stats->rx_bytes += length;
++
++ return;
++
++ case 7:
++ if (status & HERMES_RXSTAT_BADCRC) {
++ printk(KERN_DEBUG "%s: Received monitor frame: "
++ "BADCRC set\n", dev->name);
+ goto drop;
+ }
+
+- /* Remove SNAP header, reconstruct EthernetII frame */
+- data_len = length - ENCAPS_OVERHEAD;
+- data_off = HERMES_802_3_OFFSET + sizeof(hdr);
++ err = hermes_bap_pread(hw, IRQ_BAP, &hdr80211,
++ sizeof(hdr80211),
++ rxfid, HERMES_RX_80211HDR_OFF);
+
+- eh = (struct ethhdr *)skb_put(skb, ETH_HLEN);
++ if (err) {
++ printk(KERN_ERR "%s: error %d reading monitor frame. "
++ "Frame dropped.\n", dev->name, err);
++ stats->rx_errors++;
++ goto drop;
++ }
+
+- memcpy(eh, &hdr, 2 * ETH_ALEN);
+- eh->h_proto = hdr.ethertype;
+- } else {
+- /* All other cases indicate a genuine 802.3 frame. No
+- decapsulation needed. We just throw the whole
+- thing in, and hope the protocol layer can deal with
+- it as 802.3 */
+- data_len = length;
+- data_off = HERMES_802_3_OFFSET;
+- /* FIXME: we re-read from the card data we already read here */
+- }
++ orinoco_int_rxmonitor(dev, rxfid, length,
++ &desc, &hdr80211);
++ break;
+
+- p = skb_put(skb, data_len);
+- err = hermes_bap_pread(hw, IRQ_BAP, p, RUP_EVEN(data_len),
+- rxfid, data_off);
+- if (err) {
+- printk(KERN_ERR "%s: error %d reading frame. "
+- "Frame dropped.\n", dev->name, err);
+- stats->rx_errors++;
+- goto drop;
++ default:
++ printk("Received frame on unsupported port=%d\n",
++ HERMES_RXSTAT_GET_MACPORT(status));
++ break;
+ }
+-
+- dev->last_rx = jiffies;
+- skb->dev = dev;
+- skb->protocol = eth_type_trans(skb, dev);
+- skb->ip_summed = CHECKSUM_NONE;
+-
+- /* Process the wireless stats if needed */
+- orinoco_stat_gather(dev, skb, &desc);
+-
+- /* Pass the packet to the networking stack */
+- netif_rx(skb);
+- stats->rx_packets++;
+- stats->rx_bytes += length;
+-
+- return;
+-
+ drop:
+ stats->rx_dropped++;
+
+@@ -3598,6 +3631,159 @@
+ return 0;
+ }
+
++static int orinoco_wlansniff(struct net_device *dev, struct iwreq *wrq)
++{
++ struct orinoco_private *priv = dev->priv;
++ hermes_t *hw = &priv->hw;
++ int err = 0;
++ u16 word;
++ int *parms = (int *) wrq->u.name;
++ int enable = parms[0] > 0;
++ unsigned long flags;
++
++ err = orinoco_lock(priv, &flags);
++ if (err)
++ return err;
++
++ switch (enable) {
++ case 0:
++ /* Confirm that we're in monitor mode */
++ if (dev->type == ARPHRD_ETHER)
++ err = -EFAULT;
++
++ /* Disable monitor mode */
++ word = HERMES_CMD_MONITOR | (HERMES_MONITOR_DISABLE << 8);
++ err = hermes_docmd_wait(hw, word, 0, NULL);
++ if (err)
++ break;
++
++ /* Disable port 0 */
++ err = hermes_disable_port(hw, 0);
++ if (err)
++ break;
++
++ /* Clear the driver state */
++ dev->type = ARPHRD_ETHER;
++
++ /* Restore the wepflags */ /*Orinoco doesn't like this*/
++#if 0
++ err = hermes_write_wordrec(hw, USER_BAP,
++ HERMES_RID_CNFWEPFLAGS_INTERSIL,
++ priv->presniff_wepflags);
++ if (err)
++ break;
++#endif /* 0 */
++
++ /* Set the port to its prior type and enable (if necessary) */
++ if (priv->presniff_port_type != 0) {
++ word = priv->presniff_port_type;
++ err = hermes_write_wordrec(hw, USER_BAP,
++ HERMES_RID_CNFPORTTYPE,
++ word);
++ if (err)
++ break;
++
++ /* Enable the port */
++ err = hermes_enable_port(hw, 0);
++ if (err)
++ break;
++ }
++
++ break;
++
++ case 1:
++ /* Re-initialize the card before changing channel as advised at
++ * http://lists.samba.org/pipermail/wireless/2002-June/004491.html
++ * by Ian Goldberg. Implementation by Pat Swieskowski.
++ */
++/* __orinoco_down(dev); */
++ hermes_set_irqmask(hw, 0);
++ hermes_init(hw);
++/* __orinoco_up(dev); */
++ hermes_set_irqmask(hw, ORINOCO_INTEN);
++ /* Disable the port (if enabled), only check Port 0 */
++ if (hw->port_enabled[0]) {
++ /* Save macport 0 state */
++ err = hermes_read_wordrec(hw, USER_BAP,
++ HERMES_RID_CNFPORTTYPE,
++ &(priv->presniff_port_type));
++ if (err)
++ break;
++
++ /* Save the wepflags state */
++ err = hermes_read_wordrec(hw, USER_BAP,
++ HERMES_RID_CNFWEPFLAGS_INTERSIL,
++ &(priv->presniff_wepflags));
++ if (err)
++ break;
++ err = hermes_disable_port(hw, 0);
++ if (err)
++ break;
++ } else {
++ priv->presniff_port_type = 0;
++ }
++
++ /* Set the channel we wish to sniff */
++ if ((parms[1] > 0) && (parms[1] < 15)) {
++ word = parms[1];
++ err = hermes_write_wordrec(hw, USER_BAP,
++ HERMES_RID_CNFOWNCHANNEL,
++ word);
++ } else {
++ err = -EFAULT;
++ }
++
++ if (err)
++ break;
++
++ /* Set the port type to pIbss */
++ word = HFA384x_PORTTYPE_IBSS;
++ err = hermes_write_wordrec(hw, USER_BAP,
++ HERMES_RID_CNFPORTTYPE, word);
++ if (err)
++ break;
++
++#if 0
++ if ( (msg->keepwepflags.status == P80211ENUM_msgitem_status_data_ok) &&
++ (msg->keepwepflags.data != 1)) {
++ /* Set the wepflags for no decryption */
++ /* Orinoco doesn't like this */
++ word = HFA384x_WEPFLAGS_DISABLE_TXCRYPT |
++ HFA384x_WEPFLAGS_DISABLE_RXCRYPT;
++ err = hermes_write_wordrec(hw, USER_BAP,
++ HERMES_RID_CNFWEPFLAGS_INTERSIL,
++ word); /*won't work with the bits above */
++ }
++ if (err)
++ break;
++#endif /* 0 */
++ /* Enable the port */
++ err = hermes_enable_port(hw, 0);
++ if (err)
++ break;
++
++ /* Enable monitor mode */
++ word = HERMES_CMD_MONITOR | (HERMES_MONITOR_ENABLE << 8);
++ err = hermes_docmd_wait(hw, word, 0, NULL);
++ if (err)
++ break;
++
++ /* Set the driver state */
++ /* Do we want the prism2 header? */
++ if (parms[0] == 1)
++ dev->type = ARPHRD_IEEE80211_PRISM;
++ else
++ dev->type = ARPHRD_IEEE80211;
++ break;
++ default:
++ BUG();
++ break;
++ }
++
++ orinoco_unlock(priv, &flags);
++ return err;
++}
++
+ static int
+ orinoco_ioctl(struct net_device *dev, struct ifreq *rq, int cmd)
+ {
+@@ -3830,6 +4016,9 @@
+ { SIOCIWFIRSTPRIV + 0x7, 0,
+ IW_PRIV_TYPE_INT | IW_PRIV_SIZE_FIXED | 1,
+ "get_ibssport" },
++ { SIOCIWFIRSTPRIV + 0x8,
++ IW_PRIV_TYPE_INT | IW_PRIV_SIZE_FIXED | 2,
++ 0, "monitor" },
+ { SIOCIWLASTPRIV, 0, 0, "dump_recs" },
+ };
+
+@@ -3924,6 +4113,16 @@
+ err = orinoco_ioctl_getibssport(dev, wrq);
+ break;
+
++ case SIOCIWFIRSTPRIV + 0x8: /* set sniff (monitor) mode */
++ DEBUG(1, "%s: SIOCIWFIRSTPRIV + 0x8 (monitor)\n",
++ dev->name);
++ if (! capable(CAP_NET_ADMIN)) {
++ err = -EPERM;
++ break;
++ }
++ err = orinoco_wlansniff(dev, wrq);
++ break;
++
+ case SIOCIWLASTPRIV:
+ err = orinoco_debug_dump_recs(dev);
+ if (err)
+@@ -4171,6 +4370,191 @@
+
+ }
+
++/*----------------------------------------------------------------
++* orinoco_int_rxmonitor
++*
++* Handles monitor frames. Note that this function allocates space for
++* the FCS and sets it to 0xffffffff. The hfa384x doesn't give us the
++* FCS value but the higher layers expect it. 0xffffffff is used as a
++* flag to indicate the FCS is bogus.
++*
++* Arguments:
++* dev wlan device structure
++* rxfid received FID
++* rxdesc rx descriptor read from card in int_rx
++*
++* Side effects:
++* Allocates an skb and passes it up via the PF_PACKET interface.
++* Call context:
++* interrupt
++----------------------------------------------------------------*/
++void orinoco_int_rxmonitor(struct net_device *dev, u16 rxfid,
++ int len, struct hermes_rx_descriptor *rxdesc,
++ struct ieee802_11_hdr *hdr)
++{
++ struct orinoco_private *priv = dev->priv;
++ hermes_t *hw = &priv->hw;
++ u32 hdrlen = 0;
++ u32 datalen = 0;
++ u32 skblen = 0;
++ p80211msg_lnxind_wlansniffrm_t *msg;
++ struct net_device_stats *stats = &priv->stats;
++ u8 *datap;
++ u16 fc;
++ struct sk_buff *skb;
++
++ /* Don't forget the status, time, and data_len fields are in
++ * little-endian order */
++ /* Figure out how big the frame is */
++ fc = le16_to_cpu(hdr->frame_ctl);
++ switch (fc & IEEE802_11_FCTL_FTYPE) {
++ case IEEE802_11_FTYPE_DATA:
++ if ((fc & IEEE802_11_FCTL_TODS)
++ && (fc & IEEE802_11_FCTL_FROMDS))
++ hdrlen = WLAN_HDR_A4_LEN;
++ else
++ hdrlen = WLAN_HDR_A3_LEN;
++ datalen = len;
++ break;
++ case IEEE802_11_FTYPE_MGMT:
++ hdrlen = WLAN_HDR_A3_LEN;
++ datalen = len;
++ break;
++ case IEEE802_11_FTYPE_CTL:
++ switch (fc & IEEE802_11_FCTL_STYPE) {
++ case IEEE802_11_STYPE_PSPOLL:
++ case IEEE802_11_STYPE_RTS:
++ case IEEE802_11_STYPE_CFEND:
++ case IEEE802_11_STYPE_CFENDACK:
++ hdrlen = 16;
++ break;
++ case IEEE802_11_STYPE_CTS:
++ case IEEE802_11_STYPE_ACK:
++ hdrlen = 10;
++ break;
++ }
++ datalen = 0;
++ break;
++ default:
++ printk("unknown frm: fc=0x%04x\n", fc);
++ return;
++ }
++
++ /* Allocate an ind message+framesize skb */
++ skblen = sizeof(p80211msg_lnxind_wlansniffrm_t) +
++ hdrlen + datalen;
++
++ /* sanity check the length */
++ if ( skblen >
++ ( (sizeof(p80211msg_lnxind_wlansniffrm_t) +
++ WLAN_HDR_A4_LEN + WLAN_DATA_MAXLEN + WLAN_CRC_LEN) ) ) {
++ printk("overlen frm: len=%d\n",
++ skblen - sizeof(p80211msg_lnxind_wlansniffrm_t));
++ }
++
++ if ( (skb = dev_alloc_skb(skblen)) == NULL ) {
++ printk("alloc_skb failed trying to allocate %d bytes\n", skblen);
++ return;
++ }
++
++ /* only prepend the prism header if in the right mode */
++ if (dev->type != ARPHRD_IEEE80211_PRISM) {
++ skb_put(skb, skblen - sizeof(p80211msg_lnxind_wlansniffrm_t));
++ datap = skb->data;
++ } else {
++ skb_put(skb, skblen);
++ datap = skb->data + sizeof(p80211msg_lnxind_wlansniffrm_t);
++ msg = (p80211msg_lnxind_wlansniffrm_t*)skb->data;
++
++ /* Initialize the message members */
++ msg->msgcode = DIDmsg_lnxind_wlansniffrm;
++ msg->msglen = sizeof(p80211msg_lnxind_wlansniffrm_t);
++ strcpy(msg->devname, dev->name);
++
++ msg->hosttime.did = DIDmsg_lnxind_wlansniffrm_hosttime;
++ msg->hosttime.status = 0;
++ msg->hosttime.len = 4;
++ msg->hosttime.data = jiffies;
++
++ msg->mactime.did = DIDmsg_lnxind_wlansniffrm_mactime;
++ msg->mactime.status = 0;
++ msg->mactime.len = 4;
++ msg->mactime.data = rxdesc->time;
++
++ msg->channel.did = DIDmsg_lnxind_wlansniffrm_channel;
++ msg->channel.status = P80211ENUM_msgitem_status_no_value;
++ msg->channel.len = 4;
++ msg->channel.data = 0;
++
++ msg->rssi.did = DIDmsg_lnxind_wlansniffrm_rssi;
++ msg->rssi.status = P80211ENUM_msgitem_status_no_value;
++ msg->rssi.len = 4;
++ msg->rssi.data = 0;
++
++ msg->sq.did = DIDmsg_lnxind_wlansniffrm_sq;
++ msg->sq.status = P80211ENUM_msgitem_status_no_value;
++ msg->sq.len = 4;
++ msg->sq.data = 0;
++
++ msg->signal.did = DIDmsg_lnxind_wlansniffrm_signal;
++ msg->signal.status = 0;
++ msg->signal.len = 4;
++ msg->signal.data = rxdesc->signal;
++
++ msg->noise.did = DIDmsg_lnxind_wlansniffrm_noise;
++ msg->noise.status = 0;
++ msg->noise.len = 4;
++ msg->noise.data = rxdesc->silence;
++
++ msg->rate.did = DIDmsg_lnxind_wlansniffrm_rate;
++ msg->rate.status = 0;
++ msg->rate.len = 4;
++ msg->rate.data = rxdesc->rate / 5; /* set to 802.11 units */
++
++ msg->istx.did = DIDmsg_lnxind_wlansniffrm_istx;
++ msg->istx.status = 0;
++ msg->istx.len = 4;
++ msg->istx.data = 0;
++
++ msg->frmlen.did = DIDmsg_lnxind_wlansniffrm_frmlen;
++ msg->frmlen.status = 0;
++ msg->frmlen.len = 4;
++ msg->frmlen.data = hdrlen + datalen;
++ }
++
++ /* Copy the 802.11 header to the skb (ctl frames may be less
++ * than a full header) */
++ memcpy(datap, &(hdr->frame_ctl), hdrlen);
++
++ /* If any, copy the data from the card to the skb */
++ if (datalen > 0) {
++ hermes_bap_pread(hw, IRQ_BAP, datap + hdrlen, (datalen+1)&~1,
++ rxfid, HERMES_RX_DATA_OFF);
++
++ /* check for unencrypted stuff if WEP bit set. */
++ if (datap[1] & 0x40) /* wep set */
++ if ((datap[hdrlen] == 0xaa)
++ && (datap[hdrlen+1] == 0xaa))
++ datap[1] &= 0xbf; /* clear wep; it's the 802.2 header! */
++ }
++
++ /* pass it up via the PF_PACKET interface */
++ skb->dev = dev;
++ skb->dev->last_rx = jiffies;
++
++ skb->mac.raw = skb->data ;
++ skb->ip_summed = CHECKSUM_NONE;
++ skb->pkt_type = PACKET_OTHERHOST;
++ skb->protocol = htons(ETH_P_80211_RAW); /* XXX ETH_P_802_2? */
++
++ stats->rx_packets++;
++ stats->rx_bytes += skb->len;
++
++ netif_rx(skb);
++
++ return;
++}
++
+ /********************************************************************/
+ /* Module initialization */
+ /********************************************************************/
+diff -urN dist/orinoco-0.13e/orinoco.h orinoco-monitor/orinoco.h
+--- dist/orinoco-0.13e/orinoco.h 2003-05-12 16:22:27.000000000 +1000
++++ orinoco-monitor/orinoco.h 2003-05-13 13:27:02.000000000 +1000
+@@ -37,6 +37,16 @@
+ /* To enable debug messages */
+ //#define ORINOCO_DEBUG 3
+
++#define ETH_P_80211_RAW (ETH_P_ECONET + 1)
++
++#ifndef ARPHRD_IEEE80211
++#define ARPHRD_IEEE80211 801 /* kernel 2.4.6 */
++#endif
++
++#ifndef ARPHRD_IEEE80211_PRISM /* kernel 2.4.18 */
++#define ARPHRD_IEEE80211_PRISM 802
++#endif
++
+ #if (! defined (WIRELESS_EXT)) || (WIRELESS_EXT < 10)
+ #error "orinoco driver requires Wireless extensions v10 or later."
+ #endif /* (! defined (WIRELESS_EXT)) || (WIRELESS_EXT < 10) */
+@@ -55,6 +65,67 @@
+ HERMES_EV_INFDROP )
+
+
++#define WLAN_DEVNAMELEN_MAX 16
++
++/* message data item for INT, BOUNDEDINT, ENUMINT */
++typedef struct p80211item_uint32 {
++ u32 did;
++ u16 status;
++ u16 len;
++ u32 data;
++} __attribute__ ((packed)) p80211item_uint32_t;
++
++#define DIDmsg_lnxind_wlansniffrm 0x0041
++#define DIDmsg_lnxind_wlansniffrm_hosttime 0x1041
++#define DIDmsg_lnxind_wlansniffrm_mactime 0x2041
++#define DIDmsg_lnxind_wlansniffrm_channel 0x3041
++#define DIDmsg_lnxind_wlansniffrm_rssi 0x4041
++#define DIDmsg_lnxind_wlansniffrm_sq 0x5041
++#define DIDmsg_lnxind_wlansniffrm_signal 0x6041
++#define DIDmsg_lnxind_wlansniffrm_noise 0x7041
++#define DIDmsg_lnxind_wlansniffrm_rate 0x8041
++#define DIDmsg_lnxind_wlansniffrm_istx 0x9041
++#define DIDmsg_lnxind_wlansniffrm_frmlen 0xA041
++
++typedef struct p80211msg_lnxind_wlansniffrm {
++ u32 msgcode;
++ u32 msglen;
++ u8 devname[WLAN_DEVNAMELEN_MAX];
++ p80211item_uint32_t hosttime;
++ p80211item_uint32_t mactime;
++ p80211item_uint32_t channel;
++ p80211item_uint32_t rssi;
++ p80211item_uint32_t sq;
++ p80211item_uint32_t signal;
++ p80211item_uint32_t noise;
++ p80211item_uint32_t rate;
++ p80211item_uint32_t istx;
++ p80211item_uint32_t frmlen;
++} __attribute__ ((packed)) p80211msg_lnxind_wlansniffrm_t;
++
++#define P80211ENUM_msgitem_status_data_ok 0
++#define P80211ENUM_msgitem_status_no_value 1
++#define P80211ENUM_msgitem_status_invalid_itemname 2
++#define P80211ENUM_msgitem_status_invalid_itemdata 3
++#define P80211ENUM_msgitem_status_missing_itemdata 4
++#define P80211ENUM_msgitem_status_incomplete_itemdata 5
++#define P80211ENUM_msgitem_status_invalid_msg_did 6
++#define P80211ENUM_msgitem_status_invalid_mib_did 7
++#define P80211ENUM_msgitem_status_missing_conv_func 8
++#define P80211ENUM_msgitem_status_string_too_long 9
++#define P80211ENUM_msgitem_status_data_out_of_range 10
++#define P80211ENUM_msgitem_status_string_too_short 11
++#define P80211ENUM_msgitem_status_missing_valid_func 12
++#define P80211ENUM_msgitem_status_unknown 13
++#define P80211ENUM_msgitem_status_invalid_did 14
++#define P80211ENUM_msgitem_status_missing_print_func 15
++
++/*--- Sizes -----------------------------------------------*/
++#define WLAN_CRC_LEN 4
++#define WLAN_HDR_A3_LEN 24
++#define WLAN_HDR_A4_LEN 30
++#define WLAN_DATA_MAXLEN 2312
++
+ struct orinoco_private {
+ void *card; /* Pointer to card dependent structure */
+ int (*hard_reset)(struct orinoco_private *);
+@@ -116,6 +187,9 @@
+ /* Configuration dependent variables */
+ int port_type, createibss;
+ int promiscuous, mc_count;
++
++ u16 presniff_port_type;
++ u16 presniff_wepflags;
+ };
+
+ #ifdef ORINOCO_DEBUG
diff --git a/orinoco/orinoco-modules-0.13e/shmoo-monitor-0.13e.patch b/orinoco/orinoco-modules-0.13e/shmoo-monitor-0.13e.patch
index e69de29bb2..fe9693f69c 100644
--- a/orinoco/orinoco-modules-0.13e/shmoo-monitor-0.13e.patch
+++ b/orinoco/orinoco-modules-0.13e/shmoo-monitor-0.13e.patch
@@ -0,0 +1,797 @@
+diff -aur orinoco-0.13e/hermes.c orinoco-0.13e-patched/hermes.c
+--- orinoco-0.13e/hermes.c 2003-05-11 23:22:27.000000000 -0700
++++ orinoco-0.13e-patched/hermes.c 2003-08-07 04:16:04.000000000 -0700
+@@ -183,6 +183,10 @@
+ if (err)
+ return err;
+
++ for ( k = 0; k < HERMES_NUMPORTS_MAX; k++) {
++ hw->port_enabled[k] = 0;
++ }
++
+ reg = hermes_read_regn(hw, EVSTAT);
+ k = CMD_INIT_TIMEOUT;
+ while ( (! (reg & HERMES_EV_CMD)) && k) {
+diff -aur orinoco-0.13e/hermes.h orinoco-0.13e-patched/hermes.h
+--- orinoco-0.13e/hermes.h 2003-05-11 23:22:27.000000000 -0700
++++ orinoco-0.13e-patched/hermes.h 2003-08-07 04:16:04.000000000 -0700
+@@ -33,6 +33,10 @@
+ #include <linux/if_ether.h>
+ #include <asm/byteorder.h>
+
++#define HFA384x_PORTTYPE_IBSS ((uint16_t)3)
++#define HFA384x_WEPFLAGS_DISABLE_TXCRYPT (0x10)
++#define HFA384x_WEPFLAGS_DISABLE_RXCRYPT (0x80)
++
+ /*
+ * Limits and constants
+ */
+@@ -149,6 +153,38 @@
+ #define HERMES_MONITOR_DISABLE (0x000f)
+
+ /*
++ * Configuration RIDs
++ */
++
++#define HERMES_RID_CNF_PORTTYPE (0xfc00)
++#define HERMES_RID_CNF_CHANNEL (0xfc03)
++#define HERMES_RID_CNF_PRISM2_WEP_ON (0xfc28)
++
++/*-- Status Fields --*/
++#define HERMES_RXSTATUS_MSGTYPE (0xE000)
++#define HERMES_RXSTATUS_MACPORT (0x0700)
++#define HERMES_RXSTATUS_UNDECR (0x0002)
++#define HERMES_RXSTATUS_FCSERR (0x0001)
++
++/*--------------------------------------------------------------------
++Communication Frames: Test/Get/Set Field Values for Receive Frames
++--------------------------------------------------------------------*/
++#define HERMES_RXSTATUS_MSGTYPE_GET(value) (((value) & HERMES_RXSTATUS_MSGTYPE) >> 13)
++#define HERMES_RXSTATUS_MSGTYPE_SET(value) ((value) << 13)
++#define HERMES_RXSTATUS_MACPORT_GET(value) (((value) & HERMES_RXSTATUS_MACPORT) >> 8)
++#define HERMES_RXSTATUS_MACPORT_SET(value) ((value) << 8)
++#define HERMES_RXSTATUS_ISUNDECR(value) ((value) & HERMES_RXSTATUS_UNDECR)
++#define HERMES_RXSTATUS_ISFCSERR(value) ((value) & HERMES_RXSTATUS_FCSERR)
++
++/*--------------------------------------------------------------------
++Communication Frames: Field Masks for Receive Frames
++--------------------------------------------------------------------*/
++/*-- Offsets --------*/
++#define HERMES_RX_DATA_LEN_OFF (44)
++#define HERMES_RX_80211HDR_OFF (14)
++#define HERMES_RX_DATA_OFF (60)
++
++/*
+ * Frame structures and constants
+ */
+
+@@ -286,6 +322,7 @@
+ #define HERMES_32BIT_REGSPACING 1
+
+ u16 inten; /* Which interrupts should be enabled? */
++ uint8_t port_enabled[HERMES_NUMPORTS_MAX];
+
+ #ifdef HERMES_DEBUG_BUFFER
+ struct hermes_debug_entry dbuf[HERMES_DEBUG_BUFSIZE];
+@@ -339,12 +376,14 @@
+
+ static inline int hermes_enable_port(hermes_t *hw, int port)
+ {
++ hw->port_enabled[port] = 1;
+ return hermes_docmd_wait(hw, HERMES_CMD_ENABLE | (port << 8),
+ 0, NULL);
+ }
+
+ static inline int hermes_disable_port(hermes_t *hw, int port)
+ {
++ hw->port_enabled[port] = 0;
+ return hermes_docmd_wait(hw, HERMES_CMD_DISABLE | (port << 8),
+ 0, NULL);
+ }
+diff -aur orinoco-0.13e/orinoco.c orinoco-0.13e-patched/orinoco.c
+--- orinoco-0.13e/orinoco.c 2003-05-11 23:22:27.000000000 -0700
++++ orinoco-0.13e-patched/orinoco.c 2003-08-07 04:16:04.000000000 -0700
+@@ -1673,6 +1673,7 @@
+ struct header_struct hdr;
+ struct ethhdr *eh;
+ int err;
++ struct ieee802_11_hdr hdr80211;
+
+ rxfid = hermes_read_regn(hw, RXFID);
+
+@@ -1689,6 +1690,7 @@
+
+ if (status & HERMES_RXSTAT_ERR) {
+ if (status & HERMES_RXSTAT_UNDECRYPTABLE) {
++ if (dev->type != ARPHRD_ETHER) goto sniffing;
+ wstats->discard.code++;
+ DEBUG(1, "%s: Undecryptable frame on Rx. Frame dropped.\n",
+ dev->name);
+@@ -1699,7 +1701,7 @@
+ stats->rx_errors++;
+ goto drop;
+ }
+-
++sniffing:
+ /* For now we ignore the 802.11 header completely, assuming
+ that the card's firmware has handled anything vital */
+
+@@ -1730,6 +1732,11 @@
+ goto drop;
+ }
+
++ /* Now handle frame based on port# */
++ switch( HERMES_RXSTATUS_MACPORT_GET(status) )
++ {
++ case 0:
++
+ /* We need space for the packet data itself, plus an ethernet
+ header, plus 2 bytes so we can align the IP header on a
+ 32bit boundary, plus 1 byte so we can read in odd length
+@@ -1804,6 +1811,26 @@
+
+ return;
+
++ case 7:
++ if ( ! HERMES_RXSTATUS_ISFCSERR(status) ) {
++ if (hermes_bap_pread(hw, IRQ_BAP, &hdr80211, sizeof(hdr80211),
++ rxfid, HERMES_RX_80211HDR_OFF)) {
++ stats->rx_errors++;
++ }
++ else {
++ /* Copy to wlansnif skb */
++ orinoco_int_rxmonitor( priv, rxfid, length, &desc, &hdr80211);
++ }
++ } else {