Пример #1
0
void ctrl_bridge_close(unsigned int id)
{
    struct ctrl_bridge	*dev;

    if (id >= MAX_BRIDGE_DEVICES)
        return;

    dev  = __dev[id];
    if (!dev || !dev->brdg)
        return;

    dev_dbg(&dev->intf->dev, "%s:\n", __func__);

    ctrl_bridge_set_cbits(dev->brdg->ch_id, 0);


    dev_err(&dev->intf->dev, "%s: usb_wait_anchor_empty_timeout tx_submitted\n", __func__);

    usb_wait_anchor_empty_timeout(&dev->tx_submitted, 500);


    dev_err(&dev->intf->dev, "%s: tx_submitted usb_anchor_empty:%d\n", __func__, usb_anchor_empty(&dev->tx_submitted));

    usb_unlink_anchored_urbs(&dev->tx_submitted);

    dev->brdg = NULL;
}
int ctrl_bridge_suspend(unsigned int id)
{
    struct ctrl_bridge	*dev;
    unsigned long		flags;

    if (id >= MAX_BRIDGE_DEVICES)
        return -EINVAL;

    dev = __dev[id];
    if (!dev)
        return -ENODEV;
    if (!dev->int_pipe)
        return 0;

    spin_lock_irqsave(&dev->lock, flags);
    if (!usb_anchor_empty(&dev->tx_submitted) || dev->rx_state == RX_BUSY) {
        spin_unlock_irqrestore(&dev->lock, flags);
        return -EBUSY;
    }
    spin_unlock_irqrestore(&dev->lock, flags);

    usb_kill_urb(dev->inturb);

    spin_lock_irqsave(&dev->lock, flags);
    if (dev->rx_state != RX_IDLE) {
        spin_unlock_irqrestore(&dev->lock, flags);
        return -EBUSY;
    }
    if (!usb_anchor_empty(&dev->tx_submitted)) {
        spin_unlock_irqrestore(&dev->lock, flags);
        ctrl_bridge_start_read(dev, GFP_KERNEL);
        return -EBUSY;
    }
    set_bit(SUSPENDED, &dev->flags);
    spin_unlock_irqrestore(&dev->lock, flags);

    return 0;
}
static void usb_net_raw_ip_tx_urb_work(struct work_struct *work)
{
	struct baseband_usb *usb
		= container_of(work, struct baseband_usb, usb.tx_work);
	struct urb *urb;
	int err;

	pr_debug("usb_net_raw_ip_tx_urb_work {\n");

	/* check if tx urb(s) queued */
	if (!usb->usb.tx_urb && usb_anchor_empty(&usb->usb.tx_urb_deferred)) {
		pr_debug("%s: nothing to do!\n", __func__);
		return;
	}

	/* check if usb interface disconnected */
	if (!usb->usb.interface) {
		pr_err("%s: not submitting tx urb %p -interface disconnected\n",
			__func__, urb);
		return;
	}

	/* submit queued tx urb(s) */
	while ((urb = usb_get_from_anchor(&usb->usb.tx_urb_deferred))
		!= (struct urb *) 0) {
		/* decrement count from usb_get_from_anchor() */
		usb_free_urb(urb);

		/* autoresume before tx */
		usb_mark_last_busy(usb->usb.device);
		err = usb_autopm_get_interface(usb->usb.interface);
		if (err < 0) {
			pr_err("%s: usb_autopm_get_interface(%p) failed %d\n",
				__func__, usb->usb.interface, err);
			if (urb->transfer_buffer) {
				kfree(urb->transfer_buffer);
				urb->transfer_buffer = (void *) 0;
			}
			usb_free_urb(urb);
			usb->stats.tx_errors++;
			continue;
		}
		/* submit tx urb */
		err = usb_submit_urb(urb, GFP_ATOMIC);
		if (err < 0) {
			pr_err("%s: usb_submit_urb(%p) failed - err %d\n",
				__func__, urb, err);
			usb_autopm_put_interface(usb->usb.interface);
			if (urb->transfer_buffer) {
				kfree(urb->transfer_buffer);
				urb->transfer_buffer = (void *) 0;
			}
			usb_free_urb(urb);
			continue;
		}
		/* free tx urb
		 * - actual urb free occurs when refcnt which was incremented
		 *   in usb_submit_urb is decremented to 0 (usually after urb
		 *   completion function returns)
		 * - tx urb transfer buffer will be freed in urb completion
		 *   function
		 */
		usb_free_urb(urb);
	}

	pr_debug("usb_net_raw_ip_tx_urb_work }\n");
}