Linux Audio

Check our new training course

Embedded Linux training

Mar 10-20, 2025, special US time zones
Register
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
 241static void ath6kl_usb_cleanup_pipe_resources(struct ath6kl_usb *ar_usb)
 242{
 243	int i;
 244
 245	for (i = 0; i < ATH6KL_USB_PIPE_MAX; i++)
 246		ath6kl_usb_free_pipe_resources(&ar_usb->pipes[i]);
 247}
 248
 249static u8 ath6kl_usb_get_logical_pipe_num(struct ath6kl_usb *ar_usb,
 250					  u8 ep_address, int *urb_count)
 251{
 252	u8 pipe_num = ATH6KL_USB_PIPE_INVALID;
 253
 254	switch (ep_address) {
 255	case ATH6KL_USB_EP_ADDR_APP_CTRL_IN:
 256		pipe_num = ATH6KL_USB_PIPE_RX_CTRL;
 257		*urb_count = RX_URB_COUNT;
 258		break;
 259	case ATH6KL_USB_EP_ADDR_APP_DATA_IN:
 260		pipe_num = ATH6KL_USB_PIPE_RX_DATA;
 261		*urb_count = RX_URB_COUNT;
 262		break;
 263	case ATH6KL_USB_EP_ADDR_APP_INT_IN:
 264		pipe_num = ATH6KL_USB_PIPE_RX_INT;
 265		*urb_count = RX_URB_COUNT;
 266		break;
 267	case ATH6KL_USB_EP_ADDR_APP_DATA2_IN:
 268		pipe_num = ATH6KL_USB_PIPE_RX_DATA2;
 269		*urb_count = RX_URB_COUNT;
 270		break;
 271	case ATH6KL_USB_EP_ADDR_APP_CTRL_OUT:
 272		pipe_num = ATH6KL_USB_PIPE_TX_CTRL;
 273		*urb_count = TX_URB_COUNT;
 274		break;
 275	case ATH6KL_USB_EP_ADDR_APP_DATA_LP_OUT:
 276		pipe_num = ATH6KL_USB_PIPE_TX_DATA_LP;
 277		*urb_count = TX_URB_COUNT;
 278		break;
 279	case ATH6KL_USB_EP_ADDR_APP_DATA_MP_OUT:
 280		pipe_num = ATH6KL_USB_PIPE_TX_DATA_MP;
 281		*urb_count = TX_URB_COUNT;
 282		break;
 283	case ATH6KL_USB_EP_ADDR_APP_DATA_HP_OUT:
 284		pipe_num = ATH6KL_USB_PIPE_TX_DATA_HP;
 285		*urb_count = TX_URB_COUNT;
 286		break;
 287	default:
 288		/* note: there may be endpoints not currently used */
 289		break;
 290	}
 291
 292	return pipe_num;
 293}
 294
 295static int ath6kl_usb_setup_pipe_resources(struct ath6kl_usb *ar_usb)
 296{
 297	struct usb_interface *interface = ar_usb->interface;
 298	struct usb_host_interface *iface_desc = interface->cur_altsetting;
 299	struct usb_endpoint_descriptor *endpoint;
 300	struct ath6kl_usb_pipe *pipe;
 301	int i, urbcount, status = 0;
 302	u8 pipe_num;
 303
 304	ath6kl_dbg(ATH6KL_DBG_USB, "setting up USB Pipes using interface\n");
 305
 306	/* walk decriptors and setup pipes */
 307	for (i = 0; i < iface_desc->desc.bNumEndpoints; ++i) {
 308		endpoint = &iface_desc->endpoint[i].desc;
 309
 310		if (ATH6KL_USB_IS_BULK_EP(endpoint->bmAttributes)) {
 311			ath6kl_dbg(ATH6KL_DBG_USB,
 312				   "%s Bulk Ep:0x%2.2X maxpktsz:%d\n",
 313				   ATH6KL_USB_IS_DIR_IN
 314				   (endpoint->bEndpointAddress) ?
 315				   "RX" : "TX", endpoint->bEndpointAddress,
 316				   le16_to_cpu(endpoint->wMaxPacketSize));
 317		} else if (ATH6KL_USB_IS_INT_EP(endpoint->bmAttributes)) {
 318			ath6kl_dbg(ATH6KL_DBG_USB,
 319				   "%s Int Ep:0x%2.2X maxpktsz:%d interval:%d\n",
 320				   ATH6KL_USB_IS_DIR_IN
 321				   (endpoint->bEndpointAddress) ?
 322				   "RX" : "TX", endpoint->bEndpointAddress,
 323				   le16_to_cpu(endpoint->wMaxPacketSize),
 324				   endpoint->bInterval);
 325		} else if (ATH6KL_USB_IS_ISOC_EP(endpoint->bmAttributes)) {
 326			/* TODO for ISO */
 327			ath6kl_dbg(ATH6KL_DBG_USB,
 328				   "%s ISOC Ep:0x%2.2X maxpktsz:%d interval:%d\n",
 329				   ATH6KL_USB_IS_DIR_IN
 330				   (endpoint->bEndpointAddress) ?
 331				   "RX" : "TX", endpoint->bEndpointAddress,
 332				   le16_to_cpu(endpoint->wMaxPacketSize),
 333				   endpoint->bInterval);
 334		}
 335		urbcount = 0;
 336
 337		pipe_num =
 338		    ath6kl_usb_get_logical_pipe_num(ar_usb,
 339						    endpoint->bEndpointAddress,
 340						    &urbcount);
 341		if (pipe_num == ATH6KL_USB_PIPE_INVALID)
 342			continue;
 343
 344		pipe = &ar_usb->pipes[pipe_num];
 345		if (pipe->ar_usb != NULL) {
 346			/* hmmm..pipe was already setup */
 347			continue;
 348		}
 349
 350		pipe->ar_usb = ar_usb;
 351		pipe->logical_pipe_num = pipe_num;
 352		pipe->ep_address = endpoint->bEndpointAddress;
 353		pipe->max_packet_size = le16_to_cpu(endpoint->wMaxPacketSize);
 354
 355		if (ATH6KL_USB_IS_BULK_EP(endpoint->bmAttributes)) {
 356			if (ATH6KL_USB_IS_DIR_IN(pipe->ep_address)) {
 357				pipe->usb_pipe_handle =
 358				    usb_rcvbulkpipe(ar_usb->udev,
 359						    pipe->ep_address);
 360			} else {
 361				pipe->usb_pipe_handle =
 362				    usb_sndbulkpipe(ar_usb->udev,
 363						    pipe->ep_address);
 364			}
 365		} else if (ATH6KL_USB_IS_INT_EP(endpoint->bmAttributes)) {
 366			if (ATH6KL_USB_IS_DIR_IN(pipe->ep_address)) {
 367				pipe->usb_pipe_handle =
 368				    usb_rcvintpipe(ar_usb->udev,
 369						   pipe->ep_address);
 370			} else {
 371				pipe->usb_pipe_handle =
 372				    usb_sndintpipe(ar_usb->udev,
 373						   pipe->ep_address);
 374			}
 375		} else if (ATH6KL_USB_IS_ISOC_EP(endpoint->bmAttributes)) {
 376			/* TODO for ISO */
 377			if (ATH6KL_USB_IS_DIR_IN(pipe->ep_address)) {
 378				pipe->usb_pipe_handle =
 379				    usb_rcvisocpipe(ar_usb->udev,
 380						    pipe->ep_address);
 381			} else {
 382				pipe->usb_pipe_handle =
 383				    usb_sndisocpipe(ar_usb->udev,
 384						    pipe->ep_address);
 385			}
 386		}
 387
 388		pipe->ep_desc = endpoint;
 389
 390		if (!ATH6KL_USB_IS_DIR_IN(pipe->ep_address))
 391			pipe->flags |= ATH6KL_USB_PIPE_FLAG_TX;
 392
 393		status = ath6kl_usb_alloc_pipe_resources(pipe, urbcount);
 394		if (status != 0)
 395			break;
 396	}
 397
 398	return status;
 399}
 400
 401/* pipe operations */
 402static void ath6kl_usb_post_recv_transfers(struct ath6kl_usb_pipe *recv_pipe,
 403					   int buffer_length)
 404{
 405	struct ath6kl_urb_context *urb_context;
 406	struct urb *urb;
 407	int usb_status;
 408
 409	while (true) {
 410		urb_context = ath6kl_usb_alloc_urb_from_pipe(recv_pipe);
 411		if (urb_context == NULL)
 412			break;
 413
 414		urb_context->skb = dev_alloc_skb(buffer_length);
 415		if (urb_context->skb == NULL)
 416			goto err_cleanup_urb;
 417
 418		urb = usb_alloc_urb(0, GFP_ATOMIC);
 419		if (urb == NULL)
 420			goto err_cleanup_urb;
 421
 422		usb_fill_bulk_urb(urb,
 423				  recv_pipe->ar_usb->udev,
 424				  recv_pipe->usb_pipe_handle,
 425				  urb_context->skb->data,
 426				  buffer_length,
 427				  ath6kl_usb_recv_complete, urb_context);
 428
 429		ath6kl_dbg(ATH6KL_DBG_USB_BULK,
 430			   "ath6kl usb: bulk recv submit:%d, 0x%X (ep:0x%2.2X), %d bytes buf:0x%p\n",
 431			   recv_pipe->logical_pipe_num,
 432			   recv_pipe->usb_pipe_handle, recv_pipe->ep_address,
 433			   buffer_length, urb_context->skb);
 434
 435		usb_anchor_urb(urb, &recv_pipe->urb_submitted);
 436		usb_status = usb_submit_urb(urb, GFP_ATOMIC);
 437
 438		if (usb_status) {
 439			ath6kl_dbg(ATH6KL_DBG_USB_BULK,
 440				   "ath6kl usb : usb bulk recv failed %d\n",
 441				   usb_status);
 442			usb_unanchor_urb(urb);
 443			usb_free_urb(urb);
 444			goto err_cleanup_urb;
 445		}
 446		usb_free_urb(urb);
 447	}
 448	return;
 449
 450err_cleanup_urb:
 451	ath6kl_usb_cleanup_recv_urb(urb_context);
 452	return;
 453}
 454
 455static void ath6kl_usb_flush_all(struct ath6kl_usb *ar_usb)
 456{
 457	int i;
 458
 459	for (i = 0; i < ATH6KL_USB_PIPE_MAX; i++) {
 460		if (ar_usb->pipes[i].ar_usb != NULL)
 461			usb_kill_anchored_urbs(&ar_usb->pipes[i].urb_submitted);
 462	}
 463
 464	/*
 465	 * Flushing any pending I/O may schedule work this call will block
 466	 * until all scheduled work runs to completion.
 467	 */
 468	flush_scheduled_work();
 469}
 470
 471static void ath6kl_usb_start_recv_pipes(struct ath6kl_usb *ar_usb)
 472{
 473	/*
 474	 * note: control pipe is no longer used
 475	 * ar_usb->pipes[ATH6KL_USB_PIPE_RX_CTRL].urb_cnt_thresh =
 476	 *      ar_usb->pipes[ATH6KL_USB_PIPE_RX_CTRL].urb_alloc/2;
 477	 * ath6kl_usb_post_recv_transfers(&ar_usb->
 478	 *		pipes[ATH6KL_USB_PIPE_RX_CTRL],
 479	 *		ATH6KL_USB_RX_BUFFER_SIZE);
 480	 */
 481
 482	ar_usb->pipes[ATH6KL_USB_PIPE_RX_DATA].urb_cnt_thresh = 1;
 483
 484	ath6kl_usb_post_recv_transfers(&ar_usb->pipes[ATH6KL_USB_PIPE_RX_DATA],
 485				       ATH6KL_USB_RX_BUFFER_SIZE);
 486}
 487
 488/* hif usb rx/tx completion functions */
 489static void ath6kl_usb_recv_complete(struct urb *urb)
 490{
 491	struct ath6kl_urb_context *urb_context = urb->context;
 492	struct ath6kl_usb_pipe *pipe = urb_context->pipe;
 493	struct sk_buff *skb = NULL;
 494	int status = 0;
 495
 496	ath6kl_dbg(ATH6KL_DBG_USB_BULK,
 497		   "%s: recv pipe: %d, stat:%d, len:%d urb:0x%p\n", __func__,
 498		   pipe->logical_pipe_num, urb->status, urb->actual_length,
 499		   urb);
 500
 501	if (urb->status != 0) {
 502		status = -EIO;
 503		switch (urb->status) {
 504		case -ECONNRESET:
 505		case -ENOENT:
 506		case -ESHUTDOWN:
 507			/*
 508			 * no need to spew these errors when device
 509			 * removed or urb killed due to driver shutdown
 510			 */
 511			status = -ECANCELED;
 512			break;
 513		default:
 514			ath6kl_dbg(ATH6KL_DBG_USB_BULK,
 515				   "%s recv pipe: %d (ep:0x%2.2X), failed:%d\n",
 516				   __func__, pipe->logical_pipe_num,
 517				   pipe->ep_address, urb->status);
 518			break;
 519		}
 520		goto cleanup_recv_urb;
 521	}
 522
 523	if (urb->actual_length == 0)
 524		goto cleanup_recv_urb;
 525
 526	skb = urb_context->skb;
 527
 528	/* we are going to pass it up */
 529	urb_context->skb = NULL;
 530	skb_put(skb, urb->actual_length);
 531
 532	/* note: queue implements a lock */
 533	skb_queue_tail(&pipe->io_comp_queue, skb);
 534	schedule_work(&pipe->io_complete_work);
 535
 536cleanup_recv_urb:
 537	ath6kl_usb_cleanup_recv_urb(urb_context);
 538
 539	if (status == 0 &&
 540	    pipe->urb_cnt >= pipe->urb_cnt_thresh) {
 541		/* our free urbs are piling up, post more transfers */
 542		ath6kl_usb_post_recv_transfers(pipe, ATH6KL_USB_RX_BUFFER_SIZE);
 543	}
 544}
 545
 546static void ath6kl_usb_usb_transmit_complete(struct urb *urb)
 547{
 548	struct ath6kl_urb_context *urb_context = urb->context;
 549	struct ath6kl_usb_pipe *pipe = urb_context->pipe;
 550	struct sk_buff *skb;
 551
 552	ath6kl_dbg(ATH6KL_DBG_USB_BULK,
 553		   "%s: pipe: %d, stat:%d, len:%d\n",
 554		   __func__, pipe->logical_pipe_num, urb->status,
 555		   urb->actual_length);
 556
 557	if (urb->status != 0) {
 558		ath6kl_dbg(ATH6KL_DBG_USB_BULK,
 559			   "%s:  pipe: %d, failed:%d\n",
 560			   __func__, pipe->logical_pipe_num, urb->status);
 561	}
 562
 563	skb = urb_context->skb;
 564	urb_context->skb = NULL;
 565	ath6kl_usb_free_urb_to_pipe(urb_context->pipe, urb_context);
 566
 567	/* note: queue implements a lock */
 568	skb_queue_tail(&pipe->io_comp_queue, skb);
 569	schedule_work(&pipe->io_complete_work);
 570}
 571
 572static void ath6kl_usb_io_comp_work(struct work_struct *work)
 573{
 574	struct ath6kl_usb_pipe *pipe = container_of(work,
 575						    struct ath6kl_usb_pipe,
 576						    io_complete_work);
 577	struct ath6kl_usb *ar_usb;
 578	struct sk_buff *skb;
 579
 580	ar_usb = pipe->ar_usb;
 581
 582	while ((skb = skb_dequeue(&pipe->io_comp_queue))) {
 583		if (pipe->flags & ATH6KL_USB_PIPE_FLAG_TX) {
 584			ath6kl_dbg(ATH6KL_DBG_USB_BULK,
 585				   "ath6kl usb xmit callback buf:0x%p\n", skb);
 586			ath6kl_core_tx_complete(ar_usb->ar, skb);
 587		} else {
 588			ath6kl_dbg(ATH6KL_DBG_USB_BULK,
 589				   "ath6kl usb recv callback buf:0x%p\n", skb);
 590			ath6kl_core_rx_complete(ar_usb->ar, skb,
 591						pipe->logical_pipe_num);
 592		}
 593	}
 594}
 595
 596#define ATH6KL_USB_MAX_DIAG_CMD (sizeof(struct ath6kl_usb_ctrl_diag_cmd_write))
 597#define ATH6KL_USB_MAX_DIAG_RESP (sizeof(struct ath6kl_usb_ctrl_diag_resp_read))
 598
 599static void ath6kl_usb_destroy(struct ath6kl_usb *ar_usb)
 600{
 601	ath6kl_usb_flush_all(ar_usb);
 602
 603	ath6kl_usb_cleanup_pipe_resources(ar_usb);
 604
 605	usb_set_intfdata(ar_usb->interface, NULL);
 606
 607	kfree(ar_usb->diag_cmd_buffer);
 608	kfree(ar_usb->diag_resp_buffer);
 609
 610	kfree(ar_usb);
 611}
 612
 613static struct ath6kl_usb *ath6kl_usb_create(struct usb_interface *interface)
 614{
 615	struct usb_device *dev = interface_to_usbdev(interface);
 616	struct ath6kl_usb *ar_usb;
 617	struct ath6kl_usb_pipe *pipe;
 618	int status = 0;
 619	int i;
 620
 621	ar_usb = kzalloc(sizeof(struct ath6kl_usb), GFP_KERNEL);
 622	if (ar_usb == NULL)
 623		goto fail_ath6kl_usb_create;
 624
 625	usb_set_intfdata(interface, ar_usb);
 626	spin_lock_init(&(ar_usb->cs_lock));
 627	ar_usb->udev = dev;
 628	ar_usb->interface = interface;
 629
 630	for (i = 0; i < ATH6KL_USB_PIPE_MAX; i++) {
 631		pipe = &ar_usb->pipes[i];
 632		INIT_WORK(&pipe->io_complete_work,
 633			  ath6kl_usb_io_comp_work);
 634		skb_queue_head_init(&pipe->io_comp_queue);
 635	}
 636
 637	ar_usb->diag_cmd_buffer = kzalloc(ATH6KL_USB_MAX_DIAG_CMD, GFP_KERNEL);
 638	if (ar_usb->diag_cmd_buffer == NULL) {
 639		status = -ENOMEM;
 640		goto fail_ath6kl_usb_create;
 641	}
 642
 643	ar_usb->diag_resp_buffer = kzalloc(ATH6KL_USB_MAX_DIAG_RESP,
 644					   GFP_KERNEL);
 645	if (ar_usb->diag_resp_buffer == NULL) {
 646		status = -ENOMEM;
 647		goto fail_ath6kl_usb_create;
 648	}
 649
 650	status = ath6kl_usb_setup_pipe_resources(ar_usb);
 651
 652fail_ath6kl_usb_create:
 653	if (status != 0) {
 654		ath6kl_usb_destroy(ar_usb);
 655		ar_usb = NULL;
 656	}
 657	return ar_usb;
 658}
 659
 660static void ath6kl_usb_device_detached(struct usb_interface *interface)
 661{
 662	struct ath6kl_usb *ar_usb;
 663
 664	ar_usb = usb_get_intfdata(interface);
 665	if (ar_usb == NULL)
 666		return;
 667
 668	ath6kl_stop_txrx(ar_usb->ar);
 669
 670	/* Delay to wait for the target to reboot */
 671	mdelay(20);
 672	ath6kl_core_cleanup(ar_usb->ar);
 673	ath6kl_usb_destroy(ar_usb);
 674}
 675
 676/* exported hif usb APIs for htc pipe */
 677static void hif_start(struct ath6kl *ar)
 678{
 679	struct ath6kl_usb *device = ath6kl_usb_priv(ar);
 680	int i;
 681
 682	ath6kl_usb_start_recv_pipes(device);
 683
 684	/* set the TX resource avail threshold for each TX pipe */
 685	for (i = ATH6KL_USB_PIPE_TX_CTRL;
 686	     i <= ATH6KL_USB_PIPE_TX_DATA_HP; i++) {
 687		device->pipes[i].urb_cnt_thresh =
 688		    device->pipes[i].urb_alloc / 2;
 689	}
 690}
 691
 692static int ath6kl_usb_send(struct ath6kl *ar, u8 PipeID,
 693			   struct sk_buff *hdr_skb, struct sk_buff *skb)
 694{
 695	struct ath6kl_usb *device = ath6kl_usb_priv(ar);
 696	struct ath6kl_usb_pipe *pipe = &device->pipes[PipeID];
 697	struct ath6kl_urb_context *urb_context;
 698	int usb_status, status = 0;
 699	struct urb *urb;
 700	u8 *data;
 701	u32 len;
 702
 703	ath6kl_dbg(ATH6KL_DBG_USB_BULK, "+%s pipe : %d, buf:0x%p\n",
 704		   __func__, PipeID, skb);
 705
 706	urb_context = ath6kl_usb_alloc_urb_from_pipe(pipe);
 707
 708	if (urb_context == NULL) {
 709		/*
 710		 * TODO: it is possible to run out of urbs if
 711		 * 2 endpoints map to the same pipe ID
 712		 */
 713		ath6kl_dbg(ATH6KL_DBG_USB_BULK,
 714			   "%s pipe:%d no urbs left. URB Cnt : %d\n",
 715			   __func__, PipeID, pipe->urb_cnt);
 716		status = -ENOMEM;
 717		goto fail_hif_send;
 718	}
 719
 720	urb_context->skb = skb;
 721
 722	data = skb->data;
 723	len = skb->len;
 724
 725	urb = usb_alloc_urb(0, GFP_ATOMIC);
 726	if (urb == NULL) {
 727		status = -ENOMEM;
 728		ath6kl_usb_free_urb_to_pipe(urb_context->pipe,
 729					    urb_context);
 730		goto fail_hif_send;
 731	}
 732
 733	usb_fill_bulk_urb(urb,
 734			  device->udev,
 735			  pipe->usb_pipe_handle,
 736			  data,
 737			  len,
 738			  ath6kl_usb_usb_transmit_complete, urb_context);
 739
 740	if ((len % pipe->max_packet_size) == 0) {
 741		/* hit a max packet boundary on this pipe */
 742		urb->transfer_flags |= URB_ZERO_PACKET;
 743	}
 744
 745	ath6kl_dbg(ATH6KL_DBG_USB_BULK,
 746		   "athusb bulk send submit:%d, 0x%X (ep:0x%2.2X), %d bytes\n",
 747		   pipe->logical_pipe_num, pipe->usb_pipe_handle,
 748		   pipe->ep_address, len);
 749
 750	usb_anchor_urb(urb, &pipe->urb_submitted);
 751	usb_status = usb_submit_urb(urb, GFP_ATOMIC);
 752
 753	if (usb_status) {
 754		ath6kl_dbg(ATH6KL_DBG_USB_BULK,
 755			   "ath6kl usb : usb bulk transmit failed %d\n",
 756			   usb_status);
 757		usb_unanchor_urb(urb);
 758		ath6kl_usb_free_urb_to_pipe(urb_context->pipe,
 759					    urb_context);
 760		status = -EINVAL;
 761	}
 762	usb_free_urb(urb);
 763
 764fail_hif_send:
 765	return status;
 766}
 767
 768static void hif_stop(struct ath6kl *ar)
 769{
 770	struct ath6kl_usb *device = ath6kl_usb_priv(ar);
 771
 772	ath6kl_usb_flush_all(device);
 773}
 774
 775static void ath6kl_usb_get_default_pipe(struct ath6kl *ar,
 776					u8 *ul_pipe, u8 *dl_pipe)
 777{
 778	*ul_pipe = ATH6KL_USB_PIPE_TX_CTRL;
 779	*dl_pipe = ATH6KL_USB_PIPE_RX_CTRL;
 780}
 781
 782static int ath6kl_usb_map_service_pipe(struct ath6kl *ar, u16 svc_id,
 783				       u8 *ul_pipe, u8 *dl_pipe)
 784{
 785	int status = 0;
 786
 787	switch (svc_id) {
 788	case HTC_CTRL_RSVD_SVC:
 789	case WMI_CONTROL_SVC:
 790		*ul_pipe = ATH6KL_USB_PIPE_TX_CTRL;
 791		/* due to large control packets, shift to data pipe */
 792		*dl_pipe = ATH6KL_USB_PIPE_RX_DATA;
 793		break;
 794	case WMI_DATA_BE_SVC:
 795	case WMI_DATA_BK_SVC:
 796		*ul_pipe = ATH6KL_USB_PIPE_TX_DATA_LP;
 797		/*
 798		* Disable rxdata2 directly, it will be enabled
 799		* if FW enable rxdata2
 800		*/
 801		*dl_pipe = ATH6KL_USB_PIPE_RX_DATA;
 802		break;
 803	case WMI_DATA_VI_SVC:
 804
 805		if (test_bit(ATH6KL_FW_CAPABILITY_MAP_LP_ENDPOINT,
 806			     ar->fw_capabilities))
 807			*ul_pipe = ATH6KL_USB_PIPE_TX_DATA_LP;
 808		else
 809			*ul_pipe = ATH6KL_USB_PIPE_TX_DATA_MP;
 810		/*
 811		* Disable rxdata2 directly, it will be enabled
 812		* if FW enable rxdata2
 813		*/
 814		*dl_pipe = ATH6KL_USB_PIPE_RX_DATA;
 815		break;
 816	case WMI_DATA_VO_SVC:
 817
 818		if (test_bit(ATH6KL_FW_CAPABILITY_MAP_LP_ENDPOINT,
 819			     ar->fw_capabilities))
 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
1196#else
1197
1198#define ath6kl_usb_pm_suspend NULL
1199#define ath6kl_usb_pm_resume NULL
1200
1201#endif
1202
1203/* table of devices that work with this driver */
1204static struct usb_device_id ath6kl_usb_ids[] = {
1205	{USB_DEVICE(0x0cf3, 0x9375)},
1206	{USB_DEVICE(0x0cf3, 0x9374)},
1207	{ /* Terminating entry */ },
1208};
1209
1210MODULE_DEVICE_TABLE(usb, ath6kl_usb_ids);
1211
1212static struct usb_driver ath6kl_usb_driver = {
1213	.name = "ath6kl_usb",
1214	.probe = ath6kl_usb_probe,
1215	.suspend = ath6kl_usb_pm_suspend,
1216	.resume = ath6kl_usb_pm_resume,
1217	.disconnect = ath6kl_usb_remove,
1218	.id_table = ath6kl_usb_ids,
1219	.supports_autosuspend = true,
1220	.disable_hub_initiated_lpm = 1,
1221};
1222
1223module_usb_driver(ath6kl_usb_driver);
1224
1225MODULE_AUTHOR("Atheros Communications, Inc.");
1226MODULE_DESCRIPTION("Driver support for Atheros AR600x USB devices");
1227MODULE_LICENSE("Dual BSD/GPL");
1228MODULE_FIRMWARE(AR6004_HW_1_0_FIRMWARE_FILE);
1229MODULE_FIRMWARE(AR6004_HW_1_0_BOARD_DATA_FILE);
1230MODULE_FIRMWARE(AR6004_HW_1_0_DEFAULT_BOARD_DATA_FILE);
1231MODULE_FIRMWARE(AR6004_HW_1_1_FIRMWARE_FILE);
1232MODULE_FIRMWARE(AR6004_HW_1_1_BOARD_DATA_FILE);
1233MODULE_FIRMWARE(AR6004_HW_1_1_DEFAULT_BOARD_DATA_FILE);
1234MODULE_FIRMWARE(AR6004_HW_1_2_FIRMWARE_FILE);
1235MODULE_FIRMWARE(AR6004_HW_1_2_BOARD_DATA_FILE);
1236MODULE_FIRMWARE(AR6004_HW_1_2_DEFAULT_BOARD_DATA_FILE);
1237MODULE_FIRMWARE(AR6004_HW_1_3_FW_DIR "/" AR6004_HW_1_3_FIRMWARE_FILE);
1238MODULE_FIRMWARE(AR6004_HW_1_3_BOARD_DATA_FILE);
1239MODULE_FIRMWARE(AR6004_HW_1_3_DEFAULT_BOARD_DATA_FILE);