blob: 93459cadc472f75dee6c3ff52f4409ba992e6d8e [file] [log] [blame]
/*
* Copyright (c) 2007-2008 Atheros Communications Inc.
*
* Permission to use, copy, modify, and/or distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies.
*
* THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
* ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
* OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
/* */
/* Module Name : wrap_usb.c */
/* */
/* Abstract */
/* This module contains wrapper functions for USB management */
/* */
/* NOTES */
/* Platform dependent. */
/* */
/************************************************************************/
#include "oal_dt.h"
#include "usbdrv.h"
#include <linux/netlink.h>
#include <linux/slab.h>
#include <net/iw_handler.h>
extern void zfLnxInitUsbTxQ(zdev_t *dev);
extern void zfLnxInitUsbRxQ(zdev_t *dev);
extern u32_t zfLnxSubmitRegInUrb(zdev_t *dev);
u32_t zfLnxUsbOut(zdev_t *dev, u8_t *hdr, u16_t hdrlen, u8_t *snap,
u16_t snapLen, u8_t *tail, u16_t tailLen, zbuf_t *buf,
u16_t offset);
u32_t zfLnxUsbWriteReg(zdev_t *dev, u32_t *cmd, u16_t cmdLen);
void zfwUsbRegisterCallBack(zdev_t *dev, struct zfCbUsbFuncTbl *zfUsbFunc)
{
struct usbdrv_private *macp = dev->ml_priv;
macp->usbCbFunctions.zfcbUsbRecv = zfUsbFunc->zfcbUsbRecv;
macp->usbCbFunctions.zfcbUsbRegIn = zfUsbFunc->zfcbUsbRegIn;
macp->usbCbFunctions.zfcbUsbOutComplete = zfUsbFunc->zfcbUsbOutComplete;
return;
}
u32_t zfwUsbGetFreeTxQSize(zdev_t *dev)
{
struct usbdrv_private *macp = dev->ml_priv;
u32_t freeTxQSize;
unsigned long irqFlag;
/* zmw_declare_for_critical_section(); */
/* zmw_enter_critical_section(dev); */
spin_lock_irqsave(&macp->cs_lock, irqFlag);
freeTxQSize = ZM_MAX_TX_BUF_NUM - macp->TxBufCnt;
/* zmw_leave_critical_section(dev); */
spin_unlock_irqrestore(&macp->cs_lock, irqFlag);
return freeTxQSize;
}
u32_t zfwUsbGetMaxTxQSize(zdev_t *dev)
{
return ZM_MAX_TX_BUF_NUM;
}
u32_t zfwUsbEnableIntEpt(zdev_t *dev, u8_t endpt)
{
/* Initialize USB TxQ */
zfLnxInitUsbTxQ(dev);
/* Initialize USB RxQ */
zfLnxInitUsbRxQ(dev);
/* Initialize USB Register In URB */
/* zfwUsbSubmitRegIn(dev); */
/* Initialize USB Register In URB */
zfLnxSubmitRegInUrb(dev);
return 0;
}
int zfwUsbEnableRxEpt(zdev_t *dev, u8_t endpt)
{
return 0;
}
u32_t zfwUsbSubmitControl(zdev_t *dev, u8_t req, u16_t value, u16_t index,
void *data, u32_t size)
{
int result = 0;
u32_t ret = 0;
struct usbdrv_private *macp = dev->ml_priv;
u8_t *buf;
if (size > 0) {
buf = kmalloc(size, GFP_KERNEL);
memcpy(buf, (u8_t *)data, size);
} else
buf = NULL;
#if 0
printk(KERN_ERR "req = 0x%02x\n", req);
printk(KERN_ERR "value = 0x%04x\n", value);
printk(KERN_ERR "index = 0x%04x\n", index);
printk(KERN_ERR "data = 0x%lx\n", (u32_t) data);
printk(KERN_ERR "size = %ld\n", size);
#endif
result = usb_control_msg(macp->udev, usb_sndctrlpipe(macp->udev, 0),
req, USB_DIR_OUT | 0x40, value, index, buf, size, HZ);
if (result < 0) {
printk(KERN_ERR "zfwUsbSubmitControl() failed, result = 0x%x\n",
result);
ret = 1;
}
kfree(buf);
return ret;
}
void zfwUsbCmd(zdev_t *dev, u8_t endpt, u32_t *cmd, u16_t cmdLen)
{
struct usbdrv_private *macp = dev->ml_priv;
u32_t ret;
/* MPUsbCommand(dev, endpt, cmd, cmdLen); */
ret = zfLnxUsbWriteReg(dev, cmd, cmdLen);
/*
* if zfLnxUsbWriteReg() return error, free and allocate urb,
* resend again
*/
if (ret != 0) {
usb_free_urb(macp->RegOutUrb);
macp->RegOutUrb = usb_alloc_urb(0, GFP_ATOMIC);
ret = zfLnxUsbWriteReg(dev, cmd, cmdLen);
}
}
u32_t zfwUsbSend(zdev_t *dev, u8_t endpt, u8_t *hdr, u16_t hdrlen, u8_t *snap,
u16_t snapLen, u8_t *tail, u16_t tailLen,
zbuf_t *buf, u16_t offset)
{
u32_t status;
#ifdef ZM_CONFIG_BIG_ENDIAN
u32_t ii = 0;
u16_t *pc = NULL;
pc = (u16_t *)hdr;
for (ii = 0; ii < (hdrlen >> 1); ii++)
pc[ii] = cpu_to_le16(pc[ii]);
pc = (u16_t *)snap;
for (ii = 0; ii < (snapLen >> 1); ii++)
pc[ii] = cpu_to_le16(pc[ii]);
pc = (u16_t *)tail;
for (ii = 0; ii < (tailLen>>1); ii++)
pc[ii] = cpu_to_le16(pc[ii]);
#endif
status = zfLnxUsbOut(dev, hdr, hdrlen, snap, snapLen, tail, tailLen,
buf, offset);
if (status == 0)
return 0;
else
return 1;
}
/* Leave an empty line below to remove warning message on some compiler */