diff options
author | Robert Jarzmik <robert.jarzmik@free.fr> | 2009-01-25 02:57:30 -0500 |
---|---|---|
committer | Greg Kroah-Hartman <gregkh@suse.de> | 2009-03-24 19:20:27 -0400 |
commit | 7fec3c25b773883bd50c4078bcccdd23d3dadeac (patch) | |
tree | 42d46e065d2408a34c0a255e8ac1dfcb71c85972 | |
parent | b799a7eb68082af620b7e37b6f41c98802e831f6 (diff) |
USB: pxa27x_udc: add otg transceiver support
When a transceiver driver is used, no automatic udc enable
is done. The transceiver (OTG or not) should :
- take care of VBus sensing
- call usb_gadget_vbus_connect()
- call usb_gadget_vbus_disconnect()
The pullup should remain within this driver's management,
either by gpio_pullup of udc_command() fields.
Signed-off-by: Robert Jarzmik <robert.jarzmik@free.fr>
Signed-off-by: David Brownell <dbrownell@users.sourceforge.net>
Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
-rw-r--r-- | drivers/usb/gadget/Kconfig | 1 | ||||
-rw-r--r-- | drivers/usb/gadget/pxa27x_udc.c | 19 | ||||
-rw-r--r-- | drivers/usb/gadget/pxa27x_udc.h | 3 |
3 files changed, 22 insertions, 1 deletions
diff --git a/drivers/usb/gadget/Kconfig b/drivers/usb/gadget/Kconfig index e55fef52a5dc..770b3eaa9184 100644 --- a/drivers/usb/gadget/Kconfig +++ b/drivers/usb/gadget/Kconfig | |||
@@ -254,6 +254,7 @@ config USB_PXA25X_SMALL | |||
254 | config USB_GADGET_PXA27X | 254 | config USB_GADGET_PXA27X |
255 | boolean "PXA 27x" | 255 | boolean "PXA 27x" |
256 | depends on ARCH_PXA && PXA27x | 256 | depends on ARCH_PXA && PXA27x |
257 | select USB_OTG_UTILS | ||
257 | help | 258 | help |
258 | Intel's PXA 27x series XScale ARM v5TE processors include | 259 | Intel's PXA 27x series XScale ARM v5TE processors include |
259 | an integrated full speed USB 1.1 device controller. | 260 | an integrated full speed USB 1.1 device controller. |
diff --git a/drivers/usb/gadget/pxa27x_udc.c b/drivers/usb/gadget/pxa27x_udc.c index 0c9307118b54..11510472ee00 100644 --- a/drivers/usb/gadget/pxa27x_udc.c +++ b/drivers/usb/gadget/pxa27x_udc.c | |||
@@ -1779,10 +1779,21 @@ int usb_gadget_register_driver(struct usb_gadget_driver *driver) | |||
1779 | dev_dbg(udc->dev, "registered gadget driver '%s'\n", | 1779 | dev_dbg(udc->dev, "registered gadget driver '%s'\n", |
1780 | driver->driver.name); | 1780 | driver->driver.name); |
1781 | 1781 | ||
1782 | if (udc->transceiver) { | ||
1783 | retval = otg_set_peripheral(udc->transceiver, &udc->gadget); | ||
1784 | if (retval) { | ||
1785 | dev_err(udc->dev, "can't bind to transceiver\n"); | ||
1786 | goto transceiver_fail; | ||
1787 | } | ||
1788 | } | ||
1789 | |||
1782 | if (should_enable_udc(udc)) | 1790 | if (should_enable_udc(udc)) |
1783 | udc_enable(udc); | 1791 | udc_enable(udc); |
1784 | return 0; | 1792 | return 0; |
1785 | 1793 | ||
1794 | transceiver_fail: | ||
1795 | if (driver->unbind) | ||
1796 | driver->unbind(&udc->gadget); | ||
1786 | bind_fail: | 1797 | bind_fail: |
1787 | device_del(&udc->gadget.dev); | 1798 | device_del(&udc->gadget.dev); |
1788 | add_fail: | 1799 | add_fail: |
@@ -1840,9 +1851,11 @@ int usb_gadget_unregister_driver(struct usb_gadget_driver *driver) | |||
1840 | udc->driver = NULL; | 1851 | udc->driver = NULL; |
1841 | 1852 | ||
1842 | device_del(&udc->gadget.dev); | 1853 | device_del(&udc->gadget.dev); |
1843 | |||
1844 | dev_info(udc->dev, "unregistered gadget driver '%s'\n", | 1854 | dev_info(udc->dev, "unregistered gadget driver '%s'\n", |
1845 | driver->driver.name); | 1855 | driver->driver.name); |
1856 | |||
1857 | if (udc->transceiver) | ||
1858 | return otg_set_peripheral(udc->transceiver, NULL); | ||
1846 | return 0; | 1859 | return 0; |
1847 | } | 1860 | } |
1848 | EXPORT_SYMBOL(usb_gadget_unregister_driver); | 1861 | EXPORT_SYMBOL(usb_gadget_unregister_driver); |
@@ -2359,6 +2372,7 @@ static int __init pxa_udc_probe(struct platform_device *pdev) | |||
2359 | 2372 | ||
2360 | udc->dev = &pdev->dev; | 2373 | udc->dev = &pdev->dev; |
2361 | udc->mach = pdev->dev.platform_data; | 2374 | udc->mach = pdev->dev.platform_data; |
2375 | udc->transceiver = otg_get_transceiver(); | ||
2362 | 2376 | ||
2363 | gpio = udc->mach->gpio_pullup; | 2377 | gpio = udc->mach->gpio_pullup; |
2364 | if (gpio_is_valid(gpio)) { | 2378 | if (gpio_is_valid(gpio)) { |
@@ -2431,6 +2445,9 @@ static int __exit pxa_udc_remove(struct platform_device *_dev) | |||
2431 | if (gpio_is_valid(gpio)) | 2445 | if (gpio_is_valid(gpio)) |
2432 | gpio_free(gpio); | 2446 | gpio_free(gpio); |
2433 | 2447 | ||
2448 | otg_put_transceiver(udc->transceiver); | ||
2449 | |||
2450 | udc->transceiver = NULL; | ||
2434 | platform_set_drvdata(_dev, NULL); | 2451 | platform_set_drvdata(_dev, NULL); |
2435 | the_controller = NULL; | 2452 | the_controller = NULL; |
2436 | clk_put(udc->clk); | 2453 | clk_put(udc->clk); |
diff --git a/drivers/usb/gadget/pxa27x_udc.h b/drivers/usb/gadget/pxa27x_udc.h index 64741e199204..db58125331da 100644 --- a/drivers/usb/gadget/pxa27x_udc.h +++ b/drivers/usb/gadget/pxa27x_udc.h | |||
@@ -26,6 +26,7 @@ | |||
26 | #include <linux/types.h> | 26 | #include <linux/types.h> |
27 | #include <linux/spinlock.h> | 27 | #include <linux/spinlock.h> |
28 | #include <linux/io.h> | 28 | #include <linux/io.h> |
29 | #include <linux/usb/otg.h> | ||
29 | 30 | ||
30 | /* | 31 | /* |
31 | * Register definitions | 32 | * Register definitions |
@@ -421,6 +422,7 @@ struct udc_stats { | |||
421 | * @driver: bound gadget (zero, g_ether, g_file_storage, ...) | 422 | * @driver: bound gadget (zero, g_ether, g_file_storage, ...) |
422 | * @dev: device | 423 | * @dev: device |
423 | * @mach: machine info, used to activate specific GPIO | 424 | * @mach: machine info, used to activate specific GPIO |
425 | * @transceiver: external transceiver to handle vbus sense and D+ pullup | ||
424 | * @ep0state: control endpoint state machine state | 426 | * @ep0state: control endpoint state machine state |
425 | * @stats: statistics on udc usage | 427 | * @stats: statistics on udc usage |
426 | * @udc_usb_ep: array of usb endpoints offered by the gadget | 428 | * @udc_usb_ep: array of usb endpoints offered by the gadget |
@@ -446,6 +448,7 @@ struct pxa_udc { | |||
446 | struct usb_gadget_driver *driver; | 448 | struct usb_gadget_driver *driver; |
447 | struct device *dev; | 449 | struct device *dev; |
448 | struct pxa2xx_udc_mach_info *mach; | 450 | struct pxa2xx_udc_mach_info *mach; |
451 | struct otg_transceiver *transceiver; | ||
449 | 452 | ||
450 | enum ep0_state ep0state; | 453 | enum ep0_state ep0state; |
451 | struct udc_stats stats; | 454 | struct udc_stats stats; |