/*
 * Host AP (software wireless LAN access point) driver for
 * Intersil Prism2/2.5/3.
 *
 * Copyright (c) 2001-2002, SSH Communications Security Corp and Jouni Malinen
 * <j@w1.fi>
 * Copyright (c) 2002-2005, Jouni Malinen <j@w1.fi>
 *
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License version 2 as
 * published by the Free Software Foundation. See README and COPYING for
 * more details.
 *
 * FIX:
 * - there is currently no way of associating TX packets to correct wds device
 *   when TX Exc/OK event occurs, so all tx_packets and some
 *   tx_errors/tx_dropped are added to the main netdevice; using sw_support
 *   field in txdesc might be used to fix this (using Alloc event to increment
 *   tx_packets would need some further info in txfid table)
 *
 * Buffer Access Path (BAP) usage:
 *   Prism2 cards have two separate BAPs for accessing the card memory. These
 *   should allow concurrent access to two different frames and the driver
 *   previously used BAP0 for sending data and BAP1 for receiving data.
 *   However, there seems to be number of issues with concurrent access and at
 *   least one know hardware bug in using BAP0 and BAP1 concurrently with PCI
 *   Prism2.5. Therefore, the driver now only uses BAP0 for moving data between
 *   host and card memories. BAP0 accesses are protected with local->baplock
 *   (spin_lock_bh) to prevent concurrent use.
 */



#include <asm/delay.h>
#include <asm/uaccess.h>

#include <linux/slab.h>
#include <linux/netdevice.h>
#include <linux/etherdevice.h>
#include <linux/proc_fs.h>
#include <linux/seq_file.h>
#include <linux/if_arp.h>
#include <linux/delay.h>
#include <linux/random.h>
#include <linux/wait.h>
#include <linux/sched.h>
#include <linux/rtnetlink.h>
#include <linux/wireless.h>
#include <net/iw_handler.h>
#include <net/lib80211.h>
#include <asm/irq.h>

#include "hostap_80211.h"
#include "hostap.h"
#include "hostap_ap.h"


/* #define final_version */

static int mtu = 1500;
module_param(mtu, int, 0444);
MODULE_PARM_DESC(mtu, "Maximum transfer unit");

static int channel[MAX_PARM_DEVICES] = { 3, DEF_INTS };
module_param_array(channel, int, NULL, 0444);
MODULE_PARM_DESC(channel, "Initial channel");

static char essid[33] = "test";
module_param_string(essid, essid, sizeof(essid), 0444);
MODULE_PARM_DESC(essid, "Host AP's ESSID");

static int iw_mode[MAX_PARM_DEVICES] = { IW_MODE_MASTER, DEF_INTS };
module_param_array(iw_mode, int, NULL, 0444);
MODULE_PARM_DESC(iw_mode, "Initial operation mode");

static int beacon_int[MAX_PARM_DEVICES] = { 100, DEF_INTS };
module_param_array(beacon_int, int, NULL, 0444);
MODULE_PARM_DESC(beacon_int, "Beacon interval (1 = 1024 usec)");

static int dtim_period[MAX_PARM_DEVICES] = { 1, DEF_INTS };
module_param_array(dtim_period, int, NULL, 0444);
MODULE_PARM_DESC(dtim_period, "DTIM period");

static char dev_template[16] = "wlan%d";
module_param_string(dev_template, dev_template, sizeof(dev_template), 0444);
MODULE_PARM_DESC(dev_template, "Prefix for network device name (default: "
		 "wlan%d)");

#ifdef final_version
#define EXTRA_EVENTS_WTERR 0
#else
/* check WTERR events (Wait Time-out) in development versions */
#define EXTRA_EVENTS_WTERR HFA384X_EV_WTERR
#endif

/* Events that will be using BAP0 */
#define HFA384X_BAP0_EVENTS \
	(HFA384X_EV_TXEXC | HFA384X_EV_RX | HFA384X_EV_INFO | HFA384X_EV_TX)

/* event mask, i.e., events that will result in an interrupt */
#define HFA384X_EVENT_MASK \
	(HFA384X_BAP0_EVENTS | HFA384X_EV_ALLOC | HFA384X_EV_INFDROP | \
	HFA384X_EV_CMD | HFA384X_EV_TICK | \
	EXTRA_EVENTS_WTERR)

/* Default TX control flags: use 802.11 headers and request interrupt for
 * failed transmits. Frames that request ACK callback, will add
 * _TX_OK flag and _ALT_RTRY flag may be used to select different retry policy.
 */
#define HFA384X_TX_CTRL_FLAGS \
	(HFA384X_TX_CTRL_802_11 | HFA384X_TX_CTRL_TX_EX)


/* ca. 1 usec */
#define HFA384X_CMD_BUSY_TIMEOUT 5000
#define HFA384X_BAP_BUSY_TIMEOUT 50000

/* ca. 10 usec */
#define HFA384X_CMD_COMPL_TIMEOUT 20000
#define HFA384X_DL_COMPL_TIMEOUT 1000000

/* Wait times for initialization; yield to other processes to avoid busy
 * waiting for long time. */
#define HFA384X_INIT_TIMEOUT (HZ / 2) /* 500 ms */
#define HFA384X_ALLOC_COMPL_TIMEOUT (HZ / 20) /* 50 ms */


static void prism2_hw_reset(struct net_device *dev);
static void prism2_check_sta_fw_version(local_info_t *local);

#ifdef PRISM2_DOWNLOAD_SUPPORT
/* hostap_download.c */
static const struct file_operations prism2_download_aux_dump_proc_fops;
static u8 * prism2_read_pda(struct net_device *dev);
static int prism2_download(local_info_t *local,
			   struct prism2_download_param *param);
static void prism2_download_free_data(struct prism2_download_data *dl);
static int prism2_download_volatile(local_info_t *local,
				    struct prism2_download_data *param);
static int prism2_download_genesis(local_info_t *local,
				   struct prism2_download_data *param);
static int prism2_get_ram_size(local_info_t *local);
#endif /* PRISM2_DOWNLOAD_SUPPORT */




#ifndef final_version
/* magic value written to SWSUPPORT0 reg. for detecting whether card is still
 * present */
#define HFA384X_MAGIC 0x8A32
#endif


static u16 hfa384x_read_reg(struct net_device *dev, u16 reg)
{
	return HFA384X_INW(reg);
}


static void hfa384x_read_regs(struct net_device *dev,
			      struct hfa384x_regs *regs)
{
	regs->cmd = HFA384X_INW(HFA384X_CMD_OFF);
	regs->evstat = HFA384X_INW(HFA384X_EVSTAT_OFF);
	regs->offset0 = HFA384X_INW(HFA384X_OFFSET0_OFF);
	regs->offset1 = HFA384X_INW(HFA384X_OFFSET1_OFF);
	regs->swsupport0 = HFA384X_INW(HFA384X_SWSUPPORT0_OFF);
}


/**
 * __hostap_cmd_queue_free - Free Prism2 command queue entry (private)
 * @local: pointer to private Host AP driver data
 * @entry: Prism2 command queue entry to be freed
 * @del_req: request the entry to be removed
 *
 * Internal helper function for freeing Prism2 command queue entries.
 * Caller must have acquired local->cmdlock before calling this function.
 */
static inline void __hostap_cmd_queue_free(local_info_t *local,
					   struct hostap_cmd_queue *entry,
					   int del_req)
{
	if (del_req) {
		entry->del_req = 1;
		if (!list_empty(&entry->list)) {
			list_del_init(&entry->list);
			local->cmd_queue_len--;
		}
	}

	if (atomic_dec_and_test(&entry->usecnt) && entry->del_req)
		kfree(entry);
}


/**
 * hostap_cmd_queue_free - Free Prism2 command queue entry
 * @local: pointer to private Host AP driver data
 * @entry: Prism2 command queue entry to be freed
 * @del_req: request the entry to be removed
 *
 * Free a Prism2 command queue entry.
 */
static inline void hostap_cmd_queue_free(local_info_t *local,
					 struct hostap_cmd_queue *entry,
					 int del_req)
{
	unsigned long flags;

	spin_lock_irqsave(&local->cmdlock, flags);
	__hostap_cmd_queue_free(local, entry, del_req);
	spin_unlock_irqrestore(&local->cmdlock, flags);
}


/**
 * prism2_clear_cmd_queue - Free all pending Prism2 command queue entries
 * @local: pointer to private Host AP driver data
 */
static void prism2_clear_cmd_queue(local_info_t *local)
{
	struct list_head *ptr, *n;
	unsigned long flags;
	struct hostap_cmd_queue *entry;

	spin_lock_irqsave(&local->cmdlock, flags);
	list_for_each_safe(ptr, n, &local->cmd_queue) {
		entry = list_entry(ptr, struct hostap_cmd_queue, list);
		atomic_inc(&entry->usecnt);
		printk(KERN_DEBUG "%s: removed pending cmd_queue entry "
		       "(type=%d, cmd=0x%04x, param0=0x%04x)\n",
		       local->dev->name, entry->type, entry->cmd,
		       entry->param0);
		__hostap_cmd_queue_free(local, entry, 1);
	}
	if (local->cmd_queue_len) {
		/* This should not happen; print debug message and clear
		 * queue length. */
		printk(KERN_DEBUG "%s: cmd_queue_len (%d) not zero after "
		       "flush\n", local->dev->name, local->cmd_queue_len);
		local->cmd_queue_len = 0;
	}
	spin_unlock_irqrestore(&local->cmdlock, flags);
}


/**
 * hfa384x_cmd_issue - Issue a Prism2 command to the hardware
 * @dev: pointer to net_device
 * @entry: Prism2 command queue entry to be issued
 */
static int hfa384x_cmd_issue(struct net_device *dev,
				    struct hostap_cmd_queue *entry)
{
	struct hostap_interface *iface;
	local_info_t *local;
	int tries;
	u16 reg;
	unsigned long flags;

	iface = netdev_priv(dev);
	local = iface->local;

	if (local->func->card_present && !local->func->card_present(local))
		return -ENODEV;

	if (entry->issued) {
		printk(KERN_DEBUG "%s: driver bug - re-issuing command @%p\n",
		       dev->name, entry);
	}

	/* wait until busy bit is clear; this should always be clear since the
	 * commands are serialized */
	tries = HFA384X_CMD_BUSY_TIMEOUT;
	while (HFA384X_INW(HFA384X_CMD_OFF) & HFA384X_CMD_BUSY && tries > 0) {
		tries--;
		udelay(1);
	}
#ifndef final_version
	if (tries != HFA384X_CMD_BUSY_TIMEOUT) {
		prism2_io_debug_error(dev, 1);
		printk(KERN_DEBUG "%s: hfa384x_cmd_issue: cmd reg was busy "
		       "for %d usec\n", dev->name,
		       HFA384X_CMD_BUSY_TIMEOUT - tries);
	}
#endif
	if (tries == 0) {
		reg = HFA384X_INW(HFA384X_CMD_OFF);
		prism2_io_debug_error(dev, 2);
		printk(KERN_DEBUG "%s: hfa384x_cmd_issue - timeout - "
		       "reg=0x%04x\n", dev->name, reg);
		return -ETIMEDOUT;
	}

	/* write command */
	spin_lock_irqsave(&local->cmdlock, flags);
	HFA384X_OUTW(entry->param0, HFA384X_PARAM0_OFF);
	HFA384X_OUTW(entry->param1, HFA384X_PARAM1_OFF);
	HFA384X_OUTW(entry->cmd, HFA384X_CMD_OFF);
	entry->issued = 1;
	spin_unlock_irqrestore(&local->cmdlock, flags);

	return 0;
}


/**
 * hfa384x_cmd - Issue a Prism2 command and wait (sleep) for completion
 * @dev: pointer to net_device
 * @cmd: Prism2 command code (HFA384X_CMD_CODE_*)
 * @param0: value for Param0 register
 * @param1: value for Param1 register (pointer; %NULL if not used)
 * @resp0: pointer for Resp0 data or %NULL if Resp0 is not needed
 *
 * Issue given command (possibly after waiting in command queue) and sleep
 * until the command is completed (or timed out or interrupted). This can be
 * called only from user process context.
 */
static int hfa384x_cmd(struct net_device *dev, u16 cmd, u16 param0,
		       u16 *param1, u16 *resp0)
{
	struct hostap_interface *iface;
	local_info_t *local;
	int err, res, issue, issued = 0;
	unsigned long flags;
	struct hostap_cmd_queue *entry;
	DECLARE_WAITQUEUE(wait, current);

	iface = netdev_priv(dev);
	local = iface->local;

	if (in_interrupt()) {
		printk(KERN_DEBUG "%s: hfa384x_cmd called from interrupt "
		       "context\n", dev->name);
		return -1;
	}

	if (local->cmd_queue_len >= HOSTAP_CMD_QUEUE_MAX_LEN) {
		printk(KERN_DEBUG "%s: hfa384x_cmd: cmd_queue full\n",
		       dev->name);
		return -1;
	}

	if (signal_pending(current))
		return -EINTR;

	entry = kzalloc(sizeof(*entry), GFP_ATOMIC);
	if (entry == NULL)
		return -ENOMEM;

	atomic_set(&entry->usecnt, 1);
	entry->type = CMD_SLEEP;
	entry->cmd = cmd;
	entry->param0 = param0;
	if (param1)
		entry->param1 = *param1;
	init_waitqueue_head(&entry->compl);

	/* prepare to wait for command completion event, but do not sleep yet
	 */
	add_wait_queue(&entry->compl, &wait);
	set_current_state(TASK_INTERRUPTIBLE);

	spin_lock_irqsave(&local->cmdlock, flags);
	issue = list_empty(&local->cmd_queue);
	if (issue)
		entry->issuing = 1;
	list_add_tail(&entry->list, &local->cmd_queue);
	local->cmd_queue_len++;
	spin_unlock_irqrestore(&local->cmdlock, flags);

	err = 0;
	if (!issue)
		goto wait_completion;

	if (signal_pending(current))
		err = -EINTR;

	if (!err) {
		if (hfa384x_cmd_issue(dev, entry))
			err = -ETIMEDOUT;
		else
			issued = 1;
	}

 wait_completion:
	if (!err && entry->type != CMD_COMPLETED) {
		/* sleep until command is completed or timed out */
		res = schedule_timeout(2 * HZ);
	} else
		res = -1;

	if (!err && signal_pending(current))
		err = -EINTR;

	if (err && issued) {
		/* the command was issued, so a CmdCompl event should occur
		 * soon; however, there's a pending signal and
		 * schedule_timeout() would be interrupted; wait a short period
		 * of time to avoid removing entry from the list before
		 * CmdCompl event */
		udelay(300);
	}

	set_current_state(TASK_RUNNING);
	remove_wait_queue(&entry->compl, &wait);

	/* If entry->list is still in the list, it must be removed
	 * first and in this case prism2_cmd_ev() does not yet have
	 * local reference to it, and the data can be kfree()'d
	 * here. If the command completion event is still generated,
	 * it will be assigned to next (possibly) pending command, but
	 * the driver will reset the card anyway due to timeout
	 *
	 * If the entry is not in the list prism2_cmd_ev() has a local
	 * reference to it, but keeps cmdlock as long as the data is
	 * needed, so the data can be kfree()'d here. */

	/* FIX: if the entry->list is in the list, it has not been completed
	 * yet, so removing it here is somewhat wrong.. this could cause
	 * references to freed memory and next list_del() causing NULL pointer
	 * dereference.. it would probably be better to leave the entry in the
	 * list and the list should be emptied during hw reset */

	spin_lock_irqsave(&local->cmdlock, flags);
	if (!list_empty(&entry->list)) {
		printk(KERN_DEBUG "%s: hfa384x_cmd: entry still in list? "
		       "(entry=%p, type=%d, res=%d)\n", dev->name, entry,
		       entry->type, res);
		list_del_init(&entry->list);
		local->cmd_queue_len--;
	}
	spin_unlock_irqrestore(&local->cmdlock, flags);

	if (err) {
		printk(KERN_DEBUG "%s: hfa384x_cmd: interrupted; err=%d\n",
		       dev->name, err);
		res = err;
		goto done;
	}

	if (entry->type != CMD_COMPLETED) {
		u16 reg = HFA384X_INW(HFA384X_EVSTAT_OFF);
		printk(KERN_DEBUG "%s: hfa384x_cmd: command was not "
		       "completed (res=%d, entry=%p, type=%d, cmd=0x%04x, "
		       "param0=0x%04x, EVSTAT=%04x INTEN=%04x)\n", dev->name,
		       res, entry, entry->type, entry->cmd, entry->param0, reg,
		       HFA384X_INW(HFA384X_INTEN_OFF));
		if (reg & HFA384X_EV_CMD) {
			/* Command completion event is pending, but the
			 * interrupt was not delivered - probably an issue
			 * with pcmcia-cs configuration. */
			printk(KERN_WARNING "%s: interrupt delivery does not "
			       "seem to work\n", dev->name);
		}
		prism2_io_debug_error(dev, 3);
		res = -ETIMEDOUT;
		goto done;
	}

	if (resp0 != NULL)
		*resp0 = entry->resp0;
#ifndef final_version
	if (entry->res) {
		printk(KERN_DEBUG "%s: CMD=0x%04x => res=0x%02x, "
		       "resp0=0x%04x\n",
		       dev->name, cmd, entry->res, entry->resp0);
	}
#endif /* final_version */

	res = entry->res;
 done:
	hostap_cmd_queue_free(local, entry, 1);
	return res;
}


/**
 * hfa384x_cmd_callback - Issue a Prism2 command; callback when completed
 * @dev: pointer to net_device
 * @cmd: Prism2 command code (HFA384X_CMD_CODE_*)
 * @param0: value for Param0 register
 * @callback: command completion callback function (%NULL = no callback)
 * @context: context data to be given to the callback function
 *
 * Issue given command (possibly after waiting in command queue) and use
 * callback function to indicate command completion. This can be called both
 * from user and interrupt context. The callback function will be called in
 * hardware IRQ context. It can be %NULL, when no function is called when
 * command is completed.
 */
static int hfa384x_cmd_callback(struct net_device *dev, u16 cmd, u16 param0,
				void (*callback)(struct net_device *dev,
						 long context, u16 resp0,
						 u16 status),
				long context)
{
	struct hostap_interface *iface;
	local_info_t *local;
	int issue, ret;
	unsigned long flags;
	struct hostap_cmd_queue *entry;

	iface = netdev_priv(dev);
	local = iface->local;

	if (local->cmd_queue_len >= HOSTAP_CMD_QUEUE_MAX_LEN + 2) {
		printk(KERN_DEBUG "%s: hfa384x_cmd: cmd_queue full\n",
		       dev->name);
		return -1;
	}

	entry = kzalloc(sizeof(*entry), GFP_ATOMIC);
	if (entry == NULL)
		return -ENOMEM;

	atomic_set(&entry->usecnt, 1);
	entry->type = CMD_CALLBACK;
	entry->cmd = cmd;
	entry->param0 = param0;
	entry->callback = callback;
	entry->context = context;

	spin_lock_irqsave(&local->cmdlock, flags);
	issue = list_empty(&local->cmd_queue);
	if (issue)
		entry->issuing = 1;
	list_add_tail(&entry->list, &local->cmd_queue);
	local->cmd_queue_len++;
	spin_unlock_irqrestore(&local->cmdlock, flags);

	if (issue && hfa384x_cmd_issue(dev, entry))
		ret = -ETIMEDOUT;
	else
		ret = 0;

	hostap_cmd_queue_free(local, entry, ret);

	return ret;
}


/**
 * __hfa384x_cmd_no_wait - Issue a Prism2 command (private)
 * @dev: pointer to net_device
 * @cmd: Prism2 command code (HFA384X_CMD_CODE_*)
 * @param0: value for Param0 register
 * @io_debug_num: I/O debug error number
 *
 * Shared helper function for hfa384x_cmd_wait() and hfa384x_cmd_no_wait().
 */
static int __hfa384x_cmd_no_wait(struct net_device *dev, u16 cmd, u16 param0,
				 int io_debug_num)
{
	int tries;
	u16 reg;

	/* wait until busy bit is clear; this should always be clear since the
	 * commands are serialized */
	tries = HFA384X_CMD_BUSY_TIMEOUT;
	while (HFA384X_INW(HFA384X_CMD_OFF) & HFA384X_CMD_BUSY && tries > 0) {
		tries--;
		udelay(1);
	}
	if (tries == 0) {
		reg = HFA384X_INW(HFA384X_CMD_OFF);
		prism2_io_debug_error(dev, io_debug_num);
		printk(KERN_DEBUG "%s: __hfa384x_cmd_no_wait(%d) - timeout - "
		       "reg=0x%04x\n", dev->name, io_debug_num, reg);
		return -ETIMEDOUT;
	}

	/* write command */
	HFA384X_OUTW(param0, HFA384X_PARAM0_OFF);
	HFA384X_OUTW(cmd, HFA384X_CMD_OFF);

	return 0;
}


/**
 * hfa384x_cmd_wait - Issue a Prism2 command and busy wait for completion
 * @dev: pointer to net_device
 * @cmd: Prism2 command code (HFA384X_CMD_CODE_*)
 * @param0: value for Param0 register
 */
static int hfa384x_cmd_wait(struct net_device *dev, u16 cmd, u16 param0)
{
	int res, tries;
	u16 reg;

	res = __hfa384x_cmd_no_wait(dev, cmd, param0, 4);
	if (res)
		return res;

        /* wait for command completion */
	if ((cmd & HFA384X_CMDCODE_MASK) == HFA384X_CMDCODE_DOWNLOAD)
		tries = HFA384X_DL_COMPL_TIMEOUT;
	else
		tries = HFA384X_CMD_COMPL_TIMEOUT;

        while (!(HFA384X_INW(HFA384X_EVSTAT_OFF) & HFA384X_EV_CMD) &&
               tries > 0) {
                tries--;
                udelay(10);
        }
        if (tries == 0) {
                reg = HFA384X_INW(HFA384X_EVSTAT_OFF);
		prism2_io_debug_error(dev, 5);
                printk(KERN_DEBUG "%s: hfa384x_cmd_wait - timeout2 - "
		       "reg=0x%04x\n", dev->name, reg);
                return -ETIMEDOUT;
        }

        res = (HFA384X_INW(HFA384X_STATUS_OFF) &
               (BIT(14) | BIT(13) | BIT(12) | BIT(11) | BIT(10) | BIT(9) |
                BIT(8))) >> 8;
#ifndef final_version
	if (res) {
		printk(KERN_DEBUG "%s: CMD=0x%04x => res=0x%02x\n",
		       dev->name, cmd, res);
	}
#endif

	HFA384X_OUTW(HFA384X_EV_CMD, HFA384X_EVACK_OFF);

	return res;
}


/**
 * hfa384x_cmd_no_wait - Issue a Prism2 command; do not wait for completion
 * @dev: pointer to net_device
 * @cmd: Prism2 command code (HFA384X_CMD_CODE_*)
 * @param0: value for Param0 register
 */
static inline int hfa384x_cmd_no_wait(struct net_device *dev, u16 cmd,
				      u16 param0)
{
	return __hfa384x_cmd_no_wait(dev, cmd, param0, 6);
}


/**
 * prism2_cmd_ev - Prism2 command completion event handler
 * @dev: pointer to net_device
 *
 * Interrupt handler for command completion events. Called by the main
 * interrupt handler in hardware IRQ context. Read Resp0 and status registers
 * from the hardware and ACK the event. Depending on the issued command type
 * either wake up the sleeping process that is waiting for command completion
 * or call the callback function. Issue the next command, if one is pending.
 */
static void prism2_cmd_ev(struct net_device *dev)
{
	struct hostap_interface *iface;
	local_info_t *local;
	struct hostap_cmd_queue *entry = NULL;

	iface = netdev_priv(dev);
	local = iface->local;

	spin_lock(&local->cmdlock);
	if (!list_empty(&local->cmd_queue)) {
		entry = list_entry(local->cmd_queue.next,
				   struct hostap_cmd_queue, list);
		atomic_inc(&entry->usecnt);
		list_del_init(&entry->list);
		local->cmd_queue_len--;

		if (!entry->issued) {
			printk(KERN_DEBUG "%s: Command completion event, but "
			       "cmd not issued\n", dev->name);
			__hostap_cmd_queue_free(local, entry, 1);
			entry = NULL;
		}
	}
	spin_unlock(&local->cmdlock);

	if (!entry) {
		HFA384X_OUTW(HFA384X_EV_CMD, HFA384X_EVACK_OFF);
		printk(KERN_DEBUG "%s: Command completion event, but no "
		       "pending commands\n", dev->name);
		return;
	}

	entry->resp0 = HFA384X_INW(HFA384X_RESP0_OFF);
	entry->res = (HFA384X_INW(HFA384X_STATUS_OFF) &
		      (BIT(14) | BIT(13) | BIT(12) | BIT(11) | BIT(10) |
		       BIT(9) | BIT(8))) >> 8;
	HFA384X_OUTW(HFA384X_EV_CMD, HFA384X_EVACK_OFF);

	/* TODO: rest of the CmdEv handling could be moved to tasklet */
	if (entry->type == CMD_SLEEP) {
		entry->type = CMD_COMPLETED;
		wake_up_interruptible(&entry->compl);
	} else if (entry->type == CMD_CALLBACK) {
		if (entry->callback)
			entry->callback(dev, entry->context, entry->resp0,
					entry->res);
	} else {
		printk(KERN_DEBUG "%s: Invalid command completion type %d\n",
		       dev->name, entry->type);
	}
	hostap_cmd_queue_free(local, entry, 1);

	/* issue next command, if pending */
	entry = NULL;
	spin_lock(&local->cmdlock);
	if (!list_empty(&local->cmd_queue)) {
		entry = list_entry(local->cmd_queue.next,
				   struct hostap_cmd_queue, list);
		if (entry->issuing) {
			/* hfa384x_cmd() has already started issuing this
			 * command, so do not start here */
			entry = NULL;
		}
		if (entry)
			atomic_inc(&entry->usecnt);
	}
	spin_unlock(&local->cmdlock);

	if (entry) {
		/* issue next command; if command issuing fails, remove the
		 * entry from cmd_queue */
		int res = hfa384x_cmd_issue(dev, entry);
		spin_lock(&local->cmdlock);
		__hostap_cmd_queue_free(local, entry, res);
		spin_unlock(&local->cmdlock);
	}
}


static int hfa384x_wait_offset(struct net_device *dev, u16 o_off)
{
	int tries = HFA384X_BAP_BUSY_TIMEOUT;
	int res = HFA384X_INW(o_off) & HFA384X_OFFSET_BUSY;

	while (res && tries > 0) {
		tries--;
		udelay(1);
		res = HFA384X_INW(o_off) & HFA384X_OFFSET_BUSY;
	}
	return res;
}


/* Offset must be even */
static int hfa384x_setup_bap(struct net_device *dev, u16 bap, u16 id,
			     int offset)
{
	u16 o_off, s_off;
	int ret = 0;

	if (offset % 2 || bap > 1)
		return -EINVAL;

	if (bap == BAP1) {
		o_off = HFA384X_OFFSET1_OFF;
		s_off = HFA384X_SELECT1_OFF;
	} else {
		o_off = HFA384X_OFFSET0_OFF;
		s_off = HFA384X_SELECT0_OFF;
	}

	if (hfa384x_wait_offset(dev, o_off)) {
		prism2_io_debug_error(dev, 7);
		printk(KERN_DEBUG "%s: hfa384x_setup_bap - timeout before\n",
		       dev->name);
		ret = -ETIMEDOUT;
		goto out;
	}

	HFA384X_OUTW(id, s_off);
	HFA384X_OUTW(offset, o_off);

	if (hfa384x_wait_offset(dev, o_off)) {
		prism2_io_debug_error(dev, 8);
		printk(KERN_DEBUG "%s: hfa384x_setup_bap - timeout after\n",
		       dev->name);
		ret = -ETIMEDOUT;
		goto out;
	}
#ifndef final_version
	if (HFA384X_INW(o_off) & HFA384X_OFFSET_ERR) {
		prism2_io_debug_error(dev, 9);
		printk(KERN_DEBUG "%s: hfa384x_setup_bap - offset error "
		       "(%d,0x04%x,%d); reg=0x%04x\n",
		       dev->name, bap, id, offset, HFA384X_INW(o_off));
		ret = -EINVAL;
	}
#endif

 out:
	return ret;
}


static int hfa384x_get_rid(struct net_device *dev, u16 rid, void *buf, int len,
			   int exact_len)
{
	struct hostap_interface *iface;
	local_info_t *local;
	int res, rlen = 0;
	struct hfa384x_rid_hdr rec;

	iface = netdev_priv(dev);
	local = iface->local;

	if (local->no_pri) {
		printk(KERN_DEBUG "%s: cannot get RID %04x (len=%d) - no PRI "
		       "f/w\n", dev->name, rid, len);
		return -ENOTTY; /* Well.. not really correct, but return
				 * something unique enough.. */
	}

	if ((local->func->card_present && !local->func->card_present(local)) ||
	    local->hw_downloading)
		return -ENODEV;

	res = mutex_lock_interruptible(&local->rid_bap_mtx);
	if (res)
		return res;

	res = hfa384x_cmd(dev, HFA384X_CMDCODE_ACCESS, rid, NULL, NULL);
	if (res) {
		printk(KERN_DEBUG "%s: hfa384x_get_rid: CMDCODE_ACCESS failed "
		       "(res=%d, rid=%04x, len=%d)\n",
		       dev->name, res, rid, len);
		mutex_unlock(&local->rid_bap_mtx);
		return res;
	}

	spin_lock_bh(&local->baplock);

	res = hfa384x_setup_bap(dev, BAP0, rid, 0);
	if (!res)
		res = hfa384x_from_bap(dev, BAP0, &rec, sizeof(rec));

	if (le16_to_cpu(rec.len) == 0) {
		/* RID not available */
		res = -ENODATA;
	}

	rlen = (le16_to_cpu(rec.len) - 1) * 2;
	if (!res && exact_len && rlen != len) {
		printk(KERN_DEBUG "%s: hfa384x_get_rid - RID len mismatch: "
		       "rid=0x%04x, len=%d (expected %d)\n",
		       dev->name, rid, rlen, len);
		res = -ENODATA;
	}

	if (!res)
		res = hfa384x_from_bap(dev, BAP0, buf, len);

	spin_unlock_bh(&local->baplock);
	mutex_unlock(&local->rid_bap_mtx);

	if (res) {
		if (res != -ENODATA)
			printk(KERN_DEBUG "%s: hfa384x_get_rid (rid=%04x, "
			       "len=%d) - failed - res=%d\n", dev->name, rid,
			       len, res);
		if (res == -ETIMEDOUT)
			prism2_hw_reset(dev);
		return res;
	}

	return rlen;
}


static int hfa384x_set_rid(struct net_device *dev, u16 rid, void *buf, int len)
{
	struct hostap_interface *iface;
	local_info_t *local;
	struct hfa384x_rid_hdr rec;
	int res;

	iface = netdev_priv(dev);
	local = iface->local;

	if (local->no_pri) {
		printk(KERN_DEBUG "%s: cannot set RID %04x (len=%d) - no PRI "
		       "f/w\n", dev->name, rid, len);
		return -ENOTTY; /* Well.. not really correct, but return
				 * something unique enough.. */
	}

	if ((local->func->card_present && !local->func->card_present(local)) ||
	    local->hw_downloading)
		return -ENODEV;

	rec.rid = cpu_to_le16(rid);
	/* RID len in words and +1 for rec.rid */
	rec.len = cpu_to_le16(len / 2 + len % 2 + 1);

	res = mutex_lock_interruptible(&local->rid_bap_mtx);
	if (res)
		return res;

	spin_lock_bh(&local->baplock);
	res = hfa384x_setup_bap(dev, BAP0, rid, 0);
	if (!res)
		res = hfa384x_to_bap(dev, BAP0, &rec, sizeof(rec));
	if (!res)
		res = hfa384x_to_bap(dev, BAP0, buf, len);
	spin_unlock_bh(&local->baplock);

	if (res) {
		printk(KERN_DEBUG "%s: hfa384x_set_rid (rid=%04x, len=%d) - "
		       "failed - res=%d\n", dev->name, rid, len, res);
		mutex_unlock(&local->rid_bap_mtx);
		return res;
	}

	res = hfa384x_cmd(dev, HFA384X_CMDCODE_ACCESS_WRITE, rid, NULL, NULL);
	mutex_unlock(&local->rid_bap_mtx);

	if (res) {
		printk(KERN_DEBUG "%s: hfa384x_set_rid: CMDCODE_ACCESS_WRITE "
		       "failed (res=%d, rid=%04x, len=%d)\n",
		       dev->name, res, rid, len);

		if (res == -ETIMEDOUT)
			prism2_hw_reset(dev);
	}

	return res;
}


static void hfa384x_disable_interrupts(struct net_device *dev)
{
	/* disable interrupts and clear event status */
	HFA384X_OUTW(0, HFA384X_INTEN_OFF);
	HFA384X_OUTW(0xffff, HFA384X_EVACK_OFF);
}


static void hfa384x_enable_interrupts(struct net_device *dev)
{
	/* ack pending events and enable interrupts from selected events */
	HFA384X_OUTW(0xffff, HFA384X_EVACK_OFF);
	HFA384X_OUTW(HFA384X_EVENT_MASK, HFA384X_INTEN_OFF);
}


static void hfa384x_events_no_bap0(struct net_device *dev)
{
	HFA384X_OUTW(HFA384X_EVENT_MASK & ~HFA384X_BAP0_EVENTS,
		     HFA384X_INTEN_OFF);
}


static void hfa384x_events_all(struct net_device *dev)
{
	HFA384X_OUTW(HFA384X_EVENT_MASK, HFA384X_INTEN_OFF);
}


static void hfa384x_events_only_cmd(struct net_device *dev)
{
	HFA384X_OUTW(HFA384X_EV_CMD, HFA384X_INTEN_OFF);
}


static u16 hfa384x_allocate_fid(struct net_device *dev, int len)
{
	u16 fid;
	unsigned long delay;

	/* FIX: this could be replace with hfa384x_cmd() if the Alloc event
	 * below would be handled like CmdCompl event (sleep here, wake up from
	 * interrupt handler */
	if (hfa384x_cmd_wait(dev, HFA384X_CMDCODE_ALLOC, len)) {
		printk(KERN_DEBUG "%s: cannot allocate fid, len=%d\n",
		       dev->name, len);
		return 0xffff;
	}

	delay = jiffies + HFA384X_ALLOC_COMPL_TIMEOUT;
	while (!(HFA384X_INW(HFA384X_EVSTAT_OFF) & HFA384X_EV_ALLOC) &&
	       time_before(jiffies, delay))
		yield();
	if (!(HFA384X_INW(HFA384X_EVSTAT_OFF) & HFA384X_EV_ALLOC)) {
		printk("%s: fid allocate, len=%d - timeout\n", dev->name, len);
		return 0xffff;
	}

	fid = HFA384X_INW(HFA384X_ALLOCFID_OFF);
	HFA384X_OUTW(HFA384X_EV_ALLOC, HFA384X_EVACK_OFF);

	return fid;
}


static int prism2_reset_port(struct net_device *dev)
{
	struct hostap_interface *iface;
	local_info_t *local;
	int res;

	iface = netdev_priv(dev);
	local = iface->local;

	if (!local->dev_enabled)
		return 0;

	res = hfa384x_cmd(dev, HFA384X_CMDCODE_DISABLE, 0,
			  NULL, NULL);
	if (res)
		printk(KERN_DEBUG "%s: reset port failed to disable port\n",
		       dev->name);
	else {
		res = hfa384x_cmd(dev, HFA384X_CMDCODE_ENABLE, 0,
				  NULL, NULL);
		if (res)
			printk(KERN_DEBUG "%s: reset port failed to enable "
			       "port\n", dev->name);
	}

	/* It looks like at least some STA firmware versions reset
	 * fragmentation threshold back to 2346 after enable command. Restore
	 * the configured value, if it differs from this default. */
	if (local->fragm_threshold != 2346 &&
	    hostap_set_word(dev, HFA384X_RID_FRAGMENTATIONTHRESHOLD,
			    local->fragm_threshold)) {
		printk(KERN_DEBUG "%s: failed to restore fragmentation "
		       "threshold (%d) after Port0 enable\n",
		       dev->name, local->fragm_threshold);
	}

	/* Some firmwares lose antenna selection settings on reset */
	(void) hostap_set_antsel(local);

	return res;
}


static int prism2_get_version_info(struct net_device *dev, u16 rid,
				   const char *txt)
{
	struct hfa384x_comp_ident comp;
	struct hostap_interface *iface;
	local_info_t *local;

	iface = netdev_priv(dev);
	local = iface->local;

	if (local->no_pri) {
		/* PRI f/w not yet available - cannot read RIDs */
		return -1;
	}
	if (hfa384x_get_rid(dev, rid, &comp, sizeof(comp), 1) < 0) {
		printk(KERN_DEBUG "Could not get RID for component %s\n", txt);
		return -1;
	}

	printk(KERN_INFO "%s: %s: id=0x%02x v%d.%d.%d\n", dev->name, txt,
	       __le16_to_cpu(comp.id), __le16_to_cpu(comp.major),
	       __le16_to_cpu(comp.minor), __le16_to_cpu(comp.variant));
	return 0;
}


static int prism2_setup_rids(struct net_device *dev)
{
	struct hostap_interface *iface;
	local_info_t *local;
	__le16 tmp;
	int ret = 0;

	iface = netdev_priv(dev);
	local = iface->local;

	hostap_set_word(dev, HFA384X_RID_TICKTIME, 2000);

	if (!local->fw_ap) {
		u16 tmp1 = hostap_get_porttype(local);
		ret = hostap_set_word(dev, HFA384X_RID_CNFPORTTYPE, tmp1);
		if (ret) {
			printk("%s: Port type setting to %d failed\n",
			       dev->name, tmp1);
			goto fail;
		}
	}

	/* Setting SSID to empty string seems to kill the card in Host AP mode
	 */
	if (local->iw_mode != IW_MODE_MASTER || local->essid[0] != '\0') {
		ret = hostap_set_string(dev, HFA384X_RID_CNFOWNSSID,
					local->essid);
		if (ret) {
			printk("%s: AP own SSID setting failed\n", dev->name);
			goto fail;
		}
	}

	ret = hostap_set_word(dev, HFA384X_RID_CNFMAXDATALEN,
			      PRISM2_DATA_MAXLEN);
	if (ret) {
		printk("%s: MAC data length setting to %d failed\n",
		       dev->name, PRISM2_DATA_MAXLEN);
		goto fail;
	}

	if (hfa384x_get_rid(dev, HFA384X_RID_CHANNELLIST, &tmp, 2, 1) < 0) {
		printk("%s: Channel list read failed\n", dev->name);
		ret = -EINVAL;
		goto fail;
	}
	local->channel_mask = le16_to_cpu(tmp);

	if (local->channel < 1 || local->channel > 14 ||
	    !(local->channel_mask & (1 << (local->channel - 1)))) {
		printk(KERN_WARNING "%s: Channel setting out of range "
		       "(%d)!\n", dev->name, local->channel);
		ret = -EBUSY;
		goto fail;
	}

	ret = hostap_set_word(dev, HFA384X_RID_CNFOWNCHANNEL, local->channel);
	if (ret) {
		printk("%s: Channel setting to %d failed\n",
		       dev->name, local->channel);
		goto fail;
	}

	ret = hostap_set_word(dev, HFA384X_RID_CNFBEACONINT,
			      local->beacon_int);
	if (ret) {
		printk("%s: Beacon interval setting to %d failed\n",
		       dev->name, local->beacon_int);
		/* this may fail with Symbol/Lucent firmware */
		if (ret == -ETIMEDOUT)
			goto fail;
	}

	ret = hostap_set_word(dev, HFA384X_RID_CNFOWNDTIMPERIOD,
			      local->dtim_period);
	if (ret) {
		printk("%s: DTIM period setting to %d failed\n",
		       dev->name, local->dtim_period);
		/* this may fail with Symbol/Lucent firmware */
		if (ret == -ETIMEDOUT)
			goto fail;
	}

	ret = hostap_set_word(dev, HFA384X_RID_PROMISCUOUSMODE,
			      local->is_promisc);
	if (ret)
		printk(KERN_INFO "%s: Setting promiscuous mode (%d) failed\n",
		       dev->name, local->is_promisc);

	if (!local->fw_ap) {
		ret = hostap_set_string(dev, HFA384X_RID_CNFDESIREDSSID,
					local->essid);
		if (ret) {
			printk("%s: Desired SSID setting failed\n", dev->name);
			goto fail;
		}
	}

	/* Setup TXRateControl, defaults to allow use of 1, 2, 5.5, and
	 * 11 Mbps in automatic TX rate fallback and 1 and 2 Mbps as basic
	 * rates */
	if (local->tx_rate_control == 0) {
		local->tx_rate_control =
			HFA384X_RATES_1MBPS |
			HFA384X_RATES_2MBPS |
			HFA384X_RATES_5MBPS |
			HFA384X_RATES_11MBPS;
	}
	if (local->basic_rates == 0)
		local->basic_rates = HFA384X_RATES_1MBPS | HFA384X_RATES_2MBPS;

	if (!local->fw_ap) {
		ret = hostap_set_word(dev, HFA384X_RID_TXRATECONTROL,
				      local->tx_rate_control);
		if (ret) {
			printk("%s: TXRateControl setting to %d failed\n",
			       dev->name, local->tx_rate_control);
			goto fail;
		}

		ret = hostap_set_word(dev, HFA384X_RID_CNFSUPPORTEDRATES,
				      local->tx_rate_control);
		if (ret) {
			printk("%s: cnfSupportedRates setting to %d failed\n",
			       dev->name, local->tx_rate_control);
		}

		ret = hostap_set_word(dev, HFA384X_RID_CNFBASICRATES,
				      local->basic_rates);
		if (ret) {
			printk("%s: cnfBasicRates setting to %d failed\n",
			       dev->name, local->basic_rates);
		}

		ret = hostap_set_word(dev, HFA384X_RID_CREATEIBSS, 1);
		if (ret) {
			printk("%s: Create IBSS setting to 1 failed\n",
			       dev->name);
		}
	}

	if (local->name_set)
		(void) hostap_set_string(dev, HFA384X_RID_CNFOWNNAME,
					 local->name);

	if (hostap_set_encryption(local)) {
		printk(KERN_INFO "%s: could not configure encryption\n",
		       dev->name);
	}

	(void) hostap_set_antsel(local);

	if (hostap_set_roaming(local)) {
		printk(KERN_INFO "%s: could not set host roaming\n",
		       dev->name);
	}

	if (local->sta_fw_ver >= PRISM2_FW_VER(1,6,3) &&
	    hostap_set_word(dev, HFA384X_RID_CNFENHSECURITY, local->enh_sec))
		printk(KERN_INFO "%s: cnfEnhSecurity setting to 0x%x failed\n",
		       dev->name, local->enh_sec);

	/* 32-bit tallies were added in STA f/w 0.8.0, but they were apparently
	 * not working correctly (last seven counters report bogus values).
	 * This has been fixed in 0.8.2, so enable 32-bit tallies only
	 * beginning with that firmware version. Another bug fix for 32-bit
	 * tallies in 1.4.0; should 16-bit tallies be used for some other
	 * versions, too? */
	if (local->sta_fw_ver >= PRISM2_FW_VER(0,8,2)) {
		if (hostap_set_word(dev, HFA384X_RID_CNFTHIRTY2TALLY, 1)) {
			printk(KERN_INFO "%s: cnfThirty2Tally setting "
			       "failed\n", dev->name);
			local->tallies32 = 0;
		} else
			local->tallies32 = 1;
	} else
		local->tallies32 = 0;

	hostap_set_auth_algs(local);

	if (hostap_set_word(dev, HFA384X_RID_FRAGMENTATIONTHRESHOLD,
			    local->fragm_threshold)) {
		printk(KERN_INFO "%s: setting FragmentationThreshold to %d "
		       "failed\n", dev->name, local->fragm_threshold);
	}

	if (hostap_set_word(dev, HFA384X_RID_RTSTHRESHOLD,
			    local->rts_threshold)) {
		printk(KERN_INFO "%s: setting RTSThreshold to %d failed\n",
		       dev->name, local->rts_threshold);
	}

	if (local->manual_retry_count >= 0 &&
	    hostap_set_word(dev, HFA384X_RID_CNFALTRETRYCOUNT,
			    local->manual_retry_count)) {
		printk(KERN_INFO "%s: setting cnfAltRetryCount to %d failed\n",
		       dev->name, local->manual_retry_count);
	}

	if (local->sta_fw_ver >= PRISM2_FW_VER(1,3,1) &&
	    hfa384x_get_rid(dev, HFA384X_RID_CNFDBMADJUST, &tmp, 2, 1) == 2) {
		local->rssi_to_dBm = le16_to_cpu(tmp);
	}

	if (local->sta_fw_ver >= PRISM2_FW_VER(1,7,0) && local->wpa &&
	    hostap_set_word(dev, HFA384X_RID_SSNHANDLINGMODE, 1)) {
		printk(KERN_INFO "%s: setting ssnHandlingMode to 1 failed\n",
		       dev->name);
	}

	if (local->sta_fw_ver >= PRISM2_FW_VER(1,7,0) && local->generic_elem &&
	    hfa384x_set_rid(dev, HFA384X_RID_GENERICELEMENT,
			    local->generic_elem, local->generic_elem_len)) {
		printk(KERN_INFO "%s: setting genericElement failed\n",
		       dev->name);
	}

 fail:
	return ret;
}


static int prism2_hw_init(struct net_device *dev, int initial)
{
	struct hostap_interface *iface;
	local_info_t *local;
	int ret, first = 1;
	unsigned long start, delay;

	PDEBUG(DEBUG_FLOW, "prism2_hw_init()\n");

	iface = netdev_priv(dev);
	local = iface->local;

	clear_bit(HOSTAP_BITS_TRANSMIT, &local->bits);

 init:
	/* initialize HFA 384x */
	ret = hfa384x_cmd_no_wait(dev, HFA384X_CMDCODE_INIT, 0);
	if (ret) {
		printk(KERN_INFO "%s: first command failed - assuming card "
		       "does not have primary firmware\n", dev_info);
	}

	if (first && (HFA384X_INW(HFA384X_EVSTAT_OFF) & HFA384X_EV_CMD)) {
		/* EvStat has Cmd bit set in some cases, so retry once if no
		 * wait was needed */
		HFA384X_OUTW(HFA384X_EV_CMD, HFA384X_EVACK_OFF);
		printk(KERN_DEBUG "%s: init command completed too quickly - "
		       "retrying\n", dev->name);
		first = 0;
		goto init;
	}

	start = jiffies;
	delay = jiffies + HFA384X_INIT_TIMEOUT;
	while (!(HFA384X_INW(HFA384X_EVSTAT_OFF) & HFA384X_EV_CMD) &&
	       time_before(jiffies, delay))
		yield();
	if (!(HFA384X_INW(HFA384X_EVSTAT_OFF) & HFA384X_EV_CMD)) {
		printk(KERN_DEBUG "%s: assuming no Primary image in "
		       "flash - card initialization not completed\n",
		       dev_info);
		local->no_pri = 1;
#ifdef PRISM2_DOWNLOAD_SUPPORT
			if (local->sram_type == -1)
				local->sram_type = prism2_get_ram_size(local);
#endif /* PRISM2_DOWNLOAD_SUPPORT */
		return 1;
	}
	local->no_pri = 0;
	printk(KERN_DEBUG "prism2_hw_init: initialized in %lu ms\n",
	       (jiffies - start) * 1000 / HZ);
	HFA384X_OUTW(HFA384X_EV_CMD, HFA384X_EVACK_OFF);
	return 0;
}


static int prism2_hw_init2(struct net_device *dev, int initial)
{
	struct hostap_interface *iface;
	local_info_t *local;
	int i;

	iface = netdev_priv(dev);
	local = iface->local;

#ifdef PRISM2_DOWNLOAD_SUPPORT
	kfree(local->pda);
	if (local->no_pri)
		local->pda = NULL;
	else
		local->pda = prism2_read_pda(dev);
#endif /* PRISM2_DOWNLOAD_SUPPORT */

	hfa384x_disable_interrupts(dev);

#ifndef final_version
	HFA384X_OUTW(HFA384X_MAGIC, HFA384X_SWSUPPORT0_OFF);
	if (HFA384X_INW(HFA384X_SWSUPPORT0_OFF) != HFA384X_MAGIC) {
		printk("SWSUPPORT0 write/read failed: %04X != %04X\n",
		       HFA384X_INW(HFA384X_SWSUPPORT0_OFF), HFA384X_MAGIC);
		goto failed;
	}
#endif

	if (initial || local->pri_only) {
		hfa384x_events_only_cmd(dev);
		/* get card version information */
		if (prism2_get_version_info(dev, HFA384X_RID_NICID, "NIC") ||
		    prism2_get_version_info(dev, HFA384X_RID_PRIID, "PRI")) {
			hfa384x_disable_interrupts(dev);
			goto failed;
		}

		if (prism2_get_version_info(dev, HFA384X_RID_STAID, "STA")) {
			printk(KERN_DEBUG "%s: Failed to read STA f/w version "
			       "- only Primary f/w present\n", dev->name);
			local->pri_only = 1;
			return 0;
		}
		local->pri_only = 0;
		hfa384x_disable_interrupts(dev);
	}

	/* FIX: could convert allocate_fid to use sleeping CmdCompl wait and
	 * enable interrupts before this. This would also require some sort of
	 * sleeping AllocEv waiting */

	/* allocate TX FIDs */
	local->txfid_len = PRISM2_TXFID_LEN;
	for (i = 0; i < PRISM2_TXFID_COUNT; i++) {
		local->txfid[i] = hfa384x_allocate_fid(dev, local->txfid_len);
		if (local->txfid[i] == 0xffff && local->txfid_len > 1600) {
			local->txfid[i] = hfa384x_allocate_fid(dev, 1600);
			if (local->txfid[i] != 0xffff) {
				printk(KERN_DEBUG "%s: Using shorter TX FID "
				       "(1600 bytes)\n", dev->name);
				local->txfid_len = 1600;
			}
		}
		if (local->txfid[i] == 0xffff)
			goto failed;
		local->intransmitfid[i] = PRISM2_TXFID_EMPTY;
	}

	hfa384x_events_only_cmd(dev);

	if (initial) {
		struct list_head *ptr;
		prism2_check_sta_fw_version(local);

		if (hfa384x_get_rid(dev, HFA384X_RID_CNFOWNMACADDR,
				    dev->dev_addr, 6, 1) < 0) {
			printk("%s: could not get own MAC address\n",
			       dev->name);
		}
		list_for_each(ptr, &local->hostap_interfaces) {
			iface = list_entry(ptr, struct hostap_interface, list);
			eth_hw_addr_inherit(iface->dev, dev);
		}
	} else if (local->fw_ap)
		prism2_check_sta_fw_version(local);

	prism2_setup_rids(dev);

	/* MAC is now configured, but port 0 is not yet enabled */
	return 0;

 failed:
	if (!local->no_pri)
		printk(KERN_WARNING "%s: Initialization failed\n", dev_info);
	return 1;
}


static int prism2_hw_enable(struct net_device *dev, int initial)
{
	struct hostap_interface *iface;
	local_info_t *local;
	int was_resetting;

	iface = netdev_priv(dev);
	local = iface->local;
	was_resetting = local->hw_resetting;

	if (hfa384x_cmd(dev, HFA384X_CMDCODE_ENABLE, 0, NULL, NULL)) {
		printk("%s: MAC port 0 enabling failed\n", dev->name);
		return 1;
	}

	local->hw_ready = 1;
	local->hw_reset_tries = 0;
	local->hw_resetting = 0;
	hfa384x_enable_interrupts(dev);

	/* at least D-Link DWL-650 seems to require additional port reset
	 * before it starts acting as an AP, so reset port automatically
	 * here just in case */
	if (initial && prism2_reset_port(dev)) {
		printk("%s: MAC port 0 resetting failed\n", dev->name);
		return 1;
	}

	if (was_resetting && netif_queue_stopped(dev)) {
		/* If hw_reset() was called during pending transmit, netif
		 * queue was stopped. Wake it up now since the wlan card has
		 * been resetted. */
		netif_wake_queue(dev);
	}

	return 0;
}


static int prism2_hw_config(struct net_device *dev, int initial)
{
	struct hostap_interface *iface;
	local_info_t *local;

	iface = netdev_priv(dev);
	local = iface->local;

	if (local->hw_downloading)
		return 1;

	if (prism2_hw_init(dev, initial)) {
		return local->no_pri ? 0 : 1;
	}

	if (prism2_hw_init2(dev, initial))
		return 1;

	/* Enable firmware if secondary image is loaded and at least one of the
	 * netdevices is up. */
	if (!local->pri_only &&
	    (initial == 0 || (initial == 2 && local->num_dev_open > 0))) {
		if (!local->dev_enabled)
			prism2_callback(local, PRISM2_CALLBACK_ENABLE);
		local->dev_enabled = 1;
		return prism2_hw_enable(dev, initial);
	}

	return 0;
}


static void prism2_hw_shutdown(struct net_device *dev, int no_disable)
{
	struct hostap_interface *iface;
	local_info_t *local;

	iface = netdev_priv(dev);
	local = iface->local;

	/* Allow only command completion events during disable */
	hfa384x_events_only_cmd(dev);

	local->hw_ready = 0;
	if (local->dev_enabled)
		prism2_callback(local, PRISM2_CALLBACK_DISABLE);
	local->dev_enabled = 0;

	if (local->func->card_present && !local->func->card_present(local)) {
		printk(KERN_DEBUG "%s: card already removed or not configured "
		       "during shutdown\n", dev->name);
		return;
	}

	if ((no_disable & HOSTAP_HW_NO_DISABLE) == 0 &&
	    hfa384x_cmd(dev, HFA384X_CMDCODE_DISABLE, 0, NULL, NULL))
		printk(KERN_WARNING "%s: Shutdown failed\n", dev_info);

	hfa384x_disable_interrupts(dev);

	if (no_disable & HOSTAP_HW_ENABLE_CMDCOMPL)
		hfa384x_events_only_cmd(dev);
	else
		prism2_clear_cmd_queue(local);
}


static void prism2_hw_reset(struct net_device *dev)
{
	struct hostap_interface *iface;
	local_info_t *local;

#if 0
	static long last_reset = 0;

	/* do not reset card more than once per second to avoid ending up in a
	 * busy loop resetting the card */
	if (time_before_eq(jiffies, last_reset + HZ))
		return;
	last_reset = jiffies;
#endif

	iface = netdev_priv(dev);
	local = iface->local;

	if (in_interrupt()) {
		printk(KERN_DEBUG "%s: driver bug - prism2_hw_reset() called "
		       "in interrupt context\n", dev->name);
		return;
	}

	if (local->hw_downloading)
		return;

	if (local->hw_resetting) {
		printk(KERN_WARNING "%s: %s: already resetting card - "
		       "ignoring reset request\n", dev_info, dev->name);
		return;
	}

	local->hw_reset_tries++;
	if (local->hw_reset_tries > 10) {
		printk(KERN_WARNING "%s: too many reset tries, skipping\n",
		       dev->name);
		return;
	}

	printk(KERN_WARNING "%s: %s: resetting card\n", dev_info, dev->name);
	hfa384x_disable_interrupts(dev);
	local->hw_resetting = 1;
	if (local->func->cor_sreset) {
		/* Host system seems to hang in some cases with high traffic
		 * load or shared interrupts during COR sreset. Disable shared
		 * interrupts during reset to avoid these crashes. COS sreset
		 * takes quite a long time, so it is unfortunate that this
		 * seems to be needed. Anyway, I do not know of any better way
		 * of avoiding the crash. */
		disable_irq(dev->irq);
		local->func->cor_sreset(local);
		enable_irq(dev->irq);
	}
	prism2_hw_shutdown(dev, 1);
	prism2_hw_config(dev, 0);
	local->hw_resetting = 0;

#ifdef PRISM2_DOWNLOAD_SUPPORT
	if (local->dl_pri) {
		printk(KERN_DEBUG "%s: persistent download of primary "
		       "firmware\n", dev->name);
		if (prism2_download_genesis(local, local->dl_pri) < 0)
			printk(KERN_WARNING "%s: download (PRI) failed\n",
			       dev->name);
	}

	if (local->dl_sec) {
		printk(KERN_DEBUG "%s: persistent download of secondary "
		       "firmware\n", dev->name);
		if (prism2_download_volatile(local, local->dl_sec) < 0)
			printk(KERN_WARNING "%s: download (SEC) failed\n",
			       dev->name);
	}
#endif /* PRISM2_DOWNLOAD_SUPPORT */

	/* TODO: restore beacon TIM bits for STAs that have buffered frames */
}


static void prism2_schedule_reset(local_info_t *local)
{
	schedule_work(&local->reset_queue);
}


/* Called only as scheduled task after noticing card timeout in interrupt
 * context */
static void handle_reset_queue(struct work_struct *work)
{
	local_info_t *local = container_of(work, local_info_t, reset_queue);

	printk(KERN_DEBUG "%s: scheduled card reset\n", local->dev->name);
	prism2_hw_reset(local->dev);

	if (netif_queue_stopped(local->dev)) {
		int i;

		for (i = 0; i < PRISM2_TXFID_COUNT; i++)
			if (local->intransmitfid[i] == PRISM2_TXFID_EMPTY) {
				PDEBUG(DEBUG_EXTRA, "prism2_tx_timeout: "
				       "wake up queue\n");
				netif_wake_queue(local->dev);
				break;
			}
	}
}


static int prism2_get_txfid_idx(local_info_t *local)
{
	int idx, end;
	unsigned long flags;

	spin_lock_irqsave(&local->txfidlock, flags);
	end = idx = local->next_txfid;
	do {
		if (local->intransmitfid[idx] == PRISM2_TXFID_EMPTY) {
			local->intransmitfid[idx] = PRISM2_TXFID_RESERVED;
			spin_unlock_irqrestore(&local->txfidlock, flags);
			return idx;
		}
		idx++;
		if (idx >= PRISM2_TXFID_COUNT)
			idx = 0;
	} while (idx != end);
	spin_unlock_irqrestore(&local->txfidlock, flags);

	PDEBUG(DEBUG_EXTRA2, "prism2_get_txfid_idx: no room in txfid buf: "
	       "packet dropped\n");
	local->dev->stats.tx_dropped++;

	return -1;
}


/* Called only from hardware IRQ */
static void prism2_transmit_cb(struct net_device *dev, long context,
			       u16 resp0, u16 res)
{
	struct hostap_interface *iface;
	local_info_t *local;
	int idx = (int) context;

	iface = netdev_priv(dev);
	local = iface->local;

	if (res) {
		printk(KERN_DEBUG "%s: prism2_transmit_cb - res=0x%02x\n",
		       dev->name, res);
		return;
	}

	if (idx < 0 || idx >= PRISM2_TXFID_COUNT) {
		printk(KERN_DEBUG "%s: prism2_transmit_cb called with invalid "
		       "idx=%d\n", dev->name, idx);
		return;
	}

	if (!test_and_clear_bit(HOSTAP_BITS_TRANSMIT, &local->bits)) {
		printk(KERN_DEBUG "%s: driver bug: prism2_transmit_cb called "
		       "with no pending transmit\n", dev->name);
	}

	if (netif_queue_stopped(dev)) {
		/* ready for next TX, so wake up queue that was stopped in
		 * prism2_transmit() */
		netif_wake_queue(dev);
	}

	spin_lock(&local->txfidlock);

	/* With reclaim, Resp0 contains new txfid for transmit; the old txfid
	 * will be automatically allocated for the next TX frame */
	local->intransmitfid[idx] = resp0;

	PDEBUG(DEBUG_FID, "%s: prism2_transmit_cb: txfid[%d]=0x%04x, "
	       "resp0=0x%04x, transmit_txfid=0x%04x\n",
	       dev->name, idx, local->txfid[idx],
	       resp0, local->intransmitfid[local->next_txfid]);

	idx++;
	if (idx >= PRISM2_TXFID_COUNT)
		idx = 0;
	local->next_txfid = idx;

	/* check if all TX buffers are occupied */
	do {
		if (local->intransmitfid[idx] == PRISM2_TXFID_EMPTY) {
			spin_unlock(&local->txfidlock);
			return;
		}
		idx++;
		if (idx >= PRISM2_TXFID_COUNT)
			idx = 0;
	} while (idx != local->next_txfid);
	spin_unlock(&local->txfidlock);

	/* no empty TX buffers, stop queue */
	netif_stop_queue(dev);
}


/* Called only from software IRQ if PCI bus master is not used (with bus master
 * this can be called both from software and hardware IRQ) */
static int prism2_transmit(struct net_device *dev, int idx)
{
	struct hostap_interface *iface;
	local_info_t *local;
	int res;

	iface = netdev_priv(dev);
	local = iface->local;

	/* The driver tries to stop netif queue so that there would not be
	 * more than one attempt to transmit frames going on; check that this
	 * is really the case */

	if (test_and_set_bit(HOSTAP_BITS_TRANSMIT, &local->bits)) {
		printk(KERN_DEBUG "%s: driver bug - prism2_transmit() called "
		       "when previous TX was pending\n", dev->name);
		return -1;
	}

	/* stop the queue for the time that transmit is pending */
	netif_stop_queue(dev);

	/* transmit packet */
	res = hfa384x_cmd_callback(
		dev,
		HFA384X_CMDCODE_TRANSMIT | HFA384X_CMD_TX_RECLAIM,
		local->txfid[idx],
		prism2_transmit_cb, (long) idx);

	if (res) {
		printk(KERN_DEBUG "%s: prism2_transmit: CMDCODE_TRANSMIT "
		       "failed (res=%d)\n", dev->name, res);
		dev->stats.tx_dropped++;
		netif_wake_queue(dev);
		return -1;
	}
	dev->trans_start = jiffies;

	/* Since we did not wait for command completion, the card continues
	 * to process on the background and we will finish handling when
	 * command completion event is handled (prism2_cmd_ev() function) */

	return 0;
}


/* Send IEEE 802.11 frame (convert the header into Prism2 TX descriptor and
 * send the payload with this descriptor) */
/* Called only from software IRQ */
static int prism2_tx_80211(struct sk_buff *skb, struct net_device *dev)
{
	struct hostap_interface *iface;
	local_info_t *local;
	struct hfa384x_tx_frame txdesc;
	struct hostap_skb_tx_data *meta;
	int hdr_len, data_len, idx, res, ret = -1;
	u16 tx_control, fc;

	iface = netdev_priv(dev);
	local = iface->local;

	meta = (struct hostap_skb_tx_data *) skb->cb;

	prism2_callback(local, PRISM2_CALLBACK_TX_START);

	if ((local->func->card_present && !local->func->card_present(local)) ||
	    !local->hw_ready || local->hw_downloading || local->pri_only) {
		if (net_ratelimit()) {
			printk(KERN_DEBUG "%s: prism2_tx_80211: hw not ready -"
			       " skipping\n", dev->name);
		}
		goto fail;
	}

	memset(&txdesc, 0, sizeof(txdesc));

	/* skb->data starts with txdesc->frame_control */
	hdr_len = 24;
	skb_copy_from_linear_data(skb, &txdesc.frame_control, hdr_len);
 	fc = le16_to_cpu(txdesc.frame_control);
	if (ieee80211_is_data(txdesc.frame_control) &&
	    ieee80211_has_a4(txdesc.frame_control) &&
	    skb->len >= 30) {
		/* Addr4 */
		skb_copy_from_linear_data_offset(skb, hdr_len, txdesc.addr4,
						 ETH_ALEN);
		hdr_len += ETH_ALEN;
	}

	tx_control = local->tx_control;
	if (meta->tx_cb_idx) {
		tx_control |= HFA384X_TX_CTRL_TX_OK;
		txdesc.sw_support = cpu_to_le32(meta->tx_cb_idx);
	}
	txdesc.tx_control = cpu_to_le16(tx_control);
	txdesc.tx_rate = meta->rate;

	data_len = skb->len - hdr_len;
	txdesc.data_len = cpu_to_le16(data_len);
	txdesc.len = cpu_to_be16(data_len);

	idx = prism2_get_txfid_idx(local);
	if (idx < 0)
		goto fail;

	if (local->frame_dump & PRISM2_DUMP_TX_HDR)
		hostap_dump_tx_header(dev->name, &txdesc);

	spin_lock(&local->baplock);
	res = hfa384x_setup_bap(dev, BAP0, local->txfid[idx], 0);

	if (!res)
		res = hfa384x_to_bap(dev, BAP0, &txdesc, sizeof(txdesc));
	if (!res)
		res = hfa384x_to_bap(dev, BAP0, skb->data + hdr_len,
				     skb->len - hdr_len);
	spin_unlock(&local->baplock);

	if (!res)
		res = prism2_transmit(dev, idx);
	if (res) {
		printk(KERN_DEBUG "%s: prism2_tx_80211 - to BAP0 failed\n",
		       dev->name);
		local->intransmitfid[idx] = PRISM2_TXFID_EMPTY;
		schedule_work(&local->reset_queue);
		goto fail;
	}

	ret = 0;

fail:
	prism2_callback(local, PRISM2_CALLBACK_TX_END);
	return ret;
}


/* Some SMP systems have reported number of odd errors with hostap_pci. fid
 * register has changed values between consecutive reads for an unknown reason.
 * This should really not happen, so more debugging is needed. This test
 * version is a bit slower, but it will detect most of such register changes
 * and will try to get the correct fid eventually. */
#define EXTRA_FID_READ_TESTS

static u16 prism2_read_fid_reg(struct net_device *dev, u16 reg)
{
#ifdef EXTRA_FID_READ_TESTS
	u16 val, val2, val3;
	int i;

	for (i = 0; i < 10; i++) {
		val = HFA384X_INW(reg);
		val2 = HFA384X_INW(reg);
		val3 = HFA384X_INW(reg);

		if (val == val2 && val == val3)
			return val;

		printk(KERN_DEBUG "%s: detected fid change (try=%d, reg=%04x):"
		       " %04x %04x %04x\n",
		       dev->name, i, reg, val, val2, val3);
		if ((val == val2 || val == val3) && val != 0)
			return val;
		if (val2 == val3 && val2 != 0)
			return val2;
	}
	printk(KERN_WARNING "%s: Uhhuh.. could not read good fid from reg "
	       "%04x (%04x %04x %04x)\n", dev->name, reg, val, val2, val3);
	return val;
#else /* EXTRA_FID_READ_TESTS */
	return HFA384X_INW(reg);
#endif /* EXTRA_FID_READ_TESTS */
}


/* Called only as a tasklet (software IRQ) */
static void prism2_rx(local_info_t *local)
{
	struct net_device *dev = local->dev;
	int res, rx_pending = 0;
	u16 len, hdr_len, rxfid, status, macport;
	struct hfa384x_rx_frame rxdesc;
	struct sk_buff *skb = NULL;

	prism2_callback(local, PRISM2_CALLBACK_RX_START);

	rxfid = prism2_read_fid_reg(dev, HFA384X_RXFID_OFF);
#ifndef final_version
	if (rxfid == 0) {
		rxfid = HFA384X_INW(HFA384X_RXFID_OFF);
		printk(KERN_DEBUG "prism2_rx: rxfid=0 (next 0x%04x)\n",
		       rxfid);
		if (rxfid == 0) {
			schedule_work(&local->reset_queue);
			goto rx_dropped;
		}
		/* try to continue with the new rxfid value */
	}
#endif

	spin_lock(&local->baplock);
	res = hfa384x_setup_bap(dev, BAP0, rxfid, 0);
	if (!res)
		res = hfa384x_from_bap(dev, BAP0, &rxdesc, sizeof(rxdesc));

	if (res) {
		spin_unlock(&local->baplock);
		printk(KERN_DEBUG "%s: copy from BAP0 failed %d\n", dev->name,
		       res);
		if (res == -ETIMEDOUT) {
			schedule_work(&local->reset_queue);
		}
		goto rx_dropped;
	}

	len = le16_to_cpu(rxdesc.data_len);
	hdr_len = sizeof(rxdesc);
	status = le16_to_cpu(rxdesc.status);
	macport = (status >> 8) & 0x07;

	/* Drop frames with too large reported payload length. Monitor mode
	 * seems to sometimes pass frames (e.g., ctrl::ack) with signed and
	 * negative value, so allow also values 65522 .. 65534 (-14 .. -2) for
	 * macport 7 */
	if (len > PRISM2_DATA_MAXLEN + 8 /* WEP */) {
		if (macport == 7 && local->iw_mode == IW_MODE_MONITOR) {
			if (len >= (u16) -14) {
				hdr_len -= 65535 - len;
				hdr_len--;
			}
			len = 0;
		} else {
			spin_unlock(&local->baplock);
			printk(KERN_DEBUG "%s: Received frame with invalid "
			       "length 0x%04x\n", dev->name, len);
			hostap_dump_rx_header(dev->name, &rxdesc);
			goto rx_dropped;
		}
	}

	skb = dev_alloc_skb(len + hdr_len);
	if (!skb) {
		spin_unlock(&local->baplock);
		printk(KERN_DEBUG "%s: RX failed to allocate skb\n",
		       dev->name);
		goto rx_dropped;
	}
	skb->dev = dev;
	memcpy(skb_put(skb, hdr_len), &rxdesc, hdr_len);

	if (len > 0)
		res = hfa384x_from_bap(dev, BAP0, skb_put(skb, len), len);
	spin_unlock(&local->baplock);
	if (res) {
		printk(KERN_DEBUG "%s: RX failed to read "
		       "frame data\n", dev->name);
		goto rx_dropped;
	}

	skb_queue_tail(&local->rx_list, skb);
	tasklet_schedule(&local->rx_tasklet);

 rx_exit:
	prism2_callback(local, PRISM2_CALLBACK_RX_END);
	if (!rx_pending) {
		HFA384X_OUTW(HFA384X_EV_RX, HFA384X_EVACK_OFF);
	}

	return;

 rx_dropped:
	dev->stats.rx_dropped++;
	if (skb)
		dev_kfree_skb(skb);
	goto rx_exit;
}


/* Called only as a tasklet (software IRQ) */
static void hostap_rx_skb(local_info_t *local, struct sk_buff *skb)
{
	struct hfa384x_rx_frame *rxdesc;
	struct net_device *dev = skb->dev;
	struct hostap_80211_rx_status stats;
	int hdrlen, rx_hdrlen;

	rx_hdrlen = sizeof(*rxdesc);
	if (skb->len < sizeof(*rxdesc)) {
		/* Allow monitor mode to receive shorter frames */
		if (local->iw_mode == IW_MODE_MONITOR &&
		    skb->len >= sizeof(*rxdesc) - 30) {
			rx_hdrlen = skb->len;
		} else {
			dev_kfree_skb(skb);
			return;
		}
	}

	rxdesc = (struct hfa384x_rx_frame *) skb->data;

	if (local->frame_dump & PRISM2_DUMP_RX_HDR &&
	    skb->len >= sizeof(*rxdesc))
		hostap_dump_rx_header(dev->name, rxdesc);

	if (le16_to_cpu(rxdesc->status) & HFA384X_RX_STATUS_FCSERR &&
	    (!local->monitor_allow_fcserr ||
	     local->iw_mode != IW_MODE_MONITOR))
		goto drop;

	if (skb->len > PRISM2_DATA_MAXLEN) {
		printk(KERN_DEBUG "%s: RX: len(%d) > MAX(%d)\n",
		       dev->name, skb->len, PRISM2_DATA_MAXLEN);
		goto drop;
	}

	stats.mac_time = le32_to_cpu(rxdesc->time);
	stats.signal = rxdesc->signal - local->rssi_to_dBm;
	stats.noise = rxdesc->silence - local->rssi_to_dBm;
	stats.rate = rxdesc->rate;

	/* Convert Prism2 RX structure into IEEE 802.11 header */
	hdrlen = hostap_80211_get_hdrlen(rxdesc->frame_control);
	if (hdrlen > rx_hdrlen)
		hdrlen = rx_hdrlen;

	memmove(skb_pull(skb, rx_hdrlen - hdrlen),
		&rxdesc->frame_control, hdrlen);

	hostap_80211_rx(dev, skb, &stats);
	return;

 drop:
	dev_kfree_skb(skb);
}


/* Called only as a tasklet (software IRQ) */
static void hostap_rx_tasklet(unsigned long data)
{
	local_info_t *local = (local_info_t *) data;
	struct sk_buff *skb;

	while ((skb = skb_dequeue(&local->rx_list)) != NULL)
		hostap_rx_skb(local, skb);
}


/* Called only from hardware IRQ */
static void prism2_alloc_ev(struct net_device *dev)
{
	struct hostap_interface *iface;
	local_info_t *local;
	int idx;
	u16 fid;

	iface = netdev_priv(dev);
	local = iface->local;

	fid = prism2_read_fid_reg(dev, HFA384X_ALLOCFID_OFF);

	PDEBUG(DEBUG_FID, "FID: interrupt: ALLOC - fid=0x%04x\n", fid);

	spin_lock(&local->txfidlock);
	idx = local->next_alloc;

	do {
		if (local->txfid[idx] == fid) {
			PDEBUG(DEBUG_FID, "FID: found matching txfid[%d]\n",
			       idx);

#ifndef final_version
			if (local->intransmitfid[idx] == PRISM2_TXFID_EMPTY)
				printk("Already released txfid found at idx "
				       "%d\n", idx);
			if (local->intransmitfid[idx] == PRISM2_TXFID_RESERVED)
				printk("Already reserved txfid found at idx "
				       "%d\n", idx);
#endif
			local->intransmitfid[idx] = PRISM2_TXFID_EMPTY;
			idx++;
			local->next_alloc = idx >= PRISM2_TXFID_COUNT ? 0 :
				idx;

			if (!test_bit(HOSTAP_BITS_TRANSMIT, &local->bits) &&
			    netif_queue_stopped(dev))
				netif_wake_queue(dev);

			spin_unlock(&local->txfidlock);
			return;
		}

		idx++;
		if (idx >= PRISM2_TXFID_COUNT)
			idx = 0;
	} while (idx != local->next_alloc);

	printk(KERN_WARNING "%s: could not find matching txfid (0x%04x, new "
	       "read 0x%04x) for alloc event\n", dev->name, fid,
	       HFA384X_INW(HFA384X_ALLOCFID_OFF));
	printk(KERN_DEBUG "TXFIDs:");
	for (idx = 0; idx < PRISM2_TXFID_COUNT; idx++)
		printk(" %04x[%04x]", local->txfid[idx],
		       local->intransmitfid[idx]);
	printk("\n");
	spin_unlock(&local->txfidlock);

	/* FIX: should probably schedule reset; reference to one txfid was lost
	 * completely.. Bad things will happen if we run out of txfids
	 * Actually, this will cause netdev watchdog to notice TX timeout and
	 * then card reset after all txfids have been leaked. */
}


/* Called only as a tasklet (software IRQ) */
static void hostap_tx_callback(local_info_t *local,
			       struct hfa384x_tx_frame *txdesc, int ok,
			       char *payload)
{
	u16 sw_support, hdrlen, len;
	struct sk_buff *skb;
	struct hostap_tx_callback_info *cb;

	/* Make sure that frame was from us. */
	if (!ether_addr_equal(txdesc->addr2, local->dev->dev_addr)) {
		printk(KERN_DEBUG "%s: TX callback - foreign frame\n",
		       local->dev->name);
		return;
	}

	sw_support = le32_to_cpu(txdesc->sw_support);

	spin_lock(&local->lock);
	cb = local->tx_callback;
	while (cb != NULL && cb->idx != sw_support)
		cb = cb->next;
	spin_unlock(&local->lock);

	if (cb == NULL) {
		printk(KERN_DEBUG "%s: could not find TX callback (idx %d)\n",
		       local->dev->name, sw_support);
		return;
	}

	hdrlen = hostap_80211_get_hdrlen(txdesc->frame_control);
	len = le16_to_cpu(txdesc->data_len);
	skb = dev_alloc_skb(hdrlen + len);
	if (skb == NULL) {
		printk(KERN_DEBUG "%s: hostap_tx_callback failed to allocate "
		       "skb\n", local->dev->name);
		return;
	}

	memcpy(skb_put(skb, hdrlen), (void *) &txdesc->frame_control, hdrlen);
	if (payload)
		memcpy(skb_put(skb, len), payload, len);

	skb->dev = local->dev;
	skb_reset_mac_header(skb);

	cb->func(skb, ok, cb->data);
}


/* Called only as a tasklet (software IRQ) */
static int hostap_tx_compl_read(local_info_t *local, int error,
				struct hfa384x_tx_frame *txdesc,
				char **payload)
{
	u16 fid, len;
	int res, ret = 0;
	struct net_device *dev = local->dev;

	fid = prism2_read_fid_reg(dev, HFA384X_TXCOMPLFID_OFF);

	PDEBUG(DEBUG_FID, "interrupt: TX (err=%d) - fid=0x%04x\n", fid, error);

	spin_lock(&local->baplock);
	res = hfa384x_setup_bap(dev, BAP0, fid, 0);
	if (!res)
		res = hfa384x_from_bap(dev, BAP0, txdesc, sizeof(*txdesc));
	if (res) {
		PDEBUG(DEBUG_EXTRA, "%s: TX (err=%d) - fid=0x%04x - could not "
		       "read txdesc\n", dev->name, error, fid);
		if (res == -ETIMEDOUT) {
			schedule_work(&local->reset_queue);
		}
		ret = -1;
		goto fail;
	}
	if (txdesc->sw_support) {
		len = le16_to_cpu(txdesc->data_len);
		if (len < PRISM2_DATA_MAXLEN) {
			*payload = kmalloc(len, GFP_ATOMIC);
			if (*payload == NULL ||
			    hfa384x_from_bap(dev, BAP0, *payload, len)) {
				PDEBUG(DEBUG_EXTRA, "%s: could not read TX "
				       "frame payload\n", dev->name);
				kfree(*payload);
				*payload = NULL;
				ret = -1;
				goto fail;
			}
		}
	}

 fail:
	spin_unlock(&local->baplock);

	return ret;
}


/* Called only as a tasklet (software IRQ) */
static void prism2_tx_ev(local_info_t *local)
{
	struct net_device *dev = local->dev;
	char *payload = NULL;
	struct hfa384x_tx_frame txdesc;

	if (hostap_tx_compl_read(local, 0, &txdesc, &payload))
		goto fail;

	if (local->frame_dump & PRISM2_DUMP_TX_HDR) {
		PDEBUG(DEBUG_EXTRA, "%s: TX - status=0x%04x "
		       "retry_count=%d tx_rate=%d seq_ctrl=%d "
		       "duration_id=%d\n",
		       dev->name, le16_to_cpu(txdesc.status),
		       txdesc.retry_count, txdesc.tx_rate,
		       le16_to_cpu(txdesc.seq_ctrl),
		       le16_to_cpu(txdesc.duration_id));
	}

	if (txdesc.sw_support)
		hostap_tx_callback(local, &txdesc, 1, payload);
	kfree(payload);

 fail:
	HFA384X_OUTW(HFA384X_EV_TX, HFA384X_EVACK_OFF);
}


/* Called only as a tasklet (software IRQ) */
static void hostap_sta_tx_exc_tasklet(unsigned long data)
{
	local_info_t *local = (local_info_t *) data;
	struct sk_buff *skb;

	while ((skb = skb_dequeue(&local->sta_tx_exc_list)) != NULL) {
		struct hfa384x_tx_frame *txdesc =
			(struct hfa384x_tx_frame *) skb->data;

		if (skb->len >= sizeof(*txdesc)) {
			/* Convert Prism2 RX structure into IEEE 802.11 header
			 */
			int hdrlen = hostap_80211_get_hdrlen(txdesc->frame_control);
			memmove(skb_pull(skb, sizeof(*txdesc) - hdrlen),
				&txdesc->frame_control, hdrlen);

			hostap_handle_sta_tx_exc(local, skb);
		}
		dev_kfree_skb(skb);
	}
}


/* Called only as a tasklet (software IRQ) */
static void prism2_txexc(local_info_t *local)
{
	struct net_device *dev = local->dev;
	u16 status, fc;
	int show_dump, res;
	char *payload = NULL;
	struct hfa384x_tx_frame txdesc;

	show_dump = local->frame_dump & PRISM2_DUMP_TXEXC_HDR;
	dev->stats.tx_errors++;

	res = hostap_tx_compl_read(local, 1, &txdesc, &payload);
	HFA384X_OUTW(HFA384X_EV_TXEXC, HFA384X_EVACK_OFF);
	if (res)
		return;

	status = le16_to_cpu(txdesc.status);

	/* We produce a TXDROP event only for retry or lifetime
	 * exceeded, because that's the only status that really mean
	 * that this particular node went away.
	 * Other errors means that *we* screwed up. - Jean II */
	if (status & (HFA384X_TX_STATUS_RETRYERR | HFA384X_TX_STATUS_AGEDERR))
	{
		union iwreq_data wrqu;

		/* Copy 802.11 dest address. */
		memcpy(wrqu.addr.sa_data, txdesc.addr1, ETH_ALEN);
		wrqu.addr.sa_family = ARPHRD_ETHER;
		wireless_send_event(dev, IWEVTXDROP, &wrqu, NULL);
	} else
		show_dump = 1;

	if (local->iw_mode == IW_MODE_MASTER ||
	    local->iw_mode == IW_MODE_REPEAT ||
	    local->wds_type & HOSTAP_WDS_AP_CLIENT) {
		struct sk_buff *skb;
		skb = dev_alloc_skb(sizeof(txdesc));
		if (skb) {
			memcpy(skb_put(skb, sizeof(txdesc)), &txdesc,
			       sizeof(txdesc));
			skb_queue_tail(&local->sta_tx_exc_list, skb);
			tasklet_schedule(&local->sta_tx_exc_tasklet);
		}
	}

	if (txdesc.sw_support)
		hostap_tx_callback(local, &txdesc, 0, payload);
	kfree(payload);

	if (!show_dump)
		return;

	PDEBUG(DEBUG_EXTRA, "%s: TXEXC - status=0x%04x (%s%s%s%s)"
	       " tx_control=%04x\n",
	       dev->name, status,
	       status & HFA384X_TX_STATUS_RETRYERR ? "[RetryErr]" : "",
	       status & HFA384X_TX_STATUS_AGEDERR ? "[AgedErr]" : "",
	       status & HFA384X_TX_STATUS_DISCON ? "[Discon]" : "",
	       status & HFA384X_TX_STATUS_FORMERR ? "[FormErr]" : "",
	       le16_to_cpu(txdesc.tx_control));

	fc = le16_to_cpu(txdesc.frame_control);
	PDEBUG(DEBUG_EXTRA, "   retry_count=%d tx_rate=%d fc=0x%04x "
	       "(%s%s%s::%d%s%s)\n",
	       txdesc.retry_count, txdesc.tx_rate, fc,
	       ieee80211_is_mgmt(txdesc.frame_control) ? "Mgmt" : "",
	       ieee80211_is_ctl(txdesc.frame_control) ? "Ctrl" : "",
	       ieee80211_is_data(txdesc.frame_control) ? "Data" : "",
	       (fc & IEEE80211_FCTL_STYPE) >> 4,
	       ieee80211_has_tods(txdesc.frame_control) ? " ToDS" : "",
	       ieee80211_has_fromds(txdesc.frame_control) ? " FromDS" : "");
	PDEBUG(DEBUG_EXTRA, "   A1=%pM A2=%pM A3=%pM A4=%pM\n",
	       txdesc.addr1, txdesc.addr2,
	       txdesc.addr3, txdesc.addr4);
}


/* Called only as a tasklet (software IRQ) */
static void hostap_info_tasklet(unsigned long data)
{
	local_info_t *local = (local_info_t *) data;
	struct sk_buff *skb;

	while ((skb = skb_dequeue(&local->info_list)) != NULL) {
		hostap_info_process(local, skb);
		dev_kfree_skb(skb);
	}
}


/* Called only as a tasklet (software IRQ) */
static void prism2_info(local_info_t *local)
{
	struct net_device *dev = local->dev;
	u16 fid;
	int res, left;
	struct hfa384x_info_frame info;
	struct sk_buff *skb;

	fid = HFA384X_INW(HFA384X_INFOFID_OFF);

	spin_lock(&local->baplock);
	res = hfa384x_setup_bap(dev, BAP0, fid, 0);
	if (!res)
		res = hfa384x_from_bap(dev, BAP0, &info, sizeof(info));
	if (res) {
		spin_unlock(&local->baplock);
		printk(KERN_DEBUG "Could not get info frame (fid=0x%04x)\n",
		       fid);
		if (res == -ETIMEDOUT) {
			schedule_work(&local->reset_queue);
		}
		goto out;
	}

	left = (le16_to_cpu(info.len) - 1) * 2;

	if (info.len & cpu_to_le16(0x8000) || info.len == 0 || left > 2060) {
		/* data register seems to give 0x8000 in some error cases even
		 * though busy bit is not set in offset register;
		 * in addition, length must be at least 1 due to type field */
		spin_unlock(&local->baplock);
		printk(KERN_DEBUG "%s: Received info frame with invalid "
		       "length 0x%04x (type 0x%04x)\n", dev->name,
		       le16_to_cpu(info.len), le16_to_cpu(info.type));
		goto out;
	}

	skb = dev_alloc_skb(sizeof(info) + left);
	if (skb == NULL) {
		spin_unlock(&local->baplock);
		printk(KERN_DEBUG "%s: Could not allocate skb for info "
		       "frame\n", dev->name);
		goto out;
	}

	memcpy(skb_put(skb, sizeof(info)), &info, sizeof(info));
	if (left > 0 && hfa384x_from_bap(dev, BAP0, skb_put(skb, left), left))
	{
		spin_unlock(&local->baplock);
		printk(KERN_WARNING "%s: Info frame read failed (fid=0x%04x, "
		       "len=0x%04x, type=0x%04x\n", dev->name, fid,
		       le16_to_cpu(info.len), le16_to_cpu(info.type));
		dev_kfree_skb(skb);
		goto out;
	}
	spin_unlock(&local->baplock);

	skb_queue_tail(&local->info_list, skb);
	tasklet_schedule(&local->info_tasklet);

 out:
	HFA384X_OUTW(HFA384X_EV_INFO, HFA384X_EVACK_OFF);
}


/* Called only as a tasklet (software IRQ) */
static void hostap_bap_tasklet(unsigned long data)
{
	local_info_t *local = (local_info_t *) data;
	struct net_device *dev = local->dev;
	u16 ev;
	int frames = 30;

	if (local->func->card_present && !local->func->card_present(local))
		return;

	set_bit(HOSTAP_BITS_BAP_TASKLET, &local->bits);

	/* Process all pending BAP events without generating new interrupts
	 * for them */
	while (frames-- > 0) {
		ev = HFA384X_INW(HFA384X_EVSTAT_OFF);
		if (ev == 0xffff || !(ev & HFA384X_BAP0_EVENTS))
			break;
		if (ev & HFA384X_EV_RX)
			prism2_rx(local);
		if (ev & HFA384X_EV_INFO)
			prism2_info(local);
		if (ev & HFA384X_EV_TX)
			prism2_tx_ev(local);
		if (ev & HFA384X_EV_TXEXC)
			prism2_txexc(local);
	}

	set_bit(HOSTAP_BITS_BAP_TASKLET2, &local->bits);
	clear_bit(HOSTAP_BITS_BAP_TASKLET, &local->bits);

	/* Enable interrupts for new BAP events */
	hfa384x_events_all(dev);
	clear_bit(HOSTAP_BITS_BAP_TASKLET2, &local->bits);
}


/* Called only from hardware IRQ */
static void prism2_infdrop(struct net_device *dev)
{
	static unsigned long last_inquire = 0;

	PDEBUG(DEBUG_EXTRA, "%s: INFDROP event\n", dev->name);

	/* some firmware versions seem to get stuck with
	 * full CommTallies in high traffic load cases; every
	 * packet will then cause INFDROP event and CommTallies
	 * info frame will not be sent automatically. Try to
	 * get out of this state by inquiring CommTallies. */
	if (!last_inquire || time_after(jiffies, last_inquire + HZ)) {
		hfa384x_cmd_callback(dev, HFA384X_CMDCODE_INQUIRE,
				     HFA384X_INFO_COMMTALLIES, NULL, 0);
		last_inquire = jiffies;
	}
}


/* Called only from hardware IRQ */
static void prism2_ev_tick(struct net_device *dev)
{
	struct hostap_interface *iface;
	local_info_t *local;
	u16 evstat, inten;
	static int prev_stuck = 0;

	iface = netdev_priv(dev);
	local = iface->local;

	if (time_after(jiffies, local->last_tick_timer + 5 * HZ) &&
	    local->last_tick_timer) {
		evstat = HFA384X_INW(HFA384X_EVSTAT_OFF);
		inten = HFA384X_INW(HFA384X_INTEN_OFF);
		if (!prev_stuck) {
			printk(KERN_INFO "%s: SW TICK stuck? "
			       "bits=0x%lx EvStat=%04x IntEn=%04x\n",
			       dev->name, local->bits, evstat, inten);
		}
		local->sw_tick_stuck++;
		if ((evstat & HFA384X_BAP0_EVENTS) &&
		    (inten & HFA384X_BAP0_EVENTS)) {
			printk(KERN_INFO "%s: trying to recover from IRQ "
			       "hang\n", dev->name);
			hfa384x_events_no_bap0(dev);
		}
		prev_stuck = 1;
	} else
		prev_stuck = 0;
}


/* Called only from hardware IRQ */
static void prism2_check_magic(local_info_t *local)
{
	/* at least PCI Prism2.5 with bus mastering seems to sometimes
	 * return 0x0000 in SWSUPPORT0 for unknown reason, but re-reading the
	 * register once or twice seems to get the correct value.. PCI cards
	 * cannot anyway be removed during normal operation, so there is not
	 * really any need for this verification with them. */

#ifndef PRISM2_PCI
#ifndef final_version
	static unsigned long last_magic_err = 0;
	struct net_device *dev = local->dev;

	if (HFA384X_INW(HFA384X_SWSUPPORT0_OFF) != HFA384X_MAGIC) {
		if (!local->hw_ready)
			return;
		HFA384X_OUTW(0xffff, HFA384X_EVACK_OFF);
		if (time_after(jiffies, last_magic_err + 10 * HZ)) {
			printk("%s: Interrupt, but SWSUPPORT0 does not match: "
			       "%04X != %04X - card removed?\n", dev->name,
			       HFA384X_INW(HFA384X_SWSUPPORT0_OFF),
			       HFA384X_MAGIC);
			last_magic_err = jiffies;
		} else if (net_ratelimit()) {
			printk(KERN_DEBUG "%s: interrupt - SWSUPPORT0=%04x "
			       "MAGIC=%04x\n", dev->name,
			       HFA384X_INW(HFA384X_SWSUPPORT0_OFF),
			       HFA384X_MAGIC);
		}
		if (HFA384X_INW(HFA384X_SWSUPPORT0_OFF) != 0xffff)
			schedule_work(&local->reset_queue);
		return;
	}
#endif /* final_version */
#endif /* !PRISM2_PCI */
}


/* Called only from hardware IRQ */
static irqreturn_t prism2_interrupt(int irq, void *dev_id)
{
	struct net_device *dev = dev_id;
	struct hostap_interface *iface;
	local_info_t *local;
	int events = 0;
	u16 ev;

	iface = netdev_priv(dev);
	local = iface->local;

	/* Detect early interrupt before driver is fully configured */
	spin_lock(&local->irq_init_lock);
	if (!dev->base_addr) {
		if (net_ratelimit()) {
			printk(KERN_DEBUG "%s: Interrupt, but dev not configured\n",
			       dev->name);
		}
		spin_unlock(&local->irq_init_lock);
		return IRQ_HANDLED;
	}
	spin_unlock(&local->irq_init_lock);

	prism2_io_debug_add(dev, PRISM2_IO_DEBUG_CMD_INTERRUPT, 0, 0);

	if (local->func->card_present && !local->func->card_present(local)) {
		if (net_ratelimit()) {
			printk(KERN_DEBUG "%s: Interrupt, but dev not OK\n",
			       dev->name);
		}
		return IRQ_HANDLED;
	}

	prism2_check_magic(local);

	for (;;) {
		ev = HFA384X_INW(HFA384X_EVSTAT_OFF);
		if (ev == 0xffff) {
			if (local->shutdown)
				return IRQ_HANDLED;
			HFA384X_OUTW(0xffff, HFA384X_EVACK_OFF);
			printk(KERN_DEBUG "%s: prism2_interrupt: ev=0xffff\n",
			       dev->name);
			return IRQ_HANDLED;
		}

		ev &= HFA384X_INW(HFA384X_INTEN_OFF);
		if (ev == 0)
			break;

		if (ev & HFA384X_EV_CMD) {
			prism2_cmd_ev(dev);
		}

		/* Above events are needed even before hw is ready, but other
		 * events should be skipped during initialization. This may
		 * change for AllocEv if allocate_fid is implemented without
		 * busy waiting. */
		if (!local->hw_ready || local->hw_resetting ||
		    !local->dev_enabled) {
			ev = HFA384X_INW(HFA384X_EVSTAT_OFF);
			if (ev & HFA384X_EV_CMD)
				goto next_event;
			if ((ev & HFA384X_EVENT_MASK) == 0)
				return IRQ_HANDLED;
			if (local->dev_enabled && (ev & ~HFA384X_EV_TICK) &&
			    net_ratelimit()) {
				printk(KERN_DEBUG "%s: prism2_interrupt: hw "
				       "not ready; skipping events 0x%04x "
				       "(IntEn=0x%04x)%s%s%s\n",
				       dev->name, ev,
				       HFA384X_INW(HFA384X_INTEN_OFF),
				       !local->hw_ready ? " (!hw_ready)" : "",
				       local->hw_resetting ?
				       " (hw_resetting)" : "",
				       !local->dev_enabled ?
				       " (!dev_enabled)" : "");
			}
			HFA384X_OUTW(ev, HFA384X_EVACK_OFF);
			return IRQ_HANDLED;
		}

		if (ev & HFA384X_EV_TICK) {
			prism2_ev_tick(dev);
			HFA384X_OUTW(HFA384X_EV_TICK, HFA384X_EVACK_OFF);
		}

		if (ev & HFA384X_EV_ALLOC) {
			prism2_alloc_ev(dev);
			HFA384X_OUTW(HFA384X_EV_ALLOC, HFA384X_EVACK_OFF);
		}

		/* Reading data from the card is quite time consuming, so do it
		 * in tasklets. TX, TXEXC, RX, and INFO events will be ACKed
		 * and unmasked after needed data has been read completely. */
		if (ev & HFA384X_BAP0_EVENTS) {
			hfa384x_events_no_bap0(dev);
			tasklet_schedule(&local->bap_tasklet);
		}

#ifndef final_version
		if (ev & HFA384X_EV_WTERR) {
			PDEBUG(DEBUG_EXTRA, "%s: WTERR event\n", dev->name);
			HFA384X_OUTW(HFA384X_EV_WTERR, HFA384X_EVACK_OFF);
		}
#endif /* final_version */

		if (ev & HFA384X_EV_INFDROP) {
			prism2_infdrop(dev);
			HFA384X_OUTW(HFA384X_EV_INFDROP, HFA384X_EVACK_OFF);
		}

	next_event:
		events++;
		if (events >= PRISM2_MAX_INTERRUPT_EVENTS) {
			PDEBUG(DEBUG_EXTRA, "prism2_interrupt: >%d events "
			       "(EvStat=0x%04x)\n",
			       PRISM2_MAX_INTERRUPT_EVENTS,
			       HFA384X_INW(HFA384X_EVSTAT_OFF));
			break;
		}
	}
	prism2_io_debug_add(dev, PRISM2_IO_DEBUG_CMD_INTERRUPT, 0, 1);
	return IRQ_RETVAL(events);
}


static void prism2_check_sta_fw_version(local_info_t *local)
{
	struct hfa384x_comp_ident comp;
	int id, variant, major, minor;

	if (hfa384x_get_rid(local->dev, HFA384X_RID_STAID,
			    &comp, sizeof(comp), 1) < 0)
		return;

	local->fw_ap = 0;
	id = le16_to_cpu(comp.id);
	if (id != HFA384X_COMP_ID_STA) {
		if (id == HFA384X_COMP_ID_FW_AP)
			local->fw_ap = 1;
		return;
	}

	major = __le16_to_cpu(comp.major);
	minor = __le16_to_cpu(comp.minor);
	variant = __le16_to_cpu(comp.variant);
	local->sta_fw_ver = PRISM2_FW_VER(major, minor, variant);

	/* Station firmware versions before 1.4.x seem to have a bug in
	 * firmware-based WEP encryption when using Host AP mode, so use
	 * host_encrypt as a default for them. Firmware version 1.4.9 is the
	 * first one that has been seen to produce correct encryption, but the
	 * bug might be fixed before that (although, at least 1.4.2 is broken).
	 */
	local->fw_encrypt_ok = local->sta_fw_ver >= PRISM2_FW_VER(1,4,9);

	if (local->iw_mode == IW_MODE_MASTER && !local->host_encrypt &&
	    !local->fw_encrypt_ok) {
		printk(KERN_DEBUG "%s: defaulting to host-based encryption as "
		       "a workaround for firmware bug in Host AP mode WEP\n",
		       local->dev->name);
		local->host_encrypt = 1;
	}

	/* IEEE 802.11 standard compliant WDS frames (4 addresses) were broken
	 * in station firmware versions before 1.5.x. With these versions, the
	 * driver uses a workaround with bogus frame format (4th address after
	 * the payload). This is not compatible with other AP devices. Since
	 * the firmware bug is fixed in the latest station firmware versions,
	 * automatically enable standard compliant mode for cards using station
	 * firmware version 1.5.0 or newer. */
	if (local->sta_fw_ver >= PRISM2_FW_VER(1,5,0))
		local->wds_type |= HOSTAP_WDS_STANDARD_FRAME;
	else {
		printk(KERN_DEBUG "%s: defaulting to bogus WDS frame as a "
		       "workaround for firmware bug in Host AP mode WDS\n",
		       local->dev->name);
	}

	hostap_check_sta_fw_version(local->ap, local->sta_fw_ver);
}


static void hostap_passive_scan(unsigned long data)
{
	local_info_t *local = (local_info_t *) data;
	struct net_device *dev = local->dev;
	u16 chan;

	if (local->passive_scan_interval <= 0)
		return;

	if (local->passive_scan_state == PASSIVE_SCAN_LISTEN) {
		int max_tries = 16;

		/* Even though host system does not really know when the WLAN
		 * MAC is sending frames, try to avoid changing channels for
		 * passive scanning when a host-generated frame is being
		 * transmitted */
		if (test_bit(HOSTAP_BITS_TRANSMIT, &local->bits)) {
			printk(KERN_DEBUG "%s: passive scan detected pending "
			       "TX - delaying\n", dev->name);
			local->passive_scan_timer.expires = jiffies + HZ / 10;
			add_timer(&local->passive_scan_timer);
			return;
		}

		do {
			local->passive_scan_channel++;
			if (local->passive_scan_channel > 14)
				local->passive_scan_channel = 1;
			max_tries--;
		} while (!(local->channel_mask &
			   (1 << (local->passive_scan_channel - 1))) &&
			 max_tries > 0);

		if (max_tries == 0) {
			printk(KERN_INFO "%s: no allowed passive scan channels"
			       " found\n", dev->name);
			return;
		}

		printk(KERN_DEBUG "%s: passive scan channel %d\n",
		       dev->name, local->passive_scan_channel);
		chan = local->passive_scan_channel;
		local->passive_scan_state = PASSIVE_SCAN_WAIT;
		local->passive_scan_timer.expires = jiffies + HZ / 10;
	} else {
		chan = local->channel;
		local->passive_scan_state = PASSIVE_SCAN_LISTEN;
		local->passive_scan_timer.expires = jiffies +
			local->passive_scan_interval * HZ;
	}

	if (hfa384x_cmd_callback(dev, HFA384X_CMDCODE_TEST |
				 (HFA384X_TEST_CHANGE_CHANNEL << 8),
				 chan, NULL, 0))
		printk(KERN_ERR "%s: passive scan channel set %d "
		       "failed\n", dev->name, chan);

	add_timer(&local->passive_scan_timer);
}


/* Called only as a scheduled task when communications quality values should
 * be updated. */
static void handle_comms_qual_update(struct work_struct *work)
{
	local_info_t *local =
		container_of(work, local_info_t, comms_qual_update);
	prism2_update_comms_qual(local->dev);
}


/* Software watchdog - called as a timer. Hardware interrupt (Tick event) is
 * used to monitor that local->last_tick_timer is being updated. If not,
 * interrupt busy-loop is assumed and driver tries to recover by masking out
 * some events. */
static void hostap_tick_timer(unsigned long data)
{
	static unsigned long last_inquire = 0;
	local_info_t *local = (local_info_t *) data;
	local->last_tick_timer = jiffies;

	/* Inquire CommTallies every 10 seconds to keep the statistics updated
	 * more often during low load and when using 32-bit tallies. */
	if ((!last_inquire || time_after(jiffies, last_inquire + 10 * HZ)) &&
	    !local->hw_downloading && local->hw_ready &&
	    !local->hw_resetting && local->dev_enabled) {
		hfa384x_cmd_callback(local->dev, HFA384X_CMDCODE_INQUIRE,
				     HFA384X_INFO_COMMTALLIES, NULL, 0);
		last_inquire = jiffies;
	}

	if ((local->last_comms_qual_update == 0 ||
	     time_after(jiffies, local->last_comms_qual_update + 10 * HZ)) &&
	    (local->iw_mode == IW_MODE_INFRA ||
	     local->iw_mode == IW_MODE_ADHOC)) {
		schedule_work(&local->comms_qual_update);
	}

	local->tick_timer.expires = jiffies + 2 * HZ;
	add_timer(&local->tick_timer);
}


#ifndef PRISM2_NO_PROCFS_DEBUG
static int prism2_registers_proc_show(struct seq_file *m, void *v)
{
	local_info_t *local = m->private;

#define SHOW_REG(n) \
  seq_printf(m, #n "=%04x\n", hfa384x_read_reg(local->dev, HFA384X_##n##_OFF))

	SHOW_REG(CMD);
	SHOW_REG(PARAM0);
	SHOW_REG(PARAM1);
	SHOW_REG(PARAM2);
	SHOW_REG(STATUS);
	SHOW_REG(RESP0);
	SHOW_REG(RESP1);
	SHOW_REG(RESP2);
	SHOW_REG(INFOFID);
	SHOW_REG(CONTROL);
	SHOW_REG(SELECT0);
	SHOW_REG(SELECT1);
	SHOW_REG(OFFSET0);
	SHOW_REG(OFFSET1);
	SHOW_REG(RXFID);
	SHOW_REG(ALLOCFID);
	SHOW_REG(TXCOMPLFID);
	SHOW_REG(SWSUPPORT0);
	SHOW_REG(SWSUPPORT1);
	SHOW_REG(SWSUPPORT2);
	SHOW_REG(EVSTAT);
	SHOW_REG(INTEN);
	SHOW_REG(EVACK);
	/* Do not read data registers, because they change the state of the
	 * MAC (offset += 2) */
	/* SHOW_REG(DATA0); */
	/* SHOW_REG(DATA1); */
	SHOW_REG(AUXPAGE);
	SHOW_REG(AUXOFFSET);
	/* SHOW_REG(AUXDATA); */
#ifdef PRISM2_PCI
	SHOW_REG(PCICOR);
	SHOW_REG(PCIHCR);
	SHOW_REG(PCI_M0_ADDRH);
	SHOW_REG(PCI_M0_ADDRL);
	SHOW_REG(PCI_M0_LEN);
	SHOW_REG(PCI_M0_CTL);
	SHOW_REG(PCI_STATUS);
	SHOW_REG(PCI_M1_ADDRH);
	SHOW_REG(PCI_M1_ADDRL);
	SHOW_REG(PCI_M1_LEN);
	SHOW_REG(PCI_M1_CTL);
#endif /* PRISM2_PCI */

	return 0;
}

static int prism2_registers_proc_open(struct inode *inode, struct file *file)
{
	return single_open(file, prism2_registers_proc_show, PDE_DATA(inode));
}

static const struct file_operations prism2_registers_proc_fops = {
	.open		= prism2_registers_proc_open,
	.read		= seq_read,
	.llseek		= seq_lseek,
	.release	= single_release,
};

#endif /* PRISM2_NO_PROCFS_DEBUG */


struct set_tim_data {
	struct list_head list;
	int aid;
	int set;
};

static int prism2_set_tim(struct net_device *dev, int aid, int set)
{
	struct list_head *ptr;
	struct set_tim_data *new_entry;
	struct hostap_interface *iface;
	local_info_t *local;

	iface = netdev_priv(dev);
	local = iface->local;

	new_entry = kzalloc(sizeof(*new_entry), GFP_ATOMIC);
	if (new_entry == NULL)
		return -ENOMEM;

	new_entry->aid = aid;
	new_entry->set = set;

	spin_lock_bh(&local->set_tim_lock);
	list_for_each(ptr, &local->set_tim_list) {
		struct set_tim_data *entry =
			list_entry(ptr, struct set_tim_data, list);
		if (entry->aid == aid) {
			PDEBUG(DEBUG_PS2, "%s: prism2_set_tim: aid=%d "
			       "set=%d ==> %d\n",
			       local->dev->name, aid, entry->set, set);
			entry->set = set;
			kfree(new_entry);
			new_entry = NULL;
			break;
		}
	}
	if (new_entry)
		list_add_tail(&new_entry->list, &local->set_tim_list);
	spin_unlock_bh(&local->set_tim_lock);

	schedule_work(&local->set_tim_queue);

	return 0;
}


static void handle_set_tim_queue(struct work_struct *work)
{
	local_info_t *local = container_of(work, local_info_t, set_tim_queue);
	struct set_tim_data *entry;
	u16 val;

	for (;;) {
		entry = NULL;
		spin_lock_bh(&local->set_tim_lock);
		if (!list_empty(&local->set_tim_list)) {
			entry = list_entry(local->set_tim_list.next,
					   struct set_tim_data, list);
			list_del(&entry->list);
		}
		spin_unlock_bh(&local->set_tim_lock);
		if (!entry)
			break;

		PDEBUG(DEBUG_PS2, "%s: handle_set_tim_queue: aid=%d set=%d\n",
		       local->dev->name, entry->aid, entry->set);

		val = entry->aid;
		if (entry->set)
			val |= 0x8000;
		if (hostap_set_word(local->dev, HFA384X_RID_CNFTIMCTRL, val)) {
			printk(KERN_DEBUG "%s: set_tim failed (aid=%d "
			       "set=%d)\n",
			       local->dev->name, entry->aid, entry->set);
		}

		kfree(entry);
	}
}


static void prism2_clear_set_tim_queue(local_info_t *local)
{
	struct list_head *ptr, *n;

	list_for_each_safe(ptr, n, &local->set_tim_list) {
		struct set_tim_data *entry;
		entry = list_entry(ptr, struct set_tim_data, list);
		list_del(&entry->list);
		kfree(entry);
	}
}


/*
 * HostAP uses two layers of net devices, where the inner
 * layer gets called all the time from the outer layer.
 * This is a natural nesting, which needs a split lock type.
 */
static struct lock_class_key hostap_netdev_xmit_lock_key;
static struct lock_class_key hostap_netdev_addr_lock_key;

static void prism2_set_lockdep_class_one(struct net_device *dev,
					 struct netdev_queue *txq,
					 void *_unused)
{
	lockdep_set_class(&txq->_xmit_lock,
			  &hostap_netdev_xmit_lock_key);
}

static void prism2_set_lockdep_class(struct net_device *dev)
{
	lockdep_set_class(&dev->addr_list_lock,
			  &hostap_netdev_addr_lock_key);
	netdev_for_each_tx_queue(dev, prism2_set_lockdep_class_one, NULL);
}

static struct net_device *
prism2_init_local_data(struct prism2_helper_functions *funcs, int card_idx,
		       struct device *sdev)
{
	struct net_device *dev;
	struct hostap_interface *iface;
	struct local_info *local;
	int len, i, ret;

	if (funcs == NULL)
		return NULL;

	len = strlen(dev_template);
	if (len >= IFNAMSIZ || strstr(dev_template, "%d") == NULL) {
		printk(KERN_WARNING "hostap: Invalid dev_template='%s'\n",
		       dev_template);
		return NULL;
	}

	len = sizeof(struct hostap_interface) +
		3 + sizeof(struct local_info) +
		3 + sizeof(struct ap_data);

	dev = alloc_etherdev(len);
	if (dev == NULL)
		return NULL;

	iface = netdev_priv(dev);
	local = (struct local_info *) ((((long) (iface + 1)) + 3) & ~3);
	local->ap = (struct ap_data *) ((((long) (local + 1)) + 3) & ~3);
	local->dev = iface->dev = dev;
	iface->local = local;
	iface->type = HOSTAP_INTERFACE_MASTER;
	INIT_LIST_HEAD(&local->hostap_interfaces);

	local->hw_module = THIS_MODULE;

#ifdef PRISM2_IO_DEBUG
	local->io_debug_enabled = 1;
#endif /* PRISM2_IO_DEBUG */

	local->func = funcs;
	local->func->cmd = hfa384x_cmd;
	local->func->read_regs = hfa384x_read_regs;
	local->func->get_rid = hfa384x_get_rid;
	local->func->set_rid = hfa384x_set_rid;
	local->func->hw_enable = prism2_hw_enable;
	local->func->hw_config = prism2_hw_config;
	local->func->hw_reset = prism2_hw_reset;
	local->func->hw_shutdown = prism2_hw_shutdown;
	local->func->reset_port = prism2_reset_port;
	local->func->schedule_reset = prism2_schedule_reset;
#ifdef PRISM2_DOWNLOAD_SUPPORT
	local->func->read_aux_fops = &prism2_download_aux_dump_proc_fops;
	local->func->download = prism2_download;
#endif /* PRISM2_DOWNLOAD_SUPPORT */
	local->func->tx = prism2_tx_80211;
	local->func->set_tim = prism2_set_tim;
	local->func->need_tx_headroom = 0; /* no need to add txdesc in
					    * skb->data (FIX: maybe for DMA bus
					    * mastering? */

	local->mtu = mtu;

	rwlock_init(&local->iface_lock);
	spin_lock_init(&local->txfidlock);
	spin_lock_init(&local->cmdlock);
	spin_lock_init(&local->baplock);
	spin_lock_init(&local->lock);
	spin_lock_init(&local->irq_init_lock);
	mutex_init(&local->rid_bap_mtx);

	if (card_idx < 0 || card_idx >= MAX_PARM_DEVICES)
		card_idx = 0;
	local->card_idx = card_idx;

	len = strlen(essid);
	memcpy(local->essid, essid,
	       len > MAX_SSID_LEN ? MAX_SSID_LEN : len);
	local->essid[MAX_SSID_LEN] = '\0';
	i = GET_INT_PARM(iw_mode, card_idx);
	if ((i >= IW_MODE_ADHOC && i <= IW_MODE_REPEAT) ||
	    i == IW_MODE_MONITOR) {
		local->iw_mode = i;
	} else {
		printk(KERN_WARNING "prism2: Unknown iw_mode %d; using "
		       "IW_MODE_MASTER\n", i);
		local->iw_mode = IW_MODE_MASTER;
	}
	local->channel = GET_INT_PARM(channel, card_idx);
	local->beacon_int = GET_INT_PARM(beacon_int, card_idx);
	local->dtim_period = GET_INT_PARM(dtim_period, card_idx);
	local->wds_max_connections = 16;
	local->tx_control = HFA384X_TX_CTRL_FLAGS;
	local->manual_retry_count = -1;
	local->rts_threshold = 2347;
	local->fragm_threshold = 2346;
	local->rssi_to_dBm = 100; /* default; to be overriden by
				   * cnfDbmAdjust, if available */
	local->auth_algs = PRISM2_AUTH_OPEN | PRISM2_AUTH_SHARED_KEY;
	local->sram_type = -1;
	local->scan_channel_mask = 0xffff;
	local->monitor_type = PRISM2_MONITOR_RADIOTAP;

	/* Initialize task queue structures */
	INIT_WORK(&local->reset_queue, handle_reset_queue);
	INIT_WORK(&local->set_multicast_list_queue,
		  hostap_set_multicast_list_queue);

	INIT_WORK(&local->set_tim_queue, handle_set_tim_queue);
	INIT_LIST_HEAD(&local->set_tim_list);
	spin_lock_init(&local->set_tim_lock);

	INIT_WORK(&local->comms_qual_update, handle_comms_qual_update);

	/* Initialize tasklets for handling hardware IRQ related operations
	 * outside hw IRQ handler */
#define HOSTAP_TASKLET_INIT(q, f, d) \
do { memset((q), 0, sizeof(*(q))); (q)->func = (f); (q)->data = (d); } \
while (0)
	HOSTAP_TASKLET_INIT(&local->bap_tasklet, hostap_bap_tasklet,
			    (unsigned long) local);

	HOSTAP_TASKLET_INIT(&local->info_tasklet, hostap_info_tasklet,
			    (unsigned long) local);
	hostap_info_init(local);

	HOSTAP_TASKLET_INIT(&local->rx_tasklet,
			    hostap_rx_tasklet, (unsigned long) local);
	skb_queue_head_init(&local->rx_list);

	HOSTAP_TASKLET_INIT(&local->sta_tx_exc_tasklet,
			    hostap_sta_tx_exc_tasklet, (unsigned long) local);
	skb_queue_head_init(&local->sta_tx_exc_list);

	INIT_LIST_HEAD(&local->cmd_queue);
	init_waitqueue_head(&local->hostscan_wq);

	lib80211_crypt_info_init(&local->crypt_info, dev->name, &local->lock);

	init_timer(&local->passive_scan_timer);
	local->passive_scan_timer.data = (unsigned long) local;
	local->passive_scan_timer.function = hostap_passive_scan;

	init_timer(&local->tick_timer);
	local->tick_timer.data = (unsigned long) local;
	local->tick_timer.function = hostap_tick_timer;
	local->tick_timer.expires = jiffies + 2 * HZ;
	add_timer(&local->tick_timer);

	INIT_LIST_HEAD(&local->bss_list);

	hostap_setup_dev(dev, local, HOSTAP_INTERFACE_MASTER);

	dev->type = ARPHRD_IEEE80211;
	dev->header_ops = &hostap_80211_ops;

	rtnl_lock();
	ret = dev_alloc_name(dev, "wifi%d");
	SET_NETDEV_DEV(dev, sdev);
	if (ret >= 0)
		ret = register_netdevice(dev);

	prism2_set_lockdep_class(dev);
	rtnl_unlock();
	if (ret < 0) {
		printk(KERN_WARNING "%s: register netdevice failed!\n",
		       dev_info);
		goto fail;
	}
	printk(KERN_INFO "%s: Registered netdevice %s\n", dev_info, dev->name);

	hostap_init_data(local);
	return dev;

 fail:
	free_netdev(dev);
	return NULL;
}


static int hostap_hw_ready(struct net_device *dev)
{
	struct hostap_interface *iface;
	struct local_info *local;

	iface = netdev_priv(dev);
	local = iface->local;
	local->ddev = hostap_add_interface(local, HOSTAP_INTERFACE_MAIN, 0,
					   "", dev_template);

	if (local->ddev) {
		if (local->iw_mode == IW_MODE_INFRA ||
		    local->iw_mode == IW_MODE_ADHOC) {
			netif_carrier_off(local->dev);
			netif_carrier_off(local->ddev);
		}
		hostap_init_proc(local);
#ifndef PRISM2_NO_PROCFS_DEBUG
		proc_create_data("registers", 0, local->proc,
				 &prism2_registers_proc_fops, local);
#endif /* PRISM2_NO_PROCFS_DEBUG */
		hostap_init_ap_proc(local);
		return 0;
	}

	return -1;
}


static void prism2_free_local_data(struct net_device *dev)
{
	struct hostap_tx_callback_info *tx_cb, *tx_cb_prev;
	int i;
	struct hostap_interface *iface;
	struct local_info *local;
	struct list_head *ptr, *n;

	if (dev == NULL)
		return;

	iface = netdev_priv(dev);
	local = iface->local;

	/* Unregister all netdevs before freeing local data. */
	list_for_each_safe(ptr, n, &local->hostap_interfaces) {
		iface = list_entry(ptr, struct hostap_interface, list);
		if (iface->type == HOSTAP_INTERFACE_MASTER) {
			/* special handling for this interface below */
			continue;
		}
		hostap_remove_interface(iface->dev, 0, 1);
	}

	unregister_netdev(local->dev);

	flush_work(&local->reset_queue);
	flush_work(&local->set_multicast_list_queue);
	flush_work(&local->set_tim_queue);
#ifndef PRISM2_NO_STATION_MODES
	flush_work(&local->info_queue);
#endif
	flush_work(&local->comms_qual_update);

	lib80211_crypt_info_free(&local->crypt_info);

	if (timer_pending(&local->passive_scan_timer))
		del_timer(&local->passive_scan_timer);

	if (timer_pending(&local->tick_timer))
		del_timer(&local->tick_timer);

	prism2_clear_cmd_queue(local);

	skb_queue_purge(&local->info_list);
	skb_queue_purge(&local->rx_list);
	skb_queue_purge(&local->sta_tx_exc_list);

	if (local->dev_enabled)
		prism2_callback(local, PRISM2_CALLBACK_DISABLE);

	if (local->ap != NULL)
		hostap_free_data(local->ap);

#ifndef PRISM2_NO_PROCFS_DEBUG
	if (local->proc != NULL)
		remove_proc_entry("registers", local->proc);
#endif /* PRISM2_NO_PROCFS_DEBUG */
	hostap_remove_proc(local);

	tx_cb = local->tx_callback;
	while (tx_cb != NULL) {
		tx_cb_prev = tx_cb;
		tx_cb = tx_cb->next;
		kfree(tx_cb_prev);
	}

	hostap_set_hostapd(local, 0, 0);
	hostap_set_hostapd_sta(local, 0, 0);

	for (i = 0; i < PRISM2_FRAG_CACHE_LEN; i++) {
		if (local->frag_cache[i].skb != NULL)
			dev_kfree_skb(local->frag_cache[i].skb);
	}

#ifdef PRISM2_DOWNLOAD_SUPPORT
	prism2_download_free_data(local->dl_pri);
	prism2_download_free_data(local->dl_sec);
#endif /* PRISM2_DOWNLOAD_SUPPORT */

	prism2_clear_set_tim_queue(local);

	list_for_each_safe(ptr, n, &local->bss_list) {
		struct hostap_bss_info *bss =
			list_entry(ptr, struct hostap_bss_info, list);
		kfree(bss);
	}

	kfree(local->pda);
	kfree(local->last_scan_results);
	kfree(local->generic_elem);

	free_netdev(local->dev);
}


#if (defined(PRISM2_PCI) && defined(CONFIG_PM)) || defined(PRISM2_PCCARD)
static void prism2_suspend(struct net_device *dev)
{
	struct hostap_interface *iface;
	struct local_info *local;
	union iwreq_data wrqu;

	iface = netdev_priv(dev);
	local = iface->local;

	/* Send disconnect event, e.g., to trigger reassociation after resume
	 * if wpa_supplicant is used. */
	memset(&wrqu, 0, sizeof(wrqu));
	wrqu.ap_addr.sa_family = ARPHRD_ETHER;
	wireless_send_event(local->dev, SIOCGIWAP, &wrqu, NULL);

	/* Disable hardware and firmware */
	prism2_hw_shutdown(dev, 0);
}
#endif /* (PRISM2_PCI && CONFIG_PM) || PRISM2_PCCARD */


/* These might at some point be compiled separately and used as separate
 * kernel modules or linked into one */
#ifdef PRISM2_DOWNLOAD_SUPPORT
#include "hostap_download.c"
#endif /* PRISM2_DOWNLOAD_SUPPORT */

#ifdef PRISM2_CALLBACK
/* External hostap_callback.c file can be used to, e.g., blink activity led.
 * This can use platform specific code and must define prism2_callback()
 * function (if PRISM2_CALLBACK is not defined, these function calls are not
 * used. */
#include "hostap_callback.c"
#endif /* PRISM2_CALLBACK */
