staging: dwc2: add calls to usb_hcd_link_urb_to_ep() and friends
authorPaul Zimmerman <Paul.Zimmerman@synopsys.com>
Sat, 13 Jul 2013 21:53:49 +0000 (14:53 -0700)
committerGreg Kroah-Hartman <gregkh@linuxfoundation.org>
Tue, 23 Jul 2013 21:54:48 +0000 (14:54 -0700)
The driver was lacking calls to usb_hcd_link_urb_to_ep(),
usb_hcd_unlink_urb_from_ep(), and usb_hcd_check_unlink_urb(). Add
those now.

Signed-off-by: Paul Zimmerman <paulz@synopsys.com>
Tested-by: Stephen Warren <swarren@wwwdotorg.org>
Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
drivers/staging/dwc2/hcd.c

index e8fb84f53dd90d13a3741561fb64de171b711df2..d72daf17914858885e0f476b8d2df20947faec91 100644 (file)
@@ -2153,6 +2153,7 @@ void dwc2_host_complete(struct dwc2_hsotg *hsotg, struct dwc2_qtd *qtd,
                                        urb);
        }
 
+       usb_hcd_unlink_urb_from_ep(dwc2_hsotg_to_hcd(hsotg), urb);
        urb->hcpriv = NULL;
        kfree(qtd->urb);
        qtd->urb = NULL;
@@ -2343,8 +2344,8 @@ static int _dwc2_hcd_urb_enqueue(struct usb_hcd *hcd, struct urb *urb,
        struct usb_host_endpoint *ep = urb->ep;
        struct dwc2_hcd_urb *dwc2_urb;
        int i;
+       int retval;
        int alloc_bandwidth = 0;
-       int retval = 0;
        u8 ep_type = 0;
        u32 tflags = 0;
        void *buf;
@@ -2426,21 +2427,36 @@ static int _dwc2_hcd_urb_enqueue(struct usb_hcd *hcd, struct urb *urb,
                                                 urb->iso_frame_desc[i].length);
 
        urb->hcpriv = dwc2_urb;
-       retval = dwc2_hcd_urb_enqueue(hsotg, dwc2_urb, &ep->hcpriv,
-                                     mem_flags);
-       if (retval) {
-               urb->hcpriv = NULL;
-               kfree(dwc2_urb);
-       } else {
-               if (alloc_bandwidth) {
-                       spin_lock_irqsave(&hsotg->lock, flags);
-                       dwc2_allocate_bus_bandwidth(hcd,
-                                       dwc2_hcd_get_ep_bandwidth(hsotg, ep),
-                                       urb);
-                       spin_unlock_irqrestore(&hsotg->lock, flags);
-               }
+
+       spin_lock_irqsave(&hsotg->lock, flags);
+       retval = usb_hcd_link_urb_to_ep(hcd, urb);
+       spin_unlock_irqrestore(&hsotg->lock, flags);
+       if (retval)
+               goto fail1;
+
+       retval = dwc2_hcd_urb_enqueue(hsotg, dwc2_urb, &ep->hcpriv, mem_flags);
+       if (retval)
+               goto fail2;
+
+       if (alloc_bandwidth) {
+               spin_lock_irqsave(&hsotg->lock, flags);
+               dwc2_allocate_bus_bandwidth(hcd,
+                               dwc2_hcd_get_ep_bandwidth(hsotg, ep),
+                               urb);
+               spin_unlock_irqrestore(&hsotg->lock, flags);
        }
 
+       return 0;
+
+fail2:
+       spin_lock_irqsave(&hsotg->lock, flags);
+       dwc2_urb->priv = NULL;
+       usb_hcd_unlink_urb_from_ep(hcd, urb);
+       spin_unlock_irqrestore(&hsotg->lock, flags);
+fail1:
+       urb->hcpriv = NULL;
+       kfree(dwc2_urb);
+
        return retval;
 }
 
@@ -2451,7 +2467,7 @@ static int _dwc2_hcd_urb_dequeue(struct usb_hcd *hcd, struct urb *urb,
                                 int status)
 {
        struct dwc2_hsotg *hsotg = dwc2_hcd_to_hsotg(hcd);
-       int rc = 0;
+       int rc;
        unsigned long flags;
 
        dev_dbg(hsotg->dev, "DWC OTG HCD URB Dequeue\n");
@@ -2459,6 +2475,10 @@ static int _dwc2_hcd_urb_dequeue(struct usb_hcd *hcd, struct urb *urb,
 
        spin_lock_irqsave(&hsotg->lock, flags);
 
+       rc = usb_hcd_check_unlink_urb(hcd, urb, status);
+       if (rc)
+               goto out;
+
        if (!urb->hcpriv) {
                dev_dbg(hsotg->dev, "## urb->hcpriv is NULL ##\n");
                goto out;
@@ -2466,6 +2486,8 @@ static int _dwc2_hcd_urb_dequeue(struct usb_hcd *hcd, struct urb *urb,
 
        rc = dwc2_hcd_urb_dequeue(hsotg, urb->hcpriv);
 
+       usb_hcd_unlink_urb_from_ep(hcd, urb);
+
        kfree(urb->hcpriv);
        urb->hcpriv = NULL;