Linux Audio

Check our new training course

Loading...
Note: File does not exist in v3.1.
   1/*
   2 * Copyright (c) 2007-2011 Atheros Communications Inc.
   3 * Copyright (c) 2011-2012 Qualcomm Atheros, Inc.
   4 *
   5 * Permission to use, copy, modify, and/or distribute this software for any
   6 * purpose with or without fee is hereby granted, provided that the above
   7 * copyright notice and this permission notice appear in all copies.
   8 *
   9 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
  10 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
  11 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
  12 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
  13 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
  14 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
  15 * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
  16 */
  17
  18#include <linux/module.h>
  19#include <linux/usb.h>
  20
  21#include "debug.h"
  22#include "core.h"
  23
  24/* constants */
  25#define TX_URB_COUNT            32
  26#define RX_URB_COUNT            32
  27#define ATH6KL_USB_RX_BUFFER_SIZE  4096
  28
  29/* tx/rx pipes for usb */
  30enum ATH6KL_USB_PIPE_ID {
  31	ATH6KL_USB_PIPE_TX_CTRL = 0,
  32	ATH6KL_USB_PIPE_TX_DATA_LP,
  33	ATH6KL_USB_PIPE_TX_DATA_MP,
  34	ATH6KL_USB_PIPE_TX_DATA_HP,
  35	ATH6KL_USB_PIPE_RX_CTRL,
  36	ATH6KL_USB_PIPE_RX_DATA,
  37	ATH6KL_USB_PIPE_RX_DATA2,
  38	ATH6KL_USB_PIPE_RX_INT,
  39	ATH6KL_USB_PIPE_MAX
  40};
  41
  42#define ATH6KL_USB_PIPE_INVALID ATH6KL_USB_PIPE_MAX
  43
  44struct ath6kl_usb_pipe {
  45	struct list_head urb_list_head;
  46	struct usb_anchor urb_submitted;
  47	u32 urb_alloc;
  48	u32 urb_cnt;
  49	u32 urb_cnt_thresh;
  50	unsigned int usb_pipe_handle;
  51	u32 flags;
  52	u8 ep_address;
  53	u8 logical_pipe_num;
  54	struct ath6kl_usb *ar_usb;
  55	u16 max_packet_size;
  56	struct work_struct io_complete_work;
  57	struct sk_buff_head io_comp_queue;
  58	struct usb_endpoint_descriptor *ep_desc;
  59};
  60
  61#define ATH6KL_USB_PIPE_FLAG_TX    (1 << 0)
  62
  63/* usb device object */
  64struct ath6kl_usb {
  65	/* protects pipe->urb_list_head and  pipe->urb_cnt */
  66	spinlock_t cs_lock;
  67
  68	struct usb_device *udev;
  69	struct usb_interface *interface;
  70	struct ath6kl_usb_pipe pipes[ATH6KL_USB_PIPE_MAX];
  71	u8 *diag_cmd_buffer;
  72	u8 *diag_resp_buffer;
  73	struct ath6kl *ar;
  74};
  75
  76/* usb urb object */
  77struct ath6kl_urb_context {
  78	struct list_head link;
  79	struct ath6kl_usb_pipe *pipe;
  80	struct sk_buff *skb;
  81	struct ath6kl *ar;
  82};
  83
  84/* USB endpoint definitions */
  85#define ATH6KL_USB_EP_ADDR_APP_CTRL_IN          0x81
  86#define ATH6KL_USB_EP_ADDR_APP_DATA_IN          0x82
  87#define ATH6KL_USB_EP_ADDR_APP_DATA2_IN         0x83
  88#define ATH6KL_USB_EP_ADDR_APP_INT_IN           0x84
  89
  90#define ATH6KL_USB_EP_ADDR_APP_CTRL_OUT         0x01
  91#define ATH6KL_USB_EP_ADDR_APP_DATA_LP_OUT      0x02
  92#define ATH6KL_USB_EP_ADDR_APP_DATA_MP_OUT      0x03
  93#define ATH6KL_USB_EP_ADDR_APP_DATA_HP_OUT      0x04
  94
  95/* diagnostic command defnitions */
  96#define ATH6KL_USB_CONTROL_REQ_SEND_BMI_CMD        1
  97#define ATH6KL_USB_CONTROL_REQ_RECV_BMI_RESP       2
  98#define ATH6KL_USB_CONTROL_REQ_DIAG_CMD            3
  99#define ATH6KL_USB_CONTROL_REQ_DIAG_RESP           4
 100
 101#define ATH6KL_USB_CTRL_DIAG_CC_READ               0
 102#define ATH6KL_USB_CTRL_DIAG_CC_WRITE              1
 103
 104struct ath6kl_usb_ctrl_diag_cmd_write {
 105	__le32 cmd;
 106	__le32 address;
 107	__le32 value;
 108	__le32 _pad[1];
 109} __packed;
 110
 111struct ath6kl_usb_ctrl_diag_cmd_read {
 112	__le32 cmd;
 113	__le32 address;
 114} __packed;
 115
 116struct ath6kl_usb_ctrl_diag_resp_read {
 117	__le32 value;
 118} __packed;
 119
 120/* function declarations */
 121static void ath6kl_usb_recv_complete(struct urb *urb);
 122
 123#define ATH6KL_USB_IS_BULK_EP(attr) (((attr) & 3) == 0x02)
 124#define ATH6KL_USB_IS_INT_EP(attr)  (((attr) & 3) == 0x03)
 125#define ATH6KL_USB_IS_ISOC_EP(attr)  (((attr) & 3) == 0x01)
 126#define ATH6KL_USB_IS_DIR_IN(addr)  ((addr) & 0x80)
 127
 128/* pipe/urb operations */
 129static struct ath6kl_urb_context *
 130ath6kl_usb_alloc_urb_from_pipe(struct ath6kl_usb_pipe *pipe)
 131{
 132	struct ath6kl_urb_context *urb_context = NULL;
 133	unsigned long flags;
 134
 135	spin_lock_irqsave(&pipe->ar_usb->cs_lock, flags);
 136	if (!list_empty(&pipe->urb_list_head)) {
 137		urb_context =
 138		    list_first_entry(&pipe->urb_list_head,
 139				     struct ath6kl_urb_context, link);
 140		list_del(&urb_context->link);
 141		pipe->urb_cnt--;
 142	}
 143	spin_unlock_irqrestore(&pipe->ar_usb->cs_lock, flags);
 144
 145	return urb_context;
 146}
 147
 148static void ath6kl_usb_free_urb_to_pipe(struct ath6kl_usb_pipe *pipe,
 149					struct ath6kl_urb_context *urb_context)
 150{
 151	unsigned long flags;
 152
 153	spin_lock_irqsave(&pipe->ar_usb->cs_lock, flags);
 154	pipe->urb_cnt++;
 155
 156	list_add(&urb_context->link, &pipe->urb_list_head);
 157	spin_unlock_irqrestore(&pipe->ar_usb->cs_lock, flags);
 158}
 159
 160static void ath6kl_usb_cleanup_recv_urb(struct ath6kl_urb_context *urb_context)
 161{
 162	dev_kfree_skb(urb_context->skb);
 163	urb_context->skb = NULL;
 164
 165	ath6kl_usb_free_urb_to_pipe(urb_context->pipe, urb_context);
 166}
 167
 168static inline struct ath6kl_usb *ath6kl_usb_priv(struct ath6kl *ar)
 169{
 170	return ar->hif_priv;
 171}
 172
 173/* pipe resource allocation/cleanup */
 174static int ath6kl_usb_alloc_pipe_resources(struct ath6kl_usb_pipe *pipe,
 175					   int urb_cnt)
 176{
 177	struct ath6kl_urb_context *urb_context;
 178	int status = 0, i;
 179
 180	INIT_LIST_HEAD(&pipe->urb_list_head);
 181	init_usb_anchor(&pipe->urb_submitted);
 182
 183	for (i = 0; i < urb_cnt; i++) {
 184		urb_context = kzalloc(sizeof(struct ath6kl_urb_context),
 185				      GFP_KERNEL);
 186		if (urb_context == NULL) {
 187			status = -ENOMEM;
 188			goto fail_alloc_pipe_resources;
 189		}
 190
 191		urb_context->pipe = pipe;
 192
 193		/*
 194		 * we are only allocate the urb contexts here, the actual URB
 195		 * is allocated from the kernel as needed to do a transaction
 196		 */
 197		pipe->urb_alloc++;
 198		ath6kl_usb_free_urb_to_pipe(pipe, urb_context);
 199	}
 200
 201	ath6kl_dbg(ATH6KL_DBG_USB,
 202		   "ath6kl usb: alloc resources lpipe:%d hpipe:0x%X urbs:%d\n",
 203		   pipe->logical_pipe_num, pipe->usb_pipe_handle,
 204		   pipe->urb_alloc);
 205
 206fail_alloc_pipe_resources:
 207	return status;
 208}
 209
 210static void ath6kl_usb_free_pipe_resources(struct ath6kl_usb_pipe *pipe)
 211{
 212	struct ath6kl_urb_context *urb_context;
 213
 214	if (pipe->ar_usb == NULL) {
 215		/* nothing allocated for this pipe */
 216		return;
 217	}
 218
 219	ath6kl_dbg(ATH6KL_DBG_USB,
 220		   "ath6kl usb: free resources lpipe:%d"
 221		   "hpipe:0x%X urbs:%d avail:%d\n",
 222		   pipe->logical_pipe_num, pipe->usb_pipe_handle,
 223		   pipe->urb_alloc, pipe->urb_cnt);
 224
 225	if (pipe->urb_alloc != pipe->urb_cnt) {
 226		ath6kl_dbg(ATH6KL_DBG_USB,
 227			   "ath6kl usb: urb leak! lpipe:%d"
 228			   "hpipe:0x%X urbs:%d avail:%d\n",
 229			   pipe->logical_pipe_num, pipe->usb_pipe_handle,
 230			   pipe->urb_alloc, pipe->urb_cnt);
 231	}
 232
 233	while (true) {
 234		urb_context = ath6kl_usb_alloc_urb_from_pipe(pipe);
 235		if (urb_context == NULL)
 236			break;
 237		kfree(urb_context);
 238	}
 239
 240}
 241
 242static void ath6kl_usb_cleanup_pipe_resources(struct ath6kl_usb *ar_usb)
 243{
 244	int i;
 245
 246	for (i = 0; i < ATH6KL_USB_PIPE_MAX; i++)
 247		ath6kl_usb_free_pipe_resources(&ar_usb->pipes[i]);
 248
 249}
 250
 251static u8 ath6kl_usb_get_logical_pipe_num(struct ath6kl_usb *ar_usb,
 252					  u8 ep_address, int *urb_count)
 253{
 254	u8 pipe_num = ATH6KL_USB_PIPE_INVALID;
 255
 256	switch (ep_address) {
 257	case ATH6KL_USB_EP_ADDR_APP_CTRL_IN:
 258		pipe_num = ATH6KL_USB_PIPE_RX_CTRL;
 259		*urb_count = RX_URB_COUNT;
 260		break;
 261	case ATH6KL_USB_EP_ADDR_APP_DATA_IN:
 262		pipe_num = ATH6KL_USB_PIPE_RX_DATA;
 263		*urb_count = RX_URB_COUNT;
 264		break;
 265	case ATH6KL_USB_EP_ADDR_APP_INT_IN:
 266		pipe_num = ATH6KL_USB_PIPE_RX_INT;
 267		*urb_count = RX_URB_COUNT;
 268		break;
 269	case ATH6KL_USB_EP_ADDR_APP_DATA2_IN:
 270		pipe_num = ATH6KL_USB_PIPE_RX_DATA2;
 271		*urb_count = RX_URB_COUNT;
 272		break;
 273	case ATH6KL_USB_EP_ADDR_APP_CTRL_OUT:
 274		pipe_num = ATH6KL_USB_PIPE_TX_CTRL;
 275		*urb_count = TX_URB_COUNT;
 276		break;
 277	case ATH6KL_USB_EP_ADDR_APP_DATA_LP_OUT:
 278		pipe_num = ATH6KL_USB_PIPE_TX_DATA_LP;
 279		*urb_count = TX_URB_COUNT;
 280		break;
 281	case ATH6KL_USB_EP_ADDR_APP_DATA_MP_OUT:
 282		pipe_num = ATH6KL_USB_PIPE_TX_DATA_MP;
 283		*urb_count = TX_URB_COUNT;
 284		break;
 285	case ATH6KL_USB_EP_ADDR_APP_DATA_HP_OUT:
 286		pipe_num = ATH6KL_USB_PIPE_TX_DATA_HP;
 287		*urb_count = TX_URB_COUNT;
 288		break;
 289	default:
 290		/* note: there may be endpoints not currently used */
 291		break;
 292	}
 293
 294	return pipe_num;
 295}
 296
 297static int ath6kl_usb_setup_pipe_resources(struct ath6kl_usb *ar_usb)
 298{
 299	struct usb_interface *interface = ar_usb->interface;
 300	struct usb_host_interface *iface_desc = interface->cur_altsetting;
 301	struct usb_endpoint_descriptor *endpoint;
 302	struct ath6kl_usb_pipe *pipe;
 303	int i, urbcount, status = 0;
 304	u8 pipe_num;
 305
 306	ath6kl_dbg(ATH6KL_DBG_USB, "setting up USB Pipes using interface\n");
 307
 308	/* walk decriptors and setup pipes */
 309	for (i = 0; i < iface_desc->desc.bNumEndpoints; ++i) {
 310		endpoint = &iface_desc->endpoint[i].desc;
 311
 312		if (ATH6KL_USB_IS_BULK_EP(endpoint->bmAttributes)) {
 313			ath6kl_dbg(ATH6KL_DBG_USB,
 314				   "%s Bulk Ep:0x%2.2X maxpktsz:%d\n",
 315				   ATH6KL_USB_IS_DIR_IN
 316				   (endpoint->bEndpointAddress) ?
 317				   "RX" : "TX", endpoint->bEndpointAddress,
 318				   le16_to_cpu(endpoint->wMaxPacketSize));
 319		} else if (ATH6KL_USB_IS_INT_EP(endpoint->bmAttributes)) {
 320			ath6kl_dbg(ATH6KL_DBG_USB,
 321				   "%s Int Ep:0x%2.2X maxpktsz:%d interval:%d\n",
 322				   ATH6KL_USB_IS_DIR_IN
 323				   (endpoint->bEndpointAddress) ?
 324				   "RX" : "TX", endpoint->bEndpointAddress,
 325				   le16_to_cpu(endpoint->wMaxPacketSize),
 326				   endpoint->bInterval);
 327		} else if (ATH6KL_USB_IS_ISOC_EP(endpoint->bmAttributes)) {
 328			/* TODO for ISO */
 329			ath6kl_dbg(ATH6KL_DBG_USB,
 330				   "%s ISOC Ep:0x%2.2X maxpktsz:%d interval:%d\n",
 331				   ATH6KL_USB_IS_DIR_IN
 332				   (endpoint->bEndpointAddress) ?
 333				   "RX" : "TX", endpoint->bEndpointAddress,
 334				   le16_to_cpu(endpoint->wMaxPacketSize),
 335				   endpoint->bInterval);
 336		}
 337		urbcount = 0;
 338
 339		pipe_num =
 340		    ath6kl_usb_get_logical_pipe_num(ar_usb,
 341						    endpoint->bEndpointAddress,
 342						    &urbcount);
 343		if (pipe_num == ATH6KL_USB_PIPE_INVALID)
 344			continue;
 345
 346		pipe = &ar_usb->pipes[pipe_num];
 347		if (pipe->ar_usb != NULL) {
 348			/* hmmm..pipe was already setup */
 349			continue;
 350		}
 351
 352		pipe->ar_usb = ar_usb;
 353		pipe->logical_pipe_num = pipe_num;
 354		pipe->ep_address = endpoint->bEndpointAddress;
 355		pipe->max_packet_size = le16_to_cpu(endpoint->wMaxPacketSize);
 356
 357		if (ATH6KL_USB_IS_BULK_EP(endpoint->bmAttributes)) {
 358			if (ATH6KL_USB_IS_DIR_IN(pipe->ep_address)) {
 359				pipe->usb_pipe_handle =
 360				    usb_rcvbulkpipe(ar_usb->udev,
 361						    pipe->ep_address);
 362			} else {
 363				pipe->usb_pipe_handle =
 364				    usb_sndbulkpipe(ar_usb->udev,
 365						    pipe->ep_address);
 366			}
 367		} else if (ATH6KL_USB_IS_INT_EP(endpoint->bmAttributes)) {
 368			if (ATH6KL_USB_IS_DIR_IN(pipe->ep_address)) {
 369				pipe->usb_pipe_handle =
 370				    usb_rcvintpipe(ar_usb->udev,
 371						   pipe->ep_address);
 372			} else {
 373				pipe->usb_pipe_handle =
 374				    usb_sndintpipe(ar_usb->udev,
 375						   pipe->ep_address);
 376			}
 377		} else if (ATH6KL_USB_IS_ISOC_EP(endpoint->bmAttributes)) {
 378			/* TODO for ISO */
 379			if (ATH6KL_USB_IS_DIR_IN(pipe->ep_address)) {
 380				pipe->usb_pipe_handle =
 381				    usb_rcvisocpipe(ar_usb->udev,
 382						    pipe->ep_address);
 383			} else {
 384				pipe->usb_pipe_handle =
 385				    usb_sndisocpipe(ar_usb->udev,
 386						    pipe->ep_address);
 387			}
 388		}
 389
 390		pipe->ep_desc = endpoint;
 391
 392		if (!ATH6KL_USB_IS_DIR_IN(pipe->ep_address))
 393			pipe->flags |= ATH6KL_USB_PIPE_FLAG_TX;
 394
 395		status = ath6kl_usb_alloc_pipe_resources(pipe, urbcount);
 396		if (status != 0)
 397			break;
 398	}
 399
 400	return status;
 401}
 402
 403/* pipe operations */
 404static void ath6kl_usb_post_recv_transfers(struct ath6kl_usb_pipe *recv_pipe,
 405					   int buffer_length)
 406{
 407	struct ath6kl_urb_context *urb_context;
 408	struct urb *urb;
 409	int usb_status;
 410
 411	while (true) {
 412		urb_context = ath6kl_usb_alloc_urb_from_pipe(recv_pipe);
 413		if (urb_context == NULL)
 414			break;
 415
 416		urb_context->skb = dev_alloc_skb(buffer_length);
 417		if (urb_context->skb == NULL)
 418			goto err_cleanup_urb;
 419
 420		urb = usb_alloc_urb(0, GFP_ATOMIC);
 421		if (urb == NULL)
 422			goto err_cleanup_urb;
 423
 424		usb_fill_bulk_urb(urb,
 425				  recv_pipe->ar_usb->udev,
 426				  recv_pipe->usb_pipe_handle,
 427				  urb_context->skb->data,
 428				  buffer_length,
 429				  ath6kl_usb_recv_complete, urb_context);
 430
 431		ath6kl_dbg(ATH6KL_DBG_USB_BULK,
 432			   "ath6kl usb: bulk recv submit:%d, 0x%X (ep:0x%2.2X), %d bytes buf:0x%p\n",
 433			   recv_pipe->logical_pipe_num,
 434			   recv_pipe->usb_pipe_handle, recv_pipe->ep_address,
 435			   buffer_length, urb_context->skb);
 436
 437		usb_anchor_urb(urb, &recv_pipe->urb_submitted);
 438		usb_status = usb_submit_urb(urb, GFP_ATOMIC);
 439
 440		if (usb_status) {
 441			ath6kl_dbg(ATH6KL_DBG_USB_BULK,
 442				   "ath6kl usb : usb bulk recv failed %d\n",
 443				   usb_status);
 444			usb_unanchor_urb(urb);
 445			usb_free_urb(urb);
 446			goto err_cleanup_urb;
 447		}
 448		usb_free_urb(urb);
 449	}
 450	return;
 451
 452err_cleanup_urb:
 453	ath6kl_usb_cleanup_recv_urb(urb_context);
 454	return;
 455}
 456
 457static void ath6kl_usb_flush_all(struct ath6kl_usb *ar_usb)
 458{
 459	int i;
 460
 461	for (i = 0; i < ATH6KL_USB_PIPE_MAX; i++) {
 462		if (ar_usb->pipes[i].ar_usb != NULL)
 463			usb_kill_anchored_urbs(&ar_usb->pipes[i].urb_submitted);
 464	}
 465
 466	/*
 467	 * Flushing any pending I/O may schedule work this call will block
 468	 * until all scheduled work runs to completion.
 469	 */
 470	flush_scheduled_work();
 471}
 472
 473static void ath6kl_usb_start_recv_pipes(struct ath6kl_usb *ar_usb)
 474{
 475	/*
 476	 * note: control pipe is no longer used
 477	 * ar_usb->pipes[ATH6KL_USB_PIPE_RX_CTRL].urb_cnt_thresh =
 478	 *      ar_usb->pipes[ATH6KL_USB_PIPE_RX_CTRL].urb_alloc/2;
 479	 * ath6kl_usb_post_recv_transfers(&ar_usb->
 480	 *		pipes[ATH6KL_USB_PIPE_RX_CTRL],
 481	 *		ATH6KL_USB_RX_BUFFER_SIZE);
 482	 */
 483
 484	ar_usb->pipes[ATH6KL_USB_PIPE_RX_DATA].urb_cnt_thresh = 1;
 485
 486	ath6kl_usb_post_recv_transfers(&ar_usb->pipes[ATH6KL_USB_PIPE_RX_DATA],
 487				       ATH6KL_USB_RX_BUFFER_SIZE);
 488}
 489
 490/* hif usb rx/tx completion functions */
 491static void ath6kl_usb_recv_complete(struct urb *urb)
 492{
 493	struct ath6kl_urb_context *urb_context = urb->context;
 494	struct ath6kl_usb_pipe *pipe = urb_context->pipe;
 495	struct sk_buff *skb = NULL;
 496	int status = 0;
 497
 498	ath6kl_dbg(ATH6KL_DBG_USB_BULK,
 499		   "%s: recv pipe: %d, stat:%d, len:%d urb:0x%p\n", __func__,
 500		   pipe->logical_pipe_num, urb->status, urb->actual_length,
 501		   urb);
 502
 503	if (urb->status != 0) {
 504		status = -EIO;
 505		switch (urb->status) {
 506		case -ECONNRESET:
 507		case -ENOENT:
 508		case -ESHUTDOWN:
 509			/*
 510			 * no need to spew these errors when device
 511			 * removed or urb killed due to driver shutdown
 512			 */
 513			status = -ECANCELED;
 514			break;
 515		default:
 516			ath6kl_dbg(ATH6KL_DBG_USB_BULK,
 517				   "%s recv pipe: %d (ep:0x%2.2X), failed:%d\n",
 518				   __func__, pipe->logical_pipe_num,
 519				   pipe->ep_address, urb->status);
 520			break;
 521		}
 522		goto cleanup_recv_urb;
 523	}
 524
 525	if (urb->actual_length == 0)
 526		goto cleanup_recv_urb;
 527
 528	skb = urb_context->skb;
 529
 530	/* we are going to pass it up */
 531	urb_context->skb = NULL;
 532	skb_put(skb, urb->actual_length);
 533
 534	/* note: queue implements a lock */
 535	skb_queue_tail(&pipe->io_comp_queue, skb);
 536	schedule_work(&pipe->io_complete_work);
 537
 538cleanup_recv_urb:
 539	ath6kl_usb_cleanup_recv_urb(urb_context);
 540
 541	if (status == 0 &&
 542	    pipe->urb_cnt >= pipe->urb_cnt_thresh) {
 543		/* our free urbs are piling up, post more transfers */
 544		ath6kl_usb_post_recv_transfers(pipe, ATH6KL_USB_RX_BUFFER_SIZE);
 545	}
 546}
 547
 548static void ath6kl_usb_usb_transmit_complete(struct urb *urb)
 549{
 550	struct ath6kl_urb_context *urb_context = urb->context;
 551	struct ath6kl_usb_pipe *pipe = urb_context->pipe;
 552	struct sk_buff *skb;
 553
 554	ath6kl_dbg(ATH6KL_DBG_USB_BULK,
 555		   "%s: pipe: %d, stat:%d, len:%d\n",
 556		   __func__, pipe->logical_pipe_num, urb->status,
 557		   urb->actual_length);
 558
 559	if (urb->status != 0) {
 560		ath6kl_dbg(ATH6KL_DBG_USB_BULK,
 561			   "%s:  pipe: %d, failed:%d\n",
 562			   __func__, pipe->logical_pipe_num, urb->status);
 563	}
 564
 565	skb = urb_context->skb;
 566	urb_context->skb = NULL;
 567	ath6kl_usb_free_urb_to_pipe(urb_context->pipe, urb_context);
 568
 569	/* note: queue implements a lock */
 570	skb_queue_tail(&pipe->io_comp_queue, skb);
 571	schedule_work(&pipe->io_complete_work);
 572}
 573
 574static void ath6kl_usb_io_comp_work(struct work_struct *work)
 575{
 576	struct ath6kl_usb_pipe *pipe = container_of(work,
 577						    struct ath6kl_usb_pipe,
 578						    io_complete_work);
 579	struct ath6kl_usb *ar_usb;
 580	struct sk_buff *skb;
 581
 582	ar_usb = pipe->ar_usb;
 583
 584	while ((skb = skb_dequeue(&pipe->io_comp_queue))) {
 585		if (pipe->flags & ATH6KL_USB_PIPE_FLAG_TX) {
 586			ath6kl_dbg(ATH6KL_DBG_USB_BULK,
 587				   "ath6kl usb xmit callback buf:0x%p\n", skb);
 588			ath6kl_core_tx_complete(ar_usb->ar, skb);
 589		} else {
 590			ath6kl_dbg(ATH6KL_DBG_USB_BULK,
 591				   "ath6kl usb recv callback buf:0x%p\n", skb);
 592			ath6kl_core_rx_complete(ar_usb->ar, skb,
 593						pipe->logical_pipe_num);
 594		}
 595	}
 596}
 597
 598#define ATH6KL_USB_MAX_DIAG_CMD (sizeof(struct ath6kl_usb_ctrl_diag_cmd_write))
 599#define ATH6KL_USB_MAX_DIAG_RESP (sizeof(struct ath6kl_usb_ctrl_diag_resp_read))
 600
 601static void ath6kl_usb_destroy(struct ath6kl_usb *ar_usb)
 602{
 603	ath6kl_usb_flush_all(ar_usb);
 604
 605	ath6kl_usb_cleanup_pipe_resources(ar_usb);
 606
 607	usb_set_intfdata(ar_usb->interface, NULL);
 608
 609	kfree(ar_usb->diag_cmd_buffer);
 610	kfree(ar_usb->diag_resp_buffer);
 611
 612	kfree(ar_usb);
 613}
 614
 615static struct ath6kl_usb *ath6kl_usb_create(struct usb_interface *interface)
 616{
 617	struct usb_device *dev = interface_to_usbdev(interface);
 618	struct ath6kl_usb *ar_usb;
 619	struct ath6kl_usb_pipe *pipe;
 620	int status = 0;
 621	int i;
 622
 623	ar_usb = kzalloc(sizeof(struct ath6kl_usb), GFP_KERNEL);
 624	if (ar_usb == NULL)
 625		goto fail_ath6kl_usb_create;
 626
 627	usb_set_intfdata(interface, ar_usb);
 628	spin_lock_init(&(ar_usb->cs_lock));
 629	ar_usb->udev = dev;
 630	ar_usb->interface = interface;
 631
 632	for (i = 0; i < ATH6KL_USB_PIPE_MAX; i++) {
 633		pipe = &ar_usb->pipes[i];
 634		INIT_WORK(&pipe->io_complete_work,
 635			  ath6kl_usb_io_comp_work);
 636		skb_queue_head_init(&pipe->io_comp_queue);
 637	}
 638
 639	ar_usb->diag_cmd_buffer = kzalloc(ATH6KL_USB_MAX_DIAG_CMD, GFP_KERNEL);
 640	if (ar_usb->diag_cmd_buffer == NULL) {
 641		status = -ENOMEM;
 642		goto fail_ath6kl_usb_create;
 643	}
 644
 645	ar_usb->diag_resp_buffer = kzalloc(ATH6KL_USB_MAX_DIAG_RESP,
 646					   GFP_KERNEL);
 647	if (ar_usb->diag_resp_buffer == NULL) {
 648		status = -ENOMEM;
 649		goto fail_ath6kl_usb_create;
 650	}
 651
 652	status = ath6kl_usb_setup_pipe_resources(ar_usb);
 653
 654fail_ath6kl_usb_create:
 655	if (status != 0) {
 656		ath6kl_usb_destroy(ar_usb);
 657		ar_usb = NULL;
 658	}
 659	return ar_usb;
 660}
 661
 662static void ath6kl_usb_device_detached(struct usb_interface *interface)
 663{
 664	struct ath6kl_usb *ar_usb;
 665
 666	ar_usb = usb_get_intfdata(interface);
 667	if (ar_usb == NULL)
 668		return;
 669
 670	ath6kl_stop_txrx(ar_usb->ar);
 671
 672	/* Delay to wait for the target to reboot */
 673	mdelay(20);
 674	ath6kl_core_cleanup(ar_usb->ar);
 675	ath6kl_usb_destroy(ar_usb);
 676}
 677
 678/* exported hif usb APIs for htc pipe */
 679static void hif_start(struct ath6kl *ar)
 680{
 681	struct ath6kl_usb *device = ath6kl_usb_priv(ar);
 682	int i;
 683
 684	ath6kl_usb_start_recv_pipes(device);
 685
 686	/* set the TX resource avail threshold for each TX pipe */
 687	for (i = ATH6KL_USB_PIPE_TX_CTRL;
 688	     i <= ATH6KL_USB_PIPE_TX_DATA_HP; i++) {
 689		device->pipes[i].urb_cnt_thresh =
 690		    device->pipes[i].urb_alloc / 2;
 691	}
 692}
 693
 694static int ath6kl_usb_send(struct ath6kl *ar, u8 PipeID,
 695			   struct sk_buff *hdr_skb, struct sk_buff *skb)
 696{
 697	struct ath6kl_usb *device = ath6kl_usb_priv(ar);
 698	struct ath6kl_usb_pipe *pipe = &device->pipes[PipeID];
 699	struct ath6kl_urb_context *urb_context;
 700	int usb_status, status = 0;
 701	struct urb *urb;
 702	u8 *data;
 703	u32 len;
 704
 705	ath6kl_dbg(ATH6KL_DBG_USB_BULK, "+%s pipe : %d, buf:0x%p\n",
 706		   __func__, PipeID, skb);
 707
 708	urb_context = ath6kl_usb_alloc_urb_from_pipe(pipe);
 709
 710	if (urb_context == NULL) {
 711		/*
 712		 * TODO: it is possible to run out of urbs if
 713		 * 2 endpoints map to the same pipe ID
 714		 */
 715		ath6kl_dbg(ATH6KL_DBG_USB_BULK,
 716			   "%s pipe:%d no urbs left. URB Cnt : %d\n",
 717			   __func__, PipeID, pipe->urb_cnt);
 718		status = -ENOMEM;
 719		goto fail_hif_send;
 720	}
 721
 722	urb_context->skb = skb;
 723
 724	data = skb->data;
 725	len = skb->len;
 726
 727	urb = usb_alloc_urb(0, GFP_ATOMIC);
 728	if (urb == NULL) {
 729		status = -ENOMEM;
 730		ath6kl_usb_free_urb_to_pipe(urb_context->pipe,
 731					    urb_context);
 732		goto fail_hif_send;
 733	}
 734
 735	usb_fill_bulk_urb(urb,
 736			  device->udev,
 737			  pipe->usb_pipe_handle,
 738			  data,
 739			  len,
 740			  ath6kl_usb_usb_transmit_complete, urb_context);
 741
 742	if ((len % pipe->max_packet_size) == 0) {
 743		/* hit a max packet boundary on this pipe */
 744		urb->transfer_flags |= URB_ZERO_PACKET;
 745	}
 746
 747	ath6kl_dbg(ATH6KL_DBG_USB_BULK,
 748		   "athusb bulk send submit:%d, 0x%X (ep:0x%2.2X), %d bytes\n",
 749		   pipe->logical_pipe_num, pipe->usb_pipe_handle,
 750		   pipe->ep_address, len);
 751
 752	usb_anchor_urb(urb, &pipe->urb_submitted);
 753	usb_status = usb_submit_urb(urb, GFP_ATOMIC);
 754
 755	if (usb_status) {
 756		ath6kl_dbg(ATH6KL_DBG_USB_BULK,
 757			   "ath6kl usb : usb bulk transmit failed %d\n",
 758			   usb_status);
 759		usb_unanchor_urb(urb);
 760		ath6kl_usb_free_urb_to_pipe(urb_context->pipe,
 761					    urb_context);
 762		status = -EINVAL;
 763	}
 764	usb_free_urb(urb);
 765
 766fail_hif_send:
 767	return status;
 768}
 769
 770static void hif_stop(struct ath6kl *ar)
 771{
 772	struct ath6kl_usb *device = ath6kl_usb_priv(ar);
 773
 774	ath6kl_usb_flush_all(device);
 775}
 776
 777static void ath6kl_usb_get_default_pipe(struct ath6kl *ar,
 778					u8 *ul_pipe, u8 *dl_pipe)
 779{
 780	*ul_pipe = ATH6KL_USB_PIPE_TX_CTRL;
 781	*dl_pipe = ATH6KL_USB_PIPE_RX_CTRL;
 782}
 783
 784static int ath6kl_usb_map_service_pipe(struct ath6kl *ar, u16 svc_id,
 785				       u8 *ul_pipe, u8 *dl_pipe)
 786{
 787	int status = 0;
 788
 789	switch (svc_id) {
 790	case HTC_CTRL_RSVD_SVC:
 791	case WMI_CONTROL_SVC:
 792		*ul_pipe = ATH6KL_USB_PIPE_TX_CTRL;
 793		/* due to large control packets, shift to data pipe */
 794		*dl_pipe = ATH6KL_USB_PIPE_RX_DATA;
 795		break;
 796	case WMI_DATA_BE_SVC:
 797	case WMI_DATA_BK_SVC:
 798		*ul_pipe = ATH6KL_USB_PIPE_TX_DATA_LP;
 799		/*
 800		* Disable rxdata2 directly, it will be enabled
 801		* if FW enable rxdata2
 802		*/
 803		*dl_pipe = ATH6KL_USB_PIPE_RX_DATA;
 804		break;
 805	case WMI_DATA_VI_SVC:
 806
 807		if (ar->hw.flags & ATH6KL_HW_MAP_LP_ENDPOINT)
 808			*ul_pipe = ATH6KL_USB_PIPE_TX_DATA_LP;
 809		else
 810			*ul_pipe = ATH6KL_USB_PIPE_TX_DATA_MP;
 811		/*
 812		* Disable rxdata2 directly, it will be enabled
 813		* if FW enable rxdata2
 814		*/
 815		*dl_pipe = ATH6KL_USB_PIPE_RX_DATA;
 816		break;
 817	case WMI_DATA_VO_SVC:
 818
 819		if (ar->hw.flags & ATH6KL_HW_MAP_LP_ENDPOINT)
 820			*ul_pipe = ATH6KL_USB_PIPE_TX_DATA_LP;
 821		else
 822			*ul_pipe = ATH6KL_USB_PIPE_TX_DATA_MP;
 823		/*
 824		* Disable rxdata2 directly, it will be enabled
 825		* if FW enable rxdata2
 826		*/
 827		*dl_pipe = ATH6KL_USB_PIPE_RX_DATA;
 828		break;
 829	default:
 830		status = -EPERM;
 831		break;
 832	}
 833
 834	return status;
 835}
 836
 837static u16 ath6kl_usb_get_free_queue_number(struct ath6kl *ar, u8 pipe_id)
 838{
 839	struct ath6kl_usb *device = ath6kl_usb_priv(ar);
 840
 841	return device->pipes[pipe_id].urb_cnt;
 842}
 843
 844static void hif_detach_htc(struct ath6kl *ar)
 845{
 846	struct ath6kl_usb *device = ath6kl_usb_priv(ar);
 847
 848	ath6kl_usb_flush_all(device);
 849}
 850
 851static int ath6kl_usb_submit_ctrl_out(struct ath6kl_usb *ar_usb,
 852				   u8 req, u16 value, u16 index, void *data,
 853				   u32 size)
 854{
 855	u8 *buf = NULL;
 856	int ret;
 857
 858	if (size > 0) {
 859		buf = kmemdup(data, size, GFP_KERNEL);
 860		if (buf == NULL)
 861			return -ENOMEM;
 862	}
 863
 864	/* note: if successful returns number of bytes transfered */
 865	ret = usb_control_msg(ar_usb->udev,
 866			      usb_sndctrlpipe(ar_usb->udev, 0),
 867			      req,
 868			      USB_DIR_OUT | USB_TYPE_VENDOR |
 869			      USB_RECIP_DEVICE, value, index, buf,
 870			      size, 1000);
 871
 872	if (ret < 0) {
 873		ath6kl_warn("Failed to submit usb control message: %d\n", ret);
 874		kfree(buf);
 875		return ret;
 876	}
 877
 878	kfree(buf);
 879
 880	return 0;
 881}
 882
 883static int ath6kl_usb_submit_ctrl_in(struct ath6kl_usb *ar_usb,
 884				  u8 req, u16 value, u16 index, void *data,
 885				  u32 size)
 886{
 887	u8 *buf = NULL;
 888	int ret;
 889
 890	if (size > 0) {
 891		buf = kmalloc(size, GFP_KERNEL);
 892		if (buf == NULL)
 893			return -ENOMEM;
 894	}
 895
 896	/* note: if successful returns number of bytes transfered */
 897	ret = usb_control_msg(ar_usb->udev,
 898				 usb_rcvctrlpipe(ar_usb->udev, 0),
 899				 req,
 900				 USB_DIR_IN | USB_TYPE_VENDOR |
 901				 USB_RECIP_DEVICE, value, index, buf,
 902				 size, 2 * HZ);
 903
 904	if (ret < 0) {
 905		ath6kl_warn("Failed to read usb control message: %d\n", ret);
 906		kfree(buf);
 907		return ret;
 908	}
 909
 910	memcpy((u8 *) data, buf, size);
 911
 912	kfree(buf);
 913
 914	return 0;
 915}
 916
 917static int ath6kl_usb_ctrl_msg_exchange(struct ath6kl_usb *ar_usb,
 918				     u8 req_val, u8 *req_buf, u32 req_len,
 919				     u8 resp_val, u8 *resp_buf, u32 *resp_len)
 920{
 921	int ret;
 922
 923	/* send command */
 924	ret = ath6kl_usb_submit_ctrl_out(ar_usb, req_val, 0, 0,
 925					 req_buf, req_len);
 926
 927	if (ret != 0)
 928		return ret;
 929
 930	if (resp_buf == NULL) {
 931		/* no expected response */
 932		return ret;
 933	}
 934
 935	/* get response */
 936	ret = ath6kl_usb_submit_ctrl_in(ar_usb, resp_val, 0, 0,
 937					resp_buf, *resp_len);
 938
 939	return ret;
 940}
 941
 942static int ath6kl_usb_diag_read32(struct ath6kl *ar, u32 address, u32 *data)
 943{
 944	struct ath6kl_usb *ar_usb = ar->hif_priv;
 945	struct ath6kl_usb_ctrl_diag_resp_read *resp;
 946	struct ath6kl_usb_ctrl_diag_cmd_read *cmd;
 947	u32 resp_len;
 948	int ret;
 949
 950	cmd = (struct ath6kl_usb_ctrl_diag_cmd_read *) ar_usb->diag_cmd_buffer;
 951
 952	memset(cmd, 0, sizeof(*cmd));
 953	cmd->cmd = ATH6KL_USB_CTRL_DIAG_CC_READ;
 954	cmd->address = cpu_to_le32(address);
 955	resp_len = sizeof(*resp);
 956
 957	ret = ath6kl_usb_ctrl_msg_exchange(ar_usb,
 958				ATH6KL_USB_CONTROL_REQ_DIAG_CMD,
 959				(u8 *) cmd,
 960				sizeof(struct ath6kl_usb_ctrl_diag_cmd_write),
 961				ATH6KL_USB_CONTROL_REQ_DIAG_RESP,
 962				ar_usb->diag_resp_buffer, &resp_len);
 963
 964	if (ret) {
 965		ath6kl_warn("diag read32 failed: %d\n", ret);
 966		return ret;
 967	}
 968
 969	resp = (struct ath6kl_usb_ctrl_diag_resp_read *)
 970		ar_usb->diag_resp_buffer;
 971
 972	*data = le32_to_cpu(resp->value);
 973
 974	return ret;
 975}
 976
 977static int ath6kl_usb_diag_write32(struct ath6kl *ar, u32 address, __le32 data)
 978{
 979	struct ath6kl_usb *ar_usb = ar->hif_priv;
 980	struct ath6kl_usb_ctrl_diag_cmd_write *cmd;
 981	int ret;
 982
 983	cmd = (struct ath6kl_usb_ctrl_diag_cmd_write *) ar_usb->diag_cmd_buffer;
 984
 985	memset(cmd, 0, sizeof(struct ath6kl_usb_ctrl_diag_cmd_write));
 986	cmd->cmd = cpu_to_le32(ATH6KL_USB_CTRL_DIAG_CC_WRITE);
 987	cmd->address = cpu_to_le32(address);
 988	cmd->value = data;
 989
 990	ret = ath6kl_usb_ctrl_msg_exchange(ar_usb,
 991					   ATH6KL_USB_CONTROL_REQ_DIAG_CMD,
 992					   (u8 *) cmd,
 993					   sizeof(*cmd),
 994					   0, NULL, NULL);
 995	if (ret) {
 996		ath6kl_warn("diag_write32 failed: %d\n", ret);
 997		return ret;
 998	}
 999
1000	return 0;
1001}
1002
1003static int ath6kl_usb_bmi_read(struct ath6kl *ar, u8 *buf, u32 len)
1004{
1005	struct ath6kl_usb *ar_usb = ar->hif_priv;
1006	int ret;
1007
1008	/* get response */
1009	ret = ath6kl_usb_submit_ctrl_in(ar_usb,
1010					ATH6KL_USB_CONTROL_REQ_RECV_BMI_RESP,
1011					0, 0, buf, len);
1012	if (ret) {
1013		ath6kl_err("Unable to read the bmi data from the device: %d\n",
1014			   ret);
1015		return ret;
1016	}
1017
1018	return 0;
1019}
1020
1021static int ath6kl_usb_bmi_write(struct ath6kl *ar, u8 *buf, u32 len)
1022{
1023	struct ath6kl_usb *ar_usb = ar->hif_priv;
1024	int ret;
1025
1026	/* send command */
1027	ret = ath6kl_usb_submit_ctrl_out(ar_usb,
1028					 ATH6KL_USB_CONTROL_REQ_SEND_BMI_CMD,
1029					 0, 0, buf, len);
1030	if (ret) {
1031		ath6kl_err("unable to send the bmi data to the device: %d\n",
1032			   ret);
1033		return ret;
1034	}
1035
1036	return 0;
1037}
1038
1039static int ath6kl_usb_power_on(struct ath6kl *ar)
1040{
1041	hif_start(ar);
1042	return 0;
1043}
1044
1045static int ath6kl_usb_power_off(struct ath6kl *ar)
1046{
1047	hif_detach_htc(ar);
1048	return 0;
1049}
1050
1051static void ath6kl_usb_stop(struct ath6kl *ar)
1052{
1053	hif_stop(ar);
1054}
1055
1056static void ath6kl_usb_cleanup_scatter(struct ath6kl *ar)
1057{
1058	/*
1059	 * USB doesn't support it. Just return.
1060	 */
1061	return;
1062}
1063
1064static int ath6kl_usb_suspend(struct ath6kl *ar, struct cfg80211_wowlan *wow)
1065{
1066	/*
1067	 * cfg80211 suspend/WOW currently not supported for USB.
1068	 */
1069	return 0;
1070}
1071
1072static int ath6kl_usb_resume(struct ath6kl *ar)
1073{
1074	/*
1075	 * cfg80211 resume currently not supported for USB.
1076	 */
1077	return 0;
1078}
1079
1080static const struct ath6kl_hif_ops ath6kl_usb_ops = {
1081	.diag_read32 = ath6kl_usb_diag_read32,
1082	.diag_write32 = ath6kl_usb_diag_write32,
1083	.bmi_read = ath6kl_usb_bmi_read,
1084	.bmi_write = ath6kl_usb_bmi_write,
1085	.power_on = ath6kl_usb_power_on,
1086	.power_off = ath6kl_usb_power_off,
1087	.stop = ath6kl_usb_stop,
1088	.pipe_send = ath6kl_usb_send,
1089	.pipe_get_default = ath6kl_usb_get_default_pipe,
1090	.pipe_map_service = ath6kl_usb_map_service_pipe,
1091	.pipe_get_free_queue_number = ath6kl_usb_get_free_queue_number,
1092	.cleanup_scatter = ath6kl_usb_cleanup_scatter,
1093	.suspend = ath6kl_usb_suspend,
1094	.resume = ath6kl_usb_resume,
1095};
1096
1097/* ath6kl usb driver registered functions */
1098static int ath6kl_usb_probe(struct usb_interface *interface,
1099			    const struct usb_device_id *id)
1100{
1101	struct usb_device *dev = interface_to_usbdev(interface);
1102	struct ath6kl *ar;
1103	struct ath6kl_usb *ar_usb = NULL;
1104	int vendor_id, product_id;
1105	int ret = 0;
1106
1107	usb_get_dev(dev);
1108
1109	vendor_id = le16_to_cpu(dev->descriptor.idVendor);
1110	product_id = le16_to_cpu(dev->descriptor.idProduct);
1111
1112	ath6kl_dbg(ATH6KL_DBG_USB, "vendor_id = %04x\n", vendor_id);
1113	ath6kl_dbg(ATH6KL_DBG_USB, "product_id = %04x\n", product_id);
1114
1115	if (interface->cur_altsetting)
1116		ath6kl_dbg(ATH6KL_DBG_USB, "USB Interface %d\n",
1117			   interface->cur_altsetting->desc.bInterfaceNumber);
1118
1119
1120	if (dev->speed == USB_SPEED_HIGH)
1121		ath6kl_dbg(ATH6KL_DBG_USB, "USB 2.0 Host\n");
1122	else
1123		ath6kl_dbg(ATH6KL_DBG_USB, "USB 1.1 Host\n");
1124
1125	ar_usb = ath6kl_usb_create(interface);
1126
1127	if (ar_usb == NULL) {
1128		ret = -ENOMEM;
1129		goto err_usb_put;
1130	}
1131
1132	ar = ath6kl_core_create(&ar_usb->udev->dev);
1133	if (ar == NULL) {
1134		ath6kl_err("Failed to alloc ath6kl core\n");
1135		ret = -ENOMEM;
1136		goto err_usb_destroy;
1137	}
1138
1139	ar->hif_priv = ar_usb;
1140	ar->hif_type = ATH6KL_HIF_TYPE_USB;
1141	ar->hif_ops = &ath6kl_usb_ops;
1142	ar->mbox_info.block_size = 16;
1143	ar->bmi.max_data_size = 252;
1144
1145	ar_usb->ar = ar;
1146
1147	ret = ath6kl_core_init(ar, ATH6KL_HTC_TYPE_PIPE);
1148	if (ret) {
1149		ath6kl_err("Failed to init ath6kl core: %d\n", ret);
1150		goto err_core_free;
1151	}
1152
1153	return ret;
1154
1155err_core_free:
1156	ath6kl_core_destroy(ar);
1157err_usb_destroy:
1158	ath6kl_usb_destroy(ar_usb);
1159err_usb_put:
1160	usb_put_dev(dev);
1161
1162	return ret;
1163}
1164
1165static void ath6kl_usb_remove(struct usb_interface *interface)
1166{
1167	usb_put_dev(interface_to_usbdev(interface));
1168	ath6kl_usb_device_detached(interface);
1169}
1170
1171#ifdef CONFIG_PM
1172
1173static int ath6kl_usb_pm_suspend(struct usb_interface *interface,
1174			      pm_message_t message)
1175{
1176	struct ath6kl_usb *device;
1177	device = usb_get_intfdata(interface);
1178
1179	ath6kl_usb_flush_all(device);
1180	return 0;
1181}
1182
1183static int ath6kl_usb_pm_resume(struct usb_interface *interface)
1184{
1185	struct ath6kl_usb *device;
1186	device = usb_get_intfdata(interface);
1187
1188	ath6kl_usb_post_recv_transfers(&device->pipes[ATH6KL_USB_PIPE_RX_DATA],
1189				       ATH6KL_USB_RX_BUFFER_SIZE);
1190	ath6kl_usb_post_recv_transfers(&device->pipes[ATH6KL_USB_PIPE_RX_DATA2],
1191				       ATH6KL_USB_RX_BUFFER_SIZE);
1192
1193	return 0;
1194}
1195
1196static int ath6kl_usb_pm_reset_resume(struct usb_interface *intf)
1197{
1198	if (usb_get_intfdata(intf))
1199		ath6kl_usb_remove(intf);
1200	return 0;
1201}
1202
1203#else
1204
1205#define ath6kl_usb_pm_suspend NULL
1206#define ath6kl_usb_pm_resume NULL
1207#define ath6kl_usb_pm_reset_resume NULL
1208
1209#endif
1210
1211/* table of devices that work with this driver */
1212static struct usb_device_id ath6kl_usb_ids[] = {
1213	{USB_DEVICE(0x0cf3, 0x9374)},
1214	{ /* Terminating entry */ },
1215};
1216
1217MODULE_DEVICE_TABLE(usb, ath6kl_usb_ids);
1218
1219static struct usb_driver ath6kl_usb_driver = {
1220	.name = "ath6kl_usb",
1221	.probe = ath6kl_usb_probe,
1222	.suspend = ath6kl_usb_pm_suspend,
1223	.resume = ath6kl_usb_pm_resume,
1224	.reset_resume = ath6kl_usb_pm_reset_resume,
1225	.disconnect = ath6kl_usb_remove,
1226	.id_table = ath6kl_usb_ids,
1227	.supports_autosuspend = true,
1228	.disable_hub_initiated_lpm = 1,
1229};
1230
1231static int ath6kl_usb_init(void)
1232{
1233	int ret;
1234
1235	ret = usb_register(&ath6kl_usb_driver);
1236	if (ret) {
1237		ath6kl_err("usb registration failed: %d\n", ret);
1238		return ret;
1239	}
1240
1241	return 0;
1242}
1243
1244static void ath6kl_usb_exit(void)
1245{
1246	usb_deregister(&ath6kl_usb_driver);
1247}
1248
1249module_init(ath6kl_usb_init);
1250module_exit(ath6kl_usb_exit);
1251
1252MODULE_AUTHOR("Atheros Communications, Inc.");
1253MODULE_DESCRIPTION("Driver support for Atheros AR600x USB devices");
1254MODULE_LICENSE("Dual BSD/GPL");
1255MODULE_FIRMWARE(AR6004_HW_1_0_FIRMWARE_FILE);
1256MODULE_FIRMWARE(AR6004_HW_1_0_BOARD_DATA_FILE);
1257MODULE_FIRMWARE(AR6004_HW_1_0_DEFAULT_BOARD_DATA_FILE);
1258MODULE_FIRMWARE(AR6004_HW_1_1_FIRMWARE_FILE);
1259MODULE_FIRMWARE(AR6004_HW_1_1_BOARD_DATA_FILE);
1260MODULE_FIRMWARE(AR6004_HW_1_1_DEFAULT_BOARD_DATA_FILE);
1261MODULE_FIRMWARE(AR6004_HW_1_2_FIRMWARE_FILE);
1262MODULE_FIRMWARE(AR6004_HW_1_2_BOARD_DATA_FILE);
1263MODULE_FIRMWARE(AR6004_HW_1_2_DEFAULT_BOARD_DATA_FILE);
1264MODULE_FIRMWARE(AR6004_HW_1_3_FW_DIR "/" AR6004_HW_1_3_FIRMWARE_FILE);
1265MODULE_FIRMWARE(AR6004_HW_1_3_BOARD_DATA_FILE);
1266MODULE_FIRMWARE(AR6004_HW_1_3_DEFAULT_BOARD_DATA_FILE);