diff options
Diffstat (limited to 'drivers/usb/gadget/atmel_usba_udc.c')
-rw-r--r-- | drivers/usb/gadget/atmel_usba_udc.c | 76 |
1 files changed, 24 insertions, 52 deletions
diff --git a/drivers/usb/gadget/atmel_usba_udc.c b/drivers/usb/gadget/atmel_usba_udc.c index 9f98508966d..e23bf7984aa 100644 --- a/drivers/usb/gadget/atmel_usba_udc.c +++ b/drivers/usb/gadget/atmel_usba_udc.c | |||
@@ -599,13 +599,13 @@ usba_ep_enable(struct usb_ep *_ep, const struct usb_endpoint_descriptor *desc) | |||
599 | 599 | ||
600 | spin_lock_irqsave(&ep->udc->lock, flags); | 600 | spin_lock_irqsave(&ep->udc->lock, flags); |
601 | 601 | ||
602 | if (ep->desc) { | 602 | if (ep->ep.desc) { |
603 | spin_unlock_irqrestore(&ep->udc->lock, flags); | 603 | spin_unlock_irqrestore(&ep->udc->lock, flags); |
604 | DBG(DBG_ERR, "ep%d already enabled\n", ep->index); | 604 | DBG(DBG_ERR, "ep%d already enabled\n", ep->index); |
605 | return -EBUSY; | 605 | return -EBUSY; |
606 | } | 606 | } |
607 | 607 | ||
608 | ep->desc = desc; | 608 | ep->ep.desc = desc; |
609 | ep->ep.maxpacket = maxpacket; | 609 | ep->ep.maxpacket = maxpacket; |
610 | 610 | ||
611 | usba_ep_writel(ep, CFG, ept_cfg); | 611 | usba_ep_writel(ep, CFG, ept_cfg); |
@@ -647,7 +647,7 @@ static int usba_ep_disable(struct usb_ep *_ep) | |||
647 | 647 | ||
648 | spin_lock_irqsave(&udc->lock, flags); | 648 | spin_lock_irqsave(&udc->lock, flags); |
649 | 649 | ||
650 | if (!ep->desc) { | 650 | if (!ep->ep.desc) { |
651 | spin_unlock_irqrestore(&udc->lock, flags); | 651 | spin_unlock_irqrestore(&udc->lock, flags); |
652 | /* REVISIT because this driver disables endpoints in | 652 | /* REVISIT because this driver disables endpoints in |
653 | * reset_all_endpoints() before calling disconnect(), | 653 | * reset_all_endpoints() before calling disconnect(), |
@@ -658,7 +658,6 @@ static int usba_ep_disable(struct usb_ep *_ep) | |||
658 | ep->ep.name); | 658 | ep->ep.name); |
659 | return -EINVAL; | 659 | return -EINVAL; |
660 | } | 660 | } |
661 | ep->desc = NULL; | ||
662 | ep->ep.desc = NULL; | 661 | ep->ep.desc = NULL; |
663 | 662 | ||
664 | list_splice_init(&ep->queue, &req_list); | 663 | list_splice_init(&ep->queue, &req_list); |
@@ -752,7 +751,7 @@ static int queue_dma(struct usba_udc *udc, struct usba_ep *ep, | |||
752 | */ | 751 | */ |
753 | ret = -ESHUTDOWN; | 752 | ret = -ESHUTDOWN; |
754 | spin_lock_irqsave(&udc->lock, flags); | 753 | spin_lock_irqsave(&udc->lock, flags); |
755 | if (ep->desc) { | 754 | if (ep->ep.desc) { |
756 | if (list_empty(&ep->queue)) | 755 | if (list_empty(&ep->queue)) |
757 | submit_request(ep, req); | 756 | submit_request(ep, req); |
758 | 757 | ||
@@ -776,7 +775,8 @@ usba_ep_queue(struct usb_ep *_ep, struct usb_request *_req, gfp_t gfp_flags) | |||
776 | DBG(DBG_GADGET | DBG_QUEUE | DBG_REQ, "%s: queue req %p, len %u\n", | 775 | DBG(DBG_GADGET | DBG_QUEUE | DBG_REQ, "%s: queue req %p, len %u\n", |
777 | ep->ep.name, req, _req->length); | 776 | ep->ep.name, req, _req->length); |
778 | 777 | ||
779 | if (!udc->driver || udc->gadget.speed == USB_SPEED_UNKNOWN || !ep->desc) | 778 | if (!udc->driver || udc->gadget.speed == USB_SPEED_UNKNOWN || |
779 | !ep->ep.desc) | ||
780 | return -ESHUTDOWN; | 780 | return -ESHUTDOWN; |
781 | 781 | ||
782 | req->submitted = 0; | 782 | req->submitted = 0; |
@@ -792,7 +792,7 @@ usba_ep_queue(struct usb_ep *_ep, struct usb_request *_req, gfp_t gfp_flags) | |||
792 | /* May have received a reset since last time we checked */ | 792 | /* May have received a reset since last time we checked */ |
793 | ret = -ESHUTDOWN; | 793 | ret = -ESHUTDOWN; |
794 | spin_lock_irqsave(&udc->lock, flags); | 794 | spin_lock_irqsave(&udc->lock, flags); |
795 | if (ep->desc) { | 795 | if (ep->ep.desc) { |
796 | list_add_tail(&req->queue, &ep->queue); | 796 | list_add_tail(&req->queue, &ep->queue); |
797 | 797 | ||
798 | if ((!ep_is_control(ep) && ep->is_in) || | 798 | if ((!ep_is_control(ep) && ep->is_in) || |
@@ -905,7 +905,7 @@ static int usba_ep_set_halt(struct usb_ep *_ep, int value) | |||
905 | DBG(DBG_GADGET, "endpoint %s: %s HALT\n", ep->ep.name, | 905 | DBG(DBG_GADGET, "endpoint %s: %s HALT\n", ep->ep.name, |
906 | value ? "set" : "clear"); | 906 | value ? "set" : "clear"); |
907 | 907 | ||
908 | if (!ep->desc) { | 908 | if (!ep->ep.desc) { |
909 | DBG(DBG_ERR, "Attempted to halt uninitialized ep %s\n", | 909 | DBG(DBG_ERR, "Attempted to halt uninitialized ep %s\n", |
910 | ep->ep.name); | 910 | ep->ep.name); |
911 | return -ENODEV; | 911 | return -ENODEV; |
@@ -1008,16 +1008,16 @@ usba_udc_set_selfpowered(struct usb_gadget *gadget, int is_selfpowered) | |||
1008 | return 0; | 1008 | return 0; |
1009 | } | 1009 | } |
1010 | 1010 | ||
1011 | static int atmel_usba_start(struct usb_gadget_driver *driver, | 1011 | static int atmel_usba_start(struct usb_gadget *gadget, |
1012 | int (*bind)(struct usb_gadget *)); | 1012 | struct usb_gadget_driver *driver); |
1013 | static int atmel_usba_stop(struct usb_gadget_driver *driver); | 1013 | static int atmel_usba_stop(struct usb_gadget *gadget, |
1014 | 1014 | struct usb_gadget_driver *driver); | |
1015 | static const struct usb_gadget_ops usba_udc_ops = { | 1015 | static const struct usb_gadget_ops usba_udc_ops = { |
1016 | .get_frame = usba_udc_get_frame, | 1016 | .get_frame = usba_udc_get_frame, |
1017 | .wakeup = usba_udc_wakeup, | 1017 | .wakeup = usba_udc_wakeup, |
1018 | .set_selfpowered = usba_udc_set_selfpowered, | 1018 | .set_selfpowered = usba_udc_set_selfpowered, |
1019 | .start = atmel_usba_start, | 1019 | .udc_start = atmel_usba_start, |
1020 | .stop = atmel_usba_stop, | 1020 | .udc_stop = atmel_usba_stop, |
1021 | }; | 1021 | }; |
1022 | 1022 | ||
1023 | static struct usb_endpoint_descriptor usba_ep0_desc = { | 1023 | static struct usb_endpoint_descriptor usba_ep0_desc = { |
@@ -1071,7 +1071,7 @@ static void reset_all_endpoints(struct usba_udc *udc) | |||
1071 | * FIXME remove this code ... and retest thoroughly. | 1071 | * FIXME remove this code ... and retest thoroughly. |
1072 | */ | 1072 | */ |
1073 | list_for_each_entry(ep, &udc->gadget.ep_list, ep.ep_list) { | 1073 | list_for_each_entry(ep, &udc->gadget.ep_list, ep.ep_list) { |
1074 | if (ep->desc) { | 1074 | if (ep->ep.desc) { |
1075 | spin_unlock(&udc->lock); | 1075 | spin_unlock(&udc->lock); |
1076 | usba_ep_disable(&ep->ep); | 1076 | usba_ep_disable(&ep->ep); |
1077 | spin_lock(&udc->lock); | 1077 | spin_lock(&udc->lock); |
@@ -1089,9 +1089,9 @@ static struct usba_ep *get_ep_by_addr(struct usba_udc *udc, u16 wIndex) | |||
1089 | list_for_each_entry (ep, &udc->gadget.ep_list, ep.ep_list) { | 1089 | list_for_each_entry (ep, &udc->gadget.ep_list, ep.ep_list) { |
1090 | u8 bEndpointAddress; | 1090 | u8 bEndpointAddress; |
1091 | 1091 | ||
1092 | if (!ep->desc) | 1092 | if (!ep->ep.desc) |
1093 | continue; | 1093 | continue; |
1094 | bEndpointAddress = ep->desc->bEndpointAddress; | 1094 | bEndpointAddress = ep->ep.desc->bEndpointAddress; |
1095 | if ((wIndex ^ bEndpointAddress) & USB_DIR_IN) | 1095 | if ((wIndex ^ bEndpointAddress) & USB_DIR_IN) |
1096 | continue; | 1096 | continue; |
1097 | if ((bEndpointAddress & USB_ENDPOINT_NUMBER_MASK) | 1097 | if ((bEndpointAddress & USB_ENDPOINT_NUMBER_MASK) |
@@ -1727,7 +1727,7 @@ static irqreturn_t usba_udc_irq(int irq, void *devid) | |||
1727 | usb_speed_string(udc->gadget.speed)); | 1727 | usb_speed_string(udc->gadget.speed)); |
1728 | 1728 | ||
1729 | ep0 = &usba_ep[0]; | 1729 | ep0 = &usba_ep[0]; |
1730 | ep0->desc = &usba_ep0_desc; | 1730 | ep0->ep.desc = &usba_ep0_desc; |
1731 | ep0->state = WAIT_FOR_SETUP; | 1731 | ep0->state = WAIT_FOR_SETUP; |
1732 | usba_ep_writel(ep0, CFG, | 1732 | usba_ep_writel(ep0, CFG, |
1733 | (USBA_BF(EPT_SIZE, EP0_EPT_SIZE) | 1733 | (USBA_BF(EPT_SIZE, EP0_EPT_SIZE) |
@@ -1795,21 +1795,13 @@ out: | |||
1795 | return IRQ_HANDLED; | 1795 | return IRQ_HANDLED; |
1796 | } | 1796 | } |
1797 | 1797 | ||
1798 | static int atmel_usba_start(struct usb_gadget_driver *driver, | 1798 | static int atmel_usba_start(struct usb_gadget *gadget, |
1799 | int (*bind)(struct usb_gadget *)) | 1799 | struct usb_gadget_driver *driver) |
1800 | { | 1800 | { |
1801 | struct usba_udc *udc = &the_udc; | 1801 | struct usba_udc *udc = container_of(gadget, struct usba_udc, gadget); |
1802 | unsigned long flags; | 1802 | unsigned long flags; |
1803 | int ret; | ||
1804 | |||
1805 | if (!udc->pdev) | ||
1806 | return -ENODEV; | ||
1807 | 1803 | ||
1808 | spin_lock_irqsave(&udc->lock, flags); | 1804 | spin_lock_irqsave(&udc->lock, flags); |
1809 | if (udc->driver) { | ||
1810 | spin_unlock_irqrestore(&udc->lock, flags); | ||
1811 | return -EBUSY; | ||
1812 | } | ||
1813 | 1805 | ||
1814 | udc->devstatus = 1 << USB_DEVICE_SELF_POWERED; | 1806 | udc->devstatus = 1 << USB_DEVICE_SELF_POWERED; |
1815 | udc->driver = driver; | 1807 | udc->driver = driver; |
@@ -1819,13 +1811,6 @@ static int atmel_usba_start(struct usb_gadget_driver *driver, | |||
1819 | clk_enable(udc->pclk); | 1811 | clk_enable(udc->pclk); |
1820 | clk_enable(udc->hclk); | 1812 | clk_enable(udc->hclk); |
1821 | 1813 | ||
1822 | ret = bind(&udc->gadget); | ||
1823 | if (ret) { | ||
1824 | DBG(DBG_ERR, "Could not bind to driver %s: error %d\n", | ||
1825 | driver->driver.name, ret); | ||
1826 | goto err_driver_bind; | ||
1827 | } | ||
1828 | |||
1829 | DBG(DBG_GADGET, "registered driver `%s'\n", driver->driver.name); | 1814 | DBG(DBG_GADGET, "registered driver `%s'\n", driver->driver.name); |
1830 | 1815 | ||
1831 | udc->vbus_prev = 0; | 1816 | udc->vbus_prev = 0; |
@@ -1842,23 +1827,14 @@ static int atmel_usba_start(struct usb_gadget_driver *driver, | |||
1842 | spin_unlock_irqrestore(&udc->lock, flags); | 1827 | spin_unlock_irqrestore(&udc->lock, flags); |
1843 | 1828 | ||
1844 | return 0; | 1829 | return 0; |
1845 | |||
1846 | err_driver_bind: | ||
1847 | udc->driver = NULL; | ||
1848 | udc->gadget.dev.driver = NULL; | ||
1849 | return ret; | ||
1850 | } | 1830 | } |
1851 | 1831 | ||
1852 | static int atmel_usba_stop(struct usb_gadget_driver *driver) | 1832 | static int atmel_usba_stop(struct usb_gadget *gadget, |
1833 | struct usb_gadget_driver *driver) | ||
1853 | { | 1834 | { |
1854 | struct usba_udc *udc = &the_udc; | 1835 | struct usba_udc *udc = container_of(gadget, struct usba_udc, gadget); |
1855 | unsigned long flags; | 1836 | unsigned long flags; |
1856 | 1837 | ||
1857 | if (!udc->pdev) | ||
1858 | return -ENODEV; | ||
1859 | if (driver != udc->driver || !driver->unbind) | ||
1860 | return -EINVAL; | ||
1861 | |||
1862 | if (gpio_is_valid(udc->vbus_pin)) | 1838 | if (gpio_is_valid(udc->vbus_pin)) |
1863 | disable_irq(gpio_to_irq(udc->vbus_pin)); | 1839 | disable_irq(gpio_to_irq(udc->vbus_pin)); |
1864 | 1840 | ||
@@ -1871,10 +1847,6 @@ static int atmel_usba_stop(struct usb_gadget_driver *driver) | |||
1871 | toggle_bias(0); | 1847 | toggle_bias(0); |
1872 | usba_writel(udc, CTRL, USBA_DISABLE_MASK); | 1848 | usba_writel(udc, CTRL, USBA_DISABLE_MASK); |
1873 | 1849 | ||
1874 | if (udc->driver->disconnect) | ||
1875 | udc->driver->disconnect(&udc->gadget); | ||
1876 | |||
1877 | driver->unbind(&udc->gadget); | ||
1878 | udc->gadget.dev.driver = NULL; | 1850 | udc->gadget.dev.driver = NULL; |
1879 | udc->driver = NULL; | 1851 | udc->driver = NULL; |
1880 | 1852 | ||