Linux Audio

Check our new training course

Loading...
v4.6
   1/*======================================================================
   2
   3    Aironet driver for 4500 and 4800 series cards
   4
   5    This code is released under both the GPL version 2 and BSD licenses.
   6    Either license may be used.  The respective licenses are found at
   7    the end of this file.
   8
   9    This code was developed by Benjamin Reed <breed@users.sourceforge.net>
  10    including portions of which come from the Aironet PC4500
  11    Developer's Reference Manual and used with permission.  Copyright
  12    (C) 1999 Benjamin Reed.  All Rights Reserved.  Permission to use
  13    code in the Developer's manual was granted for this driver by
  14    Aironet.  Major code contributions were received from Javier Achirica
  15    <achirica@users.sourceforge.net> and Jean Tourrilhes <jt@hpl.hp.com>.
  16    Code was also integrated from the Cisco Aironet driver for Linux.
  17    Support for MPI350 cards was added by Fabrice Bellet
  18    <fabrice@bellet.info>.
  19
  20======================================================================*/
  21
  22#include <linux/err.h>
  23#include <linux/init.h>
  24
  25#include <linux/kernel.h>
  26#include <linux/module.h>
  27#include <linux/proc_fs.h>
  28
  29#include <linux/sched.h>
  30#include <linux/ptrace.h>
  31#include <linux/slab.h>
  32#include <linux/string.h>
  33#include <linux/timer.h>
  34#include <linux/interrupt.h>
  35#include <linux/in.h>
  36#include <linux/bitops.h>
  37#include <linux/scatterlist.h>
  38#include <linux/crypto.h>
  39#include <linux/io.h>
  40#include <asm/unaligned.h>
  41
  42#include <linux/netdevice.h>
  43#include <linux/etherdevice.h>
  44#include <linux/skbuff.h>
  45#include <linux/if_arp.h>
  46#include <linux/ioport.h>
  47#include <linux/pci.h>
  48#include <linux/uaccess.h>
  49#include <linux/kthread.h>
  50#include <linux/freezer.h>
  51
 
 
 
  52#include <net/cfg80211.h>
  53#include <net/iw_handler.h>
  54
  55#include "airo.h"
  56
  57#define DRV_NAME "airo"
  58
  59#ifdef CONFIG_PCI
  60static const struct pci_device_id card_ids[] = {
  61	{ 0x14b9, 1, PCI_ANY_ID, PCI_ANY_ID, },
  62	{ 0x14b9, 0x4500, PCI_ANY_ID, PCI_ANY_ID },
  63	{ 0x14b9, 0x4800, PCI_ANY_ID, PCI_ANY_ID, },
  64	{ 0x14b9, 0x0340, PCI_ANY_ID, PCI_ANY_ID, },
  65	{ 0x14b9, 0x0350, PCI_ANY_ID, PCI_ANY_ID, },
  66	{ 0x14b9, 0x5000, PCI_ANY_ID, PCI_ANY_ID, },
  67	{ 0x14b9, 0xa504, PCI_ANY_ID, PCI_ANY_ID, },
  68	{ 0, }
  69};
  70MODULE_DEVICE_TABLE(pci, card_ids);
  71
  72static int airo_pci_probe(struct pci_dev *, const struct pci_device_id *);
  73static void airo_pci_remove(struct pci_dev *);
  74static int airo_pci_suspend(struct pci_dev *pdev, pm_message_t state);
  75static int airo_pci_resume(struct pci_dev *pdev);
 
 
 
 
  76
  77static struct pci_driver airo_driver = {
  78	.name     = DRV_NAME,
  79	.id_table = card_ids,
  80	.probe    = airo_pci_probe,
  81	.remove   = airo_pci_remove,
  82	.suspend  = airo_pci_suspend,
  83	.resume   = airo_pci_resume,
  84};
  85#endif /* CONFIG_PCI */
  86
  87/* Include Wireless Extension definition and check version - Jean II */
  88#include <linux/wireless.h>
  89#define WIRELESS_SPY		/* enable iwspy support */
  90
  91#define CISCO_EXT		/* enable Cisco extensions */
  92#ifdef CISCO_EXT
  93#include <linux/delay.h>
  94#endif
  95
  96/* Hack to do some power saving */
  97#define POWER_ON_DOWN
  98
  99/* As you can see this list is HUGH!
 100   I really don't know what a lot of these counts are about, but they
 101   are all here for completeness.  If the IGNLABEL macro is put in
 102   infront of the label, that statistic will not be included in the list
 103   of statistics in the /proc filesystem */
 104
 105#define IGNLABEL(comment) NULL
 106static const char *statsLabels[] = {
 107	"RxOverrun",
 108	IGNLABEL("RxPlcpCrcErr"),
 109	IGNLABEL("RxPlcpFormatErr"),
 110	IGNLABEL("RxPlcpLengthErr"),
 111	"RxMacCrcErr",
 112	"RxMacCrcOk",
 113	"RxWepErr",
 114	"RxWepOk",
 115	"RetryLong",
 116	"RetryShort",
 117	"MaxRetries",
 118	"NoAck",
 119	"NoCts",
 120	"RxAck",
 121	"RxCts",
 122	"TxAck",
 123	"TxRts",
 124	"TxCts",
 125	"TxMc",
 126	"TxBc",
 127	"TxUcFrags",
 128	"TxUcPackets",
 129	"TxBeacon",
 130	"RxBeacon",
 131	"TxSinColl",
 132	"TxMulColl",
 133	"DefersNo",
 134	"DefersProt",
 135	"DefersEngy",
 136	"DupFram",
 137	"RxFragDisc",
 138	"TxAged",
 139	"RxAged",
 140	"LostSync-MaxRetry",
 141	"LostSync-MissedBeacons",
 142	"LostSync-ArlExceeded",
 143	"LostSync-Deauth",
 144	"LostSync-Disassoced",
 145	"LostSync-TsfTiming",
 146	"HostTxMc",
 147	"HostTxBc",
 148	"HostTxUc",
 149	"HostTxFail",
 150	"HostRxMc",
 151	"HostRxBc",
 152	"HostRxUc",
 153	"HostRxDiscard",
 154	IGNLABEL("HmacTxMc"),
 155	IGNLABEL("HmacTxBc"),
 156	IGNLABEL("HmacTxUc"),
 157	IGNLABEL("HmacTxFail"),
 158	IGNLABEL("HmacRxMc"),
 159	IGNLABEL("HmacRxBc"),
 160	IGNLABEL("HmacRxUc"),
 161	IGNLABEL("HmacRxDiscard"),
 162	IGNLABEL("HmacRxAccepted"),
 163	"SsidMismatch",
 164	"ApMismatch",
 165	"RatesMismatch",
 166	"AuthReject",
 167	"AuthTimeout",
 168	"AssocReject",
 169	"AssocTimeout",
 170	IGNLABEL("ReasonOutsideTable"),
 171	IGNLABEL("ReasonStatus1"),
 172	IGNLABEL("ReasonStatus2"),
 173	IGNLABEL("ReasonStatus3"),
 174	IGNLABEL("ReasonStatus4"),
 175	IGNLABEL("ReasonStatus5"),
 176	IGNLABEL("ReasonStatus6"),
 177	IGNLABEL("ReasonStatus7"),
 178	IGNLABEL("ReasonStatus8"),
 179	IGNLABEL("ReasonStatus9"),
 180	IGNLABEL("ReasonStatus10"),
 181	IGNLABEL("ReasonStatus11"),
 182	IGNLABEL("ReasonStatus12"),
 183	IGNLABEL("ReasonStatus13"),
 184	IGNLABEL("ReasonStatus14"),
 185	IGNLABEL("ReasonStatus15"),
 186	IGNLABEL("ReasonStatus16"),
 187	IGNLABEL("ReasonStatus17"),
 188	IGNLABEL("ReasonStatus18"),
 189	IGNLABEL("ReasonStatus19"),
 190	"RxMan",
 191	"TxMan",
 192	"RxRefresh",
 193	"TxRefresh",
 194	"RxPoll",
 195	"TxPoll",
 196	"HostRetries",
 197	"LostSync-HostReq",
 198	"HostTxBytes",
 199	"HostRxBytes",
 200	"ElapsedUsec",
 201	"ElapsedSec",
 202	"LostSyncBetterAP",
 203	"PrivacyMismatch",
 204	"Jammed",
 205	"DiscRxNotWepped",
 206	"PhyEleMismatch",
 207	(char*)-1 };
 208#ifndef RUN_AT
 209#define RUN_AT(x) (jiffies+(x))
 210#endif
 211
 212
 213/* These variables are for insmod, since it seems that the rates
 214   can only be set in setup_card.  Rates should be a comma separated
 215   (no spaces) list of rates (up to 8). */
 216
 217static int rates[8];
 218static char *ssids[3];
 219
 220static int io[4];
 221static int irq[4];
 222
 223static
 224int maxencrypt /* = 0 */; /* The highest rate that the card can encrypt at.
 225		       0 means no limit.  For old cards this was 4 */
 226
 227static int auto_wep /* = 0 */; /* If set, it tries to figure out the wep mode */
 228static int aux_bap /* = 0 */; /* Checks to see if the aux ports are needed to read
 229		    the bap, needed on some older cards and buses. */
 230static int adhoc;
 231
 232static int probe = 1;
 233
 234static kuid_t proc_kuid;
 235static int proc_uid /* = 0 */;
 236
 237static kgid_t proc_kgid;
 238static int proc_gid /* = 0 */;
 239
 240static int airo_perm = 0555;
 241
 242static int proc_perm = 0644;
 243
 244MODULE_AUTHOR("Benjamin Reed");
 245MODULE_DESCRIPTION("Support for Cisco/Aironet 802.11 wireless ethernet cards.  "
 246		   "Direct support for ISA/PCI/MPI cards and support for PCMCIA when used with airo_cs.");
 247MODULE_LICENSE("Dual BSD/GPL");
 248MODULE_SUPPORTED_DEVICE("Aironet 4500, 4800 and Cisco 340/350");
 249module_param_array(io, int, NULL, 0);
 250module_param_array(irq, int, NULL, 0);
 251module_param_array(rates, int, NULL, 0);
 252module_param_array(ssids, charp, NULL, 0);
 253module_param(auto_wep, int, 0);
 254MODULE_PARM_DESC(auto_wep,
 255		 "If non-zero, the driver will keep looping through the authentication options until an association is made.  "
 256		 "The value of auto_wep is number of the wep keys to check.  "
 257		 "A value of 2 will try using the key at index 0 and index 1.");
 258module_param(aux_bap, int, 0);
 259MODULE_PARM_DESC(aux_bap,
 260		 "If non-zero, the driver will switch into a mode that seems to work better for older cards with some older buses.  "
 261		 "Before switching it checks that the switch is needed.");
 262module_param(maxencrypt, int, 0);
 263MODULE_PARM_DESC(maxencrypt,
 264		 "The maximum speed that the card can do encryption.  "
 265		 "Units are in 512kbs.  "
 266		 "Zero (default) means there is no limit.  "
 267		 "Older cards used to be limited to 2mbs (4).");
 268module_param(adhoc, int, 0);
 269MODULE_PARM_DESC(adhoc, "If non-zero, the card will start in adhoc mode.");
 270module_param(probe, int, 0);
 271MODULE_PARM_DESC(probe, "If zero, the driver won't start the card.");
 272
 273module_param(proc_uid, int, 0);
 274MODULE_PARM_DESC(proc_uid, "The uid that the /proc files will belong to.");
 275module_param(proc_gid, int, 0);
 276MODULE_PARM_DESC(proc_gid, "The gid that the /proc files will belong to.");
 277module_param(airo_perm, int, 0);
 278MODULE_PARM_DESC(airo_perm, "The permission bits of /proc/[driver/]aironet.");
 279module_param(proc_perm, int, 0);
 280MODULE_PARM_DESC(proc_perm, "The permission bits of the files in /proc");
 281
 282/* This is a kind of sloppy hack to get this information to OUT4500 and
 283   IN4500.  I would be extremely interested in the situation where this
 284   doesn't work though!!! */
 285static int do8bitIO /* = 0 */;
 286
 287/* Return codes */
 288#define SUCCESS 0
 289#define ERROR -1
 290#define NO_PACKET -2
 291
 292/* Commands */
 293#define NOP2		0x0000
 294#define MAC_ENABLE	0x0001
 295#define MAC_DISABLE	0x0002
 296#define CMD_LOSE_SYNC	0x0003 /* Not sure what this does... */
 297#define CMD_SOFTRESET	0x0004
 298#define HOSTSLEEP	0x0005
 299#define CMD_MAGIC_PKT	0x0006
 300#define CMD_SETWAKEMASK	0x0007
 301#define CMD_READCFG	0x0008
 302#define CMD_SETMODE	0x0009
 303#define CMD_ALLOCATETX	0x000a
 304#define CMD_TRANSMIT	0x000b
 305#define CMD_DEALLOCATETX 0x000c
 306#define NOP		0x0010
 307#define CMD_WORKAROUND	0x0011
 308#define CMD_ALLOCATEAUX 0x0020
 309#define CMD_ACCESS	0x0021
 310#define CMD_PCIBAP	0x0022
 311#define CMD_PCIAUX	0x0023
 312#define CMD_ALLOCBUF	0x0028
 313#define CMD_GETTLV	0x0029
 314#define CMD_PUTTLV	0x002a
 315#define CMD_DELTLV	0x002b
 316#define CMD_FINDNEXTTLV	0x002c
 317#define CMD_PSPNODES	0x0030
 318#define CMD_SETCW	0x0031    
 319#define CMD_SETPCF	0x0032    
 320#define CMD_SETPHYREG	0x003e
 321#define CMD_TXTEST	0x003f
 322#define MAC_ENABLETX	0x0101
 323#define CMD_LISTBSS	0x0103
 324#define CMD_SAVECFG	0x0108
 325#define CMD_ENABLEAUX	0x0111
 326#define CMD_WRITERID	0x0121
 327#define CMD_USEPSPNODES	0x0130
 328#define MAC_ENABLERX	0x0201
 329
 330/* Command errors */
 331#define ERROR_QUALIF 0x00
 332#define ERROR_ILLCMD 0x01
 333#define ERROR_ILLFMT 0x02
 334#define ERROR_INVFID 0x03
 335#define ERROR_INVRID 0x04
 336#define ERROR_LARGE 0x05
 337#define ERROR_NDISABL 0x06
 338#define ERROR_ALLOCBSY 0x07
 339#define ERROR_NORD 0x0B
 340#define ERROR_NOWR 0x0C
 341#define ERROR_INVFIDTX 0x0D
 342#define ERROR_TESTACT 0x0E
 343#define ERROR_TAGNFND 0x12
 344#define ERROR_DECODE 0x20
 345#define ERROR_DESCUNAV 0x21
 346#define ERROR_BADLEN 0x22
 347#define ERROR_MODE 0x80
 348#define ERROR_HOP 0x81
 349#define ERROR_BINTER 0x82
 350#define ERROR_RXMODE 0x83
 351#define ERROR_MACADDR 0x84
 352#define ERROR_RATES 0x85
 353#define ERROR_ORDER 0x86
 354#define ERROR_SCAN 0x87
 355#define ERROR_AUTH 0x88
 356#define ERROR_PSMODE 0x89
 357#define ERROR_RTYPE 0x8A
 358#define ERROR_DIVER 0x8B
 359#define ERROR_SSID 0x8C
 360#define ERROR_APLIST 0x8D
 361#define ERROR_AUTOWAKE 0x8E
 362#define ERROR_LEAP 0x8F
 363
 364/* Registers */
 365#define COMMAND 0x00
 366#define PARAM0 0x02
 367#define PARAM1 0x04
 368#define PARAM2 0x06
 369#define STATUS 0x08
 370#define RESP0 0x0a
 371#define RESP1 0x0c
 372#define RESP2 0x0e
 373#define LINKSTAT 0x10
 374#define SELECT0 0x18
 375#define OFFSET0 0x1c
 376#define RXFID 0x20
 377#define TXALLOCFID 0x22
 378#define TXCOMPLFID 0x24
 379#define DATA0 0x36
 380#define EVSTAT 0x30
 381#define EVINTEN 0x32
 382#define EVACK 0x34
 383#define SWS0 0x28
 384#define SWS1 0x2a
 385#define SWS2 0x2c
 386#define SWS3 0x2e
 387#define AUXPAGE 0x3A
 388#define AUXOFF 0x3C
 389#define AUXDATA 0x3E
 390
 391#define FID_TX 1
 392#define FID_RX 2
 393/* Offset into aux memory for descriptors */
 394#define AUX_OFFSET 0x800
 395/* Size of allocated packets */
 396#define PKTSIZE 1840
 397#define RIDSIZE 2048
 398/* Size of the transmit queue */
 399#define MAXTXQ 64
 400
 401/* BAP selectors */
 402#define BAP0 0 /* Used for receiving packets */
 403#define BAP1 2 /* Used for xmiting packets and working with RIDS */
 404
 405/* Flags */
 406#define COMMAND_BUSY 0x8000
 407
 408#define BAP_BUSY 0x8000
 409#define BAP_ERR 0x4000
 410#define BAP_DONE 0x2000
 411
 412#define PROMISC 0xffff
 413#define NOPROMISC 0x0000
 414
 415#define EV_CMD 0x10
 416#define EV_CLEARCOMMANDBUSY 0x4000
 417#define EV_RX 0x01
 418#define EV_TX 0x02
 419#define EV_TXEXC 0x04
 420#define EV_ALLOC 0x08
 421#define EV_LINK 0x80
 422#define EV_AWAKE 0x100
 423#define EV_TXCPY 0x400
 424#define EV_UNKNOWN 0x800
 425#define EV_MIC 0x1000 /* Message Integrity Check Interrupt */
 426#define EV_AWAKEN 0x2000
 427#define STATUS_INTS (EV_AWAKE|EV_LINK|EV_TXEXC|EV_TX|EV_TXCPY|EV_RX|EV_MIC)
 428
 429#ifdef CHECK_UNKNOWN_INTS
 430#define IGNORE_INTS ( EV_CMD | EV_UNKNOWN)
 431#else
 432#define IGNORE_INTS (~STATUS_INTS)
 433#endif
 434
 435/* RID TYPES */
 436#define RID_RW 0x20
 437
 438/* The RIDs */
 439#define RID_CAPABILITIES 0xFF00
 440#define RID_APINFO     0xFF01
 441#define RID_RADIOINFO  0xFF02
 442#define RID_UNKNOWN3   0xFF03
 443#define RID_RSSI       0xFF04
 444#define RID_CONFIG     0xFF10
 445#define RID_SSID       0xFF11
 446#define RID_APLIST     0xFF12
 447#define RID_DRVNAME    0xFF13
 448#define RID_ETHERENCAP 0xFF14
 449#define RID_WEP_TEMP   0xFF15
 450#define RID_WEP_PERM   0xFF16
 451#define RID_MODULATION 0xFF17
 452#define RID_OPTIONS    0xFF18
 453#define RID_ACTUALCONFIG 0xFF20 /*readonly*/
 454#define RID_FACTORYCONFIG 0xFF21
 455#define RID_UNKNOWN22  0xFF22
 456#define RID_LEAPUSERNAME 0xFF23
 457#define RID_LEAPPASSWORD 0xFF24
 458#define RID_STATUS     0xFF50
 459#define RID_BEACON_HST 0xFF51
 460#define RID_BUSY_HST   0xFF52
 461#define RID_RETRIES_HST 0xFF53
 462#define RID_UNKNOWN54  0xFF54
 463#define RID_UNKNOWN55  0xFF55
 464#define RID_UNKNOWN56  0xFF56
 465#define RID_MIC        0xFF57
 466#define RID_STATS16    0xFF60
 467#define RID_STATS16DELTA 0xFF61
 468#define RID_STATS16DELTACLEAR 0xFF62
 469#define RID_STATS      0xFF68
 470#define RID_STATSDELTA 0xFF69
 471#define RID_STATSDELTACLEAR 0xFF6A
 472#define RID_ECHOTEST_RID 0xFF70
 473#define RID_ECHOTEST_RESULTS 0xFF71
 474#define RID_BSSLISTFIRST 0xFF72
 475#define RID_BSSLISTNEXT  0xFF73
 476#define RID_WPA_BSSLISTFIRST 0xFF74
 477#define RID_WPA_BSSLISTNEXT  0xFF75
 478
 479typedef struct {
 480	u16 cmd;
 481	u16 parm0;
 482	u16 parm1;
 483	u16 parm2;
 484} Cmd;
 485
 486typedef struct {
 487	u16 status;
 488	u16 rsp0;
 489	u16 rsp1;
 490	u16 rsp2;
 491} Resp;
 492
 493/*
 494 * Rids and endian-ness:  The Rids will always be in cpu endian, since
 495 * this all the patches from the big-endian guys end up doing that.
 496 * so all rid access should use the read/writeXXXRid routines.
 497 */
 498
 499/* This structure came from an email sent to me from an engineer at
 500   aironet for inclusion into this driver */
 501typedef struct WepKeyRid WepKeyRid;
 502struct WepKeyRid {
 503	__le16 len;
 504	__le16 kindex;
 505	u8 mac[ETH_ALEN];
 506	__le16 klen;
 507	u8 key[16];
 508} __packed;
 509
 510/* These structures are from the Aironet's PC4500 Developers Manual */
 511typedef struct Ssid Ssid;
 512struct Ssid {
 513	__le16 len;
 514	u8 ssid[32];
 515} __packed;
 516
 517typedef struct SsidRid SsidRid;
 518struct SsidRid {
 519	__le16 len;
 520	Ssid ssids[3];
 521} __packed;
 522
 523typedef struct ModulationRid ModulationRid;
 524struct ModulationRid {
 525        __le16 len;
 526        __le16 modulation;
 527#define MOD_DEFAULT cpu_to_le16(0)
 528#define MOD_CCK cpu_to_le16(1)
 529#define MOD_MOK cpu_to_le16(2)
 530} __packed;
 531
 532typedef struct ConfigRid ConfigRid;
 533struct ConfigRid {
 534	__le16 len; /* sizeof(ConfigRid) */
 535	__le16 opmode; /* operating mode */
 536#define MODE_STA_IBSS cpu_to_le16(0)
 537#define MODE_STA_ESS cpu_to_le16(1)
 538#define MODE_AP cpu_to_le16(2)
 539#define MODE_AP_RPTR cpu_to_le16(3)
 540#define MODE_CFG_MASK cpu_to_le16(0xff)
 541#define MODE_ETHERNET_HOST cpu_to_le16(0<<8) /* rx payloads converted */
 542#define MODE_LLC_HOST cpu_to_le16(1<<8) /* rx payloads left as is */
 543#define MODE_AIRONET_EXTEND cpu_to_le16(1<<9) /* enable Aironet extenstions */
 544#define MODE_AP_INTERFACE cpu_to_le16(1<<10) /* enable ap interface extensions */
 545#define MODE_ANTENNA_ALIGN cpu_to_le16(1<<11) /* enable antenna alignment */
 546#define MODE_ETHER_LLC cpu_to_le16(1<<12) /* enable ethernet LLC */
 547#define MODE_LEAF_NODE cpu_to_le16(1<<13) /* enable leaf node bridge */
 548#define MODE_CF_POLLABLE cpu_to_le16(1<<14) /* enable CF pollable */
 549#define MODE_MIC cpu_to_le16(1<<15) /* enable MIC */
 550	__le16 rmode; /* receive mode */
 551#define RXMODE_BC_MC_ADDR cpu_to_le16(0)
 552#define RXMODE_BC_ADDR cpu_to_le16(1) /* ignore multicasts */
 553#define RXMODE_ADDR cpu_to_le16(2) /* ignore multicast and broadcast */
 554#define RXMODE_RFMON cpu_to_le16(3) /* wireless monitor mode */
 555#define RXMODE_RFMON_ANYBSS cpu_to_le16(4)
 556#define RXMODE_LANMON cpu_to_le16(5) /* lan style monitor -- data packets only */
 557#define RXMODE_MASK cpu_to_le16(255)
 558#define RXMODE_DISABLE_802_3_HEADER cpu_to_le16(1<<8) /* disables 802.3 header on rx */
 559#define RXMODE_FULL_MASK (RXMODE_MASK | RXMODE_DISABLE_802_3_HEADER)
 560#define RXMODE_NORMALIZED_RSSI cpu_to_le16(1<<9) /* return normalized RSSI */
 561	__le16 fragThresh;
 562	__le16 rtsThres;
 563	u8 macAddr[ETH_ALEN];
 564	u8 rates[8];
 565	__le16 shortRetryLimit;
 566	__le16 longRetryLimit;
 567	__le16 txLifetime; /* in kusec */
 568	__le16 rxLifetime; /* in kusec */
 569	__le16 stationary;
 570	__le16 ordering;
 571	__le16 u16deviceType; /* for overriding device type */
 572	__le16 cfpRate;
 573	__le16 cfpDuration;
 574	__le16 _reserved1[3];
 575	/*---------- Scanning/Associating ----------*/
 576	__le16 scanMode;
 577#define SCANMODE_ACTIVE cpu_to_le16(0)
 578#define SCANMODE_PASSIVE cpu_to_le16(1)
 579#define SCANMODE_AIROSCAN cpu_to_le16(2)
 580	__le16 probeDelay; /* in kusec */
 581	__le16 probeEnergyTimeout; /* in kusec */
 582        __le16 probeResponseTimeout;
 583	__le16 beaconListenTimeout;
 584	__le16 joinNetTimeout;
 585	__le16 authTimeout;
 586	__le16 authType;
 587#define AUTH_OPEN cpu_to_le16(0x1)
 588#define AUTH_ENCRYPT cpu_to_le16(0x101)
 589#define AUTH_SHAREDKEY cpu_to_le16(0x102)
 590#define AUTH_ALLOW_UNENCRYPTED cpu_to_le16(0x200)
 591	__le16 associationTimeout;
 592	__le16 specifiedApTimeout;
 593	__le16 offlineScanInterval;
 594	__le16 offlineScanDuration;
 595	__le16 linkLossDelay;
 596	__le16 maxBeaconLostTime;
 597	__le16 refreshInterval;
 598#define DISABLE_REFRESH cpu_to_le16(0xFFFF)
 599	__le16 _reserved1a[1];
 600	/*---------- Power save operation ----------*/
 601	__le16 powerSaveMode;
 602#define POWERSAVE_CAM cpu_to_le16(0)
 603#define POWERSAVE_PSP cpu_to_le16(1)
 604#define POWERSAVE_PSPCAM cpu_to_le16(2)
 605	__le16 sleepForDtims;
 606	__le16 listenInterval;
 607	__le16 fastListenInterval;
 608	__le16 listenDecay;
 609	__le16 fastListenDelay;
 610	__le16 _reserved2[2];
 611	/*---------- Ap/Ibss config items ----------*/
 612	__le16 beaconPeriod;
 613	__le16 atimDuration;
 614	__le16 hopPeriod;
 615	__le16 channelSet;
 616	__le16 channel;
 617	__le16 dtimPeriod;
 618	__le16 bridgeDistance;
 619	__le16 radioID;
 620	/*---------- Radio configuration ----------*/
 621	__le16 radioType;
 622#define RADIOTYPE_DEFAULT cpu_to_le16(0)
 623#define RADIOTYPE_802_11 cpu_to_le16(1)
 624#define RADIOTYPE_LEGACY cpu_to_le16(2)
 625	u8 rxDiversity;
 626	u8 txDiversity;
 627	__le16 txPower;
 628#define TXPOWER_DEFAULT 0
 629	__le16 rssiThreshold;
 630#define RSSI_DEFAULT 0
 631        __le16 modulation;
 632#define PREAMBLE_AUTO cpu_to_le16(0)
 633#define PREAMBLE_LONG cpu_to_le16(1)
 634#define PREAMBLE_SHORT cpu_to_le16(2)
 635	__le16 preamble;
 636	__le16 homeProduct;
 637	__le16 radioSpecific;
 638	/*---------- Aironet Extensions ----------*/
 639	u8 nodeName[16];
 640	__le16 arlThreshold;
 641	__le16 arlDecay;
 642	__le16 arlDelay;
 643	__le16 _reserved4[1];
 644	/*---------- Aironet Extensions ----------*/
 645	u8 magicAction;
 646#define MAGIC_ACTION_STSCHG 1
 647#define MAGIC_ACTION_RESUME 2
 648#define MAGIC_IGNORE_MCAST (1<<8)
 649#define MAGIC_IGNORE_BCAST (1<<9)
 650#define MAGIC_SWITCH_TO_PSP (0<<10)
 651#define MAGIC_STAY_IN_CAM (1<<10)
 652	u8 magicControl;
 653	__le16 autoWake;
 654} __packed;
 655
 656typedef struct StatusRid StatusRid;
 657struct StatusRid {
 658	__le16 len;
 659	u8 mac[ETH_ALEN];
 660	__le16 mode;
 661	__le16 errorCode;
 662	__le16 sigQuality;
 663	__le16 SSIDlen;
 664	char SSID[32];
 665	char apName[16];
 666	u8 bssid[4][ETH_ALEN];
 667	__le16 beaconPeriod;
 668	__le16 dimPeriod;
 669	__le16 atimDuration;
 670	__le16 hopPeriod;
 671	__le16 channelSet;
 672	__le16 channel;
 673	__le16 hopsToBackbone;
 674	__le16 apTotalLoad;
 675	__le16 generatedLoad;
 676	__le16 accumulatedArl;
 677	__le16 signalQuality;
 678	__le16 currentXmitRate;
 679	__le16 apDevExtensions;
 680	__le16 normalizedSignalStrength;
 681	__le16 shortPreamble;
 682	u8 apIP[4];
 683	u8 noisePercent; /* Noise percent in last second */
 684	u8 noisedBm; /* Noise dBm in last second */
 685	u8 noiseAvePercent; /* Noise percent in last minute */
 686	u8 noiseAvedBm; /* Noise dBm in last minute */
 687	u8 noiseMaxPercent; /* Highest noise percent in last minute */
 688	u8 noiseMaxdBm; /* Highest noise dbm in last minute */
 689	__le16 load;
 690	u8 carrier[4];
 691	__le16 assocStatus;
 692#define STAT_NOPACKETS 0
 693#define STAT_NOCARRIERSET 10
 694#define STAT_GOTCARRIERSET 11
 695#define STAT_WRONGSSID 20
 696#define STAT_BADCHANNEL 25
 697#define STAT_BADBITRATES 30
 698#define STAT_BADPRIVACY 35
 699#define STAT_APFOUND 40
 700#define STAT_APREJECTED 50
 701#define STAT_AUTHENTICATING 60
 702#define STAT_DEAUTHENTICATED 61
 703#define STAT_AUTHTIMEOUT 62
 704#define STAT_ASSOCIATING 70
 705#define STAT_DEASSOCIATED 71
 706#define STAT_ASSOCTIMEOUT 72
 707#define STAT_NOTAIROAP 73
 708#define STAT_ASSOCIATED 80
 709#define STAT_LEAPING 90
 710#define STAT_LEAPFAILED 91
 711#define STAT_LEAPTIMEDOUT 92
 712#define STAT_LEAPCOMPLETE 93
 713} __packed;
 714
 715typedef struct StatsRid StatsRid;
 716struct StatsRid {
 717	__le16 len;
 718	__le16 spacer;
 719	__le32 vals[100];
 720} __packed;
 721
 722typedef struct APListRid APListRid;
 723struct APListRid {
 724	__le16 len;
 725	u8 ap[4][ETH_ALEN];
 726} __packed;
 727
 728typedef struct CapabilityRid CapabilityRid;
 729struct CapabilityRid {
 730	__le16 len;
 731	char oui[3];
 732	char zero;
 733	__le16 prodNum;
 734	char manName[32];
 735	char prodName[16];
 736	char prodVer[8];
 737	char factoryAddr[ETH_ALEN];
 738	char aironetAddr[ETH_ALEN];
 739	__le16 radioType;
 740	__le16 country;
 741	char callid[ETH_ALEN];
 742	char supportedRates[8];
 743	char rxDiversity;
 744	char txDiversity;
 745	__le16 txPowerLevels[8];
 746	__le16 hardVer;
 747	__le16 hardCap;
 748	__le16 tempRange;
 749	__le16 softVer;
 750	__le16 softSubVer;
 751	__le16 interfaceVer;
 752	__le16 softCap;
 753	__le16 bootBlockVer;
 754	__le16 requiredHard;
 755	__le16 extSoftCap;
 756} __packed;
 757
 758/* Only present on firmware >= 5.30.17 */
 759typedef struct BSSListRidExtra BSSListRidExtra;
 760struct BSSListRidExtra {
 761  __le16 unknown[4];
 762  u8 fixed[12]; /* WLAN management frame */
 763  u8 iep[624];
 764} __packed;
 765
 766typedef struct BSSListRid BSSListRid;
 767struct BSSListRid {
 768  __le16 len;
 769  __le16 index; /* First is 0 and 0xffff means end of list */
 770#define RADIO_FH 1 /* Frequency hopping radio type */
 771#define RADIO_DS 2 /* Direct sequence radio type */
 772#define RADIO_TMA 4 /* Proprietary radio used in old cards (2500) */
 773  __le16 radioType;
 774  u8 bssid[ETH_ALEN]; /* Mac address of the BSS */
 775  u8 zero;
 776  u8 ssidLen;
 777  u8 ssid[32];
 778  __le16 dBm;
 779#define CAP_ESS cpu_to_le16(1<<0)
 780#define CAP_IBSS cpu_to_le16(1<<1)
 781#define CAP_PRIVACY cpu_to_le16(1<<4)
 782#define CAP_SHORTHDR cpu_to_le16(1<<5)
 783  __le16 cap;
 784  __le16 beaconInterval;
 785  u8 rates[8]; /* Same as rates for config rid */
 786  struct { /* For frequency hopping only */
 787    __le16 dwell;
 788    u8 hopSet;
 789    u8 hopPattern;
 790    u8 hopIndex;
 791    u8 fill;
 792  } fh;
 793  __le16 dsChannel;
 794  __le16 atimWindow;
 795
 796  /* Only present on firmware >= 5.30.17 */
 797  BSSListRidExtra extra;
 798} __packed;
 799
 800typedef struct {
 801  BSSListRid bss;
 802  struct list_head list;
 803} BSSListElement;
 804
 805typedef struct tdsRssiEntry tdsRssiEntry;
 806struct tdsRssiEntry {
 807  u8 rssipct;
 808  u8 rssidBm;
 809} __packed;
 810
 811typedef struct tdsRssiRid tdsRssiRid;
 812struct tdsRssiRid {
 813  u16 len;
 814  tdsRssiEntry x[256];
 815} __packed;
 816
 817typedef struct MICRid MICRid;
 818struct MICRid {
 819	__le16 len;
 820	__le16 state;
 821	__le16 multicastValid;
 822	u8  multicast[16];
 823	__le16 unicastValid;
 824	u8  unicast[16];
 825} __packed;
 826
 827typedef struct MICBuffer MICBuffer;
 828struct MICBuffer {
 829	__be16 typelen;
 830
 831	union {
 832	    u8 snap[8];
 833	    struct {
 834		u8 dsap;
 835		u8 ssap;
 836		u8 control;
 837		u8 orgcode[3];
 838		u8 fieldtype[2];
 839	    } llc;
 840	} u;
 841	__be32 mic;
 842	__be32 seq;
 843} __packed;
 844
 845typedef struct {
 846	u8 da[ETH_ALEN];
 847	u8 sa[ETH_ALEN];
 848} etherHead;
 849
 850#define TXCTL_TXOK (1<<1) /* report if tx is ok */
 851#define TXCTL_TXEX (1<<2) /* report if tx fails */
 852#define TXCTL_802_3 (0<<3) /* 802.3 packet */
 853#define TXCTL_802_11 (1<<3) /* 802.11 mac packet */
 854#define TXCTL_ETHERNET (0<<4) /* payload has ethertype */
 855#define TXCTL_LLC (1<<4) /* payload is llc */
 856#define TXCTL_RELEASE (0<<5) /* release after completion */
 857#define TXCTL_NORELEASE (1<<5) /* on completion returns to host */
 858
 859#define BUSY_FID 0x10000
 860
 861#ifdef CISCO_EXT
 862#define AIROMAGIC	0xa55a
 863/* Warning : SIOCDEVPRIVATE may disapear during 2.5.X - Jean II */
 864#ifdef SIOCIWFIRSTPRIV
 865#ifdef SIOCDEVPRIVATE
 866#define AIROOLDIOCTL	SIOCDEVPRIVATE
 867#define AIROOLDIDIFC 	AIROOLDIOCTL + 1
 868#endif /* SIOCDEVPRIVATE */
 869#else /* SIOCIWFIRSTPRIV */
 870#define SIOCIWFIRSTPRIV SIOCDEVPRIVATE
 871#endif /* SIOCIWFIRSTPRIV */
 872/* This may be wrong. When using the new SIOCIWFIRSTPRIV range, we probably
 873 * should use only "GET" ioctls (last bit set to 1). "SET" ioctls are root
 874 * only and don't return the modified struct ifreq to the application which
 875 * is usually a problem. - Jean II */
 876#define AIROIOCTL	SIOCIWFIRSTPRIV
 877#define AIROIDIFC 	AIROIOCTL + 1
 878
 879/* Ioctl constants to be used in airo_ioctl.command */
 880
 881#define	AIROGCAP  		0	// Capability rid
 882#define AIROGCFG		1       // USED A LOT
 883#define AIROGSLIST		2	// System ID list
 884#define AIROGVLIST		3       // List of specified AP's
 885#define AIROGDRVNAM		4	//  NOTUSED
 886#define AIROGEHTENC		5	// NOTUSED
 887#define AIROGWEPKTMP		6
 888#define AIROGWEPKNV		7
 889#define AIROGSTAT		8
 890#define AIROGSTATSC32		9
 891#define AIROGSTATSD32		10
 892#define AIROGMICRID		11
 893#define AIROGMICSTATS		12
 894#define AIROGFLAGS		13
 895#define AIROGID			14
 896#define AIRORRID		15
 897#define AIRORSWVERSION		17
 898
 899/* Leave gap of 40 commands after AIROGSTATSD32 for future */
 900
 901#define AIROPCAP               	AIROGSTATSD32 + 40
 902#define AIROPVLIST              AIROPCAP      + 1
 903#define AIROPSLIST		AIROPVLIST    + 1
 904#define AIROPCFG		AIROPSLIST    + 1
 905#define AIROPSIDS		AIROPCFG      + 1
 906#define AIROPAPLIST		AIROPSIDS     + 1
 907#define AIROPMACON		AIROPAPLIST   + 1	/* Enable mac  */
 908#define AIROPMACOFF		AIROPMACON    + 1 	/* Disable mac */
 909#define AIROPSTCLR		AIROPMACOFF   + 1
 910#define AIROPWEPKEY		AIROPSTCLR    + 1
 911#define AIROPWEPKEYNV		AIROPWEPKEY   + 1
 912#define AIROPLEAPPWD            AIROPWEPKEYNV + 1
 913#define AIROPLEAPUSR            AIROPLEAPPWD  + 1
 914
 915/* Flash codes */
 916
 917#define AIROFLSHRST	       AIROPWEPKEYNV  + 40
 918#define AIROFLSHGCHR           AIROFLSHRST    + 1
 919#define AIROFLSHSTFL           AIROFLSHGCHR   + 1
 920#define AIROFLSHPCHR           AIROFLSHSTFL   + 1
 921#define AIROFLPUTBUF           AIROFLSHPCHR   + 1
 922#define AIRORESTART            AIROFLPUTBUF   + 1
 923
 924#define FLASHSIZE	32768
 925#define AUXMEMSIZE	(256 * 1024)
 926
 927typedef struct aironet_ioctl {
 928	unsigned short command;		// What to do
 929	unsigned short len;		// Len of data
 930	unsigned short ridnum;		// rid number
 931	unsigned char __user *data;	// d-data
 932} aironet_ioctl;
 933
 934static const char swversion[] = "2.1";
 935#endif /* CISCO_EXT */
 936
 937#define NUM_MODULES       2
 938#define MIC_MSGLEN_MAX    2400
 939#define EMMH32_MSGLEN_MAX MIC_MSGLEN_MAX
 940#define AIRO_DEF_MTU      2312
 941
 942typedef struct {
 943	u32   size;            // size
 944	u8    enabled;         // MIC enabled or not
 945	u32   rxSuccess;       // successful packets received
 946	u32   rxIncorrectMIC;  // pkts dropped due to incorrect MIC comparison
 947	u32   rxNotMICed;      // pkts dropped due to not being MIC'd
 948	u32   rxMICPlummed;    // pkts dropped due to not having a MIC plummed
 949	u32   rxWrongSequence; // pkts dropped due to sequence number violation
 950	u32   reserve[32];
 951} mic_statistics;
 952
 953typedef struct {
 954	u32 coeff[((EMMH32_MSGLEN_MAX)+3)>>2];
 955	u64 accum;	// accumulated mic, reduced to u32 in final()
 956	int position;	// current position (byte offset) in message
 957	union {
 958		u8  d8[4];
 959		__be32 d32;
 960	} part;	// saves partial message word across update() calls
 961} emmh32_context;
 962
 963typedef struct {
 964	emmh32_context seed;	    // Context - the seed
 965	u32		 rx;	    // Received sequence number
 966	u32		 tx;	    // Tx sequence number
 967	u32		 window;    // Start of window
 968	u8		 valid;	    // Flag to say if context is valid or not
 969	u8		 key[16];
 970} miccntx;
 971
 972typedef struct {
 973	miccntx mCtx;		// Multicast context
 974	miccntx uCtx;		// Unicast context
 975} mic_module;
 976
 977typedef struct {
 978	unsigned int  rid: 16;
 979	unsigned int  len: 15;
 980	unsigned int  valid: 1;
 981	dma_addr_t host_addr;
 982} Rid;
 983
 984typedef struct {
 985	unsigned int  offset: 15;
 986	unsigned int  eoc: 1;
 987	unsigned int  len: 15;
 988	unsigned int  valid: 1;
 989	dma_addr_t host_addr;
 990} TxFid;
 991
 992struct rx_hdr {
 993	__le16 status, len;
 994	u8 rssi[2];
 995	u8 rate;
 996	u8 freq;
 997	__le16 tmp[4];
 998} __packed;
 999
1000typedef struct {
1001	unsigned int  ctl: 15;
1002	unsigned int  rdy: 1;
1003	unsigned int  len: 15;
1004	unsigned int  valid: 1;
1005	dma_addr_t host_addr;
1006} RxFid;
1007
1008/*
1009 * Host receive descriptor
1010 */
1011typedef struct {
1012	unsigned char __iomem *card_ram_off; /* offset into card memory of the
1013						desc */
1014	RxFid         rx_desc;		     /* card receive descriptor */
1015	char          *virtual_host_addr;    /* virtual address of host receive
1016					        buffer */
1017	int           pending;
1018} HostRxDesc;
1019
1020/*
1021 * Host transmit descriptor
1022 */
1023typedef struct {
1024	unsigned char __iomem *card_ram_off;	     /* offset into card memory of the
1025						desc */
1026	TxFid         tx_desc;		     /* card transmit descriptor */
1027	char          *virtual_host_addr;    /* virtual address of host receive
1028					        buffer */
1029	int           pending;
1030} HostTxDesc;
1031
1032/*
1033 * Host RID descriptor
1034 */
1035typedef struct {
1036	unsigned char __iomem *card_ram_off;      /* offset into card memory of the
1037					     descriptor */
1038	Rid           rid_desc;		  /* card RID descriptor */
1039	char          *virtual_host_addr; /* virtual address of host receive
1040					     buffer */
1041} HostRidDesc;
1042
1043typedef struct {
1044	u16 sw0;
1045	u16 sw1;
1046	u16 status;
1047	u16 len;
1048#define HOST_SET (1 << 0)
1049#define HOST_INT_TX (1 << 1) /* Interrupt on successful TX */
1050#define HOST_INT_TXERR (1 << 2) /* Interrupt on unseccessful TX */
1051#define HOST_LCC_PAYLOAD (1 << 4) /* LLC payload, 0 = Ethertype */
1052#define HOST_DONT_RLSE (1 << 5) /* Don't release buffer when done */
1053#define HOST_DONT_RETRY (1 << 6) /* Don't retry trasmit */
1054#define HOST_CLR_AID (1 << 7) /* clear AID failure */
1055#define HOST_RTS (1 << 9) /* Force RTS use */
1056#define HOST_SHORT (1 << 10) /* Do short preamble */
1057	u16 ctl;
1058	u16 aid;
1059	u16 retries;
1060	u16 fill;
1061} TxCtlHdr;
1062
1063typedef struct {
1064        u16 ctl;
1065        u16 duration;
1066        char addr1[6];
1067        char addr2[6];
1068        char addr3[6];
1069        u16 seq;
1070        char addr4[6];
1071} WifiHdr;
1072
1073
1074typedef struct {
1075	TxCtlHdr ctlhdr;
1076	u16 fill1;
1077	u16 fill2;
1078	WifiHdr wifihdr;
1079	u16 gaplen;
1080	u16 status;
1081} WifiCtlHdr;
1082
1083static WifiCtlHdr wifictlhdr8023 = {
1084	.ctlhdr = {
1085		.ctl	= HOST_DONT_RLSE,
1086	}
1087};
1088
1089// A few details needed for WEP (Wireless Equivalent Privacy)
1090#define MAX_KEY_SIZE 13			// 128 (?) bits
1091#define MIN_KEY_SIZE  5			// 40 bits RC4 - WEP
1092typedef struct wep_key_t {
1093	u16	len;
1094	u8	key[16];	/* 40-bit and 104-bit keys */
1095} wep_key_t;
1096
1097/* List of Wireless Handlers (new API) */
1098static const struct iw_handler_def	airo_handler_def;
1099
1100static const char version[] = "airo.c 0.6 (Ben Reed & Javier Achirica)";
1101
1102struct airo_info;
1103
1104static int get_dec_u16( char *buffer, int *start, int limit );
1105static void OUT4500( struct airo_info *, u16 register, u16 value );
1106static unsigned short IN4500( struct airo_info *, u16 register );
1107static u16 setup_card(struct airo_info*, u8 *mac, int lock);
1108static int enable_MAC(struct airo_info *ai, int lock);
1109static void disable_MAC(struct airo_info *ai, int lock);
1110static void enable_interrupts(struct airo_info*);
1111static void disable_interrupts(struct airo_info*);
1112static u16 issuecommand(struct airo_info*, Cmd *pCmd, Resp *pRsp);
 
1113static int bap_setup(struct airo_info*, u16 rid, u16 offset, int whichbap);
1114static int aux_bap_read(struct airo_info*, __le16 *pu16Dst, int bytelen,
1115			int whichbap);
1116static int fast_bap_read(struct airo_info*, __le16 *pu16Dst, int bytelen,
1117			 int whichbap);
1118static int bap_write(struct airo_info*, const __le16 *pu16Src, int bytelen,
1119		     int whichbap);
1120static int PC4500_accessrid(struct airo_info*, u16 rid, u16 accmd);
1121static int PC4500_readrid(struct airo_info*, u16 rid, void *pBuf, int len, int lock);
1122static int PC4500_writerid(struct airo_info*, u16 rid, const void
1123			   *pBuf, int len, int lock);
1124static int do_writerid( struct airo_info*, u16 rid, const void *rid_data,
1125			int len, int dummy );
1126static u16 transmit_allocate(struct airo_info*, int lenPayload, int raw);
1127static int transmit_802_3_packet(struct airo_info*, int len, char *pPacket);
1128static int transmit_802_11_packet(struct airo_info*, int len, char *pPacket);
 
 
1129
1130static int mpi_send_packet (struct net_device *dev);
1131static void mpi_unmap_card(struct pci_dev *pci);
1132static void mpi_receive_802_3(struct airo_info *ai);
1133static void mpi_receive_802_11(struct airo_info *ai);
1134static int waitbusy (struct airo_info *ai);
1135
1136static irqreturn_t airo_interrupt( int irq, void* dev_id);
1137static int airo_thread(void *data);
1138static void timer_func( struct net_device *dev );
1139static int airo_ioctl(struct net_device *dev, struct ifreq *rq, int cmd);
1140static struct iw_statistics *airo_get_wireless_stats (struct net_device *dev);
1141static void airo_read_wireless_stats (struct airo_info *local);
1142#ifdef CISCO_EXT
1143static int readrids(struct net_device *dev, aironet_ioctl *comp);
1144static int writerids(struct net_device *dev, aironet_ioctl *comp);
1145static int flashcard(struct net_device *dev, aironet_ioctl *comp);
1146#endif /* CISCO_EXT */
1147static void micinit(struct airo_info *ai);
1148static int micsetup(struct airo_info *ai);
1149static int encapsulate(struct airo_info *ai, etherHead *pPacket, MICBuffer *buffer, int len);
1150static int decapsulate(struct airo_info *ai, MICBuffer *mic, etherHead *pPacket, u16 payLen);
1151
1152static u8 airo_rssi_to_dbm (tdsRssiEntry *rssi_rid, u8 rssi);
1153static u8 airo_dbm_to_pct (tdsRssiEntry *rssi_rid, u8 dbm);
1154
1155static void airo_networks_free(struct airo_info *ai);
1156
1157struct airo_info {
1158	struct net_device             *dev;
1159	struct list_head              dev_list;
1160	/* Note, we can have MAX_FIDS outstanding.  FIDs are 16-bits, so we
1161	   use the high bit to mark whether it is in use. */
1162#define MAX_FIDS 6
1163#define MPI_MAX_FIDS 1
1164	u32                           fids[MAX_FIDS];
1165	ConfigRid config;
1166	char keyindex; // Used with auto wep
1167	char defindex; // Used with auto wep
1168	struct proc_dir_entry *proc_entry;
1169        spinlock_t aux_lock;
1170#define FLAG_RADIO_OFF	0	/* User disabling of MAC */
1171#define FLAG_RADIO_DOWN	1	/* ifup/ifdown disabling of MAC */
1172#define FLAG_RADIO_MASK 0x03
1173#define FLAG_ENABLED	2
1174#define FLAG_ADHOC	3	/* Needed by MIC */
1175#define FLAG_MIC_CAPABLE 4
1176#define FLAG_UPDATE_MULTI 5
1177#define FLAG_UPDATE_UNI 6
1178#define FLAG_802_11	7
1179#define FLAG_PROMISC	8	/* IFF_PROMISC 0x100 - include/linux/if.h */
1180#define FLAG_PENDING_XMIT 9
1181#define FLAG_PENDING_XMIT11 10
1182#define FLAG_MPI	11
1183#define FLAG_REGISTERED	12
1184#define FLAG_COMMIT	13
1185#define FLAG_RESET	14
1186#define FLAG_FLASHING	15
1187#define FLAG_WPA_CAPABLE	16
1188	unsigned long flags;
1189#define JOB_DIE	0
1190#define JOB_XMIT	1
1191#define JOB_XMIT11	2
1192#define JOB_STATS	3
1193#define JOB_PROMISC	4
1194#define JOB_MIC	5
1195#define JOB_EVENT	6
1196#define JOB_AUTOWEP	7
1197#define JOB_WSTATS	8
1198#define JOB_SCAN_RESULTS  9
1199	unsigned long jobs;
1200	int (*bap_read)(struct airo_info*, __le16 *pu16Dst, int bytelen,
1201			int whichbap);
1202	unsigned short *flash;
1203	tdsRssiEntry *rssi;
1204	struct task_struct *list_bss_task;
1205	struct task_struct *airo_thread_task;
1206	struct semaphore sem;
1207	wait_queue_head_t thr_wait;
1208	unsigned long expires;
1209	struct {
1210		struct sk_buff *skb;
1211		int fid;
1212	} xmit, xmit11;
1213	struct net_device *wifidev;
1214	struct iw_statistics	wstats;		// wireless stats
1215	unsigned long		scan_timeout;	/* Time scan should be read */
1216	struct iw_spy_data	spy_data;
1217	struct iw_public_data	wireless_data;
1218	/* MIC stuff */
1219	struct crypto_cipher	*tfm;
1220	mic_module		mod[2];
1221	mic_statistics		micstats;
1222	HostRxDesc rxfids[MPI_MAX_FIDS]; // rx/tx/config MPI350 descriptors
1223	HostTxDesc txfids[MPI_MAX_FIDS];
1224	HostRidDesc config_desc;
1225	unsigned long ridbus; // phys addr of config_desc
1226	struct sk_buff_head txq;// tx queue used by mpi350 code
1227	struct pci_dev          *pci;
1228	unsigned char		__iomem *pcimem;
1229	unsigned char		__iomem *pciaux;
1230	unsigned char		*shared;
1231	dma_addr_t		shared_dma;
1232	pm_message_t		power;
1233	SsidRid			*SSID;
1234	APListRid		APList;
1235#define	PCI_SHARED_LEN		2*MPI_MAX_FIDS*PKTSIZE+RIDSIZE
1236	char			proc_name[IFNAMSIZ];
1237
1238	int			wep_capable;
1239	int			max_wep_idx;
1240	int			last_auth;
1241
1242	/* WPA-related stuff */
1243	unsigned int bssListFirst;
1244	unsigned int bssListNext;
1245	unsigned int bssListRidLen;
1246
1247	struct list_head network_list;
1248	struct list_head network_free_list;
1249	BSSListElement *networks;
1250};
1251
1252static inline int bap_read(struct airo_info *ai, __le16 *pu16Dst, int bytelen,
1253			   int whichbap)
1254{
1255	return ai->bap_read(ai, pu16Dst, bytelen, whichbap);
1256}
1257
1258static int setup_proc_entry( struct net_device *dev,
1259			     struct airo_info *apriv );
1260static int takedown_proc_entry( struct net_device *dev,
1261				struct airo_info *apriv );
1262
1263static int cmdreset(struct airo_info *ai);
1264static int setflashmode (struct airo_info *ai);
1265static int flashgchar(struct airo_info *ai,int matchbyte,int dwelltime);
1266static int flashputbuf(struct airo_info *ai);
1267static int flashrestart(struct airo_info *ai,struct net_device *dev);
1268
1269#define airo_print(type, name, fmt, args...) \
1270	printk(type DRV_NAME "(%s): " fmt "\n", name, ##args)
1271
1272#define airo_print_info(name, fmt, args...) \
1273	airo_print(KERN_INFO, name, fmt, ##args)
1274
1275#define airo_print_dbg(name, fmt, args...) \
1276	airo_print(KERN_DEBUG, name, fmt, ##args)
1277
1278#define airo_print_warn(name, fmt, args...) \
1279	airo_print(KERN_WARNING, name, fmt, ##args)
1280
1281#define airo_print_err(name, fmt, args...) \
1282	airo_print(KERN_ERR, name, fmt, ##args)
1283
1284#define AIRO_FLASH(dev) (((struct airo_info *)dev->ml_priv)->flash)
1285
1286/***********************************************************************
1287 *                              MIC ROUTINES                           *
1288 ***********************************************************************
1289 */
1290
1291static int RxSeqValid (struct airo_info *ai,miccntx *context,int mcast,u32 micSeq);
1292static void MoveWindow(miccntx *context, u32 micSeq);
1293static void emmh32_setseed(emmh32_context *context, u8 *pkey, int keylen,
1294			   struct crypto_cipher *tfm);
1295static void emmh32_init(emmh32_context *context);
1296static void emmh32_update(emmh32_context *context, u8 *pOctets, int len);
1297static void emmh32_final(emmh32_context *context, u8 digest[4]);
1298static int flashpchar(struct airo_info *ai,int byte,int dwelltime);
1299
1300static void age_mic_context(miccntx *cur, miccntx *old, u8 *key, int key_len,
1301			    struct crypto_cipher *tfm)
1302{
1303	/* If the current MIC context is valid and its key is the same as
1304	 * the MIC register, there's nothing to do.
1305	 */
1306	if (cur->valid && (memcmp(cur->key, key, key_len) == 0))
1307		return;
1308
1309	/* Age current mic Context */
1310	memcpy(old, cur, sizeof(*cur));
1311
1312	/* Initialize new context */
1313	memcpy(cur->key, key, key_len);
1314	cur->window  = 33; /* Window always points to the middle */
1315	cur->rx      = 0;  /* Rx Sequence numbers */
1316	cur->tx      = 0;  /* Tx sequence numbers */
1317	cur->valid   = 1;  /* Key is now valid */
1318
1319	/* Give key to mic seed */
1320	emmh32_setseed(&cur->seed, key, key_len, tfm);
1321}
1322
1323/* micinit - Initialize mic seed */
1324
1325static void micinit(struct airo_info *ai)
1326{
1327	MICRid mic_rid;
1328
1329	clear_bit(JOB_MIC, &ai->jobs);
1330	PC4500_readrid(ai, RID_MIC, &mic_rid, sizeof(mic_rid), 0);
1331	up(&ai->sem);
1332
1333	ai->micstats.enabled = (le16_to_cpu(mic_rid.state) & 0x00FF) ? 1 : 0;
1334	if (!ai->micstats.enabled) {
1335		/* So next time we have a valid key and mic is enabled, we will
1336		 * update the sequence number if the key is the same as before.
1337		 */
1338		ai->mod[0].uCtx.valid = 0;
1339		ai->mod[0].mCtx.valid = 0;
1340		return;
1341	}
1342
1343	if (mic_rid.multicastValid) {
1344		age_mic_context(&ai->mod[0].mCtx, &ai->mod[1].mCtx,
1345		                mic_rid.multicast, sizeof(mic_rid.multicast),
1346		                ai->tfm);
1347	}
1348
1349	if (mic_rid.unicastValid) {
1350		age_mic_context(&ai->mod[0].uCtx, &ai->mod[1].uCtx,
1351				mic_rid.unicast, sizeof(mic_rid.unicast),
1352				ai->tfm);
1353	}
1354}
1355
1356/* micsetup - Get ready for business */
1357
1358static int micsetup(struct airo_info *ai) {
 
1359	int i;
1360
1361	if (ai->tfm == NULL)
1362	        ai->tfm = crypto_alloc_cipher("aes", 0, CRYPTO_ALG_ASYNC);
1363
1364        if (IS_ERR(ai->tfm)) {
1365                airo_print_err(ai->dev->name, "failed to load transform for AES");
1366                ai->tfm = NULL;
1367                return ERROR;
1368        }
1369
1370	for (i=0; i < NUM_MODULES; i++) {
1371		memset(&ai->mod[i].mCtx,0,sizeof(miccntx));
1372		memset(&ai->mod[i].uCtx,0,sizeof(miccntx));
1373	}
1374	return SUCCESS;
1375}
1376
1377static const u8 micsnap[] = {0xAA,0xAA,0x03,0x00,0x40,0x96,0x00,0x02};
1378
1379/*===========================================================================
1380 * Description: Mic a packet
1381 *    
1382 *      Inputs: etherHead * pointer to an 802.3 frame
1383 *    
1384 *     Returns: BOOLEAN if successful, otherwise false.
1385 *             PacketTxLen will be updated with the mic'd packets size.
1386 *
1387 *    Caveats: It is assumed that the frame buffer will already
1388 *             be big enough to hold the largets mic message possible.
1389 *            (No memory allocation is done here).
1390 *  
1391 *    Author: sbraneky (10/15/01)
1392 *    Merciless hacks by rwilcher (1/14/02)
1393 */
1394
1395static int encapsulate(struct airo_info *ai ,etherHead *frame, MICBuffer *mic, int payLen)
1396{
1397	miccntx   *context;
1398
1399	// Determine correct context
1400	// If not adhoc, always use unicast key
1401
1402	if (test_bit(FLAG_ADHOC, &ai->flags) && (frame->da[0] & 0x1))
1403		context = &ai->mod[0].mCtx;
1404	else
1405		context = &ai->mod[0].uCtx;
1406  
1407	if (!context->valid)
1408		return ERROR;
1409
1410	mic->typelen = htons(payLen + 16); //Length of Mic'd packet
1411
1412	memcpy(&mic->u.snap, micsnap, sizeof(micsnap)); // Add Snap
1413
1414	// Add Tx sequence
1415	mic->seq = htonl(context->tx);
1416	context->tx += 2;
1417
1418	emmh32_init(&context->seed); // Mic the packet
1419	emmh32_update(&context->seed,frame->da,ETH_ALEN * 2); // DA,SA
1420	emmh32_update(&context->seed,(u8*)&mic->typelen,10); // Type/Length and Snap
1421	emmh32_update(&context->seed,(u8*)&mic->seq,sizeof(mic->seq)); //SEQ
1422	emmh32_update(&context->seed,(u8*)(frame + 1),payLen); //payload
1423	emmh32_final(&context->seed, (u8*)&mic->mic);
1424
1425	/*    New Type/length ?????????? */
1426	mic->typelen = 0; //Let NIC know it could be an oversized packet
1427	return SUCCESS;
1428}
1429
1430typedef enum {
1431    NONE,
1432    NOMIC,
1433    NOMICPLUMMED,
1434    SEQUENCE,
1435    INCORRECTMIC,
1436} mic_error;
1437
1438/*===========================================================================
1439 *  Description: Decapsulates a MIC'd packet and returns the 802.3 packet
1440 *               (removes the MIC stuff) if packet is a valid packet.
1441 *      
1442 *       Inputs: etherHead  pointer to the 802.3 packet             
1443 *     
1444 *      Returns: BOOLEAN - TRUE if packet should be dropped otherwise FALSE
1445 *     
1446 *      Author: sbraneky (10/15/01)
1447 *    Merciless hacks by rwilcher (1/14/02)
1448 *---------------------------------------------------------------------------
1449 */
1450
1451static int decapsulate(struct airo_info *ai, MICBuffer *mic, etherHead *eth, u16 payLen)
1452{
1453	int      i;
1454	u32      micSEQ;
1455	miccntx  *context;
1456	u8       digest[4];
1457	mic_error micError = NONE;
1458
1459	// Check if the packet is a Mic'd packet
1460
1461	if (!ai->micstats.enabled) {
1462		//No Mic set or Mic OFF but we received a MIC'd packet.
1463		if (memcmp ((u8*)eth + 14, micsnap, sizeof(micsnap)) == 0) {
1464			ai->micstats.rxMICPlummed++;
1465			return ERROR;
1466		}
1467		return SUCCESS;
1468	}
1469
1470	if (ntohs(mic->typelen) == 0x888E)
1471		return SUCCESS;
1472
1473	if (memcmp (mic->u.snap, micsnap, sizeof(micsnap)) != 0) {
1474	    // Mic enabled but packet isn't Mic'd
1475		ai->micstats.rxMICPlummed++;
1476	    	return ERROR;
1477	}
1478
1479	micSEQ = ntohl(mic->seq);            //store SEQ as CPU order
1480
1481	//At this point we a have a mic'd packet and mic is enabled
1482	//Now do the mic error checking.
1483
1484	//Receive seq must be odd
1485	if ( (micSEQ & 1) == 0 ) {
1486		ai->micstats.rxWrongSequence++;
1487		return ERROR;
1488	}
1489
1490	for (i = 0; i < NUM_MODULES; i++) {
1491		int mcast = eth->da[0] & 1;
1492		//Determine proper context 
1493		context = mcast ? &ai->mod[i].mCtx : &ai->mod[i].uCtx;
1494	
1495		//Make sure context is valid
1496		if (!context->valid) {
1497			if (i == 0)
1498				micError = NOMICPLUMMED;
1499			continue;                
1500		}
1501	       	//DeMic it 
1502
1503		if (!mic->typelen)
1504			mic->typelen = htons(payLen + sizeof(MICBuffer) - 2);
1505	
1506		emmh32_init(&context->seed);
1507		emmh32_update(&context->seed, eth->da, ETH_ALEN*2); 
1508		emmh32_update(&context->seed, (u8 *)&mic->typelen, sizeof(mic->typelen)+sizeof(mic->u.snap)); 
1509		emmh32_update(&context->seed, (u8 *)&mic->seq,sizeof(mic->seq));	
1510		emmh32_update(&context->seed, (u8 *)(eth + 1),payLen);	
1511		//Calculate MIC
1512		emmh32_final(&context->seed, digest);
1513	
1514		if (memcmp(digest, &mic->mic, 4)) { //Make sure the mics match
1515		  //Invalid Mic
1516			if (i == 0)
1517				micError = INCORRECTMIC;
1518			continue;
1519		}
1520
1521		//Check Sequence number if mics pass
1522		if (RxSeqValid(ai, context, mcast, micSEQ) == SUCCESS) {
1523			ai->micstats.rxSuccess++;
1524			return SUCCESS;
1525		}
1526		if (i == 0)
1527			micError = SEQUENCE;
1528	}
1529
1530	// Update statistics
1531	switch (micError) {
1532		case NOMICPLUMMED: ai->micstats.rxMICPlummed++;   break;
1533		case SEQUENCE:    ai->micstats.rxWrongSequence++; break;
1534		case INCORRECTMIC: ai->micstats.rxIncorrectMIC++; break;
1535		case NONE:  break;
1536		case NOMIC: break;
1537	}
1538	return ERROR;
1539}
1540
1541/*===========================================================================
1542 * Description:  Checks the Rx Seq number to make sure it is valid
1543 *               and hasn't already been received
1544 *   
1545 *     Inputs: miccntx - mic context to check seq against
1546 *             micSeq  - the Mic seq number
1547 *   
1548 *    Returns: TRUE if valid otherwise FALSE. 
1549 *
1550 *    Author: sbraneky (10/15/01)
1551 *    Merciless hacks by rwilcher (1/14/02)
1552 *---------------------------------------------------------------------------
1553 */
1554
1555static int RxSeqValid (struct airo_info *ai,miccntx *context,int mcast,u32 micSeq)
1556{
1557	u32 seq,index;
1558
1559	//Allow for the ap being rebooted - if it is then use the next 
1560	//sequence number of the current sequence number - might go backwards
1561
1562	if (mcast) {
1563		if (test_bit(FLAG_UPDATE_MULTI, &ai->flags)) {
1564			clear_bit (FLAG_UPDATE_MULTI, &ai->flags);
1565			context->window = (micSeq > 33) ? micSeq : 33;
1566			context->rx     = 0;        // Reset rx
1567		}
1568	} else if (test_bit(FLAG_UPDATE_UNI, &ai->flags)) {
1569		clear_bit (FLAG_UPDATE_UNI, &ai->flags);
1570		context->window = (micSeq > 33) ? micSeq : 33; // Move window
1571		context->rx     = 0;        // Reset rx
1572	}
1573
1574	//Make sequence number relative to START of window
1575	seq = micSeq - (context->window - 33);
1576
1577	//Too old of a SEQ number to check.
1578	if ((s32)seq < 0)
1579		return ERROR;
1580    
1581	if ( seq > 64 ) {
1582		//Window is infinite forward
1583		MoveWindow(context,micSeq);
1584		return SUCCESS;
1585	}
1586
1587	// We are in the window. Now check the context rx bit to see if it was already sent
1588	seq >>= 1;         //divide by 2 because we only have odd numbers
1589	index = 1 << seq;  //Get an index number
1590
1591	if (!(context->rx & index)) {
1592		//micSEQ falls inside the window.
1593		//Add seqence number to the list of received numbers.
1594		context->rx |= index;
1595
1596		MoveWindow(context,micSeq);
1597
1598		return SUCCESS;
1599	}
1600	return ERROR;
1601}
1602
1603static void MoveWindow(miccntx *context, u32 micSeq)
1604{
1605	u32 shift;
1606
1607	//Move window if seq greater than the middle of the window
1608	if (micSeq > context->window) {
1609		shift = (micSeq - context->window) >> 1;
1610    
1611		    //Shift out old
1612		if (shift < 32)
1613			context->rx >>= shift;
1614		else
1615			context->rx = 0;
1616
1617		context->window = micSeq;      //Move window
1618	}
1619}
1620
1621/*==============================================*/
1622/*========== EMMH ROUTINES  ====================*/
1623/*==============================================*/
1624
1625/* mic accumulate */
1626#define MIC_ACCUM(val)	\
1627	context->accum += (u64)(val) * context->coeff[coeff_position++];
1628
1629static unsigned char aes_counter[16];
1630
1631/* expand the key to fill the MMH coefficient array */
1632static void emmh32_setseed(emmh32_context *context, u8 *pkey, int keylen,
1633			   struct crypto_cipher *tfm)
1634{
1635  /* take the keying material, expand if necessary, truncate at 16-bytes */
1636  /* run through AES counter mode to generate context->coeff[] */
1637  
1638	int i,j;
1639	u32 counter;
1640	u8 *cipher, plain[16];
1641
1642	crypto_cipher_setkey(tfm, pkey, 16);
1643	counter = 0;
1644	for (i = 0; i < ARRAY_SIZE(context->coeff); ) {
1645		aes_counter[15] = (u8)(counter >> 0);
1646		aes_counter[14] = (u8)(counter >> 8);
1647		aes_counter[13] = (u8)(counter >> 16);
1648		aes_counter[12] = (u8)(counter >> 24);
1649		counter++;
1650		memcpy (plain, aes_counter, 16);
1651		crypto_cipher_encrypt_one(tfm, plain, plain);
1652		cipher = plain;
1653		for (j = 0; (j < 16) && (i < ARRAY_SIZE(context->coeff)); ) {
1654			context->coeff[i++] = ntohl(*(__be32 *)&cipher[j]);
1655			j += 4;
1656		}
1657	}
1658}
1659
1660/* prepare for calculation of a new mic */
1661static void emmh32_init(emmh32_context *context)
1662{
1663	/* prepare for new mic calculation */
1664	context->accum = 0;
1665	context->position = 0;
1666}
1667
1668/* add some bytes to the mic calculation */
1669static void emmh32_update(emmh32_context *context, u8 *pOctets, int len)
1670{
1671	int	coeff_position, byte_position;
1672  
1673	if (len == 0) return;
1674  
1675	coeff_position = context->position >> 2;
1676  
1677	/* deal with partial 32-bit word left over from last update */
1678	byte_position = context->position & 3;
1679	if (byte_position) {
1680		/* have a partial word in part to deal with */
1681		do {
1682			if (len == 0) return;
1683			context->part.d8[byte_position++] = *pOctets++;
1684			context->position++;
1685			len--;
1686		} while (byte_position < 4);
1687		MIC_ACCUM(ntohl(context->part.d32));
1688	}
1689
1690	/* deal with full 32-bit words */
1691	while (len >= 4) {
1692		MIC_ACCUM(ntohl(*(__be32 *)pOctets));
1693		context->position += 4;
1694		pOctets += 4;
1695		len -= 4;
1696	}
1697
1698	/* deal with partial 32-bit word that will be left over from this update */
1699	byte_position = 0;
1700	while (len > 0) {
1701		context->part.d8[byte_position++] = *pOctets++;
1702		context->position++;
1703		len--;
1704	}
1705}
1706
1707/* mask used to zero empty bytes for final partial word */
1708static u32 mask32[4] = { 0x00000000L, 0xFF000000L, 0xFFFF0000L, 0xFFFFFF00L };
1709
1710/* calculate the mic */
1711static void emmh32_final(emmh32_context *context, u8 digest[4])
1712{
1713	int	coeff_position, byte_position;
1714	u32	val;
1715  
1716	u64 sum, utmp;
1717	s64 stmp;
1718
1719	coeff_position = context->position >> 2;
1720  
1721	/* deal with partial 32-bit word left over from last update */
1722	byte_position = context->position & 3;
1723	if (byte_position) {
1724		/* have a partial word in part to deal with */
1725		val = ntohl(context->part.d32);
1726		MIC_ACCUM(val & mask32[byte_position]);	/* zero empty bytes */
1727	}
1728
1729	/* reduce the accumulated u64 to a 32-bit MIC */
1730	sum = context->accum;
1731	stmp = (sum  & 0xffffffffLL) - ((sum >> 32)  * 15);
1732	utmp = (stmp & 0xffffffffLL) - ((stmp >> 32) * 15);
1733	sum = utmp & 0xffffffffLL;
1734	if (utmp > 0x10000000fLL)
1735		sum -= 15;
1736
1737	val = (u32)sum;
1738	digest[0] = (val>>24) & 0xFF;
1739	digest[1] = (val>>16) & 0xFF;
1740	digest[2] = (val>>8) & 0xFF;
1741	digest[3] = val & 0xFF;
1742}
1743
1744static int readBSSListRid(struct airo_info *ai, int first,
1745		      BSSListRid *list)
1746{
1747	Cmd cmd;
1748	Resp rsp;
1749
1750	if (first == 1) {
1751		if (ai->flags & FLAG_RADIO_MASK) return -ENETDOWN;
1752		memset(&cmd, 0, sizeof(cmd));
1753		cmd.cmd=CMD_LISTBSS;
1754		if (down_interruptible(&ai->sem))
1755			return -ERESTARTSYS;
1756		ai->list_bss_task = current;
1757		issuecommand(ai, &cmd, &rsp);
1758		up(&ai->sem);
1759		/* Let the command take effect */
1760		schedule_timeout_uninterruptible(3 * HZ);
1761		ai->list_bss_task = NULL;
1762	}
1763	return PC4500_readrid(ai, first ? ai->bssListFirst : ai->bssListNext,
1764			    list, ai->bssListRidLen, 1);
1765}
1766
1767static int readWepKeyRid(struct airo_info *ai, WepKeyRid *wkr, int temp, int lock)
1768{
1769	return PC4500_readrid(ai, temp ? RID_WEP_TEMP : RID_WEP_PERM,
1770				wkr, sizeof(*wkr), lock);
1771}
1772
1773static int writeWepKeyRid(struct airo_info *ai, WepKeyRid *wkr, int perm, int lock)
1774{
1775	int rc;
1776	rc = PC4500_writerid(ai, RID_WEP_TEMP, wkr, sizeof(*wkr), lock);
1777	if (rc!=SUCCESS)
1778		airo_print_err(ai->dev->name, "WEP_TEMP set %x", rc);
1779	if (perm) {
1780		rc = PC4500_writerid(ai, RID_WEP_PERM, wkr, sizeof(*wkr), lock);
1781		if (rc!=SUCCESS)
1782			airo_print_err(ai->dev->name, "WEP_PERM set %x", rc);
1783	}
1784	return rc;
1785}
1786
1787static int readSsidRid(struct airo_info*ai, SsidRid *ssidr)
1788{
1789	return PC4500_readrid(ai, RID_SSID, ssidr, sizeof(*ssidr), 1);
1790}
1791
1792static int writeSsidRid(struct airo_info*ai, SsidRid *pssidr, int lock)
1793{
1794	return PC4500_writerid(ai, RID_SSID, pssidr, sizeof(*pssidr), lock);
1795}
1796
1797static int readConfigRid(struct airo_info *ai, int lock)
1798{
1799	int rc;
1800	ConfigRid cfg;
1801
1802	if (ai->config.len)
1803		return SUCCESS;
1804
1805	rc = PC4500_readrid(ai, RID_ACTUALCONFIG, &cfg, sizeof(cfg), lock);
1806	if (rc != SUCCESS)
1807		return rc;
1808
1809	ai->config = cfg;
1810	return SUCCESS;
1811}
1812
1813static inline void checkThrottle(struct airo_info *ai)
1814{
1815	int i;
1816/* Old hardware had a limit on encryption speed */
1817	if (ai->config.authType != AUTH_OPEN && maxencrypt) {
1818		for(i=0; i<8; i++) {
1819			if (ai->config.rates[i] > maxencrypt) {
1820				ai->config.rates[i] = 0;
1821			}
1822		}
1823	}
1824}
1825
1826static int writeConfigRid(struct airo_info *ai, int lock)
1827{
1828	ConfigRid cfgr;
1829
1830	if (!test_bit (FLAG_COMMIT, &ai->flags))
1831		return SUCCESS;
1832
1833	clear_bit (FLAG_COMMIT, &ai->flags);
1834	clear_bit (FLAG_RESET, &ai->flags);
1835	checkThrottle(ai);
1836	cfgr = ai->config;
1837
1838	if ((cfgr.opmode & MODE_CFG_MASK) == MODE_STA_IBSS)
1839		set_bit(FLAG_ADHOC, &ai->flags);
1840	else
1841		clear_bit(FLAG_ADHOC, &ai->flags);
1842
1843	return PC4500_writerid( ai, RID_CONFIG, &cfgr, sizeof(cfgr), lock);
1844}
1845
1846static int readStatusRid(struct airo_info *ai, StatusRid *statr, int lock)
1847{
1848	return PC4500_readrid(ai, RID_STATUS, statr, sizeof(*statr), lock);
1849}
1850
1851static int writeAPListRid(struct airo_info *ai, APListRid *aplr, int lock)
1852{
1853	return PC4500_writerid(ai, RID_APLIST, aplr, sizeof(*aplr), lock);
1854}
1855
1856static int readCapabilityRid(struct airo_info *ai, CapabilityRid *capr, int lock)
1857{
1858	return PC4500_readrid(ai, RID_CAPABILITIES, capr, sizeof(*capr), lock);
1859}
1860
1861static int readStatsRid(struct airo_info*ai, StatsRid *sr, int rid, int lock)
1862{
1863	return PC4500_readrid(ai, rid, sr, sizeof(*sr), lock);
1864}
1865
1866static void try_auto_wep(struct airo_info *ai)
1867{
1868	if (auto_wep && !test_bit(FLAG_RADIO_DOWN, &ai->flags)) {
1869		ai->expires = RUN_AT(3*HZ);
1870		wake_up_interruptible(&ai->thr_wait);
1871	}
1872}
1873
1874static int airo_open(struct net_device *dev) {
 
1875	struct airo_info *ai = dev->ml_priv;
1876	int rc = 0;
1877
1878	if (test_bit(FLAG_FLASHING, &ai->flags))
1879		return -EIO;
1880
1881	/* Make sure the card is configured.
1882	 * Wireless Extensions may postpone config changes until the card
1883	 * is open (to pipeline changes and speed-up card setup). If
1884	 * those changes are not yet committed, do it now - Jean II */
1885	if (test_bit(FLAG_COMMIT, &ai->flags)) {
1886		disable_MAC(ai, 1);
1887		writeConfigRid(ai, 1);
1888	}
1889
1890	if (ai->wifidev != dev) {
1891		clear_bit(JOB_DIE, &ai->jobs);
1892		ai->airo_thread_task = kthread_run(airo_thread, dev, "%s",
1893						   dev->name);
1894		if (IS_ERR(ai->airo_thread_task))
1895			return (int)PTR_ERR(ai->airo_thread_task);
1896
1897		rc = request_irq(dev->irq, airo_interrupt, IRQF_SHARED,
1898			dev->name, dev);
1899		if (rc) {
1900			airo_print_err(dev->name,
1901				"register interrupt %d failed, rc %d",
1902				dev->irq, rc);
1903			set_bit(JOB_DIE, &ai->jobs);
1904			kthread_stop(ai->airo_thread_task);
1905			return rc;
1906		}
1907
1908		/* Power on the MAC controller (which may have been disabled) */
1909		clear_bit(FLAG_RADIO_DOWN, &ai->flags);
1910		enable_interrupts(ai);
1911
1912		try_auto_wep(ai);
1913	}
1914	enable_MAC(ai, 1);
1915
1916	netif_start_queue(dev);
1917	return 0;
1918}
1919
1920static netdev_tx_t mpi_start_xmit(struct sk_buff *skb,
1921					struct net_device *dev)
1922{
1923	int npacks, pending;
1924	unsigned long flags;
1925	struct airo_info *ai = dev->ml_priv;
1926
1927	if (!skb) {
1928		airo_print_err(dev->name, "%s: skb == NULL!",__func__);
1929		return NETDEV_TX_OK;
1930	}
 
 
 
 
1931	npacks = skb_queue_len (&ai->txq);
1932
1933	if (npacks >= MAXTXQ - 1) {
1934		netif_stop_queue (dev);
1935		if (npacks > MAXTXQ) {
1936			dev->stats.tx_fifo_errors++;
1937			return NETDEV_TX_BUSY;
1938		}
1939		skb_queue_tail (&ai->txq, skb);
1940		return NETDEV_TX_OK;
1941	}
1942
1943	spin_lock_irqsave(&ai->aux_lock, flags);
1944	skb_queue_tail (&ai->txq, skb);
1945	pending = test_bit(FLAG_PENDING_XMIT, &ai->flags);
1946	spin_unlock_irqrestore(&ai->aux_lock,flags);
1947	netif_wake_queue (dev);
1948
1949	if (pending == 0) {
1950		set_bit(FLAG_PENDING_XMIT, &ai->flags);
1951		mpi_send_packet (dev);
1952	}
1953	return NETDEV_TX_OK;
1954}
1955
1956/*
1957 * @mpi_send_packet
1958 *
1959 * Attempt to transmit a packet. Can be called from interrupt
1960 * or transmit . return number of packets we tried to send
1961 */
1962
1963static int mpi_send_packet (struct net_device *dev)
1964{
1965	struct sk_buff *skb;
1966	unsigned char *buffer;
1967	s16 len;
1968	__le16 *payloadLen;
1969	struct airo_info *ai = dev->ml_priv;
1970	u8 *sendbuf;
1971
1972	/* get a packet to send */
1973
1974	if ((skb = skb_dequeue(&ai->txq)) == NULL) {
1975		airo_print_err(dev->name,
1976			"%s: Dequeue'd zero in send_packet()",
1977			__func__);
1978		return 0;
1979	}
1980
1981	/* check min length*/
1982	len = ETH_ZLEN < skb->len ? skb->len : ETH_ZLEN;
1983	buffer = skb->data;
1984
1985	ai->txfids[0].tx_desc.offset = 0;
1986	ai->txfids[0].tx_desc.valid = 1;
1987	ai->txfids[0].tx_desc.eoc = 1;
1988	ai->txfids[0].tx_desc.len =len+sizeof(WifiHdr);
1989
1990/*
1991 * Magic, the cards firmware needs a length count (2 bytes) in the host buffer
1992 * right after  TXFID_HDR.The TXFID_HDR contains the status short so payloadlen
1993 * is immediately after it. ------------------------------------------------
1994 *                         |TXFIDHDR+STATUS|PAYLOADLEN|802.3HDR|PACKETDATA|
1995 *                         ------------------------------------------------
1996 */
1997
1998	memcpy(ai->txfids[0].virtual_host_addr,
1999		(char *)&wifictlhdr8023, sizeof(wifictlhdr8023));
2000
2001	payloadLen = (__le16 *)(ai->txfids[0].virtual_host_addr +
2002		sizeof(wifictlhdr8023));
2003	sendbuf = ai->txfids[0].virtual_host_addr +
2004		sizeof(wifictlhdr8023) + 2 ;
2005
2006	/*
2007	 * Firmware automatically puts 802 header on so
2008	 * we don't need to account for it in the length
2009	 */
2010	if (test_bit(FLAG_MIC_CAPABLE, &ai->flags) && ai->micstats.enabled &&
2011		(ntohs(((__be16 *)buffer)[6]) != 0x888E)) {
2012		MICBuffer pMic;
2013
2014		if (encapsulate(ai, (etherHead *)buffer, &pMic, len - sizeof(etherHead)) != SUCCESS)
2015			return ERROR;
2016
2017		*payloadLen = cpu_to_le16(len-sizeof(etherHead)+sizeof(pMic));
2018		ai->txfids[0].tx_desc.len += sizeof(pMic);
2019		/* copy data into airo dma buffer */
2020		memcpy (sendbuf, buffer, sizeof(etherHead));
2021		buffer += sizeof(etherHead);
2022		sendbuf += sizeof(etherHead);
2023		memcpy (sendbuf, &pMic, sizeof(pMic));
2024		sendbuf += sizeof(pMic);
2025		memcpy (sendbuf, buffer, len - sizeof(etherHead));
2026	} else {
2027		*payloadLen = cpu_to_le16(len - sizeof(etherHead));
2028
2029		dev->trans_start = jiffies;
2030
2031		/* copy data into airo dma buffer */
2032		memcpy(sendbuf, buffer, len);
2033	}
2034
2035	memcpy_toio(ai->txfids[0].card_ram_off,
2036		&ai->txfids[0].tx_desc, sizeof(TxFid));
2037
2038	OUT4500(ai, EVACK, 8);
2039
2040	dev_kfree_skb_any(skb);
2041	return 1;
2042}
2043
2044static void get_tx_error(struct airo_info *ai, s32 fid)
2045{
2046	__le16 status;
2047
2048	if (fid < 0)
2049		status = ((WifiCtlHdr *)ai->txfids[0].virtual_host_addr)->ctlhdr.status;
2050	else {
2051		if (bap_setup(ai, ai->fids[fid] & 0xffff, 4, BAP0) != SUCCESS)
2052			return;
2053		bap_read(ai, &status, 2, BAP0);
2054	}
2055	if (le16_to_cpu(status) & 2) /* Too many retries */
2056		ai->dev->stats.tx_aborted_errors++;
2057	if (le16_to_cpu(status) & 4) /* Transmit lifetime exceeded */
2058		ai->dev->stats.tx_heartbeat_errors++;
2059	if (le16_to_cpu(status) & 8) /* Aid fail */
2060		{ }
2061	if (le16_to_cpu(status) & 0x10) /* MAC disabled */
2062		ai->dev->stats.tx_carrier_errors++;
2063	if (le16_to_cpu(status) & 0x20) /* Association lost */
2064		{ }
2065	/* We produce a TXDROP event only for retry or lifetime
2066	 * exceeded, because that's the only status that really mean
2067	 * that this particular node went away.
2068	 * Other errors means that *we* screwed up. - Jean II */
2069	if ((le16_to_cpu(status) & 2) ||
2070	     (le16_to_cpu(status) & 4)) {
2071		union iwreq_data	wrqu;
2072		char junk[0x18];
2073
2074		/* Faster to skip over useless data than to do
2075		 * another bap_setup(). We are at offset 0x6 and
2076		 * need to go to 0x18 and read 6 bytes - Jean II */
2077		bap_read(ai, (__le16 *) junk, 0x18, BAP0);
2078
2079		/* Copy 802.11 dest address.
2080		 * We use the 802.11 header because the frame may
2081		 * not be 802.3 or may be mangled...
2082		 * In Ad-Hoc mode, it will be the node address.
2083		 * In managed mode, it will be most likely the AP addr
2084		 * User space will figure out how to convert it to
2085		 * whatever it needs (IP address or else).
2086		 * - Jean II */
2087		memcpy(wrqu.addr.sa_data, junk + 0x12, ETH_ALEN);
2088		wrqu.addr.sa_family = ARPHRD_ETHER;
2089
2090		/* Send event to user space */
2091		wireless_send_event(ai->dev, IWEVTXDROP, &wrqu, NULL);
2092	}
2093}
2094
2095static void airo_end_xmit(struct net_device *dev) {
 
2096	u16 status;
2097	int i;
2098	struct airo_info *priv = dev->ml_priv;
2099	struct sk_buff *skb = priv->xmit.skb;
2100	int fid = priv->xmit.fid;
2101	u32 *fids = priv->fids;
2102
2103	clear_bit(JOB_XMIT, &priv->jobs);
2104	clear_bit(FLAG_PENDING_XMIT, &priv->flags);
2105	status = transmit_802_3_packet (priv, fids[fid], skb->data);
2106	up(&priv->sem);
2107
2108	i = 0;
2109	if ( status == SUCCESS ) {
2110		dev->trans_start = jiffies;
2111		for (; i < MAX_FIDS / 2 && (priv->fids[i] & 0xffff0000); i++);
2112	} else {
2113		priv->fids[fid] &= 0xffff;
2114		dev->stats.tx_window_errors++;
2115	}
2116	if (i < MAX_FIDS / 2)
2117		netif_wake_queue(dev);
2118	dev_kfree_skb(skb);
2119}
2120
2121static netdev_tx_t airo_start_xmit(struct sk_buff *skb,
2122					 struct net_device *dev)
2123{
2124	s16 len;
2125	int i, j;
2126	struct airo_info *priv = dev->ml_priv;
2127	u32 *fids = priv->fids;
2128
2129	if ( skb == NULL ) {
2130		airo_print_err(dev->name, "%s: skb == NULL!", __func__);
2131		return NETDEV_TX_OK;
2132	}
 
 
 
 
2133
2134	/* Find a vacant FID */
2135	for( i = 0; i < MAX_FIDS / 2 && (fids[i] & 0xffff0000); i++ );
2136	for( j = i + 1; j < MAX_FIDS / 2 && (fids[j] & 0xffff0000); j++ );
2137
2138	if ( j >= MAX_FIDS / 2 ) {
2139		netif_stop_queue(dev);
2140
2141		if (i == MAX_FIDS / 2) {
2142			dev->stats.tx_fifo_errors++;
2143			return NETDEV_TX_BUSY;
2144		}
2145	}
2146	/* check min length*/
2147	len = ETH_ZLEN < skb->len ? skb->len : ETH_ZLEN;
2148        /* Mark fid as used & save length for later */
2149	fids[i] |= (len << 16);
2150	priv->xmit.skb = skb;
2151	priv->xmit.fid = i;
2152	if (down_trylock(&priv->sem) != 0) {
2153		set_bit(FLAG_PENDING_XMIT, &priv->flags);
2154		netif_stop_queue(dev);
2155		set_bit(JOB_XMIT, &priv->jobs);
2156		wake_up_interruptible(&priv->thr_wait);
2157	} else
2158		airo_end_xmit(dev);
2159	return NETDEV_TX_OK;
2160}
2161
2162static void airo_end_xmit11(struct net_device *dev) {
 
2163	u16 status;
2164	int i;
2165	struct airo_info *priv = dev->ml_priv;
2166	struct sk_buff *skb = priv->xmit11.skb;
2167	int fid = priv->xmit11.fid;
2168	u32 *fids = priv->fids;
2169
2170	clear_bit(JOB_XMIT11, &priv->jobs);
2171	clear_bit(FLAG_PENDING_XMIT11, &priv->flags);
2172	status = transmit_802_11_packet (priv, fids[fid], skb->data);
2173	up(&priv->sem);
2174
2175	i = MAX_FIDS / 2;
2176	if ( status == SUCCESS ) {
2177		dev->trans_start = jiffies;
2178		for (; i < MAX_FIDS && (priv->fids[i] & 0xffff0000); i++);
2179	} else {
2180		priv->fids[fid] &= 0xffff;
2181		dev->stats.tx_window_errors++;
2182	}
2183	if (i < MAX_FIDS)
2184		netif_wake_queue(dev);
2185	dev_kfree_skb(skb);
2186}
2187
2188static netdev_tx_t airo_start_xmit11(struct sk_buff *skb,
2189					   struct net_device *dev)
2190{
2191	s16 len;
2192	int i, j;
2193	struct airo_info *priv = dev->ml_priv;
2194	u32 *fids = priv->fids;
2195
2196	if (test_bit(FLAG_MPI, &priv->flags)) {
2197		/* Not implemented yet for MPI350 */
2198		netif_stop_queue(dev);
2199		dev_kfree_skb_any(skb);
2200		return NETDEV_TX_OK;
2201	}
2202
2203	if ( skb == NULL ) {
2204		airo_print_err(dev->name, "%s: skb == NULL!", __func__);
2205		return NETDEV_TX_OK;
2206	}
 
 
 
 
2207
2208	/* Find a vacant FID */
2209	for( i = MAX_FIDS / 2; i < MAX_FIDS && (fids[i] & 0xffff0000); i++ );
2210	for( j = i + 1; j < MAX_FIDS && (fids[j] & 0xffff0000); j++ );
2211
2212	if ( j >= MAX_FIDS ) {
2213		netif_stop_queue(dev);
2214
2215		if (i == MAX_FIDS) {
2216			dev->stats.tx_fifo_errors++;
2217			return NETDEV_TX_BUSY;
2218		}
2219	}
2220	/* check min length*/
2221	len = ETH_ZLEN < skb->len ? skb->len : ETH_ZLEN;
2222        /* Mark fid as used & save length for later */
2223	fids[i] |= (len << 16);
2224	priv->xmit11.skb = skb;
2225	priv->xmit11.fid = i;
2226	if (down_trylock(&priv->sem) != 0) {
2227		set_bit(FLAG_PENDING_XMIT11, &priv->flags);
2228		netif_stop_queue(dev);
2229		set_bit(JOB_XMIT11, &priv->jobs);
2230		wake_up_interruptible(&priv->thr_wait);
2231	} else
2232		airo_end_xmit11(dev);
2233	return NETDEV_TX_OK;
2234}
2235
2236static void airo_read_stats(struct net_device *dev)
2237{
2238	struct airo_info *ai = dev->ml_priv;
2239	StatsRid stats_rid;
2240	__le32 *vals = stats_rid.vals;
2241
2242	clear_bit(JOB_STATS, &ai->jobs);
2243	if (ai->power.event) {
2244		up(&ai->sem);
2245		return;
2246	}
2247	readStatsRid(ai, &stats_rid, RID_STATS, 0);
2248	up(&ai->sem);
2249
2250	dev->stats.rx_packets = le32_to_cpu(vals[43]) + le32_to_cpu(vals[44]) +
2251			       le32_to_cpu(vals[45]);
2252	dev->stats.tx_packets = le32_to_cpu(vals[39]) + le32_to_cpu(vals[40]) +
2253			       le32_to_cpu(vals[41]);
2254	dev->stats.rx_bytes = le32_to_cpu(vals[92]);
2255	dev->stats.tx_bytes = le32_to_cpu(vals[91]);
2256	dev->stats.rx_errors = le32_to_cpu(vals[0]) + le32_to_cpu(vals[2]) +
2257			      le32_to_cpu(vals[3]) + le32_to_cpu(vals[4]);
2258	dev->stats.tx_errors = le32_to_cpu(vals[42]) +
2259			      dev->stats.tx_fifo_errors;
2260	dev->stats.multicast = le32_to_cpu(vals[43]);
2261	dev->stats.collisions = le32_to_cpu(vals[89]);
2262
2263	/* detailed rx_errors: */
2264	dev->stats.rx_length_errors = le32_to_cpu(vals[3]);
2265	dev->stats.rx_crc_errors = le32_to_cpu(vals[4]);
2266	dev->stats.rx_frame_errors = le32_to_cpu(vals[2]);
2267	dev->stats.rx_fifo_errors = le32_to_cpu(vals[0]);
2268}
2269
2270static struct net_device_stats *airo_get_stats(struct net_device *dev)
2271{
2272	struct airo_info *local =  dev->ml_priv;
2273
2274	if (!test_bit(JOB_STATS, &local->jobs)) {
2275		/* Get stats out of the card if available */
2276		if (down_trylock(&local->sem) != 0) {
2277			set_bit(JOB_STATS, &local->jobs);
2278			wake_up_interruptible(&local->thr_wait);
2279		} else
2280			airo_read_stats(dev);
2281	}
2282
2283	return &dev->stats;
2284}
2285
2286static void airo_set_promisc(struct airo_info *ai) {
 
2287	Cmd cmd;
2288	Resp rsp;
2289
2290	memset(&cmd, 0, sizeof(cmd));
2291	cmd.cmd=CMD_SETMODE;
2292	clear_bit(JOB_PROMISC, &ai->jobs);
2293	cmd.parm0=(ai->flags&IFF_PROMISC) ? PROMISC : NOPROMISC;
2294	issuecommand(ai, &cmd, &rsp);
2295	up(&ai->sem);
2296}
2297
2298static void airo_set_multicast_list(struct net_device *dev) {
 
2299	struct airo_info *ai = dev->ml_priv;
2300
2301	if ((dev->flags ^ ai->flags) & IFF_PROMISC) {
2302		change_bit(FLAG_PROMISC, &ai->flags);
2303		if (down_trylock(&ai->sem) != 0) {
2304			set_bit(JOB_PROMISC, &ai->jobs);
2305			wake_up_interruptible(&ai->thr_wait);
2306		} else
2307			airo_set_promisc(ai);
2308	}
2309
2310	if ((dev->flags&IFF_ALLMULTI) || !netdev_mc_empty(dev)) {
2311		/* Turn on multicast.  (Should be already setup...) */
2312	}
2313}
2314
2315static int airo_set_mac_address(struct net_device *dev, void *p)
2316{
2317	struct airo_info *ai = dev->ml_priv;
2318	struct sockaddr *addr = p;
2319
2320	readConfigRid(ai, 1);
2321	memcpy (ai->config.macAddr, addr->sa_data, dev->addr_len);
2322	set_bit (FLAG_COMMIT, &ai->flags);
2323	disable_MAC(ai, 1);
2324	writeConfigRid (ai, 1);
2325	enable_MAC(ai, 1);
2326	memcpy (ai->dev->dev_addr, addr->sa_data, dev->addr_len);
2327	if (ai->wifidev)
2328		memcpy (ai->wifidev->dev_addr, addr->sa_data, dev->addr_len);
2329	return 0;
2330}
2331
2332static int airo_change_mtu(struct net_device *dev, int new_mtu)
2333{
2334	if ((new_mtu < 68) || (new_mtu > 2400))
2335		return -EINVAL;
2336	dev->mtu = new_mtu;
2337	return 0;
2338}
2339
2340static LIST_HEAD(airo_devices);
2341
2342static void add_airo_dev(struct airo_info *ai)
2343{
2344	/* Upper layers already keep track of PCI devices,
2345	 * so we only need to remember our non-PCI cards. */
2346	if (!ai->pci)
2347		list_add_tail(&ai->dev_list, &airo_devices);
2348}
2349
2350static void del_airo_dev(struct airo_info *ai)
2351{
2352	if (!ai->pci)
2353		list_del(&ai->dev_list);
2354}
2355
2356static int airo_close(struct net_device *dev) {
 
2357	struct airo_info *ai = dev->ml_priv;
2358
2359	netif_stop_queue(dev);
2360
2361	if (ai->wifidev != dev) {
2362#ifdef POWER_ON_DOWN
2363		/* Shut power to the card. The idea is that the user can save
2364		 * power when he doesn't need the card with "ifconfig down".
2365		 * That's the method that is most friendly towards the network
2366		 * stack (i.e. the network stack won't try to broadcast
2367		 * anything on the interface and routes are gone. Jean II */
2368		set_bit(FLAG_RADIO_DOWN, &ai->flags);
2369		disable_MAC(ai, 1);
2370#endif
2371		disable_interrupts( ai );
2372
2373		free_irq(dev->irq, dev);
2374
2375		set_bit(JOB_DIE, &ai->jobs);
2376		kthread_stop(ai->airo_thread_task);
2377	}
2378	return 0;
2379}
2380
2381void stop_airo_card( struct net_device *dev, int freeres )
2382{
2383	struct airo_info *ai = dev->ml_priv;
2384
2385	set_bit(FLAG_RADIO_DOWN, &ai->flags);
2386	disable_MAC(ai, 1);
2387	disable_interrupts(ai);
2388	takedown_proc_entry( dev, ai );
2389	if (test_bit(FLAG_REGISTERED, &ai->flags)) {
2390		unregister_netdev( dev );
2391		if (ai->wifidev) {
2392			unregister_netdev(ai->wifidev);
2393			free_netdev(ai->wifidev);
2394			ai->wifidev = NULL;
2395		}
2396		clear_bit(FLAG_REGISTERED, &ai->flags);
2397	}
2398	/*
2399	 * Clean out tx queue
2400	 */
2401	if (test_bit(FLAG_MPI, &ai->flags) && !skb_queue_empty(&ai->txq)) {
2402		struct sk_buff *skb = NULL;
2403		for (;(skb = skb_dequeue(&ai->txq));)
2404			dev_kfree_skb(skb);
2405	}
2406
2407	airo_networks_free (ai);
2408
2409	kfree(ai->flash);
2410	kfree(ai->rssi);
2411	kfree(ai->SSID);
2412	if (freeres) {
2413		/* PCMCIA frees this stuff, so only for PCI and ISA */
2414	        release_region( dev->base_addr, 64 );
2415		if (test_bit(FLAG_MPI, &ai->flags)) {
2416			if (ai->pci)
2417				mpi_unmap_card(ai->pci);
2418			if (ai->pcimem)
2419				iounmap(ai->pcimem);
2420			if (ai->pciaux)
2421				iounmap(ai->pciaux);
2422			pci_free_consistent(ai->pci, PCI_SHARED_LEN,
2423				ai->shared, ai->shared_dma);
2424		}
2425        }
2426	crypto_free_cipher(ai->tfm);
2427	del_airo_dev(ai);
2428	free_netdev( dev );
2429}
2430
2431EXPORT_SYMBOL(stop_airo_card);
2432
2433static int wll_header_parse(const struct sk_buff *skb, unsigned char *haddr)
2434{
2435	memcpy(haddr, skb_mac_header(skb) + 10, ETH_ALEN);
2436	return ETH_ALEN;
2437}
2438
2439static void mpi_unmap_card(struct pci_dev *pci)
2440{
2441	unsigned long mem_start = pci_resource_start(pci, 1);
2442	unsigned long mem_len = pci_resource_len(pci, 1);
2443	unsigned long aux_start = pci_resource_start(pci, 2);
2444	unsigned long aux_len = AUXMEMSIZE;
2445
2446	release_mem_region(aux_start, aux_len);
2447	release_mem_region(mem_start, mem_len);
2448}
2449
2450/*************************************************************
2451 *  This routine assumes that descriptors have been setup .
2452 *  Run at insmod time or after reset  when the decriptors
2453 *  have been initialized . Returns 0 if all is well nz
2454 *  otherwise . Does not allocate memory but sets up card
2455 *  using previously allocated descriptors.
2456 */
2457static int mpi_init_descriptors (struct airo_info *ai)
2458{
2459	Cmd cmd;
2460	Resp rsp;
2461	int i;
2462	int rc = SUCCESS;
2463
2464	/* Alloc  card RX descriptors */
2465	netif_stop_queue(ai->dev);
2466
2467	memset(&rsp,0,sizeof(rsp));
2468	memset(&cmd,0,sizeof(cmd));
2469
2470	cmd.cmd = CMD_ALLOCATEAUX;
2471	cmd.parm0 = FID_RX;
2472	cmd.parm1 = (ai->rxfids[0].card_ram_off - ai->pciaux);
2473	cmd.parm2 = MPI_MAX_FIDS;
2474	rc=issuecommand(ai, &cmd, &rsp);
2475	if (rc != SUCCESS) {
2476		airo_print_err(ai->dev->name, "Couldn't allocate RX FID");
2477		return rc;
2478	}
2479
2480	for (i=0; i<MPI_MAX_FIDS; i++) {
2481		memcpy_toio(ai->rxfids[i].card_ram_off,
2482			&ai->rxfids[i].rx_desc, sizeof(RxFid));
2483	}
2484
2485	/* Alloc card TX descriptors */
2486
2487	memset(&rsp,0,sizeof(rsp));
2488	memset(&cmd,0,sizeof(cmd));
2489
2490	cmd.cmd = CMD_ALLOCATEAUX;
2491	cmd.parm0 = FID_TX;
2492	cmd.parm1 = (ai->txfids[0].card_ram_off - ai->pciaux);
2493	cmd.parm2 = MPI_MAX_FIDS;
2494
2495	for (i=0; i<MPI_MAX_FIDS; i++) {
2496		ai->txfids[i].tx_desc.valid = 1;
2497		memcpy_toio(ai->txfids[i].card_ram_off,
2498			&ai->txfids[i].tx_desc, sizeof(TxFid));
2499	}
2500	ai->txfids[i-1].tx_desc.eoc = 1; /* Last descriptor has EOC set */
2501
2502	rc=issuecommand(ai, &cmd, &rsp);
2503	if (rc != SUCCESS) {
2504		airo_print_err(ai->dev->name, "Couldn't allocate TX FID");
2505		return rc;
2506	}
2507
2508	/* Alloc card Rid descriptor */
2509	memset(&rsp,0,sizeof(rsp));
2510	memset(&cmd,0,sizeof(cmd));
2511
2512	cmd.cmd = CMD_ALLOCATEAUX;
2513	cmd.parm0 = RID_RW;
2514	cmd.parm1 = (ai->config_desc.card_ram_off - ai->pciaux);
2515	cmd.parm2 = 1; /* Magic number... */
2516	rc=issuecommand(ai, &cmd, &rsp);
2517	if (rc != SUCCESS) {
2518		airo_print_err(ai->dev->name, "Couldn't allocate RID");
2519		return rc;
2520	}
2521
2522	memcpy_toio(ai->config_desc.card_ram_off,
2523		&ai->config_desc.rid_desc, sizeof(Rid));
2524
2525	return rc;
2526}
2527
2528/*
2529 * We are setting up three things here:
2530 * 1) Map AUX memory for descriptors: Rid, TxFid, or RxFid.
2531 * 2) Map PCI memory for issuing commands.
2532 * 3) Allocate memory (shared) to send and receive ethernet frames.
2533 */
2534static int mpi_map_card(struct airo_info *ai, struct pci_dev *pci)
2535{
2536	unsigned long mem_start, mem_len, aux_start, aux_len;
2537	int rc = -1;
2538	int i;
2539	dma_addr_t busaddroff;
2540	unsigned char *vpackoff;
2541	unsigned char __iomem *pciaddroff;
2542
2543	mem_start = pci_resource_start(pci, 1);
2544	mem_len = pci_resource_len(pci, 1);
2545	aux_start = pci_resource_start(pci, 2);
2546	aux_len = AUXMEMSIZE;
2547
2548	if (!request_mem_region(mem_start, mem_len, DRV_NAME)) {
2549		airo_print_err("", "Couldn't get region %x[%x]",
2550			(int)mem_start, (int)mem_len);
2551		goto out;
2552	}
2553	if (!request_mem_region(aux_start, aux_len, DRV_NAME)) {
2554		airo_print_err("", "Couldn't get region %x[%x]",
2555			(int)aux_start, (int)aux_len);
2556		goto free_region1;
2557	}
2558
2559	ai->pcimem = ioremap(mem_start, mem_len);
2560	if (!ai->pcimem) {
2561		airo_print_err("", "Couldn't map region %x[%x]",
2562			(int)mem_start, (int)mem_len);
2563		goto free_region2;
2564	}
2565	ai->pciaux = ioremap(aux_start, aux_len);
2566	if (!ai->pciaux) {
2567		airo_print_err("", "Couldn't map region %x[%x]",
2568			(int)aux_start, (int)aux_len);
2569		goto free_memmap;
2570	}
2571
2572	/* Reserve PKTSIZE for each fid and 2K for the Rids */
2573	ai->shared = pci_alloc_consistent(pci, PCI_SHARED_LEN, &ai->shared_dma);
 
2574	if (!ai->shared) {
2575		airo_print_err("", "Couldn't alloc_consistent %d",
2576			PCI_SHARED_LEN);
2577		goto free_auxmap;
2578	}
2579
2580	/*
2581	 * Setup descriptor RX, TX, CONFIG
2582	 */
2583	busaddroff = ai->shared_dma;
2584	pciaddroff = ai->pciaux + AUX_OFFSET;
2585	vpackoff   = ai->shared;
2586
2587	/* RX descriptor setup */
2588	for(i = 0; i < MPI_MAX_FIDS; i++) {
2589		ai->rxfids[i].pending = 0;
2590		ai->rxfids[i].card_ram_off = pciaddroff;
2591		ai->rxfids[i].virtual_host_addr = vpackoff;
2592		ai->rxfids[i].rx_desc.host_addr = busaddroff;
2593		ai->rxfids[i].rx_desc.valid = 1;
2594		ai->rxfids[i].rx_desc.len = PKTSIZE;
2595		ai->rxfids[i].rx_desc.rdy = 0;
2596
2597		pciaddroff += sizeof(RxFid);
2598		busaddroff += PKTSIZE;
2599		vpackoff   += PKTSIZE;
2600	}
2601
2602	/* TX descriptor setup */
2603	for(i = 0; i < MPI_MAX_FIDS; i++) {
2604		ai->txfids[i].card_ram_off = pciaddroff;
2605		ai->txfids[i].virtual_host_addr = vpackoff;
2606		ai->txfids[i].tx_desc.valid = 1;
2607		ai->txfids[i].tx_desc.host_addr = busaddroff;
2608		memcpy(ai->txfids[i].virtual_host_addr,
2609			&wifictlhdr8023, sizeof(wifictlhdr8023));
2610
2611		pciaddroff += sizeof(TxFid);
2612		busaddroff += PKTSIZE;
2613		vpackoff   += PKTSIZE;
2614	}
2615	ai->txfids[i-1].tx_desc.eoc = 1; /* Last descriptor has EOC set */
2616
2617	/* Rid descriptor setup */
2618	ai->config_desc.card_ram_off = pciaddroff;
2619	ai->config_desc.virtual_host_addr = vpackoff;
2620	ai->config_desc.rid_desc.host_addr = busaddroff;
2621	ai->ridbus = busaddroff;
2622	ai->config_desc.rid_desc.rid = 0;
2623	ai->config_desc.rid_desc.len = RIDSIZE;
2624	ai->config_desc.rid_desc.valid = 1;
2625	pciaddroff += sizeof(Rid);
2626	busaddroff += RIDSIZE;
2627	vpackoff   += RIDSIZE;
2628
2629	/* Tell card about descriptors */
2630	if (mpi_init_descriptors (ai) != SUCCESS)
2631		goto free_shared;
2632
2633	return 0;
2634 free_shared:
2635	pci_free_consistent(pci, PCI_SHARED_LEN, ai->shared, ai->shared_dma);
 
2636 free_auxmap:
2637	iounmap(ai->pciaux);
2638 free_memmap:
2639	iounmap(ai->pcimem);
2640 free_region2:
2641	release_mem_region(aux_start, aux_len);
2642 free_region1:
2643	release_mem_region(mem_start, mem_len);
2644 out:
2645	return rc;
2646}
2647
2648static const struct header_ops airo_header_ops = {
2649	.parse = wll_header_parse,
2650};
2651
2652static const struct net_device_ops airo11_netdev_ops = {
2653	.ndo_open 		= airo_open,
2654	.ndo_stop 		= airo_close,
2655	.ndo_start_xmit 	= airo_start_xmit11,
2656	.ndo_get_stats 		= airo_get_stats,
2657	.ndo_set_mac_address	= airo_set_mac_address,
2658	.ndo_do_ioctl		= airo_ioctl,
2659	.ndo_change_mtu		= airo_change_mtu,
2660};
2661
2662static void wifi_setup(struct net_device *dev)
2663{
2664	dev->netdev_ops = &airo11_netdev_ops;
2665	dev->header_ops = &airo_header_ops;
2666	dev->wireless_handlers = &airo_handler_def;
2667
2668	dev->type               = ARPHRD_IEEE80211;
2669	dev->hard_header_len    = ETH_HLEN;
2670	dev->mtu                = AIRO_DEF_MTU;
 
 
2671	dev->addr_len           = ETH_ALEN;
2672	dev->tx_queue_len       = 100; 
2673
2674	eth_broadcast_addr(dev->broadcast);
2675
2676	dev->flags              = IFF_BROADCAST|IFF_MULTICAST;
2677}
2678
2679static struct net_device *init_wifidev(struct airo_info *ai,
2680					struct net_device *ethdev)
2681{
2682	int err;
2683	struct net_device *dev = alloc_netdev(0, "wifi%d", NET_NAME_UNKNOWN,
2684					      wifi_setup);
2685	if (!dev)
2686		return NULL;
2687	dev->ml_priv = ethdev->ml_priv;
2688	dev->irq = ethdev->irq;
2689	dev->base_addr = ethdev->base_addr;
2690	dev->wireless_data = ethdev->wireless_data;
2691	SET_NETDEV_DEV(dev, ethdev->dev.parent);
2692	eth_hw_addr_inherit(dev, ethdev);
2693	err = register_netdev(dev);
2694	if (err<0) {
2695		free_netdev(dev);
2696		return NULL;
2697	}
2698	return dev;
2699}
2700
2701static int reset_card( struct net_device *dev , int lock) {
 
2702	struct airo_info *ai = dev->ml_priv;
2703
2704	if (lock && down_interruptible(&ai->sem))
2705		return -1;
2706	waitbusy (ai);
2707	OUT4500(ai,COMMAND,CMD_SOFTRESET);
2708	msleep(200);
2709	waitbusy (ai);
2710	msleep(200);
2711	if (lock)
2712		up(&ai->sem);
2713	return 0;
2714}
2715
2716#define AIRO_MAX_NETWORK_COUNT	64
2717static int airo_networks_allocate(struct airo_info *ai)
2718{
2719	if (ai->networks)
2720		return 0;
2721
2722	ai->networks = kcalloc(AIRO_MAX_NETWORK_COUNT, sizeof(BSSListElement),
2723			       GFP_KERNEL);
2724	if (!ai->networks) {
2725		airo_print_warn("", "Out of memory allocating beacons");
2726		return -ENOMEM;
2727	}
2728
2729	return 0;
2730}
2731
2732static void airo_networks_free(struct airo_info *ai)
2733{
2734	kfree(ai->networks);
2735	ai->networks = NULL;
2736}
2737
2738static void airo_networks_initialize(struct airo_info *ai)
2739{
2740	int i;
2741
2742	INIT_LIST_HEAD(&ai->network_free_list);
2743	INIT_LIST_HEAD(&ai->network_list);
2744	for (i = 0; i < AIRO_MAX_NETWORK_COUNT; i++)
2745		list_add_tail(&ai->networks[i].list,
2746			      &ai->network_free_list);
2747}
2748
2749static const struct net_device_ops airo_netdev_ops = {
2750	.ndo_open		= airo_open,
2751	.ndo_stop		= airo_close,
2752	.ndo_start_xmit		= airo_start_xmit,
2753	.ndo_get_stats		= airo_get_stats,
2754	.ndo_set_rx_mode	= airo_set_multicast_list,
2755	.ndo_set_mac_address	= airo_set_mac_address,
2756	.ndo_do_ioctl		= airo_ioctl,
2757	.ndo_change_mtu		= airo_change_mtu,
2758	.ndo_validate_addr	= eth_validate_addr,
2759};
2760
2761static const struct net_device_ops mpi_netdev_ops = {
2762	.ndo_open		= airo_open,
2763	.ndo_stop		= airo_close,
2764	.ndo_start_xmit		= mpi_start_xmit,
2765	.ndo_get_stats		= airo_get_stats,
2766	.ndo_set_rx_mode	= airo_set_multicast_list,
2767	.ndo_set_mac_address	= airo_set_mac_address,
2768	.ndo_do_ioctl		= airo_ioctl,
2769	.ndo_change_mtu		= airo_change_mtu,
2770	.ndo_validate_addr	= eth_validate_addr,
2771};
2772
2773
2774static struct net_device *_init_airo_card( unsigned short irq, int port,
2775					   int is_pcmcia, struct pci_dev *pci,
2776					   struct device *dmdev )
2777{
2778	struct net_device *dev;
2779	struct airo_info *ai;
2780	int i, rc;
2781	CapabilityRid cap_rid;
2782
2783	/* Create the network device object. */
2784	dev = alloc_netdev(sizeof(*ai), "", NET_NAME_UNKNOWN, ether_setup);
2785	if (!dev) {
2786		airo_print_err("", "Couldn't alloc_etherdev");
2787		return NULL;
2788	}
2789
2790	ai = dev->ml_priv = netdev_priv(dev);
2791	ai->wifidev = NULL;
2792	ai->flags = 1 << FLAG_RADIO_DOWN;
2793	ai->jobs = 0;
2794	ai->dev = dev;
2795	if (pci && (pci->device == 0x5000 || pci->device == 0xa504)) {
2796		airo_print_dbg("", "Found an MPI350 card");
2797		set_bit(FLAG_MPI, &ai->flags);
2798	}
2799	spin_lock_init(&ai->aux_lock);
2800	sema_init(&ai->sem, 1);
2801	ai->config.len = 0;
2802	ai->pci = pci;
2803	init_waitqueue_head (&ai->thr_wait);
2804	ai->tfm = NULL;
2805	add_airo_dev(ai);
2806	ai->APList.len = cpu_to_le16(sizeof(struct APListRid));
2807
2808	if (airo_networks_allocate (ai))
2809		goto err_out_free;
2810	airo_networks_initialize (ai);
2811
2812	skb_queue_head_init (&ai->txq);
2813
2814	/* The Airo-specific entries in the device structure. */
2815	if (test_bit(FLAG_MPI,&ai->flags))
2816		dev->netdev_ops = &mpi_netdev_ops;
2817	else
2818		dev->netdev_ops = &airo_netdev_ops;
2819	dev->wireless_handlers = &airo_handler_def;
2820	ai->wireless_data.spy_data = &ai->spy_data;
2821	dev->wireless_data = &ai->wireless_data;
2822	dev->irq = irq;
2823	dev->base_addr = port;
2824	dev->priv_flags &= ~IFF_TX_SKB_SHARING;
 
2825
2826	SET_NETDEV_DEV(dev, dmdev);
2827
2828	reset_card (dev, 1);
2829	msleep(400);
2830
2831	if (!is_pcmcia) {
2832		if (!request_region(dev->base_addr, 64, DRV_NAME)) {
2833			rc = -EBUSY;
2834			airo_print_err(dev->name, "Couldn't request region");
2835			goto err_out_nets;
2836		}
2837	}
2838
2839	if (test_bit(FLAG_MPI,&ai->flags)) {
2840		if (mpi_map_card(ai, pci)) {
2841			airo_print_err("", "Could not map memory");
2842			goto err_out_res;
2843		}
2844	}
2845
2846	if (probe) {
2847		if (setup_card(ai, dev->dev_addr, 1) != SUCCESS) {
2848			airo_print_err(dev->name, "MAC could not be enabled" );
2849			rc = -EIO;
2850			goto err_out_map;
2851		}
2852	} else if (!test_bit(FLAG_MPI,&ai->flags)) {
2853		ai->bap_read = fast_bap_read;
2854		set_bit(FLAG_FLASHING, &ai->flags);
2855	}
2856
2857	strcpy(dev->name, "eth%d");
2858	rc = register_netdev(dev);
2859	if (rc) {
2860		airo_print_err(dev->name, "Couldn't register_netdev");
2861		goto err_out_map;
2862	}
2863	ai->wifidev = init_wifidev(ai, dev);
2864	if (!ai->wifidev)
2865		goto err_out_reg;
2866
2867	rc = readCapabilityRid(ai, &cap_rid, 1);
2868	if (rc != SUCCESS) {
2869		rc = -EIO;
2870		goto err_out_wifi;
2871	}
2872	/* WEP capability discovery */
2873	ai->wep_capable = (cap_rid.softCap & cpu_to_le16(0x02)) ? 1 : 0;
2874	ai->max_wep_idx = (cap_rid.softCap & cpu_to_le16(0x80)) ? 3 : 0;
2875
2876	airo_print_info(dev->name, "Firmware version %x.%x.%02d",
2877	                ((le16_to_cpu(cap_rid.softVer) >> 8) & 0xF),
2878	                (le16_to_cpu(cap_rid.softVer) & 0xFF),
2879	                le16_to_cpu(cap_rid.softSubVer));
2880
2881	/* Test for WPA support */
2882	/* Only firmware versions 5.30.17 or better can do WPA */
2883	if (le16_to_cpu(cap_rid.softVer) > 0x530
2884	 || (le16_to_cpu(cap_rid.softVer) == 0x530
2885	      && le16_to_cpu(cap_rid.softSubVer) >= 17)) {
2886		airo_print_info(ai->dev->name, "WPA supported.");
2887
2888		set_bit(FLAG_WPA_CAPABLE, &ai->flags);
2889		ai->bssListFirst = RID_WPA_BSSLISTFIRST;
2890		ai->bssListNext = RID_WPA_BSSLISTNEXT;
2891		ai->bssListRidLen = sizeof(BSSListRid);
2892	} else {
2893		airo_print_info(ai->dev->name, "WPA unsupported with firmware "
2894			"versions older than 5.30.17.");
2895
2896		ai->bssListFirst = RID_BSSLISTFIRST;
2897		ai->bssListNext = RID_BSSLISTNEXT;
2898		ai->bssListRidLen = sizeof(BSSListRid) - sizeof(BSSListRidExtra);
2899	}
2900
2901	set_bit(FLAG_REGISTERED,&ai->flags);
2902	airo_print_info(dev->name, "MAC enabled %pM", dev->dev_addr);
2903
2904	/* Allocate the transmit buffers */
2905	if (probe && !test_bit(FLAG_MPI,&ai->flags))
2906		for( i = 0; i < MAX_FIDS; i++ )
2907			ai->fids[i] = transmit_allocate(ai,AIRO_DEF_MTU,i>=MAX_FIDS/2);
2908
2909	if (setup_proc_entry(dev, dev->ml_priv) < 0)
2910		goto err_out_wifi;
2911
2912	return dev;
2913
2914err_out_wifi:
2915	unregister_netdev(ai->wifidev);
2916	free_netdev(ai->wifidev);
2917err_out_reg:
2918	unregister_netdev(dev);
2919err_out_map:
2920	if (test_bit(FLAG_MPI,&ai->flags) && pci) {
2921		pci_free_consistent(pci, PCI_SHARED_LEN, ai->shared, ai->shared_dma);
 
2922		iounmap(ai->pciaux);
2923		iounmap(ai->pcimem);
2924		mpi_unmap_card(ai->pci);
2925	}
2926err_out_res:
2927	if (!is_pcmcia)
2928	        release_region( dev->base_addr, 64 );
2929err_out_nets:
2930	airo_networks_free(ai);
2931err_out_free:
2932	del_airo_dev(ai);
2933	free_netdev(dev);
2934	return NULL;
2935}
2936
2937struct net_device *init_airo_card( unsigned short irq, int port, int is_pcmcia,
2938				  struct device *dmdev)
2939{
2940	return _init_airo_card ( irq, port, is_pcmcia, NULL, dmdev);
2941}
2942
2943EXPORT_SYMBOL(init_airo_card);
2944
2945static int waitbusy (struct airo_info *ai) {
 
2946	int delay = 0;
2947	while ((IN4500(ai, COMMAND) & COMMAND_BUSY) && (delay < 10000)) {
2948		udelay (10);
2949		if ((++delay % 20) == 0)
2950			OUT4500(ai, EVACK, EV_CLEARCOMMANDBUSY);
2951	}
2952	return delay < 10000;
2953}
2954
2955int reset_airo_card( struct net_device *dev )
2956{
2957	int i;
2958	struct airo_info *ai = dev->ml_priv;
2959
2960	if (reset_card (dev, 1))
2961		return -1;
2962
2963	if ( setup_card(ai, dev->dev_addr, 1 ) != SUCCESS ) {
2964		airo_print_err(dev->name, "MAC could not be enabled");
2965		return -1;
2966	}
2967	airo_print_info(dev->name, "MAC enabled %pM", dev->dev_addr);
2968	/* Allocate the transmit buffers if needed */
2969	if (!test_bit(FLAG_MPI,&ai->flags))
2970		for( i = 0; i < MAX_FIDS; i++ )
2971			ai->fids[i] = transmit_allocate (ai,AIRO_DEF_MTU,i>=MAX_FIDS/2);
2972
2973	enable_interrupts( ai );
2974	netif_wake_queue(dev);
2975	return 0;
2976}
2977
2978EXPORT_SYMBOL(reset_airo_card);
2979
2980static void airo_send_event(struct net_device *dev) {
 
2981	struct airo_info *ai = dev->ml_priv;
2982	union iwreq_data wrqu;
2983	StatusRid status_rid;
2984
2985	clear_bit(JOB_EVENT, &ai->jobs);
2986	PC4500_readrid(ai, RID_STATUS, &status_rid, sizeof(status_rid), 0);
2987	up(&ai->sem);
2988	wrqu.data.length = 0;
2989	wrqu.data.flags = 0;
2990	memcpy(wrqu.ap_addr.sa_data, status_rid.bssid[0], ETH_ALEN);
2991	wrqu.ap_addr.sa_family = ARPHRD_ETHER;
2992
2993	/* Send event to user space */
2994	wireless_send_event(dev, SIOCGIWAP, &wrqu, NULL);
2995}
2996
2997static void airo_process_scan_results (struct airo_info *ai) {
 
2998	union iwreq_data	wrqu;
2999	BSSListRid bss;
3000	int rc;
3001	BSSListElement * loop_net;
3002	BSSListElement * tmp_net;
3003
3004	/* Blow away current list of scan results */
3005	list_for_each_entry_safe (loop_net, tmp_net, &ai->network_list, list) {
3006		list_move_tail (&loop_net->list, &ai->network_free_list);
3007		/* Don't blow away ->list, just BSS data */
3008		memset (loop_net, 0, sizeof (loop_net->bss));
3009	}
3010
3011	/* Try to read the first entry of the scan result */
3012	rc = PC4500_readrid(ai, ai->bssListFirst, &bss, ai->bssListRidLen, 0);
3013	if((rc) || (bss.index == cpu_to_le16(0xffff))) {
3014		/* No scan results */
3015		goto out;
3016	}
3017
3018	/* Read and parse all entries */
3019	tmp_net = NULL;
3020	while((!rc) && (bss.index != cpu_to_le16(0xffff))) {
3021		/* Grab a network off the free list */
3022		if (!list_empty(&ai->network_free_list)) {
3023			tmp_net = list_entry(ai->network_free_list.next,
3024					    BSSListElement, list);
3025			list_del(ai->network_free_list.next);
3026		}
3027
3028		if (tmp_net != NULL) {
3029			memcpy(tmp_net, &bss, sizeof(tmp_net->bss));
3030			list_add_tail(&tmp_net->list, &ai->network_list);
3031			tmp_net = NULL;
3032		}
3033
3034		/* Read next entry */
3035		rc = PC4500_readrid(ai, ai->bssListNext,
3036				    &bss, ai->bssListRidLen, 0);
3037	}
3038
3039out:
3040	/* write APList back (we cleared it in airo_set_scan) */
3041	disable_MAC(ai, 2);
3042	writeAPListRid(ai, &ai->APList, 0);
3043	enable_MAC(ai, 0);
3044
3045	ai->scan_timeout = 0;
3046	clear_bit(JOB_SCAN_RESULTS, &ai->jobs);
3047	up(&ai->sem);
3048
3049	/* Send an empty event to user space.
3050	 * We don't send the received data on
3051	 * the event because it would require
3052	 * us to do complex transcoding, and
3053	 * we want to minimise the work done in
3054	 * the irq handler. Use a request to
3055	 * extract the data - Jean II */
3056	wrqu.data.length = 0;
3057	wrqu.data.flags = 0;
3058	wireless_send_event(ai->dev, SIOCGIWSCAN, &wrqu, NULL);
3059}
3060
3061static int airo_thread(void *data) {
 
3062	struct net_device *dev = data;
3063	struct airo_info *ai = dev->ml_priv;
3064	int locked;
3065
3066	set_freezable();
3067	while(1) {
3068		/* make swsusp happy with our thread */
3069		try_to_freeze();
3070
3071		if (test_bit(JOB_DIE, &ai->jobs))
3072			break;
3073
3074		if (ai->jobs) {
3075			locked = down_interruptible(&ai->sem);
3076		} else {
3077			wait_queue_t wait;
3078
3079			init_waitqueue_entry(&wait, current);
3080			add_wait_queue(&ai->thr_wait, &wait);
3081			for (;;) {
3082				set_current_state(TASK_INTERRUPTIBLE);
3083				if (ai->jobs)
3084					break;
3085				if (ai->expires || ai->scan_timeout) {
3086					if (ai->scan_timeout &&
3087							time_after_eq(jiffies,ai->scan_timeout)){
3088						set_bit(JOB_SCAN_RESULTS, &ai->jobs);
3089						break;
3090					} else if (ai->expires &&
3091							time_after_eq(jiffies,ai->expires)){
3092						set_bit(JOB_AUTOWEP, &ai->jobs);
3093						break;
3094					}
3095					if (!kthread_should_stop() &&
3096					    !freezing(current)) {
3097						unsigned long wake_at;
3098						if (!ai->expires || !ai->scan_timeout) {
3099							wake_at = max(ai->expires,
3100								ai->scan_timeout);
3101						} else {
3102							wake_at = min(ai->expires,
3103								ai->scan_timeout);
3104						}
3105						schedule_timeout(wake_at - jiffies);
3106						continue;
3107					}
3108				} else if (!kthread_should_stop() &&
3109					   !freezing(current)) {
3110					schedule();
3111					continue;
3112				}
3113				break;
3114			}
3115			current->state = TASK_RUNNING;
3116			remove_wait_queue(&ai->thr_wait, &wait);
3117			locked = 1;
3118		}
3119
3120		if (locked)
3121			continue;
3122
3123		if (test_bit(JOB_DIE, &ai->jobs)) {
3124			up(&ai->sem);
3125			break;
3126		}
3127
3128		if (ai->power.event || test_bit(FLAG_FLASHING, &ai->flags)) {
3129			up(&ai->sem);
3130			continue;
3131		}
3132
3133		if (test_bit(JOB_XMIT, &ai->jobs))
3134			airo_end_xmit(dev);
3135		else if (test_bit(JOB_XMIT11, &ai->jobs))
3136			airo_end_xmit11(dev);
3137		else if (test_bit(JOB_STATS, &ai->jobs))
3138			airo_read_stats(dev);
3139		else if (test_bit(JOB_WSTATS, &ai->jobs))
3140			airo_read_wireless_stats(ai);
3141		else if (test_bit(JOB_PROMISC, &ai->jobs))
3142			airo_set_promisc(ai);
3143		else if (test_bit(JOB_MIC, &ai->jobs))
3144			micinit(ai);
3145		else if (test_bit(JOB_EVENT, &ai->jobs))
3146			airo_send_event(dev);
3147		else if (test_bit(JOB_AUTOWEP, &ai->jobs))
3148			timer_func(dev);
3149		else if (test_bit(JOB_SCAN_RESULTS, &ai->jobs))
3150			airo_process_scan_results(ai);
3151		else  /* Shouldn't get here, but we make sure to unlock */
3152			up(&ai->sem);
3153	}
3154
3155	return 0;
3156}
3157
3158static int header_len(__le16 ctl)
3159{
3160	u16 fc = le16_to_cpu(ctl);
3161	switch (fc & 0xc) {
3162	case 4:
3163		if ((fc & 0xe0) == 0xc0)
3164			return 10;	/* one-address control packet */
3165		return 16;	/* two-address control packet */
3166	case 8:
3167		if ((fc & 0x300) == 0x300)
3168			return 30;	/* WDS packet */
3169	}
3170	return 24;
3171}
3172
3173static void airo_handle_cisco_mic(struct airo_info *ai)
3174{
3175	if (test_bit(FLAG_MIC_CAPABLE, &ai->flags)) {
3176		set_bit(JOB_MIC, &ai->jobs);
3177		wake_up_interruptible(&ai->thr_wait);
3178	}
3179}
3180
3181/* Airo Status codes */
3182#define STAT_NOBEACON	0x8000 /* Loss of sync - missed beacons */
3183#define STAT_MAXRETRIES	0x8001 /* Loss of sync - max retries */
3184#define STAT_MAXARL	0x8002 /* Loss of sync - average retry level exceeded*/
3185#define STAT_FORCELOSS	0x8003 /* Loss of sync - host request */
3186#define STAT_TSFSYNC	0x8004 /* Loss of sync - TSF synchronization */
3187#define STAT_DEAUTH	0x8100 /* low byte is 802.11 reason code */
3188#define STAT_DISASSOC	0x8200 /* low byte is 802.11 reason code */
3189#define STAT_ASSOC_FAIL	0x8400 /* low byte is 802.11 reason code */
3190#define STAT_AUTH_FAIL	0x0300 /* low byte is 802.11 reason code */
3191#define STAT_ASSOC	0x0400 /* Associated */
3192#define STAT_REASSOC    0x0600 /* Reassociated?  Only on firmware >= 5.30.17 */
3193
3194static void airo_print_status(const char *devname, u16 status)
3195{
3196	u8 reason = status & 0xFF;
3197
3198	switch (status & 0xFF00) {
3199	case STAT_NOBEACON:
3200		switch (status) {
3201		case STAT_NOBEACON:
3202			airo_print_dbg(devname, "link lost (missed beacons)");
3203			break;
3204		case STAT_MAXRETRIES:
3205		case STAT_MAXARL:
3206			airo_print_dbg(devname, "link lost (max retries)");
3207			break;
3208		case STAT_FORCELOSS:
3209			airo_print_dbg(devname, "link lost (local choice)");
3210			break;
3211		case STAT_TSFSYNC:
3212			airo_print_dbg(devname, "link lost (TSF sync lost)");
3213			break;
3214		default:
3215			airo_print_dbg(devname, "unknown status %x\n", status);
3216			break;
3217		}
3218		break;
3219	case STAT_DEAUTH:
3220		airo_print_dbg(devname, "deauthenticated (reason: %d)", reason);
3221		break;
3222	case STAT_DISASSOC:
3223		airo_print_dbg(devname, "disassociated (reason: %d)", reason);
3224		break;
3225	case STAT_ASSOC_FAIL:
3226		airo_print_dbg(devname, "association failed (reason: %d)",
3227			       reason);
3228		break;
3229	case STAT_AUTH_FAIL:
3230		airo_print_dbg(devname, "authentication failed (reason: %d)",
3231			       reason);
3232		break;
3233	case STAT_ASSOC:
3234	case STAT_REASSOC:
3235		break;
3236	default:
3237		airo_print_dbg(devname, "unknown status %x\n", status);
3238		break;
3239	}
3240}
3241
3242static void airo_handle_link(struct airo_info *ai)
3243{
3244	union iwreq_data wrqu;
3245	int scan_forceloss = 0;
3246	u16 status;
3247
3248	/* Get new status and acknowledge the link change */
3249	status = le16_to_cpu(IN4500(ai, LINKSTAT));
3250	OUT4500(ai, EVACK, EV_LINK);
3251
3252	if ((status == STAT_FORCELOSS) && (ai->scan_timeout > 0))
3253		scan_forceloss = 1;
3254
3255	airo_print_status(ai->dev->name, status);
3256
3257	if ((status == STAT_ASSOC) || (status == STAT_REASSOC)) {
3258		if (auto_wep)
3259			ai->expires = 0;
3260		if (ai->list_bss_task)
3261			wake_up_process(ai->list_bss_task);
3262		set_bit(FLAG_UPDATE_UNI, &ai->flags);
3263		set_bit(FLAG_UPDATE_MULTI, &ai->flags);
3264
3265		if (down_trylock(&ai->sem) != 0) {
3266			set_bit(JOB_EVENT, &ai->jobs);
3267			wake_up_interruptible(&ai->thr_wait);
3268		} else
3269			airo_send_event(ai->dev);
3270		netif_carrier_on(ai->dev);
3271	} else if (!scan_forceloss) {
3272		if (auto_wep && !ai->expires) {
3273			ai->expires = RUN_AT(3*HZ);
3274			wake_up_interruptible(&ai->thr_wait);
3275		}
3276
3277		/* Send event to user space */
3278		eth_zero_addr(wrqu.ap_addr.sa_data);
3279		wrqu.ap_addr.sa_family = ARPHRD_ETHER;
3280		wireless_send_event(ai->dev, SIOCGIWAP, &wrqu, NULL);
3281		netif_carrier_off(ai->dev);
3282	} else {
3283		netif_carrier_off(ai->dev);
3284	}
3285}
3286
3287static void airo_handle_rx(struct airo_info *ai)
3288{
3289	struct sk_buff *skb = NULL;
3290	__le16 fc, v, *buffer, tmpbuf[4];
3291	u16 len, hdrlen = 0, gap, fid;
3292	struct rx_hdr hdr;
3293	int success = 0;
3294
3295	if (test_bit(FLAG_MPI, &ai->flags)) {
3296		if (test_bit(FLAG_802_11, &ai->flags))
3297			mpi_receive_802_11(ai);
3298		else
3299			mpi_receive_802_3(ai);
3300		OUT4500(ai, EVACK, EV_RX);
3301		return;
3302	}
3303
3304	fid = IN4500(ai, RXFID);
3305
3306	/* Get the packet length */
3307	if (test_bit(FLAG_802_11, &ai->flags)) {
3308		bap_setup (ai, fid, 4, BAP0);
3309		bap_read (ai, (__le16*)&hdr, sizeof(hdr), BAP0);
3310		/* Bad CRC. Ignore packet */
3311		if (le16_to_cpu(hdr.status) & 2)
3312			hdr.len = 0;
3313		if (ai->wifidev == NULL)
3314			hdr.len = 0;
3315	} else {
3316		bap_setup(ai, fid, 0x36, BAP0);
3317		bap_read(ai, &hdr.len, 2, BAP0);
3318	}
3319	len = le16_to_cpu(hdr.len);
3320
3321	if (len > AIRO_DEF_MTU) {
3322		airo_print_err(ai->dev->name, "Bad size %d", len);
3323		goto done;
3324	}
3325	if (len == 0)
3326		goto done;
3327
3328	if (test_bit(FLAG_802_11, &ai->flags)) {
3329		bap_read(ai, &fc, sizeof (fc), BAP0);
3330		hdrlen = header_len(fc);
3331	} else
3332		hdrlen = ETH_ALEN * 2;
3333
3334	skb = dev_alloc_skb(len + hdrlen + 2 + 2);
3335	if (!skb) {
3336		ai->dev->stats.rx_dropped++;
3337		goto done;
3338	}
3339
3340	skb_reserve(skb, 2); /* This way the IP header is aligned */
3341	buffer = (__le16 *) skb_put(skb, len + hdrlen);
3342	if (test_bit(FLAG_802_11, &ai->flags)) {
3343		buffer[0] = fc;
3344		bap_read(ai, buffer + 1, hdrlen - 2, BAP0);
3345		if (hdrlen == 24)
3346			bap_read(ai, tmpbuf, 6, BAP0);
3347
3348		bap_read(ai, &v, sizeof(v), BAP0);
3349		gap = le16_to_cpu(v);
3350		if (gap) {
3351			if (gap <= 8) {
3352				bap_read(ai, tmpbuf, gap, BAP0);
3353			} else {
3354				airo_print_err(ai->dev->name, "gaplen too "
3355					"big. Problems will follow...");
3356			}
3357		}
3358		bap_read(ai, buffer + hdrlen/2, len, BAP0);
3359	} else {
3360		MICBuffer micbuf;
3361
3362		bap_read(ai, buffer, ETH_ALEN * 2, BAP0);
3363		if (ai->micstats.enabled) {
3364			bap_read(ai, (__le16 *) &micbuf, sizeof (micbuf), BAP0);
3365			if (ntohs(micbuf.typelen) > 0x05DC)
3366				bap_setup(ai, fid, 0x44, BAP0);
3367			else {
3368				if (len <= sizeof (micbuf)) {
3369					dev_kfree_skb_irq(skb);
3370					goto done;
3371				}
3372
3373				len -= sizeof(micbuf);
3374				skb_trim(skb, len + hdrlen);
3375			}
3376		}
3377
3378		bap_read(ai, buffer + ETH_ALEN, len, BAP0);
3379		if (decapsulate(ai, &micbuf, (etherHead*) buffer, len))
3380			dev_kfree_skb_irq (skb);
3381		else
3382			success = 1;
3383	}
3384
3385#ifdef WIRELESS_SPY
3386	if (success && (ai->spy_data.spy_number > 0)) {
3387		char *sa;
3388		struct iw_quality wstats;
3389
3390		/* Prepare spy data : addr + qual */
3391		if (!test_bit(FLAG_802_11, &ai->flags)) {
3392			sa = (char *) buffer + 6;
3393			bap_setup(ai, fid, 8, BAP0);
3394			bap_read(ai, (__le16 *) hdr.rssi, 2, BAP0);
3395		} else
3396			sa = (char *) buffer + 10;
3397		wstats.qual = hdr.rssi[0];
3398		if (ai->rssi)
3399			wstats.level = 0x100 - ai->rssi[hdr.rssi[1]].rssidBm;
3400		else
3401			wstats.level = (hdr.rssi[1] + 321) / 2;
3402		wstats.noise = ai->wstats.qual.noise;
3403		wstats.updated =  IW_QUAL_LEVEL_UPDATED
3404				| IW_QUAL_QUAL_UPDATED
3405				| IW_QUAL_DBM;
3406		/* Update spy records */
3407		wireless_spy_update(ai->dev, sa, &wstats);
3408	}
3409#endif /* WIRELESS_SPY */
3410
3411done:
3412	OUT4500(ai, EVACK, EV_RX);
3413
3414	if (success) {
3415		if (test_bit(FLAG_802_11, &ai->flags)) {
3416			skb_reset_mac_header(skb);
3417			skb->pkt_type = PACKET_OTHERHOST;
3418			skb->dev = ai->wifidev;
3419			skb->protocol = htons(ETH_P_802_2);
3420		} else
3421			skb->protocol = eth_type_trans(skb, ai->dev);
3422		skb->ip_summed = CHECKSUM_NONE;
3423
3424		netif_rx(skb);
3425	}
3426}
3427
3428static void airo_handle_tx(struct airo_info *ai, u16 status)
3429{
3430	int i, len = 0, index = -1;
3431	u16 fid;
3432
3433	if (test_bit(FLAG_MPI, &ai->flags)) {
3434		unsigned long flags;
3435
3436		if (status & EV_TXEXC)
3437			get_tx_error(ai, -1);
3438
3439		spin_lock_irqsave(&ai->aux_lock, flags);
3440		if (!skb_queue_empty(&ai->txq)) {
3441			spin_unlock_irqrestore(&ai->aux_lock,flags);
3442			mpi_send_packet(ai->dev);
3443		} else {
3444			clear_bit(FLAG_PENDING_XMIT, &ai->flags);
3445			spin_unlock_irqrestore(&ai->aux_lock,flags);
3446			netif_wake_queue(ai->dev);
3447		}
3448		OUT4500(ai, EVACK, status & (EV_TX | EV_TXCPY | EV_TXEXC));
3449		return;
3450	}
3451
3452	fid = IN4500(ai, TXCOMPLFID);
3453
3454	for(i = 0; i < MAX_FIDS; i++) {
3455		if ((ai->fids[i] & 0xffff) == fid) {
3456			len = ai->fids[i] >> 16;
3457			index = i;
3458		}
3459	}
3460
3461	if (index != -1) {
3462		if (status & EV_TXEXC)
3463			get_tx_error(ai, index);
3464
3465		OUT4500(ai, EVACK, status & (EV_TX | EV_TXEXC));
3466
3467		/* Set up to be used again */
3468		ai->fids[index] &= 0xffff;
3469		if (index < MAX_FIDS / 2) {
3470			if (!test_bit(FLAG_PENDING_XMIT, &ai->flags))
3471				netif_wake_queue(ai->dev);
3472		} else {
3473			if (!test_bit(FLAG_PENDING_XMIT11, &ai->flags))
3474				netif_wake_queue(ai->wifidev);
3475		}
3476	} else {
3477		OUT4500(ai, EVACK, status & (EV_TX | EV_TXCPY | EV_TXEXC));
3478		airo_print_err(ai->dev->name, "Unallocated FID was used to xmit");
3479	}
3480}
3481
3482static irqreturn_t airo_interrupt(int irq, void *dev_id)
3483{
3484	struct net_device *dev = dev_id;
3485	u16 status, savedInterrupts = 0;
3486	struct airo_info *ai = dev->ml_priv;
3487	int handled = 0;
3488
3489	if (!netif_device_present(dev))
3490		return IRQ_NONE;
3491
3492	for (;;) {
3493		status = IN4500(ai, EVSTAT);
3494		if (!(status & STATUS_INTS) || (status == 0xffff))
3495			break;
3496
3497		handled = 1;
3498
3499		if (status & EV_AWAKE) {
3500			OUT4500(ai, EVACK, EV_AWAKE);
3501			OUT4500(ai, EVACK, EV_AWAKE);
3502		}
3503
3504		if (!savedInterrupts) {
3505			savedInterrupts = IN4500(ai, EVINTEN);
3506			OUT4500(ai, EVINTEN, 0);
3507		}
3508
3509		if (status & EV_MIC) {
3510			OUT4500(ai, EVACK, EV_MIC);
3511			airo_handle_cisco_mic(ai);
3512		}
3513
3514		if (status & EV_LINK) {
3515			/* Link status changed */
3516			airo_handle_link(ai);
3517		}
3518
3519		/* Check to see if there is something to receive */
3520		if (status & EV_RX)
3521			airo_handle_rx(ai);
3522
3523		/* Check to see if a packet has been transmitted */
3524		if (status & (EV_TX | EV_TXCPY | EV_TXEXC))
3525			airo_handle_tx(ai, status);
3526
3527		if ( status & ~STATUS_INTS & ~IGNORE_INTS ) {
3528			airo_print_warn(ai->dev->name, "Got weird status %x",
3529				status & ~STATUS_INTS & ~IGNORE_INTS );
3530		}
3531	}
3532
3533	if (savedInterrupts)
3534		OUT4500(ai, EVINTEN, savedInterrupts);
3535
3536	return IRQ_RETVAL(handled);
3537}
3538
3539/*
3540 *  Routines to talk to the card
3541 */
3542
3543/*
3544 *  This was originally written for the 4500, hence the name
3545 *  NOTE:  If use with 8bit mode and SMP bad things will happen!
3546 *         Why would some one do 8 bit IO in an SMP machine?!?
3547 */
3548static void OUT4500( struct airo_info *ai, u16 reg, u16 val ) {
 
3549	if (test_bit(FLAG_MPI,&ai->flags))
3550		reg <<= 1;
3551	if ( !do8bitIO )
3552		outw( val, ai->dev->base_addr + reg );
3553	else {
3554		outb( val & 0xff, ai->dev->base_addr + reg );
3555		outb( val >> 8, ai->dev->base_addr + reg + 1 );
3556	}
3557}
3558
3559static u16 IN4500( struct airo_info *ai, u16 reg ) {
 
3560	unsigned short rc;
3561
3562	if (test_bit(FLAG_MPI,&ai->flags))
3563		reg <<= 1;
3564	if ( !do8bitIO )
3565		rc = inw( ai->dev->base_addr + reg );
3566	else {
3567		rc = inb( ai->dev->base_addr + reg );
3568		rc += ((int)inb( ai->dev->base_addr + reg + 1 )) << 8;
3569	}
3570	return rc;
3571}
3572
3573static int enable_MAC(struct airo_info *ai, int lock)
3574{
3575	int rc;
3576	Cmd cmd;
3577	Resp rsp;
3578
3579	/* FLAG_RADIO_OFF : Radio disabled via /proc or Wireless Extensions
3580	 * FLAG_RADIO_DOWN : Radio disabled via "ifconfig ethX down"
3581	 * Note : we could try to use !netif_running(dev) in enable_MAC()
3582	 * instead of this flag, but I don't trust it *within* the
3583	 * open/close functions, and testing both flags together is
3584	 * "cheaper" - Jean II */
3585	if (ai->flags & FLAG_RADIO_MASK) return SUCCESS;
3586
3587	if (lock && down_interruptible(&ai->sem))
3588		return -ERESTARTSYS;
3589
3590	if (!test_bit(FLAG_ENABLED, &ai->flags)) {
3591		memset(&cmd, 0, sizeof(cmd));
3592		cmd.cmd = MAC_ENABLE;
3593		rc = issuecommand(ai, &cmd, &rsp);
3594		if (rc == SUCCESS)
3595			set_bit(FLAG_ENABLED, &ai->flags);
3596	} else
3597		rc = SUCCESS;
3598
3599	if (lock)
3600	    up(&ai->sem);
3601
3602	if (rc)
3603		airo_print_err(ai->dev->name, "Cannot enable MAC");
3604	else if ((rsp.status & 0xFF00) != 0) {
3605		airo_print_err(ai->dev->name, "Bad MAC enable reason=%x, "
3606			"rid=%x, offset=%d", rsp.rsp0, rsp.rsp1, rsp.rsp2);
3607		rc = ERROR;
3608	}
3609	return rc;
3610}
3611
3612static void disable_MAC( struct airo_info *ai, int lock ) {
 
3613        Cmd cmd;
3614	Resp rsp;
3615
3616	if (lock == 1 && down_interruptible(&ai->sem))
3617		return;
3618
3619	if (test_bit(FLAG_ENABLED, &ai->flags)) {
3620		if (lock != 2) /* lock == 2 means don't disable carrier */
3621			netif_carrier_off(ai->dev);
3622		memset(&cmd, 0, sizeof(cmd));
3623		cmd.cmd = MAC_DISABLE; // disable in case already enabled
3624		issuecommand(ai, &cmd, &rsp);
3625		clear_bit(FLAG_ENABLED, &ai->flags);
3626	}
3627	if (lock == 1)
3628		up(&ai->sem);
3629}
3630
3631static void enable_interrupts( struct airo_info *ai ) {
 
3632	/* Enable the interrupts */
3633	OUT4500( ai, EVINTEN, STATUS_INTS );
3634}
3635
3636static void disable_interrupts( struct airo_info *ai ) {
3637	OUT4500( ai, EVINTEN, 0 );
 
3638}
3639
3640static void mpi_receive_802_3(struct airo_info *ai)
3641{
3642	RxFid rxd;
3643	int len = 0;
3644	struct sk_buff *skb;
3645	char *buffer;
3646	int off = 0;
3647	MICBuffer micbuf;
3648
3649	memcpy_fromio(&rxd, ai->rxfids[0].card_ram_off, sizeof(rxd));
3650	/* Make sure we got something */
3651	if (rxd.rdy && rxd.valid == 0) {
3652		len = rxd.len + 12;
3653		if (len < 12 || len > 2048)
3654			goto badrx;
3655
3656		skb = dev_alloc_skb(len);
3657		if (!skb) {
3658			ai->dev->stats.rx_dropped++;
3659			goto badrx;
3660		}
3661		buffer = skb_put(skb,len);
3662		memcpy(buffer, ai->rxfids[0].virtual_host_addr, ETH_ALEN * 2);
3663		if (ai->micstats.enabled) {
3664			memcpy(&micbuf,
3665				ai->rxfids[0].virtual_host_addr + ETH_ALEN * 2,
3666				sizeof(micbuf));
3667			if (ntohs(micbuf.typelen) <= 0x05DC) {
3668				if (len <= sizeof(micbuf) + ETH_ALEN * 2)
3669					goto badmic;
3670
3671				off = sizeof(micbuf);
3672				skb_trim (skb, len - off);
3673			}
3674		}
3675		memcpy(buffer + ETH_ALEN * 2,
3676			ai->rxfids[0].virtual_host_addr + ETH_ALEN * 2 + off,
3677			len - ETH_ALEN * 2 - off);
3678		if (decapsulate (ai, &micbuf, (etherHead*)buffer, len - off - ETH_ALEN * 2)) {
3679badmic:
3680			dev_kfree_skb_irq (skb);
3681			goto badrx;
3682		}
3683#ifdef WIRELESS_SPY
3684		if (ai->spy_data.spy_number > 0) {
3685			char *sa;
3686			struct iw_quality wstats;
3687			/* Prepare spy data : addr + qual */
3688			sa = buffer + ETH_ALEN;
3689			wstats.qual = 0; /* XXX Where do I get that info from ??? */
3690			wstats.level = 0;
3691			wstats.updated = 0;
3692			/* Update spy records */
3693			wireless_spy_update(ai->dev, sa, &wstats);
3694		}
3695#endif /* WIRELESS_SPY */
3696
3697		skb->ip_summed = CHECKSUM_NONE;
3698		skb->protocol = eth_type_trans(skb, ai->dev);
3699		netif_rx(skb);
3700	}
3701badrx:
3702	if (rxd.valid == 0) {
3703		rxd.valid = 1;
3704		rxd.rdy = 0;
3705		rxd.len = PKTSIZE;
3706		memcpy_toio(ai->rxfids[0].card_ram_off, &rxd, sizeof(rxd));
3707	}
3708}
3709
3710static void mpi_receive_802_11(struct airo_info *ai)
3711{
3712	RxFid rxd;
3713	struct sk_buff *skb = NULL;
3714	u16 len, hdrlen = 0;
3715	__le16 fc;
3716	struct rx_hdr hdr;
3717	u16 gap;
3718	u16 *buffer;
3719	char *ptr = ai->rxfids[0].virtual_host_addr + 4;
3720
3721	memcpy_fromio(&rxd, ai->rxfids[0].card_ram_off, sizeof(rxd));
3722	memcpy ((char *)&hdr, ptr, sizeof(hdr));
3723	ptr += sizeof(hdr);
3724	/* Bad CRC. Ignore packet */
3725	if (le16_to_cpu(hdr.status) & 2)
3726		hdr.len = 0;
3727	if (ai->wifidev == NULL)
3728		hdr.len = 0;
3729	len = le16_to_cpu(hdr.len);
3730	if (len > AIRO_DEF_MTU) {
3731		airo_print_err(ai->dev->name, "Bad size %d", len);
3732		goto badrx;
3733	}
3734	if (len == 0)
3735		goto badrx;
3736
3737	fc = get_unaligned((__le16 *)ptr);
3738	hdrlen = header_len(fc);
3739
3740	skb = dev_alloc_skb( len + hdrlen + 2 );
3741	if ( !skb ) {
3742		ai->dev->stats.rx_dropped++;
3743		goto badrx;
3744	}
3745	buffer = (u16*)skb_put (skb, len + hdrlen);
3746	memcpy ((char *)buffer, ptr, hdrlen);
3747	ptr += hdrlen;
3748	if (hdrlen == 24)
3749		ptr += 6;
3750	gap = get_unaligned_le16(ptr);
3751	ptr += sizeof(__le16);
3752	if (gap) {
3753		if (gap <= 8)
3754			ptr += gap;
3755		else
3756			airo_print_err(ai->dev->name,
3757			    "gaplen too big. Problems will follow...");
3758	}
3759	memcpy ((char *)buffer + hdrlen, ptr, len);
3760	ptr += len;
3761#ifdef IW_WIRELESS_SPY	  /* defined in iw_handler.h */
3762	if (ai->spy_data.spy_number > 0) {
3763		char *sa;
3764		struct iw_quality wstats;
3765		/* Prepare spy data : addr + qual */
3766		sa = (char*)buffer + 10;
3767		wstats.qual = hdr.rssi[0];
3768		if (ai->rssi)
3769			wstats.level = 0x100 - ai->rssi[hdr.rssi[1]].rssidBm;
3770		else
3771			wstats.level = (hdr.rssi[1] + 321) / 2;
3772		wstats.noise = ai->wstats.qual.noise;
3773		wstats.updated = IW_QUAL_QUAL_UPDATED
3774			| IW_QUAL_LEVEL_UPDATED
3775			| IW_QUAL_DBM;
3776		/* Update spy records */
3777		wireless_spy_update(ai->dev, sa, &wstats);
3778	}
3779#endif /* IW_WIRELESS_SPY */
3780	skb_reset_mac_header(skb);
3781	skb->pkt_type = PACKET_OTHERHOST;
3782	skb->dev = ai->wifidev;
3783	skb->protocol = htons(ETH_P_802_2);
3784	skb->ip_summed = CHECKSUM_NONE;
3785	netif_rx( skb );
3786
3787badrx:
3788	if (rxd.valid == 0) {
3789		rxd.valid = 1;
3790		rxd.rdy = 0;
3791		rxd.len = PKTSIZE;
3792		memcpy_toio(ai->rxfids[0].card_ram_off, &rxd, sizeof(rxd));
3793	}
3794}
3795
3796static inline void set_auth_type(struct airo_info *local, int auth_type)
3797{
3798	local->config.authType = auth_type;
3799	/* Cache the last auth type used (of AUTH_OPEN and AUTH_ENCRYPT).
3800	 * Used by airo_set_auth()
3801	 */
3802	if (auth_type == AUTH_OPEN || auth_type == AUTH_ENCRYPT)
3803		local->last_auth = auth_type;
3804}
3805
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
3806static u16 setup_card(struct airo_info *ai, u8 *mac, int lock)
3807{
3808	Cmd cmd;
3809	Resp rsp;
3810	int status;
3811	SsidRid mySsid;
3812	__le16 lastindex;
3813	WepKeyRid wkr;
3814	int rc;
3815
3816	memset( &mySsid, 0, sizeof( mySsid ) );
3817	kfree (ai->flash);
3818	ai->flash = NULL;
3819
3820	/* The NOP is the first step in getting the card going */
3821	cmd.cmd = NOP;
3822	cmd.parm0 = cmd.parm1 = cmd.parm2 = 0;
3823	if (lock && down_interruptible(&ai->sem))
3824		return ERROR;
3825	if ( issuecommand( ai, &cmd, &rsp ) != SUCCESS ) {
3826		if (lock)
3827			up(&ai->sem);
3828		return ERROR;
3829	}
3830	disable_MAC( ai, 0);
3831
3832	// Let's figure out if we need to use the AUX port
3833	if (!test_bit(FLAG_MPI,&ai->flags)) {
3834		cmd.cmd = CMD_ENABLEAUX;
3835		if (issuecommand(ai, &cmd, &rsp) != SUCCESS) {
3836			if (lock)
3837				up(&ai->sem);
3838			airo_print_err(ai->dev->name, "Error checking for AUX port");
3839			return ERROR;
3840		}
3841		if (!aux_bap || rsp.status & 0xff00) {
3842			ai->bap_read = fast_bap_read;
3843			airo_print_dbg(ai->dev->name, "Doing fast bap_reads");
3844		} else {
3845			ai->bap_read = aux_bap_read;
3846			airo_print_dbg(ai->dev->name, "Doing AUX bap_reads");
3847		}
3848	}
3849	if (lock)
3850		up(&ai->sem);
3851	if (ai->config.len == 0) {
3852		int i;
3853		tdsRssiRid rssi_rid;
3854		CapabilityRid cap_rid;
3855
3856		kfree(ai->SSID);
3857		ai->SSID = NULL;
3858		// general configuration (read/modify/write)
3859		status = readConfigRid(ai, lock);
3860		if ( status != SUCCESS ) return ERROR;
3861
3862		status = readCapabilityRid(ai, &cap_rid, lock);
3863		if ( status != SUCCESS ) return ERROR;
3864
3865		status = PC4500_readrid(ai,RID_RSSI,&rssi_rid,sizeof(rssi_rid),lock);
3866		if ( status == SUCCESS ) {
3867			if (ai->rssi || (ai->rssi = kmalloc(512, GFP_KERNEL)) != NULL)
3868				memcpy(ai->rssi, (u8*)&rssi_rid + 2, 512); /* Skip RID length member */
3869		}
3870		else {
3871			kfree(ai->rssi);
3872			ai->rssi = NULL;
3873			if (cap_rid.softCap & cpu_to_le16(8))
3874				ai->config.rmode |= RXMODE_NORMALIZED_RSSI;
3875			else
3876				airo_print_warn(ai->dev->name, "unknown received signal "
3877						"level scale");
3878		}
3879		ai->config.opmode = adhoc ? MODE_STA_IBSS : MODE_STA_ESS;
3880		set_auth_type(ai, AUTH_OPEN);
3881		ai->config.modulation = MOD_CCK;
3882
3883		if (le16_to_cpu(cap_rid.len) >= sizeof(cap_rid) &&
3884		    (cap_rid.extSoftCap & cpu_to_le16(1)) &&
3885		    micsetup(ai) == SUCCESS) {
3886			ai->config.opmode |= MODE_MIC;
3887			set_bit(FLAG_MIC_CAPABLE, &ai->flags);
3888		}
3889
3890		/* Save off the MAC */
3891		for( i = 0; i < ETH_ALEN; i++ ) {
3892			mac[i] = ai->config.macAddr[i];
3893		}
3894
3895		/* Check to see if there are any insmod configured
3896		   rates to add */
3897		if ( rates[0] ) {
3898			memset(ai->config.rates,0,sizeof(ai->config.rates));
3899			for( i = 0; i < 8 && rates[i]; i++ ) {
3900				ai->config.rates[i] = rates[i];
3901			}
3902		}
3903		set_bit (FLAG_COMMIT, &ai->flags);
3904	}
3905
3906	/* Setup the SSIDs if present */
3907	if ( ssids[0] ) {
3908		int i;
3909		for( i = 0; i < 3 && ssids[i]; i++ ) {
3910			size_t len = strlen(ssids[i]);
3911			if (len > 32)
3912				len = 32;
3913			mySsid.ssids[i].len = cpu_to_le16(len);
3914			memcpy(mySsid.ssids[i].ssid, ssids[i], len);
3915		}
3916		mySsid.len = cpu_to_le16(sizeof(mySsid));
3917	}
3918
3919	status = writeConfigRid(ai, lock);
3920	if ( status != SUCCESS ) return ERROR;
3921
3922	/* Set up the SSID list */
3923	if ( ssids[0] ) {
3924		status = writeSsidRid(ai, &mySsid, lock);
3925		if ( status != SUCCESS ) return ERROR;
3926	}
3927
3928	status = enable_MAC(ai, lock);
3929	if (status != SUCCESS)
3930		return ERROR;
3931
3932	/* Grab the initial wep key, we gotta save it for auto_wep */
3933	rc = readWepKeyRid(ai, &wkr, 1, lock);
3934	if (rc == SUCCESS) do {
3935		lastindex = wkr.kindex;
3936		if (wkr.kindex == cpu_to_le16(0xffff)) {
3937			ai->defindex = wkr.mac[0];
3938		}
3939		rc = readWepKeyRid(ai, &wkr, 0, lock);
3940	} while(lastindex != wkr.kindex);
3941
3942	try_auto_wep(ai);
3943
3944	return SUCCESS;
3945}
3946
3947static u16 issuecommand(struct airo_info *ai, Cmd *pCmd, Resp *pRsp) {
 
 
3948        // Im really paranoid about letting it run forever!
3949	int max_tries = 600000;
3950
3951	if (IN4500(ai, EVSTAT) & EV_CMD)
3952		OUT4500(ai, EVACK, EV_CMD);
3953
3954	OUT4500(ai, PARAM0, pCmd->parm0);
3955	OUT4500(ai, PARAM1, pCmd->parm1);
3956	OUT4500(ai, PARAM2, pCmd->parm2);
3957	OUT4500(ai, COMMAND, pCmd->cmd);
3958
3959	while (max_tries-- && (IN4500(ai, EVSTAT) & EV_CMD) == 0) {
3960		if ((IN4500(ai, COMMAND)) == pCmd->cmd)
3961			// PC4500 didn't notice command, try again
3962			OUT4500(ai, COMMAND, pCmd->cmd);
3963		if (!in_atomic() && (max_tries & 255) == 0)
3964			schedule();
3965	}
3966
3967	if ( max_tries == -1 ) {
3968		airo_print_err(ai->dev->name,
3969			"Max tries exceeded when issuing command");
3970		if (IN4500(ai, COMMAND) & COMMAND_BUSY)
3971			OUT4500(ai, EVACK, EV_CLEARCOMMANDBUSY);
3972		return ERROR;
3973	}
3974
3975	// command completed
3976	pRsp->status = IN4500(ai, STATUS);
3977	pRsp->rsp0 = IN4500(ai, RESP0);
3978	pRsp->rsp1 = IN4500(ai, RESP1);
3979	pRsp->rsp2 = IN4500(ai, RESP2);
3980	if ((pRsp->status & 0xff00)!=0 && pCmd->cmd != CMD_SOFTRESET)
3981		airo_print_err(ai->dev->name,
3982			"cmd:%x status:%x rsp0:%x rsp1:%x rsp2:%x",
3983			pCmd->cmd, pRsp->status, pRsp->rsp0, pRsp->rsp1,
3984			pRsp->rsp2);
3985
3986	// clear stuck command busy if necessary
3987	if (IN4500(ai, COMMAND) & COMMAND_BUSY) {
3988		OUT4500(ai, EVACK, EV_CLEARCOMMANDBUSY);
3989	}
3990	// acknowledge processing the status/response
3991	OUT4500(ai, EVACK, EV_CMD);
3992
3993	return SUCCESS;
3994}
3995
3996/* Sets up the bap to start exchange data.  whichbap should
3997 * be one of the BAP0 or BAP1 defines.  Locks should be held before
3998 * calling! */
3999static int bap_setup(struct airo_info *ai, u16 rid, u16 offset, int whichbap )
4000{
4001	int timeout = 50;
4002	int max_tries = 3;
4003
4004	OUT4500(ai, SELECT0+whichbap, rid);
4005	OUT4500(ai, OFFSET0+whichbap, offset);
4006	while (1) {
4007		int status = IN4500(ai, OFFSET0+whichbap);
4008		if (status & BAP_BUSY) {
4009                        /* This isn't really a timeout, but its kinda
4010			   close */
4011			if (timeout--) {
4012				continue;
4013			}
4014		} else if ( status & BAP_ERR ) {
4015			/* invalid rid or offset */
4016			airo_print_err(ai->dev->name, "BAP error %x %d",
4017				status, whichbap );
4018			return ERROR;
4019		} else if (status & BAP_DONE) { // success
4020			return SUCCESS;
4021		}
4022		if ( !(max_tries--) ) {
4023			airo_print_err(ai->dev->name,
4024				"BAP setup error too many retries\n");
4025			return ERROR;
4026		}
4027		// -- PC4500 missed it, try again
4028		OUT4500(ai, SELECT0+whichbap, rid);
4029		OUT4500(ai, OFFSET0+whichbap, offset);
4030		timeout = 50;
4031	}
4032}
4033
4034/* should only be called by aux_bap_read.  This aux function and the
4035   following use concepts not documented in the developers guide.  I
4036   got them from a patch given to my by Aironet */
4037static u16 aux_setup(struct airo_info *ai, u16 page,
4038		     u16 offset, u16 *len)
4039{
4040	u16 next;
4041
4042	OUT4500(ai, AUXPAGE, page);
4043	OUT4500(ai, AUXOFF, 0);
4044	next = IN4500(ai, AUXDATA);
4045	*len = IN4500(ai, AUXDATA)&0xff;
4046	if (offset != 4) OUT4500(ai, AUXOFF, offset);
4047	return next;
4048}
4049
4050/* requires call to bap_setup() first */
4051static int aux_bap_read(struct airo_info *ai, __le16 *pu16Dst,
4052			int bytelen, int whichbap)
4053{
4054	u16 len;
4055	u16 page;
4056	u16 offset;
4057	u16 next;
4058	int words;
4059	int i;
4060	unsigned long flags;
4061
4062	spin_lock_irqsave(&ai->aux_lock, flags);
4063	page = IN4500(ai, SWS0+whichbap);
4064	offset = IN4500(ai, SWS2+whichbap);
4065	next = aux_setup(ai, page, offset, &len);
4066	words = (bytelen+1)>>1;
4067
4068	for (i=0; i<words;) {
4069		int count;
4070		count = (len>>1) < (words-i) ? (len>>1) : (words-i);
4071		if ( !do8bitIO )
4072			insw( ai->dev->base_addr+DATA0+whichbap,
4073			      pu16Dst+i,count );
4074		else
4075			insb( ai->dev->base_addr+DATA0+whichbap,
4076			      pu16Dst+i, count << 1 );
4077		i += count;
4078		if (i<words) {
4079			next = aux_setup(ai, next, 4, &len);
4080		}
4081	}
4082	spin_unlock_irqrestore(&ai->aux_lock, flags);
4083	return SUCCESS;
4084}
4085
4086
4087/* requires call to bap_setup() first */
4088static int fast_bap_read(struct airo_info *ai, __le16 *pu16Dst,
4089			 int bytelen, int whichbap)
4090{
4091	bytelen = (bytelen + 1) & (~1); // round up to even value
4092	if ( !do8bitIO )
4093		insw( ai->dev->base_addr+DATA0+whichbap, pu16Dst, bytelen>>1 );
4094	else
4095		insb( ai->dev->base_addr+DATA0+whichbap, pu16Dst, bytelen );
4096	return SUCCESS;
4097}
4098
4099/* requires call to bap_setup() first */
4100static int bap_write(struct airo_info *ai, const __le16 *pu16Src,
4101		     int bytelen, int whichbap)
4102{
4103	bytelen = (bytelen + 1) & (~1); // round up to even value
4104	if ( !do8bitIO )
4105		outsw( ai->dev->base_addr+DATA0+whichbap,
4106		       pu16Src, bytelen>>1 );
4107	else
4108		outsb( ai->dev->base_addr+DATA0+whichbap, pu16Src, bytelen );
4109	return SUCCESS;
4110}
4111
4112static int PC4500_accessrid(struct airo_info *ai, u16 rid, u16 accmd)
4113{
4114	Cmd cmd; /* for issuing commands */
4115	Resp rsp; /* response from commands */
4116	u16 status;
4117
4118	memset(&cmd, 0, sizeof(cmd));
4119	cmd.cmd = accmd;
4120	cmd.parm0 = rid;
4121	status = issuecommand(ai, &cmd, &rsp);
4122	if (status != 0) return status;
4123	if ( (rsp.status & 0x7F00) != 0) {
4124		return (accmd << 8) + (rsp.rsp0 & 0xFF);
4125	}
4126	return 0;
4127}
4128
4129/*  Note, that we are using BAP1 which is also used by transmit, so
4130 *  we must get a lock. */
4131static int PC4500_readrid(struct airo_info *ai, u16 rid, void *pBuf, int len, int lock)
4132{
4133	u16 status;
4134        int rc = SUCCESS;
4135
4136	if (lock) {
4137		if (down_interruptible(&ai->sem))
4138			return ERROR;
4139	}
4140	if (test_bit(FLAG_MPI,&ai->flags)) {
4141		Cmd cmd;
4142		Resp rsp;
4143
4144		memset(&cmd, 0, sizeof(cmd));
4145		memset(&rsp, 0, sizeof(rsp));
4146		ai->config_desc.rid_desc.valid = 1;
4147		ai->config_desc.rid_desc.len = RIDSIZE;
4148		ai->config_desc.rid_desc.rid = 0;
4149		ai->config_desc.rid_desc.host_addr = ai->ridbus;
4150
4151		cmd.cmd = CMD_ACCESS;
4152		cmd.parm0 = rid;
4153
4154		memcpy_toio(ai->config_desc.card_ram_off,
4155			&ai->config_desc.rid_desc, sizeof(Rid));
4156
4157		rc = issuecommand(ai, &cmd, &rsp);
4158
4159		if (rsp.status & 0x7f00)
4160			rc = rsp.rsp0;
4161		if (!rc)
4162			memcpy(pBuf, ai->config_desc.virtual_host_addr, len);
4163		goto done;
4164	} else {
4165		if ((status = PC4500_accessrid(ai, rid, CMD_ACCESS))!=SUCCESS) {
4166	                rc = status;
4167	                goto done;
4168	        }
4169		if (bap_setup(ai, rid, 0, BAP1) != SUCCESS) {
4170			rc = ERROR;
4171	                goto done;
4172	        }
4173		// read the rid length field
4174		bap_read(ai, pBuf, 2, BAP1);
4175		// length for remaining part of rid
4176		len = min(len, (int)le16_to_cpu(*(__le16*)pBuf)) - 2;
4177
4178		if ( len <= 2 ) {
4179			airo_print_err(ai->dev->name,
4180				"Rid %x has a length of %d which is too short",
4181				(int)rid, (int)len );
4182			rc = ERROR;
4183	                goto done;
4184		}
4185		// read remainder of the rid
4186		rc = bap_read(ai, ((__le16*)pBuf)+1, len, BAP1);
4187	}
4188done:
4189	if (lock)
4190		up(&ai->sem);
4191	return rc;
4192}
4193
4194/*  Note, that we are using BAP1 which is also used by transmit, so
4195 *  make sure this isn't called when a transmit is happening */
4196static int PC4500_writerid(struct airo_info *ai, u16 rid,
4197			   const void *pBuf, int len, int lock)
4198{
4199	u16 status;
4200	int rc = SUCCESS;
4201
4202	*(__le16*)pBuf = cpu_to_le16((u16)len);
4203
4204	if (lock) {
4205		if (down_interruptible(&ai->sem))
4206			return ERROR;
4207	}
4208	if (test_bit(FLAG_MPI,&ai->flags)) {
4209		Cmd cmd;
4210		Resp rsp;
4211
4212		if (test_bit(FLAG_ENABLED, &ai->flags) && (RID_WEP_TEMP != rid))
4213			airo_print_err(ai->dev->name,
4214				"%s: MAC should be disabled (rid=%04x)",
4215				__func__, rid);
4216		memset(&cmd, 0, sizeof(cmd));
4217		memset(&rsp, 0, sizeof(rsp));
4218
4219		ai->config_desc.rid_desc.valid = 1;
4220		ai->config_desc.rid_desc.len = *((u16 *)pBuf);
4221		ai->config_desc.rid_desc.rid = 0;
4222
4223		cmd.cmd = CMD_WRITERID;
4224		cmd.parm0 = rid;
4225
4226		memcpy_toio(ai->config_desc.card_ram_off,
4227			&ai->config_desc.rid_desc, sizeof(Rid));
4228
4229		if (len < 4 || len > 2047) {
4230			airo_print_err(ai->dev->name, "%s: len=%d", __func__, len);
4231			rc = -1;
4232		} else {
4233			memcpy(ai->config_desc.virtual_host_addr,
4234				pBuf, len);
4235
4236			rc = issuecommand(ai, &cmd, &rsp);
4237			if ((rc & 0xff00) != 0) {
4238				airo_print_err(ai->dev->name, "%s: Write rid Error %d",
4239						__func__, rc);
4240				airo_print_err(ai->dev->name, "%s: Cmd=%04x",
4241						__func__, cmd.cmd);
4242			}
4243
4244			if ((rsp.status & 0x7f00))
4245				rc = rsp.rsp0;
4246		}
4247	} else {
4248		// --- first access so that we can write the rid data
4249		if ( (status = PC4500_accessrid(ai, rid, CMD_ACCESS)) != 0) {
4250	                rc = status;
4251	                goto done;
4252	        }
4253		// --- now write the rid data
4254		if (bap_setup(ai, rid, 0, BAP1) != SUCCESS) {
4255	                rc = ERROR;
4256	                goto done;
4257	        }
4258		bap_write(ai, pBuf, len, BAP1);
4259		// ---now commit the rid data
4260		rc = PC4500_accessrid(ai, rid, 0x100|CMD_ACCESS);
4261	}
4262done:
4263	if (lock)
4264		up(&ai->sem);
4265        return rc;
4266}
4267
4268/* Allocates a FID to be used for transmitting packets.  We only use
4269   one for now. */
4270static u16 transmit_allocate(struct airo_info *ai, int lenPayload, int raw)
4271{
4272	unsigned int loop = 3000;
4273	Cmd cmd;
4274	Resp rsp;
4275	u16 txFid;
4276	__le16 txControl;
4277
4278	cmd.cmd = CMD_ALLOCATETX;
4279	cmd.parm0 = lenPayload;
4280	if (down_interruptible(&ai->sem))
4281		return ERROR;
4282	if (issuecommand(ai, &cmd, &rsp) != SUCCESS) {
4283		txFid = ERROR;
4284		goto done;
4285	}
4286	if ( (rsp.status & 0xFF00) != 0) {
4287		txFid = ERROR;
4288		goto done;
4289	}
4290	/* wait for the allocate event/indication
4291	 * It makes me kind of nervous that this can just sit here and spin,
4292	 * but in practice it only loops like four times. */
4293	while (((IN4500(ai, EVSTAT) & EV_ALLOC) == 0) && --loop);
4294	if (!loop) {
4295		txFid = ERROR;
4296		goto done;
4297	}
4298
4299	// get the allocated fid and acknowledge
4300	txFid = IN4500(ai, TXALLOCFID);
4301	OUT4500(ai, EVACK, EV_ALLOC);
4302
4303	/*  The CARD is pretty cool since it converts the ethernet packet
4304	 *  into 802.11.  Also note that we don't release the FID since we
4305	 *  will be using the same one over and over again. */
4306	/*  We only have to setup the control once since we are not
4307	 *  releasing the fid. */
4308	if (raw)
4309		txControl = cpu_to_le16(TXCTL_TXOK | TXCTL_TXEX | TXCTL_802_11
4310			| TXCTL_ETHERNET | TXCTL_NORELEASE);
4311	else
4312		txControl = cpu_to_le16(TXCTL_TXOK | TXCTL_TXEX | TXCTL_802_3
4313			| TXCTL_ETHERNET | TXCTL_NORELEASE);
4314	if (bap_setup(ai, txFid, 0x0008, BAP1) != SUCCESS)
4315		txFid = ERROR;
4316	else
4317		bap_write(ai, &txControl, sizeof(txControl), BAP1);
4318
4319done:
4320	up(&ai->sem);
4321
4322	return txFid;
4323}
4324
4325/* In general BAP1 is dedicated to transmiting packets.  However,
4326   since we need a BAP when accessing RIDs, we also use BAP1 for that.
4327   Make sure the BAP1 spinlock is held when this is called. */
4328static int transmit_802_3_packet(struct airo_info *ai, int len, char *pPacket)
 
4329{
4330	__le16 payloadLen;
4331	Cmd cmd;
4332	Resp rsp;
4333	int miclen = 0;
4334	u16 txFid = len;
4335	MICBuffer pMic;
4336
4337	len >>= 16;
4338
4339	if (len <= ETH_ALEN * 2) {
4340		airo_print_warn(ai->dev->name, "Short packet %d", len);
4341		return ERROR;
4342	}
4343	len -= ETH_ALEN * 2;
4344
4345	if (test_bit(FLAG_MIC_CAPABLE, &ai->flags) && ai->micstats.enabled && 
4346	    (ntohs(((__be16 *)pPacket)[6]) != 0x888E)) {
4347		if (encapsulate(ai,(etherHead *)pPacket,&pMic,len) != SUCCESS)
4348			return ERROR;
4349		miclen = sizeof(pMic);
4350	}
4351	// packet is destination[6], source[6], payload[len-12]
4352	// write the payload length and dst/src/payload
4353	if (bap_setup(ai, txFid, 0x0036, BAP1) != SUCCESS) return ERROR;
4354	/* The hardware addresses aren't counted as part of the payload, so
4355	 * we have to subtract the 12 bytes for the addresses off */
4356	payloadLen = cpu_to_le16(len + miclen);
4357	bap_write(ai, &payloadLen, sizeof(payloadLen),BAP1);
4358	bap_write(ai, (__le16*)pPacket, sizeof(etherHead), BAP1);
4359	if (miclen)
4360		bap_write(ai, (__le16*)&pMic, miclen, BAP1);
4361	bap_write(ai, (__le16*)(pPacket + sizeof(etherHead)), len, BAP1);
4362	// issue the transmit command
4363	memset( &cmd, 0, sizeof( cmd ) );
4364	cmd.cmd = CMD_TRANSMIT;
4365	cmd.parm0 = txFid;
4366	if (issuecommand(ai, &cmd, &rsp) != SUCCESS) return ERROR;
4367	if ( (rsp.status & 0xFF00) != 0) return ERROR;
 
4368	return SUCCESS;
4369}
4370
4371static int transmit_802_11_packet(struct airo_info *ai, int len, char *pPacket)
 
4372{
4373	__le16 fc, payloadLen;
4374	Cmd cmd;
4375	Resp rsp;
4376	int hdrlen;
4377	static u8 tail[(30-10) + 2 + 6] = {[30-10] = 6};
4378	/* padding of header to full size + le16 gaplen (6) + gaplen bytes */
4379	u16 txFid = len;
4380	len >>= 16;
4381
4382	fc = *(__le16*)pPacket;
4383	hdrlen = header_len(fc);
4384
4385	if (len < hdrlen) {
4386		airo_print_warn(ai->dev->name, "Short packet %d", len);
4387		return ERROR;
4388	}
4389
4390	/* packet is 802.11 header +  payload
4391	 * write the payload length and dst/src/payload */
4392	if (bap_setup(ai, txFid, 6, BAP1) != SUCCESS) return ERROR;
4393	/* The 802.11 header aren't counted as part of the payload, so
4394	 * we have to subtract the header bytes off */
4395	payloadLen = cpu_to_le16(len-hdrlen);
4396	bap_write(ai, &payloadLen, sizeof(payloadLen),BAP1);
4397	if (bap_setup(ai, txFid, 0x0014, BAP1) != SUCCESS) return ERROR;
4398	bap_write(ai, (__le16 *)pPacket, hdrlen, BAP1);
4399	bap_write(ai, (__le16 *)(tail + (hdrlen - 10)), 38 - hdrlen, BAP1);
4400
4401	bap_write(ai, (__le16 *)(pPacket + hdrlen), len - hdrlen, BAP1);
4402	// issue the transmit command
4403	memset( &cmd, 0, sizeof( cmd ) );
4404	cmd.cmd = CMD_TRANSMIT;
4405	cmd.parm0 = txFid;
4406	if (issuecommand(ai, &cmd, &rsp) != SUCCESS) return ERROR;
4407	if ( (rsp.status & 0xFF00) != 0) return ERROR;
 
4408	return SUCCESS;
4409}
4410
4411/*
4412 *  This is the proc_fs routines.  It is a bit messier than I would
4413 *  like!  Feel free to clean it up!
4414 */
4415
4416static ssize_t proc_read( struct file *file,
4417			  char __user *buffer,
4418			  size_t len,
4419			  loff_t *offset);
4420
4421static ssize_t proc_write( struct file *file,
4422			   const char __user *buffer,
4423			   size_t len,
4424			   loff_t *offset );
4425static int proc_close( struct inode *inode, struct file *file );
4426
4427static int proc_stats_open( struct inode *inode, struct file *file );
4428static int proc_statsdelta_open( struct inode *inode, struct file *file );
4429static int proc_status_open( struct inode *inode, struct file *file );
4430static int proc_SSID_open( struct inode *inode, struct file *file );
4431static int proc_APList_open( struct inode *inode, struct file *file );
4432static int proc_BSSList_open( struct inode *inode, struct file *file );
4433static int proc_config_open( struct inode *inode, struct file *file );
4434static int proc_wepkey_open( struct inode *inode, struct file *file );
4435
4436static const struct file_operations proc_statsdelta_ops = {
4437	.owner		= THIS_MODULE,
4438	.read		= proc_read,
4439	.open		= proc_statsdelta_open,
4440	.release	= proc_close,
4441	.llseek		= default_llseek,
4442};
4443
4444static const struct file_operations proc_stats_ops = {
4445	.owner		= THIS_MODULE,
4446	.read		= proc_read,
4447	.open		= proc_stats_open,
4448	.release	= proc_close,
4449	.llseek		= default_llseek,
4450};
4451
4452static const struct file_operations proc_status_ops = {
4453	.owner		= THIS_MODULE,
4454	.read		= proc_read,
4455	.open		= proc_status_open,
4456	.release	= proc_close,
4457	.llseek		= default_llseek,
4458};
4459
4460static const struct file_operations proc_SSID_ops = {
4461	.owner		= THIS_MODULE,
4462	.read		= proc_read,
4463	.write		= proc_write,
4464	.open		= proc_SSID_open,
4465	.release	= proc_close,
4466	.llseek		= default_llseek,
4467};
4468
4469static const struct file_operations proc_BSSList_ops = {
4470	.owner		= THIS_MODULE,
4471	.read		= proc_read,
4472	.write		= proc_write,
4473	.open		= proc_BSSList_open,
4474	.release	= proc_close,
4475	.llseek		= default_llseek,
4476};
4477
4478static const struct file_operations proc_APList_ops = {
4479	.owner		= THIS_MODULE,
4480	.read		= proc_read,
4481	.write		= proc_write,
4482	.open		= proc_APList_open,
4483	.release	= proc_close,
4484	.llseek		= default_llseek,
4485};
4486
4487static const struct file_operations proc_config_ops = {
4488	.owner		= THIS_MODULE,
4489	.read		= proc_read,
4490	.write		= proc_write,
4491	.open		= proc_config_open,
4492	.release	= proc_close,
4493	.llseek		= default_llseek,
4494};
4495
4496static const struct file_operations proc_wepkey_ops = {
4497	.owner		= THIS_MODULE,
4498	.read		= proc_read,
4499	.write		= proc_write,
4500	.open		= proc_wepkey_open,
4501	.release	= proc_close,
4502	.llseek		= default_llseek,
4503};
4504
4505static struct proc_dir_entry *airo_entry;
4506
4507struct proc_data {
4508	int release_buffer;
4509	int readlen;
4510	char *rbuffer;
4511	int writelen;
4512	int maxwritelen;
4513	char *wbuffer;
4514	void (*on_close) (struct inode *, struct file *);
4515};
4516
4517static int setup_proc_entry( struct net_device *dev,
4518			     struct airo_info *apriv ) {
 
4519	struct proc_dir_entry *entry;
4520
4521	/* First setup the device directory */
4522	strcpy(apriv->proc_name,dev->name);
4523	apriv->proc_entry = proc_mkdir_mode(apriv->proc_name, airo_perm,
4524					    airo_entry);
4525	if (!apriv->proc_entry)
4526		return -ENOMEM;
4527	proc_set_user(apriv->proc_entry, proc_kuid, proc_kgid);
4528
4529	/* Setup the StatsDelta */
4530	entry = proc_create_data("StatsDelta", S_IRUGO & proc_perm,
4531				 apriv->proc_entry, &proc_statsdelta_ops, dev);
4532	if (!entry)
4533		goto fail;
4534	proc_set_user(entry, proc_kuid, proc_kgid);
4535
4536	/* Setup the Stats */
4537	entry = proc_create_data("Stats", S_IRUGO & proc_perm,
4538				 apriv->proc_entry, &proc_stats_ops, dev);
4539	if (!entry)
4540		goto fail;
4541	proc_set_user(entry, proc_kuid, proc_kgid);
4542
4543	/* Setup the Status */
4544	entry = proc_create_data("Status", S_IRUGO & proc_perm,
4545				 apriv->proc_entry, &proc_status_ops, dev);
4546	if (!entry)
4547		goto fail;
4548	proc_set_user(entry, proc_kuid, proc_kgid);
4549
4550	/* Setup the Config */
4551	entry = proc_create_data("Config", proc_perm,
4552				 apriv->proc_entry, &proc_config_ops, dev);
4553	if (!entry)
4554		goto fail;
4555	proc_set_user(entry, proc_kuid, proc_kgid);
4556
4557	/* Setup the SSID */
4558	entry = proc_create_data("SSID", proc_perm,
4559				 apriv->proc_entry, &proc_SSID_ops, dev);
4560	if (!entry)
4561		goto fail;
4562	proc_set_user(entry, proc_kuid, proc_kgid);
4563
4564	/* Setup the APList */
4565	entry = proc_create_data("APList", proc_perm,
4566				 apriv->proc_entry, &proc_APList_ops, dev);
4567	if (!entry)
4568		goto fail;
4569	proc_set_user(entry, proc_kuid, proc_kgid);
4570
4571	/* Setup the BSSList */
4572	entry = proc_create_data("BSSList", proc_perm,
4573				 apriv->proc_entry, &proc_BSSList_ops, dev);
4574	if (!entry)
4575		goto fail;
4576	proc_set_user(entry, proc_kuid, proc_kgid);
4577
4578	/* Setup the WepKey */
4579	entry = proc_create_data("WepKey", proc_perm,
4580				 apriv->proc_entry, &proc_wepkey_ops, dev);
4581	if (!entry)
4582		goto fail;
4583	proc_set_user(entry, proc_kuid, proc_kgid);
4584	return 0;
4585
4586fail:
4587	remove_proc_subtree(apriv->proc_name, airo_entry);
4588	return -ENOMEM;
4589}
4590
4591static int takedown_proc_entry( struct net_device *dev,
4592				struct airo_info *apriv )
4593{
4594	remove_proc_subtree(apriv->proc_name, airo_entry);
4595	return 0;
4596}
4597
4598/*
4599 *  What we want from the proc_fs is to be able to efficiently read
4600 *  and write the configuration.  To do this, we want to read the
4601 *  configuration when the file is opened and write it when the file is
4602 *  closed.  So basically we allocate a read buffer at open and fill it
4603 *  with data, and allocate a write buffer and read it at close.
4604 */
4605
4606/*
4607 *  The read routine is generic, it relies on the preallocated rbuffer
4608 *  to supply the data.
4609 */
4610static ssize_t proc_read( struct file *file,
4611			  char __user *buffer,
4612			  size_t len,
4613			  loff_t *offset )
4614{
4615	struct proc_data *priv = file->private_data;
4616
4617	if (!priv->rbuffer)
4618		return -EINVAL;
4619
4620	return simple_read_from_buffer(buffer, len, offset, priv->rbuffer,
4621					priv->readlen);
4622}
4623
4624/*
4625 *  The write routine is generic, it fills in a preallocated rbuffer
4626 *  to supply the data.
4627 */
4628static ssize_t proc_write( struct file *file,
4629			   const char __user *buffer,
4630			   size_t len,
4631			   loff_t *offset )
4632{
4633	ssize_t ret;
4634	struct proc_data *priv = file->private_data;
4635
4636	if (!priv->wbuffer)
4637		return -EINVAL;
4638
4639	ret = simple_write_to_buffer(priv->wbuffer, priv->maxwritelen, offset,
4640					buffer, len);
4641	if (ret > 0)
4642		priv->writelen = max_t(int, priv->writelen, *offset);
4643
4644	return ret;
4645}
4646
4647static int proc_status_open(struct inode *inode, struct file *file)
4648{
4649	struct proc_data *data;
4650	struct net_device *dev = PDE_DATA(inode);
4651	struct airo_info *apriv = dev->ml_priv;
4652	CapabilityRid cap_rid;
4653	StatusRid status_rid;
4654	u16 mode;
4655	int i;
4656
4657	if ((file->private_data = kzalloc(sizeof(struct proc_data ), GFP_KERNEL)) == NULL)
4658		return -ENOMEM;
4659	data = file->private_data;
4660	if ((data->rbuffer = kmalloc( 2048, GFP_KERNEL )) == NULL) {
4661		kfree (file->private_data);
4662		return -ENOMEM;
4663	}
4664
4665	readStatusRid(apriv, &status_rid, 1);
4666	readCapabilityRid(apriv, &cap_rid, 1);
4667
4668	mode = le16_to_cpu(status_rid.mode);
4669
4670        i = sprintf(data->rbuffer, "Status: %s%s%s%s%s%s%s%s%s\n",
4671                    mode & 1 ? "CFG ": "",
4672                    mode & 2 ? "ACT ": "",
4673                    mode & 0x10 ? "SYN ": "",
4674                    mode & 0x20 ? "LNK ": "",
4675                    mode & 0x40 ? "LEAP ": "",
4676                    mode & 0x80 ? "PRIV ": "",
4677                    mode & 0x100 ? "KEY ": "",
4678                    mode & 0x200 ? "WEP ": "",
4679                    mode & 0x8000 ? "ERR ": "");
4680	sprintf( data->rbuffer+i, "Mode: %x\n"
4681		 "Signal Strength: %d\n"
4682		 "Signal Quality: %d\n"
4683		 "SSID: %-.*s\n"
4684		 "AP: %-.16s\n"
4685		 "Freq: %d\n"
4686		 "BitRate: %dmbs\n"
4687		 "Driver Version: %s\n"
4688		 "Device: %s\nManufacturer: %s\nFirmware Version: %s\n"
4689		 "Radio type: %x\nCountry: %x\nHardware Version: %x\n"
4690		 "Software Version: %x\nSoftware Subversion: %x\n"
4691		 "Boot block version: %x\n",
4692		 le16_to_cpu(status_rid.mode),
4693		 le16_to_cpu(status_rid.normalizedSignalStrength),
4694		 le16_to_cpu(status_rid.signalQuality),
4695		 le16_to_cpu(status_rid.SSIDlen),
4696		 status_rid.SSID,
4697		 status_rid.apName,
4698		 le16_to_cpu(status_rid.channel),
4699		 le16_to_cpu(status_rid.currentXmitRate) / 2,
4700		 version,
4701		 cap_rid.prodName,
4702		 cap_rid.manName,
4703		 cap_rid.prodVer,
4704		 le16_to_cpu(cap_rid.radioType),
4705		 le16_to_cpu(cap_rid.country),
4706		 le16_to_cpu(cap_rid.hardVer),
4707		 le16_to_cpu(cap_rid.softVer),
4708		 le16_to_cpu(cap_rid.softSubVer),
4709		 le16_to_cpu(cap_rid.bootBlockVer));
4710	data->readlen = strlen( data->rbuffer );
4711	return 0;
4712}
4713
4714static int proc_stats_rid_open(struct inode*, struct file*, u16);
4715static int proc_statsdelta_open( struct inode *inode,
4716				 struct file *file ) {
 
4717	if (file->f_mode&FMODE_WRITE) {
4718		return proc_stats_rid_open(inode, file, RID_STATSDELTACLEAR);
4719	}
4720	return proc_stats_rid_open(inode, file, RID_STATSDELTA);
4721}
4722
4723static int proc_stats_open( struct inode *inode, struct file *file ) {
 
4724	return proc_stats_rid_open(inode, file, RID_STATS);
4725}
4726
4727static int proc_stats_rid_open( struct inode *inode,
4728				struct file *file,
4729				u16 rid )
4730{
4731	struct proc_data *data;
4732	struct net_device *dev = PDE_DATA(inode);
4733	struct airo_info *apriv = dev->ml_priv;
4734	StatsRid stats;
4735	int i, j;
4736	__le32 *vals = stats.vals;
4737	int len;
4738
4739	if ((file->private_data = kzalloc(sizeof(struct proc_data ), GFP_KERNEL)) == NULL)
4740		return -ENOMEM;
4741	data = file->private_data;
4742	if ((data->rbuffer = kmalloc( 4096, GFP_KERNEL )) == NULL) {
4743		kfree (file->private_data);
4744		return -ENOMEM;
4745	}
4746
4747	readStatsRid(apriv, &stats, rid, 1);
4748	len = le16_to_cpu(stats.len);
4749
4750        j = 0;
4751	for(i=0; statsLabels[i]!=(char *)-1 && i*4<len; i++) {
4752		if (!statsLabels[i]) continue;
4753		if (j+strlen(statsLabels[i])+16>4096) {
4754			airo_print_warn(apriv->dev->name,
4755			       "Potentially disastrous buffer overflow averted!");
4756			break;
4757		}
4758		j+=sprintf(data->rbuffer+j, "%s: %u\n", statsLabels[i],
4759				le32_to_cpu(vals[i]));
4760	}
4761	if (i*4 >= len) {
4762		airo_print_warn(apriv->dev->name, "Got a short rid");
4763	}
4764	data->readlen = j;
4765	return 0;
4766}
4767
4768static int get_dec_u16( char *buffer, int *start, int limit ) {
 
4769	u16 value;
4770	int valid = 0;
4771	for (value = 0; *start < limit && buffer[*start] >= '0' &&
4772			buffer[*start] <= '9'; (*start)++) {
4773		valid = 1;
4774		value *= 10;
4775		value += buffer[*start] - '0';
4776	}
4777	if ( !valid ) return -1;
4778	return value;
4779}
4780
4781static int airo_config_commit(struct net_device *dev,
4782			      struct iw_request_info *info, void *zwrq,
4783			      char *extra);
4784
4785static inline int sniffing_mode(struct airo_info *ai)
4786{
4787	return (le16_to_cpu(ai->config.rmode) & le16_to_cpu(RXMODE_MASK)) >=
4788		le16_to_cpu(RXMODE_RFMON);
4789}
4790
4791static void proc_config_on_close(struct inode *inode, struct file *file)
4792{
4793	struct proc_data *data = file->private_data;
4794	struct net_device *dev = PDE_DATA(inode);
4795	struct airo_info *ai = dev->ml_priv;
4796	char *line;
4797
4798	if ( !data->writelen ) return;
4799
4800	readConfigRid(ai, 1);
4801	set_bit (FLAG_COMMIT, &ai->flags);
4802
4803	line = data->wbuffer;
4804	while( line[0] ) {
4805/*** Mode processing */
4806		if ( !strncmp( line, "Mode: ", 6 ) ) {
4807			line += 6;
4808			if (sniffing_mode(ai))
4809				set_bit (FLAG_RESET, &ai->flags);
4810			ai->config.rmode &= ~RXMODE_FULL_MASK;
4811			clear_bit (FLAG_802_11, &ai->flags);
4812			ai->config.opmode &= ~MODE_CFG_MASK;
4813			ai->config.scanMode = SCANMODE_ACTIVE;
4814			if ( line[0] == 'a' ) {
4815				ai->config.opmode |= MODE_STA_IBSS;
4816			} else {
4817				ai->config.opmode |= MODE_STA_ESS;
4818				if ( line[0] == 'r' ) {
4819					ai->config.rmode |= RXMODE_RFMON | RXMODE_DISABLE_802_3_HEADER;
4820					ai->config.scanMode = SCANMODE_PASSIVE;
4821					set_bit (FLAG_802_11, &ai->flags);
4822				} else if ( line[0] == 'y' ) {
4823					ai->config.rmode |= RXMODE_RFMON_ANYBSS | RXMODE_DISABLE_802_3_HEADER;
4824					ai->config.scanMode = SCANMODE_PASSIVE;
4825					set_bit (FLAG_802_11, &ai->flags);
4826				} else if ( line[0] == 'l' )
4827					ai->config.rmode |= RXMODE_LANMON;
4828			}
4829			set_bit (FLAG_COMMIT, &ai->flags);
4830		}
4831
4832/*** Radio status */
4833		else if (!strncmp(line,"Radio: ", 7)) {
4834			line += 7;
4835			if (!strncmp(line,"off",3)) {
4836				set_bit (FLAG_RADIO_OFF, &ai->flags);
4837			} else {
4838				clear_bit (FLAG_RADIO_OFF, &ai->flags);
4839			}
4840		}
4841/*** NodeName processing */
4842		else if ( !strncmp( line, "NodeName: ", 10 ) ) {
4843			int j;
4844
4845			line += 10;
4846			memset( ai->config.nodeName, 0, 16 );
4847/* Do the name, assume a space between the mode and node name */
4848			for( j = 0; j < 16 && line[j] != '\n'; j++ ) {
4849				ai->config.nodeName[j] = line[j];
4850			}
4851			set_bit (FLAG_COMMIT, &ai->flags);
4852		}
4853
4854/*** PowerMode processing */
4855		else if ( !strncmp( line, "PowerMode: ", 11 ) ) {
4856			line += 11;
4857			if ( !strncmp( line, "PSPCAM", 6 ) ) {
4858				ai->config.powerSaveMode = POWERSAVE_PSPCAM;
4859				set_bit (FLAG_COMMIT, &ai->flags);
4860			} else if ( !strncmp( line, "PSP", 3 ) ) {
4861				ai->config.powerSaveMode = POWERSAVE_PSP;
4862				set_bit (FLAG_COMMIT, &ai->flags);
4863			} else {
4864				ai->config.powerSaveMode = POWERSAVE_CAM;
4865				set_bit (FLAG_COMMIT, &ai->flags);
4866			}
4867		} else if ( !strncmp( line, "DataRates: ", 11 ) ) {
4868			int v, i = 0, k = 0; /* i is index into line,
4869						k is index to rates */
4870
4871			line += 11;
4872			while((v = get_dec_u16(line, &i, 3))!=-1) {
4873				ai->config.rates[k++] = (u8)v;
4874				line += i + 1;
4875				i = 0;
4876			}
4877			set_bit (FLAG_COMMIT, &ai->flags);
4878		} else if ( !strncmp( line, "Channel: ", 9 ) ) {
4879			int v, i = 0;
4880			line += 9;
4881			v = get_dec_u16(line, &i, i+3);
4882			if ( v != -1 ) {
4883				ai->config.channelSet = cpu_to_le16(v);
4884				set_bit (FLAG_COMMIT, &ai->flags);
4885			}
4886		} else if ( !strncmp( line, "XmitPower: ", 11 ) ) {
4887			int v, i = 0;
4888			line += 11;
4889			v = get_dec_u16(line, &i, i+3);
4890			if ( v != -1 ) {
4891				ai->config.txPower = cpu_to_le16(v);
4892				set_bit (FLAG_COMMIT, &ai->flags);
4893			}
4894		} else if ( !strncmp( line, "WEP: ", 5 ) ) {
4895			line += 5;
4896			switch( line[0] ) {
4897			case 's':
4898				set_auth_type(ai, AUTH_SHAREDKEY);
4899				break;
4900			case 'e':
4901				set_auth_type(ai, AUTH_ENCRYPT);
4902				break;
4903			default:
4904				set_auth_type(ai, AUTH_OPEN);
4905				break;
4906			}
4907			set_bit (FLAG_COMMIT, &ai->flags);
4908		} else if ( !strncmp( line, "LongRetryLimit: ", 16 ) ) {
4909			int v, i = 0;
4910
4911			line += 16;
4912			v = get_dec_u16(line, &i, 3);
4913			v = (v<0) ? 0 : ((v>255) ? 255 : v);
4914			ai->config.longRetryLimit = cpu_to_le16(v);
4915			set_bit (FLAG_COMMIT, &ai->flags);
4916		} else if ( !strncmp( line, "ShortRetryLimit: ", 17 ) ) {
4917			int v, i = 0;
4918
4919			line += 17;
4920			v = get_dec_u16(line, &i, 3);
4921			v = (v<0) ? 0 : ((v>255) ? 255 : v);
4922			ai->config.shortRetryLimit = cpu_to_le16(v);
4923			set_bit (FLAG_COMMIT, &ai->flags);
4924		} else if ( !strncmp( line, "RTSThreshold: ", 14 ) ) {
4925			int v, i = 0;
4926
4927			line += 14;
4928			v = get_dec_u16(line, &i, 4);
4929			v = (v<0) ? 0 : ((v>AIRO_DEF_MTU) ? AIRO_DEF_MTU : v);
4930			ai->config.rtsThres = cpu_to_le16(v);
4931			set_bit (FLAG_COMMIT, &ai->flags);
4932		} else if ( !strncmp( line, "TXMSDULifetime: ", 16 ) ) {
4933			int v, i = 0;
4934
4935			line += 16;
4936			v = get_dec_u16(line, &i, 5);
4937			v = (v<0) ? 0 : v;
4938			ai->config.txLifetime = cpu_to_le16(v);
4939			set_bit (FLAG_COMMIT, &ai->flags);
4940		} else if ( !strncmp( line, "RXMSDULifetime: ", 16 ) ) {
4941			int v, i = 0;
4942
4943			line += 16;
4944			v = get_dec_u16(line, &i, 5);
4945			v = (v<0) ? 0 : v;
4946			ai->config.rxLifetime = cpu_to_le16(v);
4947			set_bit (FLAG_COMMIT, &ai->flags);
4948		} else if ( !strncmp( line, "TXDiversity: ", 13 ) ) {
4949			ai->config.txDiversity =
4950				(line[13]=='l') ? 1 :
4951				((line[13]=='r')? 2: 3);
4952			set_bit (FLAG_COMMIT, &ai->flags);
4953		} else if ( !strncmp( line, "RXDiversity: ", 13 ) ) {
4954			ai->config.rxDiversity =
4955				(line[13]=='l') ? 1 :
4956				((line[13]=='r')? 2: 3);
4957			set_bit (FLAG_COMMIT, &ai->flags);
4958		} else if ( !strncmp( line, "FragThreshold: ", 15 ) ) {
4959			int v, i = 0;
4960
4961			line += 15;
4962			v = get_dec_u16(line, &i, 4);
4963			v = (v<256) ? 256 : ((v>AIRO_DEF_MTU) ? AIRO_DEF_MTU : v);
4964			v = v & 0xfffe; /* Make sure its even */
4965			ai->config.fragThresh = cpu_to_le16(v);
4966			set_bit (FLAG_COMMIT, &ai->flags);
4967		} else if (!strncmp(line, "Modulation: ", 12)) {
4968			line += 12;
4969			switch(*line) {
4970			case 'd':  ai->config.modulation=MOD_DEFAULT; set_bit(FLAG_COMMIT, &ai->flags); break;
4971			case 'c':  ai->config.modulation=MOD_CCK; set_bit(FLAG_COMMIT, &ai->flags); break;
4972			case 'm':  ai->config.modulation=MOD_MOK; set_bit(FLAG_COMMIT, &ai->flags); break;
4973			default: airo_print_warn(ai->dev->name, "Unknown modulation");
4974			}
4975		} else if (!strncmp(line, "Preamble: ", 10)) {
4976			line += 10;
4977			switch(*line) {
4978			case 'a': ai->config.preamble=PREAMBLE_AUTO; set_bit(FLAG_COMMIT, &ai->flags); break;
4979			case 'l': ai->config.preamble=PREAMBLE_LONG; set_bit(FLAG_COMMIT, &ai->flags); break;
4980			case 's': ai->config.preamble=PREAMBLE_SHORT; set_bit(FLAG_COMMIT, &ai->flags); break;
4981			default: airo_print_warn(ai->dev->name, "Unknown preamble");
4982			}
4983		} else {
4984			airo_print_warn(ai->dev->name, "Couldn't figure out %s", line);
4985		}
4986		while( line[0] && line[0] != '\n' ) line++;
4987		if ( line[0] ) line++;
4988	}
4989	airo_config_commit(dev, NULL, NULL, NULL);
4990}
4991
4992static const char *get_rmode(__le16 mode)
4993{
4994        switch(mode & RXMODE_MASK) {
4995        case RXMODE_RFMON:  return "rfmon";
4996        case RXMODE_RFMON_ANYBSS:  return "yna (any) bss rfmon";
4997        case RXMODE_LANMON:  return "lanmon";
4998        }
4999        return "ESS";
5000}
5001
5002static int proc_config_open(struct inode *inode, struct file *file)
5003{
5004	struct proc_data *data;
5005	struct net_device *dev = PDE_DATA(inode);
5006	struct airo_info *ai = dev->ml_priv;
5007	int i;
5008	__le16 mode;
5009
5010	if ((file->private_data = kzalloc(sizeof(struct proc_data ), GFP_KERNEL)) == NULL)
5011		return -ENOMEM;
5012	data = file->private_data;
5013	if ((data->rbuffer = kmalloc( 2048, GFP_KERNEL )) == NULL) {
5014		kfree (file->private_data);
5015		return -ENOMEM;
5016	}
5017	if ((data->wbuffer = kzalloc( 2048, GFP_KERNEL )) == NULL) {
5018		kfree (data->rbuffer);
5019		kfree (file->private_data);
5020		return -ENOMEM;
5021	}
5022	data->maxwritelen = 2048;
5023	data->on_close = proc_config_on_close;
5024
5025	readConfigRid(ai, 1);
5026
5027	mode = ai->config.opmode & MODE_CFG_MASK;
5028	i = sprintf( data->rbuffer,
5029		     "Mode: %s\n"
5030		     "Radio: %s\n"
5031		     "NodeName: %-16s\n"
5032		     "PowerMode: %s\n"
5033		     "DataRates: %d %d %d %d %d %d %d %d\n"
5034		     "Channel: %d\n"
5035		     "XmitPower: %d\n",
5036		     mode == MODE_STA_IBSS ? "adhoc" :
5037		     mode == MODE_STA_ESS ? get_rmode(ai->config.rmode):
5038		     mode == MODE_AP ? "AP" :
5039		     mode == MODE_AP_RPTR ? "AP RPTR" : "Error",
5040		     test_bit(FLAG_RADIO_OFF, &ai->flags) ? "off" : "on",
5041		     ai->config.nodeName,
5042		     ai->config.powerSaveMode == POWERSAVE_CAM ? "CAM" :
5043		     ai->config.powerSaveMode == POWERSAVE_PSP ? "PSP" :
5044		     ai->config.powerSaveMode == POWERSAVE_PSPCAM ? "PSPCAM" :
5045		     "Error",
5046		     (int)ai->config.rates[0],
5047		     (int)ai->config.rates[1],
5048		     (int)ai->config.rates[2],
5049		     (int)ai->config.rates[3],
5050		     (int)ai->config.rates[4],
5051		     (int)ai->config.rates[5],
5052		     (int)ai->config.rates[6],
5053		     (int)ai->config.rates[7],
5054		     le16_to_cpu(ai->config.channelSet),
5055		     le16_to_cpu(ai->config.txPower)
5056		);
5057	sprintf( data->rbuffer + i,
5058		 "LongRetryLimit: %d\n"
5059		 "ShortRetryLimit: %d\n"
5060		 "RTSThreshold: %d\n"
5061		 "TXMSDULifetime: %d\n"
5062		 "RXMSDULifetime: %d\n"
5063		 "TXDiversity: %s\n"
5064		 "RXDiversity: %s\n"
5065		 "FragThreshold: %d\n"
5066		 "WEP: %s\n"
5067		 "Modulation: %s\n"
5068		 "Preamble: %s\n",
5069		 le16_to_cpu(ai->config.longRetryLimit),
5070		 le16_to_cpu(ai->config.shortRetryLimit),
5071		 le16_to_cpu(ai->config.rtsThres),
5072		 le16_to_cpu(ai->config.txLifetime),
5073		 le16_to_cpu(ai->config.rxLifetime),
5074		 ai->config.txDiversity == 1 ? "left" :
5075		 ai->config.txDiversity == 2 ? "right" : "both",
5076		 ai->config.rxDiversity == 1 ? "left" :
5077		 ai->config.rxDiversity == 2 ? "right" : "both",
5078		 le16_to_cpu(ai->config.fragThresh),
5079		 ai->config.authType == AUTH_ENCRYPT ? "encrypt" :
5080		 ai->config.authType == AUTH_SHAREDKEY ? "shared" : "open",
5081		 ai->config.modulation == MOD_DEFAULT ? "default" :
5082		 ai->config.modulation == MOD_CCK ? "cck" :
5083		 ai->config.modulation == MOD_MOK ? "mok" : "error",
5084		 ai->config.preamble == PREAMBLE_AUTO ? "auto" :
5085		 ai->config.preamble == PREAMBLE_LONG ? "long" :
5086		 ai->config.preamble == PREAMBLE_SHORT ? "short" : "error"
5087		);
5088	data->readlen = strlen( data->rbuffer );
5089	return 0;
5090}
5091
5092static void proc_SSID_on_close(struct inode *inode, struct file *file)
5093{
5094	struct proc_data *data = file->private_data;
5095	struct net_device *dev = PDE_DATA(inode);
5096	struct airo_info *ai = dev->ml_priv;
5097	SsidRid SSID_rid;
5098	int i;
5099	char *p = data->wbuffer;
5100	char *end = p + data->writelen;
5101
5102	if (!data->writelen)
5103		return;
5104
5105	*end = '\n'; /* sentinel; we have space for it */
5106
5107	memset(&SSID_rid, 0, sizeof(SSID_rid));
5108
5109	for (i = 0; i < 3 && p < end; i++) {
5110		int j = 0;
5111		/* copy up to 32 characters from this line */
5112		while (*p != '\n' && j < 32)
5113			SSID_rid.ssids[i].ssid[j++] = *p++;
5114		if (j == 0)
5115			break;
5116		SSID_rid.ssids[i].len = cpu_to_le16(j);
5117		/* skip to the beginning of the next line */
5118		while (*p++ != '\n')
5119			;
5120	}
5121	if (i)
5122		SSID_rid.len = cpu_to_le16(sizeof(SSID_rid));
5123	disable_MAC(ai, 1);
5124	writeSsidRid(ai, &SSID_rid, 1);
5125	enable_MAC(ai, 1);
5126}
5127
5128static void proc_APList_on_close( struct inode *inode, struct file *file ) {
 
5129	struct proc_data *data = file->private_data;
5130	struct net_device *dev = PDE_DATA(inode);
5131	struct airo_info *ai = dev->ml_priv;
5132	APListRid *APList_rid = &ai->APList;
5133	int i;
5134
5135	if ( !data->writelen ) return;
5136
5137	memset(APList_rid, 0, sizeof(*APList_rid));
5138	APList_rid->len = cpu_to_le16(sizeof(*APList_rid));
5139
5140	for (i = 0; i < 4 && data->writelen >= (i + 1) * 6 * 3; i++)
5141		mac_pton(data->wbuffer + i * 6 * 3, APList_rid->ap[i]);
5142
5143	disable_MAC(ai, 1);
5144	writeAPListRid(ai, APList_rid, 1);
5145	enable_MAC(ai, 1);
5146}
5147
5148/* This function wraps PC4500_writerid with a MAC disable */
5149static int do_writerid( struct airo_info *ai, u16 rid, const void *rid_data,
5150			int len, int dummy ) {
 
5151	int rc;
5152
5153	disable_MAC(ai, 1);
5154	rc = PC4500_writerid(ai, rid, rid_data, len, 1);
5155	enable_MAC(ai, 1);
5156	return rc;
5157}
5158
5159/* Returns the WEP key at the specified index, or -1 if that key does
5160 * not exist.  The buffer is assumed to be at least 16 bytes in length.
5161 */
5162static int get_wep_key(struct airo_info *ai, u16 index, char *buf, u16 buflen)
5163{
5164	WepKeyRid wkr;
5165	int rc;
5166	__le16 lastindex;
5167
5168	rc = readWepKeyRid(ai, &wkr, 1, 1);
5169	if (rc != SUCCESS)
5170		return -1;
5171	do {
5172		lastindex = wkr.kindex;
5173		if (le16_to_cpu(wkr.kindex) == index) {
5174			int klen = min_t(int, buflen, le16_to_cpu(wkr.klen));
5175			memcpy(buf, wkr.key, klen);
5176			return klen;
5177		}
5178		rc = readWepKeyRid(ai, &wkr, 0, 1);
5179		if (rc != SUCCESS)
5180			return -1;
5181	} while (lastindex != wkr.kindex);
5182	return -1;
5183}
5184
5185static int get_wep_tx_idx(struct airo_info *ai)
5186{
5187	WepKeyRid wkr;
5188	int rc;
5189	__le16 lastindex;
5190
5191	rc = readWepKeyRid(ai, &wkr, 1, 1);
5192	if (rc != SUCCESS)
5193		return -1;
5194	do {
5195		lastindex = wkr.kindex;
5196		if (wkr.kindex == cpu_to_le16(0xffff))
5197			return wkr.mac[0];
5198		rc = readWepKeyRid(ai, &wkr, 0, 1);
5199		if (rc != SUCCESS)
5200			return -1;
5201	} while (lastindex != wkr.kindex);
5202	return -1;
5203}
5204
5205static int set_wep_key(struct airo_info *ai, u16 index, const char *key,
5206		       u16 keylen, int perm, int lock)
5207{
5208	static const unsigned char macaddr[ETH_ALEN] = { 0x01, 0, 0, 0, 0, 0 };
5209	WepKeyRid wkr;
5210	int rc;
5211
5212	if (WARN_ON(keylen == 0))
5213		return -1;
5214
5215	memset(&wkr, 0, sizeof(wkr));
5216	wkr.len = cpu_to_le16(sizeof(wkr));
5217	wkr.kindex = cpu_to_le16(index);
5218	wkr.klen = cpu_to_le16(keylen);
5219	memcpy(wkr.key, key, keylen);
5220	memcpy(wkr.mac, macaddr, ETH_ALEN);
5221
5222	if (perm) disable_MAC(ai, lock);
5223	rc = writeWepKeyRid(ai, &wkr, perm, lock);
5224	if (perm) enable_MAC(ai, lock);
5225	return rc;
5226}
5227
5228static int set_wep_tx_idx(struct airo_info *ai, u16 index, int perm, int lock)
5229{
5230	WepKeyRid wkr;
5231	int rc;
5232
5233	memset(&wkr, 0, sizeof(wkr));
5234	wkr.len = cpu_to_le16(sizeof(wkr));
5235	wkr.kindex = cpu_to_le16(0xffff);
5236	wkr.mac[0] = (char)index;
5237
5238	if (perm) {
5239		ai->defindex = (char)index;
5240		disable_MAC(ai, lock);
5241	}
5242
5243	rc = writeWepKeyRid(ai, &wkr, perm, lock);
5244
5245	if (perm)
5246		enable_MAC(ai, lock);
5247	return rc;
5248}
5249
5250static void proc_wepkey_on_close( struct inode *inode, struct file *file ) {
 
5251	struct proc_data *data;
5252	struct net_device *dev = PDE_DATA(inode);
5253	struct airo_info *ai = dev->ml_priv;
5254	int i, rc;
5255	char key[16];
5256	u16 index = 0;
5257	int j = 0;
5258
5259	memset(key, 0, sizeof(key));
5260
5261	data = file->private_data;
5262	if ( !data->writelen ) return;
5263
5264	if (data->wbuffer[0] >= '0' && data->wbuffer[0] <= '3' &&
5265	    (data->wbuffer[1] == ' ' || data->wbuffer[1] == '\n')) {
5266		index = data->wbuffer[0] - '0';
5267		if (data->wbuffer[1] == '\n') {
5268			rc = set_wep_tx_idx(ai, index, 1, 1);
5269			if (rc < 0) {
5270				airo_print_err(ai->dev->name, "failed to set "
5271				               "WEP transmit index to %d: %d.",
5272				               index, rc);
5273			}
5274			return;
5275		}
5276		j = 2;
5277	} else {
5278		airo_print_err(ai->dev->name, "WepKey passed invalid key index");
5279		return;
5280	}
5281
5282	for( i = 0; i < 16*3 && data->wbuffer[i+j]; i++ ) {
5283		switch(i%3) {
5284		case 0:
5285			key[i/3] = hex_to_bin(data->wbuffer[i+j])<<4;
5286			break;
5287		case 1:
5288			key[i/3] |= hex_to_bin(data->wbuffer[i+j]);
5289			break;
5290		}
5291	}
5292
5293	rc = set_wep_key(ai, index, key, i/3, 1, 1);
5294	if (rc < 0) {
5295		airo_print_err(ai->dev->name, "failed to set WEP key at index "
5296		               "%d: %d.", index, rc);
5297	}
5298}
5299
5300static int proc_wepkey_open( struct inode *inode, struct file *file )
5301{
5302	struct proc_data *data;
5303	struct net_device *dev = PDE_DATA(inode);
5304	struct airo_info *ai = dev->ml_priv;
5305	char *ptr;
5306	WepKeyRid wkr;
5307	__le16 lastindex;
5308	int j=0;
5309	int rc;
5310
5311	if ((file->private_data = kzalloc(sizeof(struct proc_data ), GFP_KERNEL)) == NULL)
5312		return -ENOMEM;
5313	memset(&wkr, 0, sizeof(wkr));
5314	data = file->private_data;
5315	if ((data->rbuffer = kzalloc( 180, GFP_KERNEL )) == NULL) {
5316		kfree (file->private_data);
5317		return -ENOMEM;
5318	}
5319	data->writelen = 0;
5320	data->maxwritelen = 80;
5321	if ((data->wbuffer = kzalloc( 80, GFP_KERNEL )) == NULL) {
5322		kfree (data->rbuffer);
5323		kfree (file->private_data);
5324		return -ENOMEM;
5325	}
5326	data->on_close = proc_wepkey_on_close;
5327
5328	ptr = data->rbuffer;
5329	strcpy(ptr, "No wep keys\n");
5330	rc = readWepKeyRid(ai, &wkr, 1, 1);
5331	if (rc == SUCCESS) do {
5332		lastindex = wkr.kindex;
5333		if (wkr.kindex == cpu_to_le16(0xffff)) {
5334			j += sprintf(ptr+j, "Tx key = %d\n",
5335				     (int)wkr.mac[0]);
5336		} else {
5337			j += sprintf(ptr+j, "Key %d set with length = %d\n",
5338				     le16_to_cpu(wkr.kindex),
5339				     le16_to_cpu(wkr.klen));
5340		}
5341		readWepKeyRid(ai, &wkr, 0, 1);
5342	} while((lastindex != wkr.kindex) && (j < 180-30));
5343
5344	data->readlen = strlen( data->rbuffer );
5345	return 0;
5346}
5347
5348static int proc_SSID_open(struct inode *inode, struct file *file)
5349{
5350	struct proc_data *data;
5351	struct net_device *dev = PDE_DATA(inode);
5352	struct airo_info *ai = dev->ml_priv;
5353	int i;
5354	char *ptr;
5355	SsidRid SSID_rid;
5356
5357	if ((file->private_data = kzalloc(sizeof(struct proc_data ), GFP_KERNEL)) == NULL)
5358		return -ENOMEM;
5359	data = file->private_data;
5360	if ((data->rbuffer = kmalloc( 104, GFP_KERNEL )) == NULL) {
5361		kfree (file->private_data);
5362		return -ENOMEM;
5363	}
5364	data->writelen = 0;
5365	data->maxwritelen = 33*3;
5366	/* allocate maxwritelen + 1; we'll want a sentinel */
5367	if ((data->wbuffer = kzalloc(33*3 + 1, GFP_KERNEL)) == NULL) {
5368		kfree (data->rbuffer);
5369		kfree (file->private_data);
5370		return -ENOMEM;
5371	}
5372	data->on_close = proc_SSID_on_close;
5373
5374	readSsidRid(ai, &SSID_rid);
5375	ptr = data->rbuffer;
5376	for (i = 0; i < 3; i++) {
5377		int j;
5378		size_t len = le16_to_cpu(SSID_rid.ssids[i].len);
5379		if (!len)
5380			break;
5381		if (len > 32)
5382			len = 32;
5383		for (j = 0; j < len && SSID_rid.ssids[i].ssid[j]; j++)
5384			*ptr++ = SSID_rid.ssids[i].ssid[j];
5385		*ptr++ = '\n';
5386	}
5387	*ptr = '\0';
5388	data->readlen = strlen( data->rbuffer );
5389	return 0;
5390}
5391
5392static int proc_APList_open( struct inode *inode, struct file *file ) {
 
5393	struct proc_data *data;
5394	struct net_device *dev = PDE_DATA(inode);
5395	struct airo_info *ai = dev->ml_priv;
5396	int i;
5397	char *ptr;
5398	APListRid *APList_rid = &ai->APList;
5399
5400	if ((file->private_data = kzalloc(sizeof(struct proc_data ), GFP_KERNEL)) == NULL)
5401		return -ENOMEM;
5402	data = file->private_data;
5403	if ((data->rbuffer = kmalloc( 104, GFP_KERNEL )) == NULL) {
5404		kfree (file->private_data);
5405		return -ENOMEM;
5406	}
5407	data->writelen = 0;
5408	data->maxwritelen = 4*6*3;
5409	if ((data->wbuffer = kzalloc( data->maxwritelen, GFP_KERNEL )) == NULL) {
5410		kfree (data->rbuffer);
5411		kfree (file->private_data);
5412		return -ENOMEM;
5413	}
5414	data->on_close = proc_APList_on_close;
5415
5416	ptr = data->rbuffer;
5417	for( i = 0; i < 4; i++ ) {
5418// We end when we find a zero MAC
5419		if ( !*(int*)APList_rid->ap[i] &&
5420		     !*(int*)&APList_rid->ap[i][2]) break;
5421		ptr += sprintf(ptr, "%pM\n", APList_rid->ap[i]);
5422	}
5423	if (i==0) ptr += sprintf(ptr, "Not using specific APs\n");
5424
5425	*ptr = '\0';
5426	data->readlen = strlen( data->rbuffer );
5427	return 0;
5428}
5429
5430static int proc_BSSList_open( struct inode *inode, struct file *file ) {
 
5431	struct proc_data *data;
5432	struct net_device *dev = PDE_DATA(inode);
5433	struct airo_info *ai = dev->ml_priv;
5434	char *ptr;
5435	BSSListRid BSSList_rid;
5436	int rc;
5437	/* If doLoseSync is not 1, we won't do a Lose Sync */
5438	int doLoseSync = -1;
5439
5440	if ((file->private_data = kzalloc(sizeof(struct proc_data ), GFP_KERNEL)) == NULL)
5441		return -ENOMEM;
5442	data = file->private_data;
5443	if ((data->rbuffer = kmalloc( 1024, GFP_KERNEL )) == NULL) {
5444		kfree (file->private_data);
5445		return -ENOMEM;
5446	}
5447	data->writelen = 0;
5448	data->maxwritelen = 0;
5449	data->wbuffer = NULL;
5450	data->on_close = NULL;
5451
5452	if (file->f_mode & FMODE_WRITE) {
5453		if (!(file->f_mode & FMODE_READ)) {
5454			Cmd cmd;
5455			Resp rsp;
5456
5457			if (ai->flags & FLAG_RADIO_MASK) return -ENETDOWN;
 
 
 
 
5458			memset(&cmd, 0, sizeof(cmd));
5459			cmd.cmd=CMD_LISTBSS;
5460			if (down_interruptible(&ai->sem))
 
 
5461				return -ERESTARTSYS;
5462			issuecommand(ai, &cmd, &rsp);
 
5463			up(&ai->sem);
5464			data->readlen = 0;
5465			return 0;
5466		}
5467		doLoseSync = 1;
5468	}
5469	ptr = data->rbuffer;
5470	/* There is a race condition here if there are concurrent opens.
5471           Since it is a rare condition, we'll just live with it, otherwise
5472           we have to add a spin lock... */
5473	rc = readBSSListRid(ai, doLoseSync, &BSSList_rid);
5474	while(rc == 0 && BSSList_rid.index != cpu_to_le16(0xffff)) {
5475		ptr += sprintf(ptr, "%pM %*s rssi = %d",
5476			       BSSList_rid.bssid,
5477				(int)BSSList_rid.ssidLen,
5478				BSSList_rid.ssid,
5479				le16_to_cpu(BSSList_rid.dBm));
5480		ptr += sprintf(ptr, " channel = %d %s %s %s %s\n",
5481				le16_to_cpu(BSSList_rid.dsChannel),
5482				BSSList_rid.cap & CAP_ESS ? "ESS" : "",
5483				BSSList_rid.cap & CAP_IBSS ? "adhoc" : "",
5484				BSSList_rid.cap & CAP_PRIVACY ? "wep" : "",
5485				BSSList_rid.cap & CAP_SHORTHDR ? "shorthdr" : "");
5486		rc = readBSSListRid(ai, 0, &BSSList_rid);
5487	}
5488	*ptr = '\0';
5489	data->readlen = strlen( data->rbuffer );
5490	return 0;
5491}
5492
5493static int proc_close( struct inode *inode, struct file *file )
5494{
5495	struct proc_data *data = file->private_data;
5496
5497	if (data->on_close != NULL)
5498		data->on_close(inode, file);
5499	kfree(data->rbuffer);
5500	kfree(data->wbuffer);
5501	kfree(data);
5502	return 0;
5503}
5504
5505/* Since the card doesn't automatically switch to the right WEP mode,
5506   we will make it do it.  If the card isn't associated, every secs we
5507   will switch WEP modes to see if that will help.  If the card is
5508   associated we will check every minute to see if anything has
5509   changed. */
5510static void timer_func( struct net_device *dev ) {
 
5511	struct airo_info *apriv = dev->ml_priv;
5512
5513/* We don't have a link so try changing the authtype */
5514	readConfigRid(apriv, 0);
5515	disable_MAC(apriv, 0);
5516	switch(apriv->config.authType) {
5517		case AUTH_ENCRYPT:
5518/* So drop to OPEN */
5519			apriv->config.authType = AUTH_OPEN;
5520			break;
5521		case AUTH_SHAREDKEY:
5522			if (apriv->keyindex < auto_wep) {
5523				set_wep_tx_idx(apriv, apriv->keyindex, 0, 0);
5524				apriv->config.authType = AUTH_SHAREDKEY;
5525				apriv->keyindex++;
5526			} else {
5527			        /* Drop to ENCRYPT */
5528				apriv->keyindex = 0;
5529				set_wep_tx_idx(apriv, apriv->defindex, 0, 0);
5530				apriv->config.authType = AUTH_ENCRYPT;
5531			}
5532			break;
5533		default:  /* We'll escalate to SHAREDKEY */
5534			apriv->config.authType = AUTH_SHAREDKEY;
5535	}
5536	set_bit (FLAG_COMMIT, &apriv->flags);
5537	writeConfigRid(apriv, 0);
5538	enable_MAC(apriv, 0);
5539	up(&apriv->sem);
5540
5541/* Schedule check to see if the change worked */
5542	clear_bit(JOB_AUTOWEP, &apriv->jobs);
5543	apriv->expires = RUN_AT(HZ*3);
5544}
5545
5546#ifdef CONFIG_PCI
5547static int airo_pci_probe(struct pci_dev *pdev,
5548				    const struct pci_device_id *pent)
5549{
5550	struct net_device *dev;
5551
5552	if (pci_enable_device(pdev))
5553		return -ENODEV;
5554	pci_set_master(pdev);
5555
5556	if (pdev->device == 0x5000 || pdev->device == 0xa504)
5557			dev = _init_airo_card(pdev->irq, pdev->resource[0].start, 0, pdev, &pdev->dev);
5558	else
5559			dev = _init_airo_card(pdev->irq, pdev->resource[2].start, 0, pdev, &pdev->dev);
5560	if (!dev) {
5561		pci_disable_device(pdev);
5562		return -ENODEV;
5563	}
5564
5565	pci_set_drvdata(pdev, dev);
5566	return 0;
5567}
5568
5569static void airo_pci_remove(struct pci_dev *pdev)
5570{
5571	struct net_device *dev = pci_get_drvdata(pdev);
5572
5573	airo_print_info(dev->name, "Unregistering...");
5574	stop_airo_card(dev, 1);
5575	pci_disable_device(pdev);
5576}
5577
5578static int airo_pci_suspend(struct pci_dev *pdev, pm_message_t state)
5579{
5580	struct net_device *dev = pci_get_drvdata(pdev);
5581	struct airo_info *ai = dev->ml_priv;
5582	Cmd cmd;
5583	Resp rsp;
5584
5585	if (!ai->SSID)
5586		ai->SSID = kmalloc(sizeof(SsidRid), GFP_KERNEL);
5587	if (!ai->SSID)
5588		return -ENOMEM;
5589	readSsidRid(ai, ai->SSID);
5590	memset(&cmd, 0, sizeof(cmd));
5591	/* the lock will be released at the end of the resume callback */
5592	if (down_interruptible(&ai->sem))
5593		return -EAGAIN;
5594	disable_MAC(ai, 0);
5595	netif_device_detach(dev);
5596	ai->power = state;
5597	cmd.cmd = HOSTSLEEP;
5598	issuecommand(ai, &cmd, &rsp);
5599
5600	pci_enable_wake(pdev, pci_choose_state(pdev, state), 1);
5601	pci_save_state(pdev);
5602	pci_set_power_state(pdev, pci_choose_state(pdev, state));
5603	return 0;
5604}
5605
5606static int airo_pci_resume(struct pci_dev *pdev)
5607{
5608	struct net_device *dev = pci_get_drvdata(pdev);
5609	struct airo_info *ai = dev->ml_priv;
5610	pci_power_t prev_state = pdev->current_state;
5611
5612	pci_set_power_state(pdev, PCI_D0);
5613	pci_restore_state(pdev);
5614	pci_enable_wake(pdev, PCI_D0, 0);
5615
5616	if (prev_state != PCI_D1) {
5617		reset_card(dev, 0);
5618		mpi_init_descriptors(ai);
5619		setup_card(ai, dev->dev_addr, 0);
5620		clear_bit(FLAG_RADIO_OFF, &ai->flags);
5621		clear_bit(FLAG_PENDING_XMIT, &ai->flags);
5622	} else {
5623		OUT4500(ai, EVACK, EV_AWAKEN);
5624		OUT4500(ai, EVACK, EV_AWAKEN);
5625		msleep(100);
5626	}
5627
5628	set_bit(FLAG_COMMIT, &ai->flags);
5629	disable_MAC(ai, 0);
5630        msleep(200);
5631	if (ai->SSID) {
5632		writeSsidRid(ai, ai->SSID, 0);
5633		kfree(ai->SSID);
5634		ai->SSID = NULL;
5635	}
5636	writeAPListRid(ai, &ai->APList, 0);
5637	writeConfigRid(ai, 0);
5638	enable_MAC(ai, 0);
5639	ai->power = PMSG_ON;
5640	netif_device_attach(dev);
5641	netif_wake_queue(dev);
5642	enable_interrupts(ai);
5643	up(&ai->sem);
5644	return 0;
5645}
5646#endif
5647
5648static int __init airo_init_module( void )
5649{
5650	int i;
5651
5652	proc_kuid = make_kuid(&init_user_ns, proc_uid);
5653	proc_kgid = make_kgid(&init_user_ns, proc_gid);
5654	if (!uid_valid(proc_kuid) || !gid_valid(proc_kgid))
5655		return -EINVAL;
5656
5657	airo_entry = proc_mkdir_mode("driver/aironet", airo_perm, NULL);
5658
5659	if (airo_entry)
5660		proc_set_user(airo_entry, proc_kuid, proc_kgid);
5661
5662	for (i = 0; i < 4 && io[i] && irq[i]; i++) {
5663		airo_print_info("", "Trying to configure ISA adapter at irq=%d "
5664			"io=0x%x", irq[i], io[i] );
5665		if (init_airo_card( irq[i], io[i], 0, NULL ))
5666			/* do nothing */ ;
 
5667	}
5668
5669#ifdef CONFIG_PCI
5670	airo_print_info("", "Probing for PCI adapters");
5671	i = pci_register_driver(&airo_driver);
5672	airo_print_info("", "Finished probing for PCI adapters");
5673
5674	if (i) {
5675		remove_proc_entry("driver/aironet", NULL);
5676		return i;
5677	}
5678#endif
5679
5680	/* Always exit with success, as we are a library module
5681	 * as well as a driver module
5682	 */
5683	return 0;
5684}
5685
5686static void __exit airo_cleanup_module( void )
5687{
5688	struct airo_info *ai;
5689	while(!list_empty(&airo_devices)) {
5690		ai = list_entry(airo_devices.next, struct airo_info, dev_list);
5691		airo_print_info(ai->dev->name, "Unregistering...");
5692		stop_airo_card(ai->dev, 1);
5693	}
5694#ifdef CONFIG_PCI
5695	pci_unregister_driver(&airo_driver);
5696#endif
5697	remove_proc_entry("driver/aironet", NULL);
5698}
5699
5700/*
5701 * Initial Wireless Extension code for Aironet driver by :
5702 *	Jean Tourrilhes <jt@hpl.hp.com> - HPL - 17 November 00
5703 * Conversion to new driver API by :
5704 *	Jean Tourrilhes <jt@hpl.hp.com> - HPL - 26 March 02
5705 * Javier also did a good amount of work here, adding some new extensions
5706 * and fixing my code. Let's just say that without him this code just
5707 * would not work at all... - Jean II
5708 */
5709
5710static u8 airo_rssi_to_dbm (tdsRssiEntry *rssi_rid, u8 rssi)
5711{
5712	if (!rssi_rid)
5713		return 0;
5714
5715	return (0x100 - rssi_rid[rssi].rssidBm);
5716}
5717
5718static u8 airo_dbm_to_pct (tdsRssiEntry *rssi_rid, u8 dbm)
5719{
5720	int i;
5721
5722	if (!rssi_rid)
5723		return 0;
5724
5725	for (i = 0; i < 256; i++)
5726		if (rssi_rid[i].rssidBm == dbm)
5727			return rssi_rid[i].rssipct;
5728
5729	return 0;
5730}
5731
5732
5733static int airo_get_quality (StatusRid *status_rid, CapabilityRid *cap_rid)
5734{
5735	int quality = 0;
5736	u16 sq;
5737
5738	if ((status_rid->mode & cpu_to_le16(0x3f)) != cpu_to_le16(0x3f))
5739		return 0;
5740
5741	if (!(cap_rid->hardCap & cpu_to_le16(8)))
5742		return 0;
5743
5744	sq = le16_to_cpu(status_rid->signalQuality);
5745	if (memcmp(cap_rid->prodName, "350", 3))
5746		if (sq > 0x20)
5747			quality = 0;
5748		else
5749			quality = 0x20 - sq;
5750	else
5751		if (sq > 0xb0)
5752			quality = 0;
5753		else if (sq < 0x10)
5754			quality = 0xa0;
5755		else
5756			quality = 0xb0 - sq;
5757	return quality;
5758}
5759
5760#define airo_get_max_quality(cap_rid) (memcmp((cap_rid)->prodName, "350", 3) ? 0x20 : 0xa0)
5761#define airo_get_avg_quality(cap_rid) (memcmp((cap_rid)->prodName, "350", 3) ? 0x10 : 0x50);
5762
5763/*------------------------------------------------------------------*/
5764/*
5765 * Wireless Handler : get protocol name
5766 */
5767static int airo_get_name(struct net_device *dev,
5768			 struct iw_request_info *info,
5769			 char *cwrq,
5770			 char *extra)
5771{
5772	strcpy(cwrq, "IEEE 802.11-DS");
5773	return 0;
5774}
5775
5776/*------------------------------------------------------------------*/
5777/*
5778 * Wireless Handler : set frequency
5779 */
5780static int airo_set_freq(struct net_device *dev,
5781			 struct iw_request_info *info,
5782			 struct iw_freq *fwrq,
5783			 char *extra)
5784{
5785	struct airo_info *local = dev->ml_priv;
5786	int rc = -EINPROGRESS;		/* Call commit handler */
5787
5788	/* If setting by frequency, convert to a channel */
5789	if(fwrq->e == 1) {
5790		int f = fwrq->m / 100000;
5791
5792		/* Hack to fall through... */
5793		fwrq->e = 0;
5794		fwrq->m = ieee80211_frequency_to_channel(f);
5795	}
5796	/* Setting by channel number */
5797	if((fwrq->m > 1000) || (fwrq->e > 0))
5798		rc = -EOPNOTSUPP;
5799	else {
5800		int channel = fwrq->m;
5801		/* We should do a better check than that,
5802		 * based on the card capability !!! */
5803		if((channel < 1) || (channel > 14)) {
5804			airo_print_dbg(dev->name, "New channel value of %d is invalid!",
5805				fwrq->m);
5806			rc = -EINVAL;
5807		} else {
5808			readConfigRid(local, 1);
5809			/* Yes ! We can set it !!! */
5810			local->config.channelSet = cpu_to_le16(channel);
5811			set_bit (FLAG_COMMIT, &local->flags);
5812		}
5813	}
5814	return rc;
5815}
5816
5817/*------------------------------------------------------------------*/
5818/*
5819 * Wireless Handler : get frequency
5820 */
5821static int airo_get_freq(struct net_device *dev,
5822			 struct iw_request_info *info,
5823			 struct iw_freq *fwrq,
5824			 char *extra)
5825{
5826	struct airo_info *local = dev->ml_priv;
5827	StatusRid status_rid;		/* Card status info */
5828	int ch;
5829
5830	readConfigRid(local, 1);
5831	if ((local->config.opmode & MODE_CFG_MASK) == MODE_STA_ESS)
5832		status_rid.channel = local->config.channelSet;
5833	else
5834		readStatusRid(local, &status_rid, 1);
5835
5836	ch = le16_to_cpu(status_rid.channel);
5837	if((ch > 0) && (ch < 15)) {
5838		fwrq->m = 100000 *
5839			ieee80211_channel_to_frequency(ch, IEEE80211_BAND_2GHZ);
5840		fwrq->e = 1;
5841	} else {
5842		fwrq->m = ch;
5843		fwrq->e = 0;
5844	}
5845
5846	return 0;
5847}
5848
5849/*------------------------------------------------------------------*/
5850/*
5851 * Wireless Handler : set ESSID
5852 */
5853static int airo_set_essid(struct net_device *dev,
5854			  struct iw_request_info *info,
5855			  struct iw_point *dwrq,
5856			  char *extra)
5857{
5858	struct airo_info *local = dev->ml_priv;
5859	SsidRid SSID_rid;		/* SSIDs */
5860
5861	/* Reload the list of current SSID */
5862	readSsidRid(local, &SSID_rid);
5863
5864	/* Check if we asked for `any' */
5865	if (dwrq->flags == 0) {
5866		/* Just send an empty SSID list */
5867		memset(&SSID_rid, 0, sizeof(SSID_rid));
5868	} else {
5869		unsigned index = (dwrq->flags & IW_ENCODE_INDEX) - 1;
5870
5871		/* Check the size of the string */
5872		if (dwrq->length > IW_ESSID_MAX_SIZE)
5873			return -E2BIG ;
5874
5875		/* Check if index is valid */
5876		if (index >= ARRAY_SIZE(SSID_rid.ssids))
5877			return -EINVAL;
5878
5879		/* Set the SSID */
5880		memset(SSID_rid.ssids[index].ssid, 0,
5881		       sizeof(SSID_rid.ssids[index].ssid));
5882		memcpy(SSID_rid.ssids[index].ssid, extra, dwrq->length);
5883		SSID_rid.ssids[index].len = cpu_to_le16(dwrq->length);
5884	}
5885	SSID_rid.len = cpu_to_le16(sizeof(SSID_rid));
5886	/* Write it to the card */
5887	disable_MAC(local, 1);
5888	writeSsidRid(local, &SSID_rid, 1);
5889	enable_MAC(local, 1);
5890
5891	return 0;
5892}
5893
5894/*------------------------------------------------------------------*/
5895/*
5896 * Wireless Handler : get ESSID
5897 */
5898static int airo_get_essid(struct net_device *dev,
5899			  struct iw_request_info *info,
5900			  struct iw_point *dwrq,
5901			  char *extra)
5902{
5903	struct airo_info *local = dev->ml_priv;
5904	StatusRid status_rid;		/* Card status info */
5905
5906	readStatusRid(local, &status_rid, 1);
5907
5908	/* Note : if dwrq->flags != 0, we should
5909	 * get the relevant SSID from the SSID list... */
5910
5911	/* Get the current SSID */
5912	memcpy(extra, status_rid.SSID, le16_to_cpu(status_rid.SSIDlen));
5913	/* If none, we may want to get the one that was set */
5914
5915	/* Push it out ! */
5916	dwrq->length = le16_to_cpu(status_rid.SSIDlen);
5917	dwrq->flags = 1; /* active */
5918
5919	return 0;
5920}
5921
5922/*------------------------------------------------------------------*/
5923/*
5924 * Wireless Handler : set AP address
5925 */
5926static int airo_set_wap(struct net_device *dev,
5927			struct iw_request_info *info,
5928			struct sockaddr *awrq,
5929			char *extra)
5930{
5931	struct airo_info *local = dev->ml_priv;
5932	Cmd cmd;
5933	Resp rsp;
5934	APListRid *APList_rid = &local->APList;
5935
5936	if (awrq->sa_family != ARPHRD_ETHER)
5937		return -EINVAL;
5938	else if (is_broadcast_ether_addr(awrq->sa_data) ||
5939		 is_zero_ether_addr(awrq->sa_data)) {
5940		memset(&cmd, 0, sizeof(cmd));
5941		cmd.cmd=CMD_LOSE_SYNC;
5942		if (down_interruptible(&local->sem))
5943			return -ERESTARTSYS;
5944		issuecommand(local, &cmd, &rsp);
5945		up(&local->sem);
5946	} else {
5947		memset(APList_rid, 0, sizeof(*APList_rid));
5948		APList_rid->len = cpu_to_le16(sizeof(*APList_rid));
5949		memcpy(APList_rid->ap[0], awrq->sa_data, ETH_ALEN);
5950		disable_MAC(local, 1);
5951		writeAPListRid(local, APList_rid, 1);
5952		enable_MAC(local, 1);
5953	}
5954	return 0;
5955}
5956
5957/*------------------------------------------------------------------*/
5958/*
5959 * Wireless Handler : get AP address
5960 */
5961static int airo_get_wap(struct net_device *dev,
5962			struct iw_request_info *info,
5963			struct sockaddr *awrq,
5964			char *extra)
5965{
5966	struct airo_info *local = dev->ml_priv;
5967	StatusRid status_rid;		/* Card status info */
5968
5969	readStatusRid(local, &status_rid, 1);
5970
5971	/* Tentative. This seems to work, wow, I'm lucky !!! */
5972	memcpy(awrq->sa_data, status_rid.bssid[0], ETH_ALEN);
5973	awrq->sa_family = ARPHRD_ETHER;
5974
5975	return 0;
5976}
5977
5978/*------------------------------------------------------------------*/
5979/*
5980 * Wireless Handler : set Nickname
5981 */
5982static int airo_set_nick(struct net_device *dev,
5983			 struct iw_request_info *info,
5984			 struct iw_point *dwrq,
5985			 char *extra)
5986{
5987	struct airo_info *local = dev->ml_priv;
5988
5989	/* Check the size of the string */
5990	if(dwrq->length > 16) {
5991		return -E2BIG;
5992	}
5993	readConfigRid(local, 1);
5994	memset(local->config.nodeName, 0, sizeof(local->config.nodeName));
5995	memcpy(local->config.nodeName, extra, dwrq->length);
5996	set_bit (FLAG_COMMIT, &local->flags);
5997
5998	return -EINPROGRESS;		/* Call commit handler */
5999}
6000
6001/*------------------------------------------------------------------*/
6002/*
6003 * Wireless Handler : get Nickname
6004 */
6005static int airo_get_nick(struct net_device *dev,
6006			 struct iw_request_info *info,
6007			 struct iw_point *dwrq,
6008			 char *extra)
6009{
6010	struct airo_info *local = dev->ml_priv;
6011
6012	readConfigRid(local, 1);
6013	strncpy(extra, local->config.nodeName, 16);
6014	extra[16] = '\0';
6015	dwrq->length = strlen(extra);
6016
6017	return 0;
6018}
6019
6020/*------------------------------------------------------------------*/
6021/*
6022 * Wireless Handler : set Bit-Rate
6023 */
6024static int airo_set_rate(struct net_device *dev,
6025			 struct iw_request_info *info,
6026			 struct iw_param *vwrq,
6027			 char *extra)
6028{
6029	struct airo_info *local = dev->ml_priv;
6030	CapabilityRid cap_rid;		/* Card capability info */
6031	u8	brate = 0;
6032	int	i;
6033
6034	/* First : get a valid bit rate value */
6035	readCapabilityRid(local, &cap_rid, 1);
6036
6037	/* Which type of value ? */
6038	if((vwrq->value < 8) && (vwrq->value >= 0)) {
6039		/* Setting by rate index */
6040		/* Find value in the magic rate table */
6041		brate = cap_rid.supportedRates[vwrq->value];
6042	} else {
6043		/* Setting by frequency value */
6044		u8	normvalue = (u8) (vwrq->value/500000);
6045
6046		/* Check if rate is valid */
6047		for(i = 0 ; i < 8 ; i++) {
6048			if(normvalue == cap_rid.supportedRates[i]) {
6049				brate = normvalue;
6050				break;
6051			}
6052		}
6053	}
6054	/* -1 designed the max rate (mostly auto mode) */
6055	if(vwrq->value == -1) {
6056		/* Get the highest available rate */
6057		for(i = 0 ; i < 8 ; i++) {
6058			if(cap_rid.supportedRates[i] == 0)
6059				break;
6060		}
6061		if(i != 0)
6062			brate = cap_rid.supportedRates[i - 1];
6063	}
6064	/* Check that it is valid */
6065	if(brate == 0) {
6066		return -EINVAL;
6067	}
6068
6069	readConfigRid(local, 1);
6070	/* Now, check if we want a fixed or auto value */
6071	if(vwrq->fixed == 0) {
6072		/* Fill all the rates up to this max rate */
6073		memset(local->config.rates, 0, 8);
6074		for(i = 0 ; i < 8 ; i++) {
6075			local->config.rates[i] = cap_rid.supportedRates[i];
6076			if(local->config.rates[i] == brate)
6077				break;
6078		}
6079	} else {
6080		/* Fixed mode */
6081		/* One rate, fixed */
6082		memset(local->config.rates, 0, 8);
6083		local->config.rates[0] = brate;
6084	}
6085	set_bit (FLAG_COMMIT, &local->flags);
6086
6087	return -EINPROGRESS;		/* Call commit handler */
6088}
6089
6090/*------------------------------------------------------------------*/
6091/*
6092 * Wireless Handler : get Bit-Rate
6093 */
6094static int airo_get_rate(struct net_device *dev,
6095			 struct iw_request_info *info,
6096			 struct iw_param *vwrq,
6097			 char *extra)
6098{
6099	struct airo_info *local = dev->ml_priv;
6100	StatusRid status_rid;		/* Card status info */
6101
6102	readStatusRid(local, &status_rid, 1);
6103
6104	vwrq->value = le16_to_cpu(status_rid.currentXmitRate) * 500000;
6105	/* If more than one rate, set auto */
6106	readConfigRid(local, 1);
6107	vwrq->fixed = (local->config.rates[1] == 0);
6108
6109	return 0;
6110}
6111
6112/*------------------------------------------------------------------*/
6113/*
6114 * Wireless Handler : set RTS threshold
6115 */
6116static int airo_set_rts(struct net_device *dev,
6117			struct iw_request_info *info,
6118			struct iw_param *vwrq,
6119			char *extra)
6120{
6121	struct airo_info *local = dev->ml_priv;
6122	int rthr = vwrq->value;
6123
6124	if(vwrq->disabled)
6125		rthr = AIRO_DEF_MTU;
6126	if((rthr < 0) || (rthr > AIRO_DEF_MTU)) {
6127		return -EINVAL;
6128	}
6129	readConfigRid(local, 1);
6130	local->config.rtsThres = cpu_to_le16(rthr);
6131	set_bit (FLAG_COMMIT, &local->flags);
6132
6133	return -EINPROGRESS;		/* Call commit handler */
6134}
6135
6136/*------------------------------------------------------------------*/
6137/*
6138 * Wireless Handler : get RTS threshold
6139 */
6140static int airo_get_rts(struct net_device *dev,
6141			struct iw_request_info *info,
6142			struct iw_param *vwrq,
6143			char *extra)
6144{
6145	struct airo_info *local = dev->ml_priv;
6146
6147	readConfigRid(local, 1);
6148	vwrq->value = le16_to_cpu(local->config.rtsThres);
6149	vwrq->disabled = (vwrq->value >= AIRO_DEF_MTU);
6150	vwrq->fixed = 1;
6151
6152	return 0;
6153}
6154
6155/*------------------------------------------------------------------*/
6156/*
6157 * Wireless Handler : set Fragmentation threshold
6158 */
6159static int airo_set_frag(struct net_device *dev,
6160			 struct iw_request_info *info,
6161			 struct iw_param *vwrq,
6162			 char *extra)
6163{
6164	struct airo_info *local = dev->ml_priv;
6165	int fthr = vwrq->value;
6166
6167	if(vwrq->disabled)
6168		fthr = AIRO_DEF_MTU;
6169	if((fthr < 256) || (fthr > AIRO_DEF_MTU)) {
6170		return -EINVAL;
6171	}
6172	fthr &= ~0x1;	/* Get an even value - is it really needed ??? */
6173	readConfigRid(local, 1);
6174	local->config.fragThresh = cpu_to_le16(fthr);
6175	set_bit (FLAG_COMMIT, &local->flags);
6176
6177	return -EINPROGRESS;		/* Call commit handler */
6178}
6179
6180/*------------------------------------------------------------------*/
6181/*
6182 * Wireless Handler : get Fragmentation threshold
6183 */
6184static int airo_get_frag(struct net_device *dev,
6185			 struct iw_request_info *info,
6186			 struct iw_param *vwrq,
6187			 char *extra)
6188{
6189	struct airo_info *local = dev->ml_priv;
6190
6191	readConfigRid(local, 1);
6192	vwrq->value = le16_to_cpu(local->config.fragThresh);
6193	vwrq->disabled = (vwrq->value >= AIRO_DEF_MTU);
6194	vwrq->fixed = 1;
6195
6196	return 0;
6197}
6198
6199/*------------------------------------------------------------------*/
6200/*
6201 * Wireless Handler : set Mode of Operation
6202 */
6203static int airo_set_mode(struct net_device *dev,
6204			 struct iw_request_info *info,
6205			 __u32 *uwrq,
6206			 char *extra)
6207{
6208	struct airo_info *local = dev->ml_priv;
6209	int reset = 0;
6210
6211	readConfigRid(local, 1);
6212	if (sniffing_mode(local))
6213		reset = 1;
6214
6215	switch(*uwrq) {
6216		case IW_MODE_ADHOC:
6217			local->config.opmode &= ~MODE_CFG_MASK;
6218			local->config.opmode |= MODE_STA_IBSS;
6219			local->config.rmode &= ~RXMODE_FULL_MASK;
6220			local->config.scanMode = SCANMODE_ACTIVE;
6221			clear_bit (FLAG_802_11, &local->flags);
6222			break;
6223		case IW_MODE_INFRA:
6224			local->config.opmode &= ~MODE_CFG_MASK;
6225			local->config.opmode |= MODE_STA_ESS;
6226			local->config.rmode &= ~RXMODE_FULL_MASK;
6227			local->config.scanMode = SCANMODE_ACTIVE;
6228			clear_bit (FLAG_802_11, &local->flags);
6229			break;
6230		case IW_MODE_MASTER:
6231			local->config.opmode &= ~MODE_CFG_MASK;
6232			local->config.opmode |= MODE_AP;
6233			local->config.rmode &= ~RXMODE_FULL_MASK;
6234			local->config.scanMode = SCANMODE_ACTIVE;
6235			clear_bit (FLAG_802_11, &local->flags);
6236			break;
6237		case IW_MODE_REPEAT:
6238			local->config.opmode &= ~MODE_CFG_MASK;
6239			local->config.opmode |= MODE_AP_RPTR;
6240			local->config.rmode &= ~RXMODE_FULL_MASK;
6241			local->config.scanMode = SCANMODE_ACTIVE;
6242			clear_bit (FLAG_802_11, &local->flags);
6243			break;
6244		case IW_MODE_MONITOR:
6245			local->config.opmode &= ~MODE_CFG_MASK;
6246			local->config.opmode |= MODE_STA_ESS;
6247			local->config.rmode &= ~RXMODE_FULL_MASK;
6248			local->config.rmode |= RXMODE_RFMON | RXMODE_DISABLE_802_3_HEADER;
6249			local->config.scanMode = SCANMODE_PASSIVE;
6250			set_bit (FLAG_802_11, &local->flags);
6251			break;
6252		default:
6253			return -EINVAL;
6254	}
6255	if (reset)
6256		set_bit (FLAG_RESET, &local->flags);
6257	set_bit (FLAG_COMMIT, &local->flags);
6258
6259	return -EINPROGRESS;		/* Call commit handler */
6260}
6261
6262/*------------------------------------------------------------------*/
6263/*
6264 * Wireless Handler : get Mode of Operation
6265 */
6266static int airo_get_mode(struct net_device *dev,
6267			 struct iw_request_info *info,
6268			 __u32 *uwrq,
6269			 char *extra)
6270{
6271	struct airo_info *local = dev->ml_priv;
6272
6273	readConfigRid(local, 1);
6274	/* If not managed, assume it's ad-hoc */
6275	switch (local->config.opmode & MODE_CFG_MASK) {
6276		case MODE_STA_ESS:
6277			*uwrq = IW_MODE_INFRA;
6278			break;
6279		case MODE_AP:
6280			*uwrq = IW_MODE_MASTER;
6281			break;
6282		case MODE_AP_RPTR:
6283			*uwrq = IW_MODE_REPEAT;
6284			break;
6285		default:
6286			*uwrq = IW_MODE_ADHOC;
6287	}
6288
6289	return 0;
6290}
6291
6292static inline int valid_index(struct airo_info *ai, int index)
6293{
6294	return (index >= 0) && (index <= ai->max_wep_idx);
6295}
6296
6297/*------------------------------------------------------------------*/
6298/*
6299 * Wireless Handler : set Encryption Key
6300 */
6301static int airo_set_encode(struct net_device *dev,
6302			   struct iw_request_info *info,
6303			   struct iw_point *dwrq,
6304			   char *extra)
6305{
6306	struct airo_info *local = dev->ml_priv;
6307	int perm = (dwrq->flags & IW_ENCODE_TEMP ? 0 : 1);
6308	__le16 currentAuthType = local->config.authType;
6309	int rc = 0;
6310
6311	if (!local->wep_capable)
6312		return -EOPNOTSUPP;
6313
6314	readConfigRid(local, 1);
6315
6316	/* Basic checking: do we have a key to set ?
6317	 * Note : with the new API, it's impossible to get a NULL pointer.
6318	 * Therefore, we need to check a key size == 0 instead.
6319	 * New version of iwconfig properly set the IW_ENCODE_NOKEY flag
6320	 * when no key is present (only change flags), but older versions
6321	 * don't do it. - Jean II */
6322	if (dwrq->length > 0) {
6323		wep_key_t key;
6324		int index = (dwrq->flags & IW_ENCODE_INDEX) - 1;
6325		int current_index;
6326
6327		/* Check the size of the key */
6328		if (dwrq->length > MAX_KEY_SIZE) {
6329			return -EINVAL;
6330		}
6331
6332		current_index = get_wep_tx_idx(local);
6333		if (current_index < 0)
6334			current_index = 0;
6335
6336		/* Check the index (none -> use current) */
6337		if (!valid_index(local, index))
6338			index = current_index;
6339
6340		/* Set the length */
6341		if (dwrq->length > MIN_KEY_SIZE)
6342			key.len = MAX_KEY_SIZE;
6343		else
6344			key.len = MIN_KEY_SIZE;
6345		/* Check if the key is not marked as invalid */
6346		if(!(dwrq->flags & IW_ENCODE_NOKEY)) {
6347			/* Cleanup */
6348			memset(key.key, 0, MAX_KEY_SIZE);
6349			/* Copy the key in the driver */
6350			memcpy(key.key, extra, dwrq->length);
6351			/* Send the key to the card */
6352			rc = set_wep_key(local, index, key.key, key.len, perm, 1);
6353			if (rc < 0) {
6354				airo_print_err(local->dev->name, "failed to set"
6355				               " WEP key at index %d: %d.",
6356				               index, rc);
6357				return rc;
6358			}
6359		}
6360		/* WE specify that if a valid key is set, encryption
6361		 * should be enabled (user may turn it off later)
6362		 * This is also how "iwconfig ethX key on" works */
6363		if((index == current_index) && (key.len > 0) &&
6364		   (local->config.authType == AUTH_OPEN))
6365			set_auth_type(local, AUTH_ENCRYPT);
6366	} else {
6367		/* Do we want to just set the transmit key index ? */
6368		int index = (dwrq->flags & IW_ENCODE_INDEX) - 1;
6369		if (valid_index(local, index)) {
6370			rc = set_wep_tx_idx(local, index, perm, 1);
6371			if (rc < 0) {
6372				airo_print_err(local->dev->name, "failed to set"
6373				               " WEP transmit index to %d: %d.",
6374				               index, rc);
6375				return rc;
6376			}
6377		} else {
6378			/* Don't complain if only change the mode */
6379			if (!(dwrq->flags & IW_ENCODE_MODE))
6380				return -EINVAL;
6381		}
6382	}
6383	/* Read the flags */
6384	if (dwrq->flags & IW_ENCODE_DISABLED)
6385		set_auth_type(local, AUTH_OPEN);	/* disable encryption */
6386	if(dwrq->flags & IW_ENCODE_RESTRICTED)
6387		set_auth_type(local, AUTH_SHAREDKEY);	/* Only Both */
6388	if (dwrq->flags & IW_ENCODE_OPEN)
6389		set_auth_type(local, AUTH_ENCRYPT);	/* Only Wep */
6390	/* Commit the changes to flags if needed */
6391	if (local->config.authType != currentAuthType)
6392		set_bit (FLAG_COMMIT, &local->flags);
6393	return -EINPROGRESS;		/* Call commit handler */
6394}
6395
6396/*------------------------------------------------------------------*/
6397/*
6398 * Wireless Handler : get Encryption Key
6399 */
6400static int airo_get_encode(struct net_device *dev,
6401			   struct iw_request_info *info,
6402			   struct iw_point *dwrq,
6403			   char *extra)
6404{
6405	struct airo_info *local = dev->ml_priv;
6406	int index = (dwrq->flags & IW_ENCODE_INDEX) - 1;
6407	int wep_key_len;
6408	u8 buf[16];
6409
6410	if (!local->wep_capable)
6411		return -EOPNOTSUPP;
6412
6413	readConfigRid(local, 1);
6414
6415	/* Check encryption mode */
6416	switch(local->config.authType)	{
6417		case AUTH_ENCRYPT:
6418			dwrq->flags = IW_ENCODE_OPEN;
6419			break;
6420		case AUTH_SHAREDKEY:
6421			dwrq->flags = IW_ENCODE_RESTRICTED;
6422			break;
6423		default:
6424		case AUTH_OPEN:
6425			dwrq->flags = IW_ENCODE_DISABLED;
6426			break;
6427	}
6428	/* We can't return the key, so set the proper flag and return zero */
6429	dwrq->flags |= IW_ENCODE_NOKEY;
6430	memset(extra, 0, 16);
6431
6432	/* Which key do we want ? -1 -> tx index */
6433	if (!valid_index(local, index)) {
6434		index = get_wep_tx_idx(local);
6435		if (index < 0)
6436			index = 0;
6437	}
6438	dwrq->flags |= index + 1;
6439
6440	/* Copy the key to the user buffer */
6441	wep_key_len = get_wep_key(local, index, &buf[0], sizeof(buf));
6442	if (wep_key_len < 0) {
6443		dwrq->length = 0;
6444	} else {
6445		dwrq->length = wep_key_len;
6446		memcpy(extra, buf, dwrq->length);
6447	}
6448
6449	return 0;
6450}
6451
6452/*------------------------------------------------------------------*/
6453/*
6454 * Wireless Handler : set extended Encryption parameters
6455 */
6456static int airo_set_encodeext(struct net_device *dev,
6457			   struct iw_request_info *info,
6458			    union iwreq_data *wrqu,
6459			    char *extra)
6460{
6461	struct airo_info *local = dev->ml_priv;
6462	struct iw_point *encoding = &wrqu->encoding;
6463	struct iw_encode_ext *ext = (struct iw_encode_ext *)extra;
6464	int perm = ( encoding->flags & IW_ENCODE_TEMP ? 0 : 1 );
6465	__le16 currentAuthType = local->config.authType;
6466	int idx, key_len, alg = ext->alg, set_key = 1, rc;
6467	wep_key_t key;
6468
6469	if (!local->wep_capable)
6470		return -EOPNOTSUPP;
6471
6472	readConfigRid(local, 1);
6473
6474	/* Determine and validate the key index */
6475	idx = encoding->flags & IW_ENCODE_INDEX;
6476	if (idx) {
6477		if (!valid_index(local, idx - 1))
6478			return -EINVAL;
6479		idx--;
6480	} else {
6481		idx = get_wep_tx_idx(local);
6482		if (idx < 0)
6483			idx = 0;
6484	}
6485
6486	if (encoding->flags & IW_ENCODE_DISABLED)
6487		alg = IW_ENCODE_ALG_NONE;
6488
6489	if (ext->ext_flags & IW_ENCODE_EXT_SET_TX_KEY) {
6490		/* Only set transmit key index here, actual
6491		 * key is set below if needed.
6492		 */
6493		rc = set_wep_tx_idx(local, idx, perm, 1);
6494		if (rc < 0) {
6495			airo_print_err(local->dev->name, "failed to set "
6496			               "WEP transmit index to %d: %d.",
6497			               idx, rc);
6498			return rc;
6499		}
6500		set_key = ext->key_len > 0 ? 1 : 0;
6501	}
6502
6503	if (set_key) {
6504		/* Set the requested key first */
6505		memset(key.key, 0, MAX_KEY_SIZE);
6506		switch (alg) {
6507		case IW_ENCODE_ALG_NONE:
6508			key.len = 0;
6509			break;
6510		case IW_ENCODE_ALG_WEP:
6511			if (ext->key_len > MIN_KEY_SIZE) {
6512				key.len = MAX_KEY_SIZE;
6513			} else if (ext->key_len > 0) {
6514				key.len = MIN_KEY_SIZE;
6515			} else {
6516				return -EINVAL;
6517			}
6518			key_len = min (ext->key_len, key.len);
6519			memcpy(key.key, ext->key, key_len);
6520			break;
6521		default:
6522			return -EINVAL;
6523		}
6524		if (key.len == 0) {
6525			rc = set_wep_tx_idx(local, idx, perm, 1);
6526			if (rc < 0) {
6527				airo_print_err(local->dev->name,
6528					       "failed to set WEP transmit index to %d: %d.",
6529					       idx, rc);
6530				return rc;
6531			}
6532		} else {
6533			rc = set_wep_key(local, idx, key.key, key.len, perm, 1);
6534			if (rc < 0) {
6535				airo_print_err(local->dev->name,
6536					       "failed to set WEP key at index %d: %d.",
6537					       idx, rc);
6538				return rc;
6539			}
6540		}
6541	}
6542
6543	/* Read the flags */
6544	if (encoding->flags & IW_ENCODE_DISABLED)
6545		set_auth_type(local, AUTH_OPEN);	/* disable encryption */
6546	if(encoding->flags & IW_ENCODE_RESTRICTED)
6547		set_auth_type(local, AUTH_SHAREDKEY);	/* Only Both */
6548	if (encoding->flags & IW_ENCODE_OPEN)
6549		set_auth_type(local, AUTH_ENCRYPT);
6550	/* Commit the changes to flags if needed */
6551	if (local->config.authType != currentAuthType)
6552		set_bit (FLAG_COMMIT, &local->flags);
6553
6554	return -EINPROGRESS;
6555}
6556
6557
6558/*------------------------------------------------------------------*/
6559/*
6560 * Wireless Handler : get extended Encryption parameters
6561 */
6562static int airo_get_encodeext(struct net_device *dev,
6563			    struct iw_request_info *info,
6564			    union iwreq_data *wrqu,
6565			    char *extra)
6566{
6567	struct airo_info *local = dev->ml_priv;
6568	struct iw_point *encoding = &wrqu->encoding;
6569	struct iw_encode_ext *ext = (struct iw_encode_ext *)extra;
6570	int idx, max_key_len, wep_key_len;
6571	u8 buf[16];
6572
6573	if (!local->wep_capable)
6574		return -EOPNOTSUPP;
6575
6576	readConfigRid(local, 1);
6577
6578	max_key_len = encoding->length - sizeof(*ext);
6579	if (max_key_len < 0)
6580		return -EINVAL;
6581
6582	idx = encoding->flags & IW_ENCODE_INDEX;
6583	if (idx) {
6584		if (!valid_index(local, idx - 1))
6585			return -EINVAL;
6586		idx--;
6587	} else {
6588		idx = get_wep_tx_idx(local);
6589		if (idx < 0)
6590			idx = 0;
6591	}
6592
6593	encoding->flags = idx + 1;
6594	memset(ext, 0, sizeof(*ext));
6595
6596	/* Check encryption mode */
6597	switch(local->config.authType) {
6598		case AUTH_ENCRYPT:
6599			encoding->flags = IW_ENCODE_ALG_WEP | IW_ENCODE_ENABLED;
6600			break;
6601		case AUTH_SHAREDKEY:
6602			encoding->flags = IW_ENCODE_ALG_WEP | IW_ENCODE_ENABLED;
6603			break;
6604		default:
6605		case AUTH_OPEN:
6606			encoding->flags = IW_ENCODE_ALG_NONE | IW_ENCODE_DISABLED;
6607			break;
6608	}
6609	/* We can't return the key, so set the proper flag and return zero */
6610	encoding->flags |= IW_ENCODE_NOKEY;
6611	memset(extra, 0, 16);
6612	
6613	/* Copy the key to the user buffer */
6614	wep_key_len = get_wep_key(local, idx, &buf[0], sizeof(buf));
6615	if (wep_key_len < 0) {
6616		ext->key_len = 0;
6617	} else {
6618		ext->key_len = wep_key_len;
6619		memcpy(extra, buf, ext->key_len);
6620	}
6621
6622	return 0;
6623}
6624
6625
6626/*------------------------------------------------------------------*/
6627/*
6628 * Wireless Handler : set extended authentication parameters
6629 */
6630static int airo_set_auth(struct net_device *dev,
6631			       struct iw_request_info *info,
6632			       union iwreq_data *wrqu, char *extra)
6633{
6634	struct airo_info *local = dev->ml_priv;
6635	struct iw_param *param = &wrqu->param;
6636	__le16 currentAuthType = local->config.authType;
6637
6638	switch (param->flags & IW_AUTH_INDEX) {
6639	case IW_AUTH_WPA_VERSION:
6640	case IW_AUTH_CIPHER_PAIRWISE:
6641	case IW_AUTH_CIPHER_GROUP:
6642	case IW_AUTH_KEY_MGMT:
6643	case IW_AUTH_RX_UNENCRYPTED_EAPOL:
6644	case IW_AUTH_PRIVACY_INVOKED:
6645		/*
6646		 * airo does not use these parameters
6647		 */
6648		break;
6649
6650	case IW_AUTH_DROP_UNENCRYPTED:
6651		if (param->value) {
6652			/* Only change auth type if unencrypted */
6653			if (currentAuthType == AUTH_OPEN)
6654				set_auth_type(local, AUTH_ENCRYPT);
6655		} else {
6656			set_auth_type(local, AUTH_OPEN);
6657		}
6658
6659		/* Commit the changes to flags if needed */
6660		if (local->config.authType != currentAuthType)
6661			set_bit (FLAG_COMMIT, &local->flags);
6662		break;
6663
6664	case IW_AUTH_80211_AUTH_ALG: {
6665			if (param->value & IW_AUTH_ALG_SHARED_KEY) {
6666				set_auth_type(local, AUTH_SHAREDKEY);
6667			} else if (param->value & IW_AUTH_ALG_OPEN_SYSTEM) {
6668				/* We don't know here if WEP open system or
6669				 * unencrypted mode was requested - so use the
6670				 * last mode (of these two) used last time
6671				 */
6672				set_auth_type(local, local->last_auth);
6673			} else
6674				return -EINVAL;
6675
6676			/* Commit the changes to flags if needed */
6677			if (local->config.authType != currentAuthType)
6678				set_bit (FLAG_COMMIT, &local->flags);
6679			break;
6680		}
6681
6682	case IW_AUTH_WPA_ENABLED:
6683		/* Silently accept disable of WPA */
6684		if (param->value > 0)
6685			return -EOPNOTSUPP;
6686		break;
6687
6688	default:
6689		return -EOPNOTSUPP;
6690	}
6691	return -EINPROGRESS;
6692}
6693
6694
6695/*------------------------------------------------------------------*/
6696/*
6697 * Wireless Handler : get extended authentication parameters
6698 */
6699static int airo_get_auth(struct net_device *dev,
6700			       struct iw_request_info *info,
6701			       union iwreq_data *wrqu, char *extra)
6702{
6703	struct airo_info *local = dev->ml_priv;
6704	struct iw_param *param = &wrqu->param;
6705	__le16 currentAuthType = local->config.authType;
6706
6707	switch (param->flags & IW_AUTH_INDEX) {
6708	case IW_AUTH_DROP_UNENCRYPTED:
6709		switch (currentAuthType) {
6710		case AUTH_SHAREDKEY:
6711		case AUTH_ENCRYPT:
6712			param->value = 1;
6713			break;
6714		default:
6715			param->value = 0;
6716			break;
6717		}
6718		break;
6719
6720	case IW_AUTH_80211_AUTH_ALG:
6721		switch (currentAuthType) {
6722		case AUTH_SHAREDKEY:
6723			param->value = IW_AUTH_ALG_SHARED_KEY;
6724			break;
6725		case AUTH_ENCRYPT:
6726		default:
6727			param->value = IW_AUTH_ALG_OPEN_SYSTEM;
6728			break;
6729		}
6730		break;
6731
6732	case IW_AUTH_WPA_ENABLED:
6733		param->value = 0;
6734		break;
6735
6736	default:
6737		return -EOPNOTSUPP;
6738	}
6739	return 0;
6740}
6741
6742
6743/*------------------------------------------------------------------*/
6744/*
6745 * Wireless Handler : set Tx-Power
6746 */
6747static int airo_set_txpow(struct net_device *dev,
6748			  struct iw_request_info *info,
6749			  struct iw_param *vwrq,
6750			  char *extra)
6751{
6752	struct airo_info *local = dev->ml_priv;
6753	CapabilityRid cap_rid;		/* Card capability info */
6754	int i;
6755	int rc = -EINVAL;
6756	__le16 v = cpu_to_le16(vwrq->value);
6757
6758	readCapabilityRid(local, &cap_rid, 1);
6759
6760	if (vwrq->disabled) {
6761		set_bit (FLAG_RADIO_OFF, &local->flags);
6762		set_bit (FLAG_COMMIT, &local->flags);
6763		return -EINPROGRESS;		/* Call commit handler */
6764	}
6765	if (vwrq->flags != IW_TXPOW_MWATT) {
6766		return -EINVAL;
6767	}
6768	clear_bit (FLAG_RADIO_OFF, &local->flags);
6769	for (i = 0; i < 8 && cap_rid.txPowerLevels[i]; i++)
6770		if (v == cap_rid.txPowerLevels[i]) {
6771			readConfigRid(local, 1);
6772			local->config.txPower = v;
6773			set_bit (FLAG_COMMIT, &local->flags);
6774			rc = -EINPROGRESS;	/* Call commit handler */
6775			break;
6776		}
6777	return rc;
6778}
6779
6780/*------------------------------------------------------------------*/
6781/*
6782 * Wireless Handler : get Tx-Power
6783 */
6784static int airo_get_txpow(struct net_device *dev,
6785			  struct iw_request_info *info,
6786			  struct iw_param *vwrq,
6787			  char *extra)
6788{
6789	struct airo_info *local = dev->ml_priv;
6790
6791	readConfigRid(local, 1);
6792	vwrq->value = le16_to_cpu(local->config.txPower);
6793	vwrq->fixed = 1;	/* No power control */
6794	vwrq->disabled = test_bit(FLAG_RADIO_OFF, &local->flags);
6795	vwrq->flags = IW_TXPOW_MWATT;
6796
6797	return 0;
6798}
6799
6800/*------------------------------------------------------------------*/
6801/*
6802 * Wireless Handler : set Retry limits
6803 */
6804static int airo_set_retry(struct net_device *dev,
6805			  struct iw_request_info *info,
6806			  struct iw_param *vwrq,
6807			  char *extra)
6808{
6809	struct airo_info *local = dev->ml_priv;
6810	int rc = -EINVAL;
6811
6812	if(vwrq->disabled) {
6813		return -EINVAL;
6814	}
6815	readConfigRid(local, 1);
6816	if(vwrq->flags & IW_RETRY_LIMIT) {
6817		__le16 v = cpu_to_le16(vwrq->value);
6818		if(vwrq->flags & IW_RETRY_LONG)
6819			local->config.longRetryLimit = v;
6820		else if (vwrq->flags & IW_RETRY_SHORT)
6821			local->config.shortRetryLimit = v;
6822		else {
6823			/* No modifier : set both */
6824			local->config.longRetryLimit = v;
6825			local->config.shortRetryLimit = v;
6826		}
6827		set_bit (FLAG_COMMIT, &local->flags);
6828		rc = -EINPROGRESS;		/* Call commit handler */
6829	}
6830	if(vwrq->flags & IW_RETRY_LIFETIME) {
6831		local->config.txLifetime = cpu_to_le16(vwrq->value / 1024);
6832		set_bit (FLAG_COMMIT, &local->flags);
6833		rc = -EINPROGRESS;		/* Call commit handler */
6834	}
6835	return rc;
6836}
6837
6838/*------------------------------------------------------------------*/
6839/*
6840 * Wireless Handler : get Retry limits
6841 */
6842static int airo_get_retry(struct net_device *dev,
6843			  struct iw_request_info *info,
6844			  struct iw_param *vwrq,
6845			  char *extra)
6846{
6847	struct airo_info *local = dev->ml_priv;
6848
6849	vwrq->disabled = 0;      /* Can't be disabled */
6850
6851	readConfigRid(local, 1);
6852	/* Note : by default, display the min retry number */
6853	if((vwrq->flags & IW_RETRY_TYPE) == IW_RETRY_LIFETIME) {
6854		vwrq->flags = IW_RETRY_LIFETIME;
6855		vwrq->value = le16_to_cpu(local->config.txLifetime) * 1024;
6856	} else if((vwrq->flags & IW_RETRY_LONG)) {
6857		vwrq->flags = IW_RETRY_LIMIT | IW_RETRY_LONG;
6858		vwrq->value = le16_to_cpu(local->config.longRetryLimit);
6859	} else {
6860		vwrq->flags = IW_RETRY_LIMIT;
6861		vwrq->value = le16_to_cpu(local->config.shortRetryLimit);
6862		if(local->config.shortRetryLimit != local->config.longRetryLimit)
6863			vwrq->flags |= IW_RETRY_SHORT;
6864	}
6865
6866	return 0;
6867}
6868
6869/*------------------------------------------------------------------*/
6870/*
6871 * Wireless Handler : get range info
6872 */
6873static int airo_get_range(struct net_device *dev,
6874			  struct iw_request_info *info,
6875			  struct iw_point *dwrq,
6876			  char *extra)
6877{
6878	struct airo_info *local = dev->ml_priv;
6879	struct iw_range *range = (struct iw_range *) extra;
6880	CapabilityRid cap_rid;		/* Card capability info */
6881	int		i;
6882	int		k;
6883
6884	readCapabilityRid(local, &cap_rid, 1);
6885
6886	dwrq->length = sizeof(struct iw_range);
6887	memset(range, 0, sizeof(*range));
6888	range->min_nwid = 0x0000;
6889	range->max_nwid = 0x0000;
6890	range->num_channels = 14;
6891	/* Should be based on cap_rid.country to give only
6892	 * what the current card support */
6893	k = 0;
6894	for(i = 0; i < 14; i++) {
6895		range->freq[k].i = i + 1; /* List index */
6896		range->freq[k].m = 100000 *
6897		     ieee80211_channel_to_frequency(i + 1, IEEE80211_BAND_2GHZ);
6898		range->freq[k++].e = 1;	/* Values in MHz -> * 10^5 * 10 */
6899	}
6900	range->num_frequency = k;
6901
6902	range->sensitivity = 65535;
6903
6904	/* Hum... Should put the right values there */
6905	if (local->rssi)
6906		range->max_qual.qual = 100;	/* % */
6907	else
6908		range->max_qual.qual = airo_get_max_quality(&cap_rid);
6909	range->max_qual.level = 0x100 - 120;	/* -120 dBm */
6910	range->max_qual.noise = 0x100 - 120;	/* -120 dBm */
6911
6912	/* Experimental measurements - boundary 11/5.5 Mb/s */
6913	/* Note : with or without the (local->rssi), results
6914	 * are somewhat different. - Jean II */
6915	if (local->rssi) {
6916		range->avg_qual.qual = 50;		/* % */
6917		range->avg_qual.level = 0x100 - 70;	/* -70 dBm */
6918	} else {
6919		range->avg_qual.qual = airo_get_avg_quality(&cap_rid);
6920		range->avg_qual.level = 0x100 - 80;	/* -80 dBm */
6921	}
6922	range->avg_qual.noise = 0x100 - 85;		/* -85 dBm */
6923
6924	for(i = 0 ; i < 8 ; i++) {
6925		range->bitrate[i] = cap_rid.supportedRates[i] * 500000;
6926		if(range->bitrate[i] == 0)
6927			break;
6928	}
6929	range->num_bitrates = i;
6930
6931	/* Set an indication of the max TCP throughput
6932	 * in bit/s that we can expect using this interface.
6933	 * May be use for QoS stuff... Jean II */
6934	if(i > 2)
6935		range->throughput = 5000 * 1000;
6936	else
6937		range->throughput = 1500 * 1000;
6938
6939	range->min_rts = 0;
6940	range->max_rts = AIRO_DEF_MTU;
6941	range->min_frag = 256;
6942	range->max_frag = AIRO_DEF_MTU;
6943
6944	if(cap_rid.softCap & cpu_to_le16(2)) {
6945		// WEP: RC4 40 bits
6946		range->encoding_size[0] = 5;
6947		// RC4 ~128 bits
6948		if (cap_rid.softCap & cpu_to_le16(0x100)) {
6949			range->encoding_size[1] = 13;
6950			range->num_encoding_sizes = 2;
6951		} else
6952			range->num_encoding_sizes = 1;
6953		range->max_encoding_tokens =
6954			cap_rid.softCap & cpu_to_le16(0x80) ? 4 : 1;
6955	} else {
6956		range->num_encoding_sizes = 0;
6957		range->max_encoding_tokens = 0;
6958	}
6959	range->min_pmp = 0;
6960	range->max_pmp = 5000000;	/* 5 secs */
6961	range->min_pmt = 0;
6962	range->max_pmt = 65535 * 1024;	/* ??? */
6963	range->pmp_flags = IW_POWER_PERIOD;
6964	range->pmt_flags = IW_POWER_TIMEOUT;
6965	range->pm_capa = IW_POWER_PERIOD | IW_POWER_TIMEOUT | IW_POWER_ALL_R;
6966
6967	/* Transmit Power - values are in mW */
6968	for(i = 0 ; i < 8 ; i++) {
6969		range->txpower[i] = le16_to_cpu(cap_rid.txPowerLevels[i]);
6970		if(range->txpower[i] == 0)
6971			break;
6972	}
6973	range->num_txpower = i;
6974	range->txpower_capa = IW_TXPOW_MWATT;
6975	range->we_version_source = 19;
6976	range->we_version_compiled = WIRELESS_EXT;
6977	range->retry_capa = IW_RETRY_LIMIT | IW_RETRY_LIFETIME;
6978	range->retry_flags = IW_RETRY_LIMIT;
6979	range->r_time_flags = IW_RETRY_LIFETIME;
6980	range->min_retry = 1;
6981	range->max_retry = 65535;
6982	range->min_r_time = 1024;
6983	range->max_r_time = 65535 * 1024;
6984
6985	/* Event capability (kernel + driver) */
6986	range->event_capa[0] = (IW_EVENT_CAPA_K_0 |
6987				IW_EVENT_CAPA_MASK(SIOCGIWTHRSPY) |
6988				IW_EVENT_CAPA_MASK(SIOCGIWAP) |
6989				IW_EVENT_CAPA_MASK(SIOCGIWSCAN));
6990	range->event_capa[1] = IW_EVENT_CAPA_K_1;
6991	range->event_capa[4] = IW_EVENT_CAPA_MASK(IWEVTXDROP);
6992	return 0;
6993}
6994
6995/*------------------------------------------------------------------*/
6996/*
6997 * Wireless Handler : set Power Management
6998 */
6999static int airo_set_power(struct net_device *dev,
7000			  struct iw_request_info *info,
7001			  struct iw_param *vwrq,
7002			  char *extra)
7003{
7004	struct airo_info *local = dev->ml_priv;
7005
7006	readConfigRid(local, 1);
7007	if (vwrq->disabled) {
7008		if (sniffing_mode(local))
7009			return -EINVAL;
7010		local->config.powerSaveMode = POWERSAVE_CAM;
7011		local->config.rmode &= ~RXMODE_MASK;
7012		local->config.rmode |= RXMODE_BC_MC_ADDR;
7013		set_bit (FLAG_COMMIT, &local->flags);
7014		return -EINPROGRESS;		/* Call commit handler */
7015	}
7016	if ((vwrq->flags & IW_POWER_TYPE) == IW_POWER_TIMEOUT) {
7017		local->config.fastListenDelay = cpu_to_le16((vwrq->value + 500) / 1024);
7018		local->config.powerSaveMode = POWERSAVE_PSPCAM;
7019		set_bit (FLAG_COMMIT, &local->flags);
7020	} else if ((vwrq->flags & IW_POWER_TYPE) == IW_POWER_PERIOD) {
7021		local->config.fastListenInterval =
7022		local->config.listenInterval =
7023			cpu_to_le16((vwrq->value + 500) / 1024);
7024		local->config.powerSaveMode = POWERSAVE_PSPCAM;
7025		set_bit (FLAG_COMMIT, &local->flags);
7026	}
7027	switch (vwrq->flags & IW_POWER_MODE) {
7028		case IW_POWER_UNICAST_R:
7029			if (sniffing_mode(local))
7030				return -EINVAL;
7031			local->config.rmode &= ~RXMODE_MASK;
7032			local->config.rmode |= RXMODE_ADDR;
7033			set_bit (FLAG_COMMIT, &local->flags);
7034			break;
7035		case IW_POWER_ALL_R:
7036			if (sniffing_mode(local))
7037				return -EINVAL;
7038			local->config.rmode &= ~RXMODE_MASK;
7039			local->config.rmode |= RXMODE_BC_MC_ADDR;
7040			set_bit (FLAG_COMMIT, &local->flags);
 
7041		case IW_POWER_ON:
7042			/* This is broken, fixme ;-) */
7043			break;
7044		default:
7045			return -EINVAL;
7046	}
7047	// Note : we may want to factor local->need_commit here
7048	// Note2 : may also want to factor RXMODE_RFMON test
7049	return -EINPROGRESS;		/* Call commit handler */
7050}
7051
7052/*------------------------------------------------------------------*/
7053/*
7054 * Wireless Handler : get Power Management
7055 */
7056static int airo_get_power(struct net_device *dev,
7057			  struct iw_request_info *info,
7058			  struct iw_param *vwrq,
7059			  char *extra)
7060{
7061	struct airo_info *local = dev->ml_priv;
7062	__le16 mode;
7063
7064	readConfigRid(local, 1);
7065	mode = local->config.powerSaveMode;
7066	if ((vwrq->disabled = (mode == POWERSAVE_CAM)))
7067		return 0;
7068	if ((vwrq->flags & IW_POWER_TYPE) == IW_POWER_TIMEOUT) {
7069		vwrq->value = le16_to_cpu(local->config.fastListenDelay) * 1024;
7070		vwrq->flags = IW_POWER_TIMEOUT;
7071	} else {
7072		vwrq->value = le16_to_cpu(local->config.fastListenInterval) * 1024;
7073		vwrq->flags = IW_POWER_PERIOD;
7074	}
7075	if ((local->config.rmode & RXMODE_MASK) == RXMODE_ADDR)
7076		vwrq->flags |= IW_POWER_UNICAST_R;
7077	else
7078		vwrq->flags |= IW_POWER_ALL_R;
7079
7080	return 0;
7081}
7082
7083/*------------------------------------------------------------------*/
7084/*
7085 * Wireless Handler : set Sensitivity
7086 */
7087static int airo_set_sens(struct net_device *dev,
7088			 struct iw_request_info *info,
7089			 struct iw_param *vwrq,
7090			 char *extra)
7091{
7092	struct airo_info *local = dev->ml_priv;
7093
7094	readConfigRid(local, 1);
7095	local->config.rssiThreshold =
7096		cpu_to_le16(vwrq->disabled ? RSSI_DEFAULT : vwrq->value);
7097	set_bit (FLAG_COMMIT, &local->flags);
7098
7099	return -EINPROGRESS;		/* Call commit handler */
7100}
7101
7102/*------------------------------------------------------------------*/
7103/*
7104 * Wireless Handler : get Sensitivity
7105 */
7106static int airo_get_sens(struct net_device *dev,
7107			 struct iw_request_info *info,
7108			 struct iw_param *vwrq,
7109			 char *extra)
7110{
7111	struct airo_info *local = dev->ml_priv;
7112
7113	readConfigRid(local, 1);
7114	vwrq->value = le16_to_cpu(local->config.rssiThreshold);
7115	vwrq->disabled = (vwrq->value == 0);
7116	vwrq->fixed = 1;
7117
7118	return 0;
7119}
7120
7121/*------------------------------------------------------------------*/
7122/*
7123 * Wireless Handler : get AP List
7124 * Note : this is deprecated in favor of IWSCAN
7125 */
7126static int airo_get_aplist(struct net_device *dev,
7127			   struct iw_request_info *info,
7128			   struct iw_point *dwrq,
7129			   char *extra)
7130{
7131	struct airo_info *local = dev->ml_priv;
7132	struct sockaddr *address = (struct sockaddr *) extra;
7133	struct iw_quality *qual;
7134	BSSListRid BSSList;
7135	int i;
7136	int loseSync = capable(CAP_NET_ADMIN) ? 1: -1;
7137
7138	qual = kmalloc(IW_MAX_AP * sizeof(*qual), GFP_KERNEL);
7139	if (!qual)
7140		return -ENOMEM;
7141
7142	for (i = 0; i < IW_MAX_AP; i++) {
7143		u16 dBm;
7144		if (readBSSListRid(local, loseSync, &BSSList))
7145			break;
7146		loseSync = 0;
7147		memcpy(address[i].sa_data, BSSList.bssid, ETH_ALEN);
7148		address[i].sa_family = ARPHRD_ETHER;
7149		dBm = le16_to_cpu(BSSList.dBm);
7150		if (local->rssi) {
7151			qual[i].level = 0x100 - dBm;
7152			qual[i].qual = airo_dbm_to_pct(local->rssi, dBm);
7153			qual[i].updated = IW_QUAL_QUAL_UPDATED
7154					| IW_QUAL_LEVEL_UPDATED
7155					| IW_QUAL_DBM;
7156		} else {
7157			qual[i].level = (dBm + 321) / 2;
7158			qual[i].qual = 0;
7159			qual[i].updated = IW_QUAL_QUAL_INVALID
7160					| IW_QUAL_LEVEL_UPDATED
7161					| IW_QUAL_DBM;
7162		}
7163		qual[i].noise = local->wstats.qual.noise;
7164		if (BSSList.index == cpu_to_le16(0xffff))
7165			break;
7166	}
7167	if (!i) {
7168		StatusRid status_rid;		/* Card status info */
7169		readStatusRid(local, &status_rid, 1);
7170		for (i = 0;
7171		     i < min(IW_MAX_AP, 4) &&
7172			     (status_rid.bssid[i][0]
7173			      & status_rid.bssid[i][1]
7174			      & status_rid.bssid[i][2]
7175			      & status_rid.bssid[i][3]
7176			      & status_rid.bssid[i][4]
7177			      & status_rid.bssid[i][5])!=0xff &&
7178			     (status_rid.bssid[i][0]
7179			      | status_rid.bssid[i][1]
7180			      | status_rid.bssid[i][2]
7181			      | status_rid.bssid[i][3]
7182			      | status_rid.bssid[i][4]
7183			      | status_rid.bssid[i][5]);
7184		     i++) {
7185			memcpy(address[i].sa_data,
7186			       status_rid.bssid[i], ETH_ALEN);
7187			address[i].sa_family = ARPHRD_ETHER;
7188		}
7189	} else {
7190		dwrq->flags = 1; /* Should be define'd */
7191		memcpy(extra + sizeof(struct sockaddr) * i, qual,
7192		       sizeof(struct iw_quality) * i);
7193	}
7194	dwrq->length = i;
7195
7196	kfree(qual);
7197	return 0;
7198}
7199
7200/*------------------------------------------------------------------*/
7201/*
7202 * Wireless Handler : Initiate Scan
7203 */
7204static int airo_set_scan(struct net_device *dev,
7205			 struct iw_request_info *info,
7206			 struct iw_point *dwrq,
7207			 char *extra)
7208{
7209	struct airo_info *ai = dev->ml_priv;
7210	Cmd cmd;
7211	Resp rsp;
7212	int wake = 0;
7213	APListRid APList_rid_empty;
7214
7215	/* Note : you may have realised that, as this is a SET operation,
7216	 * this is privileged and therefore a normal user can't
7217	 * perform scanning.
7218	 * This is not an error, while the device perform scanning,
7219	 * traffic doesn't flow, so it's a perfect DoS...
7220	 * Jean II */
7221	if (ai->flags & FLAG_RADIO_MASK) return -ENETDOWN;
7222
7223	if (down_interruptible(&ai->sem))
7224		return -ERESTARTSYS;
7225
7226	/* If there's already a scan in progress, don't
7227	 * trigger another one. */
7228	if (ai->scan_timeout > 0)
7229		goto out;
7230
7231	/* Clear APList as it affects scan results */
7232	memset(&APList_rid_empty, 0, sizeof(APList_rid_empty));
7233	APList_rid_empty.len = cpu_to_le16(sizeof(APList_rid_empty));
7234	disable_MAC(ai, 2);
7235	writeAPListRid(ai, &APList_rid_empty, 0);
7236	enable_MAC(ai, 0);
7237
7238	/* Initiate a scan command */
7239	ai->scan_timeout = RUN_AT(3*HZ);
7240	memset(&cmd, 0, sizeof(cmd));
7241	cmd.cmd=CMD_LISTBSS;
7242	issuecommand(ai, &cmd, &rsp);
7243	wake = 1;
7244
7245out:
7246	up(&ai->sem);
7247	if (wake)
7248		wake_up_interruptible(&ai->thr_wait);
7249	return 0;
7250}
7251
7252/*------------------------------------------------------------------*/
7253/*
7254 * Translate scan data returned from the card to a card independent
7255 * format that the Wireless Tools will understand - Jean II
7256 */
7257static inline char *airo_translate_scan(struct net_device *dev,
7258					struct iw_request_info *info,
7259					char *current_ev,
7260					char *end_buf,
7261					BSSListRid *bss)
7262{
7263	struct airo_info *ai = dev->ml_priv;
7264	struct iw_event		iwe;		/* Temporary buffer */
7265	__le16			capabilities;
7266	char *			current_val;	/* For rates */
7267	int			i;
7268	char *		buf;
7269	u16 dBm;
7270
7271	/* First entry *MUST* be the AP MAC address */
7272	iwe.cmd = SIOCGIWAP;
7273	iwe.u.ap_addr.sa_family = ARPHRD_ETHER;
7274	memcpy(iwe.u.ap_addr.sa_data, bss->bssid, ETH_ALEN);
7275	current_ev = iwe_stream_add_event(info, current_ev, end_buf,
7276					  &iwe, IW_EV_ADDR_LEN);
7277
7278	/* Other entries will be displayed in the order we give them */
7279
7280	/* Add the ESSID */
7281	iwe.u.data.length = bss->ssidLen;
7282	if(iwe.u.data.length > 32)
7283		iwe.u.data.length = 32;
7284	iwe.cmd = SIOCGIWESSID;
7285	iwe.u.data.flags = 1;
7286	current_ev = iwe_stream_add_point(info, current_ev, end_buf,
7287					  &iwe, bss->ssid);
7288
7289	/* Add mode */
7290	iwe.cmd = SIOCGIWMODE;
7291	capabilities = bss->cap;
7292	if(capabilities & (CAP_ESS | CAP_IBSS)) {
7293		if(capabilities & CAP_ESS)
7294			iwe.u.mode = IW_MODE_MASTER;
7295		else
7296			iwe.u.mode = IW_MODE_ADHOC;
7297		current_ev = iwe_stream_add_event(info, current_ev, end_buf,
7298						  &iwe, IW_EV_UINT_LEN);
7299	}
7300
7301	/* Add frequency */
7302	iwe.cmd = SIOCGIWFREQ;
7303	iwe.u.freq.m = le16_to_cpu(bss->dsChannel);
7304	iwe.u.freq.m = 100000 *
7305	      ieee80211_channel_to_frequency(iwe.u.freq.m, IEEE80211_BAND_2GHZ);
7306	iwe.u.freq.e = 1;
7307	current_ev = iwe_stream_add_event(info, current_ev, end_buf,
7308					  &iwe, IW_EV_FREQ_LEN);
7309
7310	dBm = le16_to_cpu(bss->dBm);
7311
7312	/* Add quality statistics */
7313	iwe.cmd = IWEVQUAL;
7314	if (ai->rssi) {
7315		iwe.u.qual.level = 0x100 - dBm;
7316		iwe.u.qual.qual = airo_dbm_to_pct(ai->rssi, dBm);
7317		iwe.u.qual.updated = IW_QUAL_QUAL_UPDATED
7318				| IW_QUAL_LEVEL_UPDATED
7319				| IW_QUAL_DBM;
7320	} else {
7321		iwe.u.qual.level = (dBm + 321) / 2;
7322		iwe.u.qual.qual = 0;
7323		iwe.u.qual.updated = IW_QUAL_QUAL_INVALID
7324				| IW_QUAL_LEVEL_UPDATED
7325				| IW_QUAL_DBM;
7326	}
7327	iwe.u.qual.noise = ai->wstats.qual.noise;
7328	current_ev = iwe_stream_add_event(info, current_ev, end_buf,
7329					  &iwe, IW_EV_QUAL_LEN);
7330
7331	/* Add encryption capability */
7332	iwe.cmd = SIOCGIWENCODE;
7333	if(capabilities & CAP_PRIVACY)
7334		iwe.u.data.flags = IW_ENCODE_ENABLED | IW_ENCODE_NOKEY;
7335	else
7336		iwe.u.data.flags = IW_ENCODE_DISABLED;
7337	iwe.u.data.length = 0;
7338	current_ev = iwe_stream_add_point(info, current_ev, end_buf,
7339					  &iwe, bss->ssid);
7340
7341	/* Rate : stuffing multiple values in a single event require a bit
7342	 * more of magic - Jean II */
7343	current_val = current_ev + iwe_stream_lcp_len(info);
7344
7345	iwe.cmd = SIOCGIWRATE;
7346	/* Those two flags are ignored... */
7347	iwe.u.bitrate.fixed = iwe.u.bitrate.disabled = 0;
7348	/* Max 8 values */
7349	for(i = 0 ; i < 8 ; i++) {
7350		/* NULL terminated */
7351		if(bss->rates[i] == 0)
7352			break;
7353		/* Bit rate given in 500 kb/s units (+ 0x80) */
7354		iwe.u.bitrate.value = ((bss->rates[i] & 0x7f) * 500000);
7355		/* Add new value to event */
7356		current_val = iwe_stream_add_value(info, current_ev,
7357						   current_val, end_buf,
7358						   &iwe, IW_EV_PARAM_LEN);
7359	}
7360	/* Check if we added any event */
7361	if ((current_val - current_ev) > iwe_stream_lcp_len(info))
7362		current_ev = current_val;
7363
7364	/* Beacon interval */
7365	buf = kmalloc(30, GFP_KERNEL);
7366	if (buf) {
7367		iwe.cmd = IWEVCUSTOM;
7368		sprintf(buf, "bcn_int=%d", bss->beaconInterval);
7369		iwe.u.data.length = strlen(buf);
7370		current_ev = iwe_stream_add_point(info, current_ev, end_buf,
7371						  &iwe, buf);
7372		kfree(buf);
7373	}
7374
7375	/* Put WPA/RSN Information Elements into the event stream */
7376	if (test_bit(FLAG_WPA_CAPABLE, &ai->flags)) {
7377		unsigned int num_null_ies = 0;
7378		u16 length = sizeof (bss->extra.iep);
7379		u8 *ie = (void *)&bss->extra.iep;
7380
7381		while ((length >= 2) && (num_null_ies < 2)) {
7382			if (2 + ie[1] > length) {
7383				/* Invalid element, don't continue parsing IE */
7384				break;
7385			}
7386
7387			switch (ie[0]) {
7388			case WLAN_EID_SSID:
7389				/* Two zero-length SSID elements
7390				 * mean we're done parsing elements */
7391				if (!ie[1])
7392					num_null_ies++;
7393				break;
7394
7395			case WLAN_EID_VENDOR_SPECIFIC:
7396				if (ie[1] >= 4 &&
7397				    ie[2] == 0x00 &&
7398				    ie[3] == 0x50 &&
7399				    ie[4] == 0xf2 &&
7400				    ie[5] == 0x01) {
7401					iwe.cmd = IWEVGENIE;
7402					/* 64 is an arbitrary cut-off */
7403					iwe.u.data.length = min(ie[1] + 2,
7404								64);
7405					current_ev = iwe_stream_add_point(
7406							info, current_ev,
7407							end_buf, &iwe, ie);
7408				}
7409				break;
7410
7411			case WLAN_EID_RSN:
7412				iwe.cmd = IWEVGENIE;
7413				/* 64 is an arbitrary cut-off */
7414				iwe.u.data.length = min(ie[1] + 2, 64);
7415				current_ev = iwe_stream_add_point(
7416					info, current_ev, end_buf,
7417					&iwe, ie);
7418				break;
7419
7420			default:
7421				break;
7422			}
7423
7424			length -= 2 + ie[1];
7425			ie += 2 + ie[1];
7426		}
7427	}
7428	return current_ev;
7429}
7430
7431/*------------------------------------------------------------------*/
7432/*
7433 * Wireless Handler : Read Scan Results
7434 */
7435static int airo_get_scan(struct net_device *dev,
7436			 struct iw_request_info *info,
7437			 struct iw_point *dwrq,
7438			 char *extra)
7439{
7440	struct airo_info *ai = dev->ml_priv;
7441	BSSListElement *net;
7442	int err = 0;
7443	char *current_ev = extra;
7444
7445	/* If a scan is in-progress, return -EAGAIN */
7446	if (ai->scan_timeout > 0)
7447		return -EAGAIN;
7448
7449	if (down_interruptible(&ai->sem))
7450		return -EAGAIN;
7451
7452	list_for_each_entry (net, &ai->network_list, list) {
7453		/* Translate to WE format this entry */
7454		current_ev = airo_translate_scan(dev, info, current_ev,
7455						 extra + dwrq->length,
7456						 &net->bss);
7457
7458		/* Check if there is space for one more entry */
7459		if((extra + dwrq->length - current_ev) <= IW_EV_ADDR_LEN) {
7460			/* Ask user space to try again with a bigger buffer */
7461			err = -E2BIG;
7462			goto out;
7463		}
7464	}
7465
7466	/* Length of data */
7467	dwrq->length = (current_ev - extra);
7468	dwrq->flags = 0;	/* todo */
7469
7470out:
7471	up(&ai->sem);
7472	return err;
7473}
7474
7475/*------------------------------------------------------------------*/
7476/*
7477 * Commit handler : called after a bunch of SET operations
7478 */
7479static int airo_config_commit(struct net_device *dev,
7480			      struct iw_request_info *info,	/* NULL */
7481			      void *zwrq,			/* NULL */
7482			      char *extra)			/* NULL */
7483{
7484	struct airo_info *local = dev->ml_priv;
7485
7486	if (!test_bit (FLAG_COMMIT, &local->flags))
7487		return 0;
7488
7489	/* Some of the "SET" function may have modified some of the
7490	 * parameters. It's now time to commit them in the card */
7491	disable_MAC(local, 1);
7492	if (test_bit (FLAG_RESET, &local->flags)) {
7493		SsidRid SSID_rid;
7494
7495		readSsidRid(local, &SSID_rid);
7496		if (test_bit(FLAG_MPI,&local->flags))
7497			setup_card(local, dev->dev_addr, 1 );
7498		else
7499			reset_airo_card(dev);
7500		disable_MAC(local, 1);
7501		writeSsidRid(local, &SSID_rid, 1);
7502		writeAPListRid(local, &local->APList, 1);
7503	}
7504	if (down_interruptible(&local->sem))
7505		return -ERESTARTSYS;
7506	writeConfigRid(local, 0);
7507	enable_MAC(local, 0);
7508	if (test_bit (FLAG_RESET, &local->flags))
7509		airo_set_promisc(local);
7510	else
7511		up(&local->sem);
7512
7513	return 0;
7514}
7515
7516/*------------------------------------------------------------------*/
7517/*
7518 * Structures to export the Wireless Handlers
7519 */
7520
7521static const struct iw_priv_args airo_private_args[] = {
7522/*{ cmd,         set_args,                            get_args, name } */
7523  { AIROIOCTL, IW_PRIV_TYPE_BYTE | IW_PRIV_SIZE_FIXED | sizeof (aironet_ioctl),
7524    IW_PRIV_TYPE_BYTE | 2047, "airoioctl" },
7525  { AIROIDIFC, IW_PRIV_TYPE_BYTE | IW_PRIV_SIZE_FIXED | sizeof (aironet_ioctl),
7526    IW_PRIV_TYPE_INT | IW_PRIV_SIZE_FIXED | 1, "airoidifc" },
7527};
7528
7529static const iw_handler		airo_handler[] =
7530{
7531	(iw_handler) airo_config_commit,	/* SIOCSIWCOMMIT */
7532	(iw_handler) airo_get_name,		/* SIOCGIWNAME */
7533	(iw_handler) NULL,			/* SIOCSIWNWID */
7534	(iw_handler) NULL,			/* SIOCGIWNWID */
7535	(iw_handler) airo_set_freq,		/* SIOCSIWFREQ */
7536	(iw_handler) airo_get_freq,		/* SIOCGIWFREQ */
7537	(iw_handler) airo_set_mode,		/* SIOCSIWMODE */
7538	(iw_handler) airo_get_mode,		/* SIOCGIWMODE */
7539	(iw_handler) airo_set_sens,		/* SIOCSIWSENS */
7540	(iw_handler) airo_get_sens,		/* SIOCGIWSENS */
7541	(iw_handler) NULL,			/* SIOCSIWRANGE */
7542	(iw_handler) airo_get_range,		/* SIOCGIWRANGE */
7543	(iw_handler) NULL,			/* SIOCSIWPRIV */
7544	(iw_handler) NULL,			/* SIOCGIWPRIV */
7545	(iw_handler) NULL,			/* SIOCSIWSTATS */
7546	(iw_handler) NULL,			/* SIOCGIWSTATS */
7547	iw_handler_set_spy,			/* SIOCSIWSPY */
7548	iw_handler_get_spy,			/* SIOCGIWSPY */
7549	iw_handler_set_thrspy,			/* SIOCSIWTHRSPY */
7550	iw_handler_get_thrspy,			/* SIOCGIWTHRSPY */
7551	(iw_handler) airo_set_wap,		/* SIOCSIWAP */
7552	(iw_handler) airo_get_wap,		/* SIOCGIWAP */
7553	(iw_handler) NULL,			/* -- hole -- */
7554	(iw_handler) airo_get_aplist,		/* SIOCGIWAPLIST */
7555	(iw_handler) airo_set_scan,		/* SIOCSIWSCAN */
7556	(iw_handler) airo_get_scan,		/* SIOCGIWSCAN */
7557	(iw_handler) airo_set_essid,		/* SIOCSIWESSID */
7558	(iw_handler) airo_get_essid,		/* SIOCGIWESSID */
7559	(iw_handler) airo_set_nick,		/* SIOCSIWNICKN */
7560	(iw_handler) airo_get_nick,		/* SIOCGIWNICKN */
7561	(iw_handler) NULL,			/* -- hole -- */
7562	(iw_handler) NULL,			/* -- hole -- */
7563	(iw_handler) airo_set_rate,		/* SIOCSIWRATE */
7564	(iw_handler) airo_get_rate,		/* SIOCGIWRATE */
7565	(iw_handler) airo_set_rts,		/* SIOCSIWRTS */
7566	(iw_handler) airo_get_rts,		/* SIOCGIWRTS */
7567	(iw_handler) airo_set_frag,		/* SIOCSIWFRAG */
7568	(iw_handler) airo_get_frag,		/* SIOCGIWFRAG */
7569	(iw_handler) airo_set_txpow,		/* SIOCSIWTXPOW */
7570	(iw_handler) airo_get_txpow,		/* SIOCGIWTXPOW */
7571	(iw_handler) airo_set_retry,		/* SIOCSIWRETRY */
7572	(iw_handler) airo_get_retry,		/* SIOCGIWRETRY */
7573	(iw_handler) airo_set_encode,		/* SIOCSIWENCODE */
7574	(iw_handler) airo_get_encode,		/* SIOCGIWENCODE */
7575	(iw_handler) airo_set_power,		/* SIOCSIWPOWER */
7576	(iw_handler) airo_get_power,		/* SIOCGIWPOWER */
7577	(iw_handler) NULL,			/* -- hole -- */
7578	(iw_handler) NULL,			/* -- hole -- */
7579	(iw_handler) NULL,			/* SIOCSIWGENIE */
7580	(iw_handler) NULL,			/* SIOCGIWGENIE */
7581	(iw_handler) airo_set_auth,		/* SIOCSIWAUTH */
7582	(iw_handler) airo_get_auth,		/* SIOCGIWAUTH */
7583	(iw_handler) airo_set_encodeext,	/* SIOCSIWENCODEEXT */
7584	(iw_handler) airo_get_encodeext,	/* SIOCGIWENCODEEXT */
7585	(iw_handler) NULL,			/* SIOCSIWPMKSA */
7586};
7587
7588/* Note : don't describe AIROIDIFC and AIROOLDIDIFC in here.
7589 * We want to force the use of the ioctl code, because those can't be
7590 * won't work the iw_handler code (because they simultaneously read
7591 * and write data and iw_handler can't do that).
7592 * Note that it's perfectly legal to read/write on a single ioctl command,
7593 * you just can't use iwpriv and need to force it via the ioctl handler.
7594 * Jean II */
7595static const iw_handler		airo_private_handler[] =
7596{
7597	NULL,				/* SIOCIWFIRSTPRIV */
7598};
7599
7600static const struct iw_handler_def	airo_handler_def =
7601{
7602	.num_standard	= ARRAY_SIZE(airo_handler),
7603	.num_private	= ARRAY_SIZE(airo_private_handler),
7604	.num_private_args = ARRAY_SIZE(airo_private_args),
7605	.standard	= airo_handler,
7606	.private	= airo_private_handler,
7607	.private_args	= airo_private_args,
7608	.get_wireless_stats = airo_get_wireless_stats,
7609};
7610
7611/*
7612 * This defines the configuration part of the Wireless Extensions
7613 * Note : irq and spinlock protection will occur in the subroutines
7614 *
7615 * TODO :
7616 *	o Check input value more carefully and fill correct values in range
7617 *	o Test and shakeout the bugs (if any)
7618 *
7619 * Jean II
7620 *
7621 * Javier Achirica did a great job of merging code from the unnamed CISCO
7622 * developer that added support for flashing the card.
7623 */
7624static int airo_ioctl(struct net_device *dev, struct ifreq *rq, int cmd)
7625{
7626	int rc = 0;
7627	struct airo_info *ai = dev->ml_priv;
7628
7629	if (ai->power.event)
7630		return 0;
7631
7632	switch (cmd) {
7633#ifdef CISCO_EXT
7634	case AIROIDIFC:
7635#ifdef AIROOLDIDIFC
7636	case AIROOLDIDIFC:
7637#endif
7638	{
7639		int val = AIROMAGIC;
7640		aironet_ioctl com;
7641		if (copy_from_user(&com,rq->ifr_data,sizeof(com)))
7642			rc = -EFAULT;
7643		else if (copy_to_user(com.data,(char *)&val,sizeof(val)))
7644			rc = -EFAULT;
7645	}
7646	break;
7647
7648	case AIROIOCTL:
7649#ifdef AIROOLDIOCTL
7650	case AIROOLDIOCTL:
7651#endif
7652		/* Get the command struct and hand it off for evaluation by
7653		 * the proper subfunction
7654		 */
7655	{
7656		aironet_ioctl com;
7657		if (copy_from_user(&com,rq->ifr_data,sizeof(com))) {
7658			rc = -EFAULT;
7659			break;
7660		}
7661
7662		/* Separate R/W functions bracket legality here
7663		 */
7664		if ( com.command == AIRORSWVERSION ) {
7665			if (copy_to_user(com.data, swversion, sizeof(swversion)))
7666				rc = -EFAULT;
7667			else
7668				rc = 0;
7669		}
7670		else if ( com.command <= AIRORRID)
7671			rc = readrids(dev,&com);
7672		else if ( com.command >= AIROPCAP && com.command <= (AIROPLEAPUSR+2) )
7673			rc = writerids(dev,&com);
7674		else if ( com.command >= AIROFLSHRST && com.command <= AIRORESTART )
7675			rc = flashcard(dev,&com);
7676		else
7677			rc = -EINVAL;      /* Bad command in ioctl */
7678	}
7679	break;
7680#endif /* CISCO_EXT */
7681
7682	// All other calls are currently unsupported
7683	default:
7684		rc = -EOPNOTSUPP;
7685	}
7686	return rc;
7687}
7688
7689/*
7690 * Get the Wireless stats out of the driver
7691 * Note : irq and spinlock protection will occur in the subroutines
7692 *
7693 * TODO :
7694 *	o Check if work in Ad-Hoc mode (otherwise, use SPY, as in wvlan_cs)
7695 *
7696 * Jean
7697 */
7698static void airo_read_wireless_stats(struct airo_info *local)
7699{
7700	StatusRid status_rid;
7701	StatsRid stats_rid;
7702	CapabilityRid cap_rid;
7703	__le32 *vals = stats_rid.vals;
7704
7705	/* Get stats out of the card */
7706	clear_bit(JOB_WSTATS, &local->jobs);
7707	if (local->power.event) {
7708		up(&local->sem);
7709		return;
7710	}
7711	readCapabilityRid(local, &cap_rid, 0);
7712	readStatusRid(local, &status_rid, 0);
7713	readStatsRid(local, &stats_rid, RID_STATS, 0);
7714	up(&local->sem);
7715
7716	/* The status */
7717	local->wstats.status = le16_to_cpu(status_rid.mode);
7718
7719	/* Signal quality and co */
7720	if (local->rssi) {
7721		local->wstats.qual.level =
7722			airo_rssi_to_dbm(local->rssi,
7723					 le16_to_cpu(status_rid.sigQuality));
7724		/* normalizedSignalStrength appears to be a percentage */
7725		local->wstats.qual.qual =
7726			le16_to_cpu(status_rid.normalizedSignalStrength);
7727	} else {
7728		local->wstats.qual.level =
7729			(le16_to_cpu(status_rid.normalizedSignalStrength) + 321) / 2;
7730		local->wstats.qual.qual = airo_get_quality(&status_rid, &cap_rid);
7731	}
7732	if (le16_to_cpu(status_rid.len) >= 124) {
7733		local->wstats.qual.noise = 0x100 - status_rid.noisedBm;
7734		local->wstats.qual.updated = IW_QUAL_ALL_UPDATED | IW_QUAL_DBM;
7735	} else {
7736		local->wstats.qual.noise = 0;
7737		local->wstats.qual.updated = IW_QUAL_QUAL_UPDATED | IW_QUAL_LEVEL_UPDATED | IW_QUAL_NOISE_INVALID | IW_QUAL_DBM;
7738	}
7739
7740	/* Packets discarded in the wireless adapter due to wireless
7741	 * specific problems */
7742	local->wstats.discard.nwid = le32_to_cpu(vals[56]) +
7743				     le32_to_cpu(vals[57]) +
7744				     le32_to_cpu(vals[58]); /* SSID Mismatch */
7745	local->wstats.discard.code = le32_to_cpu(vals[6]);/* RxWepErr */
7746	local->wstats.discard.fragment = le32_to_cpu(vals[30]);
7747	local->wstats.discard.retries = le32_to_cpu(vals[10]);
7748	local->wstats.discard.misc = le32_to_cpu(vals[1]) +
7749				     le32_to_cpu(vals[32]);
7750	local->wstats.miss.beacon = le32_to_cpu(vals[34]);
7751}
7752
7753static struct iw_statistics *airo_get_wireless_stats(struct net_device *dev)
7754{
7755	struct airo_info *local =  dev->ml_priv;
7756
7757	if (!test_bit(JOB_WSTATS, &local->jobs)) {
7758		/* Get stats out of the card if available */
7759		if (down_trylock(&local->sem) != 0) {
7760			set_bit(JOB_WSTATS, &local->jobs);
7761			wake_up_interruptible(&local->thr_wait);
7762		} else
7763			airo_read_wireless_stats(local);
7764	}
7765
7766	return &local->wstats;
7767}
7768
7769#ifdef CISCO_EXT
7770/*
7771 * This just translates from driver IOCTL codes to the command codes to
7772 * feed to the radio's host interface. Things can be added/deleted
7773 * as needed.  This represents the READ side of control I/O to
7774 * the card
7775 */
7776static int readrids(struct net_device *dev, aironet_ioctl *comp) {
 
7777	unsigned short ridcode;
7778	unsigned char *iobuf;
7779	int len;
7780	struct airo_info *ai = dev->ml_priv;
7781
7782	if (test_bit(FLAG_FLASHING, &ai->flags))
7783		return -EIO;
7784
7785	switch(comp->command)
7786	{
7787	case AIROGCAP:      ridcode = RID_CAPABILITIES; break;
7788	case AIROGCFG:      ridcode = RID_CONFIG;
7789		if (test_bit(FLAG_COMMIT, &ai->flags)) {
7790			disable_MAC (ai, 1);
7791			writeConfigRid (ai, 1);
7792			enable_MAC(ai, 1);
7793		}
7794		break;
7795	case AIROGSLIST:    ridcode = RID_SSID;         break;
7796	case AIROGVLIST:    ridcode = RID_APLIST;       break;
7797	case AIROGDRVNAM:   ridcode = RID_DRVNAME;      break;
7798	case AIROGEHTENC:   ridcode = RID_ETHERENCAP;   break;
7799	case AIROGWEPKTMP:  ridcode = RID_WEP_TEMP;
7800		/* Only super-user can read WEP keys */
7801		if (!capable(CAP_NET_ADMIN))
7802			return -EPERM;
7803		break;
7804	case AIROGWEPKNV:   ridcode = RID_WEP_PERM;
7805		/* Only super-user can read WEP keys */
7806		if (!capable(CAP_NET_ADMIN))
7807			return -EPERM;
7808		break;
7809	case AIROGSTAT:     ridcode = RID_STATUS;       break;
7810	case AIROGSTATSD32: ridcode = RID_STATSDELTA;   break;
7811	case AIROGSTATSC32: ridcode = RID_STATS;        break;
7812	case AIROGMICSTATS:
7813		if (copy_to_user(comp->data, &ai->micstats,
7814				 min((int)comp->len,(int)sizeof(ai->micstats))))
7815			return -EFAULT;
7816		return 0;
7817	case AIRORRID:      ridcode = comp->ridnum;     break;
7818	default:
7819		return -EINVAL;
7820	}
7821
7822	if ((iobuf = kmalloc(RIDSIZE, GFP_KERNEL)) == NULL)
 
 
 
 
 
 
7823		return -ENOMEM;
7824
7825	PC4500_readrid(ai,ridcode,iobuf,RIDSIZE, 1);
7826	/* get the count of bytes in the rid  docs say 1st 2 bytes is it.
7827	 * then return it to the user
7828	 * 9/22/2000 Honor user given length
7829	 */
7830	len = comp->len;
7831
7832	if (copy_to_user(comp->data, iobuf, min(len, (int)RIDSIZE))) {
7833		kfree (iobuf);
7834		return -EFAULT;
7835	}
7836	kfree (iobuf);
7837	return 0;
7838}
7839
7840/*
7841 * Danger Will Robinson write the rids here
7842 */
7843
7844static int writerids(struct net_device *dev, aironet_ioctl *comp) {
 
7845	struct airo_info *ai = dev->ml_priv;
7846	int  ridcode;
7847        int  enabled;
7848	static int (* writer)(struct airo_info *, u16 rid, const void *, int, int);
7849	unsigned char *iobuf;
7850
7851	/* Only super-user can write RIDs */
7852	if (!capable(CAP_NET_ADMIN))
7853		return -EPERM;
7854
7855	if (test_bit(FLAG_FLASHING, &ai->flags))
7856		return -EIO;
7857
7858	ridcode = 0;
7859	writer = do_writerid;
7860
7861	switch(comp->command)
7862	{
7863	case AIROPSIDS:     ridcode = RID_SSID;         break;
7864	case AIROPCAP:      ridcode = RID_CAPABILITIES; break;
7865	case AIROPAPLIST:   ridcode = RID_APLIST;       break;
7866	case AIROPCFG: ai->config.len = 0;
7867			    clear_bit(FLAG_COMMIT, &ai->flags);
7868			    ridcode = RID_CONFIG;       break;
7869	case AIROPWEPKEYNV: ridcode = RID_WEP_PERM;     break;
7870	case AIROPLEAPUSR:  ridcode = RID_LEAPUSERNAME; break;
7871	case AIROPLEAPPWD:  ridcode = RID_LEAPPASSWORD; break;
7872	case AIROPWEPKEY:   ridcode = RID_WEP_TEMP; writer = PC4500_writerid;
7873		break;
7874	case AIROPLEAPUSR+1: ridcode = 0xFF2A;          break;
7875	case AIROPLEAPUSR+2: ridcode = 0xFF2B;          break;
7876
7877		/* this is not really a rid but a command given to the card
7878		 * same with MAC off
7879		 */
7880	case AIROPMACON:
7881		if (enable_MAC(ai, 1) != 0)
7882			return -EIO;
7883		return 0;
7884
7885		/*
7886		 * Evidently this code in the airo driver does not get a symbol
7887		 * as disable_MAC. it's probably so short the compiler does not gen one.
7888		 */
7889	case AIROPMACOFF:
7890		disable_MAC(ai, 1);
7891		return 0;
7892
7893		/* This command merely clears the counts does not actually store any data
7894		 * only reads rid. But as it changes the cards state, I put it in the
7895		 * writerid routines.
7896		 */
7897	case AIROPSTCLR:
7898		if ((iobuf = kmalloc(RIDSIZE, GFP_KERNEL)) == NULL)
7899			return -ENOMEM;
7900
7901		PC4500_readrid(ai,RID_STATSDELTACLEAR,iobuf,RIDSIZE, 1);
7902
7903		enabled = ai->micstats.enabled;
7904		memset(&ai->micstats,0,sizeof(ai->micstats));
7905		ai->micstats.enabled = enabled;
7906
7907		if (copy_to_user(comp->data, iobuf,
7908				 min((int)comp->len, (int)RIDSIZE))) {
7909			kfree (iobuf);
7910			return -EFAULT;
7911		}
7912		kfree (iobuf);
7913		return 0;
7914
7915	default:
7916		return -EOPNOTSUPP;	/* Blarg! */
7917	}
7918	if(comp->len > RIDSIZE)
7919		return -EINVAL;
7920
7921	if ((iobuf = kmalloc(RIDSIZE, GFP_KERNEL)) == NULL)
7922		return -ENOMEM;
7923
7924	if (copy_from_user(iobuf,comp->data,comp->len)) {
7925		kfree (iobuf);
7926		return -EFAULT;
7927	}
7928
7929	if (comp->command == AIROPCFG) {
7930		ConfigRid *cfg = (ConfigRid *)iobuf;
7931
7932		if (test_bit(FLAG_MIC_CAPABLE, &ai->flags))
7933			cfg->opmode |= MODE_MIC;
7934
7935		if ((cfg->opmode & MODE_CFG_MASK) == MODE_STA_IBSS)
7936			set_bit (FLAG_ADHOC, &ai->flags);
7937		else
7938			clear_bit (FLAG_ADHOC, &ai->flags);
7939	}
7940
7941	if((*writer)(ai, ridcode, iobuf,comp->len,1)) {
7942		kfree (iobuf);
7943		return -EIO;
7944	}
7945	kfree (iobuf);
7946	return 0;
7947}
7948
7949/*****************************************************************************
7950 * Ancillary flash / mod functions much black magic lurkes here              *
7951 *****************************************************************************
7952 */
7953
7954/*
7955 * Flash command switch table
7956 */
7957
7958static int flashcard(struct net_device *dev, aironet_ioctl *comp) {
 
7959	int z;
7960
7961	/* Only super-user can modify flash */
7962	if (!capable(CAP_NET_ADMIN))
7963		return -EPERM;
7964
7965	switch(comp->command)
7966	{
7967	case AIROFLSHRST:
7968		return cmdreset((struct airo_info *)dev->ml_priv);
7969
7970	case AIROFLSHSTFL:
7971		if (!AIRO_FLASH(dev) &&
7972		    (AIRO_FLASH(dev) = kmalloc(FLASHSIZE, GFP_KERNEL)) == NULL)
7973			return -ENOMEM;
7974		return setflashmode((struct airo_info *)dev->ml_priv);
7975
7976	case AIROFLSHGCHR: /* Get char from aux */
7977		if(comp->len != sizeof(int))
7978			return -EINVAL;
7979		if (copy_from_user(&z,comp->data,comp->len))
7980			return -EFAULT;
7981		return flashgchar((struct airo_info *)dev->ml_priv, z, 8000);
7982
7983	case AIROFLSHPCHR: /* Send char to card. */
7984		if(comp->len != sizeof(int))
7985			return -EINVAL;
7986		if (copy_from_user(&z,comp->data,comp->len))
7987			return -EFAULT;
7988		return flashpchar((struct airo_info *)dev->ml_priv, z, 8000);
7989
7990	case AIROFLPUTBUF: /* Send 32k to card */
7991		if (!AIRO_FLASH(dev))
7992			return -ENOMEM;
7993		if(comp->len > FLASHSIZE)
7994			return -EINVAL;
7995		if (copy_from_user(AIRO_FLASH(dev), comp->data, comp->len))
7996			return -EFAULT;
7997
7998		flashputbuf((struct airo_info *)dev->ml_priv);
7999		return 0;
8000
8001	case AIRORESTART:
8002		if (flashrestart((struct airo_info *)dev->ml_priv, dev))
8003			return -EIO;
8004		return 0;
8005	}
8006	return -EINVAL;
8007}
8008
8009#define FLASH_COMMAND  0x7e7e
8010
8011/*
8012 * STEP 1)
8013 * Disable MAC and do soft reset on
8014 * card.
8015 */
8016
8017static int cmdreset(struct airo_info *ai) {
 
8018	disable_MAC(ai, 1);
8019
8020	if(!waitbusy (ai)){
8021		airo_print_info(ai->dev->name, "Waitbusy hang before RESET");
8022		return -EBUSY;
8023	}
8024
8025	OUT4500(ai,COMMAND,CMD_SOFTRESET);
8026
8027	ssleep(1);			/* WAS 600 12/7/00 */
8028
8029	if(!waitbusy (ai)){
8030		airo_print_info(ai->dev->name, "Waitbusy hang AFTER RESET");
8031		return -EBUSY;
8032	}
8033	return 0;
8034}
8035
8036/* STEP 2)
8037 * Put the card in legendary flash
8038 * mode
8039 */
8040
8041static int setflashmode (struct airo_info *ai) {
 
8042	set_bit (FLAG_FLASHING, &ai->flags);
8043
8044	OUT4500(ai, SWS0, FLASH_COMMAND);
8045	OUT4500(ai, SWS1, FLASH_COMMAND);
8046	if (probe) {
8047		OUT4500(ai, SWS0, FLASH_COMMAND);
8048		OUT4500(ai, COMMAND,0x10);
8049	} else {
8050		OUT4500(ai, SWS2, FLASH_COMMAND);
8051		OUT4500(ai, SWS3, FLASH_COMMAND);
8052		OUT4500(ai, COMMAND,0);
8053	}
8054	msleep(500);		/* 500ms delay */
8055
8056	if(!waitbusy(ai)) {
8057		clear_bit (FLAG_FLASHING, &ai->flags);
8058		airo_print_info(ai->dev->name, "Waitbusy hang after setflash mode");
8059		return -EIO;
8060	}
8061	return 0;
8062}
8063
8064/* Put character to SWS0 wait for dwelltime
8065 * x 50us for  echo .
8066 */
8067
8068static int flashpchar(struct airo_info *ai,int byte,int dwelltime) {
 
8069	int echo;
8070	int waittime;
8071
8072	byte |= 0x8000;
8073
8074	if(dwelltime == 0 )
8075		dwelltime = 200;
8076
8077	waittime=dwelltime;
8078
8079	/* Wait for busy bit d15 to go false indicating buffer empty */
8080	while ((IN4500 (ai, SWS0) & 0x8000) && waittime > 0) {
8081		udelay (50);
8082		waittime -= 50;
8083	}
8084
8085	/* timeout for busy clear wait */
8086	if(waittime <= 0 ){
8087		airo_print_info(ai->dev->name, "flash putchar busywait timeout!");
8088		return -EBUSY;
8089	}
8090
8091	/* Port is clear now write byte and wait for it to echo back */
8092	do {
8093		OUT4500(ai,SWS0,byte);
8094		udelay(50);
8095		dwelltime -= 50;
8096		echo = IN4500(ai,SWS1);
8097	} while (dwelltime >= 0 && echo != byte);
8098
8099	OUT4500(ai,SWS1,0);
8100
8101	return (echo == byte) ? 0 : -EIO;
8102}
8103
8104/*
8105 * Get a character from the card matching matchbyte
8106 * Step 3)
8107 */
8108static int flashgchar(struct airo_info *ai,int matchbyte,int dwelltime){
 
8109	int           rchar;
8110	unsigned char rbyte=0;
8111
8112	do {
8113		rchar = IN4500(ai,SWS1);
8114
8115		if(dwelltime && !(0x8000 & rchar)){
8116			dwelltime -= 10;
8117			mdelay(10);
8118			continue;
8119		}
8120		rbyte = 0xff & rchar;
8121
8122		if( (rbyte == matchbyte) && (0x8000 & rchar) ){
8123			OUT4500(ai,SWS1,0);
8124			return 0;
8125		}
8126		if( rbyte == 0x81 || rbyte == 0x82 || rbyte == 0x83 || rbyte == 0x1a || 0xffff == rchar)
8127			break;
8128		OUT4500(ai,SWS1,0);
8129
8130	}while(dwelltime > 0);
8131	return -EIO;
8132}
8133
8134/*
8135 * Transfer 32k of firmware data from user buffer to our buffer and
8136 * send to the card
8137 */
8138
8139static int flashputbuf(struct airo_info *ai){
 
8140	int            nwords;
8141
8142	/* Write stuff */
8143	if (test_bit(FLAG_MPI,&ai->flags))
8144		memcpy_toio(ai->pciaux + 0x8000, ai->flash, FLASHSIZE);
8145	else {
8146		OUT4500(ai,AUXPAGE,0x100);
8147		OUT4500(ai,AUXOFF,0);
8148
8149		for(nwords=0;nwords != FLASHSIZE / 2;nwords++){
8150			OUT4500(ai,AUXDATA,ai->flash[nwords] & 0xffff);
8151		}
8152	}
8153	OUT4500(ai,SWS0,0x8000);
8154
8155	return 0;
8156}
8157
8158/*
8159 *
8160 */
8161static int flashrestart(struct airo_info *ai,struct net_device *dev){
8162	int    i,status;
 
8163
8164	ssleep(1);			/* Added 12/7/00 */
8165	clear_bit (FLAG_FLASHING, &ai->flags);
8166	if (test_bit(FLAG_MPI, &ai->flags)) {
8167		status = mpi_init_descriptors(ai);
8168		if (status != SUCCESS)
8169			return status;
8170	}
8171	status = setup_card(ai, dev->dev_addr, 1);
8172
8173	if (!test_bit(FLAG_MPI,&ai->flags))
8174		for( i = 0; i < MAX_FIDS; i++ ) {
8175			ai->fids[i] = transmit_allocate
8176				( ai, AIRO_DEF_MTU, i >= MAX_FIDS / 2 );
8177		}
8178
8179	ssleep(1);			/* Added 12/7/00 */
8180	return status;
8181}
8182#endif /* CISCO_EXT */
8183
8184/*
8185    This program is free software; you can redistribute it and/or
8186    modify it under the terms of the GNU General Public License
8187    as published by the Free Software Foundation; either version 2
8188    of the License, or (at your option) any later version.
8189
8190    This program is distributed in the hope that it will be useful,
8191    but WITHOUT ANY WARRANTY; without even the implied warranty of
8192    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
8193    GNU General Public License for more details.
8194
8195    In addition:
8196
8197    Redistribution and use in source and binary forms, with or without
8198    modification, are permitted provided that the following conditions
8199    are met:
8200
8201    1. Redistributions of source code must retain the above copyright
8202       notice, this list of conditions and the following disclaimer.
8203    2. Redistributions in binary form must reproduce the above copyright
8204       notice, this list of conditions and the following disclaimer in the
8205       documentation and/or other materials provided with the distribution.
8206    3. The name of the author may not be used to endorse or promote
8207       products derived from this software without specific prior written
8208       permission.
8209
8210    THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
8211    IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
8212    WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
8213    ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT,
8214    INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
8215    (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
8216    SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
8217    HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
8218    STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
8219    IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
8220    POSSIBILITY OF SUCH DAMAGE.
8221*/
8222
8223module_init(airo_init_module);
8224module_exit(airo_cleanup_module);
v5.14.15
   1/*======================================================================
   2
   3    Aironet driver for 4500 and 4800 series cards
   4
   5    This code is released under both the GPL version 2 and BSD licenses.
   6    Either license may be used.  The respective licenses are found at
   7    the end of this file.
   8
   9    This code was developed by Benjamin Reed <breed@users.sourceforge.net>
  10    including portions of which come from the Aironet PC4500
  11    Developer's Reference Manual and used with permission.  Copyright
  12    (C) 1999 Benjamin Reed.  All Rights Reserved.  Permission to use
  13    code in the Developer's manual was granted for this driver by
  14    Aironet.  Major code contributions were received from Javier Achirica
  15    <achirica@users.sourceforge.net> and Jean Tourrilhes <jt@hpl.hp.com>.
  16    Code was also integrated from the Cisco Aironet driver for Linux.
  17    Support for MPI350 cards was added by Fabrice Bellet
  18    <fabrice@bellet.info>.
  19
  20======================================================================*/
  21
  22#include <linux/err.h>
  23#include <linux/init.h>
  24
  25#include <linux/kernel.h>
  26#include <linux/module.h>
  27#include <linux/proc_fs.h>
  28
  29#include <linux/sched.h>
  30#include <linux/ptrace.h>
  31#include <linux/slab.h>
  32#include <linux/string.h>
  33#include <linux/timer.h>
  34#include <linux/interrupt.h>
  35#include <linux/in.h>
  36#include <linux/bitops.h>
  37#include <linux/scatterlist.h>
  38#include <linux/crypto.h>
  39#include <linux/io.h>
  40#include <asm/unaligned.h>
  41
  42#include <linux/netdevice.h>
  43#include <linux/etherdevice.h>
  44#include <linux/skbuff.h>
  45#include <linux/if_arp.h>
  46#include <linux/ioport.h>
  47#include <linux/pci.h>
  48#include <linux/uaccess.h>
  49#include <linux/kthread.h>
  50#include <linux/freezer.h>
  51
  52#include <crypto/aes.h>
  53#include <crypto/skcipher.h>
  54
  55#include <net/cfg80211.h>
  56#include <net/iw_handler.h>
  57
  58#include "airo.h"
  59
  60#define DRV_NAME "airo"
  61
  62#ifdef CONFIG_PCI
  63static const struct pci_device_id card_ids[] = {
  64	{ 0x14b9, 1, PCI_ANY_ID, PCI_ANY_ID, },
  65	{ 0x14b9, 0x4500, PCI_ANY_ID, PCI_ANY_ID },
  66	{ 0x14b9, 0x4800, PCI_ANY_ID, PCI_ANY_ID, },
  67	{ 0x14b9, 0x0340, PCI_ANY_ID, PCI_ANY_ID, },
  68	{ 0x14b9, 0x0350, PCI_ANY_ID, PCI_ANY_ID, },
  69	{ 0x14b9, 0x5000, PCI_ANY_ID, PCI_ANY_ID, },
  70	{ 0x14b9, 0xa504, PCI_ANY_ID, PCI_ANY_ID, },
  71	{ 0, }
  72};
  73MODULE_DEVICE_TABLE(pci, card_ids);
  74
  75static int airo_pci_probe(struct pci_dev *, const struct pci_device_id *);
  76static void airo_pci_remove(struct pci_dev *);
  77static int __maybe_unused airo_pci_suspend(struct device *dev);
  78static int __maybe_unused airo_pci_resume(struct device *dev);
  79
  80static SIMPLE_DEV_PM_OPS(airo_pci_pm_ops,
  81			 airo_pci_suspend,
  82			 airo_pci_resume);
  83
  84static struct pci_driver airo_driver = {
  85	.name      = DRV_NAME,
  86	.id_table  = card_ids,
  87	.probe     = airo_pci_probe,
  88	.remove    = airo_pci_remove,
  89	.driver.pm = &airo_pci_pm_ops,
 
  90};
  91#endif /* CONFIG_PCI */
  92
  93/* Include Wireless Extension definition and check version - Jean II */
  94#include <linux/wireless.h>
  95#define WIRELESS_SPY		/* enable iwspy support */
  96
  97#define CISCO_EXT		/* enable Cisco extensions */
  98#ifdef CISCO_EXT
  99#include <linux/delay.h>
 100#endif
 101
 102/* Hack to do some power saving */
 103#define POWER_ON_DOWN
 104
 105/* As you can see this list is HUGH!
 106   I really don't know what a lot of these counts are about, but they
 107   are all here for completeness.  If the IGNLABEL macro is put in
 108   infront of the label, that statistic will not be included in the list
 109   of statistics in the /proc filesystem */
 110
 111#define IGNLABEL(comment) NULL
 112static const char *statsLabels[] = {
 113	"RxOverrun",
 114	IGNLABEL("RxPlcpCrcErr"),
 115	IGNLABEL("RxPlcpFormatErr"),
 116	IGNLABEL("RxPlcpLengthErr"),
 117	"RxMacCrcErr",
 118	"RxMacCrcOk",
 119	"RxWepErr",
 120	"RxWepOk",
 121	"RetryLong",
 122	"RetryShort",
 123	"MaxRetries",
 124	"NoAck",
 125	"NoCts",
 126	"RxAck",
 127	"RxCts",
 128	"TxAck",
 129	"TxRts",
 130	"TxCts",
 131	"TxMc",
 132	"TxBc",
 133	"TxUcFrags",
 134	"TxUcPackets",
 135	"TxBeacon",
 136	"RxBeacon",
 137	"TxSinColl",
 138	"TxMulColl",
 139	"DefersNo",
 140	"DefersProt",
 141	"DefersEngy",
 142	"DupFram",
 143	"RxFragDisc",
 144	"TxAged",
 145	"RxAged",
 146	"LostSync-MaxRetry",
 147	"LostSync-MissedBeacons",
 148	"LostSync-ArlExceeded",
 149	"LostSync-Deauth",
 150	"LostSync-Disassoced",
 151	"LostSync-TsfTiming",
 152	"HostTxMc",
 153	"HostTxBc",
 154	"HostTxUc",
 155	"HostTxFail",
 156	"HostRxMc",
 157	"HostRxBc",
 158	"HostRxUc",
 159	"HostRxDiscard",
 160	IGNLABEL("HmacTxMc"),
 161	IGNLABEL("HmacTxBc"),
 162	IGNLABEL("HmacTxUc"),
 163	IGNLABEL("HmacTxFail"),
 164	IGNLABEL("HmacRxMc"),
 165	IGNLABEL("HmacRxBc"),
 166	IGNLABEL("HmacRxUc"),
 167	IGNLABEL("HmacRxDiscard"),
 168	IGNLABEL("HmacRxAccepted"),
 169	"SsidMismatch",
 170	"ApMismatch",
 171	"RatesMismatch",
 172	"AuthReject",
 173	"AuthTimeout",
 174	"AssocReject",
 175	"AssocTimeout",
 176	IGNLABEL("ReasonOutsideTable"),
 177	IGNLABEL("ReasonStatus1"),
 178	IGNLABEL("ReasonStatus2"),
 179	IGNLABEL("ReasonStatus3"),
 180	IGNLABEL("ReasonStatus4"),
 181	IGNLABEL("ReasonStatus5"),
 182	IGNLABEL("ReasonStatus6"),
 183	IGNLABEL("ReasonStatus7"),
 184	IGNLABEL("ReasonStatus8"),
 185	IGNLABEL("ReasonStatus9"),
 186	IGNLABEL("ReasonStatus10"),
 187	IGNLABEL("ReasonStatus11"),
 188	IGNLABEL("ReasonStatus12"),
 189	IGNLABEL("ReasonStatus13"),
 190	IGNLABEL("ReasonStatus14"),
 191	IGNLABEL("ReasonStatus15"),
 192	IGNLABEL("ReasonStatus16"),
 193	IGNLABEL("ReasonStatus17"),
 194	IGNLABEL("ReasonStatus18"),
 195	IGNLABEL("ReasonStatus19"),
 196	"RxMan",
 197	"TxMan",
 198	"RxRefresh",
 199	"TxRefresh",
 200	"RxPoll",
 201	"TxPoll",
 202	"HostRetries",
 203	"LostSync-HostReq",
 204	"HostTxBytes",
 205	"HostRxBytes",
 206	"ElapsedUsec",
 207	"ElapsedSec",
 208	"LostSyncBetterAP",
 209	"PrivacyMismatch",
 210	"Jammed",
 211	"DiscRxNotWepped",
 212	"PhyEleMismatch",
 213	(char*)-1 };
 214#ifndef RUN_AT
 215#define RUN_AT(x) (jiffies+(x))
 216#endif
 217
 218
 219/* These variables are for insmod, since it seems that the rates
 220   can only be set in setup_card.  Rates should be a comma separated
 221   (no spaces) list of rates (up to 8). */
 222
 223static int rates[8];
 224static char *ssids[3];
 225
 226static int io[4];
 227static int irq[4];
 228
 229static
 230int maxencrypt /* = 0 */; /* The highest rate that the card can encrypt at.
 231		       0 means no limit.  For old cards this was 4 */
 232
 233static int auto_wep /* = 0 */; /* If set, it tries to figure out the wep mode */
 234static int aux_bap /* = 0 */; /* Checks to see if the aux ports are needed to read
 235		    the bap, needed on some older cards and buses. */
 236static int adhoc;
 237
 238static int probe = 1;
 239
 240static kuid_t proc_kuid;
 241static int proc_uid /* = 0 */;
 242
 243static kgid_t proc_kgid;
 244static int proc_gid /* = 0 */;
 245
 246static int airo_perm = 0555;
 247
 248static int proc_perm = 0644;
 249
 250MODULE_AUTHOR("Benjamin Reed");
 251MODULE_DESCRIPTION("Support for Cisco/Aironet 802.11 wireless ethernet cards.  "
 252		   "Direct support for ISA/PCI/MPI cards and support for PCMCIA when used with airo_cs.");
 253MODULE_LICENSE("Dual BSD/GPL");
 254module_param_hw_array(io, int, ioport, NULL, 0);
 255module_param_hw_array(irq, int, irq, NULL, 0);
 
 256module_param_array(rates, int, NULL, 0);
 257module_param_array(ssids, charp, NULL, 0);
 258module_param(auto_wep, int, 0);
 259MODULE_PARM_DESC(auto_wep,
 260		 "If non-zero, the driver will keep looping through the authentication options until an association is made.  "
 261		 "The value of auto_wep is number of the wep keys to check.  "
 262		 "A value of 2 will try using the key at index 0 and index 1.");
 263module_param(aux_bap, int, 0);
 264MODULE_PARM_DESC(aux_bap,
 265		 "If non-zero, the driver will switch into a mode that seems to work better for older cards with some older buses.  "
 266		 "Before switching it checks that the switch is needed.");
 267module_param(maxencrypt, int, 0);
 268MODULE_PARM_DESC(maxencrypt,
 269		 "The maximum speed that the card can do encryption.  "
 270		 "Units are in 512kbs.  "
 271		 "Zero (default) means there is no limit.  "
 272		 "Older cards used to be limited to 2mbs (4).");
 273module_param(adhoc, int, 0);
 274MODULE_PARM_DESC(adhoc, "If non-zero, the card will start in adhoc mode.");
 275module_param(probe, int, 0);
 276MODULE_PARM_DESC(probe, "If zero, the driver won't start the card.");
 277
 278module_param(proc_uid, int, 0);
 279MODULE_PARM_DESC(proc_uid, "The uid that the /proc files will belong to.");
 280module_param(proc_gid, int, 0);
 281MODULE_PARM_DESC(proc_gid, "The gid that the /proc files will belong to.");
 282module_param(airo_perm, int, 0);
 283MODULE_PARM_DESC(airo_perm, "The permission bits of /proc/[driver/]aironet.");
 284module_param(proc_perm, int, 0);
 285MODULE_PARM_DESC(proc_perm, "The permission bits of the files in /proc");
 286
 287/* This is a kind of sloppy hack to get this information to OUT4500 and
 288   IN4500.  I would be extremely interested in the situation where this
 289   doesn't work though!!! */
 290static int do8bitIO /* = 0 */;
 291
 292/* Return codes */
 293#define SUCCESS 0
 294#define ERROR -1
 295#define NO_PACKET -2
 296
 297/* Commands */
 298#define NOP2		0x0000
 299#define MAC_ENABLE	0x0001
 300#define MAC_DISABLE	0x0002
 301#define CMD_LOSE_SYNC	0x0003 /* Not sure what this does... */
 302#define CMD_SOFTRESET	0x0004
 303#define HOSTSLEEP	0x0005
 304#define CMD_MAGIC_PKT	0x0006
 305#define CMD_SETWAKEMASK	0x0007
 306#define CMD_READCFG	0x0008
 307#define CMD_SETMODE	0x0009
 308#define CMD_ALLOCATETX	0x000a
 309#define CMD_TRANSMIT	0x000b
 310#define CMD_DEALLOCATETX 0x000c
 311#define NOP		0x0010
 312#define CMD_WORKAROUND	0x0011
 313#define CMD_ALLOCATEAUX 0x0020
 314#define CMD_ACCESS	0x0021
 315#define CMD_PCIBAP	0x0022
 316#define CMD_PCIAUX	0x0023
 317#define CMD_ALLOCBUF	0x0028
 318#define CMD_GETTLV	0x0029
 319#define CMD_PUTTLV	0x002a
 320#define CMD_DELTLV	0x002b
 321#define CMD_FINDNEXTTLV	0x002c
 322#define CMD_PSPNODES	0x0030
 323#define CMD_SETCW	0x0031
 324#define CMD_SETPCF	0x0032
 325#define CMD_SETPHYREG	0x003e
 326#define CMD_TXTEST	0x003f
 327#define MAC_ENABLETX	0x0101
 328#define CMD_LISTBSS	0x0103
 329#define CMD_SAVECFG	0x0108
 330#define CMD_ENABLEAUX	0x0111
 331#define CMD_WRITERID	0x0121
 332#define CMD_USEPSPNODES	0x0130
 333#define MAC_ENABLERX	0x0201
 334
 335/* Command errors */
 336#define ERROR_QUALIF 0x00
 337#define ERROR_ILLCMD 0x01
 338#define ERROR_ILLFMT 0x02
 339#define ERROR_INVFID 0x03
 340#define ERROR_INVRID 0x04
 341#define ERROR_LARGE 0x05
 342#define ERROR_NDISABL 0x06
 343#define ERROR_ALLOCBSY 0x07
 344#define ERROR_NORD 0x0B
 345#define ERROR_NOWR 0x0C
 346#define ERROR_INVFIDTX 0x0D
 347#define ERROR_TESTACT 0x0E
 348#define ERROR_TAGNFND 0x12
 349#define ERROR_DECODE 0x20
 350#define ERROR_DESCUNAV 0x21
 351#define ERROR_BADLEN 0x22
 352#define ERROR_MODE 0x80
 353#define ERROR_HOP 0x81
 354#define ERROR_BINTER 0x82
 355#define ERROR_RXMODE 0x83
 356#define ERROR_MACADDR 0x84
 357#define ERROR_RATES 0x85
 358#define ERROR_ORDER 0x86
 359#define ERROR_SCAN 0x87
 360#define ERROR_AUTH 0x88
 361#define ERROR_PSMODE 0x89
 362#define ERROR_RTYPE 0x8A
 363#define ERROR_DIVER 0x8B
 364#define ERROR_SSID 0x8C
 365#define ERROR_APLIST 0x8D
 366#define ERROR_AUTOWAKE 0x8E
 367#define ERROR_LEAP 0x8F
 368
 369/* Registers */
 370#define COMMAND 0x00
 371#define PARAM0 0x02
 372#define PARAM1 0x04
 373#define PARAM2 0x06
 374#define STATUS 0x08
 375#define RESP0 0x0a
 376#define RESP1 0x0c
 377#define RESP2 0x0e
 378#define LINKSTAT 0x10
 379#define SELECT0 0x18
 380#define OFFSET0 0x1c
 381#define RXFID 0x20
 382#define TXALLOCFID 0x22
 383#define TXCOMPLFID 0x24
 384#define DATA0 0x36
 385#define EVSTAT 0x30
 386#define EVINTEN 0x32
 387#define EVACK 0x34
 388#define SWS0 0x28
 389#define SWS1 0x2a
 390#define SWS2 0x2c
 391#define SWS3 0x2e
 392#define AUXPAGE 0x3A
 393#define AUXOFF 0x3C
 394#define AUXDATA 0x3E
 395
 396#define FID_TX 1
 397#define FID_RX 2
 398/* Offset into aux memory for descriptors */
 399#define AUX_OFFSET 0x800
 400/* Size of allocated packets */
 401#define PKTSIZE 1840
 402#define RIDSIZE 2048
 403/* Size of the transmit queue */
 404#define MAXTXQ 64
 405
 406/* BAP selectors */
 407#define BAP0 0 /* Used for receiving packets */
 408#define BAP1 2 /* Used for xmiting packets and working with RIDS */
 409
 410/* Flags */
 411#define COMMAND_BUSY 0x8000
 412
 413#define BAP_BUSY 0x8000
 414#define BAP_ERR 0x4000
 415#define BAP_DONE 0x2000
 416
 417#define PROMISC 0xffff
 418#define NOPROMISC 0x0000
 419
 420#define EV_CMD 0x10
 421#define EV_CLEARCOMMANDBUSY 0x4000
 422#define EV_RX 0x01
 423#define EV_TX 0x02
 424#define EV_TXEXC 0x04
 425#define EV_ALLOC 0x08
 426#define EV_LINK 0x80
 427#define EV_AWAKE 0x100
 428#define EV_TXCPY 0x400
 429#define EV_UNKNOWN 0x800
 430#define EV_MIC 0x1000 /* Message Integrity Check Interrupt */
 431#define EV_AWAKEN 0x2000
 432#define STATUS_INTS (EV_AWAKE|EV_LINK|EV_TXEXC|EV_TX|EV_TXCPY|EV_RX|EV_MIC)
 433
 434#ifdef CHECK_UNKNOWN_INTS
 435#define IGNORE_INTS (EV_CMD | EV_UNKNOWN)
 436#else
 437#define IGNORE_INTS (~STATUS_INTS)
 438#endif
 439
 440/* RID TYPES */
 441#define RID_RW 0x20
 442
 443/* The RIDs */
 444#define RID_CAPABILITIES 0xFF00
 445#define RID_APINFO     0xFF01
 446#define RID_RADIOINFO  0xFF02
 447#define RID_UNKNOWN3   0xFF03
 448#define RID_RSSI       0xFF04
 449#define RID_CONFIG     0xFF10
 450#define RID_SSID       0xFF11
 451#define RID_APLIST     0xFF12
 452#define RID_DRVNAME    0xFF13
 453#define RID_ETHERENCAP 0xFF14
 454#define RID_WEP_TEMP   0xFF15
 455#define RID_WEP_PERM   0xFF16
 456#define RID_MODULATION 0xFF17
 457#define RID_OPTIONS    0xFF18
 458#define RID_ACTUALCONFIG 0xFF20 /*readonly*/
 459#define RID_FACTORYCONFIG 0xFF21
 460#define RID_UNKNOWN22  0xFF22
 461#define RID_LEAPUSERNAME 0xFF23
 462#define RID_LEAPPASSWORD 0xFF24
 463#define RID_STATUS     0xFF50
 464#define RID_BEACON_HST 0xFF51
 465#define RID_BUSY_HST   0xFF52
 466#define RID_RETRIES_HST 0xFF53
 467#define RID_UNKNOWN54  0xFF54
 468#define RID_UNKNOWN55  0xFF55
 469#define RID_UNKNOWN56  0xFF56
 470#define RID_MIC        0xFF57
 471#define RID_STATS16    0xFF60
 472#define RID_STATS16DELTA 0xFF61
 473#define RID_STATS16DELTACLEAR 0xFF62
 474#define RID_STATS      0xFF68
 475#define RID_STATSDELTA 0xFF69
 476#define RID_STATSDELTACLEAR 0xFF6A
 477#define RID_ECHOTEST_RID 0xFF70
 478#define RID_ECHOTEST_RESULTS 0xFF71
 479#define RID_BSSLISTFIRST 0xFF72
 480#define RID_BSSLISTNEXT  0xFF73
 481#define RID_WPA_BSSLISTFIRST 0xFF74
 482#define RID_WPA_BSSLISTNEXT  0xFF75
 483
 484typedef struct {
 485	u16 cmd;
 486	u16 parm0;
 487	u16 parm1;
 488	u16 parm2;
 489} Cmd;
 490
 491typedef struct {
 492	u16 status;
 493	u16 rsp0;
 494	u16 rsp1;
 495	u16 rsp2;
 496} Resp;
 497
 498/*
 499 * Rids and endian-ness:  The Rids will always be in cpu endian, since
 500 * this all the patches from the big-endian guys end up doing that.
 501 * so all rid access should use the read/writeXXXRid routines.
 502 */
 503
 504/* This structure came from an email sent to me from an engineer at
 505   aironet for inclusion into this driver */
 506typedef struct WepKeyRid WepKeyRid;
 507struct WepKeyRid {
 508	__le16 len;
 509	__le16 kindex;
 510	u8 mac[ETH_ALEN];
 511	__le16 klen;
 512	u8 key[16];
 513} __packed;
 514
 515/* These structures are from the Aironet's PC4500 Developers Manual */
 516typedef struct Ssid Ssid;
 517struct Ssid {
 518	__le16 len;
 519	u8 ssid[32];
 520} __packed;
 521
 522typedef struct SsidRid SsidRid;
 523struct SsidRid {
 524	__le16 len;
 525	Ssid ssids[3];
 526} __packed;
 527
 528typedef struct ModulationRid ModulationRid;
 529struct ModulationRid {
 530        __le16 len;
 531        __le16 modulation;
 532#define MOD_DEFAULT cpu_to_le16(0)
 533#define MOD_CCK cpu_to_le16(1)
 534#define MOD_MOK cpu_to_le16(2)
 535} __packed;
 536
 537typedef struct ConfigRid ConfigRid;
 538struct ConfigRid {
 539	__le16 len; /* sizeof(ConfigRid) */
 540	__le16 opmode; /* operating mode */
 541#define MODE_STA_IBSS cpu_to_le16(0)
 542#define MODE_STA_ESS cpu_to_le16(1)
 543#define MODE_AP cpu_to_le16(2)
 544#define MODE_AP_RPTR cpu_to_le16(3)
 545#define MODE_CFG_MASK cpu_to_le16(0xff)
 546#define MODE_ETHERNET_HOST cpu_to_le16(0<<8) /* rx payloads converted */
 547#define MODE_LLC_HOST cpu_to_le16(1<<8) /* rx payloads left as is */
 548#define MODE_AIRONET_EXTEND cpu_to_le16(1<<9) /* enable Aironet extenstions */
 549#define MODE_AP_INTERFACE cpu_to_le16(1<<10) /* enable ap interface extensions */
 550#define MODE_ANTENNA_ALIGN cpu_to_le16(1<<11) /* enable antenna alignment */
 551#define MODE_ETHER_LLC cpu_to_le16(1<<12) /* enable ethernet LLC */
 552#define MODE_LEAF_NODE cpu_to_le16(1<<13) /* enable leaf node bridge */
 553#define MODE_CF_POLLABLE cpu_to_le16(1<<14) /* enable CF pollable */
 554#define MODE_MIC cpu_to_le16(1<<15) /* enable MIC */
 555	__le16 rmode; /* receive mode */
 556#define RXMODE_BC_MC_ADDR cpu_to_le16(0)
 557#define RXMODE_BC_ADDR cpu_to_le16(1) /* ignore multicasts */
 558#define RXMODE_ADDR cpu_to_le16(2) /* ignore multicast and broadcast */
 559#define RXMODE_RFMON cpu_to_le16(3) /* wireless monitor mode */
 560#define RXMODE_RFMON_ANYBSS cpu_to_le16(4)
 561#define RXMODE_LANMON cpu_to_le16(5) /* lan style monitor -- data packets only */
 562#define RXMODE_MASK cpu_to_le16(255)
 563#define RXMODE_DISABLE_802_3_HEADER cpu_to_le16(1<<8) /* disables 802.3 header on rx */
 564#define RXMODE_FULL_MASK (RXMODE_MASK | RXMODE_DISABLE_802_3_HEADER)
 565#define RXMODE_NORMALIZED_RSSI cpu_to_le16(1<<9) /* return normalized RSSI */
 566	__le16 fragThresh;
 567	__le16 rtsThres;
 568	u8 macAddr[ETH_ALEN];
 569	u8 rates[8];
 570	__le16 shortRetryLimit;
 571	__le16 longRetryLimit;
 572	__le16 txLifetime; /* in kusec */
 573	__le16 rxLifetime; /* in kusec */
 574	__le16 stationary;
 575	__le16 ordering;
 576	__le16 u16deviceType; /* for overriding device type */
 577	__le16 cfpRate;
 578	__le16 cfpDuration;
 579	__le16 _reserved1[3];
 580	/*---------- Scanning/Associating ----------*/
 581	__le16 scanMode;
 582#define SCANMODE_ACTIVE cpu_to_le16(0)
 583#define SCANMODE_PASSIVE cpu_to_le16(1)
 584#define SCANMODE_AIROSCAN cpu_to_le16(2)
 585	__le16 probeDelay; /* in kusec */
 586	__le16 probeEnergyTimeout; /* in kusec */
 587        __le16 probeResponseTimeout;
 588	__le16 beaconListenTimeout;
 589	__le16 joinNetTimeout;
 590	__le16 authTimeout;
 591	__le16 authType;
 592#define AUTH_OPEN cpu_to_le16(0x1)
 593#define AUTH_ENCRYPT cpu_to_le16(0x101)
 594#define AUTH_SHAREDKEY cpu_to_le16(0x102)
 595#define AUTH_ALLOW_UNENCRYPTED cpu_to_le16(0x200)
 596	__le16 associationTimeout;
 597	__le16 specifiedApTimeout;
 598	__le16 offlineScanInterval;
 599	__le16 offlineScanDuration;
 600	__le16 linkLossDelay;
 601	__le16 maxBeaconLostTime;
 602	__le16 refreshInterval;
 603#define DISABLE_REFRESH cpu_to_le16(0xFFFF)
 604	__le16 _reserved1a[1];
 605	/*---------- Power save operation ----------*/
 606	__le16 powerSaveMode;
 607#define POWERSAVE_CAM cpu_to_le16(0)
 608#define POWERSAVE_PSP cpu_to_le16(1)
 609#define POWERSAVE_PSPCAM cpu_to_le16(2)
 610	__le16 sleepForDtims;
 611	__le16 listenInterval;
 612	__le16 fastListenInterval;
 613	__le16 listenDecay;
 614	__le16 fastListenDelay;
 615	__le16 _reserved2[2];
 616	/*---------- Ap/Ibss config items ----------*/
 617	__le16 beaconPeriod;
 618	__le16 atimDuration;
 619	__le16 hopPeriod;
 620	__le16 channelSet;
 621	__le16 channel;
 622	__le16 dtimPeriod;
 623	__le16 bridgeDistance;
 624	__le16 radioID;
 625	/*---------- Radio configuration ----------*/
 626	__le16 radioType;
 627#define RADIOTYPE_DEFAULT cpu_to_le16(0)
 628#define RADIOTYPE_802_11 cpu_to_le16(1)
 629#define RADIOTYPE_LEGACY cpu_to_le16(2)
 630	u8 rxDiversity;
 631	u8 txDiversity;
 632	__le16 txPower;
 633#define TXPOWER_DEFAULT 0
 634	__le16 rssiThreshold;
 635#define RSSI_DEFAULT 0
 636        __le16 modulation;
 637#define PREAMBLE_AUTO cpu_to_le16(0)
 638#define PREAMBLE_LONG cpu_to_le16(1)
 639#define PREAMBLE_SHORT cpu_to_le16(2)
 640	__le16 preamble;
 641	__le16 homeProduct;
 642	__le16 radioSpecific;
 643	/*---------- Aironet Extensions ----------*/
 644	u8 nodeName[16];
 645	__le16 arlThreshold;
 646	__le16 arlDecay;
 647	__le16 arlDelay;
 648	__le16 _reserved4[1];
 649	/*---------- Aironet Extensions ----------*/
 650	u8 magicAction;
 651#define MAGIC_ACTION_STSCHG 1
 652#define MAGIC_ACTION_RESUME 2
 653#define MAGIC_IGNORE_MCAST (1<<8)
 654#define MAGIC_IGNORE_BCAST (1<<9)
 655#define MAGIC_SWITCH_TO_PSP (0<<10)
 656#define MAGIC_STAY_IN_CAM (1<<10)
 657	u8 magicControl;
 658	__le16 autoWake;
 659} __packed;
 660
 661typedef struct StatusRid StatusRid;
 662struct StatusRid {
 663	__le16 len;
 664	u8 mac[ETH_ALEN];
 665	__le16 mode;
 666	__le16 errorCode;
 667	__le16 sigQuality;
 668	__le16 SSIDlen;
 669	char SSID[32];
 670	char apName[16];
 671	u8 bssid[4][ETH_ALEN];
 672	__le16 beaconPeriod;
 673	__le16 dimPeriod;
 674	__le16 atimDuration;
 675	__le16 hopPeriod;
 676	__le16 channelSet;
 677	__le16 channel;
 678	__le16 hopsToBackbone;
 679	__le16 apTotalLoad;
 680	__le16 generatedLoad;
 681	__le16 accumulatedArl;
 682	__le16 signalQuality;
 683	__le16 currentXmitRate;
 684	__le16 apDevExtensions;
 685	__le16 normalizedSignalStrength;
 686	__le16 shortPreamble;
 687	u8 apIP[4];
 688	u8 noisePercent; /* Noise percent in last second */
 689	u8 noisedBm; /* Noise dBm in last second */
 690	u8 noiseAvePercent; /* Noise percent in last minute */
 691	u8 noiseAvedBm; /* Noise dBm in last minute */
 692	u8 noiseMaxPercent; /* Highest noise percent in last minute */
 693	u8 noiseMaxdBm; /* Highest noise dbm in last minute */
 694	__le16 load;
 695	u8 carrier[4];
 696	__le16 assocStatus;
 697#define STAT_NOPACKETS 0
 698#define STAT_NOCARRIERSET 10
 699#define STAT_GOTCARRIERSET 11
 700#define STAT_WRONGSSID 20
 701#define STAT_BADCHANNEL 25
 702#define STAT_BADBITRATES 30
 703#define STAT_BADPRIVACY 35
 704#define STAT_APFOUND 40
 705#define STAT_APREJECTED 50
 706#define STAT_AUTHENTICATING 60
 707#define STAT_DEAUTHENTICATED 61
 708#define STAT_AUTHTIMEOUT 62
 709#define STAT_ASSOCIATING 70
 710#define STAT_DEASSOCIATED 71
 711#define STAT_ASSOCTIMEOUT 72
 712#define STAT_NOTAIROAP 73
 713#define STAT_ASSOCIATED 80
 714#define STAT_LEAPING 90
 715#define STAT_LEAPFAILED 91
 716#define STAT_LEAPTIMEDOUT 92
 717#define STAT_LEAPCOMPLETE 93
 718} __packed;
 719
 720typedef struct StatsRid StatsRid;
 721struct StatsRid {
 722	__le16 len;
 723	__le16 spacer;
 724	__le32 vals[100];
 725} __packed;
 726
 727typedef struct APListRid APListRid;
 728struct APListRid {
 729	__le16 len;
 730	u8 ap[4][ETH_ALEN];
 731} __packed;
 732
 733typedef struct CapabilityRid CapabilityRid;
 734struct CapabilityRid {
 735	__le16 len;
 736	char oui[3];
 737	char zero;
 738	__le16 prodNum;
 739	char manName[32];
 740	char prodName[16];
 741	char prodVer[8];
 742	char factoryAddr[ETH_ALEN];
 743	char aironetAddr[ETH_ALEN];
 744	__le16 radioType;
 745	__le16 country;
 746	char callid[ETH_ALEN];
 747	char supportedRates[8];
 748	char rxDiversity;
 749	char txDiversity;
 750	__le16 txPowerLevels[8];
 751	__le16 hardVer;
 752	__le16 hardCap;
 753	__le16 tempRange;
 754	__le16 softVer;
 755	__le16 softSubVer;
 756	__le16 interfaceVer;
 757	__le16 softCap;
 758	__le16 bootBlockVer;
 759	__le16 requiredHard;
 760	__le16 extSoftCap;
 761} __packed;
 762
 763/* Only present on firmware >= 5.30.17 */
 764typedef struct BSSListRidExtra BSSListRidExtra;
 765struct BSSListRidExtra {
 766  __le16 unknown[4];
 767  u8 fixed[12]; /* WLAN management frame */
 768  u8 iep[624];
 769} __packed;
 770
 771typedef struct BSSListRid BSSListRid;
 772struct BSSListRid {
 773  __le16 len;
 774  __le16 index; /* First is 0 and 0xffff means end of list */
 775#define RADIO_FH 1 /* Frequency hopping radio type */
 776#define RADIO_DS 2 /* Direct sequence radio type */
 777#define RADIO_TMA 4 /* Proprietary radio used in old cards (2500) */
 778  __le16 radioType;
 779  u8 bssid[ETH_ALEN]; /* Mac address of the BSS */
 780  u8 zero;
 781  u8 ssidLen;
 782  u8 ssid[32];
 783  __le16 dBm;
 784#define CAP_ESS cpu_to_le16(1<<0)
 785#define CAP_IBSS cpu_to_le16(1<<1)
 786#define CAP_PRIVACY cpu_to_le16(1<<4)
 787#define CAP_SHORTHDR cpu_to_le16(1<<5)
 788  __le16 cap;
 789  __le16 beaconInterval;
 790  u8 rates[8]; /* Same as rates for config rid */
 791  struct { /* For frequency hopping only */
 792    __le16 dwell;
 793    u8 hopSet;
 794    u8 hopPattern;
 795    u8 hopIndex;
 796    u8 fill;
 797  } fh;
 798  __le16 dsChannel;
 799  __le16 atimWindow;
 800
 801  /* Only present on firmware >= 5.30.17 */
 802  BSSListRidExtra extra;
 803} __packed;
 804
 805typedef struct {
 806  BSSListRid bss;
 807  struct list_head list;
 808} BSSListElement;
 809
 810typedef struct tdsRssiEntry tdsRssiEntry;
 811struct tdsRssiEntry {
 812  u8 rssipct;
 813  u8 rssidBm;
 814} __packed;
 815
 816typedef struct tdsRssiRid tdsRssiRid;
 817struct tdsRssiRid {
 818  u16 len;
 819  tdsRssiEntry x[256];
 820} __packed;
 821
 822typedef struct MICRid MICRid;
 823struct MICRid {
 824	__le16 len;
 825	__le16 state;
 826	__le16 multicastValid;
 827	u8  multicast[16];
 828	__le16 unicastValid;
 829	u8  unicast[16];
 830} __packed;
 831
 832typedef struct MICBuffer MICBuffer;
 833struct MICBuffer {
 834	__be16 typelen;
 835
 836	union {
 837	    u8 snap[8];
 838	    struct {
 839		u8 dsap;
 840		u8 ssap;
 841		u8 control;
 842		u8 orgcode[3];
 843		u8 fieldtype[2];
 844	    } llc;
 845	} u;
 846	__be32 mic;
 847	__be32 seq;
 848} __packed;
 849
 850typedef struct {
 851	u8 da[ETH_ALEN];
 852	u8 sa[ETH_ALEN];
 853} etherHead;
 854
 855#define TXCTL_TXOK (1<<1) /* report if tx is ok */
 856#define TXCTL_TXEX (1<<2) /* report if tx fails */
 857#define TXCTL_802_3 (0<<3) /* 802.3 packet */
 858#define TXCTL_802_11 (1<<3) /* 802.11 mac packet */
 859#define TXCTL_ETHERNET (0<<4) /* payload has ethertype */
 860#define TXCTL_LLC (1<<4) /* payload is llc */
 861#define TXCTL_RELEASE (0<<5) /* release after completion */
 862#define TXCTL_NORELEASE (1<<5) /* on completion returns to host */
 863
 864#define BUSY_FID 0x10000
 865
 866#ifdef CISCO_EXT
 867#define AIROMAGIC	0xa55a
 868/* Warning : SIOCDEVPRIVATE may disapear during 2.5.X - Jean II */
 869#ifdef SIOCIWFIRSTPRIV
 870#ifdef SIOCDEVPRIVATE
 871#define AIROOLDIOCTL	SIOCDEVPRIVATE
 872#define AIROOLDIDIFC 	AIROOLDIOCTL + 1
 873#endif /* SIOCDEVPRIVATE */
 874#else /* SIOCIWFIRSTPRIV */
 875#define SIOCIWFIRSTPRIV SIOCDEVPRIVATE
 876#endif /* SIOCIWFIRSTPRIV */
 877/* This may be wrong. When using the new SIOCIWFIRSTPRIV range, we probably
 878 * should use only "GET" ioctls (last bit set to 1). "SET" ioctls are root
 879 * only and don't return the modified struct ifreq to the application which
 880 * is usually a problem. - Jean II */
 881#define AIROIOCTL	SIOCIWFIRSTPRIV
 882#define AIROIDIFC 	AIROIOCTL + 1
 883
 884/* Ioctl constants to be used in airo_ioctl.command */
 885
 886#define	AIROGCAP  		0	// Capability rid
 887#define AIROGCFG		1       // USED A LOT
 888#define AIROGSLIST		2	// System ID list
 889#define AIROGVLIST		3       // List of specified AP's
 890#define AIROGDRVNAM		4	//  NOTUSED
 891#define AIROGEHTENC		5	// NOTUSED
 892#define AIROGWEPKTMP		6
 893#define AIROGWEPKNV		7
 894#define AIROGSTAT		8
 895#define AIROGSTATSC32		9
 896#define AIROGSTATSD32		10
 897#define AIROGMICRID		11
 898#define AIROGMICSTATS		12
 899#define AIROGFLAGS		13
 900#define AIROGID			14
 901#define AIRORRID		15
 902#define AIRORSWVERSION		17
 903
 904/* Leave gap of 40 commands after AIROGSTATSD32 for future */
 905
 906#define AIROPCAP               	AIROGSTATSD32 + 40
 907#define AIROPVLIST              AIROPCAP      + 1
 908#define AIROPSLIST		AIROPVLIST    + 1
 909#define AIROPCFG		AIROPSLIST    + 1
 910#define AIROPSIDS		AIROPCFG      + 1
 911#define AIROPAPLIST		AIROPSIDS     + 1
 912#define AIROPMACON		AIROPAPLIST   + 1	/* Enable mac  */
 913#define AIROPMACOFF		AIROPMACON    + 1 	/* Disable mac */
 914#define AIROPSTCLR		AIROPMACOFF   + 1
 915#define AIROPWEPKEY		AIROPSTCLR    + 1
 916#define AIROPWEPKEYNV		AIROPWEPKEY   + 1
 917#define AIROPLEAPPWD            AIROPWEPKEYNV + 1
 918#define AIROPLEAPUSR            AIROPLEAPPWD  + 1
 919
 920/* Flash codes */
 921
 922#define AIROFLSHRST	       AIROPWEPKEYNV  + 40
 923#define AIROFLSHGCHR           AIROFLSHRST    + 1
 924#define AIROFLSHSTFL           AIROFLSHGCHR   + 1
 925#define AIROFLSHPCHR           AIROFLSHSTFL   + 1
 926#define AIROFLPUTBUF           AIROFLSHPCHR   + 1
 927#define AIRORESTART            AIROFLPUTBUF   + 1
 928
 929#define FLASHSIZE	32768
 930#define AUXMEMSIZE	(256 * 1024)
 931
 932typedef struct aironet_ioctl {
 933	unsigned short command;		// What to do
 934	unsigned short len;		// Len of data
 935	unsigned short ridnum;		// rid number
 936	unsigned char __user *data;	// d-data
 937} aironet_ioctl;
 938
 939static const char swversion[] = "2.1";
 940#endif /* CISCO_EXT */
 941
 942#define NUM_MODULES       2
 943#define MIC_MSGLEN_MAX    2400
 944#define EMMH32_MSGLEN_MAX MIC_MSGLEN_MAX
 945#define AIRO_DEF_MTU      2312
 946
 947typedef struct {
 948	u32   size;            // size
 949	u8    enabled;         // MIC enabled or not
 950	u32   rxSuccess;       // successful packets received
 951	u32   rxIncorrectMIC;  // pkts dropped due to incorrect MIC comparison
 952	u32   rxNotMICed;      // pkts dropped due to not being MIC'd
 953	u32   rxMICPlummed;    // pkts dropped due to not having a MIC plummed
 954	u32   rxWrongSequence; // pkts dropped due to sequence number violation
 955	u32   reserve[32];
 956} mic_statistics;
 957
 958typedef struct {
 959	__be32 coeff[((EMMH32_MSGLEN_MAX)+3)>>2];
 960	u64 accum;	// accumulated mic, reduced to u32 in final()
 961	int position;	// current position (byte offset) in message
 962	union {
 963		u8  d8[4];
 964		__be32 d32;
 965	} part;	// saves partial message word across update() calls
 966} emmh32_context;
 967
 968typedef struct {
 969	emmh32_context seed;	    // Context - the seed
 970	u32		 rx;	    // Received sequence number
 971	u32		 tx;	    // Tx sequence number
 972	u32		 window;    // Start of window
 973	u8		 valid;	    // Flag to say if context is valid or not
 974	u8		 key[16];
 975} miccntx;
 976
 977typedef struct {
 978	miccntx mCtx;		// Multicast context
 979	miccntx uCtx;		// Unicast context
 980} mic_module;
 981
 982typedef struct {
 983	unsigned int  rid: 16;
 984	unsigned int  len: 15;
 985	unsigned int  valid: 1;
 986	dma_addr_t host_addr;
 987} Rid;
 988
 989typedef struct {
 990	unsigned int  offset: 15;
 991	unsigned int  eoc: 1;
 992	unsigned int  len: 15;
 993	unsigned int  valid: 1;
 994	dma_addr_t host_addr;
 995} TxFid;
 996
 997struct rx_hdr {
 998	__le16 status, len;
 999	u8 rssi[2];
1000	u8 rate;
1001	u8 freq;
1002	__le16 tmp[4];
1003} __packed;
1004
1005typedef struct {
1006	unsigned int  ctl: 15;
1007	unsigned int  rdy: 1;
1008	unsigned int  len: 15;
1009	unsigned int  valid: 1;
1010	dma_addr_t host_addr;
1011} RxFid;
1012
1013/*
1014 * Host receive descriptor
1015 */
1016typedef struct {
1017	unsigned char __iomem *card_ram_off; /* offset into card memory of the
1018						desc */
1019	RxFid         rx_desc;		     /* card receive descriptor */
1020	char          *virtual_host_addr;    /* virtual address of host receive
1021					        buffer */
1022	int           pending;
1023} HostRxDesc;
1024
1025/*
1026 * Host transmit descriptor
1027 */
1028typedef struct {
1029	unsigned char __iomem *card_ram_off;	     /* offset into card memory of the
1030						desc */
1031	TxFid         tx_desc;		     /* card transmit descriptor */
1032	char          *virtual_host_addr;    /* virtual address of host receive
1033					        buffer */
1034	int           pending;
1035} HostTxDesc;
1036
1037/*
1038 * Host RID descriptor
1039 */
1040typedef struct {
1041	unsigned char __iomem *card_ram_off;      /* offset into card memory of the
1042					     descriptor */
1043	Rid           rid_desc;		  /* card RID descriptor */
1044	char          *virtual_host_addr; /* virtual address of host receive
1045					     buffer */
1046} HostRidDesc;
1047
1048typedef struct {
1049	u16 sw0;
1050	u16 sw1;
1051	u16 status;
1052	u16 len;
1053#define HOST_SET (1 << 0)
1054#define HOST_INT_TX (1 << 1) /* Interrupt on successful TX */
1055#define HOST_INT_TXERR (1 << 2) /* Interrupt on unseccessful TX */
1056#define HOST_LCC_PAYLOAD (1 << 4) /* LLC payload, 0 = Ethertype */
1057#define HOST_DONT_RLSE (1 << 5) /* Don't release buffer when done */
1058#define HOST_DONT_RETRY (1 << 6) /* Don't retry trasmit */
1059#define HOST_CLR_AID (1 << 7) /* clear AID failure */
1060#define HOST_RTS (1 << 9) /* Force RTS use */
1061#define HOST_SHORT (1 << 10) /* Do short preamble */
1062	u16 ctl;
1063	u16 aid;
1064	u16 retries;
1065	u16 fill;
1066} TxCtlHdr;
1067
1068typedef struct {
1069        u16 ctl;
1070        u16 duration;
1071        char addr1[6];
1072        char addr2[6];
1073        char addr3[6];
1074        u16 seq;
1075        char addr4[6];
1076} WifiHdr;
1077
1078
1079typedef struct {
1080	TxCtlHdr ctlhdr;
1081	u16 fill1;
1082	u16 fill2;
1083	WifiHdr wifihdr;
1084	u16 gaplen;
1085	u16 status;
1086} WifiCtlHdr;
1087
1088static WifiCtlHdr wifictlhdr8023 = {
1089	.ctlhdr = {
1090		.ctl	= HOST_DONT_RLSE,
1091	}
1092};
1093
1094// A few details needed for WEP (Wireless Equivalent Privacy)
1095#define MAX_KEY_SIZE 13			// 128 (?) bits
1096#define MIN_KEY_SIZE  5			// 40 bits RC4 - WEP
1097typedef struct wep_key_t {
1098	u16	len;
1099	u8	key[16];	/* 40-bit and 104-bit keys */
1100} wep_key_t;
1101
1102/* List of Wireless Handlers (new API) */
1103static const struct iw_handler_def	airo_handler_def;
1104
1105static const char version[] = "airo.c 0.6 (Ben Reed & Javier Achirica)";
1106
1107struct airo_info;
1108
1109static int get_dec_u16(char *buffer, int *start, int limit);
1110static void OUT4500(struct airo_info *, u16 reg, u16 value);
1111static unsigned short IN4500(struct airo_info *, u16 reg);
1112static u16 setup_card(struct airo_info*, u8 *mac, int lock);
1113static int enable_MAC(struct airo_info *ai, int lock);
1114static void disable_MAC(struct airo_info *ai, int lock);
1115static void enable_interrupts(struct airo_info*);
1116static void disable_interrupts(struct airo_info*);
1117static u16 issuecommand(struct airo_info*, Cmd *pCmd, Resp *pRsp,
1118			bool may_sleep);
1119static int bap_setup(struct airo_info*, u16 rid, u16 offset, int whichbap);
1120static int aux_bap_read(struct airo_info*, __le16 *pu16Dst, int bytelen,
1121			int whichbap);
1122static int fast_bap_read(struct airo_info*, __le16 *pu16Dst, int bytelen,
1123			 int whichbap);
1124static int bap_write(struct airo_info*, const __le16 *pu16Src, int bytelen,
1125		     int whichbap);
1126static int PC4500_accessrid(struct airo_info*, u16 rid, u16 accmd);
1127static int PC4500_readrid(struct airo_info*, u16 rid, void *pBuf, int len, int lock);
1128static int PC4500_writerid(struct airo_info*, u16 rid, const void
1129			   *pBuf, int len, int lock);
1130static int do_writerid(struct airo_info*, u16 rid, const void *rid_data,
1131			int len, int dummy);
1132static u16 transmit_allocate(struct airo_info*, int lenPayload, int raw);
1133static int transmit_802_3_packet(struct airo_info*, int len, char *pPacket,
1134				 bool may_sleep);
1135static int transmit_802_11_packet(struct airo_info*, int len, char *pPacket,
1136				  bool may_sleep);
1137
1138static int mpi_send_packet(struct net_device *dev);
1139static void mpi_unmap_card(struct pci_dev *pci);
1140static void mpi_receive_802_3(struct airo_info *ai);
1141static void mpi_receive_802_11(struct airo_info *ai);
1142static int waitbusy(struct airo_info *ai);
1143
1144static irqreturn_t airo_interrupt(int irq, void* dev_id);
1145static int airo_thread(void *data);
1146static void timer_func(struct net_device *dev);
1147static int airo_ioctl(struct net_device *dev, struct ifreq *rq, int cmd);
1148static struct iw_statistics *airo_get_wireless_stats(struct net_device *dev);
 
1149#ifdef CISCO_EXT
1150static int readrids(struct net_device *dev, aironet_ioctl *comp);
1151static int writerids(struct net_device *dev, aironet_ioctl *comp);
1152static int flashcard(struct net_device *dev, aironet_ioctl *comp);
1153#endif /* CISCO_EXT */
1154static void micinit(struct airo_info *ai);
1155static int micsetup(struct airo_info *ai);
1156static int encapsulate(struct airo_info *ai, etherHead *pPacket, MICBuffer *buffer, int len);
1157static int decapsulate(struct airo_info *ai, MICBuffer *mic, etherHead *pPacket, u16 payLen);
1158
1159static u8 airo_rssi_to_dbm(tdsRssiEntry *rssi_rid, u8 rssi);
1160static u8 airo_dbm_to_pct(tdsRssiEntry *rssi_rid, u8 dbm);
1161
1162static void airo_networks_free(struct airo_info *ai);
1163
1164struct airo_info {
1165	struct net_device             *dev;
1166	struct list_head              dev_list;
1167	/* Note, we can have MAX_FIDS outstanding.  FIDs are 16-bits, so we
1168	   use the high bit to mark whether it is in use. */
1169#define MAX_FIDS 6
1170#define MPI_MAX_FIDS 1
1171	u32                           fids[MAX_FIDS];
1172	ConfigRid config;
1173	char keyindex; // Used with auto wep
1174	char defindex; // Used with auto wep
1175	struct proc_dir_entry *proc_entry;
1176        spinlock_t aux_lock;
1177#define FLAG_RADIO_OFF	0	/* User disabling of MAC */
1178#define FLAG_RADIO_DOWN	1	/* ifup/ifdown disabling of MAC */
1179#define FLAG_RADIO_MASK 0x03
1180#define FLAG_ENABLED	2
1181#define FLAG_ADHOC	3	/* Needed by MIC */
1182#define FLAG_MIC_CAPABLE 4
1183#define FLAG_UPDATE_MULTI 5
1184#define FLAG_UPDATE_UNI 6
1185#define FLAG_802_11	7
1186#define FLAG_PROMISC	8	/* IFF_PROMISC 0x100 - include/linux/if.h */
1187#define FLAG_PENDING_XMIT 9
1188#define FLAG_PENDING_XMIT11 10
1189#define FLAG_MPI	11
1190#define FLAG_REGISTERED	12
1191#define FLAG_COMMIT	13
1192#define FLAG_RESET	14
1193#define FLAG_FLASHING	15
1194#define FLAG_WPA_CAPABLE	16
1195	unsigned long flags;
1196#define JOB_DIE	0
1197#define JOB_XMIT	1
1198#define JOB_XMIT11	2
1199#define JOB_STATS	3
1200#define JOB_PROMISC	4
1201#define JOB_MIC	5
1202#define JOB_EVENT	6
1203#define JOB_AUTOWEP	7
 
1204#define JOB_SCAN_RESULTS  9
1205	unsigned long jobs;
1206	int (*bap_read)(struct airo_info*, __le16 *pu16Dst, int bytelen,
1207			int whichbap);
1208	unsigned short *flash;
1209	tdsRssiEntry *rssi;
1210	struct task_struct *list_bss_task;
1211	struct task_struct *airo_thread_task;
1212	struct semaphore sem;
1213	wait_queue_head_t thr_wait;
1214	unsigned long expires;
1215	struct {
1216		struct sk_buff *skb;
1217		int fid;
1218	} xmit, xmit11;
1219	struct net_device *wifidev;
1220	struct iw_statistics	wstats;		// wireless stats
1221	unsigned long		scan_timeout;	/* Time scan should be read */
1222	struct iw_spy_data	spy_data;
1223	struct iw_public_data	wireless_data;
1224	/* MIC stuff */
1225	struct crypto_sync_skcipher	*tfm;
1226	mic_module		mod[2];
1227	mic_statistics		micstats;
1228	HostRxDesc rxfids[MPI_MAX_FIDS]; // rx/tx/config MPI350 descriptors
1229	HostTxDesc txfids[MPI_MAX_FIDS];
1230	HostRidDesc config_desc;
1231	unsigned long ridbus; // phys addr of config_desc
1232	struct sk_buff_head txq;// tx queue used by mpi350 code
1233	struct pci_dev          *pci;
1234	unsigned char		__iomem *pcimem;
1235	unsigned char		__iomem *pciaux;
1236	unsigned char		*shared;
1237	dma_addr_t		shared_dma;
1238	pm_message_t		power;
1239	SsidRid			*SSID;
1240	APListRid		APList;
1241#define	PCI_SHARED_LEN		2*MPI_MAX_FIDS*PKTSIZE+RIDSIZE
1242	char			proc_name[IFNAMSIZ];
1243
1244	int			wep_capable;
1245	int			max_wep_idx;
1246	int			last_auth;
1247
1248	/* WPA-related stuff */
1249	unsigned int bssListFirst;
1250	unsigned int bssListNext;
1251	unsigned int bssListRidLen;
1252
1253	struct list_head network_list;
1254	struct list_head network_free_list;
1255	BSSListElement *networks;
1256};
1257
1258static inline int bap_read(struct airo_info *ai, __le16 *pu16Dst, int bytelen,
1259			   int whichbap)
1260{
1261	return ai->bap_read(ai, pu16Dst, bytelen, whichbap);
1262}
1263
1264static int setup_proc_entry(struct net_device *dev,
1265			     struct airo_info *apriv);
1266static int takedown_proc_entry(struct net_device *dev,
1267				struct airo_info *apriv);
1268
1269static int cmdreset(struct airo_info *ai);
1270static int setflashmode(struct airo_info *ai);
1271static int flashgchar(struct airo_info *ai, int matchbyte, int dwelltime);
1272static int flashputbuf(struct airo_info *ai);
1273static int flashrestart(struct airo_info *ai, struct net_device *dev);
1274
1275#define airo_print(type, name, fmt, args...) \
1276	printk(type DRV_NAME "(%s): " fmt "\n", name, ##args)
1277
1278#define airo_print_info(name, fmt, args...) \
1279	airo_print(KERN_INFO, name, fmt, ##args)
1280
1281#define airo_print_dbg(name, fmt, args...) \
1282	airo_print(KERN_DEBUG, name, fmt, ##args)
1283
1284#define airo_print_warn(name, fmt, args...) \
1285	airo_print(KERN_WARNING, name, fmt, ##args)
1286
1287#define airo_print_err(name, fmt, args...) \
1288	airo_print(KERN_ERR, name, fmt, ##args)
1289
1290#define AIRO_FLASH(dev) (((struct airo_info *)dev->ml_priv)->flash)
1291
1292/***********************************************************************
1293 *                              MIC ROUTINES                           *
1294 ***********************************************************************
1295 */
1296
1297static int RxSeqValid(struct airo_info *ai, miccntx *context, int mcast, u32 micSeq);
1298static void MoveWindow(miccntx *context, u32 micSeq);
1299static void emmh32_setseed(emmh32_context *context, u8 *pkey, int keylen,
1300			   struct crypto_sync_skcipher *tfm);
1301static void emmh32_init(emmh32_context *context);
1302static void emmh32_update(emmh32_context *context, u8 *pOctets, int len);
1303static void emmh32_final(emmh32_context *context, u8 digest[4]);
1304static int flashpchar(struct airo_info *ai, int byte, int dwelltime);
1305
1306static void age_mic_context(miccntx *cur, miccntx *old, u8 *key, int key_len,
1307			    struct crypto_sync_skcipher *tfm)
1308{
1309	/* If the current MIC context is valid and its key is the same as
1310	 * the MIC register, there's nothing to do.
1311	 */
1312	if (cur->valid && (memcmp(cur->key, key, key_len) == 0))
1313		return;
1314
1315	/* Age current mic Context */
1316	memcpy(old, cur, sizeof(*cur));
1317
1318	/* Initialize new context */
1319	memcpy(cur->key, key, key_len);
1320	cur->window  = 33; /* Window always points to the middle */
1321	cur->rx      = 0;  /* Rx Sequence numbers */
1322	cur->tx      = 0;  /* Tx sequence numbers */
1323	cur->valid   = 1;  /* Key is now valid */
1324
1325	/* Give key to mic seed */
1326	emmh32_setseed(&cur->seed, key, key_len, tfm);
1327}
1328
1329/* micinit - Initialize mic seed */
1330
1331static void micinit(struct airo_info *ai)
1332{
1333	MICRid mic_rid;
1334
1335	clear_bit(JOB_MIC, &ai->jobs);
1336	PC4500_readrid(ai, RID_MIC, &mic_rid, sizeof(mic_rid), 0);
1337	up(&ai->sem);
1338
1339	ai->micstats.enabled = (le16_to_cpu(mic_rid.state) & 0x00FF) ? 1 : 0;
1340	if (!ai->micstats.enabled) {
1341		/* So next time we have a valid key and mic is enabled, we will
1342		 * update the sequence number if the key is the same as before.
1343		 */
1344		ai->mod[0].uCtx.valid = 0;
1345		ai->mod[0].mCtx.valid = 0;
1346		return;
1347	}
1348
1349	if (mic_rid.multicastValid) {
1350		age_mic_context(&ai->mod[0].mCtx, &ai->mod[1].mCtx,
1351		                mic_rid.multicast, sizeof(mic_rid.multicast),
1352		                ai->tfm);
1353	}
1354
1355	if (mic_rid.unicastValid) {
1356		age_mic_context(&ai->mod[0].uCtx, &ai->mod[1].uCtx,
1357				mic_rid.unicast, sizeof(mic_rid.unicast),
1358				ai->tfm);
1359	}
1360}
1361
1362/* micsetup - Get ready for business */
1363
1364static int micsetup(struct airo_info *ai)
1365{
1366	int i;
1367
1368	if (ai->tfm == NULL)
1369		ai->tfm = crypto_alloc_sync_skcipher("ctr(aes)", 0, 0);
1370
1371        if (IS_ERR(ai->tfm)) {
1372                airo_print_err(ai->dev->name, "failed to load transform for AES");
1373                ai->tfm = NULL;
1374                return ERROR;
1375        }
1376
1377	for (i = 0; i < NUM_MODULES; i++) {
1378		memset(&ai->mod[i].mCtx, 0, sizeof(miccntx));
1379		memset(&ai->mod[i].uCtx, 0, sizeof(miccntx));
1380	}
1381	return SUCCESS;
1382}
1383
1384static const u8 micsnap[] = {0xAA, 0xAA, 0x03, 0x00, 0x40, 0x96, 0x00, 0x02};
1385
1386/*===========================================================================
1387 * Description: Mic a packet
1388 *
1389 *      Inputs: etherHead * pointer to an 802.3 frame
1390 *
1391 *     Returns: BOOLEAN if successful, otherwise false.
1392 *             PacketTxLen will be updated with the mic'd packets size.
1393 *
1394 *    Caveats: It is assumed that the frame buffer will already
1395 *             be big enough to hold the largets mic message possible.
1396 *            (No memory allocation is done here).
1397 *
1398 *    Author: sbraneky (10/15/01)
1399 *    Merciless hacks by rwilcher (1/14/02)
1400 */
1401
1402static int encapsulate(struct airo_info *ai, etherHead *frame, MICBuffer *mic, int payLen)
1403{
1404	miccntx   *context;
1405
1406	// Determine correct context
1407	// If not adhoc, always use unicast key
1408
1409	if (test_bit(FLAG_ADHOC, &ai->flags) && (frame->da[0] & 0x1))
1410		context = &ai->mod[0].mCtx;
1411	else
1412		context = &ai->mod[0].uCtx;
1413
1414	if (!context->valid)
1415		return ERROR;
1416
1417	mic->typelen = htons(payLen + 16); //Length of Mic'd packet
1418
1419	memcpy(&mic->u.snap, micsnap, sizeof(micsnap)); // Add Snap
1420
1421	// Add Tx sequence
1422	mic->seq = htonl(context->tx);
1423	context->tx += 2;
1424
1425	emmh32_init(&context->seed); // Mic the packet
1426	emmh32_update(&context->seed, frame->da, ETH_ALEN * 2); // DA, SA
1427	emmh32_update(&context->seed, (u8*)&mic->typelen, 10); // Type/Length and Snap
1428	emmh32_update(&context->seed, (u8*)&mic->seq, sizeof(mic->seq)); //SEQ
1429	emmh32_update(&context->seed, (u8*)(frame + 1), payLen); //payload
1430	emmh32_final(&context->seed, (u8*)&mic->mic);
1431
1432	/*    New Type/length ?????????? */
1433	mic->typelen = 0; //Let NIC know it could be an oversized packet
1434	return SUCCESS;
1435}
1436
1437typedef enum {
1438    NONE,
1439    NOMIC,
1440    NOMICPLUMMED,
1441    SEQUENCE,
1442    INCORRECTMIC,
1443} mic_error;
1444
1445/*===========================================================================
1446 *  Description: Decapsulates a MIC'd packet and returns the 802.3 packet
1447 *               (removes the MIC stuff) if packet is a valid packet.
1448 *
1449 *       Inputs: etherHead  pointer to the 802.3 packet
1450 *
1451 *      Returns: BOOLEAN - TRUE if packet should be dropped otherwise FALSE
1452 *
1453 *      Author: sbraneky (10/15/01)
1454 *    Merciless hacks by rwilcher (1/14/02)
1455 *---------------------------------------------------------------------------
1456 */
1457
1458static int decapsulate(struct airo_info *ai, MICBuffer *mic, etherHead *eth, u16 payLen)
1459{
1460	int      i;
1461	u32      micSEQ;
1462	miccntx  *context;
1463	u8       digest[4];
1464	mic_error micError = NONE;
1465
1466	// Check if the packet is a Mic'd packet
1467
1468	if (!ai->micstats.enabled) {
1469		//No Mic set or Mic OFF but we received a MIC'd packet.
1470		if (memcmp ((u8*)eth + 14, micsnap, sizeof(micsnap)) == 0) {
1471			ai->micstats.rxMICPlummed++;
1472			return ERROR;
1473		}
1474		return SUCCESS;
1475	}
1476
1477	if (ntohs(mic->typelen) == 0x888E)
1478		return SUCCESS;
1479
1480	if (memcmp (mic->u.snap, micsnap, sizeof(micsnap)) != 0) {
1481	    // Mic enabled but packet isn't Mic'd
1482		ai->micstats.rxMICPlummed++;
1483	    	return ERROR;
1484	}
1485
1486	micSEQ = ntohl(mic->seq);            //store SEQ as CPU order
1487
1488	//At this point we a have a mic'd packet and mic is enabled
1489	//Now do the mic error checking.
1490
1491	//Receive seq must be odd
1492	if ((micSEQ & 1) == 0) {
1493		ai->micstats.rxWrongSequence++;
1494		return ERROR;
1495	}
1496
1497	for (i = 0; i < NUM_MODULES; i++) {
1498		int mcast = eth->da[0] & 1;
1499		//Determine proper context
1500		context = mcast ? &ai->mod[i].mCtx : &ai->mod[i].uCtx;
1501
1502		//Make sure context is valid
1503		if (!context->valid) {
1504			if (i == 0)
1505				micError = NOMICPLUMMED;
1506			continue;
1507		}
1508		//DeMic it
1509
1510		if (!mic->typelen)
1511			mic->typelen = htons(payLen + sizeof(MICBuffer) - 2);
1512
1513		emmh32_init(&context->seed);
1514		emmh32_update(&context->seed, eth->da, ETH_ALEN*2);
1515		emmh32_update(&context->seed, (u8 *)&mic->typelen, sizeof(mic->typelen)+sizeof(mic->u.snap));
1516		emmh32_update(&context->seed, (u8 *)&mic->seq, sizeof(mic->seq));
1517		emmh32_update(&context->seed, (u8 *)(eth + 1), payLen);
1518		//Calculate MIC
1519		emmh32_final(&context->seed, digest);
1520
1521		if (memcmp(digest, &mic->mic, 4)) { //Make sure the mics match
1522		  //Invalid Mic
1523			if (i == 0)
1524				micError = INCORRECTMIC;
1525			continue;
1526		}
1527
1528		//Check Sequence number if mics pass
1529		if (RxSeqValid(ai, context, mcast, micSEQ) == SUCCESS) {
1530			ai->micstats.rxSuccess++;
1531			return SUCCESS;
1532		}
1533		if (i == 0)
1534			micError = SEQUENCE;
1535	}
1536
1537	// Update statistics
1538	switch (micError) {
1539		case NOMICPLUMMED: ai->micstats.rxMICPlummed++;   break;
1540		case SEQUENCE:    ai->micstats.rxWrongSequence++; break;
1541		case INCORRECTMIC: ai->micstats.rxIncorrectMIC++; break;
1542		case NONE:  break;
1543		case NOMIC: break;
1544	}
1545	return ERROR;
1546}
1547
1548/*===========================================================================
1549 * Description:  Checks the Rx Seq number to make sure it is valid
1550 *               and hasn't already been received
1551 *
1552 *     Inputs: miccntx - mic context to check seq against
1553 *             micSeq  - the Mic seq number
1554 *
1555 *    Returns: TRUE if valid otherwise FALSE.
1556 *
1557 *    Author: sbraneky (10/15/01)
1558 *    Merciless hacks by rwilcher (1/14/02)
1559 *---------------------------------------------------------------------------
1560 */
1561
1562static int RxSeqValid(struct airo_info *ai, miccntx *context, int mcast, u32 micSeq)
1563{
1564	u32 seq, index;
1565
1566	//Allow for the ap being rebooted - if it is then use the next
1567	//sequence number of the current sequence number - might go backwards
1568
1569	if (mcast) {
1570		if (test_bit(FLAG_UPDATE_MULTI, &ai->flags)) {
1571			clear_bit (FLAG_UPDATE_MULTI, &ai->flags);
1572			context->window = (micSeq > 33) ? micSeq : 33;
1573			context->rx     = 0;        // Reset rx
1574		}
1575	} else if (test_bit(FLAG_UPDATE_UNI, &ai->flags)) {
1576		clear_bit (FLAG_UPDATE_UNI, &ai->flags);
1577		context->window = (micSeq > 33) ? micSeq : 33; // Move window
1578		context->rx     = 0;        // Reset rx
1579	}
1580
1581	//Make sequence number relative to START of window
1582	seq = micSeq - (context->window - 33);
1583
1584	//Too old of a SEQ number to check.
1585	if ((s32)seq < 0)
1586		return ERROR;
1587
1588	if (seq > 64) {
1589		//Window is infinite forward
1590		MoveWindow(context, micSeq);
1591		return SUCCESS;
1592	}
1593
1594	// We are in the window. Now check the context rx bit to see if it was already sent
1595	seq >>= 1;         //divide by 2 because we only have odd numbers
1596	index = 1 << seq;  //Get an index number
1597
1598	if (!(context->rx & index)) {
1599		//micSEQ falls inside the window.
1600		//Add seqence number to the list of received numbers.
1601		context->rx |= index;
1602
1603		MoveWindow(context, micSeq);
1604
1605		return SUCCESS;
1606	}
1607	return ERROR;
1608}
1609
1610static void MoveWindow(miccntx *context, u32 micSeq)
1611{
1612	u32 shift;
1613
1614	//Move window if seq greater than the middle of the window
1615	if (micSeq > context->window) {
1616		shift = (micSeq - context->window) >> 1;
1617
1618		    //Shift out old
1619		if (shift < 32)
1620			context->rx >>= shift;
1621		else
1622			context->rx = 0;
1623
1624		context->window = micSeq;      //Move window
1625	}
1626}
1627
1628/*==============================================*/
1629/*========== EMMH ROUTINES  ====================*/
1630/*==============================================*/
1631
1632/* mic accumulate */
1633#define MIC_ACCUM(val)	\
1634	context->accum += (u64)(val) * be32_to_cpu(context->coeff[coeff_position++]);
 
 
1635
1636/* expand the key to fill the MMH coefficient array */
1637static void emmh32_setseed(emmh32_context *context, u8 *pkey, int keylen,
1638			   struct crypto_sync_skcipher *tfm)
1639{
1640  /* take the keying material, expand if necessary, truncate at 16-bytes */
1641  /* run through AES counter mode to generate context->coeff[] */
1642
1643	SYNC_SKCIPHER_REQUEST_ON_STACK(req, tfm);
1644	struct scatterlist sg;
1645	u8 iv[AES_BLOCK_SIZE] = {};
1646	int ret;
1647
1648	crypto_sync_skcipher_setkey(tfm, pkey, 16);
1649
1650	memset(context->coeff, 0, sizeof(context->coeff));
1651	sg_init_one(&sg, context->coeff, sizeof(context->coeff));
1652
1653	skcipher_request_set_sync_tfm(req, tfm);
1654	skcipher_request_set_callback(req, 0, NULL, NULL);
1655	skcipher_request_set_crypt(req, &sg, &sg, sizeof(context->coeff), iv);
1656
1657	ret = crypto_skcipher_encrypt(req);
1658	WARN_ON_ONCE(ret);
 
 
 
 
1659}
1660
1661/* prepare for calculation of a new mic */
1662static void emmh32_init(emmh32_context *context)
1663{
1664	/* prepare for new mic calculation */
1665	context->accum = 0;
1666	context->position = 0;
1667}
1668
1669/* add some bytes to the mic calculation */
1670static void emmh32_update(emmh32_context *context, u8 *pOctets, int len)
1671{
1672	int	coeff_position, byte_position;
1673
1674	if (len == 0) return;
1675
1676	coeff_position = context->position >> 2;
1677
1678	/* deal with partial 32-bit word left over from last update */
1679	byte_position = context->position & 3;
1680	if (byte_position) {
1681		/* have a partial word in part to deal with */
1682		do {
1683			if (len == 0) return;
1684			context->part.d8[byte_position++] = *pOctets++;
1685			context->position++;
1686			len--;
1687		} while (byte_position < 4);
1688		MIC_ACCUM(ntohl(context->part.d32));
1689	}
1690
1691	/* deal with full 32-bit words */
1692	while (len >= 4) {
1693		MIC_ACCUM(ntohl(*(__be32 *)pOctets));
1694		context->position += 4;
1695		pOctets += 4;
1696		len -= 4;
1697	}
1698
1699	/* deal with partial 32-bit word that will be left over from this update */
1700	byte_position = 0;
1701	while (len > 0) {
1702		context->part.d8[byte_position++] = *pOctets++;
1703		context->position++;
1704		len--;
1705	}
1706}
1707
1708/* mask used to zero empty bytes for final partial word */
1709static u32 mask32[4] = { 0x00000000L, 0xFF000000L, 0xFFFF0000L, 0xFFFFFF00L };
1710
1711/* calculate the mic */
1712static void emmh32_final(emmh32_context *context, u8 digest[4])
1713{
1714	int	coeff_position, byte_position;
1715	u32	val;
1716
1717	u64 sum, utmp;
1718	s64 stmp;
1719
1720	coeff_position = context->position >> 2;
1721
1722	/* deal with partial 32-bit word left over from last update */
1723	byte_position = context->position & 3;
1724	if (byte_position) {
1725		/* have a partial word in part to deal with */
1726		val = ntohl(context->part.d32);
1727		MIC_ACCUM(val & mask32[byte_position]);	/* zero empty bytes */
1728	}
1729
1730	/* reduce the accumulated u64 to a 32-bit MIC */
1731	sum = context->accum;
1732	stmp = (sum  & 0xffffffffLL) - ((sum >> 32)  * 15);
1733	utmp = (stmp & 0xffffffffLL) - ((stmp >> 32) * 15);
1734	sum = utmp & 0xffffffffLL;
1735	if (utmp > 0x10000000fLL)
1736		sum -= 15;
1737
1738	val = (u32)sum;
1739	digest[0] = (val>>24) & 0xFF;
1740	digest[1] = (val>>16) & 0xFF;
1741	digest[2] = (val>>8) & 0xFF;
1742	digest[3] = val & 0xFF;
1743}
1744
1745static int readBSSListRid(struct airo_info *ai, int first,
1746		      BSSListRid *list)
1747{
1748	Cmd cmd;
1749	Resp rsp;
1750
1751	if (first == 1) {
1752		if (ai->flags & FLAG_RADIO_MASK) return -ENETDOWN;
1753		memset(&cmd, 0, sizeof(cmd));
1754		cmd.cmd = CMD_LISTBSS;
1755		if (down_interruptible(&ai->sem))
1756			return -ERESTARTSYS;
1757		ai->list_bss_task = current;
1758		issuecommand(ai, &cmd, &rsp, true);
1759		up(&ai->sem);
1760		/* Let the command take effect */
1761		schedule_timeout_uninterruptible(3 * HZ);
1762		ai->list_bss_task = NULL;
1763	}
1764	return PC4500_readrid(ai, first ? ai->bssListFirst : ai->bssListNext,
1765			    list, ai->bssListRidLen, 1);
1766}
1767
1768static int readWepKeyRid(struct airo_info *ai, WepKeyRid *wkr, int temp, int lock)
1769{
1770	return PC4500_readrid(ai, temp ? RID_WEP_TEMP : RID_WEP_PERM,
1771				wkr, sizeof(*wkr), lock);
1772}
1773
1774static int writeWepKeyRid(struct airo_info *ai, WepKeyRid *wkr, int perm, int lock)
1775{
1776	int rc;
1777	rc = PC4500_writerid(ai, RID_WEP_TEMP, wkr, sizeof(*wkr), lock);
1778	if (rc!=SUCCESS)
1779		airo_print_err(ai->dev->name, "WEP_TEMP set %x", rc);
1780	if (perm) {
1781		rc = PC4500_writerid(ai, RID_WEP_PERM, wkr, sizeof(*wkr), lock);
1782		if (rc!=SUCCESS)
1783			airo_print_err(ai->dev->name, "WEP_PERM set %x", rc);
1784	}
1785	return rc;
1786}
1787
1788static int readSsidRid(struct airo_info*ai, SsidRid *ssidr)
1789{
1790	return PC4500_readrid(ai, RID_SSID, ssidr, sizeof(*ssidr), 1);
1791}
1792
1793static int writeSsidRid(struct airo_info*ai, SsidRid *pssidr, int lock)
1794{
1795	return PC4500_writerid(ai, RID_SSID, pssidr, sizeof(*pssidr), lock);
1796}
1797
1798static int readConfigRid(struct airo_info *ai, int lock)
1799{
1800	int rc;
1801	ConfigRid cfg;
1802
1803	if (ai->config.len)
1804		return SUCCESS;
1805
1806	rc = PC4500_readrid(ai, RID_ACTUALCONFIG, &cfg, sizeof(cfg), lock);
1807	if (rc != SUCCESS)
1808		return rc;
1809
1810	ai->config = cfg;
1811	return SUCCESS;
1812}
1813
1814static inline void checkThrottle(struct airo_info *ai)
1815{
1816	int i;
1817/* Old hardware had a limit on encryption speed */
1818	if (ai->config.authType != AUTH_OPEN && maxencrypt) {
1819		for (i = 0; i<8; i++) {
1820			if (ai->config.rates[i] > maxencrypt) {
1821				ai->config.rates[i] = 0;
1822			}
1823		}
1824	}
1825}
1826
1827static int writeConfigRid(struct airo_info *ai, int lock)
1828{
1829	ConfigRid cfgr;
1830
1831	if (!test_bit (FLAG_COMMIT, &ai->flags))
1832		return SUCCESS;
1833
1834	clear_bit (FLAG_COMMIT, &ai->flags);
1835	clear_bit (FLAG_RESET, &ai->flags);
1836	checkThrottle(ai);
1837	cfgr = ai->config;
1838
1839	if ((cfgr.opmode & MODE_CFG_MASK) == MODE_STA_IBSS)
1840		set_bit(FLAG_ADHOC, &ai->flags);
1841	else
1842		clear_bit(FLAG_ADHOC, &ai->flags);
1843
1844	return PC4500_writerid(ai, RID_CONFIG, &cfgr, sizeof(cfgr), lock);
1845}
1846
1847static int readStatusRid(struct airo_info *ai, StatusRid *statr, int lock)
1848{
1849	return PC4500_readrid(ai, RID_STATUS, statr, sizeof(*statr), lock);
1850}
1851
1852static int writeAPListRid(struct airo_info *ai, APListRid *aplr, int lock)
1853{
1854	return PC4500_writerid(ai, RID_APLIST, aplr, sizeof(*aplr), lock);
1855}
1856
1857static int readCapabilityRid(struct airo_info *ai, CapabilityRid *capr, int lock)
1858{
1859	return PC4500_readrid(ai, RID_CAPABILITIES, capr, sizeof(*capr), lock);
1860}
1861
1862static int readStatsRid(struct airo_info*ai, StatsRid *sr, int rid, int lock)
1863{
1864	return PC4500_readrid(ai, rid, sr, sizeof(*sr), lock);
1865}
1866
1867static void try_auto_wep(struct airo_info *ai)
1868{
1869	if (auto_wep && !test_bit(FLAG_RADIO_DOWN, &ai->flags)) {
1870		ai->expires = RUN_AT(3*HZ);
1871		wake_up_interruptible(&ai->thr_wait);
1872	}
1873}
1874
1875static int airo_open(struct net_device *dev)
1876{
1877	struct airo_info *ai = dev->ml_priv;
1878	int rc = 0;
1879
1880	if (test_bit(FLAG_FLASHING, &ai->flags))
1881		return -EIO;
1882
1883	/* Make sure the card is configured.
1884	 * Wireless Extensions may postpone config changes until the card
1885	 * is open (to pipeline changes and speed-up card setup). If
1886	 * those changes are not yet committed, do it now - Jean II */
1887	if (test_bit(FLAG_COMMIT, &ai->flags)) {
1888		disable_MAC(ai, 1);
1889		writeConfigRid(ai, 1);
1890	}
1891
1892	if (ai->wifidev != dev) {
1893		clear_bit(JOB_DIE, &ai->jobs);
1894		ai->airo_thread_task = kthread_run(airo_thread, dev, "%s",
1895						   dev->name);
1896		if (IS_ERR(ai->airo_thread_task))
1897			return (int)PTR_ERR(ai->airo_thread_task);
1898
1899		rc = request_irq(dev->irq, airo_interrupt, IRQF_SHARED,
1900			dev->name, dev);
1901		if (rc) {
1902			airo_print_err(dev->name,
1903				"register interrupt %d failed, rc %d",
1904				dev->irq, rc);
1905			set_bit(JOB_DIE, &ai->jobs);
1906			kthread_stop(ai->airo_thread_task);
1907			return rc;
1908		}
1909
1910		/* Power on the MAC controller (which may have been disabled) */
1911		clear_bit(FLAG_RADIO_DOWN, &ai->flags);
1912		enable_interrupts(ai);
1913
1914		try_auto_wep(ai);
1915	}
1916	enable_MAC(ai, 1);
1917
1918	netif_start_queue(dev);
1919	return 0;
1920}
1921
1922static netdev_tx_t mpi_start_xmit(struct sk_buff *skb,
1923					struct net_device *dev)
1924{
1925	int npacks, pending;
1926	unsigned long flags;
1927	struct airo_info *ai = dev->ml_priv;
1928
1929	if (!skb) {
1930		airo_print_err(dev->name, "%s: skb == NULL!",__func__);
1931		return NETDEV_TX_OK;
1932	}
1933	if (skb_padto(skb, ETH_ZLEN)) {
1934		dev->stats.tx_dropped++;
1935		return NETDEV_TX_OK;
1936	}
1937	npacks = skb_queue_len (&ai->txq);
1938
1939	if (npacks >= MAXTXQ - 1) {
1940		netif_stop_queue (dev);
1941		if (npacks > MAXTXQ) {
1942			dev->stats.tx_fifo_errors++;
1943			return NETDEV_TX_BUSY;
1944		}
1945		skb_queue_tail (&ai->txq, skb);
1946		return NETDEV_TX_OK;
1947	}
1948
1949	spin_lock_irqsave(&ai->aux_lock, flags);
1950	skb_queue_tail (&ai->txq, skb);
1951	pending = test_bit(FLAG_PENDING_XMIT, &ai->flags);
1952	spin_unlock_irqrestore(&ai->aux_lock, flags);
1953	netif_wake_queue (dev);
1954
1955	if (pending == 0) {
1956		set_bit(FLAG_PENDING_XMIT, &ai->flags);
1957		mpi_send_packet (dev);
1958	}
1959	return NETDEV_TX_OK;
1960}
1961
1962/*
1963 * @mpi_send_packet
1964 *
1965 * Attempt to transmit a packet. Can be called from interrupt
1966 * or transmit . return number of packets we tried to send
1967 */
1968
1969static int mpi_send_packet (struct net_device *dev)
1970{
1971	struct sk_buff *skb;
1972	unsigned char *buffer;
1973	s16 len;
1974	__le16 *payloadLen;
1975	struct airo_info *ai = dev->ml_priv;
1976	u8 *sendbuf;
1977
1978	/* get a packet to send */
1979
1980	if ((skb = skb_dequeue(&ai->txq)) == NULL) {
1981		airo_print_err(dev->name,
1982			"%s: Dequeue'd zero in send_packet()",
1983			__func__);
1984		return 0;
1985	}
1986
1987	/* check min length*/
1988	len = ETH_ZLEN < skb->len ? skb->len : ETH_ZLEN;
1989	buffer = skb->data;
1990
1991	ai->txfids[0].tx_desc.offset = 0;
1992	ai->txfids[0].tx_desc.valid = 1;
1993	ai->txfids[0].tx_desc.eoc = 1;
1994	ai->txfids[0].tx_desc.len =len+sizeof(WifiHdr);
1995
1996/*
1997 * Magic, the cards firmware needs a length count (2 bytes) in the host buffer
1998 * right after  TXFID_HDR.The TXFID_HDR contains the status short so payloadlen
1999 * is immediately after it. ------------------------------------------------
2000 *                         |TXFIDHDR+STATUS|PAYLOADLEN|802.3HDR|PACKETDATA|
2001 *                         ------------------------------------------------
2002 */
2003
2004	memcpy(ai->txfids[0].virtual_host_addr,
2005		(char *)&wifictlhdr8023, sizeof(wifictlhdr8023));
2006
2007	payloadLen = (__le16 *)(ai->txfids[0].virtual_host_addr +
2008		sizeof(wifictlhdr8023));
2009	sendbuf = ai->txfids[0].virtual_host_addr +
2010		sizeof(wifictlhdr8023) + 2 ;
2011
2012	/*
2013	 * Firmware automatically puts 802 header on so
2014	 * we don't need to account for it in the length
2015	 */
2016	if (test_bit(FLAG_MIC_CAPABLE, &ai->flags) && ai->micstats.enabled &&
2017		(ntohs(((__be16 *)buffer)[6]) != 0x888E)) {
2018		MICBuffer pMic;
2019
2020		if (encapsulate(ai, (etherHead *)buffer, &pMic, len - sizeof(etherHead)) != SUCCESS)
2021			return ERROR;
2022
2023		*payloadLen = cpu_to_le16(len-sizeof(etherHead)+sizeof(pMic));
2024		ai->txfids[0].tx_desc.len += sizeof(pMic);
2025		/* copy data into airo dma buffer */
2026		memcpy (sendbuf, buffer, sizeof(etherHead));
2027		buffer += sizeof(etherHead);
2028		sendbuf += sizeof(etherHead);
2029		memcpy (sendbuf, &pMic, sizeof(pMic));
2030		sendbuf += sizeof(pMic);
2031		memcpy (sendbuf, buffer, len - sizeof(etherHead));
2032	} else {
2033		*payloadLen = cpu_to_le16(len - sizeof(etherHead));
2034
2035		netif_trans_update(dev);
2036
2037		/* copy data into airo dma buffer */
2038		memcpy(sendbuf, buffer, len);
2039	}
2040
2041	memcpy_toio(ai->txfids[0].card_ram_off,
2042		&ai->txfids[0].tx_desc, sizeof(TxFid));
2043
2044	OUT4500(ai, EVACK, 8);
2045
2046	dev_kfree_skb_any(skb);
2047	return 1;
2048}
2049
2050static void get_tx_error(struct airo_info *ai, s32 fid)
2051{
2052	__le16 status;
2053
2054	if (fid < 0)
2055		status = ((WifiCtlHdr *)ai->txfids[0].virtual_host_addr)->ctlhdr.status;
2056	else {
2057		if (bap_setup(ai, ai->fids[fid] & 0xffff, 4, BAP0) != SUCCESS)
2058			return;
2059		bap_read(ai, &status, 2, BAP0);
2060	}
2061	if (le16_to_cpu(status) & 2) /* Too many retries */
2062		ai->dev->stats.tx_aborted_errors++;
2063	if (le16_to_cpu(status) & 4) /* Transmit lifetime exceeded */
2064		ai->dev->stats.tx_heartbeat_errors++;
2065	if (le16_to_cpu(status) & 8) /* Aid fail */
2066		{ }
2067	if (le16_to_cpu(status) & 0x10) /* MAC disabled */
2068		ai->dev->stats.tx_carrier_errors++;
2069	if (le16_to_cpu(status) & 0x20) /* Association lost */
2070		{ }
2071	/* We produce a TXDROP event only for retry or lifetime
2072	 * exceeded, because that's the only status that really mean
2073	 * that this particular node went away.
2074	 * Other errors means that *we* screwed up. - Jean II */
2075	if ((le16_to_cpu(status) & 2) ||
2076	     (le16_to_cpu(status) & 4)) {
2077		union iwreq_data	wrqu;
2078		char junk[0x18];
2079
2080		/* Faster to skip over useless data than to do
2081		 * another bap_setup(). We are at offset 0x6 and
2082		 * need to go to 0x18 and read 6 bytes - Jean II */
2083		bap_read(ai, (__le16 *) junk, 0x18, BAP0);
2084
2085		/* Copy 802.11 dest address.
2086		 * We use the 802.11 header because the frame may
2087		 * not be 802.3 or may be mangled...
2088		 * In Ad-Hoc mode, it will be the node address.
2089		 * In managed mode, it will be most likely the AP addr
2090		 * User space will figure out how to convert it to
2091		 * whatever it needs (IP address or else).
2092		 * - Jean II */
2093		memcpy(wrqu.addr.sa_data, junk + 0x12, ETH_ALEN);
2094		wrqu.addr.sa_family = ARPHRD_ETHER;
2095
2096		/* Send event to user space */
2097		wireless_send_event(ai->dev, IWEVTXDROP, &wrqu, NULL);
2098	}
2099}
2100
2101static void airo_end_xmit(struct net_device *dev, bool may_sleep)
2102{
2103	u16 status;
2104	int i;
2105	struct airo_info *priv = dev->ml_priv;
2106	struct sk_buff *skb = priv->xmit.skb;
2107	int fid = priv->xmit.fid;
2108	u32 *fids = priv->fids;
2109
2110	clear_bit(JOB_XMIT, &priv->jobs);
2111	clear_bit(FLAG_PENDING_XMIT, &priv->flags);
2112	status = transmit_802_3_packet(priv, fids[fid], skb->data, may_sleep);
2113	up(&priv->sem);
2114
2115	i = 0;
2116	if (status == SUCCESS) {
2117		netif_trans_update(dev);
2118		for (; i < MAX_FIDS / 2 && (priv->fids[i] & 0xffff0000); i++);
2119	} else {
2120		priv->fids[fid] &= 0xffff;
2121		dev->stats.tx_window_errors++;
2122	}
2123	if (i < MAX_FIDS / 2)
2124		netif_wake_queue(dev);
2125	dev_kfree_skb(skb);
2126}
2127
2128static netdev_tx_t airo_start_xmit(struct sk_buff *skb,
2129					 struct net_device *dev)
2130{
2131	s16 len;
2132	int i, j;
2133	struct airo_info *priv = dev->ml_priv;
2134	u32 *fids = priv->fids;
2135
2136	if (skb == NULL) {
2137		airo_print_err(dev->name, "%s: skb == NULL!", __func__);
2138		return NETDEV_TX_OK;
2139	}
2140	if (skb_padto(skb, ETH_ZLEN)) {
2141		dev->stats.tx_dropped++;
2142		return NETDEV_TX_OK;
2143	}
2144
2145	/* Find a vacant FID */
2146	for (i = 0; i < MAX_FIDS / 2 && (fids[i] & 0xffff0000); i++);
2147	for (j = i + 1; j < MAX_FIDS / 2 && (fids[j] & 0xffff0000); j++);
2148
2149	if (j >= MAX_FIDS / 2) {
2150		netif_stop_queue(dev);
2151
2152		if (i == MAX_FIDS / 2) {
2153			dev->stats.tx_fifo_errors++;
2154			return NETDEV_TX_BUSY;
2155		}
2156	}
2157	/* check min length*/
2158	len = ETH_ZLEN < skb->len ? skb->len : ETH_ZLEN;
2159        /* Mark fid as used & save length for later */
2160	fids[i] |= (len << 16);
2161	priv->xmit.skb = skb;
2162	priv->xmit.fid = i;
2163	if (down_trylock(&priv->sem) != 0) {
2164		set_bit(FLAG_PENDING_XMIT, &priv->flags);
2165		netif_stop_queue(dev);
2166		set_bit(JOB_XMIT, &priv->jobs);
2167		wake_up_interruptible(&priv->thr_wait);
2168	} else
2169		airo_end_xmit(dev, false);
2170	return NETDEV_TX_OK;
2171}
2172
2173static void airo_end_xmit11(struct net_device *dev, bool may_sleep)
2174{
2175	u16 status;
2176	int i;
2177	struct airo_info *priv = dev->ml_priv;
2178	struct sk_buff *skb = priv->xmit11.skb;
2179	int fid = priv->xmit11.fid;
2180	u32 *fids = priv->fids;
2181
2182	clear_bit(JOB_XMIT11, &priv->jobs);
2183	clear_bit(FLAG_PENDING_XMIT11, &priv->flags);
2184	status = transmit_802_11_packet(priv, fids[fid], skb->data, may_sleep);
2185	up(&priv->sem);
2186
2187	i = MAX_FIDS / 2;
2188	if (status == SUCCESS) {
2189		netif_trans_update(dev);
2190		for (; i < MAX_FIDS && (priv->fids[i] & 0xffff0000); i++);
2191	} else {
2192		priv->fids[fid] &= 0xffff;
2193		dev->stats.tx_window_errors++;
2194	}
2195	if (i < MAX_FIDS)
2196		netif_wake_queue(dev);
2197	dev_kfree_skb(skb);
2198}
2199
2200static netdev_tx_t airo_start_xmit11(struct sk_buff *skb,
2201					   struct net_device *dev)
2202{
2203	s16 len;
2204	int i, j;
2205	struct airo_info *priv = dev->ml_priv;
2206	u32 *fids = priv->fids;
2207
2208	if (test_bit(FLAG_MPI, &priv->flags)) {
2209		/* Not implemented yet for MPI350 */
2210		netif_stop_queue(dev);
2211		dev_kfree_skb_any(skb);
2212		return NETDEV_TX_OK;
2213	}
2214
2215	if (skb == NULL) {
2216		airo_print_err(dev->name, "%s: skb == NULL!", __func__);
2217		return NETDEV_TX_OK;
2218	}
2219	if (skb_padto(skb, ETH_ZLEN)) {
2220		dev->stats.tx_dropped++;
2221		return NETDEV_TX_OK;
2222	}
2223
2224	/* Find a vacant FID */
2225	for (i = MAX_FIDS / 2; i < MAX_FIDS && (fids[i] & 0xffff0000); i++);
2226	for (j = i + 1; j < MAX_FIDS && (fids[j] & 0xffff0000); j++);
2227
2228	if (j >= MAX_FIDS) {
2229		netif_stop_queue(dev);
2230
2231		if (i == MAX_FIDS) {
2232			dev->stats.tx_fifo_errors++;
2233			return NETDEV_TX_BUSY;
2234		}
2235	}
2236	/* check min length*/
2237	len = ETH_ZLEN < skb->len ? skb->len : ETH_ZLEN;
2238        /* Mark fid as used & save length for later */
2239	fids[i] |= (len << 16);
2240	priv->xmit11.skb = skb;
2241	priv->xmit11.fid = i;
2242	if (down_trylock(&priv->sem) != 0) {
2243		set_bit(FLAG_PENDING_XMIT11, &priv->flags);
2244		netif_stop_queue(dev);
2245		set_bit(JOB_XMIT11, &priv->jobs);
2246		wake_up_interruptible(&priv->thr_wait);
2247	} else
2248		airo_end_xmit11(dev, false);
2249	return NETDEV_TX_OK;
2250}
2251
2252static void airo_read_stats(struct net_device *dev)
2253{
2254	struct airo_info *ai = dev->ml_priv;
2255	StatsRid stats_rid;
2256	__le32 *vals = stats_rid.vals;
2257
2258	clear_bit(JOB_STATS, &ai->jobs);
2259	if (ai->power.event) {
2260		up(&ai->sem);
2261		return;
2262	}
2263	readStatsRid(ai, &stats_rid, RID_STATS, 0);
2264	up(&ai->sem);
2265
2266	dev->stats.rx_packets = le32_to_cpu(vals[43]) + le32_to_cpu(vals[44]) +
2267			       le32_to_cpu(vals[45]);
2268	dev->stats.tx_packets = le32_to_cpu(vals[39]) + le32_to_cpu(vals[40]) +
2269			       le32_to_cpu(vals[41]);
2270	dev->stats.rx_bytes = le32_to_cpu(vals[92]);
2271	dev->stats.tx_bytes = le32_to_cpu(vals[91]);
2272	dev->stats.rx_errors = le32_to_cpu(vals[0]) + le32_to_cpu(vals[2]) +
2273			      le32_to_cpu(vals[3]) + le32_to_cpu(vals[4]);
2274	dev->stats.tx_errors = le32_to_cpu(vals[42]) +
2275			      dev->stats.tx_fifo_errors;
2276	dev->stats.multicast = le32_to_cpu(vals[43]);
2277	dev->stats.collisions = le32_to_cpu(vals[89]);
2278
2279	/* detailed rx_errors: */
2280	dev->stats.rx_length_errors = le32_to_cpu(vals[3]);
2281	dev->stats.rx_crc_errors = le32_to_cpu(vals[4]);
2282	dev->stats.rx_frame_errors = le32_to_cpu(vals[2]);
2283	dev->stats.rx_fifo_errors = le32_to_cpu(vals[0]);
2284}
2285
2286static struct net_device_stats *airo_get_stats(struct net_device *dev)
2287{
2288	struct airo_info *local =  dev->ml_priv;
2289
2290	if (!test_bit(JOB_STATS, &local->jobs)) {
2291		set_bit(JOB_STATS, &local->jobs);
2292		wake_up_interruptible(&local->thr_wait);
 
 
 
 
2293	}
2294
2295	return &dev->stats;
2296}
2297
2298static void airo_set_promisc(struct airo_info *ai, bool may_sleep)
2299{
2300	Cmd cmd;
2301	Resp rsp;
2302
2303	memset(&cmd, 0, sizeof(cmd));
2304	cmd.cmd = CMD_SETMODE;
2305	clear_bit(JOB_PROMISC, &ai->jobs);
2306	cmd.parm0=(ai->flags&IFF_PROMISC) ? PROMISC : NOPROMISC;
2307	issuecommand(ai, &cmd, &rsp, may_sleep);
2308	up(&ai->sem);
2309}
2310
2311static void airo_set_multicast_list(struct net_device *dev)
2312{
2313	struct airo_info *ai = dev->ml_priv;
2314
2315	if ((dev->flags ^ ai->flags) & IFF_PROMISC) {
2316		change_bit(FLAG_PROMISC, &ai->flags);
2317		if (down_trylock(&ai->sem) != 0) {
2318			set_bit(JOB_PROMISC, &ai->jobs);
2319			wake_up_interruptible(&ai->thr_wait);
2320		} else
2321			airo_set_promisc(ai, false);
2322	}
2323
2324	if ((dev->flags&IFF_ALLMULTI) || !netdev_mc_empty(dev)) {
2325		/* Turn on multicast.  (Should be already setup...) */
2326	}
2327}
2328
2329static int airo_set_mac_address(struct net_device *dev, void *p)
2330{
2331	struct airo_info *ai = dev->ml_priv;
2332	struct sockaddr *addr = p;
2333
2334	readConfigRid(ai, 1);
2335	memcpy (ai->config.macAddr, addr->sa_data, dev->addr_len);
2336	set_bit (FLAG_COMMIT, &ai->flags);
2337	disable_MAC(ai, 1);
2338	writeConfigRid (ai, 1);
2339	enable_MAC(ai, 1);
2340	memcpy (ai->dev->dev_addr, addr->sa_data, dev->addr_len);
2341	if (ai->wifidev)
2342		memcpy (ai->wifidev->dev_addr, addr->sa_data, dev->addr_len);
2343	return 0;
2344}
2345
 
 
 
 
 
 
 
 
2346static LIST_HEAD(airo_devices);
2347
2348static void add_airo_dev(struct airo_info *ai)
2349{
2350	/* Upper layers already keep track of PCI devices,
2351	 * so we only need to remember our non-PCI cards. */
2352	if (!ai->pci)
2353		list_add_tail(&ai->dev_list, &airo_devices);
2354}
2355
2356static void del_airo_dev(struct airo_info *ai)
2357{
2358	if (!ai->pci)
2359		list_del(&ai->dev_list);
2360}
2361
2362static int airo_close(struct net_device *dev)
2363{
2364	struct airo_info *ai = dev->ml_priv;
2365
2366	netif_stop_queue(dev);
2367
2368	if (ai->wifidev != dev) {
2369#ifdef POWER_ON_DOWN
2370		/* Shut power to the card. The idea is that the user can save
2371		 * power when he doesn't need the card with "ifconfig down".
2372		 * That's the method that is most friendly towards the network
2373		 * stack (i.e. the network stack won't try to broadcast
2374		 * anything on the interface and routes are gone. Jean II */
2375		set_bit(FLAG_RADIO_DOWN, &ai->flags);
2376		disable_MAC(ai, 1);
2377#endif
2378		disable_interrupts(ai);
2379
2380		free_irq(dev->irq, dev);
2381
2382		set_bit(JOB_DIE, &ai->jobs);
2383		kthread_stop(ai->airo_thread_task);
2384	}
2385	return 0;
2386}
2387
2388void stop_airo_card(struct net_device *dev, int freeres)
2389{
2390	struct airo_info *ai = dev->ml_priv;
2391
2392	set_bit(FLAG_RADIO_DOWN, &ai->flags);
2393	disable_MAC(ai, 1);
2394	disable_interrupts(ai);
2395	takedown_proc_entry(dev, ai);
2396	if (test_bit(FLAG_REGISTERED, &ai->flags)) {
2397		unregister_netdev(dev);
2398		if (ai->wifidev) {
2399			unregister_netdev(ai->wifidev);
2400			free_netdev(ai->wifidev);
2401			ai->wifidev = NULL;
2402		}
2403		clear_bit(FLAG_REGISTERED, &ai->flags);
2404	}
2405	/*
2406	 * Clean out tx queue
2407	 */
2408	if (test_bit(FLAG_MPI, &ai->flags) && !skb_queue_empty(&ai->txq)) {
2409		struct sk_buff *skb = NULL;
2410		for (;(skb = skb_dequeue(&ai->txq));)
2411			dev_kfree_skb(skb);
2412	}
2413
2414	airo_networks_free (ai);
2415
2416	kfree(ai->flash);
2417	kfree(ai->rssi);
2418	kfree(ai->SSID);
2419	if (freeres) {
2420		/* PCMCIA frees this stuff, so only for PCI and ISA */
2421		release_region(dev->base_addr, 64);
2422		if (test_bit(FLAG_MPI, &ai->flags)) {
2423			if (ai->pci)
2424				mpi_unmap_card(ai->pci);
2425			if (ai->pcimem)
2426				iounmap(ai->pcimem);
2427			if (ai->pciaux)
2428				iounmap(ai->pciaux);
2429			dma_free_coherent(&ai->pci->dev, PCI_SHARED_LEN,
2430					  ai->shared, ai->shared_dma);
2431		}
2432        }
2433	crypto_free_sync_skcipher(ai->tfm);
2434	del_airo_dev(ai);
2435	free_netdev(dev);
2436}
2437
2438EXPORT_SYMBOL(stop_airo_card);
2439
2440static int wll_header_parse(const struct sk_buff *skb, unsigned char *haddr)
2441{
2442	memcpy(haddr, skb_mac_header(skb) + 10, ETH_ALEN);
2443	return ETH_ALEN;
2444}
2445
2446static void mpi_unmap_card(struct pci_dev *pci)
2447{
2448	unsigned long mem_start = pci_resource_start(pci, 1);
2449	unsigned long mem_len = pci_resource_len(pci, 1);
2450	unsigned long aux_start = pci_resource_start(pci, 2);
2451	unsigned long aux_len = AUXMEMSIZE;
2452
2453	release_mem_region(aux_start, aux_len);
2454	release_mem_region(mem_start, mem_len);
2455}
2456
2457/*************************************************************
2458 *  This routine assumes that descriptors have been setup .
2459 *  Run at insmod time or after reset when the descriptors
2460 *  have been initialized . Returns 0 if all is well nz
2461 *  otherwise . Does not allocate memory but sets up card
2462 *  using previously allocated descriptors.
2463 */
2464static int mpi_init_descriptors (struct airo_info *ai)
2465{
2466	Cmd cmd;
2467	Resp rsp;
2468	int i;
2469	int rc = SUCCESS;
2470
2471	/* Alloc  card RX descriptors */
2472	netif_stop_queue(ai->dev);
2473
2474	memset(&rsp, 0, sizeof(rsp));
2475	memset(&cmd, 0, sizeof(cmd));
2476
2477	cmd.cmd = CMD_ALLOCATEAUX;
2478	cmd.parm0 = FID_RX;
2479	cmd.parm1 = (ai->rxfids[0].card_ram_off - ai->pciaux);
2480	cmd.parm2 = MPI_MAX_FIDS;
2481	rc = issuecommand(ai, &cmd, &rsp, true);
2482	if (rc != SUCCESS) {
2483		airo_print_err(ai->dev->name, "Couldn't allocate RX FID");
2484		return rc;
2485	}
2486
2487	for (i = 0; i<MPI_MAX_FIDS; i++) {
2488		memcpy_toio(ai->rxfids[i].card_ram_off,
2489			&ai->rxfids[i].rx_desc, sizeof(RxFid));
2490	}
2491
2492	/* Alloc card TX descriptors */
2493
2494	memset(&rsp, 0, sizeof(rsp));
2495	memset(&cmd, 0, sizeof(cmd));
2496
2497	cmd.cmd = CMD_ALLOCATEAUX;
2498	cmd.parm0 = FID_TX;
2499	cmd.parm1 = (ai->txfids[0].card_ram_off - ai->pciaux);
2500	cmd.parm2 = MPI_MAX_FIDS;
2501
2502	for (i = 0; i<MPI_MAX_FIDS; i++) {
2503		ai->txfids[i].tx_desc.valid = 1;
2504		memcpy_toio(ai->txfids[i].card_ram_off,
2505			&ai->txfids[i].tx_desc, sizeof(TxFid));
2506	}
2507	ai->txfids[i-1].tx_desc.eoc = 1; /* Last descriptor has EOC set */
2508
2509	rc = issuecommand(ai, &cmd, &rsp, true);
2510	if (rc != SUCCESS) {
2511		airo_print_err(ai->dev->name, "Couldn't allocate TX FID");
2512		return rc;
2513	}
2514
2515	/* Alloc card Rid descriptor */
2516	memset(&rsp, 0, sizeof(rsp));
2517	memset(&cmd, 0, sizeof(cmd));
2518
2519	cmd.cmd = CMD_ALLOCATEAUX;
2520	cmd.parm0 = RID_RW;
2521	cmd.parm1 = (ai->config_desc.card_ram_off - ai->pciaux);
2522	cmd.parm2 = 1; /* Magic number... */
2523	rc = issuecommand(ai, &cmd, &rsp, true);
2524	if (rc != SUCCESS) {
2525		airo_print_err(ai->dev->name, "Couldn't allocate RID");
2526		return rc;
2527	}
2528
2529	memcpy_toio(ai->config_desc.card_ram_off,
2530		&ai->config_desc.rid_desc, sizeof(Rid));
2531
2532	return rc;
2533}
2534
2535/*
2536 * We are setting up three things here:
2537 * 1) Map AUX memory for descriptors: Rid, TxFid, or RxFid.
2538 * 2) Map PCI memory for issuing commands.
2539 * 3) Allocate memory (shared) to send and receive ethernet frames.
2540 */
2541static int mpi_map_card(struct airo_info *ai, struct pci_dev *pci)
2542{
2543	unsigned long mem_start, mem_len, aux_start, aux_len;
2544	int rc = -1;
2545	int i;
2546	dma_addr_t busaddroff;
2547	unsigned char *vpackoff;
2548	unsigned char __iomem *pciaddroff;
2549
2550	mem_start = pci_resource_start(pci, 1);
2551	mem_len = pci_resource_len(pci, 1);
2552	aux_start = pci_resource_start(pci, 2);
2553	aux_len = AUXMEMSIZE;
2554
2555	if (!request_mem_region(mem_start, mem_len, DRV_NAME)) {
2556		airo_print_err("", "Couldn't get region %x[%x]",
2557			(int)mem_start, (int)mem_len);
2558		goto out;
2559	}
2560	if (!request_mem_region(aux_start, aux_len, DRV_NAME)) {
2561		airo_print_err("", "Couldn't get region %x[%x]",
2562			(int)aux_start, (int)aux_len);
2563		goto free_region1;
2564	}
2565
2566	ai->pcimem = ioremap(mem_start, mem_len);
2567	if (!ai->pcimem) {
2568		airo_print_err("", "Couldn't map region %x[%x]",
2569			(int)mem_start, (int)mem_len);
2570		goto free_region2;
2571	}
2572	ai->pciaux = ioremap(aux_start, aux_len);
2573	if (!ai->pciaux) {
2574		airo_print_err("", "Couldn't map region %x[%x]",
2575			(int)aux_start, (int)aux_len);
2576		goto free_memmap;
2577	}
2578
2579	/* Reserve PKTSIZE for each fid and 2K for the Rids */
2580	ai->shared = dma_alloc_coherent(&pci->dev, PCI_SHARED_LEN,
2581					&ai->shared_dma, GFP_KERNEL);
2582	if (!ai->shared) {
2583		airo_print_err("", "Couldn't alloc_coherent %d",
2584			PCI_SHARED_LEN);
2585		goto free_auxmap;
2586	}
2587
2588	/*
2589	 * Setup descriptor RX, TX, CONFIG
2590	 */
2591	busaddroff = ai->shared_dma;
2592	pciaddroff = ai->pciaux + AUX_OFFSET;
2593	vpackoff   = ai->shared;
2594
2595	/* RX descriptor setup */
2596	for (i = 0; i < MPI_MAX_FIDS; i++) {
2597		ai->rxfids[i].pending = 0;
2598		ai->rxfids[i].card_ram_off = pciaddroff;
2599		ai->rxfids[i].virtual_host_addr = vpackoff;
2600		ai->rxfids[i].rx_desc.host_addr = busaddroff;
2601		ai->rxfids[i].rx_desc.valid = 1;
2602		ai->rxfids[i].rx_desc.len = PKTSIZE;
2603		ai->rxfids[i].rx_desc.rdy = 0;
2604
2605		pciaddroff += sizeof(RxFid);
2606		busaddroff += PKTSIZE;
2607		vpackoff   += PKTSIZE;
2608	}
2609
2610	/* TX descriptor setup */
2611	for (i = 0; i < MPI_MAX_FIDS; i++) {
2612		ai->txfids[i].card_ram_off = pciaddroff;
2613		ai->txfids[i].virtual_host_addr = vpackoff;
2614		ai->txfids[i].tx_desc.valid = 1;
2615		ai->txfids[i].tx_desc.host_addr = busaddroff;
2616		memcpy(ai->txfids[i].virtual_host_addr,
2617			&wifictlhdr8023, sizeof(wifictlhdr8023));
2618
2619		pciaddroff += sizeof(TxFid);
2620		busaddroff += PKTSIZE;
2621		vpackoff   += PKTSIZE;
2622	}
2623	ai->txfids[i-1].tx_desc.eoc = 1; /* Last descriptor has EOC set */
2624
2625	/* Rid descriptor setup */
2626	ai->config_desc.card_ram_off = pciaddroff;
2627	ai->config_desc.virtual_host_addr = vpackoff;
2628	ai->config_desc.rid_desc.host_addr = busaddroff;
2629	ai->ridbus = busaddroff;
2630	ai->config_desc.rid_desc.rid = 0;
2631	ai->config_desc.rid_desc.len = RIDSIZE;
2632	ai->config_desc.rid_desc.valid = 1;
2633	pciaddroff += sizeof(Rid);
2634	busaddroff += RIDSIZE;
2635	vpackoff   += RIDSIZE;
2636
2637	/* Tell card about descriptors */
2638	if (mpi_init_descriptors (ai) != SUCCESS)
2639		goto free_shared;
2640
2641	return 0;
2642 free_shared:
2643	dma_free_coherent(&pci->dev, PCI_SHARED_LEN, ai->shared,
2644			  ai->shared_dma);
2645 free_auxmap:
2646	iounmap(ai->pciaux);
2647 free_memmap:
2648	iounmap(ai->pcimem);
2649 free_region2:
2650	release_mem_region(aux_start, aux_len);
2651 free_region1:
2652	release_mem_region(mem_start, mem_len);
2653 out:
2654	return rc;
2655}
2656
2657static const struct header_ops airo_header_ops = {
2658	.parse = wll_header_parse,
2659};
2660
2661static const struct net_device_ops airo11_netdev_ops = {
2662	.ndo_open 		= airo_open,
2663	.ndo_stop 		= airo_close,
2664	.ndo_start_xmit 	= airo_start_xmit11,
2665	.ndo_get_stats 		= airo_get_stats,
2666	.ndo_set_mac_address	= airo_set_mac_address,
2667	.ndo_do_ioctl		= airo_ioctl,
 
2668};
2669
2670static void wifi_setup(struct net_device *dev)
2671{
2672	dev->netdev_ops = &airo11_netdev_ops;
2673	dev->header_ops = &airo_header_ops;
2674	dev->wireless_handlers = &airo_handler_def;
2675
2676	dev->type               = ARPHRD_IEEE80211;
2677	dev->hard_header_len    = ETH_HLEN;
2678	dev->mtu                = AIRO_DEF_MTU;
2679	dev->min_mtu            = 68;
2680	dev->max_mtu            = MIC_MSGLEN_MAX;
2681	dev->addr_len           = ETH_ALEN;
2682	dev->tx_queue_len       = 100;
2683
2684	eth_broadcast_addr(dev->broadcast);
2685
2686	dev->flags              = IFF_BROADCAST|IFF_MULTICAST;
2687}
2688
2689static struct net_device *init_wifidev(struct airo_info *ai,
2690					struct net_device *ethdev)
2691{
2692	int err;
2693	struct net_device *dev = alloc_netdev(0, "wifi%d", NET_NAME_UNKNOWN,
2694					      wifi_setup);
2695	if (!dev)
2696		return NULL;
2697	dev->ml_priv = ethdev->ml_priv;
2698	dev->irq = ethdev->irq;
2699	dev->base_addr = ethdev->base_addr;
2700	dev->wireless_data = ethdev->wireless_data;
2701	SET_NETDEV_DEV(dev, ethdev->dev.parent);
2702	eth_hw_addr_inherit(dev, ethdev);
2703	err = register_netdev(dev);
2704	if (err<0) {
2705		free_netdev(dev);
2706		return NULL;
2707	}
2708	return dev;
2709}
2710
2711static int reset_card(struct net_device *dev, int lock)
2712{
2713	struct airo_info *ai = dev->ml_priv;
2714
2715	if (lock && down_interruptible(&ai->sem))
2716		return -1;
2717	waitbusy (ai);
2718	OUT4500(ai, COMMAND, CMD_SOFTRESET);
2719	msleep(200);
2720	waitbusy (ai);
2721	msleep(200);
2722	if (lock)
2723		up(&ai->sem);
2724	return 0;
2725}
2726
2727#define AIRO_MAX_NETWORK_COUNT	64
2728static int airo_networks_allocate(struct airo_info *ai)
2729{
2730	if (ai->networks)
2731		return 0;
2732
2733	ai->networks = kcalloc(AIRO_MAX_NETWORK_COUNT, sizeof(BSSListElement),
2734			       GFP_KERNEL);
2735	if (!ai->networks) {
2736		airo_print_warn("", "Out of memory allocating beacons");
2737		return -ENOMEM;
2738	}
2739
2740	return 0;
2741}
2742
2743static void airo_networks_free(struct airo_info *ai)
2744{
2745	kfree(ai->networks);
2746	ai->networks = NULL;
2747}
2748
2749static void airo_networks_initialize(struct airo_info *ai)
2750{
2751	int i;
2752
2753	INIT_LIST_HEAD(&ai->network_free_list);
2754	INIT_LIST_HEAD(&ai->network_list);
2755	for (i = 0; i < AIRO_MAX_NETWORK_COUNT; i++)
2756		list_add_tail(&ai->networks[i].list,
2757			      &ai->network_free_list);
2758}
2759
2760static const struct net_device_ops airo_netdev_ops = {
2761	.ndo_open		= airo_open,
2762	.ndo_stop		= airo_close,
2763	.ndo_start_xmit		= airo_start_xmit,
2764	.ndo_get_stats		= airo_get_stats,
2765	.ndo_set_rx_mode	= airo_set_multicast_list,
2766	.ndo_set_mac_address	= airo_set_mac_address,
2767	.ndo_do_ioctl		= airo_ioctl,
 
2768	.ndo_validate_addr	= eth_validate_addr,
2769};
2770
2771static const struct net_device_ops mpi_netdev_ops = {
2772	.ndo_open		= airo_open,
2773	.ndo_stop		= airo_close,
2774	.ndo_start_xmit		= mpi_start_xmit,
2775	.ndo_get_stats		= airo_get_stats,
2776	.ndo_set_rx_mode	= airo_set_multicast_list,
2777	.ndo_set_mac_address	= airo_set_mac_address,
2778	.ndo_do_ioctl		= airo_ioctl,
 
2779	.ndo_validate_addr	= eth_validate_addr,
2780};
2781
2782
2783static struct net_device *_init_airo_card(unsigned short irq, int port,
2784					   int is_pcmcia, struct pci_dev *pci,
2785					   struct device *dmdev)
2786{
2787	struct net_device *dev;
2788	struct airo_info *ai;
2789	int i, rc;
2790	CapabilityRid cap_rid;
2791
2792	/* Create the network device object. */
2793	dev = alloc_netdev(sizeof(*ai), "", NET_NAME_UNKNOWN, ether_setup);
2794	if (!dev) {
2795		airo_print_err("", "Couldn't alloc_etherdev");
2796		return NULL;
2797	}
2798
2799	ai = dev->ml_priv = netdev_priv(dev);
2800	ai->wifidev = NULL;
2801	ai->flags = 1 << FLAG_RADIO_DOWN;
2802	ai->jobs = 0;
2803	ai->dev = dev;
2804	if (pci && (pci->device == 0x5000 || pci->device == 0xa504)) {
2805		airo_print_dbg("", "Found an MPI350 card");
2806		set_bit(FLAG_MPI, &ai->flags);
2807	}
2808	spin_lock_init(&ai->aux_lock);
2809	sema_init(&ai->sem, 1);
2810	ai->config.len = 0;
2811	ai->pci = pci;
2812	init_waitqueue_head (&ai->thr_wait);
2813	ai->tfm = NULL;
2814	add_airo_dev(ai);
2815	ai->APList.len = cpu_to_le16(sizeof(struct APListRid));
2816
2817	if (airo_networks_allocate (ai))
2818		goto err_out_free;
2819	airo_networks_initialize (ai);
2820
2821	skb_queue_head_init (&ai->txq);
2822
2823	/* The Airo-specific entries in the device structure. */
2824	if (test_bit(FLAG_MPI,&ai->flags))
2825		dev->netdev_ops = &mpi_netdev_ops;
2826	else
2827		dev->netdev_ops = &airo_netdev_ops;
2828	dev->wireless_handlers = &airo_handler_def;
2829	ai->wireless_data.spy_data = &ai->spy_data;
2830	dev->wireless_data = &ai->wireless_data;
2831	dev->irq = irq;
2832	dev->base_addr = port;
2833	dev->priv_flags &= ~IFF_TX_SKB_SHARING;
2834	dev->max_mtu = MIC_MSGLEN_MAX;
2835
2836	SET_NETDEV_DEV(dev, dmdev);
2837
2838	reset_card (dev, 1);
2839	msleep(400);
2840
2841	if (!is_pcmcia) {
2842		if (!request_region(dev->base_addr, 64, DRV_NAME)) {
2843			rc = -EBUSY;
2844			airo_print_err(dev->name, "Couldn't request region");
2845			goto err_out_nets;
2846		}
2847	}
2848
2849	if (test_bit(FLAG_MPI,&ai->flags)) {
2850		if (mpi_map_card(ai, pci)) {
2851			airo_print_err("", "Could not map memory");
2852			goto err_out_res;
2853		}
2854	}
2855
2856	if (probe) {
2857		if (setup_card(ai, dev->dev_addr, 1) != SUCCESS) {
2858			airo_print_err(dev->name, "MAC could not be enabled");
2859			rc = -EIO;
2860			goto err_out_map;
2861		}
2862	} else if (!test_bit(FLAG_MPI,&ai->flags)) {
2863		ai->bap_read = fast_bap_read;
2864		set_bit(FLAG_FLASHING, &ai->flags);
2865	}
2866
2867	strcpy(dev->name, "eth%d");
2868	rc = register_netdev(dev);
2869	if (rc) {
2870		airo_print_err(dev->name, "Couldn't register_netdev");
2871		goto err_out_map;
2872	}
2873	ai->wifidev = init_wifidev(ai, dev);
2874	if (!ai->wifidev)
2875		goto err_out_reg;
2876
2877	rc = readCapabilityRid(ai, &cap_rid, 1);
2878	if (rc != SUCCESS) {
2879		rc = -EIO;
2880		goto err_out_wifi;
2881	}
2882	/* WEP capability discovery */
2883	ai->wep_capable = (cap_rid.softCap & cpu_to_le16(0x02)) ? 1 : 0;
2884	ai->max_wep_idx = (cap_rid.softCap & cpu_to_le16(0x80)) ? 3 : 0;
2885
2886	airo_print_info(dev->name, "Firmware version %x.%x.%02d",
2887	                ((le16_to_cpu(cap_rid.softVer) >> 8) & 0xF),
2888	                (le16_to_cpu(cap_rid.softVer) & 0xFF),
2889	                le16_to_cpu(cap_rid.softSubVer));
2890
2891	/* Test for WPA support */
2892	/* Only firmware versions 5.30.17 or better can do WPA */
2893	if (le16_to_cpu(cap_rid.softVer) > 0x530
2894	 || (le16_to_cpu(cap_rid.softVer) == 0x530
2895	      && le16_to_cpu(cap_rid.softSubVer) >= 17)) {
2896		airo_print_info(ai->dev->name, "WPA supported.");
2897
2898		set_bit(FLAG_WPA_CAPABLE, &ai->flags);
2899		ai->bssListFirst = RID_WPA_BSSLISTFIRST;
2900		ai->bssListNext = RID_WPA_BSSLISTNEXT;
2901		ai->bssListRidLen = sizeof(BSSListRid);
2902	} else {
2903		airo_print_info(ai->dev->name, "WPA unsupported with firmware "
2904			"versions older than 5.30.17.");
2905
2906		ai->bssListFirst = RID_BSSLISTFIRST;
2907		ai->bssListNext = RID_BSSLISTNEXT;
2908		ai->bssListRidLen = sizeof(BSSListRid) - sizeof(BSSListRidExtra);
2909	}
2910
2911	set_bit(FLAG_REGISTERED,&ai->flags);
2912	airo_print_info(dev->name, "MAC enabled %pM", dev->dev_addr);
2913
2914	/* Allocate the transmit buffers */
2915	if (probe && !test_bit(FLAG_MPI,&ai->flags))
2916		for (i = 0; i < MAX_FIDS; i++)
2917			ai->fids[i] = transmit_allocate(ai, AIRO_DEF_MTU, i>=MAX_FIDS/2);
2918
2919	if (setup_proc_entry(dev, dev->ml_priv) < 0)
2920		goto err_out_wifi;
2921
2922	return dev;
2923
2924err_out_wifi:
2925	unregister_netdev(ai->wifidev);
2926	free_netdev(ai->wifidev);
2927err_out_reg:
2928	unregister_netdev(dev);
2929err_out_map:
2930	if (test_bit(FLAG_MPI,&ai->flags) && pci) {
2931		dma_free_coherent(&pci->dev, PCI_SHARED_LEN, ai->shared,
2932				  ai->shared_dma);
2933		iounmap(ai->pciaux);
2934		iounmap(ai->pcimem);
2935		mpi_unmap_card(ai->pci);
2936	}
2937err_out_res:
2938	if (!is_pcmcia)
2939		release_region(dev->base_addr, 64);
2940err_out_nets:
2941	airo_networks_free(ai);
2942err_out_free:
2943	del_airo_dev(ai);
2944	free_netdev(dev);
2945	return NULL;
2946}
2947
2948struct net_device *init_airo_card(unsigned short irq, int port, int is_pcmcia,
2949				  struct device *dmdev)
2950{
2951	return _init_airo_card (irq, port, is_pcmcia, NULL, dmdev);
2952}
2953
2954EXPORT_SYMBOL(init_airo_card);
2955
2956static int waitbusy (struct airo_info *ai)
2957{
2958	int delay = 0;
2959	while ((IN4500(ai, COMMAND) & COMMAND_BUSY) && (delay < 10000)) {
2960		udelay (10);
2961		if ((++delay % 20) == 0)
2962			OUT4500(ai, EVACK, EV_CLEARCOMMANDBUSY);
2963	}
2964	return delay < 10000;
2965}
2966
2967int reset_airo_card(struct net_device *dev)
2968{
2969	int i;
2970	struct airo_info *ai = dev->ml_priv;
2971
2972	if (reset_card (dev, 1))
2973		return -1;
2974
2975	if (setup_card(ai, dev->dev_addr, 1) != SUCCESS) {
2976		airo_print_err(dev->name, "MAC could not be enabled");
2977		return -1;
2978	}
2979	airo_print_info(dev->name, "MAC enabled %pM", dev->dev_addr);
2980	/* Allocate the transmit buffers if needed */
2981	if (!test_bit(FLAG_MPI,&ai->flags))
2982		for (i = 0; i < MAX_FIDS; i++)
2983			ai->fids[i] = transmit_allocate (ai, AIRO_DEF_MTU, i>=MAX_FIDS/2);
2984
2985	enable_interrupts(ai);
2986	netif_wake_queue(dev);
2987	return 0;
2988}
2989
2990EXPORT_SYMBOL(reset_airo_card);
2991
2992static void airo_send_event(struct net_device *dev)
2993{
2994	struct airo_info *ai = dev->ml_priv;
2995	union iwreq_data wrqu;
2996	StatusRid status_rid;
2997
2998	clear_bit(JOB_EVENT, &ai->jobs);
2999	PC4500_readrid(ai, RID_STATUS, &status_rid, sizeof(status_rid), 0);
3000	up(&ai->sem);
3001	wrqu.data.length = 0;
3002	wrqu.data.flags = 0;
3003	memcpy(wrqu.ap_addr.sa_data, status_rid.bssid[0], ETH_ALEN);
3004	wrqu.ap_addr.sa_family = ARPHRD_ETHER;
3005
3006	/* Send event to user space */
3007	wireless_send_event(dev, SIOCGIWAP, &wrqu, NULL);
3008}
3009
3010static void airo_process_scan_results (struct airo_info *ai)
3011{
3012	union iwreq_data	wrqu;
3013	BSSListRid bss;
3014	int rc;
3015	BSSListElement * loop_net;
3016	BSSListElement * tmp_net;
3017
3018	/* Blow away current list of scan results */
3019	list_for_each_entry_safe (loop_net, tmp_net, &ai->network_list, list) {
3020		list_move_tail (&loop_net->list, &ai->network_free_list);
3021		/* Don't blow away ->list, just BSS data */
3022		memset (loop_net, 0, sizeof (loop_net->bss));
3023	}
3024
3025	/* Try to read the first entry of the scan result */
3026	rc = PC4500_readrid(ai, ai->bssListFirst, &bss, ai->bssListRidLen, 0);
3027	if ((rc) || (bss.index == cpu_to_le16(0xffff))) {
3028		/* No scan results */
3029		goto out;
3030	}
3031
3032	/* Read and parse all entries */
3033	tmp_net = NULL;
3034	while ((!rc) && (bss.index != cpu_to_le16(0xffff))) {
3035		/* Grab a network off the free list */
3036		if (!list_empty(&ai->network_free_list)) {
3037			tmp_net = list_entry(ai->network_free_list.next,
3038					    BSSListElement, list);
3039			list_del(ai->network_free_list.next);
3040		}
3041
3042		if (tmp_net != NULL) {
3043			memcpy(tmp_net, &bss, sizeof(tmp_net->bss));
3044			list_add_tail(&tmp_net->list, &ai->network_list);
3045			tmp_net = NULL;
3046		}
3047
3048		/* Read next entry */
3049		rc = PC4500_readrid(ai, ai->bssListNext,
3050				    &bss, ai->bssListRidLen, 0);
3051	}
3052
3053out:
3054	/* write APList back (we cleared it in airo_set_scan) */
3055	disable_MAC(ai, 2);
3056	writeAPListRid(ai, &ai->APList, 0);
3057	enable_MAC(ai, 0);
3058
3059	ai->scan_timeout = 0;
3060	clear_bit(JOB_SCAN_RESULTS, &ai->jobs);
3061	up(&ai->sem);
3062
3063	/* Send an empty event to user space.
3064	 * We don't send the received data on
3065	 * the event because it would require
3066	 * us to do complex transcoding, and
3067	 * we want to minimise the work done in
3068	 * the irq handler. Use a request to
3069	 * extract the data - Jean II */
3070	wrqu.data.length = 0;
3071	wrqu.data.flags = 0;
3072	wireless_send_event(ai->dev, SIOCGIWSCAN, &wrqu, NULL);
3073}
3074
3075static int airo_thread(void *data)
3076{
3077	struct net_device *dev = data;
3078	struct airo_info *ai = dev->ml_priv;
3079	int locked;
3080
3081	set_freezable();
3082	while (1) {
3083		/* make swsusp happy with our thread */
3084		try_to_freeze();
3085
3086		if (test_bit(JOB_DIE, &ai->jobs))
3087			break;
3088
3089		if (ai->jobs) {
3090			locked = down_interruptible(&ai->sem);
3091		} else {
3092			wait_queue_entry_t wait;
3093
3094			init_waitqueue_entry(&wait, current);
3095			add_wait_queue(&ai->thr_wait, &wait);
3096			for (;;) {
3097				set_current_state(TASK_INTERRUPTIBLE);
3098				if (ai->jobs)
3099					break;
3100				if (ai->expires || ai->scan_timeout) {
3101					if (ai->scan_timeout &&
3102							time_after_eq(jiffies, ai->scan_timeout)) {
3103						set_bit(JOB_SCAN_RESULTS, &ai->jobs);
3104						break;
3105					} else if (ai->expires &&
3106							time_after_eq(jiffies, ai->expires)) {
3107						set_bit(JOB_AUTOWEP, &ai->jobs);
3108						break;
3109					}
3110					if (!kthread_should_stop() &&
3111					    !freezing(current)) {
3112						unsigned long wake_at;
3113						if (!ai->expires || !ai->scan_timeout) {
3114							wake_at = max(ai->expires,
3115								ai->scan_timeout);
3116						} else {
3117							wake_at = min(ai->expires,
3118								ai->scan_timeout);
3119						}
3120						schedule_timeout(wake_at - jiffies);
3121						continue;
3122					}
3123				} else if (!kthread_should_stop() &&
3124					   !freezing(current)) {
3125					schedule();
3126					continue;
3127				}
3128				break;
3129			}
3130			__set_current_state(TASK_RUNNING);
3131			remove_wait_queue(&ai->thr_wait, &wait);
3132			locked = 1;
3133		}
3134
3135		if (locked)
3136			continue;
3137
3138		if (test_bit(JOB_DIE, &ai->jobs)) {
3139			up(&ai->sem);
3140			break;
3141		}
3142
3143		if (ai->power.event || test_bit(FLAG_FLASHING, &ai->flags)) {
3144			up(&ai->sem);
3145			continue;
3146		}
3147
3148		if (test_bit(JOB_XMIT, &ai->jobs))
3149			airo_end_xmit(dev, true);
3150		else if (test_bit(JOB_XMIT11, &ai->jobs))
3151			airo_end_xmit11(dev, true);
3152		else if (test_bit(JOB_STATS, &ai->jobs))
3153			airo_read_stats(dev);
 
 
3154		else if (test_bit(JOB_PROMISC, &ai->jobs))
3155			airo_set_promisc(ai, true);
3156		else if (test_bit(JOB_MIC, &ai->jobs))
3157			micinit(ai);
3158		else if (test_bit(JOB_EVENT, &ai->jobs))
3159			airo_send_event(dev);
3160		else if (test_bit(JOB_AUTOWEP, &ai->jobs))
3161			timer_func(dev);
3162		else if (test_bit(JOB_SCAN_RESULTS, &ai->jobs))
3163			airo_process_scan_results(ai);
3164		else  /* Shouldn't get here, but we make sure to unlock */
3165			up(&ai->sem);
3166	}
3167
3168	return 0;
3169}
3170
3171static int header_len(__le16 ctl)
3172{
3173	u16 fc = le16_to_cpu(ctl);
3174	switch (fc & 0xc) {
3175	case 4:
3176		if ((fc & 0xe0) == 0xc0)
3177			return 10;	/* one-address control packet */
3178		return 16;	/* two-address control packet */
3179	case 8:
3180		if ((fc & 0x300) == 0x300)
3181			return 30;	/* WDS packet */
3182	}
3183	return 24;
3184}
3185
3186static void airo_handle_cisco_mic(struct airo_info *ai)
3187{
3188	if (test_bit(FLAG_MIC_CAPABLE, &ai->flags)) {
3189		set_bit(JOB_MIC, &ai->jobs);
3190		wake_up_interruptible(&ai->thr_wait);
3191	}
3192}
3193
3194/* Airo Status codes */
3195#define STAT_NOBEACON	0x8000 /* Loss of sync - missed beacons */
3196#define STAT_MAXRETRIES	0x8001 /* Loss of sync - max retries */
3197#define STAT_MAXARL	0x8002 /* Loss of sync - average retry level exceeded*/
3198#define STAT_FORCELOSS	0x8003 /* Loss of sync - host request */
3199#define STAT_TSFSYNC	0x8004 /* Loss of sync - TSF synchronization */
3200#define STAT_DEAUTH	0x8100 /* low byte is 802.11 reason code */
3201#define STAT_DISASSOC	0x8200 /* low byte is 802.11 reason code */
3202#define STAT_ASSOC_FAIL	0x8400 /* low byte is 802.11 reason code */
3203#define STAT_AUTH_FAIL	0x0300 /* low byte is 802.11 reason code */
3204#define STAT_ASSOC	0x0400 /* Associated */
3205#define STAT_REASSOC    0x0600 /* Reassociated?  Only on firmware >= 5.30.17 */
3206
3207static void airo_print_status(const char *devname, u16 status)
3208{
3209	u8 reason = status & 0xFF;
3210
3211	switch (status & 0xFF00) {
3212	case STAT_NOBEACON:
3213		switch (status) {
3214		case STAT_NOBEACON:
3215			airo_print_dbg(devname, "link lost (missed beacons)");
3216			break;
3217		case STAT_MAXRETRIES:
3218		case STAT_MAXARL:
3219			airo_print_dbg(devname, "link lost (max retries)");
3220			break;
3221		case STAT_FORCELOSS:
3222			airo_print_dbg(devname, "link lost (local choice)");
3223			break;
3224		case STAT_TSFSYNC:
3225			airo_print_dbg(devname, "link lost (TSF sync lost)");
3226			break;
3227		default:
3228			airo_print_dbg(devname, "unknown status %x\n", status);
3229			break;
3230		}
3231		break;
3232	case STAT_DEAUTH:
3233		airo_print_dbg(devname, "deauthenticated (reason: %d)", reason);
3234		break;
3235	case STAT_DISASSOC:
3236		airo_print_dbg(devname, "disassociated (reason: %d)", reason);
3237		break;
3238	case STAT_ASSOC_FAIL:
3239		airo_print_dbg(devname, "association failed (reason: %d)",
3240			       reason);
3241		break;
3242	case STAT_AUTH_FAIL:
3243		airo_print_dbg(devname, "authentication failed (reason: %d)",
3244			       reason);
3245		break;
3246	case STAT_ASSOC:
3247	case STAT_REASSOC:
3248		break;
3249	default:
3250		airo_print_dbg(devname, "unknown status %x\n", status);
3251		break;
3252	}
3253}
3254
3255static void airo_handle_link(struct airo_info *ai)
3256{
3257	union iwreq_data wrqu;
3258	int scan_forceloss = 0;
3259	u16 status;
3260
3261	/* Get new status and acknowledge the link change */
3262	status = le16_to_cpu(IN4500(ai, LINKSTAT));
3263	OUT4500(ai, EVACK, EV_LINK);
3264
3265	if ((status == STAT_FORCELOSS) && (ai->scan_timeout > 0))
3266		scan_forceloss = 1;
3267
3268	airo_print_status(ai->dev->name, status);
3269
3270	if ((status == STAT_ASSOC) || (status == STAT_REASSOC)) {
3271		if (auto_wep)
3272			ai->expires = 0;
3273		if (ai->list_bss_task)
3274			wake_up_process(ai->list_bss_task);
3275		set_bit(FLAG_UPDATE_UNI, &ai->flags);
3276		set_bit(FLAG_UPDATE_MULTI, &ai->flags);
3277
3278		set_bit(JOB_EVENT, &ai->jobs);
3279		wake_up_interruptible(&ai->thr_wait);
3280
 
 
3281		netif_carrier_on(ai->dev);
3282	} else if (!scan_forceloss) {
3283		if (auto_wep && !ai->expires) {
3284			ai->expires = RUN_AT(3*HZ);
3285			wake_up_interruptible(&ai->thr_wait);
3286		}
3287
3288		/* Send event to user space */
3289		eth_zero_addr(wrqu.ap_addr.sa_data);
3290		wrqu.ap_addr.sa_family = ARPHRD_ETHER;
3291		wireless_send_event(ai->dev, SIOCGIWAP, &wrqu, NULL);
3292		netif_carrier_off(ai->dev);
3293	} else {
3294		netif_carrier_off(ai->dev);
3295	}
3296}
3297
3298static void airo_handle_rx(struct airo_info *ai)
3299{
3300	struct sk_buff *skb = NULL;
3301	__le16 fc, v, *buffer, tmpbuf[4];
3302	u16 len, hdrlen = 0, gap, fid;
3303	struct rx_hdr hdr;
3304	int success = 0;
3305
3306	if (test_bit(FLAG_MPI, &ai->flags)) {
3307		if (test_bit(FLAG_802_11, &ai->flags))
3308			mpi_receive_802_11(ai);
3309		else
3310			mpi_receive_802_3(ai);
3311		OUT4500(ai, EVACK, EV_RX);
3312		return;
3313	}
3314
3315	fid = IN4500(ai, RXFID);
3316
3317	/* Get the packet length */
3318	if (test_bit(FLAG_802_11, &ai->flags)) {
3319		bap_setup (ai, fid, 4, BAP0);
3320		bap_read (ai, (__le16*)&hdr, sizeof(hdr), BAP0);
3321		/* Bad CRC. Ignore packet */
3322		if (le16_to_cpu(hdr.status) & 2)
3323			hdr.len = 0;
3324		if (ai->wifidev == NULL)
3325			hdr.len = 0;
3326	} else {
3327		bap_setup(ai, fid, 0x36, BAP0);
3328		bap_read(ai, &hdr.len, 2, BAP0);
3329	}
3330	len = le16_to_cpu(hdr.len);
3331
3332	if (len > AIRO_DEF_MTU) {
3333		airo_print_err(ai->dev->name, "Bad size %d", len);
3334		goto done;
3335	}
3336	if (len == 0)
3337		goto done;
3338
3339	if (test_bit(FLAG_802_11, &ai->flags)) {
3340		bap_read(ai, &fc, sizeof (fc), BAP0);
3341		hdrlen = header_len(fc);
3342	} else
3343		hdrlen = ETH_ALEN * 2;
3344
3345	skb = dev_alloc_skb(len + hdrlen + 2 + 2);
3346	if (!skb) {
3347		ai->dev->stats.rx_dropped++;
3348		goto done;
3349	}
3350
3351	skb_reserve(skb, 2); /* This way the IP header is aligned */
3352	buffer = skb_put(skb, len + hdrlen);
3353	if (test_bit(FLAG_802_11, &ai->flags)) {
3354		buffer[0] = fc;
3355		bap_read(ai, buffer + 1, hdrlen - 2, BAP0);
3356		if (hdrlen == 24)
3357			bap_read(ai, tmpbuf, 6, BAP0);
3358
3359		bap_read(ai, &v, sizeof(v), BAP0);
3360		gap = le16_to_cpu(v);
3361		if (gap) {
3362			if (gap <= 8) {
3363				bap_read(ai, tmpbuf, gap, BAP0);
3364			} else {
3365				airo_print_err(ai->dev->name, "gaplen too "
3366					"big. Problems will follow...");
3367			}
3368		}
3369		bap_read(ai, buffer + hdrlen/2, len, BAP0);
3370	} else {
3371		MICBuffer micbuf;
3372
3373		bap_read(ai, buffer, ETH_ALEN * 2, BAP0);
3374		if (ai->micstats.enabled) {
3375			bap_read(ai, (__le16 *) &micbuf, sizeof (micbuf), BAP0);
3376			if (ntohs(micbuf.typelen) > 0x05DC)
3377				bap_setup(ai, fid, 0x44, BAP0);
3378			else {
3379				if (len <= sizeof (micbuf)) {
3380					dev_kfree_skb_irq(skb);
3381					goto done;
3382				}
3383
3384				len -= sizeof(micbuf);
3385				skb_trim(skb, len + hdrlen);
3386			}
3387		}
3388
3389		bap_read(ai, buffer + ETH_ALEN, len, BAP0);
3390		if (decapsulate(ai, &micbuf, (etherHead*) buffer, len))
3391			dev_kfree_skb_irq (skb);
3392		else
3393			success = 1;
3394	}
3395
3396#ifdef WIRELESS_SPY
3397	if (success && (ai->spy_data.spy_number > 0)) {
3398		char *sa;
3399		struct iw_quality wstats;
3400
3401		/* Prepare spy data : addr + qual */
3402		if (!test_bit(FLAG_802_11, &ai->flags)) {
3403			sa = (char *) buffer + 6;
3404			bap_setup(ai, fid, 8, BAP0);
3405			bap_read(ai, (__le16 *) hdr.rssi, 2, BAP0);
3406		} else
3407			sa = (char *) buffer + 10;
3408		wstats.qual = hdr.rssi[0];
3409		if (ai->rssi)
3410			wstats.level = 0x100 - ai->rssi[hdr.rssi[1]].rssidBm;
3411		else
3412			wstats.level = (hdr.rssi[1] + 321) / 2;
3413		wstats.noise = ai->wstats.qual.noise;
3414		wstats.updated =  IW_QUAL_LEVEL_UPDATED
3415				| IW_QUAL_QUAL_UPDATED
3416				| IW_QUAL_DBM;
3417		/* Update spy records */
3418		wireless_spy_update(ai->dev, sa, &wstats);
3419	}
3420#endif /* WIRELESS_SPY */
3421
3422done:
3423	OUT4500(ai, EVACK, EV_RX);
3424
3425	if (success) {
3426		if (test_bit(FLAG_802_11, &ai->flags)) {
3427			skb_reset_mac_header(skb);
3428			skb->pkt_type = PACKET_OTHERHOST;
3429			skb->dev = ai->wifidev;
3430			skb->protocol = htons(ETH_P_802_2);
3431		} else
3432			skb->protocol = eth_type_trans(skb, ai->dev);
3433		skb->ip_summed = CHECKSUM_NONE;
3434
3435		netif_rx(skb);
3436	}
3437}
3438
3439static void airo_handle_tx(struct airo_info *ai, u16 status)
3440{
3441	int i, index = -1;
3442	u16 fid;
3443
3444	if (test_bit(FLAG_MPI, &ai->flags)) {
3445		unsigned long flags;
3446
3447		if (status & EV_TXEXC)
3448			get_tx_error(ai, -1);
3449
3450		spin_lock_irqsave(&ai->aux_lock, flags);
3451		if (!skb_queue_empty(&ai->txq)) {
3452			spin_unlock_irqrestore(&ai->aux_lock, flags);
3453			mpi_send_packet(ai->dev);
3454		} else {
3455			clear_bit(FLAG_PENDING_XMIT, &ai->flags);
3456			spin_unlock_irqrestore(&ai->aux_lock, flags);
3457			netif_wake_queue(ai->dev);
3458		}
3459		OUT4500(ai, EVACK, status & (EV_TX | EV_TXCPY | EV_TXEXC));
3460		return;
3461	}
3462
3463	fid = IN4500(ai, TXCOMPLFID);
3464
3465	for (i = 0; i < MAX_FIDS; i++) {
3466		if ((ai->fids[i] & 0xffff) == fid)
 
3467			index = i;
 
3468	}
3469
3470	if (index != -1) {
3471		if (status & EV_TXEXC)
3472			get_tx_error(ai, index);
3473
3474		OUT4500(ai, EVACK, status & (EV_TX | EV_TXEXC));
3475
3476		/* Set up to be used again */
3477		ai->fids[index] &= 0xffff;
3478		if (index < MAX_FIDS / 2) {
3479			if (!test_bit(FLAG_PENDING_XMIT, &ai->flags))
3480				netif_wake_queue(ai->dev);
3481		} else {
3482			if (!test_bit(FLAG_PENDING_XMIT11, &ai->flags))
3483				netif_wake_queue(ai->wifidev);
3484		}
3485	} else {
3486		OUT4500(ai, EVACK, status & (EV_TX | EV_TXCPY | EV_TXEXC));
3487		airo_print_err(ai->dev->name, "Unallocated FID was used to xmit");
3488	}
3489}
3490
3491static irqreturn_t airo_interrupt(int irq, void *dev_id)
3492{
3493	struct net_device *dev = dev_id;
3494	u16 status, savedInterrupts = 0;
3495	struct airo_info *ai = dev->ml_priv;
3496	int handled = 0;
3497
3498	if (!netif_device_present(dev))
3499		return IRQ_NONE;
3500
3501	for (;;) {
3502		status = IN4500(ai, EVSTAT);
3503		if (!(status & STATUS_INTS) || (status == 0xffff))
3504			break;
3505
3506		handled = 1;
3507
3508		if (status & EV_AWAKE) {
3509			OUT4500(ai, EVACK, EV_AWAKE);
3510			OUT4500(ai, EVACK, EV_AWAKE);
3511		}
3512
3513		if (!savedInterrupts) {
3514			savedInterrupts = IN4500(ai, EVINTEN);
3515			OUT4500(ai, EVINTEN, 0);
3516		}
3517
3518		if (status & EV_MIC) {
3519			OUT4500(ai, EVACK, EV_MIC);
3520			airo_handle_cisco_mic(ai);
3521		}
3522
3523		if (status & EV_LINK) {
3524			/* Link status changed */
3525			airo_handle_link(ai);
3526		}
3527
3528		/* Check to see if there is something to receive */
3529		if (status & EV_RX)
3530			airo_handle_rx(ai);
3531
3532		/* Check to see if a packet has been transmitted */
3533		if (status & (EV_TX | EV_TXCPY | EV_TXEXC))
3534			airo_handle_tx(ai, status);
3535
3536		if (status & ~STATUS_INTS & ~IGNORE_INTS) {
3537			airo_print_warn(ai->dev->name, "Got weird status %x",
3538				status & ~STATUS_INTS & ~IGNORE_INTS);
3539		}
3540	}
3541
3542	if (savedInterrupts)
3543		OUT4500(ai, EVINTEN, savedInterrupts);
3544
3545	return IRQ_RETVAL(handled);
3546}
3547
3548/*
3549 *  Routines to talk to the card
3550 */
3551
3552/*
3553 *  This was originally written for the 4500, hence the name
3554 *  NOTE:  If use with 8bit mode and SMP bad things will happen!
3555 *         Why would some one do 8 bit IO in an SMP machine?!?
3556 */
3557static void OUT4500(struct airo_info *ai, u16 reg, u16 val)
3558{
3559	if (test_bit(FLAG_MPI,&ai->flags))
3560		reg <<= 1;
3561	if (!do8bitIO)
3562		outw(val, ai->dev->base_addr + reg);
3563	else {
3564		outb(val & 0xff, ai->dev->base_addr + reg);
3565		outb(val >> 8, ai->dev->base_addr + reg + 1);
3566	}
3567}
3568
3569static u16 IN4500(struct airo_info *ai, u16 reg)
3570{
3571	unsigned short rc;
3572
3573	if (test_bit(FLAG_MPI,&ai->flags))
3574		reg <<= 1;
3575	if (!do8bitIO)
3576		rc = inw(ai->dev->base_addr + reg);
3577	else {
3578		rc = inb(ai->dev->base_addr + reg);
3579		rc += ((int)inb(ai->dev->base_addr + reg + 1)) << 8;
3580	}
3581	return rc;
3582}
3583
3584static int enable_MAC(struct airo_info *ai, int lock)
3585{
3586	int rc;
3587	Cmd cmd;
3588	Resp rsp;
3589
3590	/* FLAG_RADIO_OFF : Radio disabled via /proc or Wireless Extensions
3591	 * FLAG_RADIO_DOWN : Radio disabled via "ifconfig ethX down"
3592	 * Note : we could try to use !netif_running(dev) in enable_MAC()
3593	 * instead of this flag, but I don't trust it *within* the
3594	 * open/close functions, and testing both flags together is
3595	 * "cheaper" - Jean II */
3596	if (ai->flags & FLAG_RADIO_MASK) return SUCCESS;
3597
3598	if (lock && down_interruptible(&ai->sem))
3599		return -ERESTARTSYS;
3600
3601	if (!test_bit(FLAG_ENABLED, &ai->flags)) {
3602		memset(&cmd, 0, sizeof(cmd));
3603		cmd.cmd = MAC_ENABLE;
3604		rc = issuecommand(ai, &cmd, &rsp, true);
3605		if (rc == SUCCESS)
3606			set_bit(FLAG_ENABLED, &ai->flags);
3607	} else
3608		rc = SUCCESS;
3609
3610	if (lock)
3611	    up(&ai->sem);
3612
3613	if (rc)
3614		airo_print_err(ai->dev->name, "Cannot enable MAC");
3615	else if ((rsp.status & 0xFF00) != 0) {
3616		airo_print_err(ai->dev->name, "Bad MAC enable reason=%x, "
3617			"rid=%x, offset=%d", rsp.rsp0, rsp.rsp1, rsp.rsp2);
3618		rc = ERROR;
3619	}
3620	return rc;
3621}
3622
3623static void disable_MAC(struct airo_info *ai, int lock)
3624{
3625        Cmd cmd;
3626	Resp rsp;
3627
3628	if (lock == 1 && down_interruptible(&ai->sem))
3629		return;
3630
3631	if (test_bit(FLAG_ENABLED, &ai->flags)) {
3632		if (lock != 2) /* lock == 2 means don't disable carrier */
3633			netif_carrier_off(ai->dev);
3634		memset(&cmd, 0, sizeof(cmd));
3635		cmd.cmd = MAC_DISABLE; // disable in case already enabled
3636		issuecommand(ai, &cmd, &rsp, true);
3637		clear_bit(FLAG_ENABLED, &ai->flags);
3638	}
3639	if (lock == 1)
3640		up(&ai->sem);
3641}
3642
3643static void enable_interrupts(struct airo_info *ai)
3644{
3645	/* Enable the interrupts */
3646	OUT4500(ai, EVINTEN, STATUS_INTS);
3647}
3648
3649static void disable_interrupts(struct airo_info *ai)
3650{
3651	OUT4500(ai, EVINTEN, 0);
3652}
3653
3654static void mpi_receive_802_3(struct airo_info *ai)
3655{
3656	RxFid rxd;
3657	int len = 0;
3658	struct sk_buff *skb;
3659	char *buffer;
3660	int off = 0;
3661	MICBuffer micbuf;
3662
3663	memcpy_fromio(&rxd, ai->rxfids[0].card_ram_off, sizeof(rxd));
3664	/* Make sure we got something */
3665	if (rxd.rdy && rxd.valid == 0) {
3666		len = rxd.len + 12;
3667		if (len < 12 || len > 2048)
3668			goto badrx;
3669
3670		skb = dev_alloc_skb(len);
3671		if (!skb) {
3672			ai->dev->stats.rx_dropped++;
3673			goto badrx;
3674		}
3675		buffer = skb_put(skb, len);
3676		memcpy(buffer, ai->rxfids[0].virtual_host_addr, ETH_ALEN * 2);
3677		if (ai->micstats.enabled) {
3678			memcpy(&micbuf,
3679				ai->rxfids[0].virtual_host_addr + ETH_ALEN * 2,
3680				sizeof(micbuf));
3681			if (ntohs(micbuf.typelen) <= 0x05DC) {
3682				if (len <= sizeof(micbuf) + ETH_ALEN * 2)
3683					goto badmic;
3684
3685				off = sizeof(micbuf);
3686				skb_trim (skb, len - off);
3687			}
3688		}
3689		memcpy(buffer + ETH_ALEN * 2,
3690			ai->rxfids[0].virtual_host_addr + ETH_ALEN * 2 + off,
3691			len - ETH_ALEN * 2 - off);
3692		if (decapsulate (ai, &micbuf, (etherHead*)buffer, len - off - ETH_ALEN * 2)) {
3693badmic:
3694			dev_kfree_skb_irq (skb);
3695			goto badrx;
3696		}
3697#ifdef WIRELESS_SPY
3698		if (ai->spy_data.spy_number > 0) {
3699			char *sa;
3700			struct iw_quality wstats;
3701			/* Prepare spy data : addr + qual */
3702			sa = buffer + ETH_ALEN;
3703			wstats.qual = 0; /* XXX Where do I get that info from ??? */
3704			wstats.level = 0;
3705			wstats.updated = 0;
3706			/* Update spy records */
3707			wireless_spy_update(ai->dev, sa, &wstats);
3708		}
3709#endif /* WIRELESS_SPY */
3710
3711		skb->ip_summed = CHECKSUM_NONE;
3712		skb->protocol = eth_type_trans(skb, ai->dev);
3713		netif_rx(skb);
3714	}
3715badrx:
3716	if (rxd.valid == 0) {
3717		rxd.valid = 1;
3718		rxd.rdy = 0;
3719		rxd.len = PKTSIZE;
3720		memcpy_toio(ai->rxfids[0].card_ram_off, &rxd, sizeof(rxd));
3721	}
3722}
3723
3724static void mpi_receive_802_11(struct airo_info *ai)
3725{
3726	RxFid rxd;
3727	struct sk_buff *skb = NULL;
3728	u16 len, hdrlen = 0;
3729	__le16 fc;
3730	struct rx_hdr hdr;
3731	u16 gap;
3732	u16 *buffer;
3733	char *ptr = ai->rxfids[0].virtual_host_addr + 4;
3734
3735	memcpy_fromio(&rxd, ai->rxfids[0].card_ram_off, sizeof(rxd));
3736	memcpy ((char *)&hdr, ptr, sizeof(hdr));
3737	ptr += sizeof(hdr);
3738	/* Bad CRC. Ignore packet */
3739	if (le16_to_cpu(hdr.status) & 2)
3740		hdr.len = 0;
3741	if (ai->wifidev == NULL)
3742		hdr.len = 0;
3743	len = le16_to_cpu(hdr.len);
3744	if (len > AIRO_DEF_MTU) {
3745		airo_print_err(ai->dev->name, "Bad size %d", len);
3746		goto badrx;
3747	}
3748	if (len == 0)
3749		goto badrx;
3750
3751	fc = get_unaligned((__le16 *)ptr);
3752	hdrlen = header_len(fc);
3753
3754	skb = dev_alloc_skb(len + hdrlen + 2);
3755	if (!skb) {
3756		ai->dev->stats.rx_dropped++;
3757		goto badrx;
3758	}
3759	buffer = skb_put(skb, len + hdrlen);
3760	memcpy ((char *)buffer, ptr, hdrlen);
3761	ptr += hdrlen;
3762	if (hdrlen == 24)
3763		ptr += 6;
3764	gap = get_unaligned_le16(ptr);
3765	ptr += sizeof(__le16);
3766	if (gap) {
3767		if (gap <= 8)
3768			ptr += gap;
3769		else
3770			airo_print_err(ai->dev->name,
3771			    "gaplen too big. Problems will follow...");
3772	}
3773	memcpy ((char *)buffer + hdrlen, ptr, len);
3774	ptr += len;
3775#ifdef IW_WIRELESS_SPY	  /* defined in iw_handler.h */
3776	if (ai->spy_data.spy_number > 0) {
3777		char *sa;
3778		struct iw_quality wstats;
3779		/* Prepare spy data : addr + qual */
3780		sa = (char*)buffer + 10;
3781		wstats.qual = hdr.rssi[0];
3782		if (ai->rssi)
3783			wstats.level = 0x100 - ai->rssi[hdr.rssi[1]].rssidBm;
3784		else
3785			wstats.level = (hdr.rssi[1] + 321) / 2;
3786		wstats.noise = ai->wstats.qual.noise;
3787		wstats.updated = IW_QUAL_QUAL_UPDATED
3788			| IW_QUAL_LEVEL_UPDATED
3789			| IW_QUAL_DBM;
3790		/* Update spy records */
3791		wireless_spy_update(ai->dev, sa, &wstats);
3792	}
3793#endif /* IW_WIRELESS_SPY */
3794	skb_reset_mac_header(skb);
3795	skb->pkt_type = PACKET_OTHERHOST;
3796	skb->dev = ai->wifidev;
3797	skb->protocol = htons(ETH_P_802_2);
3798	skb->ip_summed = CHECKSUM_NONE;
3799	netif_rx(skb);
3800
3801badrx:
3802	if (rxd.valid == 0) {
3803		rxd.valid = 1;
3804		rxd.rdy = 0;
3805		rxd.len = PKTSIZE;
3806		memcpy_toio(ai->rxfids[0].card_ram_off, &rxd, sizeof(rxd));
3807	}
3808}
3809
3810static inline void set_auth_type(struct airo_info *local, int auth_type)
3811{
3812	local->config.authType = auth_type;
3813	/* Cache the last auth type used (of AUTH_OPEN and AUTH_ENCRYPT).
3814	 * Used by airo_set_auth()
3815	 */
3816	if (auth_type == AUTH_OPEN || auth_type == AUTH_ENCRYPT)
3817		local->last_auth = auth_type;
3818}
3819
3820static int noinline_for_stack airo_readconfig(struct airo_info *ai, u8 *mac, int lock)
3821{
3822	int i, status;
3823	/* large variables, so don't inline this function,
3824	 * maybe change to kmalloc
3825	 */
3826	tdsRssiRid rssi_rid;
3827	CapabilityRid cap_rid;
3828
3829	kfree(ai->SSID);
3830	ai->SSID = NULL;
3831	// general configuration (read/modify/write)
3832	status = readConfigRid(ai, lock);
3833	if (status != SUCCESS) return ERROR;
3834
3835	status = readCapabilityRid(ai, &cap_rid, lock);
3836	if (status != SUCCESS) return ERROR;
3837
3838	status = PC4500_readrid(ai, RID_RSSI, &rssi_rid, sizeof(rssi_rid), lock);
3839	if (status == SUCCESS) {
3840		if (ai->rssi || (ai->rssi = kmalloc(512, GFP_KERNEL)) != NULL)
3841			memcpy(ai->rssi, (u8*)&rssi_rid + 2, 512); /* Skip RID length member */
3842	}
3843	else {
3844		kfree(ai->rssi);
3845		ai->rssi = NULL;
3846		if (cap_rid.softCap & cpu_to_le16(8))
3847			ai->config.rmode |= RXMODE_NORMALIZED_RSSI;
3848		else
3849			airo_print_warn(ai->dev->name, "unknown received signal "
3850					"level scale");
3851	}
3852	ai->config.opmode = adhoc ? MODE_STA_IBSS : MODE_STA_ESS;
3853	set_auth_type(ai, AUTH_OPEN);
3854	ai->config.modulation = MOD_CCK;
3855
3856	if (le16_to_cpu(cap_rid.len) >= sizeof(cap_rid) &&
3857	    (cap_rid.extSoftCap & cpu_to_le16(1)) &&
3858	    micsetup(ai) == SUCCESS) {
3859		ai->config.opmode |= MODE_MIC;
3860		set_bit(FLAG_MIC_CAPABLE, &ai->flags);
3861	}
3862
3863	/* Save off the MAC */
3864	for (i = 0; i < ETH_ALEN; i++) {
3865		mac[i] = ai->config.macAddr[i];
3866	}
3867
3868	/* Check to see if there are any insmod configured
3869	   rates to add */
3870	if (rates[0]) {
3871		memset(ai->config.rates, 0, sizeof(ai->config.rates));
3872		for (i = 0; i < 8 && rates[i]; i++) {
3873			ai->config.rates[i] = rates[i];
3874		}
3875	}
3876	set_bit (FLAG_COMMIT, &ai->flags);
3877
3878	return SUCCESS;
3879}
3880
3881
3882static u16 setup_card(struct airo_info *ai, u8 *mac, int lock)
3883{
3884	Cmd cmd;
3885	Resp rsp;
3886	int status;
3887	SsidRid mySsid;
3888	__le16 lastindex;
3889	WepKeyRid wkr;
3890	int rc;
3891
3892	memset(&mySsid, 0, sizeof(mySsid));
3893	kfree (ai->flash);
3894	ai->flash = NULL;
3895
3896	/* The NOP is the first step in getting the card going */
3897	cmd.cmd = NOP;
3898	cmd.parm0 = cmd.parm1 = cmd.parm2 = 0;
3899	if (lock && down_interruptible(&ai->sem))
3900		return ERROR;
3901	if (issuecommand(ai, &cmd, &rsp, true) != SUCCESS) {
3902		if (lock)
3903			up(&ai->sem);
3904		return ERROR;
3905	}
3906	disable_MAC(ai, 0);
3907
3908	// Let's figure out if we need to use the AUX port
3909	if (!test_bit(FLAG_MPI,&ai->flags)) {
3910		cmd.cmd = CMD_ENABLEAUX;
3911		if (issuecommand(ai, &cmd, &rsp, true) != SUCCESS) {
3912			if (lock)
3913				up(&ai->sem);
3914			airo_print_err(ai->dev->name, "Error checking for AUX port");
3915			return ERROR;
3916		}
3917		if (!aux_bap || rsp.status & 0xff00) {
3918			ai->bap_read = fast_bap_read;
3919			airo_print_dbg(ai->dev->name, "Doing fast bap_reads");
3920		} else {
3921			ai->bap_read = aux_bap_read;
3922			airo_print_dbg(ai->dev->name, "Doing AUX bap_reads");
3923		}
3924	}
3925	if (lock)
3926		up(&ai->sem);
3927	if (ai->config.len == 0) {
3928		status = airo_readconfig(ai, mac, lock);
3929		if (status != SUCCESS)
3930			return ERROR;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
3931	}
3932
3933	/* Setup the SSIDs if present */
3934	if (ssids[0]) {
3935		int i;
3936		for (i = 0; i < 3 && ssids[i]; i++) {
3937			size_t len = strlen(ssids[i]);
3938			if (len > 32)
3939				len = 32;
3940			mySsid.ssids[i].len = cpu_to_le16(len);
3941			memcpy(mySsid.ssids[i].ssid, ssids[i], len);
3942		}
3943		mySsid.len = cpu_to_le16(sizeof(mySsid));
3944	}
3945
3946	status = writeConfigRid(ai, lock);
3947	if (status != SUCCESS) return ERROR;
3948
3949	/* Set up the SSID list */
3950	if (ssids[0]) {
3951		status = writeSsidRid(ai, &mySsid, lock);
3952		if (status != SUCCESS) return ERROR;
3953	}
3954
3955	status = enable_MAC(ai, lock);
3956	if (status != SUCCESS)
3957		return ERROR;
3958
3959	/* Grab the initial wep key, we gotta save it for auto_wep */
3960	rc = readWepKeyRid(ai, &wkr, 1, lock);
3961	if (rc == SUCCESS) do {
3962		lastindex = wkr.kindex;
3963		if (wkr.kindex == cpu_to_le16(0xffff)) {
3964			ai->defindex = wkr.mac[0];
3965		}
3966		rc = readWepKeyRid(ai, &wkr, 0, lock);
3967	} while (lastindex != wkr.kindex);
3968
3969	try_auto_wep(ai);
3970
3971	return SUCCESS;
3972}
3973
3974static u16 issuecommand(struct airo_info *ai, Cmd *pCmd, Resp *pRsp,
3975			bool may_sleep)
3976{
3977        // Im really paranoid about letting it run forever!
3978	int max_tries = 600000;
3979
3980	if (IN4500(ai, EVSTAT) & EV_CMD)
3981		OUT4500(ai, EVACK, EV_CMD);
3982
3983	OUT4500(ai, PARAM0, pCmd->parm0);
3984	OUT4500(ai, PARAM1, pCmd->parm1);
3985	OUT4500(ai, PARAM2, pCmd->parm2);
3986	OUT4500(ai, COMMAND, pCmd->cmd);
3987
3988	while (max_tries-- && (IN4500(ai, EVSTAT) & EV_CMD) == 0) {
3989		if ((IN4500(ai, COMMAND)) == pCmd->cmd)
3990			// PC4500 didn't notice command, try again
3991			OUT4500(ai, COMMAND, pCmd->cmd);
3992		if (may_sleep && (max_tries & 255) == 0)
3993			cond_resched();
3994	}
3995
3996	if (max_tries == -1) {
3997		airo_print_err(ai->dev->name,
3998			"Max tries exceeded when issuing command");
3999		if (IN4500(ai, COMMAND) & COMMAND_BUSY)
4000			OUT4500(ai, EVACK, EV_CLEARCOMMANDBUSY);
4001		return ERROR;
4002	}
4003
4004	// command completed
4005	pRsp->status = IN4500(ai, STATUS);
4006	pRsp->rsp0 = IN4500(ai, RESP0);
4007	pRsp->rsp1 = IN4500(ai, RESP1);
4008	pRsp->rsp2 = IN4500(ai, RESP2);
4009	if ((pRsp->status & 0xff00)!=0 && pCmd->cmd != CMD_SOFTRESET)
4010		airo_print_err(ai->dev->name,
4011			"cmd:%x status:%x rsp0:%x rsp1:%x rsp2:%x",
4012			pCmd->cmd, pRsp->status, pRsp->rsp0, pRsp->rsp1,
4013			pRsp->rsp2);
4014
4015	// clear stuck command busy if necessary
4016	if (IN4500(ai, COMMAND) & COMMAND_BUSY) {
4017		OUT4500(ai, EVACK, EV_CLEARCOMMANDBUSY);
4018	}
4019	// acknowledge processing the status/response
4020	OUT4500(ai, EVACK, EV_CMD);
4021
4022	return SUCCESS;
4023}
4024
4025/* Sets up the bap to start exchange data.  whichbap should
4026 * be one of the BAP0 or BAP1 defines.  Locks should be held before
4027 * calling! */
4028static int bap_setup(struct airo_info *ai, u16 rid, u16 offset, int whichbap)
4029{
4030	int timeout = 50;
4031	int max_tries = 3;
4032
4033	OUT4500(ai, SELECT0+whichbap, rid);
4034	OUT4500(ai, OFFSET0+whichbap, offset);
4035	while (1) {
4036		int status = IN4500(ai, OFFSET0+whichbap);
4037		if (status & BAP_BUSY) {
4038                        /* This isn't really a timeout, but its kinda
4039			   close */
4040			if (timeout--) {
4041				continue;
4042			}
4043		} else if (status & BAP_ERR) {
4044			/* invalid rid or offset */
4045			airo_print_err(ai->dev->name, "BAP error %x %d",
4046				status, whichbap);
4047			return ERROR;
4048		} else if (status & BAP_DONE) { // success
4049			return SUCCESS;
4050		}
4051		if (!(max_tries--)) {
4052			airo_print_err(ai->dev->name,
4053				"BAP setup error too many retries\n");
4054			return ERROR;
4055		}
4056		// -- PC4500 missed it, try again
4057		OUT4500(ai, SELECT0+whichbap, rid);
4058		OUT4500(ai, OFFSET0+whichbap, offset);
4059		timeout = 50;
4060	}
4061}
4062
4063/* should only be called by aux_bap_read.  This aux function and the
4064   following use concepts not documented in the developers guide.  I
4065   got them from a patch given to my by Aironet */
4066static u16 aux_setup(struct airo_info *ai, u16 page,
4067		     u16 offset, u16 *len)
4068{
4069	u16 next;
4070
4071	OUT4500(ai, AUXPAGE, page);
4072	OUT4500(ai, AUXOFF, 0);
4073	next = IN4500(ai, AUXDATA);
4074	*len = IN4500(ai, AUXDATA)&0xff;
4075	if (offset != 4) OUT4500(ai, AUXOFF, offset);
4076	return next;
4077}
4078
4079/* requires call to bap_setup() first */
4080static int aux_bap_read(struct airo_info *ai, __le16 *pu16Dst,
4081			int bytelen, int whichbap)
4082{
4083	u16 len;
4084	u16 page;
4085	u16 offset;
4086	u16 next;
4087	int words;
4088	int i;
4089	unsigned long flags;
4090
4091	spin_lock_irqsave(&ai->aux_lock, flags);
4092	page = IN4500(ai, SWS0+whichbap);
4093	offset = IN4500(ai, SWS2+whichbap);
4094	next = aux_setup(ai, page, offset, &len);
4095	words = (bytelen+1)>>1;
4096
4097	for (i = 0; i<words;) {
4098		int count;
4099		count = (len>>1) < (words-i) ? (len>>1) : (words-i);
4100		if (!do8bitIO)
4101			insw(ai->dev->base_addr+DATA0+whichbap,
4102			      pu16Dst+i, count);
4103		else
4104			insb(ai->dev->base_addr+DATA0+whichbap,
4105			      pu16Dst+i, count << 1);
4106		i += count;
4107		if (i<words) {
4108			next = aux_setup(ai, next, 4, &len);
4109		}
4110	}
4111	spin_unlock_irqrestore(&ai->aux_lock, flags);
4112	return SUCCESS;
4113}
4114
4115
4116/* requires call to bap_setup() first */
4117static int fast_bap_read(struct airo_info *ai, __le16 *pu16Dst,
4118			 int bytelen, int whichbap)
4119{
4120	bytelen = (bytelen + 1) & (~1); // round up to even value
4121	if (!do8bitIO)
4122		insw(ai->dev->base_addr+DATA0+whichbap, pu16Dst, bytelen>>1);
4123	else
4124		insb(ai->dev->base_addr+DATA0+whichbap, pu16Dst, bytelen);
4125	return SUCCESS;
4126}
4127
4128/* requires call to bap_setup() first */
4129static int bap_write(struct airo_info *ai, const __le16 *pu16Src,
4130		     int bytelen, int whichbap)
4131{
4132	bytelen = (bytelen + 1) & (~1); // round up to even value
4133	if (!do8bitIO)
4134		outsw(ai->dev->base_addr+DATA0+whichbap,
4135		       pu16Src, bytelen>>1);
4136	else
4137		outsb(ai->dev->base_addr+DATA0+whichbap, pu16Src, bytelen);
4138	return SUCCESS;
4139}
4140
4141static int PC4500_accessrid(struct airo_info *ai, u16 rid, u16 accmd)
4142{
4143	Cmd cmd; /* for issuing commands */
4144	Resp rsp; /* response from commands */
4145	u16 status;
4146
4147	memset(&cmd, 0, sizeof(cmd));
4148	cmd.cmd = accmd;
4149	cmd.parm0 = rid;
4150	status = issuecommand(ai, &cmd, &rsp, true);
4151	if (status != 0) return status;
4152	if ((rsp.status & 0x7F00) != 0) {
4153		return (accmd << 8) + (rsp.rsp0 & 0xFF);
4154	}
4155	return 0;
4156}
4157
4158/*  Note, that we are using BAP1 which is also used by transmit, so
4159 *  we must get a lock. */
4160static int PC4500_readrid(struct airo_info *ai, u16 rid, void *pBuf, int len, int lock)
4161{
4162	u16 status;
4163        int rc = SUCCESS;
4164
4165	if (lock) {
4166		if (down_interruptible(&ai->sem))
4167			return ERROR;
4168	}
4169	if (test_bit(FLAG_MPI,&ai->flags)) {
4170		Cmd cmd;
4171		Resp rsp;
4172
4173		memset(&cmd, 0, sizeof(cmd));
4174		memset(&rsp, 0, sizeof(rsp));
4175		ai->config_desc.rid_desc.valid = 1;
4176		ai->config_desc.rid_desc.len = RIDSIZE;
4177		ai->config_desc.rid_desc.rid = 0;
4178		ai->config_desc.rid_desc.host_addr = ai->ridbus;
4179
4180		cmd.cmd = CMD_ACCESS;
4181		cmd.parm0 = rid;
4182
4183		memcpy_toio(ai->config_desc.card_ram_off,
4184			&ai->config_desc.rid_desc, sizeof(Rid));
4185
4186		rc = issuecommand(ai, &cmd, &rsp, true);
4187
4188		if (rsp.status & 0x7f00)
4189			rc = rsp.rsp0;
4190		if (!rc)
4191			memcpy(pBuf, ai->config_desc.virtual_host_addr, len);
4192		goto done;
4193	} else {
4194		if ((status = PC4500_accessrid(ai, rid, CMD_ACCESS))!=SUCCESS) {
4195	                rc = status;
4196	                goto done;
4197	        }
4198		if (bap_setup(ai, rid, 0, BAP1) != SUCCESS) {
4199			rc = ERROR;
4200	                goto done;
4201	        }
4202		// read the rid length field
4203		bap_read(ai, pBuf, 2, BAP1);
4204		// length for remaining part of rid
4205		len = min(len, (int)le16_to_cpu(*(__le16*)pBuf)) - 2;
4206
4207		if (len <= 2) {
4208			airo_print_err(ai->dev->name,
4209				"Rid %x has a length of %d which is too short",
4210				(int)rid, (int)len);
4211			rc = ERROR;
4212	                goto done;
4213		}
4214		// read remainder of the rid
4215		rc = bap_read(ai, ((__le16*)pBuf)+1, len, BAP1);
4216	}
4217done:
4218	if (lock)
4219		up(&ai->sem);
4220	return rc;
4221}
4222
4223/*  Note, that we are using BAP1 which is also used by transmit, so
4224 *  make sure this isn't called when a transmit is happening */
4225static int PC4500_writerid(struct airo_info *ai, u16 rid,
4226			   const void *pBuf, int len, int lock)
4227{
4228	u16 status;
4229	int rc = SUCCESS;
4230
4231	*(__le16*)pBuf = cpu_to_le16((u16)len);
4232
4233	if (lock) {
4234		if (down_interruptible(&ai->sem))
4235			return ERROR;
4236	}
4237	if (test_bit(FLAG_MPI,&ai->flags)) {
4238		Cmd cmd;
4239		Resp rsp;
4240
4241		if (test_bit(FLAG_ENABLED, &ai->flags) && (RID_WEP_TEMP != rid))
4242			airo_print_err(ai->dev->name,
4243				"%s: MAC should be disabled (rid=%04x)",
4244				__func__, rid);
4245		memset(&cmd, 0, sizeof(cmd));
4246		memset(&rsp, 0, sizeof(rsp));
4247
4248		ai->config_desc.rid_desc.valid = 1;
4249		ai->config_desc.rid_desc.len = *((u16 *)pBuf);
4250		ai->config_desc.rid_desc.rid = 0;
4251
4252		cmd.cmd = CMD_WRITERID;
4253		cmd.parm0 = rid;
4254
4255		memcpy_toio(ai->config_desc.card_ram_off,
4256			&ai->config_desc.rid_desc, sizeof(Rid));
4257
4258		if (len < 4 || len > 2047) {
4259			airo_print_err(ai->dev->name, "%s: len=%d", __func__, len);
4260			rc = -1;
4261		} else {
4262			memcpy(ai->config_desc.virtual_host_addr,
4263				pBuf, len);
4264
4265			rc = issuecommand(ai, &cmd, &rsp, true);
4266			if ((rc & 0xff00) != 0) {
4267				airo_print_err(ai->dev->name, "%s: Write rid Error %d",
4268						__func__, rc);
4269				airo_print_err(ai->dev->name, "%s: Cmd=%04x",
4270						__func__, cmd.cmd);
4271			}
4272
4273			if ((rsp.status & 0x7f00))
4274				rc = rsp.rsp0;
4275		}
4276	} else {
4277		// --- first access so that we can write the rid data
4278		if ((status = PC4500_accessrid(ai, rid, CMD_ACCESS)) != 0) {
4279	                rc = status;
4280	                goto done;
4281	        }
4282		// --- now write the rid data
4283		if (bap_setup(ai, rid, 0, BAP1) != SUCCESS) {
4284	                rc = ERROR;
4285	                goto done;
4286	        }
4287		bap_write(ai, pBuf, len, BAP1);
4288		// ---now commit the rid data
4289		rc = PC4500_accessrid(ai, rid, 0x100|CMD_ACCESS);
4290	}
4291done:
4292	if (lock)
4293		up(&ai->sem);
4294        return rc;
4295}
4296
4297/* Allocates a FID to be used for transmitting packets.  We only use
4298   one for now. */
4299static u16 transmit_allocate(struct airo_info *ai, int lenPayload, int raw)
4300{
4301	unsigned int loop = 3000;
4302	Cmd cmd;
4303	Resp rsp;
4304	u16 txFid;
4305	__le16 txControl;
4306
4307	cmd.cmd = CMD_ALLOCATETX;
4308	cmd.parm0 = lenPayload;
4309	if (down_interruptible(&ai->sem))
4310		return ERROR;
4311	if (issuecommand(ai, &cmd, &rsp, true) != SUCCESS) {
4312		txFid = ERROR;
4313		goto done;
4314	}
4315	if ((rsp.status & 0xFF00) != 0) {
4316		txFid = ERROR;
4317		goto done;
4318	}
4319	/* wait for the allocate event/indication
4320	 * It makes me kind of nervous that this can just sit here and spin,
4321	 * but in practice it only loops like four times. */
4322	while (((IN4500(ai, EVSTAT) & EV_ALLOC) == 0) && --loop);
4323	if (!loop) {
4324		txFid = ERROR;
4325		goto done;
4326	}
4327
4328	// get the allocated fid and acknowledge
4329	txFid = IN4500(ai, TXALLOCFID);
4330	OUT4500(ai, EVACK, EV_ALLOC);
4331
4332	/*  The CARD is pretty cool since it converts the ethernet packet
4333	 *  into 802.11.  Also note that we don't release the FID since we
4334	 *  will be using the same one over and over again. */
4335	/*  We only have to setup the control once since we are not
4336	 *  releasing the fid. */
4337	if (raw)
4338		txControl = cpu_to_le16(TXCTL_TXOK | TXCTL_TXEX | TXCTL_802_11
4339			| TXCTL_ETHERNET | TXCTL_NORELEASE);
4340	else
4341		txControl = cpu_to_le16(TXCTL_TXOK | TXCTL_TXEX | TXCTL_802_3
4342			| TXCTL_ETHERNET | TXCTL_NORELEASE);
4343	if (bap_setup(ai, txFid, 0x0008, BAP1) != SUCCESS)
4344		txFid = ERROR;
4345	else
4346		bap_write(ai, &txControl, sizeof(txControl), BAP1);
4347
4348done:
4349	up(&ai->sem);
4350
4351	return txFid;
4352}
4353
4354/* In general BAP1 is dedicated to transmiting packets.  However,
4355   since we need a BAP when accessing RIDs, we also use BAP1 for that.
4356   Make sure the BAP1 spinlock is held when this is called. */
4357static int transmit_802_3_packet(struct airo_info *ai, int len, char *pPacket,
4358				 bool may_sleep)
4359{
4360	__le16 payloadLen;
4361	Cmd cmd;
4362	Resp rsp;
4363	int miclen = 0;
4364	u16 txFid = len;
4365	MICBuffer pMic;
4366
4367	len >>= 16;
4368
4369	if (len <= ETH_ALEN * 2) {
4370		airo_print_warn(ai->dev->name, "Short packet %d", len);
4371		return ERROR;
4372	}
4373	len -= ETH_ALEN * 2;
4374
4375	if (test_bit(FLAG_MIC_CAPABLE, &ai->flags) && ai->micstats.enabled &&
4376	    (ntohs(((__be16 *)pPacket)[6]) != 0x888E)) {
4377		if (encapsulate(ai, (etherHead *)pPacket,&pMic, len) != SUCCESS)
4378			return ERROR;
4379		miclen = sizeof(pMic);
4380	}
4381	// packet is destination[6], source[6], payload[len-12]
4382	// write the payload length and dst/src/payload
4383	if (bap_setup(ai, txFid, 0x0036, BAP1) != SUCCESS) return ERROR;
4384	/* The hardware addresses aren't counted as part of the payload, so
4385	 * we have to subtract the 12 bytes for the addresses off */
4386	payloadLen = cpu_to_le16(len + miclen);
4387	bap_write(ai, &payloadLen, sizeof(payloadLen), BAP1);
4388	bap_write(ai, (__le16*)pPacket, sizeof(etherHead), BAP1);
4389	if (miclen)
4390		bap_write(ai, (__le16*)&pMic, miclen, BAP1);
4391	bap_write(ai, (__le16*)(pPacket + sizeof(etherHead)), len, BAP1);
4392	// issue the transmit command
4393	memset(&cmd, 0, sizeof(cmd));
4394	cmd.cmd = CMD_TRANSMIT;
4395	cmd.parm0 = txFid;
4396	if (issuecommand(ai, &cmd, &rsp, may_sleep) != SUCCESS)
4397		return ERROR;
4398	if ((rsp.status & 0xFF00) != 0) return ERROR;
4399	return SUCCESS;
4400}
4401
4402static int transmit_802_11_packet(struct airo_info *ai, int len, char *pPacket,
4403				  bool may_sleep)
4404{
4405	__le16 fc, payloadLen;
4406	Cmd cmd;
4407	Resp rsp;
4408	int hdrlen;
4409	static u8 tail[(30-10) + 2 + 6] = {[30-10] = 6};
4410	/* padding of header to full size + le16 gaplen (6) + gaplen bytes */
4411	u16 txFid = len;
4412	len >>= 16;
4413
4414	fc = *(__le16*)pPacket;
4415	hdrlen = header_len(fc);
4416
4417	if (len < hdrlen) {
4418		airo_print_warn(ai->dev->name, "Short packet %d", len);
4419		return ERROR;
4420	}
4421
4422	/* packet is 802.11 header +  payload
4423	 * write the payload length and dst/src/payload */
4424	if (bap_setup(ai, txFid, 6, BAP1) != SUCCESS) return ERROR;
4425	/* The 802.11 header aren't counted as part of the payload, so
4426	 * we have to subtract the header bytes off */
4427	payloadLen = cpu_to_le16(len-hdrlen);
4428	bap_write(ai, &payloadLen, sizeof(payloadLen), BAP1);
4429	if (bap_setup(ai, txFid, 0x0014, BAP1) != SUCCESS) return ERROR;
4430	bap_write(ai, (__le16 *)pPacket, hdrlen, BAP1);
4431	bap_write(ai, (__le16 *)(tail + (hdrlen - 10)), 38 - hdrlen, BAP1);
4432
4433	bap_write(ai, (__le16 *)(pPacket + hdrlen), len - hdrlen, BAP1);
4434	// issue the transmit command
4435	memset(&cmd, 0, sizeof(cmd));
4436	cmd.cmd = CMD_TRANSMIT;
4437	cmd.parm0 = txFid;
4438	if (issuecommand(ai, &cmd, &rsp, may_sleep) != SUCCESS)
4439		return ERROR;
4440	if ((rsp.status & 0xFF00) != 0) return ERROR;
4441	return SUCCESS;
4442}
4443
4444/*
4445 *  This is the proc_fs routines.  It is a bit messier than I would
4446 *  like!  Feel free to clean it up!
4447 */
4448
4449static ssize_t proc_read(struct file *file,
4450			  char __user *buffer,
4451			  size_t len,
4452			  loff_t *offset);
4453
4454static ssize_t proc_write(struct file *file,
4455			   const char __user *buffer,
4456			   size_t len,
4457			   loff_t *offset);
4458static int proc_close(struct inode *inode, struct file *file);
4459
4460static int proc_stats_open(struct inode *inode, struct file *file);
4461static int proc_statsdelta_open(struct inode *inode, struct file *file);
4462static int proc_status_open(struct inode *inode, struct file *file);
4463static int proc_SSID_open(struct inode *inode, struct file *file);
4464static int proc_APList_open(struct inode *inode, struct file *file);
4465static int proc_BSSList_open(struct inode *inode, struct file *file);
4466static int proc_config_open(struct inode *inode, struct file *file);
4467static int proc_wepkey_open(struct inode *inode, struct file *file);
4468
4469static const struct proc_ops proc_statsdelta_ops = {
4470	.proc_read	= proc_read,
4471	.proc_open	= proc_statsdelta_open,
4472	.proc_release	= proc_close,
4473	.proc_lseek	= default_llseek,
 
4474};
4475
4476static const struct proc_ops proc_stats_ops = {
4477	.proc_read	= proc_read,
4478	.proc_open	= proc_stats_open,
4479	.proc_release	= proc_close,
4480	.proc_lseek	= default_llseek,
 
4481};
4482
4483static const struct proc_ops proc_status_ops = {
4484	.proc_read	= proc_read,
4485	.proc_open	= proc_status_open,
4486	.proc_release	= proc_close,
4487	.proc_lseek	= default_llseek,
 
4488};
4489
4490static const struct proc_ops proc_SSID_ops = {
4491	.proc_read	= proc_read,
4492	.proc_write	= proc_write,
4493	.proc_open	= proc_SSID_open,
4494	.proc_release	= proc_close,
4495	.proc_lseek	= default_llseek,
 
4496};
4497
4498static const struct proc_ops proc_BSSList_ops = {
4499	.proc_read	= proc_read,
4500	.proc_write	= proc_write,
4501	.proc_open	= proc_BSSList_open,
4502	.proc_release	= proc_close,
4503	.proc_lseek	= default_llseek,
 
4504};
4505
4506static const struct proc_ops proc_APList_ops = {
4507	.proc_read	= proc_read,
4508	.proc_write	= proc_write,
4509	.proc_open	= proc_APList_open,
4510	.proc_release	= proc_close,
4511	.proc_lseek	= default_llseek,
 
4512};
4513
4514static const struct proc_ops proc_config_ops = {
4515	.proc_read	= proc_read,
4516	.proc_write	= proc_write,
4517	.proc_open	= proc_config_open,
4518	.proc_release	= proc_close,
4519	.proc_lseek	= default_llseek,
 
4520};
4521
4522static const struct proc_ops proc_wepkey_ops = {
4523	.proc_read	= proc_read,
4524	.proc_write	= proc_write,
4525	.proc_open	= proc_wepkey_open,
4526	.proc_release	= proc_close,
4527	.proc_lseek	= default_llseek,
 
4528};
4529
4530static struct proc_dir_entry *airo_entry;
4531
4532struct proc_data {
4533	int release_buffer;
4534	int readlen;
4535	char *rbuffer;
4536	int writelen;
4537	int maxwritelen;
4538	char *wbuffer;
4539	void (*on_close) (struct inode *, struct file *);
4540};
4541
4542static int setup_proc_entry(struct net_device *dev,
4543			     struct airo_info *apriv)
4544{
4545	struct proc_dir_entry *entry;
4546
4547	/* First setup the device directory */
4548	strcpy(apriv->proc_name, dev->name);
4549	apriv->proc_entry = proc_mkdir_mode(apriv->proc_name, airo_perm,
4550					    airo_entry);
4551	if (!apriv->proc_entry)
4552		return -ENOMEM;
4553	proc_set_user(apriv->proc_entry, proc_kuid, proc_kgid);
4554
4555	/* Setup the StatsDelta */
4556	entry = proc_create_data("StatsDelta", 0444 & proc_perm,
4557				 apriv->proc_entry, &proc_statsdelta_ops, dev);
4558	if (!entry)
4559		goto fail;
4560	proc_set_user(entry, proc_kuid, proc_kgid);
4561
4562	/* Setup the Stats */
4563	entry = proc_create_data("Stats", 0444 & proc_perm,
4564				 apriv->proc_entry, &proc_stats_ops, dev);
4565	if (!entry)
4566		goto fail;
4567	proc_set_user(entry, proc_kuid, proc_kgid);
4568
4569	/* Setup the Status */
4570	entry = proc_create_data("Status", 0444 & proc_perm,
4571				 apriv->proc_entry, &proc_status_ops, dev);
4572	if (!entry)
4573		goto fail;
4574	proc_set_user(entry, proc_kuid, proc_kgid);
4575
4576	/* Setup the Config */
4577	entry = proc_create_data("Config", proc_perm,
4578				 apriv->proc_entry, &proc_config_ops, dev);
4579	if (!entry)
4580		goto fail;
4581	proc_set_user(entry, proc_kuid, proc_kgid);
4582
4583	/* Setup the SSID */
4584	entry = proc_create_data("SSID", proc_perm,
4585				 apriv->proc_entry, &proc_SSID_ops, dev);
4586	if (!entry)
4587		goto fail;
4588	proc_set_user(entry, proc_kuid, proc_kgid);
4589
4590	/* Setup the APList */
4591	entry = proc_create_data("APList", proc_perm,
4592				 apriv->proc_entry, &proc_APList_ops, dev);
4593	if (!entry)
4594		goto fail;
4595	proc_set_user(entry, proc_kuid, proc_kgid);
4596
4597	/* Setup the BSSList */
4598	entry = proc_create_data("BSSList", proc_perm,
4599				 apriv->proc_entry, &proc_BSSList_ops, dev);
4600	if (!entry)
4601		goto fail;
4602	proc_set_user(entry, proc_kuid, proc_kgid);
4603
4604	/* Setup the WepKey */
4605	entry = proc_create_data("WepKey", proc_perm,
4606				 apriv->proc_entry, &proc_wepkey_ops, dev);
4607	if (!entry)
4608		goto fail;
4609	proc_set_user(entry, proc_kuid, proc_kgid);
4610	return 0;
4611
4612fail:
4613	remove_proc_subtree(apriv->proc_name, airo_entry);
4614	return -ENOMEM;
4615}
4616
4617static int takedown_proc_entry(struct net_device *dev,
4618				struct airo_info *apriv)
4619{
4620	remove_proc_subtree(apriv->proc_name, airo_entry);
4621	return 0;
4622}
4623
4624/*
4625 *  What we want from the proc_fs is to be able to efficiently read
4626 *  and write the configuration.  To do this, we want to read the
4627 *  configuration when the file is opened and write it when the file is
4628 *  closed.  So basically we allocate a read buffer at open and fill it
4629 *  with data, and allocate a write buffer and read it at close.
4630 */
4631
4632/*
4633 *  The read routine is generic, it relies on the preallocated rbuffer
4634 *  to supply the data.
4635 */
4636static ssize_t proc_read(struct file *file,
4637			  char __user *buffer,
4638			  size_t len,
4639			  loff_t *offset)
4640{
4641	struct proc_data *priv = file->private_data;
4642
4643	if (!priv->rbuffer)
4644		return -EINVAL;
4645
4646	return simple_read_from_buffer(buffer, len, offset, priv->rbuffer,
4647					priv->readlen);
4648}
4649
4650/*
4651 *  The write routine is generic, it fills in a preallocated rbuffer
4652 *  to supply the data.
4653 */
4654static ssize_t proc_write(struct file *file,
4655			   const char __user *buffer,
4656			   size_t len,
4657			   loff_t *offset)
4658{
4659	ssize_t ret;
4660	struct proc_data *priv = file->private_data;
4661
4662	if (!priv->wbuffer)
4663		return -EINVAL;
4664
4665	ret = simple_write_to_buffer(priv->wbuffer, priv->maxwritelen, offset,
4666					buffer, len);
4667	if (ret > 0)
4668		priv->writelen = max_t(int, priv->writelen, *offset);
4669
4670	return ret;
4671}
4672
4673static int proc_status_open(struct inode *inode, struct file *file)
4674{
4675	struct proc_data *data;
4676	struct net_device *dev = PDE_DATA(inode);
4677	struct airo_info *apriv = dev->ml_priv;
4678	CapabilityRid cap_rid;
4679	StatusRid status_rid;
4680	u16 mode;
4681	int i;
4682
4683	if ((file->private_data = kzalloc(sizeof(struct proc_data), GFP_KERNEL)) == NULL)
4684		return -ENOMEM;
4685	data = file->private_data;
4686	if ((data->rbuffer = kmalloc(2048, GFP_KERNEL)) == NULL) {
4687		kfree (file->private_data);
4688		return -ENOMEM;
4689	}
4690
4691	readStatusRid(apriv, &status_rid, 1);
4692	readCapabilityRid(apriv, &cap_rid, 1);
4693
4694	mode = le16_to_cpu(status_rid.mode);
4695
4696        i = sprintf(data->rbuffer, "Status: %s%s%s%s%s%s%s%s%s\n",
4697                    mode & 1 ? "CFG ": "",
4698                    mode & 2 ? "ACT ": "",
4699                    mode & 0x10 ? "SYN ": "",
4700                    mode & 0x20 ? "LNK ": "",
4701                    mode & 0x40 ? "LEAP ": "",
4702                    mode & 0x80 ? "PRIV ": "",
4703                    mode & 0x100 ? "KEY ": "",
4704                    mode & 0x200 ? "WEP ": "",
4705                    mode & 0x8000 ? "ERR ": "");
4706	sprintf(data->rbuffer+i, "Mode: %x\n"
4707		 "Signal Strength: %d\n"
4708		 "Signal Quality: %d\n"
4709		 "SSID: %-.*s\n"
4710		 "AP: %-.16s\n"
4711		 "Freq: %d\n"
4712		 "BitRate: %dmbs\n"
4713		 "Driver Version: %s\n"
4714		 "Device: %s\nManufacturer: %s\nFirmware Version: %s\n"
4715		 "Radio type: %x\nCountry: %x\nHardware Version: %x\n"
4716		 "Software Version: %x\nSoftware Subversion: %x\n"
4717		 "Boot block version: %x\n",
4718		 le16_to_cpu(status_rid.mode),
4719		 le16_to_cpu(status_rid.normalizedSignalStrength),
4720		 le16_to_cpu(status_rid.signalQuality),
4721		 le16_to_cpu(status_rid.SSIDlen),
4722		 status_rid.SSID,
4723		 status_rid.apName,
4724		 le16_to_cpu(status_rid.channel),
4725		 le16_to_cpu(status_rid.currentXmitRate) / 2,
4726		 version,
4727		 cap_rid.prodName,
4728		 cap_rid.manName,
4729		 cap_rid.prodVer,
4730		 le16_to_cpu(cap_rid.radioType),
4731		 le16_to_cpu(cap_rid.country),
4732		 le16_to_cpu(cap_rid.hardVer),
4733		 le16_to_cpu(cap_rid.softVer),
4734		 le16_to_cpu(cap_rid.softSubVer),
4735		 le16_to_cpu(cap_rid.bootBlockVer));
4736	data->readlen = strlen(data->rbuffer);
4737	return 0;
4738}
4739
4740static int proc_stats_rid_open(struct inode*, struct file*, u16);
4741static int proc_statsdelta_open(struct inode *inode,
4742				 struct file *file)
4743{
4744	if (file->f_mode&FMODE_WRITE) {
4745		return proc_stats_rid_open(inode, file, RID_STATSDELTACLEAR);
4746	}
4747	return proc_stats_rid_open(inode, file, RID_STATSDELTA);
4748}
4749
4750static int proc_stats_open(struct inode *inode, struct file *file)
4751{
4752	return proc_stats_rid_open(inode, file, RID_STATS);
4753}
4754
4755static int proc_stats_rid_open(struct inode *inode,
4756				struct file *file,
4757				u16 rid)
4758{
4759	struct proc_data *data;
4760	struct net_device *dev = PDE_DATA(inode);
4761	struct airo_info *apriv = dev->ml_priv;
4762	StatsRid stats;
4763	int i, j;
4764	__le32 *vals = stats.vals;
4765	int len;
4766
4767	if ((file->private_data = kzalloc(sizeof(struct proc_data), GFP_KERNEL)) == NULL)
4768		return -ENOMEM;
4769	data = file->private_data;
4770	if ((data->rbuffer = kmalloc(4096, GFP_KERNEL)) == NULL) {
4771		kfree (file->private_data);
4772		return -ENOMEM;
4773	}
4774
4775	readStatsRid(apriv, &stats, rid, 1);
4776	len = le16_to_cpu(stats.len);
4777
4778        j = 0;
4779	for (i = 0; statsLabels[i]!=(char *)-1 && i*4<len; i++) {
4780		if (!statsLabels[i]) continue;
4781		if (j+strlen(statsLabels[i])+16>4096) {
4782			airo_print_warn(apriv->dev->name,
4783			       "Potentially disastrous buffer overflow averted!");
4784			break;
4785		}
4786		j+=sprintf(data->rbuffer+j, "%s: %u\n", statsLabels[i],
4787				le32_to_cpu(vals[i]));
4788	}
4789	if (i*4 >= len) {
4790		airo_print_warn(apriv->dev->name, "Got a short rid");
4791	}
4792	data->readlen = j;
4793	return 0;
4794}
4795
4796static int get_dec_u16(char *buffer, int *start, int limit)
4797{
4798	u16 value;
4799	int valid = 0;
4800	for (value = 0; *start < limit && buffer[*start] >= '0' &&
4801			buffer[*start] <= '9'; (*start)++) {
4802		valid = 1;
4803		value *= 10;
4804		value += buffer[*start] - '0';
4805	}
4806	if (!valid) return -1;
4807	return value;
4808}
4809
4810static int airo_config_commit(struct net_device *dev,
4811			      struct iw_request_info *info, void *zwrq,
4812			      char *extra);
4813
4814static inline int sniffing_mode(struct airo_info *ai)
4815{
4816	return (le16_to_cpu(ai->config.rmode) & le16_to_cpu(RXMODE_MASK)) >=
4817		le16_to_cpu(RXMODE_RFMON);
4818}
4819
4820static void proc_config_on_close(struct inode *inode, struct file *file)
4821{
4822	struct proc_data *data = file->private_data;
4823	struct net_device *dev = PDE_DATA(inode);
4824	struct airo_info *ai = dev->ml_priv;
4825	char *line;
4826
4827	if (!data->writelen) return;
4828
4829	readConfigRid(ai, 1);
4830	set_bit (FLAG_COMMIT, &ai->flags);
4831
4832	line = data->wbuffer;
4833	while (line[0]) {
4834/*** Mode processing */
4835		if (!strncmp(line, "Mode: ", 6)) {
4836			line += 6;
4837			if (sniffing_mode(ai))
4838				set_bit (FLAG_RESET, &ai->flags);
4839			ai->config.rmode &= ~RXMODE_FULL_MASK;
4840			clear_bit (FLAG_802_11, &ai->flags);
4841			ai->config.opmode &= ~MODE_CFG_MASK;
4842			ai->config.scanMode = SCANMODE_ACTIVE;
4843			if (line[0] == 'a') {
4844				ai->config.opmode |= MODE_STA_IBSS;
4845			} else {
4846				ai->config.opmode |= MODE_STA_ESS;
4847				if (line[0] == 'r') {
4848					ai->config.rmode |= RXMODE_RFMON | RXMODE_DISABLE_802_3_HEADER;
4849					ai->config.scanMode = SCANMODE_PASSIVE;
4850					set_bit (FLAG_802_11, &ai->flags);
4851				} else if (line[0] == 'y') {
4852					ai->config.rmode |= RXMODE_RFMON_ANYBSS | RXMODE_DISABLE_802_3_HEADER;
4853					ai->config.scanMode = SCANMODE_PASSIVE;
4854					set_bit (FLAG_802_11, &ai->flags);
4855				} else if (line[0] == 'l')
4856					ai->config.rmode |= RXMODE_LANMON;
4857			}
4858			set_bit (FLAG_COMMIT, &ai->flags);
4859		}
4860
4861/*** Radio status */
4862		else if (!strncmp(line,"Radio: ", 7)) {
4863			line += 7;
4864			if (!strncmp(line,"off", 3)) {
4865				set_bit (FLAG_RADIO_OFF, &ai->flags);
4866			} else {
4867				clear_bit (FLAG_RADIO_OFF, &ai->flags);
4868			}
4869		}
4870/*** NodeName processing */
4871		else if (!strncmp(line, "NodeName: ", 10)) {
4872			int j;
4873
4874			line += 10;
4875			memset(ai->config.nodeName, 0, 16);
4876/* Do the name, assume a space between the mode and node name */
4877			for (j = 0; j < 16 && line[j] != '\n'; j++) {
4878				ai->config.nodeName[j] = line[j];
4879			}
4880			set_bit (FLAG_COMMIT, &ai->flags);
4881		}
4882
4883/*** PowerMode processing */
4884		else if (!strncmp(line, "PowerMode: ", 11)) {
4885			line += 11;
4886			if (!strncmp(line, "PSPCAM", 6)) {
4887				ai->config.powerSaveMode = POWERSAVE_PSPCAM;
4888				set_bit (FLAG_COMMIT, &ai->flags);
4889			} else if (!strncmp(line, "PSP", 3)) {
4890				ai->config.powerSaveMode = POWERSAVE_PSP;
4891				set_bit (FLAG_COMMIT, &ai->flags);
4892			} else {
4893				ai->config.powerSaveMode = POWERSAVE_CAM;
4894				set_bit (FLAG_COMMIT, &ai->flags);
4895			}
4896		} else if (!strncmp(line, "DataRates: ", 11)) {
4897			int v, i = 0, k = 0; /* i is index into line,
4898						k is index to rates */
4899
4900			line += 11;
4901			while ((v = get_dec_u16(line, &i, 3))!=-1) {
4902				ai->config.rates[k++] = (u8)v;
4903				line += i + 1;
4904				i = 0;
4905			}
4906			set_bit (FLAG_COMMIT, &ai->flags);
4907		} else if (!strncmp(line, "Channel: ", 9)) {
4908			int v, i = 0;
4909			line += 9;
4910			v = get_dec_u16(line, &i, i+3);
4911			if (v != -1) {
4912				ai->config.channelSet = cpu_to_le16(v);
4913				set_bit (FLAG_COMMIT, &ai->flags);
4914			}
4915		} else if (!strncmp(line, "XmitPower: ", 11)) {
4916			int v, i = 0;
4917			line += 11;
4918			v = get_dec_u16(line, &i, i+3);
4919			if (v != -1) {
4920				ai->config.txPower = cpu_to_le16(v);
4921				set_bit (FLAG_COMMIT, &ai->flags);
4922			}
4923		} else if (!strncmp(line, "WEP: ", 5)) {
4924			line += 5;
4925			switch(line[0]) {
4926			case 's':
4927				set_auth_type(ai, AUTH_SHAREDKEY);
4928				break;
4929			case 'e':
4930				set_auth_type(ai, AUTH_ENCRYPT);
4931				break;
4932			default:
4933				set_auth_type(ai, AUTH_OPEN);
4934				break;
4935			}
4936			set_bit (FLAG_COMMIT, &ai->flags);
4937		} else if (!strncmp(line, "LongRetryLimit: ", 16)) {
4938			int v, i = 0;
4939
4940			line += 16;
4941			v = get_dec_u16(line, &i, 3);
4942			v = (v<0) ? 0 : ((v>255) ? 255 : v);
4943			ai->config.longRetryLimit = cpu_to_le16(v);
4944			set_bit (FLAG_COMMIT, &ai->flags);
4945		} else if (!strncmp(line, "ShortRetryLimit: ", 17)) {
4946			int v, i = 0;
4947
4948			line += 17;
4949			v = get_dec_u16(line, &i, 3);
4950			v = (v<0) ? 0 : ((v>255) ? 255 : v);
4951			ai->config.shortRetryLimit = cpu_to_le16(v);
4952			set_bit (FLAG_COMMIT, &ai->flags);
4953		} else if (!strncmp(line, "RTSThreshold: ", 14)) {
4954			int v, i = 0;
4955
4956			line += 14;
4957			v = get_dec_u16(line, &i, 4);
4958			v = (v<0) ? 0 : ((v>AIRO_DEF_MTU) ? AIRO_DEF_MTU : v);
4959			ai->config.rtsThres = cpu_to_le16(v);
4960			set_bit (FLAG_COMMIT, &ai->flags);
4961		} else if (!strncmp(line, "TXMSDULifetime: ", 16)) {
4962			int v, i = 0;
4963
4964			line += 16;
4965			v = get_dec_u16(line, &i, 5);
4966			v = (v<0) ? 0 : v;
4967			ai->config.txLifetime = cpu_to_le16(v);
4968			set_bit (FLAG_COMMIT, &ai->flags);
4969		} else if (!strncmp(line, "RXMSDULifetime: ", 16)) {
4970			int v, i = 0;
4971
4972			line += 16;
4973			v = get_dec_u16(line, &i, 5);
4974			v = (v<0) ? 0 : v;
4975			ai->config.rxLifetime = cpu_to_le16(v);
4976			set_bit (FLAG_COMMIT, &ai->flags);
4977		} else if (!strncmp(line, "TXDiversity: ", 13)) {
4978			ai->config.txDiversity =
4979				(line[13]=='l') ? 1 :
4980				((line[13]=='r')? 2: 3);
4981			set_bit (FLAG_COMMIT, &ai->flags);
4982		} else if (!strncmp(line, "RXDiversity: ", 13)) {
4983			ai->config.rxDiversity =
4984				(line[13]=='l') ? 1 :
4985				((line[13]=='r')? 2: 3);
4986			set_bit (FLAG_COMMIT, &ai->flags);
4987		} else if (!strncmp(line, "FragThreshold: ", 15)) {
4988			int v, i = 0;
4989
4990			line += 15;
4991			v = get_dec_u16(line, &i, 4);
4992			v = (v<256) ? 256 : ((v>AIRO_DEF_MTU) ? AIRO_DEF_MTU : v);
4993			v = v & 0xfffe; /* Make sure its even */
4994			ai->config.fragThresh = cpu_to_le16(v);
4995			set_bit (FLAG_COMMIT, &ai->flags);
4996		} else if (!strncmp(line, "Modulation: ", 12)) {
4997			line += 12;
4998			switch(*line) {
4999			case 'd':  ai->config.modulation = MOD_DEFAULT; set_bit(FLAG_COMMIT, &ai->flags); break;
5000			case 'c':  ai->config.modulation = MOD_CCK; set_bit(FLAG_COMMIT, &ai->flags); break;
5001			case 'm':  ai->config.modulation = MOD_MOK; set_bit(FLAG_COMMIT, &ai->flags); break;
5002			default: airo_print_warn(ai->dev->name, "Unknown modulation");
5003			}
5004		} else if (!strncmp(line, "Preamble: ", 10)) {
5005			line += 10;
5006			switch(*line) {
5007			case 'a': ai->config.preamble = PREAMBLE_AUTO; set_bit(FLAG_COMMIT, &ai->flags); break;
5008			case 'l': ai->config.preamble = PREAMBLE_LONG; set_bit(FLAG_COMMIT, &ai->flags); break;
5009			case 's': ai->config.preamble = PREAMBLE_SHORT; set_bit(FLAG_COMMIT, &ai->flags); break;
5010			default: airo_print_warn(ai->dev->name, "Unknown preamble");
5011			}
5012		} else {
5013			airo_print_warn(ai->dev->name, "Couldn't figure out %s", line);
5014		}
5015		while (line[0] && line[0] != '\n') line++;
5016		if (line[0]) line++;
5017	}
5018	airo_config_commit(dev, NULL, NULL, NULL);
5019}
5020
5021static const char *get_rmode(__le16 mode)
5022{
5023        switch(mode & RXMODE_MASK) {
5024        case RXMODE_RFMON:  return "rfmon";
5025        case RXMODE_RFMON_ANYBSS:  return "yna (any) bss rfmon";
5026        case RXMODE_LANMON:  return "lanmon";
5027        }
5028        return "ESS";
5029}
5030
5031static int proc_config_open(struct inode *inode, struct file *file)
5032{
5033	struct proc_data *data;
5034	struct net_device *dev = PDE_DATA(inode);
5035	struct airo_info *ai = dev->ml_priv;
5036	int i;
5037	__le16 mode;
5038
5039	if ((file->private_data = kzalloc(sizeof(struct proc_data), GFP_KERNEL)) == NULL)
5040		return -ENOMEM;
5041	data = file->private_data;
5042	if ((data->rbuffer = kmalloc(2048, GFP_KERNEL)) == NULL) {
5043		kfree (file->private_data);
5044		return -ENOMEM;
5045	}
5046	if ((data->wbuffer = kzalloc(2048, GFP_KERNEL)) == NULL) {
5047		kfree (data->rbuffer);
5048		kfree (file->private_data);
5049		return -ENOMEM;
5050	}
5051	data->maxwritelen = 2048;
5052	data->on_close = proc_config_on_close;
5053
5054	readConfigRid(ai, 1);
5055
5056	mode = ai->config.opmode & MODE_CFG_MASK;
5057	i = sprintf(data->rbuffer,
5058		     "Mode: %s\n"
5059		     "Radio: %s\n"
5060		     "NodeName: %-16s\n"
5061		     "PowerMode: %s\n"
5062		     "DataRates: %d %d %d %d %d %d %d %d\n"
5063		     "Channel: %d\n"
5064		     "XmitPower: %d\n",
5065		     mode == MODE_STA_IBSS ? "adhoc" :
5066		     mode == MODE_STA_ESS ? get_rmode(ai->config.rmode):
5067		     mode == MODE_AP ? "AP" :
5068		     mode == MODE_AP_RPTR ? "AP RPTR" : "Error",
5069		     test_bit(FLAG_RADIO_OFF, &ai->flags) ? "off" : "on",
5070		     ai->config.nodeName,
5071		     ai->config.powerSaveMode == POWERSAVE_CAM ? "CAM" :
5072		     ai->config.powerSaveMode == POWERSAVE_PSP ? "PSP" :
5073		     ai->config.powerSaveMode == POWERSAVE_PSPCAM ? "PSPCAM" :
5074		     "Error",
5075		     (int)ai->config.rates[0],
5076		     (int)ai->config.rates[1],
5077		     (int)ai->config.rates[2],
5078		     (int)ai->config.rates[3],
5079		     (int)ai->config.rates[4],
5080		     (int)ai->config.rates[5],
5081		     (int)ai->config.rates[6],
5082		     (int)ai->config.rates[7],
5083		     le16_to_cpu(ai->config.channelSet),
5084		     le16_to_cpu(ai->config.txPower)
5085		);
5086	sprintf(data->rbuffer + i,
5087		 "LongRetryLimit: %d\n"
5088		 "ShortRetryLimit: %d\n"
5089		 "RTSThreshold: %d\n"
5090		 "TXMSDULifetime: %d\n"
5091		 "RXMSDULifetime: %d\n"
5092		 "TXDiversity: %s\n"
5093		 "RXDiversity: %s\n"
5094		 "FragThreshold: %d\n"
5095		 "WEP: %s\n"
5096		 "Modulation: %s\n"
5097		 "Preamble: %s\n",
5098		 le16_to_cpu(ai->config.longRetryLimit),
5099		 le16_to_cpu(ai->config.shortRetryLimit),
5100		 le16_to_cpu(ai->config.rtsThres),
5101		 le16_to_cpu(ai->config.txLifetime),
5102		 le16_to_cpu(ai->config.rxLifetime),
5103		 ai->config.txDiversity == 1 ? "left" :
5104		 ai->config.txDiversity == 2 ? "right" : "both",
5105		 ai->config.rxDiversity == 1 ? "left" :
5106		 ai->config.rxDiversity == 2 ? "right" : "both",
5107		 le16_to_cpu(ai->config.fragThresh),
5108		 ai->config.authType == AUTH_ENCRYPT ? "encrypt" :
5109		 ai->config.authType == AUTH_SHAREDKEY ? "shared" : "open",
5110		 ai->config.modulation == MOD_DEFAULT ? "default" :
5111		 ai->config.modulation == MOD_CCK ? "cck" :
5112		 ai->config.modulation == MOD_MOK ? "mok" : "error",
5113		 ai->config.preamble == PREAMBLE_AUTO ? "auto" :
5114		 ai->config.preamble == PREAMBLE_LONG ? "long" :
5115		 ai->config.preamble == PREAMBLE_SHORT ? "short" : "error"
5116		);
5117	data->readlen = strlen(data->rbuffer);
5118	return 0;
5119}
5120
5121static void proc_SSID_on_close(struct inode *inode, struct file *file)
5122{
5123	struct proc_data *data = file->private_data;
5124	struct net_device *dev = PDE_DATA(inode);
5125	struct airo_info *ai = dev->ml_priv;
5126	SsidRid SSID_rid;
5127	int i;
5128	char *p = data->wbuffer;
5129	char *end = p + data->writelen;
5130
5131	if (!data->writelen)
5132		return;
5133
5134	*end = '\n'; /* sentinel; we have space for it */
5135
5136	memset(&SSID_rid, 0, sizeof(SSID_rid));
5137
5138	for (i = 0; i < 3 && p < end; i++) {
5139		int j = 0;
5140		/* copy up to 32 characters from this line */
5141		while (*p != '\n' && j < 32)
5142			SSID_rid.ssids[i].ssid[j++] = *p++;
5143		if (j == 0)
5144			break;
5145		SSID_rid.ssids[i].len = cpu_to_le16(j);
5146		/* skip to the beginning of the next line */
5147		while (*p++ != '\n')
5148			;
5149	}
5150	if (i)
5151		SSID_rid.len = cpu_to_le16(sizeof(SSID_rid));
5152	disable_MAC(ai, 1);
5153	writeSsidRid(ai, &SSID_rid, 1);
5154	enable_MAC(ai, 1);
5155}
5156
5157static void proc_APList_on_close(struct inode *inode, struct file *file)
5158{
5159	struct proc_data *data = file->private_data;
5160	struct net_device *dev = PDE_DATA(inode);
5161	struct airo_info *ai = dev->ml_priv;
5162	APListRid *APList_rid = &ai->APList;
5163	int i;
5164
5165	if (!data->writelen) return;
5166
5167	memset(APList_rid, 0, sizeof(*APList_rid));
5168	APList_rid->len = cpu_to_le16(sizeof(*APList_rid));
5169
5170	for (i = 0; i < 4 && data->writelen >= (i + 1) * 6 * 3; i++)
5171		mac_pton(data->wbuffer + i * 6 * 3, APList_rid->ap[i]);
5172
5173	disable_MAC(ai, 1);
5174	writeAPListRid(ai, APList_rid, 1);
5175	enable_MAC(ai, 1);
5176}
5177
5178/* This function wraps PC4500_writerid with a MAC disable */
5179static int do_writerid(struct airo_info *ai, u16 rid, const void *rid_data,
5180			int len, int dummy)
5181{
5182	int rc;
5183
5184	disable_MAC(ai, 1);
5185	rc = PC4500_writerid(ai, rid, rid_data, len, 1);
5186	enable_MAC(ai, 1);
5187	return rc;
5188}
5189
5190/* Returns the WEP key at the specified index, or -1 if that key does
5191 * not exist.  The buffer is assumed to be at least 16 bytes in length.
5192 */
5193static int get_wep_key(struct airo_info *ai, u16 index, char *buf, u16 buflen)
5194{
5195	WepKeyRid wkr;
5196	int rc;
5197	__le16 lastindex;
5198
5199	rc = readWepKeyRid(ai, &wkr, 1, 1);
5200	if (rc != SUCCESS)
5201		return -1;
5202	do {
5203		lastindex = wkr.kindex;
5204		if (le16_to_cpu(wkr.kindex) == index) {
5205			int klen = min_t(int, buflen, le16_to_cpu(wkr.klen));
5206			memcpy(buf, wkr.key, klen);
5207			return klen;
5208		}
5209		rc = readWepKeyRid(ai, &wkr, 0, 1);
5210		if (rc != SUCCESS)
5211			return -1;
5212	} while (lastindex != wkr.kindex);
5213	return -1;
5214}
5215
5216static int get_wep_tx_idx(struct airo_info *ai)
5217{
5218	WepKeyRid wkr;
5219	int rc;
5220	__le16 lastindex;
5221
5222	rc = readWepKeyRid(ai, &wkr, 1, 1);
5223	if (rc != SUCCESS)
5224		return -1;
5225	do {
5226		lastindex = wkr.kindex;
5227		if (wkr.kindex == cpu_to_le16(0xffff))
5228			return wkr.mac[0];
5229		rc = readWepKeyRid(ai, &wkr, 0, 1);
5230		if (rc != SUCCESS)
5231			return -1;
5232	} while (lastindex != wkr.kindex);
5233	return -1;
5234}
5235
5236static int set_wep_key(struct airo_info *ai, u16 index, const char *key,
5237		       u16 keylen, int perm, int lock)
5238{
5239	static const unsigned char macaddr[ETH_ALEN] = { 0x01, 0, 0, 0, 0, 0 };
5240	WepKeyRid wkr;
5241	int rc;
5242
5243	if (WARN_ON(keylen == 0))
5244		return -1;
5245
5246	memset(&wkr, 0, sizeof(wkr));
5247	wkr.len = cpu_to_le16(sizeof(wkr));
5248	wkr.kindex = cpu_to_le16(index);
5249	wkr.klen = cpu_to_le16(keylen);
5250	memcpy(wkr.key, key, keylen);
5251	memcpy(wkr.mac, macaddr, ETH_ALEN);
5252
5253	if (perm) disable_MAC(ai, lock);
5254	rc = writeWepKeyRid(ai, &wkr, perm, lock);
5255	if (perm) enable_MAC(ai, lock);
5256	return rc;
5257}
5258
5259static int set_wep_tx_idx(struct airo_info *ai, u16 index, int perm, int lock)
5260{
5261	WepKeyRid wkr;
5262	int rc;
5263
5264	memset(&wkr, 0, sizeof(wkr));
5265	wkr.len = cpu_to_le16(sizeof(wkr));
5266	wkr.kindex = cpu_to_le16(0xffff);
5267	wkr.mac[0] = (char)index;
5268
5269	if (perm) {
5270		ai->defindex = (char)index;
5271		disable_MAC(ai, lock);
5272	}
5273
5274	rc = writeWepKeyRid(ai, &wkr, perm, lock);
5275
5276	if (perm)
5277		enable_MAC(ai, lock);
5278	return rc;
5279}
5280
5281static void proc_wepkey_on_close(struct inode *inode, struct file *file)
5282{
5283	struct proc_data *data;
5284	struct net_device *dev = PDE_DATA(inode);
5285	struct airo_info *ai = dev->ml_priv;
5286	int i, rc;
5287	char key[16];
5288	u16 index = 0;
5289	int j = 0;
5290
5291	memset(key, 0, sizeof(key));
5292
5293	data = file->private_data;
5294	if (!data->writelen) return;
5295
5296	if (data->wbuffer[0] >= '0' && data->wbuffer[0] <= '3' &&
5297	    (data->wbuffer[1] == ' ' || data->wbuffer[1] == '\n')) {
5298		index = data->wbuffer[0] - '0';
5299		if (data->wbuffer[1] == '\n') {
5300			rc = set_wep_tx_idx(ai, index, 1, 1);
5301			if (rc < 0) {
5302				airo_print_err(ai->dev->name, "failed to set "
5303				               "WEP transmit index to %d: %d.",
5304				               index, rc);
5305			}
5306			return;
5307		}
5308		j = 2;
5309	} else {
5310		airo_print_err(ai->dev->name, "WepKey passed invalid key index");
5311		return;
5312	}
5313
5314	for (i = 0; i < 16*3 && data->wbuffer[i+j]; i++) {
5315		switch(i%3) {
5316		case 0:
5317			key[i/3] = hex_to_bin(data->wbuffer[i+j])<<4;
5318			break;
5319		case 1:
5320			key[i/3] |= hex_to_bin(data->wbuffer[i+j]);
5321			break;
5322		}
5323	}
5324
5325	rc = set_wep_key(ai, index, key, i/3, 1, 1);
5326	if (rc < 0) {
5327		airo_print_err(ai->dev->name, "failed to set WEP key at index "
5328		               "%d: %d.", index, rc);
5329	}
5330}
5331
5332static int proc_wepkey_open(struct inode *inode, struct file *file)
5333{
5334	struct proc_data *data;
5335	struct net_device *dev = PDE_DATA(inode);
5336	struct airo_info *ai = dev->ml_priv;
5337	char *ptr;
5338	WepKeyRid wkr;
5339	__le16 lastindex;
5340	int j = 0;
5341	int rc;
5342
5343	if ((file->private_data = kzalloc(sizeof(struct proc_data), GFP_KERNEL)) == NULL)
5344		return -ENOMEM;
5345	memset(&wkr, 0, sizeof(wkr));
5346	data = file->private_data;
5347	if ((data->rbuffer = kzalloc(180, GFP_KERNEL)) == NULL) {
5348		kfree (file->private_data);
5349		return -ENOMEM;
5350	}
5351	data->writelen = 0;
5352	data->maxwritelen = 80;
5353	if ((data->wbuffer = kzalloc(80, GFP_KERNEL)) == NULL) {
5354		kfree (data->rbuffer);
5355		kfree (file->private_data);
5356		return -ENOMEM;
5357	}
5358	data->on_close = proc_wepkey_on_close;
5359
5360	ptr = data->rbuffer;
5361	strcpy(ptr, "No wep keys\n");
5362	rc = readWepKeyRid(ai, &wkr, 1, 1);
5363	if (rc == SUCCESS) do {
5364		lastindex = wkr.kindex;
5365		if (wkr.kindex == cpu_to_le16(0xffff)) {
5366			j += sprintf(ptr+j, "Tx key = %d\n",
5367				     (int)wkr.mac[0]);
5368		} else {
5369			j += sprintf(ptr+j, "Key %d set with length = %d\n",
5370				     le16_to_cpu(wkr.kindex),
5371				     le16_to_cpu(wkr.klen));
5372		}
5373		readWepKeyRid(ai, &wkr, 0, 1);
5374	} while ((lastindex != wkr.kindex) && (j < 180-30));
5375
5376	data->readlen = strlen(data->rbuffer);
5377	return 0;
5378}
5379
5380static int proc_SSID_open(struct inode *inode, struct file *file)
5381{
5382	struct proc_data *data;
5383	struct net_device *dev = PDE_DATA(inode);
5384	struct airo_info *ai = dev->ml_priv;
5385	int i;
5386	char *ptr;
5387	SsidRid SSID_rid;
5388
5389	if ((file->private_data = kzalloc(sizeof(struct proc_data), GFP_KERNEL)) == NULL)
5390		return -ENOMEM;
5391	data = file->private_data;
5392	if ((data->rbuffer = kmalloc(104, GFP_KERNEL)) == NULL) {
5393		kfree (file->private_data);
5394		return -ENOMEM;
5395	}
5396	data->writelen = 0;
5397	data->maxwritelen = 33*3;
5398	/* allocate maxwritelen + 1; we'll want a sentinel */
5399	if ((data->wbuffer = kzalloc(33*3 + 1, GFP_KERNEL)) == NULL) {
5400		kfree (data->rbuffer);
5401		kfree (file->private_data);
5402		return -ENOMEM;
5403	}
5404	data->on_close = proc_SSID_on_close;
5405
5406	readSsidRid(ai, &SSID_rid);
5407	ptr = data->rbuffer;
5408	for (i = 0; i < 3; i++) {
5409		int j;
5410		size_t len = le16_to_cpu(SSID_rid.ssids[i].len);
5411		if (!len)
5412			break;
5413		if (len > 32)
5414			len = 32;
5415		for (j = 0; j < len && SSID_rid.ssids[i].ssid[j]; j++)
5416			*ptr++ = SSID_rid.ssids[i].ssid[j];
5417		*ptr++ = '\n';
5418	}
5419	*ptr = '\0';
5420	data->readlen = strlen(data->rbuffer);
5421	return 0;
5422}
5423
5424static int proc_APList_open(struct inode *inode, struct file *file)
5425{
5426	struct proc_data *data;
5427	struct net_device *dev = PDE_DATA(inode);
5428	struct airo_info *ai = dev->ml_priv;
5429	int i;
5430	char *ptr;
5431	APListRid *APList_rid = &ai->APList;
5432
5433	if ((file->private_data = kzalloc(sizeof(struct proc_data), GFP_KERNEL)) == NULL)
5434		return -ENOMEM;
5435	data = file->private_data;
5436	if ((data->rbuffer = kmalloc(104, GFP_KERNEL)) == NULL) {
5437		kfree (file->private_data);
5438		return -ENOMEM;
5439	}
5440	data->writelen = 0;
5441	data->maxwritelen = 4*6*3;
5442	if ((data->wbuffer = kzalloc(data->maxwritelen, GFP_KERNEL)) == NULL) {
5443		kfree (data->rbuffer);
5444		kfree (file->private_data);
5445		return -ENOMEM;
5446	}
5447	data->on_close = proc_APList_on_close;
5448
5449	ptr = data->rbuffer;
5450	for (i = 0; i < 4; i++) {
5451// We end when we find a zero MAC
5452		if (!*(int*)APList_rid->ap[i] &&
5453		     !*(int*)&APList_rid->ap[i][2]) break;
5454		ptr += sprintf(ptr, "%pM\n", APList_rid->ap[i]);
5455	}
5456	if (i==0) ptr += sprintf(ptr, "Not using specific APs\n");
5457
5458	*ptr = '\0';
5459	data->readlen = strlen(data->rbuffer);
5460	return 0;
5461}
5462
5463static int proc_BSSList_open(struct inode *inode, struct file *file)
5464{
5465	struct proc_data *data;
5466	struct net_device *dev = PDE_DATA(inode);
5467	struct airo_info *ai = dev->ml_priv;
5468	char *ptr;
5469	BSSListRid BSSList_rid;
5470	int rc;
5471	/* If doLoseSync is not 1, we won't do a Lose Sync */
5472	int doLoseSync = -1;
5473
5474	if ((file->private_data = kzalloc(sizeof(struct proc_data), GFP_KERNEL)) == NULL)
5475		return -ENOMEM;
5476	data = file->private_data;
5477	if ((data->rbuffer = kmalloc(1024, GFP_KERNEL)) == NULL) {
5478		kfree (file->private_data);
5479		return -ENOMEM;
5480	}
5481	data->writelen = 0;
5482	data->maxwritelen = 0;
5483	data->wbuffer = NULL;
5484	data->on_close = NULL;
5485
5486	if (file->f_mode & FMODE_WRITE) {
5487		if (!(file->f_mode & FMODE_READ)) {
5488			Cmd cmd;
5489			Resp rsp;
5490
5491			if (ai->flags & FLAG_RADIO_MASK) {
5492				kfree(data->rbuffer);
5493				kfree(file->private_data);
5494				return -ENETDOWN;
5495			}
5496			memset(&cmd, 0, sizeof(cmd));
5497			cmd.cmd = CMD_LISTBSS;
5498			if (down_interruptible(&ai->sem)) {
5499				kfree(data->rbuffer);
5500				kfree(file->private_data);
5501				return -ERESTARTSYS;
5502			}
5503			issuecommand(ai, &cmd, &rsp, true);
5504			up(&ai->sem);
5505			data->readlen = 0;
5506			return 0;
5507		}
5508		doLoseSync = 1;
5509	}
5510	ptr = data->rbuffer;
5511	/* There is a race condition here if there are concurrent opens.
5512           Since it is a rare condition, we'll just live with it, otherwise
5513           we have to add a spin lock... */
5514	rc = readBSSListRid(ai, doLoseSync, &BSSList_rid);
5515	while (rc == 0 && BSSList_rid.index != cpu_to_le16(0xffff)) {
5516		ptr += sprintf(ptr, "%pM %.*s rssi = %d",
5517			       BSSList_rid.bssid,
5518				(int)BSSList_rid.ssidLen,
5519				BSSList_rid.ssid,
5520				le16_to_cpu(BSSList_rid.dBm));
5521		ptr += sprintf(ptr, " channel = %d %s %s %s %s\n",
5522				le16_to_cpu(BSSList_rid.dsChannel),
5523				BSSList_rid.cap & CAP_ESS ? "ESS" : "",
5524				BSSList_rid.cap & CAP_IBSS ? "adhoc" : "",
5525				BSSList_rid.cap & CAP_PRIVACY ? "wep" : "",
5526				BSSList_rid.cap & CAP_SHORTHDR ? "shorthdr" : "");
5527		rc = readBSSListRid(ai, 0, &BSSList_rid);
5528	}
5529	*ptr = '\0';
5530	data->readlen = strlen(data->rbuffer);
5531	return 0;
5532}
5533
5534static int proc_close(struct inode *inode, struct file *file)
5535{
5536	struct proc_data *data = file->private_data;
5537
5538	if (data->on_close != NULL)
5539		data->on_close(inode, file);
5540	kfree(data->rbuffer);
5541	kfree(data->wbuffer);
5542	kfree(data);
5543	return 0;
5544}
5545
5546/* Since the card doesn't automatically switch to the right WEP mode,
5547   we will make it do it.  If the card isn't associated, every secs we
5548   will switch WEP modes to see if that will help.  If the card is
5549   associated we will check every minute to see if anything has
5550   changed. */
5551static void timer_func(struct net_device *dev)
5552{
5553	struct airo_info *apriv = dev->ml_priv;
5554
5555/* We don't have a link so try changing the authtype */
5556	readConfigRid(apriv, 0);
5557	disable_MAC(apriv, 0);
5558	switch(apriv->config.authType) {
5559		case AUTH_ENCRYPT:
5560/* So drop to OPEN */
5561			apriv->config.authType = AUTH_OPEN;
5562			break;
5563		case AUTH_SHAREDKEY:
5564			if (apriv->keyindex < auto_wep) {
5565				set_wep_tx_idx(apriv, apriv->keyindex, 0, 0);
5566				apriv->config.authType = AUTH_SHAREDKEY;
5567				apriv->keyindex++;
5568			} else {
5569			        /* Drop to ENCRYPT */
5570				apriv->keyindex = 0;
5571				set_wep_tx_idx(apriv, apriv->defindex, 0, 0);
5572				apriv->config.authType = AUTH_ENCRYPT;
5573			}
5574			break;
5575		default:  /* We'll escalate to SHAREDKEY */
5576			apriv->config.authType = AUTH_SHAREDKEY;
5577	}
5578	set_bit (FLAG_COMMIT, &apriv->flags);
5579	writeConfigRid(apriv, 0);
5580	enable_MAC(apriv, 0);
5581	up(&apriv->sem);
5582
5583/* Schedule check to see if the change worked */
5584	clear_bit(JOB_AUTOWEP, &apriv->jobs);
5585	apriv->expires = RUN_AT(HZ*3);
5586}
5587
5588#ifdef CONFIG_PCI
5589static int airo_pci_probe(struct pci_dev *pdev,
5590				    const struct pci_device_id *pent)
5591{
5592	struct net_device *dev;
5593
5594	if (pci_enable_device(pdev))
5595		return -ENODEV;
5596	pci_set_master(pdev);
5597
5598	if (pdev->device == 0x5000 || pdev->device == 0xa504)
5599			dev = _init_airo_card(pdev->irq, pdev->resource[0].start, 0, pdev, &pdev->dev);
5600	else
5601			dev = _init_airo_card(pdev->irq, pdev->resource[2].start, 0, pdev, &pdev->dev);
5602	if (!dev) {
5603		pci_disable_device(pdev);
5604		return -ENODEV;
5605	}
5606
5607	pci_set_drvdata(pdev, dev);
5608	return 0;
5609}
5610
5611static void airo_pci_remove(struct pci_dev *pdev)
5612{
5613	struct net_device *dev = pci_get_drvdata(pdev);
5614
5615	airo_print_info(dev->name, "Unregistering...");
5616	stop_airo_card(dev, 1);
5617	pci_disable_device(pdev);
5618}
5619
5620static int __maybe_unused airo_pci_suspend(struct device *dev_d)
5621{
5622	struct net_device *dev = dev_get_drvdata(dev_d);
5623	struct airo_info *ai = dev->ml_priv;
5624	Cmd cmd;
5625	Resp rsp;
5626
5627	if (!ai->SSID)
5628		ai->SSID = kmalloc(sizeof(SsidRid), GFP_KERNEL);
5629	if (!ai->SSID)
5630		return -ENOMEM;
5631	readSsidRid(ai, ai->SSID);
5632	memset(&cmd, 0, sizeof(cmd));
5633	/* the lock will be released at the end of the resume callback */
5634	if (down_interruptible(&ai->sem))
5635		return -EAGAIN;
5636	disable_MAC(ai, 0);
5637	netif_device_detach(dev);
5638	ai->power = PMSG_SUSPEND;
5639	cmd.cmd = HOSTSLEEP;
5640	issuecommand(ai, &cmd, &rsp, true);
5641
5642	device_wakeup_enable(dev_d);
 
 
5643	return 0;
5644}
5645
5646static int __maybe_unused airo_pci_resume(struct device *dev_d)
5647{
5648	struct net_device *dev = dev_get_drvdata(dev_d);
5649	struct airo_info *ai = dev->ml_priv;
5650	pci_power_t prev_state = to_pci_dev(dev_d)->current_state;
5651
5652	device_wakeup_disable(dev_d);
 
 
5653
5654	if (prev_state != PCI_D1) {
5655		reset_card(dev, 0);
5656		mpi_init_descriptors(ai);
5657		setup_card(ai, dev->dev_addr, 0);
5658		clear_bit(FLAG_RADIO_OFF, &ai->flags);
5659		clear_bit(FLAG_PENDING_XMIT, &ai->flags);
5660	} else {
5661		OUT4500(ai, EVACK, EV_AWAKEN);
5662		OUT4500(ai, EVACK, EV_AWAKEN);
5663		msleep(100);
5664	}
5665
5666	set_bit(FLAG_COMMIT, &ai->flags);
5667	disable_MAC(ai, 0);
5668        msleep(200);
5669	if (ai->SSID) {
5670		writeSsidRid(ai, ai->SSID, 0);
5671		kfree(ai->SSID);
5672		ai->SSID = NULL;
5673	}
5674	writeAPListRid(ai, &ai->APList, 0);
5675	writeConfigRid(ai, 0);
5676	enable_MAC(ai, 0);
5677	ai->power = PMSG_ON;
5678	netif_device_attach(dev);
5679	netif_wake_queue(dev);
5680	enable_interrupts(ai);
5681	up(&ai->sem);
5682	return 0;
5683}
5684#endif
5685
5686static int __init airo_init_module(void)
5687{
5688	int i;
5689
5690	proc_kuid = make_kuid(&init_user_ns, proc_uid);
5691	proc_kgid = make_kgid(&init_user_ns, proc_gid);
5692	if (!uid_valid(proc_kuid) || !gid_valid(proc_kgid))
5693		return -EINVAL;
5694
5695	airo_entry = proc_mkdir_mode("driver/aironet", airo_perm, NULL);
5696
5697	if (airo_entry)
5698		proc_set_user(airo_entry, proc_kuid, proc_kgid);
5699
5700	for (i = 0; i < 4 && io[i] && irq[i]; i++) {
5701		airo_print_info("", "Trying to configure ISA adapter at irq=%d "
5702			"io = 0x%x", irq[i], io[i]);
5703		if (init_airo_card(irq[i], io[i], 0, NULL)) {
5704			/* do nothing */ ;
5705		}
5706	}
5707
5708#ifdef CONFIG_PCI
5709	airo_print_info("", "Probing for PCI adapters");
5710	i = pci_register_driver(&airo_driver);
5711	airo_print_info("", "Finished probing for PCI adapters");
5712
5713	if (i) {
5714		remove_proc_entry("driver/aironet", NULL);
5715		return i;
5716	}
5717#endif
5718
5719	/* Always exit with success, as we are a library module
5720	 * as well as a driver module
5721	 */
5722	return 0;
5723}
5724
5725static void __exit airo_cleanup_module(void)
5726{
5727	struct airo_info *ai;
5728	while (!list_empty(&airo_devices)) {
5729		ai = list_entry(airo_devices.next, struct airo_info, dev_list);
5730		airo_print_info(ai->dev->name, "Unregistering...");
5731		stop_airo_card(ai->dev, 1);
5732	}
5733#ifdef CONFIG_PCI
5734	pci_unregister_driver(&airo_driver);
5735#endif
5736	remove_proc_entry("driver/aironet", NULL);
5737}
5738
5739/*
5740 * Initial Wireless Extension code for Aironet driver by :
5741 *	Jean Tourrilhes <jt@hpl.hp.com> - HPL - 17 November 00
5742 * Conversion to new driver API by :
5743 *	Jean Tourrilhes <jt@hpl.hp.com> - HPL - 26 March 02
5744 * Javier also did a good amount of work here, adding some new extensions
5745 * and fixing my code. Let's just say that without him this code just
5746 * would not work at all... - Jean II
5747 */
5748
5749static u8 airo_rssi_to_dbm (tdsRssiEntry *rssi_rid, u8 rssi)
5750{
5751	if (!rssi_rid)
5752		return 0;
5753
5754	return (0x100 - rssi_rid[rssi].rssidBm);
5755}
5756
5757static u8 airo_dbm_to_pct (tdsRssiEntry *rssi_rid, u8 dbm)
5758{
5759	int i;
5760
5761	if (!rssi_rid)
5762		return 0;
5763
5764	for (i = 0; i < 256; i++)
5765		if (rssi_rid[i].rssidBm == dbm)
5766			return rssi_rid[i].rssipct;
5767
5768	return 0;
5769}
5770
5771
5772static int airo_get_quality (StatusRid *status_rid, CapabilityRid *cap_rid)
5773{
5774	int quality = 0;
5775	u16 sq;
5776
5777	if ((status_rid->mode & cpu_to_le16(0x3f)) != cpu_to_le16(0x3f))
5778		return 0;
5779
5780	if (!(cap_rid->hardCap & cpu_to_le16(8)))
5781		return 0;
5782
5783	sq = le16_to_cpu(status_rid->signalQuality);
5784	if (memcmp(cap_rid->prodName, "350", 3))
5785		if (sq > 0x20)
5786			quality = 0;
5787		else
5788			quality = 0x20 - sq;
5789	else
5790		if (sq > 0xb0)
5791			quality = 0;
5792		else if (sq < 0x10)
5793			quality = 0xa0;
5794		else
5795			quality = 0xb0 - sq;
5796	return quality;
5797}
5798
5799#define airo_get_max_quality(cap_rid) (memcmp((cap_rid)->prodName, "350", 3) ? 0x20 : 0xa0)
5800#define airo_get_avg_quality(cap_rid) (memcmp((cap_rid)->prodName, "350", 3) ? 0x10 : 0x50)
5801
5802/*------------------------------------------------------------------*/
5803/*
5804 * Wireless Handler : get protocol name
5805 */
5806static int airo_get_name(struct net_device *dev,
5807			 struct iw_request_info *info,
5808			 char *cwrq,
5809			 char *extra)
5810{
5811	strcpy(cwrq, "IEEE 802.11-DS");
5812	return 0;
5813}
5814
5815/*------------------------------------------------------------------*/
5816/*
5817 * Wireless Handler : set frequency
5818 */
5819static int airo_set_freq(struct net_device *dev,
5820			 struct iw_request_info *info,
5821			 struct iw_freq *fwrq,
5822			 char *extra)
5823{
5824	struct airo_info *local = dev->ml_priv;
5825	int rc = -EINPROGRESS;		/* Call commit handler */
5826
5827	/* If setting by frequency, convert to a channel */
5828	if (fwrq->e == 1) {
5829		int f = fwrq->m / 100000;
5830
5831		/* Hack to fall through... */
5832		fwrq->e = 0;
5833		fwrq->m = ieee80211_frequency_to_channel(f);
5834	}
5835	/* Setting by channel number */
5836	if (fwrq->m < 0 || fwrq->m > 1000 || fwrq->e > 0)
5837		rc = -EOPNOTSUPP;
5838	else {
5839		int channel = fwrq->m;
5840		/* We should do a better check than that,
5841		 * based on the card capability !!! */
5842		if ((channel < 1) || (channel > 14)) {
5843			airo_print_dbg(dev->name, "New channel value of %d is invalid!",
5844				fwrq->m);
5845			rc = -EINVAL;
5846		} else {
5847			readConfigRid(local, 1);
5848			/* Yes ! We can set it !!! */
5849			local->config.channelSet = cpu_to_le16(channel);
5850			set_bit (FLAG_COMMIT, &local->flags);
5851		}
5852	}
5853	return rc;
5854}
5855
5856/*------------------------------------------------------------------*/
5857/*
5858 * Wireless Handler : get frequency
5859 */
5860static int airo_get_freq(struct net_device *dev,
5861			 struct iw_request_info *info,
5862			 struct iw_freq *fwrq,
5863			 char *extra)
5864{
5865	struct airo_info *local = dev->ml_priv;
5866	StatusRid status_rid;		/* Card status info */
5867	int ch;
5868
5869	readConfigRid(local, 1);
5870	if ((local->config.opmode & MODE_CFG_MASK) == MODE_STA_ESS)
5871		status_rid.channel = local->config.channelSet;
5872	else
5873		readStatusRid(local, &status_rid, 1);
5874
5875	ch = le16_to_cpu(status_rid.channel);
5876	if ((ch > 0) && (ch < 15)) {
5877		fwrq->m = 100000 *
5878			ieee80211_channel_to_frequency(ch, NL80211_BAND_2GHZ);
5879		fwrq->e = 1;
5880	} else {
5881		fwrq->m = ch;
5882		fwrq->e = 0;
5883	}
5884
5885	return 0;
5886}
5887
5888/*------------------------------------------------------------------*/
5889/*
5890 * Wireless Handler : set ESSID
5891 */
5892static int airo_set_essid(struct net_device *dev,
5893			  struct iw_request_info *info,
5894			  struct iw_point *dwrq,
5895			  char *extra)
5896{
5897	struct airo_info *local = dev->ml_priv;
5898	SsidRid SSID_rid;		/* SSIDs */
5899
5900	/* Reload the list of current SSID */
5901	readSsidRid(local, &SSID_rid);
5902
5903	/* Check if we asked for `any' */
5904	if (dwrq->flags == 0) {
5905		/* Just send an empty SSID list */
5906		memset(&SSID_rid, 0, sizeof(SSID_rid));
5907	} else {
5908		unsigned index = (dwrq->flags & IW_ENCODE_INDEX) - 1;
5909
5910		/* Check the size of the string */
5911		if (dwrq->length > IW_ESSID_MAX_SIZE)
5912			return -E2BIG ;
5913
5914		/* Check if index is valid */
5915		if (index >= ARRAY_SIZE(SSID_rid.ssids))
5916			return -EINVAL;
5917
5918		/* Set the SSID */
5919		memset(SSID_rid.ssids[index].ssid, 0,
5920		       sizeof(SSID_rid.ssids[index].ssid));
5921		memcpy(SSID_rid.ssids[index].ssid, extra, dwrq->length);
5922		SSID_rid.ssids[index].len = cpu_to_le16(dwrq->length);
5923	}
5924	SSID_rid.len = cpu_to_le16(sizeof(SSID_rid));
5925	/* Write it to the card */
5926	disable_MAC(local, 1);
5927	writeSsidRid(local, &SSID_rid, 1);
5928	enable_MAC(local, 1);
5929
5930	return 0;
5931}
5932
5933/*------------------------------------------------------------------*/
5934/*
5935 * Wireless Handler : get ESSID
5936 */
5937static int airo_get_essid(struct net_device *dev,
5938			  struct iw_request_info *info,
5939			  struct iw_point *dwrq,
5940			  char *extra)
5941{
5942	struct airo_info *local = dev->ml_priv;
5943	StatusRid status_rid;		/* Card status info */
5944
5945	readStatusRid(local, &status_rid, 1);
5946
5947	/* Note : if dwrq->flags != 0, we should
5948	 * get the relevant SSID from the SSID list... */
5949
5950	/* Get the current SSID */
5951	memcpy(extra, status_rid.SSID, le16_to_cpu(status_rid.SSIDlen));
5952	/* If none, we may want to get the one that was set */
5953
5954	/* Push it out ! */
5955	dwrq->length = le16_to_cpu(status_rid.SSIDlen);
5956	dwrq->flags = 1; /* active */
5957
5958	return 0;
5959}
5960
5961/*------------------------------------------------------------------*/
5962/*
5963 * Wireless Handler : set AP address
5964 */
5965static int airo_set_wap(struct net_device *dev,
5966			struct iw_request_info *info,
5967			struct sockaddr *awrq,
5968			char *extra)
5969{
5970	struct airo_info *local = dev->ml_priv;
5971	Cmd cmd;
5972	Resp rsp;
5973	APListRid *APList_rid = &local->APList;
5974
5975	if (awrq->sa_family != ARPHRD_ETHER)
5976		return -EINVAL;
5977	else if (is_broadcast_ether_addr(awrq->sa_data) ||
5978		 is_zero_ether_addr(awrq->sa_data)) {
5979		memset(&cmd, 0, sizeof(cmd));
5980		cmd.cmd = CMD_LOSE_SYNC;
5981		if (down_interruptible(&local->sem))
5982			return -ERESTARTSYS;
5983		issuecommand(local, &cmd, &rsp, true);
5984		up(&local->sem);
5985	} else {
5986		memset(APList_rid, 0, sizeof(*APList_rid));
5987		APList_rid->len = cpu_to_le16(sizeof(*APList_rid));
5988		memcpy(APList_rid->ap[0], awrq->sa_data, ETH_ALEN);
5989		disable_MAC(local, 1);
5990		writeAPListRid(local, APList_rid, 1);
5991		enable_MAC(local, 1);
5992	}
5993	return 0;
5994}
5995
5996/*------------------------------------------------------------------*/
5997/*
5998 * Wireless Handler : get AP address
5999 */
6000static int airo_get_wap(struct net_device *dev,
6001			struct iw_request_info *info,
6002			struct sockaddr *awrq,
6003			char *extra)
6004{
6005	struct airo_info *local = dev->ml_priv;
6006	StatusRid status_rid;		/* Card status info */
6007
6008	readStatusRid(local, &status_rid, 1);
6009
6010	/* Tentative. This seems to work, wow, I'm lucky !!! */
6011	memcpy(awrq->sa_data, status_rid.bssid[0], ETH_ALEN);
6012	awrq->sa_family = ARPHRD_ETHER;
6013
6014	return 0;
6015}
6016
6017/*------------------------------------------------------------------*/
6018/*
6019 * Wireless Handler : set Nickname
6020 */
6021static int airo_set_nick(struct net_device *dev,
6022			 struct iw_request_info *info,
6023			 struct iw_point *dwrq,
6024			 char *extra)
6025{
6026	struct airo_info *local = dev->ml_priv;
6027
6028	/* Check the size of the string */
6029	if (dwrq->length > 16) {
6030		return -E2BIG;
6031	}
6032	readConfigRid(local, 1);
6033	memset(local->config.nodeName, 0, sizeof(local->config.nodeName));
6034	memcpy(local->config.nodeName, extra, dwrq->length);
6035	set_bit (FLAG_COMMIT, &local->flags);
6036
6037	return -EINPROGRESS;		/* Call commit handler */
6038}
6039
6040/*------------------------------------------------------------------*/
6041/*
6042 * Wireless Handler : get Nickname
6043 */
6044static int airo_get_nick(struct net_device *dev,
6045			 struct iw_request_info *info,
6046			 struct iw_point *dwrq,
6047			 char *extra)
6048{
6049	struct airo_info *local = dev->ml_priv;
6050
6051	readConfigRid(local, 1);
6052	strncpy(extra, local->config.nodeName, 16);
6053	extra[16] = '\0';
6054	dwrq->length = strlen(extra);
6055
6056	return 0;
6057}
6058
6059/*------------------------------------------------------------------*/
6060/*
6061 * Wireless Handler : set Bit-Rate
6062 */
6063static int airo_set_rate(struct net_device *dev,
6064			 struct iw_request_info *info,
6065			 struct iw_param *vwrq,
6066			 char *extra)
6067{
6068	struct airo_info *local = dev->ml_priv;
6069	CapabilityRid cap_rid;		/* Card capability info */
6070	u8	brate = 0;
6071	int	i;
6072
6073	/* First : get a valid bit rate value */
6074	readCapabilityRid(local, &cap_rid, 1);
6075
6076	/* Which type of value ? */
6077	if ((vwrq->value < 8) && (vwrq->value >= 0)) {
6078		/* Setting by rate index */
6079		/* Find value in the magic rate table */
6080		brate = cap_rid.supportedRates[vwrq->value];
6081	} else {
6082		/* Setting by frequency value */
6083		u8	normvalue = (u8) (vwrq->value/500000);
6084
6085		/* Check if rate is valid */
6086		for (i = 0 ; i < 8 ; i++) {
6087			if (normvalue == cap_rid.supportedRates[i]) {
6088				brate = normvalue;
6089				break;
6090			}
6091		}
6092	}
6093	/* -1 designed the max rate (mostly auto mode) */
6094	if (vwrq->value == -1) {
6095		/* Get the highest available rate */
6096		for (i = 0 ; i < 8 ; i++) {
6097			if (cap_rid.supportedRates[i] == 0)
6098				break;
6099		}
6100		if (i != 0)
6101			brate = cap_rid.supportedRates[i - 1];
6102	}
6103	/* Check that it is valid */
6104	if (brate == 0) {
6105		return -EINVAL;
6106	}
6107
6108	readConfigRid(local, 1);
6109	/* Now, check if we want a fixed or auto value */
6110	if (vwrq->fixed == 0) {
6111		/* Fill all the rates up to this max rate */
6112		memset(local->config.rates, 0, 8);
6113		for (i = 0 ; i < 8 ; i++) {
6114			local->config.rates[i] = cap_rid.supportedRates[i];
6115			if (local->config.rates[i] == brate)
6116				break;
6117		}
6118	} else {
6119		/* Fixed mode */
6120		/* One rate, fixed */
6121		memset(local->config.rates, 0, 8);
6122		local->config.rates[0] = brate;
6123	}
6124	set_bit (FLAG_COMMIT, &local->flags);
6125
6126	return -EINPROGRESS;		/* Call commit handler */
6127}
6128
6129/*------------------------------------------------------------------*/
6130/*
6131 * Wireless Handler : get Bit-Rate
6132 */
6133static int airo_get_rate(struct net_device *dev,
6134			 struct iw_request_info *info,
6135			 struct iw_param *vwrq,
6136			 char *extra)
6137{
6138	struct airo_info *local = dev->ml_priv;
6139	StatusRid status_rid;		/* Card status info */
6140
6141	readStatusRid(local, &status_rid, 1);
6142
6143	vwrq->value = le16_to_cpu(status_rid.currentXmitRate) * 500000;
6144	/* If more than one rate, set auto */
6145	readConfigRid(local, 1);
6146	vwrq->fixed = (local->config.rates[1] == 0);
6147
6148	return 0;
6149}
6150
6151/*------------------------------------------------------------------*/
6152/*
6153 * Wireless Handler : set RTS threshold
6154 */
6155static int airo_set_rts(struct net_device *dev,
6156			struct iw_request_info *info,
6157			struct iw_param *vwrq,
6158			char *extra)
6159{
6160	struct airo_info *local = dev->ml_priv;
6161	int rthr = vwrq->value;
6162
6163	if (vwrq->disabled)
6164		rthr = AIRO_DEF_MTU;
6165	if ((rthr < 0) || (rthr > AIRO_DEF_MTU)) {
6166		return -EINVAL;
6167	}
6168	readConfigRid(local, 1);
6169	local->config.rtsThres = cpu_to_le16(rthr);
6170	set_bit (FLAG_COMMIT, &local->flags);
6171
6172	return -EINPROGRESS;		/* Call commit handler */
6173}
6174
6175/*------------------------------------------------------------------*/
6176/*
6177 * Wireless Handler : get RTS threshold
6178 */
6179static int airo_get_rts(struct net_device *dev,
6180			struct iw_request_info *info,
6181			struct iw_param *vwrq,
6182			char *extra)
6183{
6184	struct airo_info *local = dev->ml_priv;
6185
6186	readConfigRid(local, 1);
6187	vwrq->value = le16_to_cpu(local->config.rtsThres);
6188	vwrq->disabled = (vwrq->value >= AIRO_DEF_MTU);
6189	vwrq->fixed = 1;
6190
6191	return 0;
6192}
6193
6194/*------------------------------------------------------------------*/
6195/*
6196 * Wireless Handler : set Fragmentation threshold
6197 */
6198static int airo_set_frag(struct net_device *dev,
6199			 struct iw_request_info *info,
6200			 struct iw_param *vwrq,
6201			 char *extra)
6202{
6203	struct airo_info *local = dev->ml_priv;
6204	int fthr = vwrq->value;
6205
6206	if (vwrq->disabled)
6207		fthr = AIRO_DEF_MTU;
6208	if ((fthr < 256) || (fthr > AIRO_DEF_MTU)) {
6209		return -EINVAL;
6210	}
6211	fthr &= ~0x1;	/* Get an even value - is it really needed ??? */
6212	readConfigRid(local, 1);
6213	local->config.fragThresh = cpu_to_le16(fthr);
6214	set_bit (FLAG_COMMIT, &local->flags);
6215
6216	return -EINPROGRESS;		/* Call commit handler */
6217}
6218
6219/*------------------------------------------------------------------*/
6220/*
6221 * Wireless Handler : get Fragmentation threshold
6222 */
6223static int airo_get_frag(struct net_device *dev,
6224			 struct iw_request_info *info,
6225			 struct iw_param *vwrq,
6226			 char *extra)
6227{
6228	struct airo_info *local = dev->ml_priv;
6229
6230	readConfigRid(local, 1);
6231	vwrq->value = le16_to_cpu(local->config.fragThresh);
6232	vwrq->disabled = (vwrq->value >= AIRO_DEF_MTU);
6233	vwrq->fixed = 1;
6234
6235	return 0;
6236}
6237
6238/*------------------------------------------------------------------*/
6239/*
6240 * Wireless Handler : set Mode of Operation
6241 */
6242static int airo_set_mode(struct net_device *dev,
6243			 struct iw_request_info *info,
6244			 __u32 *uwrq,
6245			 char *extra)
6246{
6247	struct airo_info *local = dev->ml_priv;
6248	int reset = 0;
6249
6250	readConfigRid(local, 1);
6251	if (sniffing_mode(local))
6252		reset = 1;
6253
6254	switch(*uwrq) {
6255		case IW_MODE_ADHOC:
6256			local->config.opmode &= ~MODE_CFG_MASK;
6257			local->config.opmode |= MODE_STA_IBSS;
6258			local->config.rmode &= ~RXMODE_FULL_MASK;
6259			local->config.scanMode = SCANMODE_ACTIVE;
6260			clear_bit (FLAG_802_11, &local->flags);
6261			break;
6262		case IW_MODE_INFRA:
6263			local->config.opmode &= ~MODE_CFG_MASK;
6264			local->config.opmode |= MODE_STA_ESS;
6265			local->config.rmode &= ~RXMODE_FULL_MASK;
6266			local->config.scanMode = SCANMODE_ACTIVE;
6267			clear_bit (FLAG_802_11, &local->flags);
6268			break;
6269		case IW_MODE_MASTER:
6270			local->config.opmode &= ~MODE_CFG_MASK;
6271			local->config.opmode |= MODE_AP;
6272			local->config.rmode &= ~RXMODE_FULL_MASK;
6273			local->config.scanMode = SCANMODE_ACTIVE;
6274			clear_bit (FLAG_802_11, &local->flags);
6275			break;
6276		case IW_MODE_REPEAT:
6277			local->config.opmode &= ~MODE_CFG_MASK;
6278			local->config.opmode |= MODE_AP_RPTR;
6279			local->config.rmode &= ~RXMODE_FULL_MASK;
6280			local->config.scanMode = SCANMODE_ACTIVE;
6281			clear_bit (FLAG_802_11, &local->flags);
6282			break;
6283		case IW_MODE_MONITOR:
6284			local->config.opmode &= ~MODE_CFG_MASK;
6285			local->config.opmode |= MODE_STA_ESS;
6286			local->config.rmode &= ~RXMODE_FULL_MASK;
6287			local->config.rmode |= RXMODE_RFMON | RXMODE_DISABLE_802_3_HEADER;
6288			local->config.scanMode = SCANMODE_PASSIVE;
6289			set_bit (FLAG_802_11, &local->flags);
6290			break;
6291		default:
6292			return -EINVAL;
6293	}
6294	if (reset)
6295		set_bit (FLAG_RESET, &local->flags);
6296	set_bit (FLAG_COMMIT, &local->flags);
6297
6298	return -EINPROGRESS;		/* Call commit handler */
6299}
6300
6301/*------------------------------------------------------------------*/
6302/*
6303 * Wireless Handler : get Mode of Operation
6304 */
6305static int airo_get_mode(struct net_device *dev,
6306			 struct iw_request_info *info,
6307			 __u32 *uwrq,
6308			 char *extra)
6309{
6310	struct airo_info *local = dev->ml_priv;
6311
6312	readConfigRid(local, 1);
6313	/* If not managed, assume it's ad-hoc */
6314	switch (local->config.opmode & MODE_CFG_MASK) {
6315		case MODE_STA_ESS:
6316			*uwrq = IW_MODE_INFRA;
6317			break;
6318		case MODE_AP:
6319			*uwrq = IW_MODE_MASTER;
6320			break;
6321		case MODE_AP_RPTR:
6322			*uwrq = IW_MODE_REPEAT;
6323			break;
6324		default:
6325			*uwrq = IW_MODE_ADHOC;
6326	}
6327
6328	return 0;
6329}
6330
6331static inline int valid_index(struct airo_info *ai, int index)
6332{
6333	return (index >= 0) && (index <= ai->max_wep_idx);
6334}
6335
6336/*------------------------------------------------------------------*/
6337/*
6338 * Wireless Handler : set Encryption Key
6339 */
6340static int airo_set_encode(struct net_device *dev,
6341			   struct iw_request_info *info,
6342			   struct iw_point *dwrq,
6343			   char *extra)
6344{
6345	struct airo_info *local = dev->ml_priv;
6346	int perm = (dwrq->flags & IW_ENCODE_TEMP ? 0 : 1);
6347	__le16 currentAuthType = local->config.authType;
6348	int rc = 0;
6349
6350	if (!local->wep_capable)
6351		return -EOPNOTSUPP;
6352
6353	readConfigRid(local, 1);
6354
6355	/* Basic checking: do we have a key to set ?
6356	 * Note : with the new API, it's impossible to get a NULL pointer.
6357	 * Therefore, we need to check a key size == 0 instead.
6358	 * New version of iwconfig properly set the IW_ENCODE_NOKEY flag
6359	 * when no key is present (only change flags), but older versions
6360	 * don't do it. - Jean II */
6361	if (dwrq->length > 0) {
6362		wep_key_t key;
6363		int index = (dwrq->flags & IW_ENCODE_INDEX) - 1;
6364		int current_index;
6365
6366		/* Check the size of the key */
6367		if (dwrq->length > MAX_KEY_SIZE) {
6368			return -EINVAL;
6369		}
6370
6371		current_index = get_wep_tx_idx(local);
6372		if (current_index < 0)
6373			current_index = 0;
6374
6375		/* Check the index (none -> use current) */
6376		if (!valid_index(local, index))
6377			index = current_index;
6378
6379		/* Set the length */
6380		if (dwrq->length > MIN_KEY_SIZE)
6381			key.len = MAX_KEY_SIZE;
6382		else
6383			key.len = MIN_KEY_SIZE;
6384		/* Check if the key is not marked as invalid */
6385		if (!(dwrq->flags & IW_ENCODE_NOKEY)) {
6386			/* Cleanup */
6387			memset(key.key, 0, MAX_KEY_SIZE);
6388			/* Copy the key in the driver */
6389			memcpy(key.key, extra, dwrq->length);
6390			/* Send the key to the card */
6391			rc = set_wep_key(local, index, key.key, key.len, perm, 1);
6392			if (rc < 0) {
6393				airo_print_err(local->dev->name, "failed to set"
6394				               " WEP key at index %d: %d.",
6395				               index, rc);
6396				return rc;
6397			}
6398		}
6399		/* WE specify that if a valid key is set, encryption
6400		 * should be enabled (user may turn it off later)
6401		 * This is also how "iwconfig ethX key on" works */
6402		if ((index == current_index) && (key.len > 0) &&
6403		   (local->config.authType == AUTH_OPEN))
6404			set_auth_type(local, AUTH_ENCRYPT);
6405	} else {
6406		/* Do we want to just set the transmit key index ? */
6407		int index = (dwrq->flags & IW_ENCODE_INDEX) - 1;
6408		if (valid_index(local, index)) {
6409			rc = set_wep_tx_idx(local, index, perm, 1);
6410			if (rc < 0) {
6411				airo_print_err(local->dev->name, "failed to set"
6412				               " WEP transmit index to %d: %d.",
6413				               index, rc);
6414				return rc;
6415			}
6416		} else {
6417			/* Don't complain if only change the mode */
6418			if (!(dwrq->flags & IW_ENCODE_MODE))
6419				return -EINVAL;
6420		}
6421	}
6422	/* Read the flags */
6423	if (dwrq->flags & IW_ENCODE_DISABLED)
6424		set_auth_type(local, AUTH_OPEN);	/* disable encryption */
6425	if (dwrq->flags & IW_ENCODE_RESTRICTED)
6426		set_auth_type(local, AUTH_SHAREDKEY);	/* Only Both */
6427	if (dwrq->flags & IW_ENCODE_OPEN)
6428		set_auth_type(local, AUTH_ENCRYPT);	/* Only Wep */
6429	/* Commit the changes to flags if needed */
6430	if (local->config.authType != currentAuthType)
6431		set_bit (FLAG_COMMIT, &local->flags);
6432	return -EINPROGRESS;		/* Call commit handler */
6433}
6434
6435/*------------------------------------------------------------------*/
6436/*
6437 * Wireless Handler : get Encryption Key
6438 */
6439static int airo_get_encode(struct net_device *dev,
6440			   struct iw_request_info *info,
6441			   struct iw_point *dwrq,
6442			   char *extra)
6443{
6444	struct airo_info *local = dev->ml_priv;
6445	int index = (dwrq->flags & IW_ENCODE_INDEX) - 1;
6446	int wep_key_len;
6447	u8 buf[16];
6448
6449	if (!local->wep_capable)
6450		return -EOPNOTSUPP;
6451
6452	readConfigRid(local, 1);
6453
6454	/* Check encryption mode */
6455	switch(local->config.authType)	{
6456		case AUTH_ENCRYPT:
6457			dwrq->flags = IW_ENCODE_OPEN;
6458			break;
6459		case AUTH_SHAREDKEY:
6460			dwrq->flags = IW_ENCODE_RESTRICTED;
6461			break;
6462		default:
6463		case AUTH_OPEN:
6464			dwrq->flags = IW_ENCODE_DISABLED;
6465			break;
6466	}
6467	/* We can't return the key, so set the proper flag and return zero */
6468	dwrq->flags |= IW_ENCODE_NOKEY;
6469	memset(extra, 0, 16);
6470
6471	/* Which key do we want ? -1 -> tx index */
6472	if (!valid_index(local, index)) {
6473		index = get_wep_tx_idx(local);
6474		if (index < 0)
6475			index = 0;
6476	}
6477	dwrq->flags |= index + 1;
6478
6479	/* Copy the key to the user buffer */
6480	wep_key_len = get_wep_key(local, index, &buf[0], sizeof(buf));
6481	if (wep_key_len < 0) {
6482		dwrq->length = 0;
6483	} else {
6484		dwrq->length = wep_key_len;
6485		memcpy(extra, buf, dwrq->length);
6486	}
6487
6488	return 0;
6489}
6490
6491/*------------------------------------------------------------------*/
6492/*
6493 * Wireless Handler : set extended Encryption parameters
6494 */
6495static int airo_set_encodeext(struct net_device *dev,
6496			   struct iw_request_info *info,
6497			    union iwreq_data *wrqu,
6498			    char *extra)
6499{
6500	struct airo_info *local = dev->ml_priv;
6501	struct iw_point *encoding = &wrqu->encoding;
6502	struct iw_encode_ext *ext = (struct iw_encode_ext *)extra;
6503	int perm = (encoding->flags & IW_ENCODE_TEMP ? 0 : 1);
6504	__le16 currentAuthType = local->config.authType;
6505	int idx, key_len, alg = ext->alg, set_key = 1, rc;
6506	wep_key_t key;
6507
6508	if (!local->wep_capable)
6509		return -EOPNOTSUPP;
6510
6511	readConfigRid(local, 1);
6512
6513	/* Determine and validate the key index */
6514	idx = encoding->flags & IW_ENCODE_INDEX;
6515	if (idx) {
6516		if (!valid_index(local, idx - 1))
6517			return -EINVAL;
6518		idx--;
6519	} else {
6520		idx = get_wep_tx_idx(local);
6521		if (idx < 0)
6522			idx = 0;
6523	}
6524
6525	if (encoding->flags & IW_ENCODE_DISABLED)
6526		alg = IW_ENCODE_ALG_NONE;
6527
6528	if (ext->ext_flags & IW_ENCODE_EXT_SET_TX_KEY) {
6529		/* Only set transmit key index here, actual
6530		 * key is set below if needed.
6531		 */
6532		rc = set_wep_tx_idx(local, idx, perm, 1);
6533		if (rc < 0) {
6534			airo_print_err(local->dev->name, "failed to set "
6535			               "WEP transmit index to %d: %d.",
6536			               idx, rc);
6537			return rc;
6538		}
6539		set_key = ext->key_len > 0 ? 1 : 0;
6540	}
6541
6542	if (set_key) {
6543		/* Set the requested key first */
6544		memset(key.key, 0, MAX_KEY_SIZE);
6545		switch (alg) {
6546		case IW_ENCODE_ALG_NONE:
6547			key.len = 0;
6548			break;
6549		case IW_ENCODE_ALG_WEP:
6550			if (ext->key_len > MIN_KEY_SIZE) {
6551				key.len = MAX_KEY_SIZE;
6552			} else if (ext->key_len > 0) {
6553				key.len = MIN_KEY_SIZE;
6554			} else {
6555				return -EINVAL;
6556			}
6557			key_len = min (ext->key_len, key.len);
6558			memcpy(key.key, ext->key, key_len);
6559			break;
6560		default:
6561			return -EINVAL;
6562		}
6563		if (key.len == 0) {
6564			rc = set_wep_tx_idx(local, idx, perm, 1);
6565			if (rc < 0) {
6566				airo_print_err(local->dev->name,
6567					       "failed to set WEP transmit index to %d: %d.",
6568					       idx, rc);
6569				return rc;
6570			}
6571		} else {
6572			rc = set_wep_key(local, idx, key.key, key.len, perm, 1);
6573			if (rc < 0) {
6574				airo_print_err(local->dev->name,
6575					       "failed to set WEP key at index %d: %d.",
6576					       idx, rc);
6577				return rc;
6578			}
6579		}
6580	}
6581
6582	/* Read the flags */
6583	if (encoding->flags & IW_ENCODE_DISABLED)
6584		set_auth_type(local, AUTH_OPEN);	/* disable encryption */
6585	if (encoding->flags & IW_ENCODE_RESTRICTED)
6586		set_auth_type(local, AUTH_SHAREDKEY);	/* Only Both */
6587	if (encoding->flags & IW_ENCODE_OPEN)
6588		set_auth_type(local, AUTH_ENCRYPT);
6589	/* Commit the changes to flags if needed */
6590	if (local->config.authType != currentAuthType)
6591		set_bit (FLAG_COMMIT, &local->flags);
6592
6593	return -EINPROGRESS;
6594}
6595
6596
6597/*------------------------------------------------------------------*/
6598/*
6599 * Wireless Handler : get extended Encryption parameters
6600 */
6601static int airo_get_encodeext(struct net_device *dev,
6602			    struct iw_request_info *info,
6603			    union iwreq_data *wrqu,
6604			    char *extra)
6605{
6606	struct airo_info *local = dev->ml_priv;
6607	struct iw_point *encoding = &wrqu->encoding;
6608	struct iw_encode_ext *ext = (struct iw_encode_ext *)extra;
6609	int idx, max_key_len, wep_key_len;
6610	u8 buf[16];
6611
6612	if (!local->wep_capable)
6613		return -EOPNOTSUPP;
6614
6615	readConfigRid(local, 1);
6616
6617	max_key_len = encoding->length - sizeof(*ext);
6618	if (max_key_len < 0)
6619		return -EINVAL;
6620
6621	idx = encoding->flags & IW_ENCODE_INDEX;
6622	if (idx) {
6623		if (!valid_index(local, idx - 1))
6624			return -EINVAL;
6625		idx--;
6626	} else {
6627		idx = get_wep_tx_idx(local);
6628		if (idx < 0)
6629			idx = 0;
6630	}
6631
6632	encoding->flags = idx + 1;
6633	memset(ext, 0, sizeof(*ext));
6634
6635	/* Check encryption mode */
6636	switch(local->config.authType) {
6637		case AUTH_ENCRYPT:
6638			encoding->flags = IW_ENCODE_ALG_WEP | IW_ENCODE_ENABLED;
6639			break;
6640		case AUTH_SHAREDKEY:
6641			encoding->flags = IW_ENCODE_ALG_WEP | IW_ENCODE_ENABLED;
6642			break;
6643		default:
6644		case AUTH_OPEN:
6645			encoding->flags = IW_ENCODE_ALG_NONE | IW_ENCODE_DISABLED;
6646			break;
6647	}
6648	/* We can't return the key, so set the proper flag and return zero */
6649	encoding->flags |= IW_ENCODE_NOKEY;
6650	memset(extra, 0, 16);
6651
6652	/* Copy the key to the user buffer */
6653	wep_key_len = get_wep_key(local, idx, &buf[0], sizeof(buf));
6654	if (wep_key_len < 0) {
6655		ext->key_len = 0;
6656	} else {
6657		ext->key_len = wep_key_len;
6658		memcpy(extra, buf, ext->key_len);
6659	}
6660
6661	return 0;
6662}
6663
6664
6665/*------------------------------------------------------------------*/
6666/*
6667 * Wireless Handler : set extended authentication parameters
6668 */
6669static int airo_set_auth(struct net_device *dev,
6670			       struct iw_request_info *info,
6671			       union iwreq_data *wrqu, char *extra)
6672{
6673	struct airo_info *local = dev->ml_priv;
6674	struct iw_param *param = &wrqu->param;
6675	__le16 currentAuthType = local->config.authType;
6676
6677	switch (param->flags & IW_AUTH_INDEX) {
6678	case IW_AUTH_WPA_VERSION:
6679	case IW_AUTH_CIPHER_PAIRWISE:
6680	case IW_AUTH_CIPHER_GROUP:
6681	case IW_AUTH_KEY_MGMT:
6682	case IW_AUTH_RX_UNENCRYPTED_EAPOL:
6683	case IW_AUTH_PRIVACY_INVOKED:
6684		/*
6685		 * airo does not use these parameters
6686		 */
6687		break;
6688
6689	case IW_AUTH_DROP_UNENCRYPTED:
6690		if (param->value) {
6691			/* Only change auth type if unencrypted */
6692			if (currentAuthType == AUTH_OPEN)
6693				set_auth_type(local, AUTH_ENCRYPT);
6694		} else {
6695			set_auth_type(local, AUTH_OPEN);
6696		}
6697
6698		/* Commit the changes to flags if needed */
6699		if (local->config.authType != currentAuthType)
6700			set_bit (FLAG_COMMIT, &local->flags);
6701		break;
6702
6703	case IW_AUTH_80211_AUTH_ALG: {
6704			if (param->value & IW_AUTH_ALG_SHARED_KEY) {
6705				set_auth_type(local, AUTH_SHAREDKEY);
6706			} else if (param->value & IW_AUTH_ALG_OPEN_SYSTEM) {
6707				/* We don't know here if WEP open system or
6708				 * unencrypted mode was requested - so use the
6709				 * last mode (of these two) used last time
6710				 */
6711				set_auth_type(local, local->last_auth);
6712			} else
6713				return -EINVAL;
6714
6715			/* Commit the changes to flags if needed */
6716			if (local->config.authType != currentAuthType)
6717				set_bit (FLAG_COMMIT, &local->flags);
6718			break;
6719		}
6720
6721	case IW_AUTH_WPA_ENABLED:
6722		/* Silently accept disable of WPA */
6723		if (param->value > 0)
6724			return -EOPNOTSUPP;
6725		break;
6726
6727	default:
6728		return -EOPNOTSUPP;
6729	}
6730	return -EINPROGRESS;
6731}
6732
6733
6734/*------------------------------------------------------------------*/
6735/*
6736 * Wireless Handler : get extended authentication parameters
6737 */
6738static int airo_get_auth(struct net_device *dev,
6739			       struct iw_request_info *info,
6740			       union iwreq_data *wrqu, char *extra)
6741{
6742	struct airo_info *local = dev->ml_priv;
6743	struct iw_param *param = &wrqu->param;
6744	__le16 currentAuthType = local->config.authType;
6745
6746	switch (param->flags & IW_AUTH_INDEX) {
6747	case IW_AUTH_DROP_UNENCRYPTED:
6748		switch (currentAuthType) {
6749		case AUTH_SHAREDKEY:
6750		case AUTH_ENCRYPT:
6751			param->value = 1;
6752			break;
6753		default:
6754			param->value = 0;
6755			break;
6756		}
6757		break;
6758
6759	case IW_AUTH_80211_AUTH_ALG:
6760		switch (currentAuthType) {
6761		case AUTH_SHAREDKEY:
6762			param->value = IW_AUTH_ALG_SHARED_KEY;
6763			break;
6764		case AUTH_ENCRYPT:
6765		default:
6766			param->value = IW_AUTH_ALG_OPEN_SYSTEM;
6767			break;
6768		}
6769		break;
6770
6771	case IW_AUTH_WPA_ENABLED:
6772		param->value = 0;
6773		break;
6774
6775	default:
6776		return -EOPNOTSUPP;
6777	}
6778	return 0;
6779}
6780
6781
6782/*------------------------------------------------------------------*/
6783/*
6784 * Wireless Handler : set Tx-Power
6785 */
6786static int airo_set_txpow(struct net_device *dev,
6787			  struct iw_request_info *info,
6788			  struct iw_param *vwrq,
6789			  char *extra)
6790{
6791	struct airo_info *local = dev->ml_priv;
6792	CapabilityRid cap_rid;		/* Card capability info */
6793	int i;
6794	int rc = -EINVAL;
6795	__le16 v = cpu_to_le16(vwrq->value);
6796
6797	readCapabilityRid(local, &cap_rid, 1);
6798
6799	if (vwrq->disabled) {
6800		set_bit (FLAG_RADIO_OFF, &local->flags);
6801		set_bit (FLAG_COMMIT, &local->flags);
6802		return -EINPROGRESS;		/* Call commit handler */
6803	}
6804	if (vwrq->flags != IW_TXPOW_MWATT) {
6805		return -EINVAL;
6806	}
6807	clear_bit (FLAG_RADIO_OFF, &local->flags);
6808	for (i = 0; i < 8 && cap_rid.txPowerLevels[i]; i++)
6809		if (v == cap_rid.txPowerLevels[i]) {
6810			readConfigRid(local, 1);
6811			local->config.txPower = v;
6812			set_bit (FLAG_COMMIT, &local->flags);
6813			rc = -EINPROGRESS;	/* Call commit handler */
6814			break;
6815		}
6816	return rc;
6817}
6818
6819/*------------------------------------------------------------------*/
6820/*
6821 * Wireless Handler : get Tx-Power
6822 */
6823static int airo_get_txpow(struct net_device *dev,
6824			  struct iw_request_info *info,
6825			  struct iw_param *vwrq,
6826			  char *extra)
6827{
6828	struct airo_info *local = dev->ml_priv;
6829
6830	readConfigRid(local, 1);
6831	vwrq->value = le16_to_cpu(local->config.txPower);
6832	vwrq->fixed = 1;	/* No power control */
6833	vwrq->disabled = test_bit(FLAG_RADIO_OFF, &local->flags);
6834	vwrq->flags = IW_TXPOW_MWATT;
6835
6836	return 0;
6837}
6838
6839/*------------------------------------------------------------------*/
6840/*
6841 * Wireless Handler : set Retry limits
6842 */
6843static int airo_set_retry(struct net_device *dev,
6844			  struct iw_request_info *info,
6845			  struct iw_param *vwrq,
6846			  char *extra)
6847{
6848	struct airo_info *local = dev->ml_priv;
6849	int rc = -EINVAL;
6850
6851	if (vwrq->disabled) {
6852		return -EINVAL;
6853	}
6854	readConfigRid(local, 1);
6855	if (vwrq->flags & IW_RETRY_LIMIT) {
6856		__le16 v = cpu_to_le16(vwrq->value);
6857		if (vwrq->flags & IW_RETRY_LONG)
6858			local->config.longRetryLimit = v;
6859		else if (vwrq->flags & IW_RETRY_SHORT)
6860			local->config.shortRetryLimit = v;
6861		else {
6862			/* No modifier : set both */
6863			local->config.longRetryLimit = v;
6864			local->config.shortRetryLimit = v;
6865		}
6866		set_bit (FLAG_COMMIT, &local->flags);
6867		rc = -EINPROGRESS;		/* Call commit handler */
6868	}
6869	if (vwrq->flags & IW_RETRY_LIFETIME) {
6870		local->config.txLifetime = cpu_to_le16(vwrq->value / 1024);
6871		set_bit (FLAG_COMMIT, &local->flags);
6872		rc = -EINPROGRESS;		/* Call commit handler */
6873	}
6874	return rc;
6875}
6876
6877/*------------------------------------------------------------------*/
6878/*
6879 * Wireless Handler : get Retry limits
6880 */
6881static int airo_get_retry(struct net_device *dev,
6882			  struct iw_request_info *info,
6883			  struct iw_param *vwrq,
6884			  char *extra)
6885{
6886	struct airo_info *local = dev->ml_priv;
6887
6888	vwrq->disabled = 0;      /* Can't be disabled */
6889
6890	readConfigRid(local, 1);
6891	/* Note : by default, display the min retry number */
6892	if ((vwrq->flags & IW_RETRY_TYPE) == IW_RETRY_LIFETIME) {
6893		vwrq->flags = IW_RETRY_LIFETIME;
6894		vwrq->value = le16_to_cpu(local->config.txLifetime) * 1024;
6895	} else if ((vwrq->flags & IW_RETRY_LONG)) {
6896		vwrq->flags = IW_RETRY_LIMIT | IW_RETRY_LONG;
6897		vwrq->value = le16_to_cpu(local->config.longRetryLimit);
6898	} else {
6899		vwrq->flags = IW_RETRY_LIMIT;
6900		vwrq->value = le16_to_cpu(local->config.shortRetryLimit);
6901		if (local->config.shortRetryLimit != local->config.longRetryLimit)
6902			vwrq->flags |= IW_RETRY_SHORT;
6903	}
6904
6905	return 0;
6906}
6907
6908/*------------------------------------------------------------------*/
6909/*
6910 * Wireless Handler : get range info
6911 */
6912static int airo_get_range(struct net_device *dev,
6913			  struct iw_request_info *info,
6914			  struct iw_point *dwrq,
6915			  char *extra)
6916{
6917	struct airo_info *local = dev->ml_priv;
6918	struct iw_range *range = (struct iw_range *) extra;
6919	CapabilityRid cap_rid;		/* Card capability info */
6920	int		i;
6921	int		k;
6922
6923	readCapabilityRid(local, &cap_rid, 1);
6924
6925	dwrq->length = sizeof(struct iw_range);
6926	memset(range, 0, sizeof(*range));
6927	range->min_nwid = 0x0000;
6928	range->max_nwid = 0x0000;
6929	range->num_channels = 14;
6930	/* Should be based on cap_rid.country to give only
6931	 * what the current card support */
6932	k = 0;
6933	for (i = 0; i < 14; i++) {
6934		range->freq[k].i = i + 1; /* List index */
6935		range->freq[k].m = 100000 *
6936		     ieee80211_channel_to_frequency(i + 1, NL80211_BAND_2GHZ);
6937		range->freq[k++].e = 1;	/* Values in MHz -> * 10^5 * 10 */
6938	}
6939	range->num_frequency = k;
6940
6941	range->sensitivity = 65535;
6942
6943	/* Hum... Should put the right values there */
6944	if (local->rssi)
6945		range->max_qual.qual = 100;	/* % */
6946	else
6947		range->max_qual.qual = airo_get_max_quality(&cap_rid);
6948	range->max_qual.level = 0x100 - 120;	/* -120 dBm */
6949	range->max_qual.noise = 0x100 - 120;	/* -120 dBm */
6950
6951	/* Experimental measurements - boundary 11/5.5 Mb/s */
6952	/* Note : with or without the (local->rssi), results
6953	 * are somewhat different. - Jean II */
6954	if (local->rssi) {
6955		range->avg_qual.qual = 50;		/* % */
6956		range->avg_qual.level = 0x100 - 70;	/* -70 dBm */
6957	} else {
6958		range->avg_qual.qual = airo_get_avg_quality(&cap_rid);
6959		range->avg_qual.level = 0x100 - 80;	/* -80 dBm */
6960	}
6961	range->avg_qual.noise = 0x100 - 85;		/* -85 dBm */
6962
6963	for (i = 0 ; i < 8 ; i++) {
6964		range->bitrate[i] = cap_rid.supportedRates[i] * 500000;
6965		if (range->bitrate[i] == 0)
6966			break;
6967	}
6968	range->num_bitrates = i;
6969
6970	/* Set an indication of the max TCP throughput
6971	 * in bit/s that we can expect using this interface.
6972	 * May be use for QoS stuff... Jean II */
6973	if (i > 2)
6974		range->throughput = 5000 * 1000;
6975	else
6976		range->throughput = 1500 * 1000;
6977
6978	range->min_rts = 0;
6979	range->max_rts = AIRO_DEF_MTU;
6980	range->min_frag = 256;
6981	range->max_frag = AIRO_DEF_MTU;
6982
6983	if (cap_rid.softCap & cpu_to_le16(2)) {
6984		// WEP: RC4 40 bits
6985		range->encoding_size[0] = 5;
6986		// RC4 ~128 bits
6987		if (cap_rid.softCap & cpu_to_le16(0x100)) {
6988			range->encoding_size[1] = 13;
6989			range->num_encoding_sizes = 2;
6990		} else
6991			range->num_encoding_sizes = 1;
6992		range->max_encoding_tokens =
6993			cap_rid.softCap & cpu_to_le16(0x80) ? 4 : 1;
6994	} else {
6995		range->num_encoding_sizes = 0;
6996		range->max_encoding_tokens = 0;
6997	}
6998	range->min_pmp = 0;
6999	range->max_pmp = 5000000;	/* 5 secs */
7000	range->min_pmt = 0;
7001	range->max_pmt = 65535 * 1024;	/* ??? */
7002	range->pmp_flags = IW_POWER_PERIOD;
7003	range->pmt_flags = IW_POWER_TIMEOUT;
7004	range->pm_capa = IW_POWER_PERIOD | IW_POWER_TIMEOUT | IW_POWER_ALL_R;
7005
7006	/* Transmit Power - values are in mW */
7007	for (i = 0 ; i < 8 ; i++) {
7008		range->txpower[i] = le16_to_cpu(cap_rid.txPowerLevels[i]);
7009		if (range->txpower[i] == 0)
7010			break;
7011	}
7012	range->num_txpower = i;
7013	range->txpower_capa = IW_TXPOW_MWATT;
7014	range->we_version_source = 19;
7015	range->we_version_compiled = WIRELESS_EXT;
7016	range->retry_capa = IW_RETRY_LIMIT | IW_RETRY_LIFETIME;
7017	range->retry_flags = IW_RETRY_LIMIT;
7018	range->r_time_flags = IW_RETRY_LIFETIME;
7019	range->min_retry = 1;
7020	range->max_retry = 65535;
7021	range->min_r_time = 1024;
7022	range->max_r_time = 65535 * 1024;
7023
7024	/* Event capability (kernel + driver) */
7025	range->event_capa[0] = (IW_EVENT_CAPA_K_0 |
7026				IW_EVENT_CAPA_MASK(SIOCGIWTHRSPY) |
7027				IW_EVENT_CAPA_MASK(SIOCGIWAP) |
7028				IW_EVENT_CAPA_MASK(SIOCGIWSCAN));
7029	range->event_capa[1] = IW_EVENT_CAPA_K_1;
7030	range->event_capa[4] = IW_EVENT_CAPA_MASK(IWEVTXDROP);
7031	return 0;
7032}
7033
7034/*------------------------------------------------------------------*/
7035/*
7036 * Wireless Handler : set Power Management
7037 */
7038static int airo_set_power(struct net_device *dev,
7039			  struct iw_request_info *info,
7040			  struct iw_param *vwrq,
7041			  char *extra)
7042{
7043	struct airo_info *local = dev->ml_priv;
7044
7045	readConfigRid(local, 1);
7046	if (vwrq->disabled) {
7047		if (sniffing_mode(local))
7048			return -EINVAL;
7049		local->config.powerSaveMode = POWERSAVE_CAM;
7050		local->config.rmode &= ~RXMODE_MASK;
7051		local->config.rmode |= RXMODE_BC_MC_ADDR;
7052		set_bit (FLAG_COMMIT, &local->flags);
7053		return -EINPROGRESS;		/* Call commit handler */
7054	}
7055	if ((vwrq->flags & IW_POWER_TYPE) == IW_POWER_TIMEOUT) {
7056		local->config.fastListenDelay = cpu_to_le16((vwrq->value + 500) / 1024);
7057		local->config.powerSaveMode = POWERSAVE_PSPCAM;
7058		set_bit (FLAG_COMMIT, &local->flags);
7059	} else if ((vwrq->flags & IW_POWER_TYPE) == IW_POWER_PERIOD) {
7060		local->config.fastListenInterval =
7061		local->config.listenInterval =
7062			cpu_to_le16((vwrq->value + 500) / 1024);
7063		local->config.powerSaveMode = POWERSAVE_PSPCAM;
7064		set_bit (FLAG_COMMIT, &local->flags);
7065	}
7066	switch (vwrq->flags & IW_POWER_MODE) {
7067		case IW_POWER_UNICAST_R:
7068			if (sniffing_mode(local))
7069				return -EINVAL;
7070			local->config.rmode &= ~RXMODE_MASK;
7071			local->config.rmode |= RXMODE_ADDR;
7072			set_bit (FLAG_COMMIT, &local->flags);
7073			break;
7074		case IW_POWER_ALL_R:
7075			if (sniffing_mode(local))
7076				return -EINVAL;
7077			local->config.rmode &= ~RXMODE_MASK;
7078			local->config.rmode |= RXMODE_BC_MC_ADDR;
7079			set_bit (FLAG_COMMIT, &local->flags);
7080			break;
7081		case IW_POWER_ON:
7082			/* This is broken, fixme ;-) */
7083			break;
7084		default:
7085			return -EINVAL;
7086	}
7087	// Note : we may want to factor local->need_commit here
7088	// Note2 : may also want to factor RXMODE_RFMON test
7089	return -EINPROGRESS;		/* Call commit handler */
7090}
7091
7092/*------------------------------------------------------------------*/
7093/*
7094 * Wireless Handler : get Power Management
7095 */
7096static int airo_get_power(struct net_device *dev,
7097			  struct iw_request_info *info,
7098			  struct iw_param *vwrq,
7099			  char *extra)
7100{
7101	struct airo_info *local = dev->ml_priv;
7102	__le16 mode;
7103
7104	readConfigRid(local, 1);
7105	mode = local->config.powerSaveMode;
7106	if ((vwrq->disabled = (mode == POWERSAVE_CAM)))
7107		return 0;
7108	if ((vwrq->flags & IW_POWER_TYPE) == IW_POWER_TIMEOUT) {
7109		vwrq->value = le16_to_cpu(local->config.fastListenDelay) * 1024;
7110		vwrq->flags = IW_POWER_TIMEOUT;
7111	} else {
7112		vwrq->value = le16_to_cpu(local->config.fastListenInterval) * 1024;
7113		vwrq->flags = IW_POWER_PERIOD;
7114	}
7115	if ((local->config.rmode & RXMODE_MASK) == RXMODE_ADDR)
7116		vwrq->flags |= IW_POWER_UNICAST_R;
7117	else
7118		vwrq->flags |= IW_POWER_ALL_R;
7119
7120	return 0;
7121}
7122
7123/*------------------------------------------------------------------*/
7124/*
7125 * Wireless Handler : set Sensitivity
7126 */
7127static int airo_set_sens(struct net_device *dev,
7128			 struct iw_request_info *info,
7129			 struct iw_param *vwrq,
7130			 char *extra)
7131{
7132	struct airo_info *local = dev->ml_priv;
7133
7134	readConfigRid(local, 1);
7135	local->config.rssiThreshold =
7136		cpu_to_le16(vwrq->disabled ? RSSI_DEFAULT : vwrq->value);
7137	set_bit (FLAG_COMMIT, &local->flags);
7138
7139	return -EINPROGRESS;		/* Call commit handler */
7140}
7141
7142/*------------------------------------------------------------------*/
7143/*
7144 * Wireless Handler : get Sensitivity
7145 */
7146static int airo_get_sens(struct net_device *dev,
7147			 struct iw_request_info *info,
7148			 struct iw_param *vwrq,
7149			 char *extra)
7150{
7151	struct airo_info *local = dev->ml_priv;
7152
7153	readConfigRid(local, 1);
7154	vwrq->value = le16_to_cpu(local->config.rssiThreshold);
7155	vwrq->disabled = (vwrq->value == 0);
7156	vwrq->fixed = 1;
7157
7158	return 0;
7159}
7160
7161/*------------------------------------------------------------------*/
7162/*
7163 * Wireless Handler : get AP List
7164 * Note : this is deprecated in favor of IWSCAN
7165 */
7166static int airo_get_aplist(struct net_device *dev,
7167			   struct iw_request_info *info,
7168			   struct iw_point *dwrq,
7169			   char *extra)
7170{
7171	struct airo_info *local = dev->ml_priv;
7172	struct sockaddr *address = (struct sockaddr *) extra;
7173	struct iw_quality *qual;
7174	BSSListRid BSSList;
7175	int i;
7176	int loseSync = capable(CAP_NET_ADMIN) ? 1: -1;
7177
7178	qual = kmalloc_array(IW_MAX_AP, sizeof(*qual), GFP_KERNEL);
7179	if (!qual)
7180		return -ENOMEM;
7181
7182	for (i = 0; i < IW_MAX_AP; i++) {
7183		u16 dBm;
7184		if (readBSSListRid(local, loseSync, &BSSList))
7185			break;
7186		loseSync = 0;
7187		memcpy(address[i].sa_data, BSSList.bssid, ETH_ALEN);
7188		address[i].sa_family = ARPHRD_ETHER;
7189		dBm = le16_to_cpu(BSSList.dBm);
7190		if (local->rssi) {
7191			qual[i].level = 0x100 - dBm;
7192			qual[i].qual = airo_dbm_to_pct(local->rssi, dBm);
7193			qual[i].updated = IW_QUAL_QUAL_UPDATED
7194					| IW_QUAL_LEVEL_UPDATED
7195					| IW_QUAL_DBM;
7196		} else {
7197			qual[i].level = (dBm + 321) / 2;
7198			qual[i].qual = 0;
7199			qual[i].updated = IW_QUAL_QUAL_INVALID
7200					| IW_QUAL_LEVEL_UPDATED
7201					| IW_QUAL_DBM;
7202		}
7203		qual[i].noise = local->wstats.qual.noise;
7204		if (BSSList.index == cpu_to_le16(0xffff))
7205			break;
7206	}
7207	if (!i) {
7208		StatusRid status_rid;		/* Card status info */
7209		readStatusRid(local, &status_rid, 1);
7210		for (i = 0;
7211		     i < min(IW_MAX_AP, 4) &&
7212			     (status_rid.bssid[i][0]
7213			      & status_rid.bssid[i][1]
7214			      & status_rid.bssid[i][2]
7215			      & status_rid.bssid[i][3]
7216			      & status_rid.bssid[i][4]
7217			      & status_rid.bssid[i][5])!=0xff &&
7218			     (status_rid.bssid[i][0]
7219			      | status_rid.bssid[i][1]
7220			      | status_rid.bssid[i][2]
7221			      | status_rid.bssid[i][3]
7222			      | status_rid.bssid[i][4]
7223			      | status_rid.bssid[i][5]);
7224		     i++) {
7225			memcpy(address[i].sa_data,
7226			       status_rid.bssid[i], ETH_ALEN);
7227			address[i].sa_family = ARPHRD_ETHER;
7228		}
7229	} else {
7230		dwrq->flags = 1; /* Should be define'd */
7231		memcpy(extra + sizeof(struct sockaddr) * i, qual,
7232		       sizeof(struct iw_quality) * i);
7233	}
7234	dwrq->length = i;
7235
7236	kfree(qual);
7237	return 0;
7238}
7239
7240/*------------------------------------------------------------------*/
7241/*
7242 * Wireless Handler : Initiate Scan
7243 */
7244static int airo_set_scan(struct net_device *dev,
7245			 struct iw_request_info *info,
7246			 struct iw_point *dwrq,
7247			 char *extra)
7248{
7249	struct airo_info *ai = dev->ml_priv;
7250	Cmd cmd;
7251	Resp rsp;
7252	int wake = 0;
7253	APListRid APList_rid_empty;
7254
7255	/* Note : you may have realised that, as this is a SET operation,
7256	 * this is privileged and therefore a normal user can't
7257	 * perform scanning.
7258	 * This is not an error, while the device perform scanning,
7259	 * traffic doesn't flow, so it's a perfect DoS...
7260	 * Jean II */
7261	if (ai->flags & FLAG_RADIO_MASK) return -ENETDOWN;
7262
7263	if (down_interruptible(&ai->sem))
7264		return -ERESTARTSYS;
7265
7266	/* If there's already a scan in progress, don't
7267	 * trigger another one. */
7268	if (ai->scan_timeout > 0)
7269		goto out;
7270
7271	/* Clear APList as it affects scan results */
7272	memset(&APList_rid_empty, 0, sizeof(APList_rid_empty));
7273	APList_rid_empty.len = cpu_to_le16(sizeof(APList_rid_empty));
7274	disable_MAC(ai, 2);
7275	writeAPListRid(ai, &APList_rid_empty, 0);
7276	enable_MAC(ai, 0);
7277
7278	/* Initiate a scan command */
7279	ai->scan_timeout = RUN_AT(3*HZ);
7280	memset(&cmd, 0, sizeof(cmd));
7281	cmd.cmd = CMD_LISTBSS;
7282	issuecommand(ai, &cmd, &rsp, true);
7283	wake = 1;
7284
7285out:
7286	up(&ai->sem);
7287	if (wake)
7288		wake_up_interruptible(&ai->thr_wait);
7289	return 0;
7290}
7291
7292/*------------------------------------------------------------------*/
7293/*
7294 * Translate scan data returned from the card to a card independent
7295 * format that the Wireless Tools will understand - Jean II
7296 */
7297static inline char *airo_translate_scan(struct net_device *dev,
7298					struct iw_request_info *info,
7299					char *current_ev,
7300					char *end_buf,
7301					BSSListRid *bss)
7302{
7303	struct airo_info *ai = dev->ml_priv;
7304	struct iw_event		iwe;		/* Temporary buffer */
7305	__le16			capabilities;
7306	char *			current_val;	/* For rates */
7307	int			i;
7308	char *		buf;
7309	u16 dBm;
7310
7311	/* First entry *MUST* be the AP MAC address */
7312	iwe.cmd = SIOCGIWAP;
7313	iwe.u.ap_addr.sa_family = ARPHRD_ETHER;
7314	memcpy(iwe.u.ap_addr.sa_data, bss->bssid, ETH_ALEN);
7315	current_ev = iwe_stream_add_event(info, current_ev, end_buf,
7316					  &iwe, IW_EV_ADDR_LEN);
7317
7318	/* Other entries will be displayed in the order we give them */
7319
7320	/* Add the ESSID */
7321	iwe.u.data.length = bss->ssidLen;
7322	if (iwe.u.data.length > 32)
7323		iwe.u.data.length = 32;
7324	iwe.cmd = SIOCGIWESSID;
7325	iwe.u.data.flags = 1;
7326	current_ev = iwe_stream_add_point(info, current_ev, end_buf,
7327					  &iwe, bss->ssid);
7328
7329	/* Add mode */
7330	iwe.cmd = SIOCGIWMODE;
7331	capabilities = bss->cap;
7332	if (capabilities & (CAP_ESS | CAP_IBSS)) {
7333		if (capabilities & CAP_ESS)
7334			iwe.u.mode = IW_MODE_MASTER;
7335		else
7336			iwe.u.mode = IW_MODE_ADHOC;
7337		current_ev = iwe_stream_add_event(info, current_ev, end_buf,
7338						  &iwe, IW_EV_UINT_LEN);
7339	}
7340
7341	/* Add frequency */
7342	iwe.cmd = SIOCGIWFREQ;
7343	iwe.u.freq.m = le16_to_cpu(bss->dsChannel);
7344	iwe.u.freq.m = 100000 *
7345	      ieee80211_channel_to_frequency(iwe.u.freq.m, NL80211_BAND_2GHZ);
7346	iwe.u.freq.e = 1;
7347	current_ev = iwe_stream_add_event(info, current_ev, end_buf,
7348					  &iwe, IW_EV_FREQ_LEN);
7349
7350	dBm = le16_to_cpu(bss->dBm);
7351
7352	/* Add quality statistics */
7353	iwe.cmd = IWEVQUAL;
7354	if (ai->rssi) {
7355		iwe.u.qual.level = 0x100 - dBm;
7356		iwe.u.qual.qual = airo_dbm_to_pct(ai->rssi, dBm);
7357		iwe.u.qual.updated = IW_QUAL_QUAL_UPDATED
7358				| IW_QUAL_LEVEL_UPDATED
7359				| IW_QUAL_DBM;
7360	} else {
7361		iwe.u.qual.level = (dBm + 321) / 2;
7362		iwe.u.qual.qual = 0;
7363		iwe.u.qual.updated = IW_QUAL_QUAL_INVALID
7364				| IW_QUAL_LEVEL_UPDATED
7365				| IW_QUAL_DBM;
7366	}
7367	iwe.u.qual.noise = ai->wstats.qual.noise;
7368	current_ev = iwe_stream_add_event(info, current_ev, end_buf,
7369					  &iwe, IW_EV_QUAL_LEN);
7370
7371	/* Add encryption capability */
7372	iwe.cmd = SIOCGIWENCODE;
7373	if (capabilities & CAP_PRIVACY)
7374		iwe.u.data.flags = IW_ENCODE_ENABLED | IW_ENCODE_NOKEY;
7375	else
7376		iwe.u.data.flags = IW_ENCODE_DISABLED;
7377	iwe.u.data.length = 0;
7378	current_ev = iwe_stream_add_point(info, current_ev, end_buf,
7379					  &iwe, bss->ssid);
7380
7381	/* Rate : stuffing multiple values in a single event require a bit
7382	 * more of magic - Jean II */
7383	current_val = current_ev + iwe_stream_lcp_len(info);
7384
7385	iwe.cmd = SIOCGIWRATE;
7386	/* Those two flags are ignored... */
7387	iwe.u.bitrate.fixed = iwe.u.bitrate.disabled = 0;
7388	/* Max 8 values */
7389	for (i = 0 ; i < 8 ; i++) {
7390		/* NULL terminated */
7391		if (bss->rates[i] == 0)
7392			break;
7393		/* Bit rate given in 500 kb/s units (+ 0x80) */
7394		iwe.u.bitrate.value = ((bss->rates[i] & 0x7f) * 500000);
7395		/* Add new value to event */
7396		current_val = iwe_stream_add_value(info, current_ev,
7397						   current_val, end_buf,
7398						   &iwe, IW_EV_PARAM_LEN);
7399	}
7400	/* Check if we added any event */
7401	if ((current_val - current_ev) > iwe_stream_lcp_len(info))
7402		current_ev = current_val;
7403
7404	/* Beacon interval */
7405	buf = kmalloc(30, GFP_KERNEL);
7406	if (buf) {
7407		iwe.cmd = IWEVCUSTOM;
7408		sprintf(buf, "bcn_int=%d", bss->beaconInterval);
7409		iwe.u.data.length = strlen(buf);
7410		current_ev = iwe_stream_add_point(info, current_ev, end_buf,
7411						  &iwe, buf);
7412		kfree(buf);
7413	}
7414
7415	/* Put WPA/RSN Information Elements into the event stream */
7416	if (test_bit(FLAG_WPA_CAPABLE, &ai->flags)) {
7417		unsigned int num_null_ies = 0;
7418		u16 length = sizeof (bss->extra.iep);
7419		u8 *ie = (void *)&bss->extra.iep;
7420
7421		while ((length >= 2) && (num_null_ies < 2)) {
7422			if (2 + ie[1] > length) {
7423				/* Invalid element, don't continue parsing IE */
7424				break;
7425			}
7426
7427			switch (ie[0]) {
7428			case WLAN_EID_SSID:
7429				/* Two zero-length SSID elements
7430				 * mean we're done parsing elements */
7431				if (!ie[1])
7432					num_null_ies++;
7433				break;
7434
7435			case WLAN_EID_VENDOR_SPECIFIC:
7436				if (ie[1] >= 4 &&
7437				    ie[2] == 0x00 &&
7438				    ie[3] == 0x50 &&
7439				    ie[4] == 0xf2 &&
7440				    ie[5] == 0x01) {
7441					iwe.cmd = IWEVGENIE;
7442					/* 64 is an arbitrary cut-off */
7443					iwe.u.data.length = min(ie[1] + 2,
7444								64);
7445					current_ev = iwe_stream_add_point(
7446							info, current_ev,
7447							end_buf, &iwe, ie);
7448				}
7449				break;
7450
7451			case WLAN_EID_RSN:
7452				iwe.cmd = IWEVGENIE;
7453				/* 64 is an arbitrary cut-off */
7454				iwe.u.data.length = min(ie[1] + 2, 64);
7455				current_ev = iwe_stream_add_point(
7456					info, current_ev, end_buf,
7457					&iwe, ie);
7458				break;
7459
7460			default:
7461				break;
7462			}
7463
7464			length -= 2 + ie[1];
7465			ie += 2 + ie[1];
7466		}
7467	}
7468	return current_ev;
7469}
7470
7471/*------------------------------------------------------------------*/
7472/*
7473 * Wireless Handler : Read Scan Results
7474 */
7475static int airo_get_scan(struct net_device *dev,
7476			 struct iw_request_info *info,
7477			 struct iw_point *dwrq,
7478			 char *extra)
7479{
7480	struct airo_info *ai = dev->ml_priv;
7481	BSSListElement *net;
7482	int err = 0;
7483	char *current_ev = extra;
7484
7485	/* If a scan is in-progress, return -EAGAIN */
7486	if (ai->scan_timeout > 0)
7487		return -EAGAIN;
7488
7489	if (down_interruptible(&ai->sem))
7490		return -EAGAIN;
7491
7492	list_for_each_entry (net, &ai->network_list, list) {
7493		/* Translate to WE format this entry */
7494		current_ev = airo_translate_scan(dev, info, current_ev,
7495						 extra + dwrq->length,
7496						 &net->bss);
7497
7498		/* Check if there is space for one more entry */
7499		if ((extra + dwrq->length - current_ev) <= IW_EV_ADDR_LEN) {
7500			/* Ask user space to try again with a bigger buffer */
7501			err = -E2BIG;
7502			goto out;
7503		}
7504	}
7505
7506	/* Length of data */
7507	dwrq->length = (current_ev - extra);
7508	dwrq->flags = 0;	/* todo */
7509
7510out:
7511	up(&ai->sem);
7512	return err;
7513}
7514
7515/*------------------------------------------------------------------*/
7516/*
7517 * Commit handler : called after a bunch of SET operations
7518 */
7519static int airo_config_commit(struct net_device *dev,
7520			      struct iw_request_info *info,	/* NULL */
7521			      void *zwrq,			/* NULL */
7522			      char *extra)			/* NULL */
7523{
7524	struct airo_info *local = dev->ml_priv;
7525
7526	if (!test_bit (FLAG_COMMIT, &local->flags))
7527		return 0;
7528
7529	/* Some of the "SET" function may have modified some of the
7530	 * parameters. It's now time to commit them in the card */
7531	disable_MAC(local, 1);
7532	if (test_bit (FLAG_RESET, &local->flags)) {
7533		SsidRid SSID_rid;
7534
7535		readSsidRid(local, &SSID_rid);
7536		if (test_bit(FLAG_MPI,&local->flags))
7537			setup_card(local, dev->dev_addr, 1);
7538		else
7539			reset_airo_card(dev);
7540		disable_MAC(local, 1);
7541		writeSsidRid(local, &SSID_rid, 1);
7542		writeAPListRid(local, &local->APList, 1);
7543	}
7544	if (down_interruptible(&local->sem))
7545		return -ERESTARTSYS;
7546	writeConfigRid(local, 0);
7547	enable_MAC(local, 0);
7548	if (test_bit (FLAG_RESET, &local->flags))
7549		airo_set_promisc(local, true);
7550	else
7551		up(&local->sem);
7552
7553	return 0;
7554}
7555
7556/*------------------------------------------------------------------*/
7557/*
7558 * Structures to export the Wireless Handlers
7559 */
7560
7561static const struct iw_priv_args airo_private_args[] = {
7562/*{ cmd,         set_args,                            get_args, name } */
7563  { AIROIOCTL, IW_PRIV_TYPE_BYTE | IW_PRIV_SIZE_FIXED | sizeof (aironet_ioctl),
7564    IW_PRIV_TYPE_BYTE | 2047, "airoioctl" },
7565  { AIROIDIFC, IW_PRIV_TYPE_BYTE | IW_PRIV_SIZE_FIXED | sizeof (aironet_ioctl),
7566    IW_PRIV_TYPE_INT | IW_PRIV_SIZE_FIXED | 1, "airoidifc" },
7567};
7568
7569static const iw_handler		airo_handler[] =
7570{
7571	(iw_handler) airo_config_commit,	/* SIOCSIWCOMMIT */
7572	(iw_handler) airo_get_name,		/* SIOCGIWNAME */
7573	(iw_handler) NULL,			/* SIOCSIWNWID */
7574	(iw_handler) NULL,			/* SIOCGIWNWID */
7575	(iw_handler) airo_set_freq,		/* SIOCSIWFREQ */
7576	(iw_handler) airo_get_freq,		/* SIOCGIWFREQ */
7577	(iw_handler) airo_set_mode,		/* SIOCSIWMODE */
7578	(iw_handler) airo_get_mode,		/* SIOCGIWMODE */
7579	(iw_handler) airo_set_sens,		/* SIOCSIWSENS */
7580	(iw_handler) airo_get_sens,		/* SIOCGIWSENS */
7581	(iw_handler) NULL,			/* SIOCSIWRANGE */
7582	(iw_handler) airo_get_range,		/* SIOCGIWRANGE */
7583	(iw_handler) NULL,			/* SIOCSIWPRIV */
7584	(iw_handler) NULL,			/* SIOCGIWPRIV */
7585	(iw_handler) NULL,			/* SIOCSIWSTATS */
7586	(iw_handler) NULL,			/* SIOCGIWSTATS */
7587	iw_handler_set_spy,			/* SIOCSIWSPY */
7588	iw_handler_get_spy,			/* SIOCGIWSPY */
7589	iw_handler_set_thrspy,			/* SIOCSIWTHRSPY */
7590	iw_handler_get_thrspy,			/* SIOCGIWTHRSPY */
7591	(iw_handler) airo_set_wap,		/* SIOCSIWAP */
7592	(iw_handler) airo_get_wap,		/* SIOCGIWAP */
7593	(iw_handler) NULL,			/* -- hole -- */
7594	(iw_handler) airo_get_aplist,		/* SIOCGIWAPLIST */
7595	(iw_handler) airo_set_scan,		/* SIOCSIWSCAN */
7596	(iw_handler) airo_get_scan,		/* SIOCGIWSCAN */
7597	(iw_handler) airo_set_essid,		/* SIOCSIWESSID */
7598	(iw_handler) airo_get_essid,		/* SIOCGIWESSID */
7599	(iw_handler) airo_set_nick,		/* SIOCSIWNICKN */
7600	(iw_handler) airo_get_nick,		/* SIOCGIWNICKN */
7601	(iw_handler) NULL,			/* -- hole -- */
7602	(iw_handler) NULL,			/* -- hole -- */
7603	(iw_handler) airo_set_rate,		/* SIOCSIWRATE */
7604	(iw_handler) airo_get_rate,		/* SIOCGIWRATE */
7605	(iw_handler) airo_set_rts,		/* SIOCSIWRTS */
7606	(iw_handler) airo_get_rts,		/* SIOCGIWRTS */
7607	(iw_handler) airo_set_frag,		/* SIOCSIWFRAG */
7608	(iw_handler) airo_get_frag,		/* SIOCGIWFRAG */
7609	(iw_handler) airo_set_txpow,		/* SIOCSIWTXPOW */
7610	(iw_handler) airo_get_txpow,		/* SIOCGIWTXPOW */
7611	(iw_handler) airo_set_retry,		/* SIOCSIWRETRY */
7612	(iw_handler) airo_get_retry,		/* SIOCGIWRETRY */
7613	(iw_handler) airo_set_encode,		/* SIOCSIWENCODE */
7614	(iw_handler) airo_get_encode,		/* SIOCGIWENCODE */
7615	(iw_handler) airo_set_power,		/* SIOCSIWPOWER */
7616	(iw_handler) airo_get_power,		/* SIOCGIWPOWER */
7617	(iw_handler) NULL,			/* -- hole -- */
7618	(iw_handler) NULL,			/* -- hole -- */
7619	(iw_handler) NULL,			/* SIOCSIWGENIE */
7620	(iw_handler) NULL,			/* SIOCGIWGENIE */
7621	(iw_handler) airo_set_auth,		/* SIOCSIWAUTH */
7622	(iw_handler) airo_get_auth,		/* SIOCGIWAUTH */
7623	(iw_handler) airo_set_encodeext,	/* SIOCSIWENCODEEXT */
7624	(iw_handler) airo_get_encodeext,	/* SIOCGIWENCODEEXT */
7625	(iw_handler) NULL,			/* SIOCSIWPMKSA */
7626};
7627
7628/* Note : don't describe AIROIDIFC and AIROOLDIDIFC in here.
7629 * We want to force the use of the ioctl code, because those can't be
7630 * won't work the iw_handler code (because they simultaneously read
7631 * and write data and iw_handler can't do that).
7632 * Note that it's perfectly legal to read/write on a single ioctl command,
7633 * you just can't use iwpriv and need to force it via the ioctl handler.
7634 * Jean II */
7635static const iw_handler		airo_private_handler[] =
7636{
7637	NULL,				/* SIOCIWFIRSTPRIV */
7638};
7639
7640static const struct iw_handler_def	airo_handler_def =
7641{
7642	.num_standard	= ARRAY_SIZE(airo_handler),
7643	.num_private	= ARRAY_SIZE(airo_private_handler),
7644	.num_private_args = ARRAY_SIZE(airo_private_args),
7645	.standard	= airo_handler,
7646	.private	= airo_private_handler,
7647	.private_args	= airo_private_args,
7648	.get_wireless_stats = airo_get_wireless_stats,
7649};
7650
7651/*
7652 * This defines the configuration part of the Wireless Extensions
7653 * Note : irq and spinlock protection will occur in the subroutines
7654 *
7655 * TODO :
7656 *	o Check input value more carefully and fill correct values in range
7657 *	o Test and shakeout the bugs (if any)
7658 *
7659 * Jean II
7660 *
7661 * Javier Achirica did a great job of merging code from the unnamed CISCO
7662 * developer that added support for flashing the card.
7663 */
7664static int airo_ioctl(struct net_device *dev, struct ifreq *rq, int cmd)
7665{
7666	int rc = 0;
7667	struct airo_info *ai = dev->ml_priv;
7668
7669	if (ai->power.event)
7670		return 0;
7671
7672	switch (cmd) {
7673#ifdef CISCO_EXT
7674	case AIROIDIFC:
7675#ifdef AIROOLDIDIFC
7676	case AIROOLDIDIFC:
7677#endif
7678	{
7679		int val = AIROMAGIC;
7680		aironet_ioctl com;
7681		if (copy_from_user(&com, rq->ifr_data, sizeof(com)))
7682			rc = -EFAULT;
7683		else if (copy_to_user(com.data, (char *)&val, sizeof(val)))
7684			rc = -EFAULT;
7685	}
7686	break;
7687
7688	case AIROIOCTL:
7689#ifdef AIROOLDIOCTL
7690	case AIROOLDIOCTL:
7691#endif
7692		/* Get the command struct and hand it off for evaluation by
7693		 * the proper subfunction
7694		 */
7695	{
7696		aironet_ioctl com;
7697		if (copy_from_user(&com, rq->ifr_data, sizeof(com))) {
7698			rc = -EFAULT;
7699			break;
7700		}
7701
7702		/* Separate R/W functions bracket legality here
7703		 */
7704		if (com.command == AIRORSWVERSION) {
7705			if (copy_to_user(com.data, swversion, sizeof(swversion)))
7706				rc = -EFAULT;
7707			else
7708				rc = 0;
7709		}
7710		else if (com.command <= AIRORRID)
7711			rc = readrids(dev,&com);
7712		else if (com.command >= AIROPCAP && com.command <= (AIROPLEAPUSR+2))
7713			rc = writerids(dev,&com);
7714		else if (com.command >= AIROFLSHRST && com.command <= AIRORESTART)
7715			rc = flashcard(dev,&com);
7716		else
7717			rc = -EINVAL;      /* Bad command in ioctl */
7718	}
7719	break;
7720#endif /* CISCO_EXT */
7721
7722	// All other calls are currently unsupported
7723	default:
7724		rc = -EOPNOTSUPP;
7725	}
7726	return rc;
7727}
7728
7729/*
7730 * Get the Wireless stats out of the driver
7731 * Note : irq and spinlock protection will occur in the subroutines
7732 *
7733 * TODO :
7734 *	o Check if work in Ad-Hoc mode (otherwise, use SPY, as in wvlan_cs)
7735 *
7736 * Jean
7737 */
7738static void airo_read_wireless_stats(struct airo_info *local)
7739{
7740	StatusRid status_rid;
7741	StatsRid stats_rid;
7742	CapabilityRid cap_rid;
7743	__le32 *vals = stats_rid.vals;
7744
7745	/* Get stats out of the card */
7746	if (local->power.event)
 
 
7747		return;
7748
7749	readCapabilityRid(local, &cap_rid, 0);
7750	readStatusRid(local, &status_rid, 0);
7751	readStatsRid(local, &stats_rid, RID_STATS, 0);
 
7752
7753	/* The status */
7754	local->wstats.status = le16_to_cpu(status_rid.mode);
7755
7756	/* Signal quality and co */
7757	if (local->rssi) {
7758		local->wstats.qual.level =
7759			airo_rssi_to_dbm(local->rssi,
7760					 le16_to_cpu(status_rid.sigQuality));
7761		/* normalizedSignalStrength appears to be a percentage */
7762		local->wstats.qual.qual =
7763			le16_to_cpu(status_rid.normalizedSignalStrength);
7764	} else {
7765		local->wstats.qual.level =
7766			(le16_to_cpu(status_rid.normalizedSignalStrength) + 321) / 2;
7767		local->wstats.qual.qual = airo_get_quality(&status_rid, &cap_rid);
7768	}
7769	if (le16_to_cpu(status_rid.len) >= 124) {
7770		local->wstats.qual.noise = 0x100 - status_rid.noisedBm;
7771		local->wstats.qual.updated = IW_QUAL_ALL_UPDATED | IW_QUAL_DBM;
7772	} else {
7773		local->wstats.qual.noise = 0;
7774		local->wstats.qual.updated = IW_QUAL_QUAL_UPDATED | IW_QUAL_LEVEL_UPDATED | IW_QUAL_NOISE_INVALID | IW_QUAL_DBM;
7775	}
7776
7777	/* Packets discarded in the wireless adapter due to wireless
7778	 * specific problems */
7779	local->wstats.discard.nwid = le32_to_cpu(vals[56]) +
7780				     le32_to_cpu(vals[57]) +
7781				     le32_to_cpu(vals[58]); /* SSID Mismatch */
7782	local->wstats.discard.code = le32_to_cpu(vals[6]);/* RxWepErr */
7783	local->wstats.discard.fragment = le32_to_cpu(vals[30]);
7784	local->wstats.discard.retries = le32_to_cpu(vals[10]);
7785	local->wstats.discard.misc = le32_to_cpu(vals[1]) +
7786				     le32_to_cpu(vals[32]);
7787	local->wstats.miss.beacon = le32_to_cpu(vals[34]);
7788}
7789
7790static struct iw_statistics *airo_get_wireless_stats(struct net_device *dev)
7791{
7792	struct airo_info *local =  dev->ml_priv;
7793
7794	if (!down_interruptible(&local->sem)) {
7795		airo_read_wireless_stats(local);
7796		up(&local->sem);
 
 
 
 
7797	}
 
7798	return &local->wstats;
7799}
7800
7801#ifdef CISCO_EXT
7802/*
7803 * This just translates from driver IOCTL codes to the command codes to
7804 * feed to the radio's host interface. Things can be added/deleted
7805 * as needed.  This represents the READ side of control I/O to
7806 * the card
7807 */
7808static int readrids(struct net_device *dev, aironet_ioctl *comp)
7809{
7810	unsigned short ridcode;
7811	unsigned char *iobuf;
7812	int len;
7813	struct airo_info *ai = dev->ml_priv;
7814
7815	if (test_bit(FLAG_FLASHING, &ai->flags))
7816		return -EIO;
7817
7818	switch(comp->command)
7819	{
7820	case AIROGCAP:      ridcode = RID_CAPABILITIES; break;
7821	case AIROGCFG:      ridcode = RID_CONFIG;
7822		if (test_bit(FLAG_COMMIT, &ai->flags)) {
7823			disable_MAC (ai, 1);
7824			writeConfigRid (ai, 1);
7825			enable_MAC(ai, 1);
7826		}
7827		break;
7828	case AIROGSLIST:    ridcode = RID_SSID;         break;
7829	case AIROGVLIST:    ridcode = RID_APLIST;       break;
7830	case AIROGDRVNAM:   ridcode = RID_DRVNAME;      break;
7831	case AIROGEHTENC:   ridcode = RID_ETHERENCAP;   break;
7832	case AIROGWEPKTMP:  ridcode = RID_WEP_TEMP;	break;
7833	case AIROGWEPKNV:   ridcode = RID_WEP_PERM;	break;
 
 
 
 
 
 
 
 
7834	case AIROGSTAT:     ridcode = RID_STATUS;       break;
7835	case AIROGSTATSD32: ridcode = RID_STATSDELTA;   break;
7836	case AIROGSTATSC32: ridcode = RID_STATS;        break;
7837	case AIROGMICSTATS:
7838		if (copy_to_user(comp->data, &ai->micstats,
7839				 min((int)comp->len, (int)sizeof(ai->micstats))))
7840			return -EFAULT;
7841		return 0;
7842	case AIRORRID:      ridcode = comp->ridnum;     break;
7843	default:
7844		return -EINVAL;
7845	}
7846
7847	if (ridcode == RID_WEP_TEMP || ridcode == RID_WEP_PERM) {
7848		/* Only super-user can read WEP keys */
7849		if (!capable(CAP_NET_ADMIN))
7850			return -EPERM;
7851	}
7852
7853	if ((iobuf = kzalloc(RIDSIZE, GFP_KERNEL)) == NULL)
7854		return -ENOMEM;
7855
7856	PC4500_readrid(ai, ridcode, iobuf, RIDSIZE, 1);
7857	/* get the count of bytes in the rid  docs say 1st 2 bytes is it.
7858	 * then return it to the user
7859	 * 9/22/2000 Honor user given length
7860	 */
7861	len = comp->len;
7862
7863	if (copy_to_user(comp->data, iobuf, min(len, (int)RIDSIZE))) {
7864		kfree (iobuf);
7865		return -EFAULT;
7866	}
7867	kfree (iobuf);
7868	return 0;
7869}
7870
7871/*
7872 * Danger Will Robinson write the rids here
7873 */
7874
7875static int writerids(struct net_device *dev, aironet_ioctl *comp)
7876{
7877	struct airo_info *ai = dev->ml_priv;
7878	int  ridcode;
7879        int  enabled;
7880	int (*writer)(struct airo_info *, u16 rid, const void *, int, int);
7881	unsigned char *iobuf;
7882
7883	/* Only super-user can write RIDs */
7884	if (!capable(CAP_NET_ADMIN))
7885		return -EPERM;
7886
7887	if (test_bit(FLAG_FLASHING, &ai->flags))
7888		return -EIO;
7889
7890	ridcode = 0;
7891	writer = do_writerid;
7892
7893	switch(comp->command)
7894	{
7895	case AIROPSIDS:     ridcode = RID_SSID;         break;
7896	case AIROPCAP:      ridcode = RID_CAPABILITIES; break;
7897	case AIROPAPLIST:   ridcode = RID_APLIST;       break;
7898	case AIROPCFG: ai->config.len = 0;
7899			    clear_bit(FLAG_COMMIT, &ai->flags);
7900			    ridcode = RID_CONFIG;       break;
7901	case AIROPWEPKEYNV: ridcode = RID_WEP_PERM;     break;
7902	case AIROPLEAPUSR:  ridcode = RID_LEAPUSERNAME; break;
7903	case AIROPLEAPPWD:  ridcode = RID_LEAPPASSWORD; break;
7904	case AIROPWEPKEY:   ridcode = RID_WEP_TEMP; writer = PC4500_writerid;
7905		break;
7906	case AIROPLEAPUSR+1: ridcode = 0xFF2A;          break;
7907	case AIROPLEAPUSR+2: ridcode = 0xFF2B;          break;
7908
7909		/* this is not really a rid but a command given to the card
7910		 * same with MAC off
7911		 */
7912	case AIROPMACON:
7913		if (enable_MAC(ai, 1) != 0)
7914			return -EIO;
7915		return 0;
7916
7917		/*
7918		 * Evidently this code in the airo driver does not get a symbol
7919		 * as disable_MAC. it's probably so short the compiler does not gen one.
7920		 */
7921	case AIROPMACOFF:
7922		disable_MAC(ai, 1);
7923		return 0;
7924
7925		/* This command merely clears the counts does not actually store any data
7926		 * only reads rid. But as it changes the cards state, I put it in the
7927		 * writerid routines.
7928		 */
7929	case AIROPSTCLR:
7930		if ((iobuf = kmalloc(RIDSIZE, GFP_KERNEL)) == NULL)
7931			return -ENOMEM;
7932
7933		PC4500_readrid(ai, RID_STATSDELTACLEAR, iobuf, RIDSIZE, 1);
7934
7935		enabled = ai->micstats.enabled;
7936		memset(&ai->micstats, 0, sizeof(ai->micstats));
7937		ai->micstats.enabled = enabled;
7938
7939		if (copy_to_user(comp->data, iobuf,
7940				 min((int)comp->len, (int)RIDSIZE))) {
7941			kfree (iobuf);
7942			return -EFAULT;
7943		}
7944		kfree (iobuf);
7945		return 0;
7946
7947	default:
7948		return -EOPNOTSUPP;	/* Blarg! */
7949	}
7950	if (comp->len > RIDSIZE)
7951		return -EINVAL;
7952
7953	if ((iobuf = kmalloc(RIDSIZE, GFP_KERNEL)) == NULL)
7954		return -ENOMEM;
7955
7956	if (copy_from_user(iobuf, comp->data, comp->len)) {
7957		kfree (iobuf);
7958		return -EFAULT;
7959	}
7960
7961	if (comp->command == AIROPCFG) {
7962		ConfigRid *cfg = (ConfigRid *)iobuf;
7963
7964		if (test_bit(FLAG_MIC_CAPABLE, &ai->flags))
7965			cfg->opmode |= MODE_MIC;
7966
7967		if ((cfg->opmode & MODE_CFG_MASK) == MODE_STA_IBSS)
7968			set_bit (FLAG_ADHOC, &ai->flags);
7969		else
7970			clear_bit (FLAG_ADHOC, &ai->flags);
7971	}
7972
7973	if ((*writer)(ai, ridcode, iobuf, comp->len, 1)) {
7974		kfree (iobuf);
7975		return -EIO;
7976	}
7977	kfree (iobuf);
7978	return 0;
7979}
7980
7981/*****************************************************************************
7982 * Ancillary flash / mod functions much black magic lurkes here              *
7983 *****************************************************************************
7984 */
7985
7986/*
7987 * Flash command switch table
7988 */
7989
7990static int flashcard(struct net_device *dev, aironet_ioctl *comp)
7991{
7992	int z;
7993
7994	/* Only super-user can modify flash */
7995	if (!capable(CAP_NET_ADMIN))
7996		return -EPERM;
7997
7998	switch(comp->command)
7999	{
8000	case AIROFLSHRST:
8001		return cmdreset((struct airo_info *)dev->ml_priv);
8002
8003	case AIROFLSHSTFL:
8004		if (!AIRO_FLASH(dev) &&
8005		    (AIRO_FLASH(dev) = kmalloc(FLASHSIZE, GFP_KERNEL)) == NULL)
8006			return -ENOMEM;
8007		return setflashmode((struct airo_info *)dev->ml_priv);
8008
8009	case AIROFLSHGCHR: /* Get char from aux */
8010		if (comp->len != sizeof(int))
8011			return -EINVAL;
8012		if (copy_from_user(&z, comp->data, comp->len))
8013			return -EFAULT;
8014		return flashgchar((struct airo_info *)dev->ml_priv, z, 8000);
8015
8016	case AIROFLSHPCHR: /* Send char to card. */
8017		if (comp->len != sizeof(int))
8018			return -EINVAL;
8019		if (copy_from_user(&z, comp->data, comp->len))
8020			return -EFAULT;
8021		return flashpchar((struct airo_info *)dev->ml_priv, z, 8000);
8022
8023	case AIROFLPUTBUF: /* Send 32k to card */
8024		if (!AIRO_FLASH(dev))
8025			return -ENOMEM;
8026		if (comp->len > FLASHSIZE)
8027			return -EINVAL;
8028		if (copy_from_user(AIRO_FLASH(dev), comp->data, comp->len))
8029			return -EFAULT;
8030
8031		flashputbuf((struct airo_info *)dev->ml_priv);
8032		return 0;
8033
8034	case AIRORESTART:
8035		if (flashrestart((struct airo_info *)dev->ml_priv, dev))
8036			return -EIO;
8037		return 0;
8038	}
8039	return -EINVAL;
8040}
8041
8042#define FLASH_COMMAND  0x7e7e
8043
8044/*
8045 * STEP 1)
8046 * Disable MAC and do soft reset on
8047 * card.
8048 */
8049
8050static int cmdreset(struct airo_info *ai)
8051{
8052	disable_MAC(ai, 1);
8053
8054	if (!waitbusy (ai)) {
8055		airo_print_info(ai->dev->name, "Waitbusy hang before RESET");
8056		return -EBUSY;
8057	}
8058
8059	OUT4500(ai, COMMAND, CMD_SOFTRESET);
8060
8061	ssleep(1);			/* WAS 600 12/7/00 */
8062
8063	if (!waitbusy (ai)) {
8064		airo_print_info(ai->dev->name, "Waitbusy hang AFTER RESET");
8065		return -EBUSY;
8066	}
8067	return 0;
8068}
8069
8070/* STEP 2)
8071 * Put the card in legendary flash
8072 * mode
8073 */
8074
8075static int setflashmode (struct airo_info *ai)
8076{
8077	set_bit (FLAG_FLASHING, &ai->flags);
8078
8079	OUT4500(ai, SWS0, FLASH_COMMAND);
8080	OUT4500(ai, SWS1, FLASH_COMMAND);
8081	if (probe) {
8082		OUT4500(ai, SWS0, FLASH_COMMAND);
8083		OUT4500(ai, COMMAND, 0x10);
8084	} else {
8085		OUT4500(ai, SWS2, FLASH_COMMAND);
8086		OUT4500(ai, SWS3, FLASH_COMMAND);
8087		OUT4500(ai, COMMAND, 0);
8088	}
8089	msleep(500);		/* 500ms delay */
8090
8091	if (!waitbusy(ai)) {
8092		clear_bit (FLAG_FLASHING, &ai->flags);
8093		airo_print_info(ai->dev->name, "Waitbusy hang after setflash mode");
8094		return -EIO;
8095	}
8096	return 0;
8097}
8098
8099/* Put character to SWS0 wait for dwelltime
8100 * x 50us for  echo .
8101 */
8102
8103static int flashpchar(struct airo_info *ai, int byte, int dwelltime)
8104{
8105	int echo;
8106	int waittime;
8107
8108	byte |= 0x8000;
8109
8110	if (dwelltime == 0)
8111		dwelltime = 200;
8112
8113	waittime = dwelltime;
8114
8115	/* Wait for busy bit d15 to go false indicating buffer empty */
8116	while ((IN4500 (ai, SWS0) & 0x8000) && waittime > 0) {
8117		udelay (50);
8118		waittime -= 50;
8119	}
8120
8121	/* timeout for busy clear wait */
8122	if (waittime <= 0) {
8123		airo_print_info(ai->dev->name, "flash putchar busywait timeout!");
8124		return -EBUSY;
8125	}
8126
8127	/* Port is clear now write byte and wait for it to echo back */
8128	do {
8129		OUT4500(ai, SWS0, byte);
8130		udelay(50);
8131		dwelltime -= 50;
8132		echo = IN4500(ai, SWS1);
8133	} while (dwelltime >= 0 && echo != byte);
8134
8135	OUT4500(ai, SWS1, 0);
8136
8137	return (echo == byte) ? 0 : -EIO;
8138}
8139
8140/*
8141 * Get a character from the card matching matchbyte
8142 * Step 3)
8143 */
8144static int flashgchar(struct airo_info *ai, int matchbyte, int dwelltime)
8145{
8146	int           rchar;
8147	unsigned char rbyte = 0;
8148
8149	do {
8150		rchar = IN4500(ai, SWS1);
8151
8152		if (dwelltime && !(0x8000 & rchar)) {
8153			dwelltime -= 10;
8154			mdelay(10);
8155			continue;
8156		}
8157		rbyte = 0xff & rchar;
8158
8159		if ((rbyte == matchbyte) && (0x8000 & rchar)) {
8160			OUT4500(ai, SWS1, 0);
8161			return 0;
8162		}
8163		if (rbyte == 0x81 || rbyte == 0x82 || rbyte == 0x83 || rbyte == 0x1a || 0xffff == rchar)
8164			break;
8165		OUT4500(ai, SWS1, 0);
8166
8167	} while (dwelltime > 0);
8168	return -EIO;
8169}
8170
8171/*
8172 * Transfer 32k of firmware data from user buffer to our buffer and
8173 * send to the card
8174 */
8175
8176static int flashputbuf(struct airo_info *ai)
8177{
8178	int            nwords;
8179
8180	/* Write stuff */
8181	if (test_bit(FLAG_MPI,&ai->flags))
8182		memcpy_toio(ai->pciaux + 0x8000, ai->flash, FLASHSIZE);
8183	else {
8184		OUT4500(ai, AUXPAGE, 0x100);
8185		OUT4500(ai, AUXOFF, 0);
8186
8187		for (nwords = 0; nwords != FLASHSIZE / 2; nwords++) {
8188			OUT4500(ai, AUXDATA, ai->flash[nwords] & 0xffff);
8189		}
8190	}
8191	OUT4500(ai, SWS0, 0x8000);
8192
8193	return 0;
8194}
8195
8196/*
8197 *
8198 */
8199static int flashrestart(struct airo_info *ai, struct net_device *dev)
8200{
8201	int    i, status;
8202
8203	ssleep(1);			/* Added 12/7/00 */
8204	clear_bit (FLAG_FLASHING, &ai->flags);
8205	if (test_bit(FLAG_MPI, &ai->flags)) {
8206		status = mpi_init_descriptors(ai);
8207		if (status != SUCCESS)
8208			return status;
8209	}
8210	status = setup_card(ai, dev->dev_addr, 1);
8211
8212	if (!test_bit(FLAG_MPI,&ai->flags))
8213		for (i = 0; i < MAX_FIDS; i++) {
8214			ai->fids[i] = transmit_allocate
8215				(ai, AIRO_DEF_MTU, i >= MAX_FIDS / 2);
8216		}
8217
8218	ssleep(1);			/* Added 12/7/00 */
8219	return status;
8220}
8221#endif /* CISCO_EXT */
8222
8223/*
8224    This program is free software; you can redistribute it and/or
8225    modify it under the terms of the GNU General Public License
8226    as published by the Free Software Foundation; either version 2
8227    of the License, or (at your option) any later version.
8228
8229    This program is distributed in the hope that it will be useful,
8230    but WITHOUT ANY WARRANTY; without even the implied warranty of
8231    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
8232    GNU General Public License for more details.
8233
8234    In addition:
8235
8236    Redistribution and use in source and binary forms, with or without
8237    modification, are permitted provided that the following conditions
8238    are met:
8239
8240    1. Redistributions of source code must retain the above copyright
8241       notice, this list of conditions and the following disclaimer.
8242    2. Redistributions in binary form must reproduce the above copyright
8243       notice, this list of conditions and the following disclaimer in the
8244       documentation and/or other materials provided with the distribution.
8245    3. The name of the author may not be used to endorse or promote
8246       products derived from this software without specific prior written
8247       permission.
8248
8249    THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
8250    IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
8251    WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
8252    ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT,
8253    INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
8254    (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
8255    SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
8256    HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
8257    STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
8258    IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
8259    POSSIBILITY OF SUCH DAMAGE.
8260*/
8261
8262module_init(airo_init_module);
8263module_exit(airo_cleanup_module);