// SPDX-License-Identifier: GPL-2.0-only
/*
 *	Driver for ZyDAS zd1201 based USB wireless devices.
 *
 *	Copyright (c) 2004, 2005 Jeroen Vreeken (pe1rxq@amsat.org)
 *
 *	Parts of this driver have been derived from a wlan-ng version
 *	modified by ZyDAS. They also made documentation available, thanks!
 *	Copyright (C) 1999 AbsoluteValue Systems, Inc.  All Rights Reserved.
 */

#include <linux/module.h>
#include <linux/usb.h>
#include <linux/slab.h>
#include <linux/netdevice.h>
#include <linux/etherdevice.h>
#include <linux/wireless.h>
#include <net/cfg80211.h>
#include <net/iw_handler.h>
#include <linux/string.h>
#include <linux/if_arp.h>
#include <linux/firmware.h>
#include "zd1201.h"

static const struct usb_device_id zd1201_table[] = {
	{USB_DEVICE(0x0586, 0x3400)}, /* Peabird USB Wireless Adapter */
	{USB_DEVICE(0x0ace, 0x1201)}, /* ZyDAS ZD1201 USB Wireless Adapter */
	{USB_DEVICE(0x050d, 0x6051)}, /* Belkin F5D6051 usb  adapter */
	{USB_DEVICE(0x0db0, 0x6823)}, /* MSI UB11B usb  adapter */
	{USB_DEVICE(0x1044, 0x8004)}, /* Gigabyte GN-WLBZ101 */
	{USB_DEVICE(0x1044, 0x8005)}, /* GIGABYTE GN-WLBZ201 usb adapter */
	{}
};

static int ap;	/* Are we an AP or a normal station? */

#define ZD1201_VERSION	"0.15"

MODULE_AUTHOR("Jeroen Vreeken <pe1rxq@amsat.org>");
MODULE_DESCRIPTION("Driver for ZyDAS ZD1201 based USB Wireless adapters");
MODULE_VERSION(ZD1201_VERSION);
MODULE_LICENSE("GPL");
module_param(ap, int, 0);
MODULE_PARM_DESC(ap, "If non-zero Access Point firmware will be loaded");
MODULE_DEVICE_TABLE(usb, zd1201_table);


static int zd1201_fw_upload(struct usb_device *dev, int apfw)
{
	const struct firmware *fw_entry;
	const char *data;
	unsigned long len;
	int err;
	unsigned char ret;
	char *buf;
	char *fwfile;

	if (apfw)
		fwfile = "zd1201-ap.fw";
	else
		fwfile = "zd1201.fw";

	err = request_firmware(&fw_entry, fwfile, &dev->dev);
	if (err) {
		dev_err(&dev->dev, "Failed to load %s firmware file!\n", fwfile);
		dev_err(&dev->dev, "Make sure the hotplug firmware loader is installed.\n");
		dev_err(&dev->dev, "Goto http://linux-lc100020.sourceforge.net for more info.\n");
		return err;
	}

	data = fw_entry->data;
        len = fw_entry->size;

	buf = kmalloc(1024, GFP_ATOMIC);
	if (!buf) {
		err = -ENOMEM;
		goto exit;
	}
	
	while (len > 0) {
		int translen = (len > 1024) ? 1024 : len;
		memcpy(buf, data, translen);

		err = usb_control_msg(dev, usb_sndctrlpipe(dev, 0), 0,
		    USB_DIR_OUT | 0x40, 0, 0, buf, translen,
		    ZD1201_FW_TIMEOUT);
		if (err < 0)
			goto exit;

		len -= translen;
		data += translen;
	}
                                        
	err = usb_control_msg(dev, usb_sndctrlpipe(dev, 0), 0x2,
	    USB_DIR_OUT | 0x40, 0, 0, NULL, 0, ZD1201_FW_TIMEOUT);
	if (err < 0)
		goto exit;

	err = usb_control_msg(dev, usb_rcvctrlpipe(dev, 0), 0x4,
	    USB_DIR_IN | 0x40, 0, 0, buf, sizeof(ret), ZD1201_FW_TIMEOUT);
	if (err < 0)
		goto exit;

	memcpy(&ret, buf, sizeof(ret));

	if (ret & 0x80) {
		err = -EIO;
		goto exit;
	}

	err = 0;
exit:
	kfree(buf);
	release_firmware(fw_entry);
	return err;
}

MODULE_FIRMWARE("zd1201-ap.fw");
MODULE_FIRMWARE("zd1201.fw");

static void zd1201_usbfree(struct urb *urb)
{
	struct zd1201 *zd = urb->context;

	switch(urb->status) {
		case -EILSEQ:
		case -ENODEV:
		case -ETIME:
		case -ENOENT:
		case -EPIPE:
		case -EOVERFLOW:
		case -ESHUTDOWN:
			dev_warn(&zd->usb->dev, "%s: urb failed: %d\n", 
			    zd->dev->name, urb->status);
	}

	kfree(urb->transfer_buffer);
	usb_free_urb(urb);
}

/* cmdreq message: 
	u32 type
	u16 cmd
	u16 parm0
	u16 parm1
	u16 parm2
	u8  pad[4]

	total: 4 + 2 + 2 + 2 + 2 + 4 = 16
*/
static int zd1201_docmd(struct zd1201 *zd, int cmd, int parm0,
			int parm1, int parm2)
{
	unsigned char *command;
	int ret;
	struct urb *urb;

	command = kmalloc(16, GFP_ATOMIC);
	if (!command)
		return -ENOMEM;

	*((__le32*)command) = cpu_to_le32(ZD1201_USB_CMDREQ);
	*((__le16*)&command[4]) = cpu_to_le16(cmd);
	*((__le16*)&command[6]) = cpu_to_le16(parm0);
	*((__le16*)&command[8]) = cpu_to_le16(parm1);
	*((__le16*)&command[10])= cpu_to_le16(parm2);

	urb = usb_alloc_urb(0, GFP_ATOMIC);
	if (!urb) {
		kfree(command);
		return -ENOMEM;
	}
	usb_fill_bulk_urb(urb, zd->usb, usb_sndbulkpipe(zd->usb, zd->endp_out2),
			  command, 16, zd1201_usbfree, zd);
	ret = usb_submit_urb(urb, GFP_ATOMIC);
	if (ret) {
		kfree(command);
		usb_free_urb(urb);
	}

	return ret;
}

/* Callback after sending out a packet */
static void zd1201_usbtx(struct urb *urb)
{
	struct zd1201 *zd = urb->context;
	netif_wake_queue(zd->dev);
}

/* Incoming data */
static void zd1201_usbrx(struct urb *urb)
{
	struct zd1201 *zd = urb->context;
	int free = 0;
	unsigned char *data = urb->transfer_buffer;
	struct sk_buff *skb;
	unsigned char type;

	if (!zd)
		return;

	switch(urb->status) {
		case -EILSEQ:
		case -ENODEV:
		case -ETIME:
		case -ENOENT:
		case -EPIPE:
		case -EOVERFLOW:
		case -ESHUTDOWN:
			dev_warn(&zd->usb->dev, "%s: rx urb failed: %d\n",
			    zd->dev->name, urb->status);
			free = 1;
			goto exit;
	}
	
	if (urb->status != 0 || urb->actual_length == 0)
		goto resubmit;

	type = data[0];
	if (type == ZD1201_PACKET_EVENTSTAT || type == ZD1201_PACKET_RESOURCE) {
		memcpy(zd->rxdata, data, urb->actual_length);
		zd->rxlen = urb->actual_length;
		zd->rxdatas = 1;
		wake_up(&zd->rxdataq);
	}
	/* Info frame */
	if (type == ZD1201_PACKET_INQUIRE) {
		int i = 0;
		unsigned short infotype, copylen;
		infotype = le16_to_cpu(*(__le16*)&data[6]);

		if (infotype == ZD1201_INF_LINKSTATUS) {
			short linkstatus;

			linkstatus = le16_to_cpu(*(__le16*)&data[8]);
			switch(linkstatus) {
				case 1:
					netif_carrier_on(zd->dev);
					break;
				case 2:
					netif_carrier_off(zd->dev);
					break;
				case 3:
					netif_carrier_off(zd->dev);
					break;
				case 4:
					netif_carrier_on(zd->dev);
					break;
				default:
					netif_carrier_off(zd->dev);
			}
			goto resubmit;
		}
		if (infotype == ZD1201_INF_ASSOCSTATUS) {
			short status = le16_to_cpu(*(__le16*)(data+8));
			int event;
			union iwreq_data wrqu;

			switch (status) {
				case ZD1201_ASSOCSTATUS_STAASSOC:
				case ZD1201_ASSOCSTATUS_REASSOC:
					event = IWEVREGISTERED;
					break;
				case ZD1201_ASSOCSTATUS_DISASSOC:
				case ZD1201_ASSOCSTATUS_ASSOCFAIL:
				case ZD1201_ASSOCSTATUS_AUTHFAIL:
				default:
					event = IWEVEXPIRED;
			}
			memcpy(wrqu.addr.sa_data, data+10, ETH_ALEN);
			wrqu.addr.sa_family = ARPHRD_ETHER;

			/* Send event to user space */
			wireless_send_event(zd->dev, event, &wrqu, NULL);

			goto resubmit;
		}
		if (infotype == ZD1201_INF_AUTHREQ) {
			union iwreq_data wrqu;

			memcpy(wrqu.addr.sa_data, data+8, ETH_ALEN);
			wrqu.addr.sa_family = ARPHRD_ETHER;
			/* There isn't a event that trully fits this request.
			   We assume that userspace will be smart enough to
			   see a new station being expired and sends back a
			   authstation ioctl to authorize it. */
			wireless_send_event(zd->dev, IWEVEXPIRED, &wrqu, NULL);
			goto resubmit;
		}
		/* Other infotypes are handled outside this handler */
		zd->rxlen = 0;
		while (i < urb->actual_length) {
			copylen = le16_to_cpu(*(__le16*)&data[i+2]);
			/* Sanity check, sometimes we get junk */
			if (copylen+zd->rxlen > sizeof(zd->rxdata))
				break;
			memcpy(zd->rxdata+zd->rxlen, data+i+4, copylen);
			zd->rxlen += copylen;
			i += 64;
		}
		if (i >= urb->actual_length) {
			zd->rxdatas = 1;
			wake_up(&zd->rxdataq);
		}
		goto  resubmit;
	}
	/* Actual data */
	if (data[urb->actual_length-1] == ZD1201_PACKET_RXDATA) {
		int datalen = urb->actual_length-1;
		unsigned short len, fc, seq;

		len = ntohs(*(__be16 *)&data[datalen-2]);
		if (len>datalen)
			len=datalen;
		fc = le16_to_cpu(*(__le16 *)&data[datalen-16]);
		seq = le16_to_cpu(*(__le16 *)&data[datalen-24]);

		if (zd->monitor) {
			if (datalen < 24)
				goto resubmit;
			if (!(skb = dev_alloc_skb(datalen+24)))
				goto resubmit;
			
			skb_put_data(skb, &data[datalen - 16], 2);
			skb_put_data(skb, &data[datalen - 2], 2);
			skb_put_data(skb, &data[datalen - 14], 6);
			skb_put_data(skb, &data[datalen - 22], 6);
			skb_put_data(skb, &data[datalen - 8], 6);
			skb_put_data(skb, &data[datalen - 24], 2);
			skb_put_data(skb, data, len);
			skb->protocol = eth_type_trans(skb, zd->dev);
			zd->dev->stats.rx_packets++;
			zd->dev->stats.rx_bytes += skb->len;
			netif_rx(skb);
			goto resubmit;
		}
			
		if ((seq & IEEE80211_SCTL_FRAG) ||
		    (fc & IEEE80211_FCTL_MOREFRAGS)) {
			struct zd1201_frag *frag = NULL;
			char *ptr;

			if (datalen<14)
				goto resubmit;
			if ((seq & IEEE80211_SCTL_FRAG) == 0) {
				frag = kmalloc(sizeof(*frag), GFP_ATOMIC);
				if (!frag)
					goto resubmit;
				skb = dev_alloc_skb(IEEE80211_MAX_DATA_LEN +14+2);
				if (!skb) {
					kfree(frag);
					goto resubmit;
				}
				frag->skb = skb;
				frag->seq = seq & IEEE80211_SCTL_SEQ;
				skb_reserve(skb, 2);
				skb_put_data(skb, &data[datalen - 14], 12);
				skb_put_data(skb, &data[6], 2);
				skb_put_data(skb, data + 8, len);
				hlist_add_head(&frag->fnode, &zd->fraglist);
				goto resubmit;
			}
			hlist_for_each_entry(frag, &zd->fraglist, fnode)
				if (frag->seq == (seq&IEEE80211_SCTL_SEQ))
					break;
			if (!frag)
				goto resubmit;
			skb = frag->skb;
			ptr = skb_put(skb, len);
			if (ptr)
				memcpy(ptr, data+8, len);
			if (fc & IEEE80211_FCTL_MOREFRAGS)
				goto resubmit;
			hlist_del_init(&frag->fnode);
			kfree(frag);
		} else {
			if (datalen<14)
				goto resubmit;
			skb = dev_alloc_skb(len + 14 + 2);
			if (!skb)
				goto resubmit;
			skb_reserve(skb, 2);
			skb_put_data(skb, &data[datalen - 14], 12);
			skb_put_data(skb, &data[6], 2);
			skb_put_data(skb, data + 8, len);
		}
		skb->protocol = eth_type_trans(skb, zd->dev);
		zd->dev->stats.rx_packets++;
		zd->dev->stats.rx_bytes += skb->len;
		netif_rx(skb);
	}
resubmit:
	memset(data, 0, ZD1201_RXSIZE);

	urb->status = 0;
	urb->dev = zd->usb;
	if(usb_submit_urb(urb, GFP_ATOMIC))
		free = 1;

exit:
	if (free) {
		zd->rxlen = 0;
		zd->rxdatas = 1;
		wake_up(&zd->rxdataq);
		kfree(urb->transfer_buffer);
	}
}

static int zd1201_getconfig(struct zd1201 *zd, int rid, void *riddata,
	unsigned int riddatalen)
{
	int err;
	int i = 0;
	int code;
	int rid_fid;
	int length;
	unsigned char *pdata;

	zd->rxdatas = 0;
	err = zd1201_docmd(zd, ZD1201_CMDCODE_ACCESS, rid, 0, 0);
	if (err)
		return err;

	wait_event_interruptible(zd->rxdataq, zd->rxdatas);
	if (!zd->rxlen)
		return -EIO;

	code = le16_to_cpu(*(__le16*)(&zd->rxdata[4]));
	rid_fid = le16_to_cpu(*(__le16*)(&zd->rxdata[6]));
	length = le16_to_cpu(*(__le16*)(&zd->rxdata[8]));
	if (length > zd->rxlen)
		length = zd->rxlen-6;

	/* If access bit is not on, then error */
	if ((code & ZD1201_ACCESSBIT) != ZD1201_ACCESSBIT || rid_fid != rid )
		return -EINVAL;

	/* Not enough buffer for allocating data */
	if (riddatalen != (length - 4)) {
		dev_dbg(&zd->usb->dev, "riddatalen mismatches, expected=%u, (packet=%u) length=%u, rid=0x%04X, rid_fid=0x%04X\n",
		    riddatalen, zd->rxlen, length, rid, rid_fid);
		return -ENODATA;
	}

	zd->rxdatas = 0;
	/* Issue SetRxRid commnd */			
	err = zd1201_docmd(zd, ZD1201_CMDCODE_SETRXRID, rid, 0, length);
	if (err)
		return err;

	/* Receive RID record from resource packets */
	wait_event_interruptible(zd->rxdataq, zd->rxdatas);
	if (!zd->rxlen)
		return -EIO;

	if (zd->rxdata[zd->rxlen - 1] != ZD1201_PACKET_RESOURCE) {
		dev_dbg(&zd->usb->dev, "Packet type mismatch: 0x%x not 0x3\n",
		    zd->rxdata[zd->rxlen-1]);
		return -EINVAL;
	}

	/* Set the data pointer and received data length */
	pdata = zd->rxdata;
	length = zd->rxlen;

	do {
		int actual_length;

		actual_length = (length > 64) ? 64 : length;

		if (pdata[0] != 0x3) {
			dev_dbg(&zd->usb->dev, "Rx Resource packet type error: %02X\n",
			    pdata[0]);
			return -EINVAL;
		}

		if (actual_length != 64) {
			/* Trim the last packet type byte */
			actual_length--;
		}

		/* Skip the 4 bytes header (RID length and RID) */
		if (i == 0) {
			pdata += 8;
			actual_length -= 8;
		} else {
			pdata += 4;
			actual_length -= 4;
		}
		
		memcpy(riddata, pdata, actual_length);
		riddata += actual_length;
		pdata += actual_length;
		length -= 64;
		i++;
	} while (length > 0);

	return 0;
}

/*
 *	resreq:
 *		byte	type
 *		byte	sequence
 *		u16	reserved
 *		byte	data[12]
 *	total: 16
 */
static int zd1201_setconfig(struct zd1201 *zd, int rid, const void *buf, int len, int wait)
{
	int err;
	unsigned char *request;
	int reqlen;
	char seq=0;
	struct urb *urb;
	gfp_t gfp_mask = wait ? GFP_NOIO : GFP_ATOMIC;

	len += 4;			/* first 4 are for header */

	zd->rxdatas = 0;
	zd->rxlen = 0;
	for (seq=0; len > 0; seq++) {
		request = kzalloc(16, gfp_mask);
		if (!request)
			return -ENOMEM;
		urb = usb_alloc_urb(0, gfp_mask);
		if (!urb) {
			kfree(request);
			return -ENOMEM;
		}
		reqlen = len>12 ? 12 : len;
		request[0] = ZD1201_USB_RESREQ;
		request[1] = seq;
		request[2] = 0;
		request[3] = 0;
		if (request[1] == 0) {
			/* add header */
			*(__le16*)&request[4] = cpu_to_le16((len-2+1)/2);
			*(__le16*)&request[6] = cpu_to_le16(rid);
			memcpy(request+8, buf, reqlen-4);
			buf += reqlen-4;
		} else {
			memcpy(request+4, buf, reqlen);
			buf += reqlen;
		}

		len -= reqlen;

		usb_fill_bulk_urb(urb, zd->usb, usb_sndbulkpipe(zd->usb,
		    zd->endp_out2), request, 16, zd1201_usbfree, zd);
		err = usb_submit_urb(urb, gfp_mask);
		if (err)
			goto err;
	}

	request = kmalloc(16, gfp_mask);
	if (!request)
		return -ENOMEM;
	urb = usb_alloc_urb(0, gfp_mask);
	if (!urb) {
		kfree(request);
		return -ENOMEM;
	}
	*((__le32*)request) = cpu_to_le32(ZD1201_USB_CMDREQ);
	*((__le16*)&request[4]) = 
	    cpu_to_le16(ZD1201_CMDCODE_ACCESS|ZD1201_ACCESSBIT);
	*((__le16*)&request[6]) = cpu_to_le16(rid);
	*((__le16*)&request[8]) = cpu_to_le16(0);
	*((__le16*)&request[10]) = cpu_to_le16(0);
	usb_fill_bulk_urb(urb, zd->usb, usb_sndbulkpipe(zd->usb, zd->endp_out2),
	     request, 16, zd1201_usbfree, zd);
	err = usb_submit_urb(urb, gfp_mask);
	if (err)
		goto err;
	
	if (wait) {
		wait_event_interruptible(zd->rxdataq, zd->rxdatas);
		if (!zd->rxlen || le16_to_cpu(*(__le16*)&zd->rxdata[6]) != rid) {
			dev_dbg(&zd->usb->dev, "wrong or no RID received\n");
		}
	}

	return 0;
err:
	kfree(request);
	usb_free_urb(urb);
	return err;
}

static inline int zd1201_getconfig16(struct zd1201 *zd, int rid, short *val)
{
	int err;
	__le16 zdval;

	err = zd1201_getconfig(zd, rid, &zdval, sizeof(__le16));
	if (err)
		return err;
	*val = le16_to_cpu(zdval);
	return 0;
}

static inline int zd1201_setconfig16(struct zd1201 *zd, int rid, short val)
{
	__le16 zdval = cpu_to_le16(val);
	return (zd1201_setconfig(zd, rid, &zdval, sizeof(__le16), 1));
}

static int zd1201_drvr_start(struct zd1201 *zd)
{
	int err, i;
	short max;
	__le16 zdmax;
	unsigned char *buffer;

	buffer = kzalloc(ZD1201_RXSIZE, GFP_KERNEL);
	if (!buffer)
		return -ENOMEM;

	usb_fill_bulk_urb(zd->rx_urb, zd->usb, 
	    usb_rcvbulkpipe(zd->usb, zd->endp_in), buffer, ZD1201_RXSIZE,
	    zd1201_usbrx, zd);

	err = usb_submit_urb(zd->rx_urb, GFP_KERNEL);
	if (err)
		goto err_buffer;

	err = zd1201_docmd(zd, ZD1201_CMDCODE_INIT, 0, 0, 0);
	if (err)
		goto err_urb;

	err = zd1201_getconfig(zd, ZD1201_RID_CNFMAXTXBUFFERNUMBER, &zdmax,
	    sizeof(__le16));
	if (err)
		goto err_urb;

	max = le16_to_cpu(zdmax);
	for (i=0; i<max; i++) {
		err = zd1201_docmd(zd, ZD1201_CMDCODE_ALLOC, 1514, 0, 0);
		if (err)
			goto err_urb;
	}

	return 0;

err_urb:
	usb_kill_urb(zd->rx_urb);
	return err;
err_buffer:
	kfree(buffer);
	return err;
}

/*	Magic alert: The firmware doesn't seem to like the MAC state being
 *	toggled in promisc (aka monitor) mode.
 *	(It works a number of times, but will halt eventually)
 *	So we turn it of before disabling and on after enabling if needed.
 */
static int zd1201_enable(struct zd1201 *zd)
{
	int err;

	if (zd->mac_enabled)
		return 0;

	err = zd1201_docmd(zd, ZD1201_CMDCODE_ENABLE, 0, 0, 0);
	if (!err)
		zd->mac_enabled = 1;

	if (zd->monitor)
		err = zd1201_setconfig16(zd, ZD1201_RID_PROMISCUOUSMODE, 1);

	return err;
}

static int zd1201_disable(struct zd1201 *zd)
{
	int err;

	if (!zd->mac_enabled)
		return 0;
	if (zd->monitor) {
		err = zd1201_setconfig16(zd, ZD1201_RID_PROMISCUOUSMODE, 0);
		if (err)
			return err;
	}

	err = zd1201_docmd(zd, ZD1201_CMDCODE_DISABLE, 0, 0, 0);
	if (!err)
		zd->mac_enabled = 0;
	return err;
}

static int zd1201_mac_reset(struct zd1201 *zd)
{
	if (!zd->mac_enabled)
		return 0;
	zd1201_disable(zd);
	return zd1201_enable(zd);
}

static int zd1201_join(struct zd1201 *zd, char *essid, int essidlen)
{
	int err, val;
	char buf[IW_ESSID_MAX_SIZE+2];

	err = zd1201_disable(zd);
	if (err)
		return err;

	val = ZD1201_CNFAUTHENTICATION_OPENSYSTEM;
	val |= ZD1201_CNFAUTHENTICATION_SHAREDKEY;
	err = zd1201_setconfig16(zd, ZD1201_RID_CNFAUTHENTICATION, val);
	if (err)
		return err;

	*(__le16 *)buf = cpu_to_le16(essidlen);
	memcpy(buf+2, essid, essidlen);
	if (!zd->ap) {	/* Normal station */
		err = zd1201_setconfig(zd, ZD1201_RID_CNFDESIREDSSID, buf,
		    IW_ESSID_MAX_SIZE+2, 1);
		if (err)
			return err;
	} else {	/* AP */
		err = zd1201_setconfig(zd, ZD1201_RID_CNFOWNSSID, buf,
		    IW_ESSID_MAX_SIZE+2, 1);
		if (err)
			return err;
	}

	err = zd1201_setconfig(zd, ZD1201_RID_CNFOWNMACADDR, 
	    zd->dev->dev_addr, zd->dev->addr_len, 1);
	if (err)
		return err;

	err = zd1201_enable(zd);
	if (err)
		return err;

	msleep(100);
	return 0;
}

static int zd1201_net_open(struct net_device *dev)
{
	struct zd1201 *zd = netdev_priv(dev);

	/* Start MAC with wildcard if no essid set */
	if (!zd->mac_enabled)
		zd1201_join(zd, zd->essid, zd->essidlen);
	netif_start_queue(dev);

	return 0;
}

static int zd1201_net_stop(struct net_device *dev)
{
	netif_stop_queue(dev);
	return 0;
}

/*
	RFC 1042 encapsulates Ethernet frames in 802.11 frames
	by prefixing them with 0xaa, 0xaa, 0x03) followed by a SNAP OID of 0
	(0x00, 0x00, 0x00). Zd requires an additional padding, copy
	of ethernet addresses, length of the standard RFC 1042 packet
	and a command byte (which is nul for tx).
	
	tx frame (from Wlan NG):
	RFC 1042:
		llc		0xAA 0xAA 0x03 (802.2 LLC)
		snap		0x00 0x00 0x00 (Ethernet encapsulated)
		type		2 bytes, Ethernet type field
		payload		(minus eth header)
	Zydas specific:
		padding		1B if (skb->len+8+1)%64==0
		Eth MAC addr	12 bytes, Ethernet MAC addresses
		length		2 bytes, RFC 1042 packet length 
				(llc+snap+type+payload)
		zd		1 null byte, zd1201 packet type
 */
static netdev_tx_t zd1201_hard_start_xmit(struct sk_buff *skb,
						struct net_device *dev)
{
	struct zd1201 *zd = netdev_priv(dev);
	unsigned char *txbuf = zd->txdata;
	int txbuflen, pad = 0, err;
	struct urb *urb = zd->tx_urb;

	if (!zd->mac_enabled || zd->monitor) {
		dev->stats.tx_dropped++;
		kfree_skb(skb);
		return NETDEV_TX_OK;
	}
	netif_stop_queue(dev);

	txbuflen = skb->len + 8 + 1;
	if (txbuflen%64 == 0) {
		pad = 1;
		txbuflen++;
	}
	txbuf[0] = 0xAA;
	txbuf[1] = 0xAA;
	txbuf[2] = 0x03;
	txbuf[3] = 0x00;	/* rfc1042 */
	txbuf[4] = 0x00;
	txbuf[5] = 0x00;

	skb_copy_from_linear_data_offset(skb, 12, txbuf + 6, skb->len - 12);
	if (pad)
		txbuf[skb->len-12+6]=0;
	skb_copy_from_linear_data(skb, txbuf + skb->len - 12 + 6 + pad, 12);
	*(__be16*)&txbuf[skb->len+6+pad] = htons(skb->len-12+6);
	txbuf[txbuflen-1] = 0;

	usb_fill_bulk_urb(urb, zd->usb, usb_sndbulkpipe(zd->usb, zd->endp_out),
	    txbuf, txbuflen, zd1201_usbtx, zd);

	err = usb_submit_urb(zd->tx_urb, GFP_ATOMIC);
	if (err) {
		dev->stats.tx_errors++;
		netif_start_queue(dev);
	} else {
		dev->stats.tx_packets++;
		dev->stats.tx_bytes += skb->len;
	}
	kfree_skb(skb);

	return NETDEV_TX_OK;
}

static void zd1201_tx_timeout(struct net_device *dev, unsigned int txqueue)
{
	struct zd1201 *zd = netdev_priv(dev);

	if (!zd)
		return;
	dev_warn(&zd->usb->dev, "%s: TX timeout, shooting down urb\n",
	    dev->name);
	usb_unlink_urb(zd->tx_urb);
	dev->stats.tx_errors++;
	/* Restart the timeout to quiet the watchdog: */
	netif_trans_update(dev); /* prevent tx timeout */
}

static int zd1201_set_mac_address(struct net_device *dev, void *p)
{
	struct sockaddr *addr = p;
	struct zd1201 *zd = netdev_priv(dev);
	int err;

	if (!zd)
		return -ENODEV;

	err = zd1201_setconfig(zd, ZD1201_RID_CNFOWNMACADDR, 
	    addr->sa_data, dev->addr_len, 1);
	if (err)
		return err;
	eth_hw_addr_set(dev, addr->sa_data);

	return zd1201_mac_reset(zd);
}

static struct iw_statistics *zd1201_get_wireless_stats(struct net_device *dev)
{
	struct zd1201 *zd = netdev_priv(dev);

	return &zd->iwstats;
}

static void zd1201_set_multicast(struct net_device *dev)
{
	struct zd1201 *zd = netdev_priv(dev);
	struct netdev_hw_addr *ha;
	unsigned char reqbuf[ETH_ALEN*ZD1201_MAXMULTI];
	int i;

	if (netdev_mc_count(dev) > ZD1201_MAXMULTI)
		return;

	i = 0;
	netdev_for_each_mc_addr(ha, dev)
		memcpy(reqbuf + i++ * ETH_ALEN, ha->addr, ETH_ALEN);
	zd1201_setconfig(zd, ZD1201_RID_CNFGROUPADDRESS, reqbuf,
			 netdev_mc_count(dev) * ETH_ALEN, 0);
}

static int zd1201_config_commit(struct net_device *dev, 
	struct iw_request_info *info, union iwreq_data *wrqu, char *essid)
{
	struct zd1201 *zd = netdev_priv(dev);

	return zd1201_mac_reset(zd);
}

static int zd1201_get_name(struct net_device *dev,
	struct iw_request_info *info, union iwreq_data *wrqu, char *extra)
{
	strcpy(wrqu->name, "IEEE 802.11b");
	return 0;
}

static int zd1201_set_freq(struct net_device *dev,
	struct iw_request_info *info, union iwreq_data *wrqu, char *extra)
{
	struct iw_freq *freq = &wrqu->freq;
	struct zd1201 *zd = netdev_priv(dev);
	short channel = 0;
	int err;

	if (freq->e == 0)
		channel = freq->m;
	else
		channel = ieee80211_frequency_to_channel(freq->m);

	err = zd1201_setconfig16(zd, ZD1201_RID_CNFOWNCHANNEL, channel);
	if (err)
		return err;

	zd1201_mac_reset(zd);

	return 0;
}

static int zd1201_get_freq(struct net_device *dev,
	struct iw_request_info *info, union iwreq_data *wrqu, char *extra)
{
	struct iw_freq *freq = &wrqu->freq;
	struct zd1201 *zd = netdev_priv(dev);
	short channel;
	int err;

	err = zd1201_getconfig16(zd, ZD1201_RID_CNFOWNCHANNEL, &channel);
	if (err)
		return err;
	freq->e = 0;
	freq->m = channel;

	return 0;
}

static int zd1201_set_mode(struct net_device *dev,
	struct iw_request_info *info, union iwreq_data *wrqu, char *extra)
{
	__u32 *mode = &wrqu->mode;
	struct zd1201 *zd = netdev_priv(dev);
	short porttype, monitor = 0;
	unsigned char buffer[IW_ESSID_MAX_SIZE+2];
	int err;

	if (zd->ap) {
		if (*mode != IW_MODE_MASTER)
			return -EINVAL;
		return 0;
	}

	err = zd1201_setconfig16(zd, ZD1201_RID_PROMISCUOUSMODE, 0);
	if (err)
		return err;
	zd->dev->type = ARPHRD_ETHER;
	switch(*mode) {
		case IW_MODE_MONITOR:
			monitor = 1;
			zd->dev->type = ARPHRD_IEEE80211;
			/* Make sure we are no longer associated with by
			   setting an 'impossible' essid.
			   (otherwise we mess up firmware)
			 */
			zd1201_join(zd, "\0-*#\0", 5);
			/* Put port in pIBSS */
			fallthrough;
		case 8: /* No pseudo-IBSS in wireless extensions (yet) */
			porttype = ZD1201_PORTTYPE_PSEUDOIBSS;
			break;
		case IW_MODE_ADHOC:
			porttype = ZD1201_PORTTYPE_IBSS;
			break;
		case IW_MODE_INFRA:
			porttype = ZD1201_PORTTYPE_BSS;
			break;
		default:
			return -EINVAL;
	}

	err = zd1201_setconfig16(zd, ZD1201_RID_CNFPORTTYPE, porttype);
	if (err)
		return err;
	if (zd->monitor && !monitor) {
			zd1201_disable(zd);
			*(__le16 *)buffer = cpu_to_le16(zd->essidlen);
			memcpy(buffer+2, zd->essid, zd->essidlen);
			err = zd1201_setconfig(zd, ZD1201_RID_CNFDESIREDSSID,
			    buffer, IW_ESSID_MAX_SIZE+2, 1);
			if (err)
				return err;
	}
	zd->monitor = monitor;
	/* If monitor mode is set we don't actually turn it on here since it
	 * is done during mac reset anyway (see zd1201_mac_enable).
	 */
	zd1201_mac_reset(zd);

	return 0;
}

static int zd1201_get_mode(struct net_device *dev,
	struct iw_request_info *info, union iwreq_data *wrqu, char *extra)
{
	__u32 *mode = &wrqu->mode;
	struct zd1201 *zd = netdev_priv(dev);
	short porttype;
	int err;

	err = zd1201_getconfig16(zd, ZD1201_RID_CNFPORTTYPE, &porttype);
	if (err)
		return err;
	switch(porttype) {
		case ZD1201_PORTTYPE_IBSS:
			*mode = IW_MODE_ADHOC;
			break;
		case ZD1201_PORTTYPE_BSS:
			*mode = IW_MODE_INFRA;
			break;
		case ZD1201_PORTTYPE_WDS:
			*mode = IW_MODE_REPEAT;
			break;
		case ZD1201_PORTTYPE_PSEUDOIBSS:
			*mode = 8;/* No Pseudo-IBSS... */
			break;
		case ZD1201_PORTTYPE_AP:
			*mode = IW_MODE_MASTER;
			break;
		default:
			dev_dbg(&zd->usb->dev, "Unknown porttype: %d\n",
			    porttype);
			*mode = IW_MODE_AUTO;
	}
	if (zd->monitor)
		*mode = IW_MODE_MONITOR;

	return 0;
}

static int zd1201_get_range(struct net_device *dev,
	struct iw_request_info *info, union iwreq_data *wrqu, char *extra)
{
	struct iw_point *wrq = &wrqu->data;
	struct iw_range *range = (struct iw_range *)extra;

	wrq->length = sizeof(struct iw_range);
	memset(range, 0, sizeof(struct iw_range));
	range->we_version_compiled = WIRELESS_EXT;
	range->we_version_source = WIRELESS_EXT;

	range->max_qual.qual = 128;
	range->max_qual.level = 128;
	range->max_qual.noise = 128;
	range->max_qual.updated = 7;

	range->encoding_size[0] = 5;
	range->encoding_size[1] = 13;
	range->num_encoding_sizes = 2;
	range->max_encoding_tokens = ZD1201_NUMKEYS;

	range->num_bitrates = 4;
	range->bitrate[0] = 1000000;
	range->bitrate[1] = 2000000;
	range->bitrate[2] = 5500000;
	range->bitrate[3] = 11000000;

	range->min_rts = 0;
	range->min_frag = ZD1201_FRAGMIN;
	range->max_rts = ZD1201_RTSMAX;
	range->min_frag = ZD1201_FRAGMAX;

	return 0;
}

/*	Little bit of magic here: we only get the quality if we poll
 *	for it, and we never get an actual request to trigger such
 *	a poll. Therefore we 'assume' that the user will soon ask for
 *	the stats after asking the bssid.
 */
static int zd1201_get_wap(struct net_device *dev,
	struct iw_request_info *info, union iwreq_data *wrqu, char *extra)
{
	struct sockaddr *ap_addr = &wrqu->ap_addr;
	struct zd1201 *zd = netdev_priv(dev);
	unsigned char buffer[6];

	if (!zd1201_getconfig(zd, ZD1201_RID_COMMSQUALITY, buffer, 6)) {
		/* Unfortunately the quality and noise reported is useless.
		   they seem to be accumulators that increase until you
		   read them, unless we poll on a fixed interval we can't
		   use them
		 */
		/*zd->iwstats.qual.qual = le16_to_cpu(((__le16 *)buffer)[0]);*/
		zd->iwstats.qual.level = le16_to_cpu(((__le16 *)buffer)[1]);
		/*zd->iwstats.qual.noise = le16_to_cpu(((__le16 *)buffer)[2]);*/
		zd->iwstats.qual.updated = 2;
	}

	return zd1201_getconfig(zd, ZD1201_RID_CURRENTBSSID, ap_addr->sa_data, 6);
}

static int zd1201_set_scan(struct net_device *dev,
	struct iw_request_info *info, union iwreq_data *wrqu, char *extra)
{
	/* We do everything in get_scan */
	return 0;
}

static int zd1201_get_scan(struct net_device *dev,
	struct iw_request_info *info, union iwreq_data *wrqu, char *extra)
{
	struct iw_point *srq = &wrqu->data;
	struct zd1201 *zd = netdev_priv(dev);
	int err, i, j, enabled_save;
	struct iw_event iwe;
	char *cev = extra;
	char *end_buf = extra + IW_SCAN_MAX_DATA;

	/* No scanning in AP mode */
	if (zd->ap)
		return -EOPNOTSUPP;

	/* Scan doesn't seem to work if disabled */
	enabled_save = zd->mac_enabled;
	zd1201_enable(zd);

	zd->rxdatas = 0;
	err = zd1201_docmd(zd, ZD1201_CMDCODE_INQUIRE, 
	     ZD1201_INQ_SCANRESULTS, 0, 0);
	if (err)
		return err;

	wait_event_interruptible(zd->rxdataq, zd->rxdatas);
	if (!zd->rxlen)
		return -EIO;

	if (le16_to_cpu(*(__le16*)&zd->rxdata[2]) != ZD1201_INQ_SCANRESULTS)
		return -EIO;

	for(i=8; i<zd->rxlen; i+=62) {
		iwe.cmd = SIOCGIWAP;
		iwe.u.ap_addr.sa_family = ARPHRD_ETHER;
		memcpy(iwe.u.ap_addr.sa_data, zd->rxdata+i+6, 6);
		cev = iwe_stream_add_event(info, cev, end_buf,
					   &iwe, IW_EV_ADDR_LEN);

		iwe.cmd = SIOCGIWESSID;
		iwe.u.data.length = zd->rxdata[i+16];
		iwe.u.data.flags = 1;
		cev = iwe_stream_add_point(info, cev, end_buf,
					   &iwe, zd->rxdata+i+18);

		iwe.cmd = SIOCGIWMODE;
		if (zd->rxdata[i+14]&0x01)
			iwe.u.mode = IW_MODE_MASTER;
		else
			iwe.u.mode = IW_MODE_ADHOC;
		cev = iwe_stream_add_event(info, cev, end_buf,
					   &iwe, IW_EV_UINT_LEN);
		
		iwe.cmd = SIOCGIWFREQ;
		iwe.u.freq.m = zd->rxdata[i+0];
		iwe.u.freq.e = 0;
		cev = iwe_stream_add_event(info, cev, end_buf,
					   &iwe, IW_EV_FREQ_LEN);
		
		iwe.cmd = SIOCGIWRATE;
		iwe.u.bitrate.fixed = 0;
		iwe.u.bitrate.disabled = 0;
		for (j=0; j<10; j++) if (zd->rxdata[i+50+j]) {
			iwe.u.bitrate.value = (zd->rxdata[i+50+j]&0x7f)*500000;
			cev = iwe_stream_add_event(info, cev, end_buf,
						   &iwe, IW_EV_PARAM_LEN);
		}
		
		iwe.cmd = SIOCGIWENCODE;
		iwe.u.data.length = 0;
		if (zd->rxdata[i+14]&0x10)
			iwe.u.data.flags = IW_ENCODE_ENABLED;
		else
			iwe.u.data.flags = IW_ENCODE_DISABLED;
		cev = iwe_stream_add_point(info, cev, end_buf, &iwe, NULL);
		
		iwe.cmd = IWEVQUAL;
		iwe.u.qual.qual = zd->rxdata[i+4];
		iwe.u.qual.noise= zd->rxdata[i+2]/10-100;
		iwe.u.qual.level = (256+zd->rxdata[i+4]*100)/255-100;
		iwe.u.qual.updated = 7;
		cev = iwe_stream_add_event(info, cev, end_buf,
					   &iwe, IW_EV_QUAL_LEN);
	}

	if (!enabled_save)
		zd1201_disable(zd);

	srq->length = cev - extra;
	srq->flags = 0;

	return 0;
}

static int zd1201_set_essid(struct net_device *dev,
	struct iw_request_info *info, union iwreq_data *wrqu, char *essid)
{
	struct iw_point *data = &wrqu->data;
	struct zd1201 *zd = netdev_priv(dev);

	if (data->length > IW_ESSID_MAX_SIZE)
		return -EINVAL;
	if (data->length < 1)
		data->length = 1;
	zd->essidlen = data->length;
	memset(zd->essid, 0, IW_ESSID_MAX_SIZE+1);
	memcpy(zd->essid, essid, data->length);
	return zd1201_join(zd, zd->essid, zd->essidlen);
}

static int zd1201_get_essid(struct net_device *dev,
	struct iw_request_info *info, union iwreq_data *wrqu, char *essid)
{
	struct iw_point *data = &wrqu->data;
	struct zd1201 *zd = netdev_priv(dev);

	memcpy(essid, zd->essid, zd->essidlen);
	data->flags = 1;
	data->length = zd->essidlen;

	return 0;
}

static int zd1201_get_nick(struct net_device *dev, struct iw_request_info *info,
	union iwreq_data *wrqu, char *nick)
{
	struct iw_point *data = &wrqu->data;
	strcpy(nick, "zd1201");
	data->flags = 1;
	data->length = strlen(nick);
	return 0;
}

static int zd1201_set_rate(struct net_device *dev,
	struct iw_request_info *info, union iwreq_data *wrqu, char *extra)
{
	struct iw_param *rrq = &wrqu->bitrate;
	struct zd1201 *zd = netdev_priv(dev);
	short rate;
	int err;

	switch (rrq->value) {
		case 1000000:
			rate = ZD1201_RATEB1;
			break;
		case 2000000:
			rate = ZD1201_RATEB2;
			break;
		case 5500000:
			rate = ZD1201_RATEB5;
			break;
		case 11000000:
		default:
			rate = ZD1201_RATEB11;
			break;
	}
	if (!rrq->fixed) { /* Also enable all lower bitrates */
		rate |= rate-1;
	}

	err = zd1201_setconfig16(zd, ZD1201_RID_TXRATECNTL, rate);
	if (err)
		return err;

	return zd1201_mac_reset(zd);
}

static int zd1201_get_rate(struct net_device *dev,
	struct iw_request_info *info, union iwreq_data *wrqu, char *extra)
{
	struct iw_param *rrq = &wrqu->bitrate;
	struct zd1201 *zd = netdev_priv(dev);
	short rate;
	int err;

	err = zd1201_getconfig16(zd, ZD1201_RID_CURRENTTXRATE, &rate);
	if (err)
		return err;

	switch(rate) {
		case 1:
			rrq->value = 1000000;
			break;
		case 2:
			rrq->value = 2000000;
			break;
		case 5:
			rrq->value = 5500000;
			break;
		case 11:
			rrq->value = 11000000;
			break;
		default:
			rrq->value = 0;
	}
	rrq->fixed = 0;
	rrq->disabled = 0;

	return 0;
}

static int zd1201_set_rts(struct net_device *dev, struct iw_request_info *info,
	union iwreq_data *wrqu, char *extra)
{
	struct iw_param *rts = &wrqu->rts;
	struct zd1201 *zd = netdev_priv(dev);
	int err;
	short val = rts->value;

	if (rts->disabled || !rts->fixed)
		val = ZD1201_RTSMAX;
	if (val > ZD1201_RTSMAX)
		return -EINVAL;
	if (val < 0)
		return -EINVAL;

	err = zd1201_setconfig16(zd, ZD1201_RID_CNFRTSTHRESHOLD, val);
	if (err)
		return err;
	return zd1201_mac_reset(zd);
}

static int zd1201_get_rts(struct net_device *dev, struct iw_request_info *info,
	union iwreq_data *wrqu, char *extra)
{
	struct iw_param *rts = &wrqu->rts;
	struct zd1201 *zd = netdev_priv(dev);
	short rtst;
	int err;

	err = zd1201_getconfig16(zd, ZD1201_RID_CNFRTSTHRESHOLD, &rtst);
	if (err)
		return err;
	rts->value = rtst;
	rts->disabled = (rts->value == ZD1201_RTSMAX);
	rts->fixed = 1;

	return 0;
}

static int zd1201_set_frag(struct net_device *dev, struct iw_request_info *info,
	union iwreq_data *wrqu, char *extra)
{
	struct iw_param *frag = &wrqu->frag;
	struct zd1201 *zd = netdev_priv(dev);
	int err;
	short val = frag->value;

	if (frag->disabled || !frag->fixed)
		val = ZD1201_FRAGMAX;
	if (val > ZD1201_FRAGMAX)
		return -EINVAL;
	if (val < ZD1201_FRAGMIN)
		return -EINVAL;
	if (val & 1)
		return -EINVAL;
	err = zd1201_setconfig16(zd, ZD1201_RID_CNFFRAGTHRESHOLD, val);
	if (err)
		return err;
	return zd1201_mac_reset(zd);
}

static int zd1201_get_frag(struct net_device *dev, struct iw_request_info *info,
	union iwreq_data *wrqu, char *extra)
{
	struct iw_param *frag = &wrqu->frag;
	struct zd1201 *zd = netdev_priv(dev);
	short fragt;
	int err;

	err = zd1201_getconfig16(zd, ZD1201_RID_CNFFRAGTHRESHOLD, &fragt);
	if (err)
		return err;
	frag->value = fragt;
	frag->disabled = (frag->value == ZD1201_FRAGMAX);
	frag->fixed = 1;

	return 0;
}

static int zd1201_set_retry(struct net_device *dev,
	struct iw_request_info *info, union iwreq_data *wrqu, char *extra)
{
	return 0;
}

static int zd1201_get_retry(struct net_device *dev,
	struct iw_request_info *info, union iwreq_data *wrqu, char *extra)
{
	return 0;
}

static int zd1201_set_encode(struct net_device *dev,
	struct iw_request_info *info, union iwreq_data *wrqu, char *key)
{
	struct iw_point *erq = &wrqu->encoding;
	struct zd1201 *zd = netdev_priv(dev);
	short i;
	int err, rid;

	if (erq->length > ZD1201_MAXKEYLEN)
		return -EINVAL;

	i = (erq->flags & IW_ENCODE_INDEX)-1;
	if (i == -1) {
		err = zd1201_getconfig16(zd,ZD1201_RID_CNFDEFAULTKEYID,&i);
		if (err)
			return err;
	} else {
		err = zd1201_setconfig16(zd, ZD1201_RID_CNFDEFAULTKEYID, i);
		if (err)
			return err;
	}

	if (i < 0 || i >= ZD1201_NUMKEYS)
		return -EINVAL;

	rid = ZD1201_RID_CNFDEFAULTKEY0 + i;
	err = zd1201_setconfig(zd, rid, key, erq->length, 1);
	if (err)
		return err;
	zd->encode_keylen[i] = erq->length;
	memcpy(zd->encode_keys[i], key, erq->length);

	i=0;
	if (!(erq->flags & IW_ENCODE_DISABLED & IW_ENCODE_MODE)) {
		i |= 0x01;
		zd->encode_enabled = 1;
	} else
		zd->encode_enabled = 0;
	if (erq->flags & IW_ENCODE_RESTRICTED & IW_ENCODE_MODE) {
		i |= 0x02;
		zd->encode_restricted = 1;
	} else
		zd->encode_restricted = 0;
	err = zd1201_setconfig16(zd, ZD1201_RID_CNFWEBFLAGS, i);
	if (err)
		return err;

	if (zd->encode_enabled)
		i = ZD1201_CNFAUTHENTICATION_SHAREDKEY;
	else
		i = ZD1201_CNFAUTHENTICATION_OPENSYSTEM;
	err = zd1201_setconfig16(zd, ZD1201_RID_CNFAUTHENTICATION, i);
	if (err)
		return err;

	return zd1201_mac_reset(zd);
}

static int zd1201_get_encode(struct net_device *dev,
	struct iw_request_info *info, union iwreq_data *wrqu, char *key)
{
	struct iw_point *erq = &wrqu->encoding;
	struct zd1201 *zd = netdev_priv(dev);
	short i;
	int err;

	if (zd->encode_enabled)
		erq->flags = IW_ENCODE_ENABLED;
	else
		erq->flags = IW_ENCODE_DISABLED;
	if (zd->encode_restricted)
		erq->flags |= IW_ENCODE_RESTRICTED;
	else
		erq->flags |= IW_ENCODE_OPEN;

	i = (erq->flags & IW_ENCODE_INDEX) -1;
	if (i == -1) {
		err = zd1201_getconfig16(zd, ZD1201_RID_CNFDEFAULTKEYID, &i);
		if (err)
			return err;
	}
	if (i<0 || i>= ZD1201_NUMKEYS)
		return -EINVAL;

	erq->flags |= i+1;

	erq->length = zd->encode_keylen[i];
	memcpy(key, zd->encode_keys[i], erq->length);

	return 0;
}

static int zd1201_set_power(struct net_device *dev, 
	struct iw_request_info *info, union iwreq_data *wrqu, char *extra)
{
	struct iw_param *vwrq = &wrqu->power;
	struct zd1201 *zd = netdev_priv(dev);
	short enabled, duration, level;
	int err;

	enabled = vwrq->disabled ? 0 : 1;
	if (enabled) {
		if (vwrq->flags & IW_POWER_PERIOD) {
			duration = vwrq->value;
			err = zd1201_setconfig16(zd, 
			    ZD1201_RID_CNFMAXSLEEPDURATION, duration);
			if (err)
				return err;
			goto out;
		}
		if (vwrq->flags & IW_POWER_TIMEOUT) {
			err = zd1201_getconfig16(zd, 
			    ZD1201_RID_CNFMAXSLEEPDURATION, &duration);
			if (err)
				return err;
			level = vwrq->value * 4 / duration;
			if (level > 4)
				level = 4;
			if (level < 0)
				level = 0;
			err = zd1201_setconfig16(zd, ZD1201_RID_CNFPMEPS,
			    level);
			if (err)
				return err;
			goto out;
		}
		return -EINVAL;
	}
out:
	return zd1201_setconfig16(zd, ZD1201_RID_CNFPMENABLED, enabled);
}

static int zd1201_get_power(struct net_device *dev,
	struct iw_request_info *info, union iwreq_data *wrqu, char *extra)
{
	struct iw_param *vwrq = &wrqu->power;
	struct zd1201 *zd = netdev_priv(dev);
	short enabled, level, duration;
	int err;

	err = zd1201_getconfig16(zd, ZD1201_RID_CNFPMENABLED, &enabled);
	if (err)
		return err;
	err = zd1201_getconfig16(zd, ZD1201_RID_CNFPMEPS, &level);
	if (err)
		return err;
	err = zd1201_getconfig16(zd, ZD1201_RID_CNFMAXSLEEPDURATION, &duration);
	if (err)
		return err;
	vwrq->disabled = enabled ? 0 : 1;
	if (vwrq->flags & IW_POWER_TYPE) {
		if (vwrq->flags & IW_POWER_PERIOD) {
			vwrq->value = duration;
			vwrq->flags = IW_POWER_PERIOD;
		} else {
			vwrq->value = duration * level / 4;
			vwrq->flags = IW_POWER_TIMEOUT;
		}
	}
	if (vwrq->flags & IW_POWER_MODE) {
		if (enabled && level)
			vwrq->flags = IW_POWER_UNICAST_R;
		else
			vwrq->flags = IW_POWER_ALL_R;
	}

	return 0;
}


static const iw_handler zd1201_iw_handler[] =
{
	IW_HANDLER(SIOCSIWCOMMIT,	zd1201_config_commit),
	IW_HANDLER(SIOCGIWNAME,		zd1201_get_name),
	IW_HANDLER(SIOCSIWFREQ,		zd1201_set_freq),
	IW_HANDLER(SIOCGIWFREQ,		zd1201_get_freq),
	IW_HANDLER(SIOCSIWMODE,		zd1201_set_mode),
	IW_HANDLER(SIOCGIWMODE,		zd1201_get_mode),
	IW_HANDLER(SIOCGIWRANGE,	zd1201_get_range),
	IW_HANDLER(SIOCGIWAP,		zd1201_get_wap),
	IW_HANDLER(SIOCSIWSCAN,		zd1201_set_scan),
	IW_HANDLER(SIOCGIWSCAN,		zd1201_get_scan),
	IW_HANDLER(SIOCSIWESSID,	zd1201_set_essid),
	IW_HANDLER(SIOCGIWESSID,	zd1201_get_essid),
	IW_HANDLER(SIOCGIWNICKN,	zd1201_get_nick),
	IW_HANDLER(SIOCSIWRATE,		zd1201_set_rate),
	IW_HANDLER(SIOCGIWRATE,		zd1201_get_rate),
	IW_HANDLER(SIOCSIWRTS,		zd1201_set_rts),
	IW_HANDLER(SIOCGIWRTS,		zd1201_get_rts),
	IW_HANDLER(SIOCSIWFRAG,		zd1201_set_frag),
	IW_HANDLER(SIOCGIWFRAG,		zd1201_get_frag),
	IW_HANDLER(SIOCSIWRETRY,	zd1201_set_retry),
	IW_HANDLER(SIOCGIWRETRY,	zd1201_get_retry),
	IW_HANDLER(SIOCSIWENCODE,	zd1201_set_encode),
	IW_HANDLER(SIOCGIWENCODE,	zd1201_get_encode),
	IW_HANDLER(SIOCSIWPOWER,	zd1201_set_power),
	IW_HANDLER(SIOCGIWPOWER,	zd1201_get_power),
};

static int zd1201_set_hostauth(struct net_device *dev,
	struct iw_request_info *info, union iwreq_data *wrqu, char *extra)
{
	struct iw_param *rrq = &wrqu->param;
	struct zd1201 *zd = netdev_priv(dev);

	if (!zd->ap)
		return -EOPNOTSUPP;

	return zd1201_setconfig16(zd, ZD1201_RID_CNFHOSTAUTH, rrq->value);
}

static int zd1201_get_hostauth(struct net_device *dev,
	struct iw_request_info *info, union iwreq_data *wrqu, char *extra)
{
	struct iw_param *rrq = &wrqu->param;
	struct zd1201 *zd = netdev_priv(dev);
	short hostauth;
	int err;

	if (!zd->ap)
		return -EOPNOTSUPP;

	err = zd1201_getconfig16(zd, ZD1201_RID_CNFHOSTAUTH, &hostauth);
	if (err)
		return err;
	rrq->value = hostauth;
	rrq->fixed = 1;

	return 0;
}

static int zd1201_auth_sta(struct net_device *dev,
	struct iw_request_info *info, union iwreq_data *wrqu, char *extra)
{
	struct sockaddr *sta = &wrqu->ap_addr;
	struct zd1201 *zd = netdev_priv(dev);
	unsigned char buffer[10];

	if (!zd->ap)
		return -EOPNOTSUPP;

	memcpy(buffer, sta->sa_data, ETH_ALEN);
	*(short*)(buffer+6) = 0;	/* 0==success, 1==failure */
	*(short*)(buffer+8) = 0;

	return zd1201_setconfig(zd, ZD1201_RID_AUTHENTICATESTA, buffer, 10, 1);
}

static int zd1201_set_maxassoc(struct net_device *dev,
	struct iw_request_info *info, union iwreq_data *wrqu, char *extra)
{
	struct iw_param *rrq = &wrqu->param;
	struct zd1201 *zd = netdev_priv(dev);

	if (!zd->ap)
		return -EOPNOTSUPP;

	return zd1201_setconfig16(zd, ZD1201_RID_CNFMAXASSOCSTATIONS, rrq->value);
}

static int zd1201_get_maxassoc(struct net_device *dev,
	struct iw_request_info *info, union iwreq_data *wrqu, char *extra)
{
	struct iw_param *rrq = &wrqu->param;
	struct zd1201 *zd = netdev_priv(dev);
	short maxassoc;
	int err;

	if (!zd->ap)
		return -EOPNOTSUPP;

	err = zd1201_getconfig16(zd, ZD1201_RID_CNFMAXASSOCSTATIONS, &maxassoc);
	if (err)
		return err;
	rrq->value = maxassoc;
	rrq->fixed = 1;

	return 0;
}

static const iw_handler zd1201_private_handler[] = {
	zd1201_set_hostauth,	/* ZD1201SIWHOSTAUTH */
	zd1201_get_hostauth,	/* ZD1201GIWHOSTAUTH */
	zd1201_auth_sta,	/* ZD1201SIWAUTHSTA */
	NULL,			/* nothing to get */
	zd1201_set_maxassoc,	/* ZD1201SIMAXASSOC */
	zd1201_get_maxassoc,	/* ZD1201GIMAXASSOC */
};

static const struct iw_priv_args zd1201_private_args[] = {
	{ ZD1201SIWHOSTAUTH, IW_PRIV_TYPE_INT | IW_PRIV_SIZE_FIXED | 1,
	    IW_PRIV_TYPE_NONE, "sethostauth" },
	{ ZD1201GIWHOSTAUTH, IW_PRIV_TYPE_NONE,
	    IW_PRIV_TYPE_INT | IW_PRIV_SIZE_FIXED | 1, "gethostauth" },
	{ ZD1201SIWAUTHSTA, IW_PRIV_TYPE_ADDR | IW_PRIV_SIZE_FIXED | 1,
	    IW_PRIV_TYPE_NONE, "authstation" },
	{ ZD1201SIWMAXASSOC, IW_PRIV_TYPE_INT | IW_PRIV_SIZE_FIXED | 1,
	    IW_PRIV_TYPE_NONE, "setmaxassoc" },
	{ ZD1201GIWMAXASSOC, IW_PRIV_TYPE_NONE,
	    IW_PRIV_TYPE_INT | IW_PRIV_SIZE_FIXED | 1, "getmaxassoc" },
};

static const struct iw_handler_def zd1201_iw_handlers = {
	.num_standard 		= ARRAY_SIZE(zd1201_iw_handler),
	.num_private 		= ARRAY_SIZE(zd1201_private_handler),
	.num_private_args 	= ARRAY_SIZE(zd1201_private_args),
	.standard		= zd1201_iw_handler,
	.private		= zd1201_private_handler,
	.private_args 		= (struct iw_priv_args *) zd1201_private_args,
	.get_wireless_stats	= zd1201_get_wireless_stats,
};

static const struct net_device_ops zd1201_netdev_ops = {
	.ndo_open		= zd1201_net_open,
	.ndo_stop		= zd1201_net_stop,
	.ndo_start_xmit		= zd1201_hard_start_xmit,
	.ndo_tx_timeout		= zd1201_tx_timeout,
	.ndo_set_rx_mode	= zd1201_set_multicast,
	.ndo_set_mac_address	= zd1201_set_mac_address,
	.ndo_validate_addr	= eth_validate_addr,
};

static int zd1201_probe(struct usb_interface *interface,
			const struct usb_device_id *id)
{
	struct zd1201 *zd;
	struct net_device *dev;
	struct usb_device *usb;
	int err;
	short porttype;
	char buf[IW_ESSID_MAX_SIZE+2];
	u8 addr[ETH_ALEN];

	usb = interface_to_usbdev(interface);

	dev = alloc_etherdev(sizeof(*zd));
	if (!dev)
		return -ENOMEM;
	zd = netdev_priv(dev);
	zd->dev = dev;

	zd->ap = ap;
	zd->usb = usb;
	zd->removed = 0;
	init_waitqueue_head(&zd->rxdataq);
	INIT_HLIST_HEAD(&zd->fraglist);
	
	err = zd1201_fw_upload(usb, zd->ap);
	if (err) {
		dev_err(&usb->dev, "zd1201 firmware upload failed: %d\n", err);
		goto err_zd;
	}
	
	zd->endp_in = 1;
	zd->endp_out = 1;
	zd->endp_out2 = 2;
	zd->rx_urb = usb_alloc_urb(0, GFP_KERNEL);
	zd->tx_urb = usb_alloc_urb(0, GFP_KERNEL);
	if (!zd->rx_urb || !zd->tx_urb) {
		err = -ENOMEM;
		goto err_zd;
	}

	mdelay(100);
	err = zd1201_drvr_start(zd);
	if (err)
		goto err_zd;

	err = zd1201_setconfig16(zd, ZD1201_RID_CNFMAXDATALEN, 2312);
	if (err)
		goto err_start;

	err = zd1201_setconfig16(zd, ZD1201_RID_TXRATECNTL,
	    ZD1201_RATEB1 | ZD1201_RATEB2 | ZD1201_RATEB5 | ZD1201_RATEB11);
	if (err)
		goto err_start;

	dev->netdev_ops = &zd1201_netdev_ops;
	dev->wireless_handlers = &zd1201_iw_handlers;
	dev->watchdog_timeo = ZD1201_TX_TIMEOUT;
	strcpy(dev->name, "wlan%d");

	err = zd1201_getconfig(zd, ZD1201_RID_CNFOWNMACADDR, addr, ETH_ALEN);
	if (err)
		goto err_start;
	eth_hw_addr_set(dev, addr);

	/* Set wildcard essid to match zd->essid */
	*(__le16 *)buf = cpu_to_le16(0);
	err = zd1201_setconfig(zd, ZD1201_RID_CNFDESIREDSSID, buf,
	    IW_ESSID_MAX_SIZE+2, 1);
	if (err)
		goto err_start;

	if (zd->ap)
		porttype = ZD1201_PORTTYPE_AP;
	else
		porttype = ZD1201_PORTTYPE_BSS;
	err = zd1201_setconfig16(zd, ZD1201_RID_CNFPORTTYPE, porttype);
	if (err)
		goto err_start;

	SET_NETDEV_DEV(dev, &usb->dev);

	err = register_netdev(dev);
	if (err)
		goto err_start;
	dev_info(&usb->dev, "%s: ZD1201 USB Wireless interface\n",
	    dev->name);

	usb_set_intfdata(interface, zd);
	zd1201_enable(zd);	/* zd1201 likes to startup enabled, */
	zd1201_disable(zd);	/* interfering with all the wifis in range */
	return 0;

err_start:
	/* Leave the device in reset state */
	zd1201_docmd(zd, ZD1201_CMDCODE_INIT, 0, 0, 0);
err_zd:
	usb_free_urb(zd->tx_urb);
	usb_free_urb(zd->rx_urb);
	free_netdev(dev);
	return err;
}

static void zd1201_disconnect(struct usb_interface *interface)
{
	struct zd1201 *zd = usb_get_intfdata(interface);
	struct hlist_node *node2;
	struct zd1201_frag *frag;

	if (!zd)
		return;
	usb_set_intfdata(interface, NULL);

	hlist_for_each_entry_safe(frag, node2, &zd->fraglist, fnode) {
		hlist_del_init(&frag->fnode);
		kfree_skb(frag->skb);
		kfree(frag);
	}

	if (zd->tx_urb) {
		usb_kill_urb(zd->tx_urb);
		usb_free_urb(zd->tx_urb);
	}
	if (zd->rx_urb) {
		usb_kill_urb(zd->rx_urb);
		usb_free_urb(zd->rx_urb);
	}

	if (zd->dev) {
		unregister_netdev(zd->dev);
		free_netdev(zd->dev);
	}
}

#ifdef CONFIG_PM

static int zd1201_suspend(struct usb_interface *interface,
			   pm_message_t message)
{
	struct zd1201 *zd = usb_get_intfdata(interface);

	netif_device_detach(zd->dev);

	zd->was_enabled = zd->mac_enabled;

	if (zd->was_enabled)
		return zd1201_disable(zd);
	else
		return 0;
}

static int zd1201_resume(struct usb_interface *interface)
{
	struct zd1201 *zd = usb_get_intfdata(interface);

	if (!zd || !zd->dev)
		return -ENODEV;

	netif_device_attach(zd->dev);

	if (zd->was_enabled)
		return zd1201_enable(zd);
	else
		return 0;
}

#else

#define zd1201_suspend NULL
#define zd1201_resume  NULL

#endif

static struct usb_driver zd1201_usb = {
	.name = "zd1201",
	.probe = zd1201_probe,
	.disconnect = zd1201_disconnect,
	.id_table = zd1201_table,
	.suspend = zd1201_suspend,
	.resume = zd1201_resume,
	.disable_hub_initiated_lpm = 1,
};

module_usb_driver(zd1201_usb);
