/*
 * WUSB Host Wire Adapter: Radio Control Interface (WUSB[8.6])
 * Radio Control command/event transport
 *
 * Copyright (C) 2005-2006 Intel Corporation
 * Inaky Perez-Gonzalez <inaky.perez-gonzalez@intel.com>
 *
 * 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.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.	 See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program; if not, write to the Free Software
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
 * 02110-1301, USA.
 *
 *
 * Initialize the Radio Control interface Driver.
 *
 * For each device probed, creates an 'struct hwarc' which contains
 * just the representation of the UWB Radio Controller, and the logic
 * for reading notifications and passing them to the UWB Core.
 *
 * So we initialize all of those, register the UWB Radio Controller
 * and setup the notification/event handle to pipe the notifications
 * to the UWB management Daemon.
 *
 * Command and event filtering.
 *
 * This is the driver for the Radio Control Interface described in WUSB
 * 1.0. The core UWB module assumes that all drivers are compliant to the
 * WHCI 0.95 specification. We thus create a filter that parses all
 * incoming messages from the (WUSB 1.0) device and manipulate them to
 * conform to the WHCI 0.95 specification. Similarly, outgoing messages
 * are parsed and manipulated to conform to the WUSB 1.0 compliant messages
 * that the device expects. Only a few messages are affected:
 * Affected events:
 *    UWB_RC_EVT_BEACON
 *    UWB_RC_EVT_BP_SLOT_CHANGE
 *    UWB_RC_EVT_DRP_AVAIL
 *    UWB_RC_EVT_DRP
 * Affected commands:
 *    UWB_RC_CMD_SCAN
 *    UWB_RC_CMD_SET_DRP_IE
 *
 *
 *
 */
#include <linux/init.h>
#include <linux/module.h>
#include <linux/slab.h>
#include <linux/usb.h>
#include <linux/usb/wusb.h>
#include <linux/usb/wusb-wa.h>
#include <linux/uwb.h>

#include "uwb-internal.h"

/* The device uses commands and events from the WHCI specification, although
 * reporting itself as WUSB compliant. */
#define WUSB_QUIRK_WHCI_CMD_EVT		0x01

/**
 * Descriptor for an instance of the UWB Radio Control Driver that
 * attaches to the RCI interface of the Host Wired Adapter.
 *
 * Unless there is a lock specific to the 'data members', all access
 * is protected by uwb_rc->mutex.
 *
 * The NEEP (Notification/Event EndPoint) URB (@neep_urb) writes to
 * @rd_buffer. Note there is no locking because it is perfectly (heh!)
 * serialized--probe() submits an URB, callback is called, processes
 * the data (synchronously), submits another URB, and so on. There is
 * no concurrent access to the buffer.
 */
struct hwarc {
	struct usb_device *usb_dev;
	struct usb_interface *usb_iface;
	struct uwb_rc *uwb_rc;		/* UWB host controller */
	struct urb *neep_urb;		/* Notification endpoint handling */
	struct edc neep_edc;
	void *rd_buffer;		/* NEEP read buffer */
};


/* Beacon received notification (WUSB 1.0 [8.6.3.2]) */
struct uwb_rc_evt_beacon_WUSB_0100 {
	struct uwb_rceb rceb;
	u8	bChannelNumber;
	__le16	wBPSTOffset;
	u8	bLQI;
	u8	bRSSI;
	__le16	wBeaconInfoLength;
	u8	BeaconInfo[];
} __attribute__((packed));

/**
 * Filter WUSB 1.0 BEACON RCV notification to be WHCI 0.95
 *
 * @header: the incoming event
 * @buf_size: size of buffer containing incoming event
 * @new_size: size of event after filtering completed
 *
 * The WHCI 0.95 spec has a "Beacon Type" field. This value is unknown at
 * the time we receive the beacon from WUSB so we just set it to
 * UWB_RC_BEACON_TYPE_NEIGHBOR as a default.
 * The solution below allocates memory upon receipt of every beacon from a
 * WUSB device. This will deteriorate performance. What is the right way to
 * do this?
 */
static
int hwarc_filter_evt_beacon_WUSB_0100(struct uwb_rc *rc,
				      struct uwb_rceb **header,
				      const size_t buf_size,
				      size_t *new_size)
{
	struct uwb_rc_evt_beacon_WUSB_0100 *be;
	struct uwb_rc_evt_beacon *newbe;
	size_t bytes_left, ielength;
	struct device *dev = &rc->uwb_dev.dev;

	be = container_of(*header, struct uwb_rc_evt_beacon_WUSB_0100, rceb);
	bytes_left = buf_size;
	if (bytes_left < sizeof(*be)) {
		dev_err(dev, "Beacon Received Notification: Not enough data "
			"to decode for filtering (%zu vs %zu bytes needed)\n",
			bytes_left, sizeof(*be));
		return -EINVAL;
	}
	bytes_left -= sizeof(*be);
	ielength = le16_to_cpu(be->wBeaconInfoLength);
	if (bytes_left < ielength) {
		dev_err(dev, "Beacon Received Notification: Not enough data "
			"to decode IEs (%zu vs %zu bytes needed)\n",
			bytes_left, ielength);
		return -EINVAL;
	}
	newbe = kzalloc(sizeof(*newbe) + ielength, GFP_ATOMIC);
	if (newbe == NULL)
		return -ENOMEM;
	newbe->rceb = be->rceb;
	newbe->bChannelNumber = be->bChannelNumber;
	newbe->bBeaconType = UWB_RC_BEACON_TYPE_NEIGHBOR;
	newbe->wBPSTOffset = be->wBPSTOffset;
	newbe->bLQI = be->bLQI;
	newbe->bRSSI = be->bRSSI;
	newbe->wBeaconInfoLength = be->wBeaconInfoLength;
	memcpy(newbe->BeaconInfo, be->BeaconInfo, ielength);
	*header = &newbe->rceb;
	*new_size = sizeof(*newbe) + ielength;
	return 1;  /* calling function will free memory */
}


/* DRP Availability change notification (WUSB 1.0 [8.6.3.8]) */
struct uwb_rc_evt_drp_avail_WUSB_0100 {
	struct uwb_rceb rceb;
	__le16 wIELength;
	u8 IEData[];
} __attribute__((packed));

/**
 * Filter WUSB 1.0 DRP AVAILABILITY CHANGE notification to be WHCI 0.95
 *
 * @header: the incoming event
 * @buf_size: size of buffer containing incoming event
 * @new_size: size of event after filtering completed
 */
static
int hwarc_filter_evt_drp_avail_WUSB_0100(struct uwb_rc *rc,
					 struct uwb_rceb **header,
					 const size_t buf_size,
					 size_t *new_size)
{
	struct uwb_rc_evt_drp_avail_WUSB_0100 *da;
	struct uwb_rc_evt_drp_avail *newda;
	struct uwb_ie_hdr *ie_hdr;
	size_t bytes_left, ielength;
	struct device *dev = &rc->uwb_dev.dev;


	da = container_of(*header, struct uwb_rc_evt_drp_avail_WUSB_0100, rceb);
	bytes_left = buf_size;
	if (bytes_left < sizeof(*da)) {
		dev_err(dev, "Not enough data to decode DRP Avail "
			"Notification for filtering. Expected %zu, "
			"received %zu.\n", (size_t)sizeof(*da), bytes_left);
		return -EINVAL;
	}
	bytes_left -= sizeof(*da);
	ielength = le16_to_cpu(da->wIELength);
	if (bytes_left < ielength) {
		dev_err(dev, "DRP Avail Notification filter: IE length "
			"[%zu bytes] does not match actual length "
			"[%zu bytes].\n", ielength, bytes_left);
		return -EINVAL;
	}
	if (ielength < sizeof(*ie_hdr)) {
		dev_err(dev, "DRP Avail Notification filter: Not enough "
			"data to decode IE [%zu bytes, %zu needed]\n",
			ielength, sizeof(*ie_hdr));
		return -EINVAL;
	}
	ie_hdr = (void *) da->IEData;
	if (ie_hdr->length > 32) {
		dev_err(dev, "DRP Availability Change event has unexpected "
			"length for filtering. Expected < 32 bytes, "
			"got %zu bytes.\n", (size_t)ie_hdr->length);
		return -EINVAL;
	}
	newda = kzalloc(sizeof(*newda), GFP_ATOMIC);
	if (newda == NULL)
		return -ENOMEM;
	newda->rceb = da->rceb;
	memcpy(newda->bmp, (u8 *) ie_hdr + sizeof(*ie_hdr), ie_hdr->length);
	*header = &newda->rceb;
	*new_size = sizeof(*newda);
	return 1; /* calling function will free memory */
}


/* DRP notification (WUSB 1.0 [8.6.3.9]) */
struct uwb_rc_evt_drp_WUSB_0100 {
	struct uwb_rceb rceb;
	struct uwb_dev_addr wSrcAddr;
	u8 bExplicit;
	__le16 wIELength;
	u8 IEData[];
} __attribute__((packed));

/**
 * Filter WUSB 1.0 DRP Notification to be WHCI 0.95
 *
 * @header: the incoming event
 * @buf_size: size of buffer containing incoming event
 * @new_size: size of event after filtering completed
 *
 * It is hard to manage DRP reservations without having a Reason code.
 * Unfortunately there is none in the WUSB spec. We just set the default to
 * DRP IE RECEIVED.
 * We do not currently use the bBeaconSlotNumber value, so we set this to
 * zero for now.
 */
static
int hwarc_filter_evt_drp_WUSB_0100(struct uwb_rc *rc,
				   struct uwb_rceb **header,
				   const size_t buf_size,
				   size_t *new_size)
{
	struct uwb_rc_evt_drp_WUSB_0100 *drpev;
	struct uwb_rc_evt_drp *newdrpev;
	size_t bytes_left, ielength;
	struct device *dev = &rc->uwb_dev.dev;

	drpev = container_of(*header, struct uwb_rc_evt_drp_WUSB_0100, rceb);
	bytes_left = buf_size;
	if (bytes_left < sizeof(*drpev)) {
		dev_err(dev, "Not enough data to decode DRP Notification "
			"for filtering. Expected %zu, received %zu.\n",
			(size_t)sizeof(*drpev), bytes_left);
		return -EINVAL;
	}
	ielength = le16_to_cpu(drpev->wIELength);
	bytes_left -= sizeof(*drpev);
	if (bytes_left < ielength) {
		dev_err(dev, "DRP Notification filter: header length [%zu "
			"bytes] does not match actual length [%zu "
			"bytes].\n", ielength, bytes_left);
		return -EINVAL;
	}
	newdrpev = kzalloc(sizeof(*newdrpev) + ielength, GFP_ATOMIC);
	if (newdrpev == NULL)
		return -ENOMEM;
	newdrpev->rceb = drpev->rceb;
	newdrpev->src_addr = drpev->wSrcAddr;
	newdrpev->reason = UWB_DRP_NOTIF_DRP_IE_RCVD;
	newdrpev->beacon_slot_number = 0;
	newdrpev->ie_length = drpev->wIELength;
	memcpy(newdrpev->ie_data, drpev->IEData, ielength);
	*header = &newdrpev->rceb;
	*new_size = sizeof(*newdrpev) + ielength;
	return 1; /* calling function will free memory */
}


/* Scan Command (WUSB 1.0 [8.6.2.5]) */
struct uwb_rc_cmd_scan_WUSB_0100 {
	struct uwb_rccb rccb;
	u8 bChannelNumber;
	u8 bScanState;
} __attribute__((packed));

/**
 * Filter WHCI 0.95 SCAN command to be WUSB 1.0 SCAN command
 *
 * @header:   command sent to device (compliant to WHCI 0.95)
 * @size:     size of command sent to device
 *
 * We only reduce the size by two bytes because the WUSB 1.0 scan command
 * does not have the last field (wStarttime). Also, make sure we don't send
 * the device an unexpected scan type.
 */
static
int hwarc_filter_cmd_scan_WUSB_0100(struct uwb_rc *rc,
				    struct uwb_rccb **header,
				    size_t *size)
{
	struct uwb_rc_cmd_scan *sc;

	sc = container_of(*header, struct uwb_rc_cmd_scan, rccb);

	if (sc->bScanState == UWB_SCAN_ONLY_STARTTIME)
		sc->bScanState = UWB_SCAN_ONLY;
	/* Don't send the last two bytes. */
	*size -= 2;
	return 0;
}


/* SET DRP IE command (WUSB 1.0 [8.6.2.7]) */
struct uwb_rc_cmd_set_drp_ie_WUSB_0100 {
	struct uwb_rccb rccb;
	u8 bExplicit;
	__le16 wIELength;
	struct uwb_ie_drp IEData[];
} __attribute__((packed));

/**
 * Filter WHCI 0.95 SET DRP IE command to be WUSB 1.0 SET DRP IE command
 *
 * @header:   command sent to device (compliant to WHCI 0.95)
 * @size:     size of command sent to device
 *
 * WUSB has an extra bExplicit field - we assume always explicit
 * negotiation so this field is set. The command expected by the device is
 * thus larger than the one prepared by the driver so we need to
 * reallocate memory to accommodate this.
 * We trust the driver to send us the correct data so no checking is done
 * on incoming data - evn though it is variable length.
 */
static
int hwarc_filter_cmd_set_drp_ie_WUSB_0100(struct uwb_rc *rc,
					  struct uwb_rccb **header,
					  size_t *size)
{
	struct uwb_rc_cmd_set_drp_ie *orgcmd;
	struct uwb_rc_cmd_set_drp_ie_WUSB_0100 *cmd;
	size_t ielength;

	orgcmd = container_of(*header, struct uwb_rc_cmd_set_drp_ie, rccb);
	ielength = le16_to_cpu(orgcmd->wIELength);
	cmd = kzalloc(sizeof(*cmd) + ielength, GFP_KERNEL);
	if (cmd == NULL)
		return -ENOMEM;
	cmd->rccb = orgcmd->rccb;
	cmd->bExplicit = 0;
	cmd->wIELength = orgcmd->wIELength;
	memcpy(cmd->IEData, orgcmd->IEData, ielength);
	*header = &cmd->rccb;
	*size = sizeof(*cmd) + ielength;
	return 1; /* calling function will free memory */
}


/**
 * Filter data from WHCI driver to WUSB device
 *
 * @header: WHCI 0.95 compliant command from driver
 * @size:   length of command
 *
 * The routine managing commands to the device (uwb_rc_cmd()) will call the
 * filtering function pointer (if it exists) before it passes any data to
 * the device. At this time the command has been formatted according to
 * WHCI 0.95 and is ready to be sent to the device.
 *
 * The filter function will be provided with the current command and its
 * length. The function will manipulate the command if necessary and
 * potentially reallocate memory for a command that needed more memory that
 * the given command. If new memory was created the function will return 1
 * to indicate to the calling function that the memory need to be freed
 * when not needed any more. The size will contain the new length of the
 * command.
 * If memory has not been allocated we rely on the original mechanisms to
 * free the memory of the command - even when we reduce the value of size.
 */
static
int hwarc_filter_cmd_WUSB_0100(struct uwb_rc *rc, struct uwb_rccb **header,
			       size_t *size)
{
	int result;
	struct uwb_rccb *rccb = *header;
	int cmd = le16_to_cpu(rccb->wCommand);
	switch (cmd) {
	case UWB_RC_CMD_SCAN:
		result = hwarc_filter_cmd_scan_WUSB_0100(rc, header, size);
		break;
	case UWB_RC_CMD_SET_DRP_IE:
		result = hwarc_filter_cmd_set_drp_ie_WUSB_0100(rc, header, size);
		break;
	default:
		result = -ENOANO;
		break;
	}
	return result;
}


/**
 * Filter data from WHCI driver to WUSB device
 *
 * @header: WHCI 0.95 compliant command from driver
 * @size:   length of command
 *
 * Filter commands based on which protocol the device supports. The WUSB
 * errata should be the same as WHCI 0.95 so we do not filter that here -
 * only WUSB 1.0.
 */
static
int hwarc_filter_cmd(struct uwb_rc *rc, struct uwb_rccb **header,
		     size_t *size)
{
	int result = -ENOANO;
	if (rc->version == 0x0100)
		result = hwarc_filter_cmd_WUSB_0100(rc, header, size);
	return result;
}


/**
 * Compute return value as sum of incoming value and value at given offset
 *
 * @rceb:      event for which we compute the size, it contains a variable
 *	       length field.
 * @core_size: size of the "non variable" part of the event
 * @offset:    place in event where the length of the variable part is stored
 * @buf_size: total length of buffer in which event arrived - we need to make
 *	       sure we read the offset in memory that is still part of the event
 */
static
ssize_t hwarc_get_event_size(struct uwb_rc *rc, const struct uwb_rceb *rceb,
			     size_t core_size, size_t offset,
			     const size_t buf_size)
{
	ssize_t size = -ENOSPC;
	const void *ptr = rceb;
	size_t type_size = sizeof(__le16);
	struct device *dev = &rc->uwb_dev.dev;

	if (offset + type_size >= buf_size) {
		dev_err(dev, "Not enough data to read extra size of event "
			"0x%02x/%04x/%02x, only got %zu bytes.\n",
			rceb->bEventType, le16_to_cpu(rceb->wEvent),
			rceb->bEventContext, buf_size);
		goto out;
	}
	ptr += offset;
	size = core_size + le16_to_cpu(*(__le16 *)ptr);
out:
	return size;
}


/* Beacon slot change notification (WUSB 1.0 [8.6.3.5]) */
struct uwb_rc_evt_bp_slot_change_WUSB_0100 {
	struct uwb_rceb rceb;
	u8 bSlotNumber;
} __attribute__((packed));


/**
 * Filter data from WUSB device to WHCI driver
 *
 * @header:	 incoming event
 * @buf_size:	 size of buffer in which event arrived
 * @_event_size: actual size of event in the buffer
 * @new_size:	 size of event after filtered
 *
 * We don't know how the buffer is constructed - there may be more than one
 * event in it so buffer length does not determine event length. We first
 * determine the expected size of the incoming event. This value is passed
 * back only if the actual filtering succeeded (so we know the computed
 * expected size is correct). This value will be zero if
 * the event did not need any filtering.
 *
 * WHCI interprets the BP Slot Change event's data differently than
 * WUSB. The event sizes are exactly the same. The data field
 * indicates the new beacon slot in which a RC is transmitting its
 * beacon. The maximum value of this is 96 (wMacBPLength ECMA-368
 * 17.16 (Table 117)). We thus know that the WUSB value will not set
 * the bit bNoSlot, so we don't really do anything (placeholder).
 */
static
int hwarc_filter_event_WUSB_0100(struct uwb_rc *rc, struct uwb_rceb **header,
				 const size_t buf_size, size_t *_real_size,
				 size_t *_new_size)
{
	int result = -ENOANO;
	struct uwb_rceb *rceb = *header;
	int event = le16_to_cpu(rceb->wEvent);
	ssize_t event_size;
	size_t core_size, offset;

	if (rceb->bEventType != UWB_RC_CET_GENERAL)
		goto out;
	switch (event) {
	case UWB_RC_EVT_BEACON:
		core_size = sizeof(struct uwb_rc_evt_beacon_WUSB_0100);
		offset = offsetof(struct uwb_rc_evt_beacon_WUSB_0100,
				  wBeaconInfoLength);
		event_size = hwarc_get_event_size(rc, rceb, core_size,
						  offset, buf_size);
		if (event_size < 0)
			goto out;
		*_real_size = event_size;
		result = hwarc_filter_evt_beacon_WUSB_0100(rc, header,
							   buf_size, _new_size);
		break;
	case UWB_RC_EVT_BP_SLOT_CHANGE:
		*_new_size = *_real_size =
			sizeof(struct uwb_rc_evt_bp_slot_change_WUSB_0100);
		result = 0;
		break;

	case UWB_RC_EVT_DRP_AVAIL:
		core_size = sizeof(struct uwb_rc_evt_drp_avail_WUSB_0100);
		offset = offsetof(struct uwb_rc_evt_drp_avail_WUSB_0100,
				  wIELength);
		event_size = hwarc_get_event_size(rc, rceb, core_size,
						  offset, buf_size);
		if (event_size < 0)
			goto out;
		*_real_size = event_size;
		result = hwarc_filter_evt_drp_avail_WUSB_0100(
			rc, header, buf_size, _new_size);
		break;

	case UWB_RC_EVT_DRP:
		core_size = sizeof(struct uwb_rc_evt_drp_WUSB_0100);
		offset = offsetof(struct uwb_rc_evt_drp_WUSB_0100, wIELength);
		event_size = hwarc_get_event_size(rc, rceb, core_size,
						  offset, buf_size);
		if (event_size < 0)
			goto out;
		*_real_size = event_size;
		result = hwarc_filter_evt_drp_WUSB_0100(rc, header,
							buf_size, _new_size);
		break;

	default:
		break;
	}
out:
	return result;
}

/**
 * Filter data from WUSB device to WHCI driver
 *
 * @header:	 incoming event
 * @buf_size:	 size of buffer in which event arrived
 * @_event_size: actual size of event in the buffer
 * @_new_size:	 size of event after filtered
 *
 * Filter events based on which protocol the device supports. The WUSB
 * errata should be the same as WHCI 0.95 so we do not filter that here -
 * only WUSB 1.0.
 *
 * If we don't handle it, we return -ENOANO (why the weird error code?
 * well, so if I get it, I can pinpoint in the code that raised
 * it...after all, not too many places use the higher error codes).
 */
static
int hwarc_filter_event(struct uwb_rc *rc, struct uwb_rceb **header,
		       const size_t buf_size, size_t *_real_size,
		       size_t *_new_size)
{
	int result = -ENOANO;
	if (rc->version == 0x0100)
		result =  hwarc_filter_event_WUSB_0100(
			rc, header, buf_size, _real_size, _new_size);
	return result;
}


/**
 * Execute an UWB RC command on HWA
 *
 * @rc:	      Instance of a Radio Controller that is a HWA
 * @cmd:      Buffer containing the RCCB and payload to execute
 * @cmd_size: Size of the command buffer.
 *
 * NOTE: rc's mutex has to be locked
 */
static
int hwarc_cmd(struct uwb_rc *uwb_rc, const struct uwb_rccb *cmd, size_t cmd_size)
{
	struct hwarc *hwarc = uwb_rc->priv;
	return usb_control_msg(
		hwarc->usb_dev, usb_sndctrlpipe(hwarc->usb_dev, 0),
		WA_EXEC_RC_CMD, USB_DIR_OUT | USB_TYPE_CLASS | USB_RECIP_INTERFACE,
		0, hwarc->usb_iface->cur_altsetting->desc.bInterfaceNumber,
		(void *) cmd, cmd_size, 100 /* FIXME: this is totally arbitrary */);
}

static
int hwarc_reset(struct uwb_rc *uwb_rc)
{
	struct hwarc *hwarc = uwb_rc->priv;
	return usb_reset_device(hwarc->usb_dev);
}

/**
 * Callback for the notification and event endpoint
 *
 * Check's that everything is fine and then passes the read data to
 * the notification/event handling mechanism (neh).
 */
static
void hwarc_neep_cb(struct urb *urb)
{
	struct hwarc *hwarc = urb->context;
	struct usb_interface *usb_iface = hwarc->usb_iface;
	struct device *dev = &usb_iface->dev;
	int result;

	switch (result = urb->status) {
	case 0:
		uwb_rc_neh_grok(hwarc->uwb_rc, urb->transfer_buffer,
				urb->actual_length);
		break;
	case -ECONNRESET:	/* Not an error, but a controlled situation; */
	case -ENOENT:		/* (we killed the URB)...so, no broadcast */
		goto out;
	case -ESHUTDOWN:	/* going away! */
		goto out;
	default:		/* On general errors, retry unless it gets ugly */
		if (edc_inc(&hwarc->neep_edc, EDC_MAX_ERRORS,
			    EDC_ERROR_TIMEFRAME))
			goto error_exceeded;
		dev_err(dev, "NEEP: URB error %d\n", urb->status);
	}
	result = usb_submit_urb(urb, GFP_ATOMIC);
	if (result < 0 && result != -ENODEV && result != -EPERM) {
		/* ignoring unrecoverable errors */
		dev_err(dev, "NEEP: Can't resubmit URB (%d) resetting device\n",
			result);
		goto error;
	}
out:
	return;

error_exceeded:
	dev_err(dev, "NEEP: URB max acceptable errors "
		"exceeded, resetting device\n");
error:
	uwb_rc_neh_error(hwarc->uwb_rc, result);
	uwb_rc_reset_all(hwarc->uwb_rc);
	return;
}

static void hwarc_init(struct hwarc *hwarc)
{
	edc_init(&hwarc->neep_edc);
}

/**
 * Initialize the notification/event endpoint stuff
 *
 * Note this is effectively a parallel thread; it knows that
 * hwarc->uwb_rc always exists because the existence of a 'hwarc'
 * means that there is a reverence on the hwarc->uwb_rc (see
 * _probe()), and thus _neep_cb() can execute safely.
 */
static int hwarc_neep_init(struct uwb_rc *rc)
{
	struct hwarc *hwarc = rc->priv;
	struct usb_interface *iface = hwarc->usb_iface;
	struct usb_device *usb_dev = interface_to_usbdev(iface);
	struct device *dev = &iface->dev;
	int result;
	struct usb_endpoint_descriptor *epd;

	epd = &iface->cur_altsetting->endpoint[0].desc;
	hwarc->rd_buffer = (void *) __get_free_page(GFP_KERNEL);
	if (hwarc->rd_buffer == NULL) {
		dev_err(dev, "Unable to allocate notification's read buffer\n");
		goto error_rd_buffer;
	}
	hwarc->neep_urb = usb_alloc_urb(0, GFP_KERNEL);
	if (hwarc->neep_urb == NULL) {
		dev_err(dev, "Unable to allocate notification URB\n");
		goto error_urb_alloc;
	}
	usb_fill_int_urb(hwarc->neep_urb, usb_dev,
			 usb_rcvintpipe(usb_dev, epd->bEndpointAddress),
			 hwarc->rd_buffer, PAGE_SIZE,
			 hwarc_neep_cb, hwarc, epd->bInterval);
	result = usb_submit_urb(hwarc->neep_urb, GFP_ATOMIC);
	if (result < 0) {
		dev_err(dev, "Cannot submit notification URB: %d\n", result);
		goto error_neep_submit;
	}
	return 0;

error_neep_submit:
	usb_free_urb(hwarc->neep_urb);
error_urb_alloc:
	free_page((unsigned long)hwarc->rd_buffer);
error_rd_buffer:
	return -ENOMEM;
}


/** Clean up all the notification endpoint resources */
static void hwarc_neep_release(struct uwb_rc *rc)
{
	struct hwarc *hwarc = rc->priv;

	usb_kill_urb(hwarc->neep_urb);
	usb_free_urb(hwarc->neep_urb);
	free_page((unsigned long)hwarc->rd_buffer);
}

/**
 * Get the version from class-specific descriptor
 *
 * NOTE: this descriptor comes with the big bundled configuration
 *	 descriptor that includes the interfaces' and endpoints', so
 *	 we just look for it in the cached copy kept by the USB stack.
 *
 * NOTE2: We convert LE fields to CPU order.
 */
static int hwarc_get_version(struct uwb_rc *rc)
{
	int result;

	struct hwarc *hwarc = rc->priv;
	struct uwb_rc_control_intf_class_desc *descr;
	struct device *dev = &rc->uwb_dev.dev;
	struct usb_device *usb_dev = hwarc->usb_dev;
	char *itr;
	struct usb_descriptor_header *hdr;
	size_t itr_size, actconfig_idx;
	u16 version;

	actconfig_idx = (usb_dev->actconfig - usb_dev->config) /
		sizeof(usb_dev->config[0]);
	itr = usb_dev->rawdescriptors[actconfig_idx];
	itr_size = le16_to_cpu(usb_dev->actconfig->desc.wTotalLength);
	while (itr_size >= sizeof(*hdr)) {
		hdr = (struct usb_descriptor_header *) itr;
		dev_dbg(dev, "Extra device descriptor: "
			"type %02x/%u bytes @ %zu (%zu left)\n",
			hdr->bDescriptorType, hdr->bLength,
			(itr - usb_dev->rawdescriptors[actconfig_idx]),
			itr_size);
		if (hdr->bDescriptorType == USB_DT_CS_RADIO_CONTROL)
			goto found;
		itr += hdr->bLength;
		itr_size -= hdr->bLength;
	}
	dev_err(dev, "cannot find Radio Control Interface Class descriptor\n");
	return -ENODEV;

found:
	result = -EINVAL;
	if (hdr->bLength > itr_size) {	/* is it available? */
		dev_err(dev, "incomplete Radio Control Interface Class "
			"descriptor (%zu bytes left, %u needed)\n",
			itr_size, hdr->bLength);
		goto error;
	}
	if (hdr->bLength < sizeof(*descr)) {
		dev_err(dev, "short Radio Control Interface Class "
			"descriptor\n");
		goto error;
	}
	descr = (struct uwb_rc_control_intf_class_desc *) hdr;
	/* Make LE fields CPU order */
	version = __le16_to_cpu(descr->bcdRCIVersion);
	if (version != 0x0100) {
		dev_err(dev, "Device reports protocol version 0x%04x. We "
			"do not support that. \n", version);
		result = -EINVAL;
		goto error;
	}
	rc->version = version;
	dev_dbg(dev, "Device supports WUSB protocol version 0x%04x \n",	rc->version);
	result = 0;
error:
	return result;
}

/*
 * By creating a 'uwb_rc', we have a reference on it -- that reference
 * is the one we drop when we disconnect.
 *
 * No need to switch altsettings; according to WUSB1.0[8.6.1.1], there
 * is only one altsetting allowed.
 */
static int hwarc_probe(struct usb_interface *iface,
		       const struct usb_device_id *id)
{
	int result;
	struct uwb_rc *uwb_rc;
	struct hwarc *hwarc;
	struct device *dev = &iface->dev;

	result = -ENOMEM;
	uwb_rc = uwb_rc_alloc();
	if (uwb_rc == NULL) {
		dev_err(dev, "unable to allocate RC instance\n");
		goto error_rc_alloc;
	}
	hwarc = kzalloc(sizeof(*hwarc), GFP_KERNEL);
	if (hwarc == NULL) {
		dev_err(dev, "unable to allocate HWA RC instance\n");
		goto error_alloc;
	}
	hwarc_init(hwarc);
	hwarc->usb_dev = usb_get_dev(interface_to_usbdev(iface));
	hwarc->usb_iface = usb_get_intf(iface);
	hwarc->uwb_rc = uwb_rc;

	uwb_rc->owner = THIS_MODULE;
	uwb_rc->start = hwarc_neep_init;
	uwb_rc->stop  = hwarc_neep_release;
	uwb_rc->cmd   = hwarc_cmd;
	uwb_rc->reset = hwarc_reset;
	if (id->driver_info & WUSB_QUIRK_WHCI_CMD_EVT) {
		uwb_rc->filter_cmd   = NULL;
		uwb_rc->filter_event = NULL;
	} else {
		uwb_rc->filter_cmd   = hwarc_filter_cmd;
		uwb_rc->filter_event = hwarc_filter_event;
	}

	result = uwb_rc_add(uwb_rc, dev, hwarc);
	if (result < 0)
		goto error_rc_add;
	result = hwarc_get_version(uwb_rc);
	if (result < 0) {
		dev_err(dev, "cannot retrieve version of RC \n");
		goto error_get_version;
	}
	usb_set_intfdata(iface, hwarc);
	return 0;

error_get_version:
	uwb_rc_rm(uwb_rc);
error_rc_add:
	usb_put_intf(iface);
	usb_put_dev(hwarc->usb_dev);
error_alloc:
	uwb_rc_put(uwb_rc);
error_rc_alloc:
	return result;
}

static void hwarc_disconnect(struct usb_interface *iface)
{
	struct hwarc *hwarc = usb_get_intfdata(iface);
	struct uwb_rc *uwb_rc = hwarc->uwb_rc;

	usb_set_intfdata(hwarc->usb_iface, NULL);
	uwb_rc_rm(uwb_rc);
	usb_put_intf(hwarc->usb_iface);
	usb_put_dev(hwarc->usb_dev);
	kfree(hwarc);
	uwb_rc_put(uwb_rc);	/* when creating the device, refcount = 1 */
}

static int hwarc_pre_reset(struct usb_interface *iface)
{
	struct hwarc *hwarc = usb_get_intfdata(iface);
	struct uwb_rc *uwb_rc = hwarc->uwb_rc;

	uwb_rc_pre_reset(uwb_rc);
	return 0;
}

static int hwarc_post_reset(struct usb_interface *iface)
{
	struct hwarc *hwarc = usb_get_intfdata(iface);
	struct uwb_rc *uwb_rc = hwarc->uwb_rc;

	return uwb_rc_post_reset(uwb_rc);
}

/** USB device ID's that we handle */
static const struct usb_device_id hwarc_id_table[] = {
	/* D-Link DUB-1210 */
	{ USB_DEVICE_AND_INTERFACE_INFO(0x07d1, 0x3d02, 0xe0, 0x01, 0x02),
	  .driver_info = WUSB_QUIRK_WHCI_CMD_EVT },
	/* Intel i1480 (using firmware 1.3PA2-20070828) */
	{ USB_DEVICE_AND_INTERFACE_INFO(0x8086, 0x0c3b, 0xe0, 0x01, 0x02),
	  .driver_info = WUSB_QUIRK_WHCI_CMD_EVT },
	/* Generic match for the Radio Control interface */
	{ USB_INTERFACE_INFO(0xe0, 0x01, 0x02), },
	{ },
};
MODULE_DEVICE_TABLE(usb, hwarc_id_table);

static struct usb_driver hwarc_driver = {
	.name =		"hwa-rc",
	.id_table =	hwarc_id_table,
	.probe =	hwarc_probe,
	.disconnect =	hwarc_disconnect,
	.pre_reset =    hwarc_pre_reset,
	.post_reset =   hwarc_post_reset,
};

static int __init hwarc_driver_init(void)
{
	return usb_register(&hwarc_driver);
}
module_init(hwarc_driver_init);

static void __exit hwarc_driver_exit(void)
{
	usb_deregister(&hwarc_driver);
}
module_exit(hwarc_driver_exit);

MODULE_AUTHOR("Inaky Perez-Gonzalez <inaky.perez-gonzalez@intel.com>");
MODULE_DESCRIPTION("Host Wireless Adapter Radio Control Driver");
MODULE_LICENSE("GPL");
