diff options
Diffstat (limited to 'drivers/usb/host/ehci-mxc.c')
-rw-r--r-- | drivers/usb/host/ehci-mxc.c | 25 |
1 files changed, 23 insertions, 2 deletions
diff --git a/drivers/usb/host/ehci-mxc.c b/drivers/usb/host/ehci-mxc.c index fa59b26fc5bc..c8e360d7d975 100644 --- a/drivers/usb/host/ehci-mxc.c +++ b/drivers/usb/host/ehci-mxc.c | |||
@@ -21,10 +21,13 @@ | |||
21 | #include <linux/clk.h> | 21 | #include <linux/clk.h> |
22 | #include <linux/delay.h> | 22 | #include <linux/delay.h> |
23 | #include <linux/usb/otg.h> | 23 | #include <linux/usb/otg.h> |
24 | #include <linux/usb/ulpi.h> | ||
24 | #include <linux/slab.h> | 25 | #include <linux/slab.h> |
25 | 26 | ||
26 | #include <mach/mxc_ehci.h> | 27 | #include <mach/mxc_ehci.h> |
27 | 28 | ||
29 | #include <asm/mach-types.h> | ||
30 | |||
28 | #define ULPI_VIEWPORT_OFFSET 0x170 | 31 | #define ULPI_VIEWPORT_OFFSET 0x170 |
29 | 32 | ||
30 | struct ehci_mxc_priv { | 33 | struct ehci_mxc_priv { |
@@ -114,6 +117,7 @@ static int ehci_mxc_drv_probe(struct platform_device *pdev) | |||
114 | struct usb_hcd *hcd; | 117 | struct usb_hcd *hcd; |
115 | struct resource *res; | 118 | struct resource *res; |
116 | int irq, ret; | 119 | int irq, ret; |
120 | unsigned int flags; | ||
117 | struct ehci_mxc_priv *priv; | 121 | struct ehci_mxc_priv *priv; |
118 | struct device *dev = &pdev->dev; | 122 | struct device *dev = &pdev->dev; |
119 | struct ehci_hcd *ehci; | 123 | struct ehci_hcd *ehci; |
@@ -177,8 +181,8 @@ static int ehci_mxc_drv_probe(struct platform_device *pdev) | |||
177 | clk_enable(priv->ahbclk); | 181 | clk_enable(priv->ahbclk); |
178 | } | 182 | } |
179 | 183 | ||
180 | /* "dr" device has its own clock */ | 184 | /* "dr" device has its own clock on i.MX51 */ |
181 | if (pdev->id == 0) { | 185 | if (cpu_is_mx51() && (pdev->id == 0)) { |
182 | priv->phy1clk = clk_get(dev, "usb_phy1"); | 186 | priv->phy1clk = clk_get(dev, "usb_phy1"); |
183 | if (IS_ERR(priv->phy1clk)) { | 187 | if (IS_ERR(priv->phy1clk)) { |
184 | ret = PTR_ERR(priv->phy1clk); | 188 | ret = PTR_ERR(priv->phy1clk); |
@@ -240,6 +244,23 @@ static int ehci_mxc_drv_probe(struct platform_device *pdev) | |||
240 | if (ret) | 244 | if (ret) |
241 | goto err_add; | 245 | goto err_add; |
242 | 246 | ||
247 | if (pdata->otg) { | ||
248 | /* | ||
249 | * efikamx and efikasb have some hardware bug which is | ||
250 | * preventing usb to work unless CHRGVBUS is set. | ||
251 | * It's in violation of USB specs | ||
252 | */ | ||
253 | if (machine_is_mx51_efikamx() || machine_is_mx51_efikasb()) { | ||
254 | flags = otg_io_read(pdata->otg, ULPI_OTG_CTRL); | ||
255 | flags |= ULPI_OTG_CTRL_CHRGVBUS; | ||
256 | ret = otg_io_write(pdata->otg, flags, ULPI_OTG_CTRL); | ||
257 | if (ret) { | ||
258 | dev_err(dev, "unable to set CHRVBUS\n"); | ||
259 | goto err_add; | ||
260 | } | ||
261 | } | ||
262 | } | ||
263 | |||
243 | return 0; | 264 | return 0; |
244 | 265 | ||
245 | err_add: | 266 | err_add: |