Пример #1
0
static int new_usb_control_msg2(struct usb_ctrlrequest *dr, struct urb *urb, struct usb_device *dev, unsigned int pipe, __u8 request, __u8 requesttype,
			 __u16 value, __u16 index, void *data, __u16 size, int timeout)
{
	static volatile int done=1;
	unsigned long expire;
	int status;
	int retval;

	if(done==0) {
		//printk("%s, %d, done=%d, busy!\n", __func__, __LINE__, done);
		return -EBUSY;
	}
	
	dr->bRequestType= requesttype;
	dr->bRequest = request;
	dr->wValue = cpu_to_le16p(&value);
	dr->wIndex = cpu_to_le16p(&index);
	dr->wLength = cpu_to_le16p(&size);
	
  	done = 0;
  	
	usb_fill_control_urb(urb, dev, pipe, (unsigned char *)dr, data,
			     size, new_usb_api_blocking_completion, (void *)&done);
	dma_cache_wback_inv((unsigned long)data, size);
	urb->actual_length = 0;
	urb->status = 0;
	
	status = usb_submit_urb(urb, GFP_ATOMIC);
	
	return status;
}
Пример #2
0
/* Send a generic nonblocking control request, without completion notification.
 * This is safe for use in interrupt context.
 */
static void rwand_nb_request(struct rwand_dev *dev, unsigned short request,
			  unsigned short wValue, unsigned short wIndex)
{
	int retval;
	struct urb *urb;
	struct usb_ctrlrequest *dr = kmalloc(sizeof(struct usb_ctrlrequest), GFP_ATOMIC);
	if (!dr) {
		err("Out of memory in rwand_nb_request");
		return;
	}

	dr->bRequestType = USB_TYPE_VENDOR;
	dr->bRequest = request;
	dr->wValue = cpu_to_le16p(&wValue);
	dr->wIndex = cpu_to_le16p(&wIndex);
	dr->wLength = 0;

	urb = usb_alloc_urb(0, GFP_ATOMIC);
	if (!urb) {
		kfree(dr);
		err("Out of memory in rwand_nb_request");
		return;
	}

	usb_fill_control_urb(urb, dev->udev, usb_sndctrlpipe(dev->udev, 0),
			     (unsigned char*)dr, NULL, 0,
			     rwand_nb_irq, dr);

	retval = usb_submit_urb(urb, GFP_ATOMIC);
	if (retval) {
		dbg("Error in rwand_nb_request, retval=%d", retval);
	}
}
Пример #3
0
int PIPEnsControlOut(
     PSDevice     pDevice,
     BYTE         byRequest,
     WORD         wValue,
     WORD         wIndex,
     WORD         wLength,
     PBYTE        pbyBuffer
    )
{
	int ntStatus = 0;
    int ii;

    if (pDevice->Flags & fMP_DISCONNECTED)
        return STATUS_FAILURE;

    if (pDevice->Flags & fMP_CONTROL_WRITES)
        return STATUS_FAILURE;

	pDevice->sUsbCtlRequest.bRequestType = 0x40;
	pDevice->sUsbCtlRequest.bRequest = byRequest;
	pDevice->sUsbCtlRequest.wValue = cpu_to_le16p(&wValue);
	pDevice->sUsbCtlRequest.wIndex = cpu_to_le16p(&wIndex);
	pDevice->sUsbCtlRequest.wLength = cpu_to_le16p(&wLength);
	pDevice->pControlURB->transfer_flags |= URB_ASYNC_UNLINK;
    pDevice->pControlURB->actual_length = 0;
    // Notice, pbyBuffer limited point to variable buffer, can't be constant.
  	usb_fill_control_urb(pDevice->pControlURB, pDevice->usb,
			 usb_sndctrlpipe(pDevice->usb , 0), (char *) &pDevice->sUsbCtlRequest,
			 pbyBuffer, wLength, s_nsControlInUsbIoCompleteWrite, pDevice);

	ntStatus = usb_submit_urb(pDevice->pControlURB, GFP_ATOMIC);
	if (ntStatus != 0) {
		DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO"control send request submission failed: %d\n", ntStatus);
		return STATUS_FAILURE;
	}
	else {
	    MP_SET_FLAG(pDevice, fMP_CONTROL_WRITES);
	}
	spin_unlock_irq(&pDevice->lock);
    for (ii = 0; ii <= USB_CTL_WAIT; ii ++) {

	if (pDevice->Flags & fMP_CONTROL_WRITES)
		mdelay(1);
        else
		break;

        if (ii >= USB_CTL_WAIT) {
		DBG_PRT(MSG_LEVEL_DEBUG,
			KERN_INFO "control send request submission timeout\n");
            spin_lock_irq(&pDevice->lock);
            MP_CLEAR_FLAG(pDevice, fMP_CONTROL_WRITES);
            return STATUS_FAILURE;
        }
    }
	spin_lock_irq(&pDevice->lock);

    return STATUS_SUCCESS;
}
Пример #4
0
int PIPEnsControlIn(struct vnt_private *pDevice, u8 byRequest, u16 wValue,
	u16 wIndex, u16 wLength,  u8 *pbyBuffer)
{
	int ntStatus = 0;
	int ii;

    if (pDevice->Flags & fMP_DISCONNECTED)
        return STATUS_FAILURE;

    if (pDevice->Flags & fMP_CONTROL_READS)
	return STATUS_FAILURE;

	if (pDevice->Flags & fMP_CONTROL_WRITES)
		return STATUS_FAILURE;

	MP_SET_FLAG(pDevice, fMP_CONTROL_READS);

	pDevice->sUsbCtlRequest.bRequestType = 0xC0;
	pDevice->sUsbCtlRequest.bRequest = byRequest;
	pDevice->sUsbCtlRequest.wValue = cpu_to_le16p(&wValue);
	pDevice->sUsbCtlRequest.wIndex = cpu_to_le16p(&wIndex);
	pDevice->sUsbCtlRequest.wLength = cpu_to_le16p(&wLength);
	pDevice->pControlURB->transfer_flags |= URB_ASYNC_UNLINK;
    pDevice->pControlURB->actual_length = 0;
	usb_fill_control_urb(pDevice->pControlURB, pDevice->usb,
			 usb_rcvctrlpipe(pDevice->usb , 0), (char *) &pDevice->sUsbCtlRequest,
			 pbyBuffer, wLength, s_nsControlInUsbIoCompleteRead, pDevice);

	ntStatus = usb_submit_urb(pDevice->pControlURB, GFP_ATOMIC);
	if (ntStatus != 0) {
		DBG_PRT(MSG_LEVEL_DEBUG, KERN_INFO
			"control request submission failed: %d\n", ntStatus);
		MP_CLEAR_FLAG(pDevice, fMP_CONTROL_READS);
		return STATUS_FAILURE;
	}

	spin_unlock_irq(&pDevice->lock);
    for (ii = 0; ii <= USB_CTL_WAIT; ii ++) {

	if (pDevice->Flags & fMP_CONTROL_READS)
		mdelay(1);
	else
		break;

	if (ii >= USB_CTL_WAIT) {
		DBG_PRT(MSG_LEVEL_DEBUG,
			KERN_INFO "control rcv request submission timeout\n");
            spin_lock_irq(&pDevice->lock);
            MP_CLEAR_FLAG(pDevice, fMP_CONTROL_READS);
            return STATUS_FAILURE;
        }
    }
	spin_lock_irq(&pDevice->lock);

    return ntStatus;
}
Пример #5
0
static int set_registers(pegasus_t * pegasus, __u16 indx, __u16 size,
			 void *data)
{
	int ret;
	char *buffer;
	DECLARE_WAITQUEUE(wait, current);

	buffer = kmalloc(size, GFP_KERNEL);
	if (!buffer) {
		warn("%s: looks like we're out of memory", __FUNCTION__);
		return -ENOMEM;
	}
	memcpy(buffer, data, size);

	add_wait_queue(&pegasus->ctrl_wait, &wait);
	set_current_state(TASK_UNINTERRUPTIBLE);
	while (pegasus->flags & ETH_REGS_CHANGED)
		schedule();
	remove_wait_queue(&pegasus->ctrl_wait, &wait);
	set_current_state(TASK_RUNNING);

	pegasus->dr.bRequestType = PEGASUS_REQT_WRITE;
	pegasus->dr.bRequest = PEGASUS_REQ_SET_REGS;
	pegasus->dr.wValue = cpu_to_le16(0);
	pegasus->dr.wIndex = cpu_to_le16p(&indx);
	pegasus->dr.wLength = cpu_to_le16p(&size);
	pegasus->ctrl_urb->transfer_buffer_length = size;

	usb_fill_control_urb(pegasus->ctrl_urb, pegasus->usb,
			     usb_sndctrlpipe(pegasus->usb, 0),
			     (char *) &pegasus->dr,
			     buffer, size, ctrl_callback, pegasus);

	add_wait_queue(&pegasus->ctrl_wait, &wait);
	set_current_state(TASK_UNINTERRUPTIBLE);

	if ((ret = usb_submit_urb(pegasus->ctrl_urb, GFP_ATOMIC))) {
		err("%s: BAD CTRL %d", __FUNCTION__, ret);
		goto out;
	}

	schedule();
out:
	remove_wait_queue(&pegasus->ctrl_wait, &wait);
	kfree(buffer);

	return ret;
}
Пример #6
0
static int
brcmf_usb_send_ctl(struct brcmf_usbdev_info *devinfo, u8 *buf, int len)
{
	int ret;
	u16 size;

	brcmf_dbg(USB, "Enter\n");
	if (devinfo == NULL || buf == NULL ||
	    len == 0 || devinfo->ctl_urb == NULL)
		return -EINVAL;

	size = len;
	devinfo->ctl_write.wLength = cpu_to_le16p(&size);
	devinfo->ctl_urb->transfer_buffer_length = size;
	devinfo->ctl_urb_status = 0;
	devinfo->ctl_urb_actual_length = 0;

	usb_fill_control_urb(devinfo->ctl_urb,
		devinfo->usbdev,
		devinfo->ctl_out_pipe,
		(unsigned char *) &devinfo->ctl_write,
		buf, size,
		(usb_complete_t)brcmf_usb_ctlwrite_complete,
		devinfo);

	ret = usb_submit_urb(devinfo->ctl_urb, GFP_ATOMIC);
	if (ret < 0)
		brcmf_err("usb_submit_urb failed %d\n", ret);

	return ret;
}
Пример #7
0
static int
brcmf_usb_recv_ctl(struct brcmf_usbdev_info *devinfo, u8 *buf, int len)
{
	int ret;
	u16 size;

	brcmf_dbg(USB, "Enter\n");
	if ((devinfo == NULL) || (buf == NULL) || (len == 0)
		|| (devinfo->ctl_urb == NULL))
		return -EINVAL;

	size = len;
	devinfo->ctl_read.wLength = cpu_to_le16p(&size);
	devinfo->ctl_urb->transfer_buffer_length = size;

	devinfo->ctl_read.bRequestType = USB_DIR_IN
		| USB_TYPE_CLASS | USB_RECIP_INTERFACE;
	devinfo->ctl_read.bRequest = 1;

	usb_fill_control_urb(devinfo->ctl_urb,
		devinfo->usbdev,
		devinfo->ctl_in_pipe,
		(unsigned char *) &devinfo->ctl_read,
		buf, size,
		(usb_complete_t)brcmf_usb_ctlread_complete,
		devinfo);

	ret = usb_submit_urb(devinfo->ctl_urb, GFP_ATOMIC);
	if (ret < 0)
		brcmf_err("usb_submit_urb failed %d\n", ret);

	return ret;
}
Пример #8
0
static inline void get_node_id(pegasus_t * pegasus, __u8 * id)
{
	int i;
	__u16 w16;

	for (i = 0; i < 3; i++) {
		read_eprom_word(pegasus, i, &w16);
		((__u16 *) id)[i] = cpu_to_le16p(&w16);
	}
}
Пример #9
0
void tdsp_usb_set_ctrlreq(void * ctrl_req,void * req)
{
    struct usb_ctrlrequest*	set_up = (struct usb_ctrlrequest*)ctrl_req;
    PTDSP_USB_CTRLREQ req_cntxt= (PTDSP_USB_CTRLREQ)req;
    if(NULL == set_up)
    {
        printk("%s: ctlr req is NULL\n",__FUNCTION__);    
    }
    if(NULL == ctrl_req)
    {
         printk("%s: input req is NULL\n",__FUNCTION__);    
    }
    set_up->bRequestType = USB_DIR_OUT | USB_TYPE_VENDOR | USB_RECIP_DEVICE;
	set_up->bRequest = req_cntxt->request;
	set_up->wValue = cpu_to_le16p(&req_cntxt->value);
	set_up->wIndex = cpu_to_le16p(&req_cntxt->index);
	set_up->wLength = cpu_to_le16p((unsigned short *)&req_cntxt->len);
    
}
Пример #10
0
/**
 *	usb_control_msg - Builds a control urb, sends it off and waits for completion
 *	@dev: pointer to the usb device to send the message to
 *	@pipe: endpoint "pipe" to send the message to
 *	@request: USB message request value
 *	@requesttype: USB message request type value
 *	@value: USB message value
 *	@index: USB message index value
 *	@data: pointer to the data to send
 *	@size: length in bytes of the data to send
 *	@timeout: time in jiffies to wait for the message to complete before
 *		timing out (if 0 the wait is forever)
 *	Context: !in_interrupt ()
 *
 *	This function sends a simple control message to a specified endpoint
 *	and waits for the message to complete, or timeout.
 *	
 *	If successful, it returns the number of bytes transferred, otherwise a negative error number.
 *
 *	Don't use this function from within an interrupt context, like a
 *	bottom half handler.  If you need an asynchronous message, or need to send
 *	a message from within interrupt context, use usb_submit_urb()
 *      If a thread in your driver uses this call, make sure your disconnect()
 *      method can wait for it to complete.  Since you don't have a handle on
 *      the URB used, you can't cancel the request.
 */
int usb_control_msg(struct usb_device *dev, unsigned int pipe, __u8 request, __u8 requesttype,
			 __u16 value, __u16 index, void *data, __u16 size, int timeout)
{
	struct usb_ctrlrequest *dr = kmalloc(sizeof(struct usb_ctrlrequest), GFP_NOIO);
	int ret;
	
	if (!dr)
		return -ENOMEM;

	dr->bRequestType= requesttype;
	dr->bRequest = request;
	dr->wValue = cpu_to_le16p(&value);
	dr->wIndex = cpu_to_le16p(&index);
	dr->wLength = cpu_to_le16p(&size);

	//dbg("usb_control_msg");	

	ret = usb_internal_control_msg(dev, pipe, dr, data, size, timeout);

	kfree(dr);

	return ret;
}
static void usb_ctrl_msg(struct st5481_adapter *adapter,
			 u8 request, u8 requesttype, u16 value, u16 index,
			 ctrl_complete_t complete, void *context)
{
	struct st5481_ctrl *ctrl = &adapter->ctrl;
	int w_index;
	struct ctrl_msg *ctrl_msg;

	if ((w_index = fifo_add(&ctrl->msg_fifo.f)) < 0) {
		WARNING("control msg FIFO full");
		return;
	}
	ctrl_msg = &ctrl->msg_fifo.data[w_index];

	ctrl_msg->dr.bRequestType = requesttype;
	ctrl_msg->dr.bRequest = request;
	ctrl_msg->dr.wValue = cpu_to_le16p(&value);
	ctrl_msg->dr.wIndex = cpu_to_le16p(&index);
	ctrl_msg->dr.wLength = 0;
	ctrl_msg->complete = complete;
	ctrl_msg->context = context;

	usb_next_ctrl_msg(ctrl->urb, adapter);
}
Пример #12
0
static int brcmf_usb_dl_cmd(struct brcmf_usbdev_info *devinfo, u8 cmd,
			    void *buffer, int buflen)
{
	int ret;
	char *tmpbuf;
	u16 size;

	if ((!devinfo) || (devinfo->ctl_urb == NULL))
		return -EINVAL;

	tmpbuf = kmalloc(buflen, GFP_ATOMIC);
	if (!tmpbuf)
		return -ENOMEM;

	size = buflen;
	devinfo->ctl_urb->transfer_buffer_length = size;

	devinfo->ctl_read.wLength = cpu_to_le16p(&size);
	devinfo->ctl_read.bRequestType = USB_DIR_IN | USB_TYPE_VENDOR |
		USB_RECIP_INTERFACE;
	devinfo->ctl_read.bRequest = cmd;

	usb_fill_control_urb(devinfo->ctl_urb,
		devinfo->usbdev,
		usb_rcvctrlpipe(devinfo->usbdev, 0),
		(unsigned char *) &devinfo->ctl_read,
		(void *) tmpbuf, size,
		(usb_complete_t)brcmf_usb_sync_complete, devinfo);

	devinfo->ctl_completed = false;
	ret = usb_submit_urb(devinfo->ctl_urb, GFP_ATOMIC);
	if (ret < 0) {
		brcmf_err("usb_submit_urb failed %d\n", ret);
		goto finalize;
	}

	if (!brcmf_usb_ioctl_resp_wait(devinfo)) {
		usb_kill_urb(devinfo->ctl_urb);
		ret = -ETIMEDOUT;
	} else {
		memcpy(buffer, tmpbuf, buflen);
	}

finalize:
	kfree(tmpbuf);
	return ret;
}
Пример #13
0
static void
ecos_usbeth_set_rx_mode(struct net_device* net)
{
    ecos_usbeth* usbeth         = (ecos_usbeth*) net->priv;
    __u16        promiscuous    = net->flags & IFF_PROMISC;
    int          res;
    
    if (promiscuous != usbeth->target_promiscuous) {
        devrequest*     req;
        urb_t*          urb;

        urb = usb_alloc_urb(0);
        if ((urb_t*)0 == urb) {
            return;
        }
        req = kmalloc(sizeof(devrequest), GFP_KERNEL);
        if ((devrequest*)0 == req) {
            usb_free_urb(urb);
            return;
        }
        req->requesttype        = USB_TYPE_CLASS | USB_RECIP_DEVICE;
        req->request            = ECOS_USBETH_CONTROL_SET_PROMISCUOUS_MODE;
        req->value              = cpu_to_le16p(&promiscuous);
        req->index              = 0;
        req->length             = 0;

        FILL_CONTROL_URB(urb,
                         usbeth->usb_dev,
                         usb_sndctrlpipe(usbeth->usb_dev, 0),
                         (unsigned char*) req,
                         (void*) 0,
                         0,
                         &ecos_usbeth_set_rx_mode_callback,
                         (void*) usbeth);
        res = usb_submit_urb(urb);
        if (0 != res) {
            kfree(req);
            usb_free_urb(urb);
        } else {
            usbeth->target_promiscuous = promiscuous;
        }
    }
}
Пример #14
0
static bool brcmf_usb_dl_cmd(struct brcmf_usbdev_info *devinfo, u8 cmd,
                             void *buffer, int buflen)
{
    int ret = 0;
    char *tmpbuf;
    u16 size;

    if ((!devinfo) || (devinfo->ctl_urb == NULL))
        return false;

    tmpbuf = kmalloc(buflen, GFP_ATOMIC);
    if (!tmpbuf)
        return false;

    size = buflen;
    devinfo->ctl_urb->transfer_buffer_length = size;

    devinfo->ctl_read.wLength = cpu_to_le16p(&size);
    devinfo->ctl_read.bRequestType = USB_DIR_IN | USB_TYPE_VENDOR |
                                     USB_RECIP_INTERFACE;
    devinfo->ctl_read.bRequest = cmd;

    usb_fill_control_urb(devinfo->ctl_urb,
                         devinfo->usbdev,
                         usb_rcvctrlpipe(devinfo->usbdev, 0),
                         (unsigned char *) &devinfo->ctl_read,
                         (void *) tmpbuf, size,
                         (usb_complete_t)brcmf_usb_sync_complete, devinfo);

    ret = usb_submit_urb(devinfo->ctl_urb, GFP_ATOMIC);
    if (ret < 0) {
        brcmf_dbg(ERROR, "usb_submit_urb failed %d\n", ret);
        kfree(tmpbuf);
        return false;
    }

    ret = brcmf_usb_sync_wait(devinfo, BRCMF_USB_SYNC_TIMEOUT);
    memcpy(buffer, tmpbuf, buflen);
    kfree(tmpbuf);

    return (ret == 0);
}
Пример #15
0
static int write_mii_word(pegasus_t * pegasus, __u8 phy, __u8 indx, __u16 regd)
{
	int i;
	__u8 data[4] = { phy, 0, 0, indx };

	*(data + 1) = cpu_to_le16p(&regd);
	set_register(pegasus, PhyCtrl, 0);
	set_registers(pegasus, PhyAddr, 4, data);
	set_register(pegasus, PhyCtrl, (indx | PHY_WRITE));
	for (i = 0; i < REG_TIMEOUT; i++) {
		get_registers(pegasus, PhyCtrl, 1, data);
		if (data[0] & PHY_DONE)
			break;
	}
	if (i < REG_TIMEOUT)
		return 0;
	warn("%s: failed", __FUNCTION__);

	return 1;
}
Пример #16
0
static int write_mii_word(rtl8150_t * dev, u8 phy, __u8 indx, u16 reg)
{
	int i;
	u8 data[3], tmp;

	data[0] = phy;
	*(data + 1) = cpu_to_le16p(&reg);
	tmp = indx | PHY_WRITE | PHY_GO;
	i = 0;

	set_registers(dev, PHYADD, sizeof(data), data);
	set_registers(dev, PHYCNT, 1, &tmp);
	do {
		get_registers(dev, PHYCNT, 1, data);
	} while ((data[0] & PHY_GO) && (i++ < HZ));

	if (i < HZ)
		return 0;
	else
		return 1;
}
Пример #17
0
static int
brcmf_usb_recv_ctl(struct brcmf_usbdev_info *devinfo, u8 *buf, int len)
{
    int ret;
    u16 size;

    if ((devinfo == NULL) || (buf == NULL) || (len == 0)
            || (devinfo->ctl_urb == NULL))
        return -EINVAL;

    size = len;
    devinfo->ctl_read.wLength = cpu_to_le16p(&size);
    devinfo->ctl_urb->transfer_buffer_length = size;

    if (devinfo->rxctl_deferrespok) {
        /* BMAC model */
        devinfo->ctl_read.bRequestType = USB_DIR_IN
                                         | USB_TYPE_VENDOR | USB_RECIP_INTERFACE;
        devinfo->ctl_read.bRequest = DL_DEFER_RESP_OK;
    } else {
        /* full dongle model */
        devinfo->ctl_read.bRequestType = USB_DIR_IN
                                         | USB_TYPE_CLASS | USB_RECIP_INTERFACE;
        devinfo->ctl_read.bRequest = 1;
    }

    usb_fill_control_urb(devinfo->ctl_urb,
                         devinfo->usbdev,
                         devinfo->ctl_in_pipe,
                         (unsigned char *) &devinfo->ctl_read,
                         buf, size,
                         (usb_complete_t)brcmf_usb_ctlread_complete,
                         devinfo);

    ret = usb_submit_urb(devinfo->ctl_urb, GFP_ATOMIC);
    if (ret < 0)
        brcmf_dbg(ERROR, "usb_submit_urb failed %d\n", ret);

    return ret;
}
Пример #18
0
static int
brcmf_usb_send_ctl(struct brcmf_usbdev_info *devinfo, u8 *buf, int len)
{
    int ret;
    u16 size;

    if (devinfo == NULL || buf == NULL ||
            len == 0 || devinfo->ctl_urb == NULL)
        return -EINVAL;

    /* If the USB/HSIC bus in sleep state, wake it up */
    if (devinfo->suspend_state == USBOS_SUSPEND_STATE_SUSPENDED)
        if (brcmf_usb_pnp(devinfo, BCMFMAC_USB_PNP_RESUME) != 0) {
            brcmf_dbg(ERROR, "Could not Resume the bus!\n");
            return -EIO;
        }

    devinfo->activity = true;
    size = len;
    devinfo->ctl_write.wLength = cpu_to_le16p(&size);
    devinfo->ctl_urb->transfer_buffer_length = size;
    devinfo->ctl_urb_status = 0;
    devinfo->ctl_urb_actual_length = 0;

    usb_fill_control_urb(devinfo->ctl_urb,
                         devinfo->usbdev,
                         devinfo->ctl_out_pipe,
                         (unsigned char *) &devinfo->ctl_write,
                         buf, size,
                         (usb_complete_t)brcmf_usb_ctlwrite_complete,
                         devinfo);

    ret = usb_submit_urb(devinfo->ctl_urb, GFP_ATOMIC);
    if (ret < 0)
        brcmf_dbg(ERROR, "usb_submit_urb failed %d\n", ret);

    return ret;
}
Пример #19
0
static int brcmf_usb_up(struct device *dev)
{
    struct brcmf_usbdev_info *devinfo = brcmf_usb_get_businfo(dev);
    u16 ifnum;

    if (devinfo->bus_pub.state == BCMFMAC_USB_STATE_UP)
        return 0;

    /* If the USB/HSIC bus in sleep state, wake it up */
    if (devinfo->suspend_state == USBOS_SUSPEND_STATE_SUSPENDED) {
        if (brcmf_usb_pnp(devinfo, BCMFMAC_USB_PNP_RESUME) != 0) {
            brcmf_dbg(ERROR, "Could not Resume the bus!\n");
            return -EIO;
        }
    }
    devinfo->activity = true;

    /* Success, indicate devinfo is fully up */
    brcmf_usb_state_change(devinfo, BCMFMAC_USB_STATE_UP);

    if (devinfo->intr_urb) {
        int ret;

        usb_fill_int_urb(devinfo->intr_urb, devinfo->usbdev,
                         devinfo->intr_pipe,
                         &devinfo->intr,
                         devinfo->intr_size,
                         (usb_complete_t)brcmf_usb_intr_complete,
                         devinfo,
                         devinfo->interval);

        ret = usb_submit_urb(devinfo->intr_urb, GFP_ATOMIC);
        if (ret) {
            brcmf_dbg(ERROR, "USB_SUBMIT_URB failed with status %d\n",
                      ret);
            return -EINVAL;
        }
    }

    if (devinfo->ctl_urb) {
        devinfo->ctl_in_pipe = usb_rcvctrlpipe(devinfo->usbdev, 0);
        devinfo->ctl_out_pipe = usb_sndctrlpipe(devinfo->usbdev, 0);

        ifnum = IFDESC(devinfo->usbdev, CONTROL_IF).bInterfaceNumber;

        /* CTL Write */
        devinfo->ctl_write.bRequestType =
            USB_DIR_OUT | USB_TYPE_CLASS | USB_RECIP_INTERFACE;
        devinfo->ctl_write.bRequest = 0;
        devinfo->ctl_write.wValue = cpu_to_le16(0);
        devinfo->ctl_write.wIndex = cpu_to_le16p(&ifnum);

        /* CTL Read */
        devinfo->ctl_read.bRequestType =
            USB_DIR_IN | USB_TYPE_CLASS | USB_RECIP_INTERFACE;
        devinfo->ctl_read.bRequest = 1;
        devinfo->ctl_read.wValue = cpu_to_le16(0);
        devinfo->ctl_read.wIndex = cpu_to_le16p(&ifnum);
    }
    brcmf_usb_rx_fill_all(devinfo);
    return 0;
}
Пример #20
0
int new_usb_control_msg(struct usb_device *dev, unsigned int pipe, __u8 request, __u8 requesttype,
			 __u16 value, __u16 index, void *data, __u16 size, int timeout)
{

#ifdef CONFIG_ENABLE_MIPS16
	u8 *dma_data=kmalloc(16,GFP_NOIO);
#endif
	struct usb_ctrlrequest *dr;
	struct urb *urb;
	volatile int done=0;
	unsigned long expire;
	int retry_cnt=0;	
	int status;
	int retval;
#ifdef USB_LOCK_ENABLE
	unsigned long flags;
#endif
	
	dr = kmalloc(sizeof(struct usb_ctrlrequest), GFP_NOIO);
	if (!dr)
	{
		return -ENOMEM;
	}

	dr->bRequestType= requesttype;
	dr->bRequest = request;
	dr->wValue = cpu_to_le16p(&value);
	dr->wIndex = cpu_to_le16p(&index);
	dr->wLength = cpu_to_le16p(&size);

	if((value==0x300)||(value==0x320))
	{
		printk("Can't submit control msg value=%x\n",value);
		if(size==4)
			*(u32*)(data)=0;
		else if(size==1)
			*(u8*)(data)=0;
		else if(size==2)
			*(u16*)(data)=0;
		
		kfree(dr);
		return 0;
	}
	
#ifdef __LINUX_2_6__
	urb = usb_alloc_urb(0, GFP_ATOMIC);
#else
	urb = usb_alloc_urb(0);
#endif
	if (!urb)
	{
		kfree(dr);
		return -ENOMEM;
	}

	usb_control_cnt++;
	if(usb_control_cnt>1)
		printk("Error usb_control_cnt=%x\n",usb_control_cnt);	

//  printk("fill urb data=%x indx=%x size=%d\n",*(u8*)data,index,size);
#ifdef CONFIG_ENABLE_MIPS16
	usb_fill_control_urb(urb, dev, pipe, (unsigned char *)dr, (void*)dma_data,
			     size, new_usb_api_blocking_completion, (void *)&done);
#else
	usb_fill_control_urb(urb, dev, pipe, (unsigned char *)dr, data,
			     size, new_usb_api_blocking_completion, (void *)&done);
#endif
	urb->actual_length = 0;

#ifdef CONFIG_ENABLE_MIPS16
	if(request==RTL8192_REQ_SET_REGS) memcpy(dma_data,data,size);
	dma_cache_wback_inv((u32)dma_data,size);
	//rtl_cache_sync_wback(priv, (unsigned int)dma_data, size, 0);
#else
	if(request==RTL8192_REQ_SET_REGS)
		dma_cache_wback_inv((unsigned long)data, size);
#endif

#ifdef __LINUX_2_6__
	status = usb_submit_urb(urb, GFP_ATOMIC);
#else
	status = usb_submit_urb(urb);
#endif
	if (unlikely(status))
	{
		goto out;
	}


	if(timeout)		//expire = msecs_to_jiffies(timeout) + jiffies;
		expire = timeout + jiffies;
	else
		expire =  200 + jiffies; //cathy
 
	if(expire<200)
	{
		if(!in_atomic())
		{
			delay_ms(2100);
			expire=jiffies+200;
		}
		else
			expire=0xffffffffL; 
	}
 
retry:
	
	if(done==1) goto out;
	if(jiffies>=expire) goto out;
	
#ifndef USB_LOCK_ENABLE
	if(in_atomic())
#endif
	{
		unsigned long		flags=0;
		retry_cnt++;
		if(retry_cnt>2000) goto out;

#ifdef CONFIG_USB_OTG_Driver
		dwc_otg_hcd_irq(usbhcd, NULL);
		printk("%s %d done=%x jiffies=%x expire=%x\n",__FUNCTION__,__LINE__,done,jiffies,expire);
#elif defined(CONFIG_USB_OTG_HOST_RTL8672)
		usb_scan_async(dev->bus, 0);
#elif defined(CONFIG_USB_EHCI_HCD) || defined(CONFIG_USB_EHCI_HCD_RTL8652)
{
		struct usb_hcd *hcd=bus_to_hcd(dev->bus);
#ifdef __LINUX_2_6__
		struct ehci_hcd *ehci=(struct ehci_hcd *)hcd->hcd_priv;
		spin_lock_irqsave (&ehci->lock, flags);
		//scan_async(ehci);
		ehci_irq(hcd);		
		spin_unlock_irqrestore (&ehci->lock, flags);
#else
		ehci_irq(hcd, NULL);
#endif
}
#endif
		
	}
#ifndef USB_LOCK_ENABLE
	else
		schedule();	
#endif

	goto retry;

out:

	if(retry_cnt>2000)
	{
		printk("Timeout! requesttype=%x request=%x value=%x index=%x size=%x retry_cnt=%d\n",requesttype,request,value,index,size,retry_cnt);
	}
	
	if(done==0)
	{
#if 0
		printk("USB Timeout!!!\n");		
		if(!in_atomic()) 
		{
			usb_kill_urb(urb);
		}
		else
		{
			printk("in atomic, can't kill urb\n");
		}
		status = urb->status == -ENOENT ? -ETIMEDOUT : urb->status;
#else
		retval = new_usb_kill_urb(urb);
		status = urb->status == -ENOENT ? -ETIMEDOUT : urb->status;
		if((status != 0) && (status!= -ETIMEDOUT)) {
			printk("[%s,%d], urb->status = %d, retval = %d\n", __func__, __LINE__, urb->status, retval);
		}
#endif
	}
	else
	{
//		  printk("index=%x data=%x done\n",index,*(u8*)data); 
#ifdef CONFIG_ENABLE_MIPS16
		if(request==RTL8192_REQ_GET_REGS) memcpy(data,dma_data,size);
#endif
		status = urb->status;
	}

	usb_free_urb(urb);
#ifdef CONFIG_ENABLE_MIPS16
	kfree(dma_data);
#endif
	kfree(dr);

	usb_control_cnt--;
	return status;
}