summaryrefslogtreecommitdiffstats
path: root/drivers/usb/host/ehci-fsl.c
diff options
context:
space:
mode:
authorRamneek Mehresh <ramneek.mehresh@freescale.com>2012-03-20 10:35:50 +0530
committerGreg Kroah-Hartman <gregkh@linuxfoundation.org>2012-04-18 13:46:42 -0700
commit58c559e6509f276d0afb4621b2122e994e70160c (patch)
treea283772f0748cb6dd63d236851ecd20b3f89b780 /drivers/usb/host/ehci-fsl.c
parent67c88382e0bf92d7e09536ac47674c9fc9398b98 (diff)
downloadlinux-58c559e6509f276d0afb4621b2122e994e70160c.tar.gz
linux-58c559e6509f276d0afb4621b2122e994e70160c.tar.bz2
linux-58c559e6509f276d0afb4621b2122e994e70160c.zip
fsl/usb: Add controller version based ULPI and UTMI phy support
Add support for ULPI and UTMI PHYs based on usb controller version info read from device-tree Example of USB Controller versioning info: Version 1.2 and below : MPC8536, MPC8315, etc Version 1.6 : P1020, P1010, P2020, P5020, etc Version 2.2 : PSC9131, PSC9132, P3060, etc No changes for non-DT users Signed-off-by: Ramneek Mehresh <ramneek.mehresh@freescale.com> Acked-by: Li Yang <leoli@freescale.com> Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
Diffstat (limited to 'drivers/usb/host/ehci-fsl.c')
-rw-r--r--drivers/usb/host/ehci-fsl.c35
1 files changed, 28 insertions, 7 deletions
diff --git a/drivers/usb/host/ehci-fsl.c b/drivers/usb/host/ehci-fsl.c
index 3e7345172e03..653e577ab3ee 100644
--- a/drivers/usb/host/ehci-fsl.c
+++ b/drivers/usb/host/ehci-fsl.c
@@ -1,6 +1,6 @@
/*
* Copyright 2005-2009 MontaVista Software, Inc.
- * Copyright 2008 Freescale Semiconductor, Inc.
+ * Copyright 2008,2012 Freescale Semiconductor, Inc.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License as published by the
@@ -211,19 +211,32 @@ static void usb_hcd_fsl_remove(struct usb_hcd *hcd,
usb_put_hcd(hcd);
}
-static void ehci_fsl_setup_phy(struct ehci_hcd *ehci,
+static void ehci_fsl_setup_phy(struct usb_hcd *hcd,
enum fsl_usb2_phy_modes phy_mode,
unsigned int port_offset)
{
- u32 portsc;
- struct usb_hcd *hcd = ehci_to_hcd(ehci);
+ u32 portsc, temp;
+ struct ehci_hcd *ehci = hcd_to_ehci(hcd);
void __iomem *non_ehci = hcd->regs;
+ struct device *dev = hcd->self.controller;
+ struct fsl_usb2_platform_data *pdata = dev->platform_data;
+
+ if (pdata->controller_ver < 0) {
+ dev_warn(hcd->self.controller, "Could not get controller version\n");
+ return;
+ }
portsc = ehci_readl(ehci, &ehci->regs->port_status[port_offset]);
portsc &= ~(PORT_PTS_MSK | PORT_PTS_PTW);
switch (phy_mode) {
case FSL_USB2_PHY_ULPI:
+ if (pdata->controller_ver) {
+ /* controller version 1.6 or above */
+ temp = in_be32(non_ehci + FSL_SOC_USB_CTRL);
+ out_be32(non_ehci + FSL_SOC_USB_CTRL, temp |
+ USB_CTRL_USB_EN | ULPI_PHY_CLK_SEL);
+ }
portsc |= PORT_PTS_ULPI;
break;
case FSL_USB2_PHY_SERIAL:
@@ -233,6 +246,14 @@ static void ehci_fsl_setup_phy(struct ehci_hcd *ehci,
portsc |= PORT_PTS_PTW;
/* fall through */
case FSL_USB2_PHY_UTMI:
+ if (pdata->controller_ver) {
+ /* controller version 1.6 or above */
+ temp = in_be32(non_ehci + FSL_SOC_USB_CTRL);
+ out_be32(non_ehci + FSL_SOC_USB_CTRL, temp |
+ UTMI_PHY_EN | USB_CTRL_USB_EN);
+ mdelay(FSL_UTMI_PHY_DLY); /* Delay for UTMI PHY CLK to
+ become stable - 10ms*/
+ }
/* enable UTMI PHY */
setbits32(non_ehci + FSL_SOC_USB_CTRL, CTRL_UTMI_PHY_EN);
portsc |= PORT_PTS_UTMI;
@@ -271,7 +292,7 @@ static void ehci_fsl_usb_setup(struct ehci_hcd *ehci)
if ((pdata->operating_mode == FSL_USB2_DR_HOST) ||
(pdata->operating_mode == FSL_USB2_DR_OTG))
- ehci_fsl_setup_phy(ehci, pdata->phy_mode, 0);
+ ehci_fsl_setup_phy(hcd, pdata->phy_mode, 0);
if (pdata->operating_mode == FSL_USB2_MPH_HOST) {
unsigned int chip, rev, svr;
@@ -285,9 +306,9 @@ static void ehci_fsl_usb_setup(struct ehci_hcd *ehci)
ehci->has_fsl_port_bug = 1;
if (pdata->port_enables & FSL_USB2_PORT0_ENABLED)
- ehci_fsl_setup_phy(ehci, pdata->phy_mode, 0);
+ ehci_fsl_setup_phy(hcd, pdata->phy_mode, 0);
if (pdata->port_enables & FSL_USB2_PORT1_ENABLED)
- ehci_fsl_setup_phy(ehci, pdata->phy_mode, 1);
+ ehci_fsl_setup_phy(hcd, pdata->phy_mode, 1);
}
if (pdata->have_sysif_regs) {