diff options
Diffstat (limited to 'drivers/usb/host')
| -rw-r--r-- | drivers/usb/host/Kconfig | 4 | ||||
| -rw-r--r-- | drivers/usb/host/ehci-fsl.c | 21 | ||||
| -rw-r--r-- | drivers/usb/host/ehci-hcd.c | 17 | ||||
| -rw-r--r-- | drivers/usb/host/ehci-hub.c | 28 | ||||
| -rw-r--r-- | drivers/usb/host/ehci-omap.c | 174 | ||||
| -rw-r--r-- | drivers/usb/host/ehci-pci.c | 8 | ||||
| -rw-r--r-- | drivers/usb/host/ehci-sh.c | 3 | ||||
| -rw-r--r-- | drivers/usb/host/ehci-xilinx-of.c | 4 | ||||
| -rw-r--r-- | drivers/usb/host/ehci.h | 4 | ||||
| -rw-r--r-- | drivers/usb/host/fhci-dbg.c | 12 | ||||
| -rw-r--r-- | drivers/usb/host/fhci-hcd.c | 32 | ||||
| -rw-r--r-- | drivers/usb/host/fhci-hub.c | 16 | ||||
| -rw-r--r-- | drivers/usb/host/fhci-sched.c | 30 | ||||
| -rw-r--r-- | drivers/usb/host/fhci-tds.c | 14 | ||||
| -rw-r--r-- | drivers/usb/host/fhci.h | 22 | ||||
| -rw-r--r-- | drivers/usb/host/imx21-hcd.c | 6 | ||||
| -rw-r--r-- | drivers/usb/host/ohci-hub.c | 2 | ||||
| -rw-r--r-- | drivers/usb/host/ohci-nxp.c | 88 | ||||
| -rw-r--r-- | drivers/usb/host/ohci-omap.c | 27 | ||||
| -rw-r--r-- | drivers/usb/host/ohci.h | 5 | ||||
| -rw-r--r-- | drivers/usb/host/xhci-mem.c | 74 | ||||
| -rw-r--r-- | drivers/usb/host/xhci.c | 10 |
22 files changed, 358 insertions, 243 deletions
diff --git a/drivers/usb/host/Kconfig b/drivers/usb/host/Kconfig index 83e58df29fe3..18ba33da34ec 100644 --- a/drivers/usb/host/Kconfig +++ b/drivers/usb/host/Kconfig @@ -652,7 +652,7 @@ config USB_HCD_BCMA select USB_OHCI_HCD_PLATFORM if USB_OHCI_HCD select USB_EHCI_HCD_PLATFORM if USB_EHCI_HCD help - Enbale support for the EHCI and OCHI host controller on an bcma bus. + Enable support for the EHCI and OCHI host controller on an bcma bus. It converts the bcma driver into two platform device drivers for ehci and ohci. @@ -664,7 +664,7 @@ config USB_HCD_SSB select USB_OHCI_HCD_PLATFORM if USB_OHCI_HCD select USB_EHCI_HCD_PLATFORM if USB_EHCI_HCD help - Enbale support for the EHCI and OCHI host controller on an bcma bus. + Enable support for the EHCI and OCHI host controller on an bcma bus. It converts the bcma driver into two platform device drivers for ehci and ohci. diff --git a/drivers/usb/host/ehci-fsl.c b/drivers/usb/host/ehci-fsl.c index 32865a7145a8..74914de8b9bf 100644 --- a/drivers/usb/host/ehci-fsl.c +++ b/drivers/usb/host/ehci-fsl.c @@ -143,19 +143,19 @@ static int usb_hcd_fsl_probe(const struct hc_driver *driver, if (pdata->operating_mode == FSL_USB2_DR_OTG) { struct ehci_hcd *ehci = hcd_to_ehci(hcd); - ehci->transceiver = usb_get_phy(USB_PHY_TYPE_USB2); - dev_dbg(&pdev->dev, "hcd=0x%p ehci=0x%p, transceiver=0x%p\n", - hcd, ehci, ehci->transceiver); + hcd->phy = usb_get_phy(USB_PHY_TYPE_USB2); + dev_dbg(&pdev->dev, "hcd=0x%p ehci=0x%p, phy=0x%p\n", + hcd, ehci, hcd->phy); - if (!IS_ERR_OR_NULL(ehci->transceiver)) { - retval = otg_set_host(ehci->transceiver->otg, + if (!IS_ERR_OR_NULL(hcd->phy)) { + retval = otg_set_host(hcd->phy->otg, &ehci_to_hcd(ehci)->self); if (retval) { - usb_put_phy(ehci->transceiver); + usb_put_phy(hcd->phy); goto err4; } } else { - dev_err(&pdev->dev, "can't find transceiver\n"); + dev_err(&pdev->dev, "can't find phy\n"); retval = -ENODEV; goto err4; } @@ -191,11 +191,10 @@ static void usb_hcd_fsl_remove(struct usb_hcd *hcd, struct platform_device *pdev) { struct fsl_usb2_platform_data *pdata = pdev->dev.platform_data; - struct ehci_hcd *ehci = hcd_to_ehci(hcd); - if (!IS_ERR_OR_NULL(ehci->transceiver)) { - otg_set_host(ehci->transceiver->otg, NULL); - usb_put_phy(ehci->transceiver); + if (!IS_ERR_OR_NULL(hcd->phy)) { + otg_set_host(hcd->phy->otg, NULL); + usb_put_phy(hcd->phy); } usb_remove_hcd(hcd); diff --git a/drivers/usb/host/ehci-hcd.c b/drivers/usb/host/ehci-hcd.c index b100f5f9f4b6..c49fc1e7895d 100644 --- a/drivers/usb/host/ehci-hcd.c +++ b/drivers/usb/host/ehci-hcd.c @@ -203,11 +203,9 @@ static int handshake (struct ehci_hcd *ehci, void __iomem *ptr, /* check TDI/ARC silicon is in host mode */ static int tdi_in_host_mode (struct ehci_hcd *ehci) { - u32 __iomem *reg_ptr; u32 tmp; - reg_ptr = (u32 __iomem *)(((u8 __iomem *)ehci->regs) + USBMODE); - tmp = ehci_readl(ehci, reg_ptr); + tmp = ehci_readl(ehci, &ehci->regs->usbmode); return (tmp & 3) == USBMODE_CM_HC; } @@ -303,11 +301,9 @@ static int handshake_on_error_set_halt(struct ehci_hcd *ehci, void __iomem *ptr, /* put TDI/ARC silicon into EHCI mode */ static void tdi_reset (struct ehci_hcd *ehci) { - u32 __iomem *reg_ptr; u32 tmp; - reg_ptr = (u32 __iomem *)(((u8 __iomem *)ehci->regs) + USBMODE); - tmp = ehci_readl(ehci, reg_ptr); + tmp = ehci_readl(ehci, &ehci->regs->usbmode); tmp |= USBMODE_CM_HC; /* The default byte access to MMR space is LE after * controller reset. Set the required endian mode @@ -315,7 +311,7 @@ static void tdi_reset (struct ehci_hcd *ehci) */ if (ehci_big_endian_mmio(ehci)) tmp |= USBMODE_BE; - ehci_writel(ehci, tmp, reg_ptr); + ehci_writel(ehci, tmp, &ehci->regs->usbmode); } /* reset a non-running (STS_HALT == 1) controller */ @@ -339,9 +335,8 @@ static int ehci_reset (struct ehci_hcd *ehci) if (ehci->has_hostpc) { ehci_writel(ehci, USBMODE_EX_HC | USBMODE_EX_VBPS, - (u32 __iomem *)(((u8 *)ehci->regs) + USBMODE_EX)); - ehci_writel(ehci, TXFIFO_DEFAULT, - (u32 __iomem *)(((u8 *)ehci->regs) + TXFILLTUNING)); + &ehci->regs->usbmode_ex); + ehci_writel(ehci, TXFIFO_DEFAULT, &ehci->regs->txfill_tuning); } if (retval) return retval; @@ -671,7 +666,9 @@ static int ehci_init(struct usb_hcd *hcd) hw = ehci->async->hw; hw->hw_next = QH_NEXT(ehci, ehci->async->qh_dma); hw->hw_info1 = cpu_to_hc32(ehci, QH_HEAD); +#if defined(CONFIG_PPC_PS3) hw->hw_info1 |= cpu_to_hc32(ehci, (1 << 7)); /* I = 1 */ +#endif hw->hw_token = cpu_to_hc32(ehci, QTD_STS_HALT); hw->hw_qtd_next = EHCI_LIST_END(ehci); ehci->async->qh_state = QH_STATE_LINKED; diff --git a/drivers/usb/host/ehci-hub.c b/drivers/usb/host/ehci-hub.c index fc9e7cc6ac9b..db05e358677a 100644 --- a/drivers/usb/host/ehci-hub.c +++ b/drivers/usb/host/ehci-hub.c @@ -149,10 +149,8 @@ static __maybe_unused void ehci_adjust_port_wakeup_flags(struct ehci_hcd *ehci, if (ehci->has_hostpc) { port = HCS_N_PORTS(ehci->hcs_params); while (port--) { - u32 __iomem *hostpc_reg; + u32 __iomem *hostpc_reg = &ehci->regs->hostpc[port]; - hostpc_reg = (u32 __iomem *)((u8 *) ehci->regs - + HOSTPC0 + 4 * port); temp = ehci_readl(ehci, hostpc_reg); ehci_writel(ehci, temp & ~HOSTPC_PHCD, hostpc_reg); } @@ -185,10 +183,8 @@ static __maybe_unused void ehci_adjust_port_wakeup_flags(struct ehci_hcd *ehci, if (ehci->has_hostpc) { port = HCS_N_PORTS(ehci->hcs_params); while (port--) { - u32 __iomem *hostpc_reg; + u32 __iomem *hostpc_reg = &ehci->regs->hostpc[port]; - hostpc_reg = (u32 __iomem *)((u8 *) ehci->regs - + HOSTPC0 + 4 * port); temp = ehci_readl(ehci, hostpc_reg); ehci_writel(ehci, temp | HOSTPC_PHCD, hostpc_reg); } @@ -285,11 +281,9 @@ static int ehci_bus_suspend (struct usb_hcd *hcd) port = HCS_N_PORTS(ehci->hcs_params); while (port--) { - u32 __iomem *hostpc_reg; + u32 __iomem *hostpc_reg = &ehci->regs->hostpc[port]; u32 t3; - hostpc_reg = (u32 __iomem *)((u8 *) ehci->regs - + HOSTPC0 + 4 * port); t3 = ehci_readl(ehci, hostpc_reg); ehci_writel(ehci, t3 | HOSTPC_PHCD, hostpc_reg); t3 = ehci_readl(ehci, hostpc_reg); @@ -388,10 +382,9 @@ static int ehci_bus_resume (struct usb_hcd *hcd) i = HCS_N_PORTS(ehci->hcs_params); while (i--) { if (test_bit(i, &ehci->bus_suspended)) { - u32 __iomem *hostpc_reg; + u32 __iomem *hostpc_reg = + &ehci->regs->hostpc[i]; - hostpc_reg = (u32 __iomem *)((u8 *) ehci->regs - + HOSTPC0 + 4 * i); temp = ehci_readl(ehci, hostpc_reg); ehci_writel(ehci, temp & ~HOSTPC_PHCD, hostpc_reg); @@ -667,7 +660,7 @@ static int ehci_hub_control ( int ports = HCS_N_PORTS (ehci->hcs_params); u32 __iomem *status_reg = &ehci->regs->port_status[ (wIndex & 0xff) - 1]; - u32 __iomem *hostpc_reg = NULL; + u32 __iomem *hostpc_reg = &ehci->regs->hostpc[(wIndex & 0xff) - 1]; u32 temp, temp1, status; unsigned long flags; int retval = 0; @@ -680,9 +673,6 @@ static int ehci_hub_control ( * power, "this is the one", etc. EHCI spec supports this. */ - if (ehci->has_hostpc) - hostpc_reg = (u32 __iomem *)((u8 *)ehci->regs - + HOSTPC0 + 4 * ((wIndex & 0xff) - 1)); spin_lock_irqsave (&ehci->lock, flags); switch (typeReq) { case ClearHubFeature: @@ -724,7 +714,7 @@ static int ehci_hub_control ( #ifdef CONFIG_USB_OTG if ((hcd->self.otg_port == (wIndex + 1)) && hcd->self.b_hnp_enable) { - otg_start_hnp(ehci->transceiver->otg); + otg_start_hnp(hcd->phy->otg); break; } #endif @@ -734,7 +724,7 @@ static int ehci_hub_control ( goto error; /* clear phy low-power mode before resume */ - if (hostpc_reg) { + if (ehci->has_hostpc) { temp1 = ehci_readl(ehci, hostpc_reg); ehci_writel(ehci, temp1 & ~HOSTPC_PHCD, hostpc_reg); @@ -984,7 +974,7 @@ static int ehci_hub_control ( temp &= ~PORT_WKCONN_E; temp |= PORT_WKDISC_E | PORT_WKOC_E; ehci_writel(ehci, temp | PORT_SUSPEND, status_reg); - if (hostpc_reg) { + if (ehci->has_hostpc) { spin_unlock_irqrestore(&ehci->lock, flags); msleep(5);/* 5ms for HCD enter low pwr mode */ spin_lock_irqsave(&ehci->lock, flags); diff --git a/drivers/usb/host/ehci-omap.c b/drivers/usb/host/ehci-omap.c index a44294d13494..6e15fc87cf60 100644 --- a/drivers/usb/host/ehci-omap.c +++ b/drivers/usb/host/ehci-omap.c @@ -43,6 +43,7 @@ #include <linux/regulator/consumer.h> #include <linux/pm_runtime.h> #include <linux/gpio.h> +#include <linux/clk.h> /* EHCI Register Set */ #define EHCI_INSNREG04 (0xA0) @@ -55,6 +56,15 @@ #define EHCI_INSNREG05_ULPI_EXTREGADD_SHIFT 8 #define EHCI_INSNREG05_ULPI_WRDATA_SHIFT 0 +/* Errata i693 */ +static struct clk *utmi_p1_fck; +static struct clk *utmi_p2_fck; +static struct clk *xclk60mhsp1_ck; +static struct clk *xclk60mhsp2_ck; +static struct clk *usbhost_p1_fck; +static struct clk *usbhost_p2_fck; +static struct clk *init_60m_fclk; + /*-------------------------------------------------------------------------*/ static const struct hc_driver ehci_omap_hc_driver; @@ -70,6 +80,41 @@ static inline u32 ehci_read(void __iomem *base, u32 reg) return __raw_readl(base + reg); } +/* Erratum i693 workaround sequence */ +static void omap_ehci_erratum_i693(struct ehci_hcd *ehci) +{ + int ret = 0; + + /* Switch to the internal 60 MHz clock */ + ret = clk_set_parent(utmi_p1_fck, init_60m_fclk); + if (ret != 0) + ehci_err(ehci, "init_60m_fclk set parent" + "failed error:%d\n", ret); + + ret = clk_set_parent(utmi_p2_fck, init_60m_fclk); + if (ret != 0) + ehci_err(ehci, "init_60m_fclk set parent" + "failed error:%d\n", ret); + + clk_enable(usbhost_p1_fck); + clk_enable(usbhost_p2_fck); + + /* Wait 1ms and switch back to the external clock */ + mdelay(1); + ret = clk_set_parent(utmi_p1_fck, xclk60mhsp1_ck); + if (ret != 0) + ehci_err(ehci, "xclk60mhsp1_ck set parent" + "failed error:%d\n", ret); + + ret = clk_set_parent(utmi_p2_fck, xclk60mhsp2_ck); + if (ret != 0) + ehci_err(ehci, "xclk60mhsp2_ck set parent" + "failed error:%d\n", ret); + + clk_disable(usbhost_p1_fck); + clk_disable(usbhost_p2_fck); +} + static void omap_ehci_soft_phy_reset(struct platform_device *pdev, u8 port) { struct usb_hcd *hcd = dev_get_drvdata(&pdev->dev); @@ -100,6 +145,50 @@ static void omap_ehci_soft_phy_reset(struct platform_device *pdev, u8 port) } } +static int omap_ehci_hub_control( + struct usb_hcd *hcd, + u16 typeReq, + u16 wValue, + u16 wIndex, + char *buf, + u16 wLength +) +{ + struct ehci_hcd *ehci = hcd_to_ehci(hcd); + u32 __iomem *status_reg = &ehci->regs->port_status[ + (wIndex & 0xff) - 1]; + u32 temp; + unsigned long flags; + int retval = 0; + + spin_lock_irqsave(&ehci->lock, flags); + + if (typeReq == SetPortFeature && wValue == USB_PORT_FEAT_SUSPEND) { + temp = ehci_readl(ehci, status_reg); + if ((temp & PORT_PE) == 0 || (temp & PORT_RESET) != 0) { + retval = -EPIPE; + goto done; + } + + temp &= ~PORT_WKCONN_E; + temp |= PORT_WKDISC_E | PORT_WKOC_E; + ehci_writel(ehci, temp | PORT_SUSPEND, status_reg); + + omap_ehci_erratum_i693(ehci); + + set_bit((wIndex & 0xff) - 1, &ehci->suspended_ports); + goto done; + } + + spin_unlock_irqrestore(&ehci->lock, flags); + + /* Handle the hub control events here */ + return ehci_hub_control(hcd, typeReq, wValue, wIndex, buf, wLength); +done: + spin_unlock_irqrestore(&ehci->lock, flags); + return retval; +} + static void disable_put_regulator( struct ehci_hcd_omap_platform_data *pdata) { @@ -258,17 +347,89 @@ static int ehci_hcd_omap_probe(struct platform_device *pdev) ret = usb_add_hcd(hcd, irq, IRQF_SHARED); if (ret) { dev_err(dev, "failed to add hcd with err %d\n", ret); - goto err_add_hcd; + goto err_pm_runtime; } /* root ports should always stay powered */ ehci_port_power(omap_ehci, 1); + /* get clocks */ + utmi_p1_fck = clk_get(dev, "utmi_p1_gfclk"); + if (IS_ERR(utmi_p1_fck)) { + ret = PTR_ERR(utmi_p1_fck); + dev_err(dev, "utmi_p1_gfclk failed error:%d\n", ret); + goto err_add_hcd; + } + + xclk60mhsp1_ck = clk_get(dev, "xclk60mhsp1_ck"); + if (IS_ERR(xclk60mhsp1_ck)) { + ret = PTR_ERR(xclk60mhsp1_ck); + dev_err(dev, "xclk60mhsp1_ck failed error:%d\n", ret); + goto err_utmi_p1_fck; + } + + utmi_p2_fck = clk_get(dev, "utmi_p2_gfclk"); + if (IS_ERR(utmi_p2_fck)) { + ret = PTR_ERR(utmi_p2_fck); + dev_err(dev, "utmi_p2_gfclk failed error:%d\n", ret); + goto err_xclk60mhsp1_ck; + } + + xclk60mhsp2_ck = clk_get(dev, "xclk60mhsp2_ck"); + if (IS_ERR(xclk60mhsp2_ck)) { + ret = PTR_ERR(xclk60mhsp2_ck); + dev_err(dev, "xclk60mhsp2_ck failed error:%d\n", ret); + goto err_utmi_p2_fck; + } + + usbhost_p1_fck = clk_get(dev, "usb_host_hs_utmi_p1_clk"); + if (IS_ERR(usbhost_p1_fck)) { + ret = PTR_ERR(usbhost_p1_fck); + dev_err(dev, "usbhost_p1_fck failed error:%d\n", ret); + goto err_xclk60mhsp2_ck; + } + + usbhost_p2_fck = clk_get(dev, "usb_host_hs_utmi_p2_clk"); + if (IS_ERR(usbhost_p2_fck)) { + ret = PTR_ERR(usbhost_p2_fck); + dev_err(dev, "usbhost_p2_fck failed error:%d\n", ret); + goto err_usbhost_p1_fck; + } + + init_60m_fclk = clk_get(dev, "init_60m_fclk"); + if (IS_ERR(init_60m_fclk)) { + ret = PTR_ERR(init_60m_fclk); + dev_err(dev, "init_60m_fclk failed error:%d\n", ret); + goto err_usbhost_p2_fck; + } + return 0; +err_usbhost_p2_fck: + clk_put(usbhost_p2_fck); + +err_usbhost_p1_fck: + clk_put(usbhost_p1_fck); + +err_xclk60mhsp2_ck: + clk_put(xclk60mhsp2_ck); + +err_utmi_p2_fck: + clk_put(utmi_p2_fck); + +err_xclk60mhsp1_ck: + clk_put(xclk60mhsp1_ck); + +err_utmi_p1_fck: + clk_put(utmi_p1_fck); + err_add_hcd: + usb_remove_hcd(hcd); + +err_pm_runtime: disable_put_regulator(pdata); pm_runtime_put_sync(dev); + usb_put_hcd(hcd); err_io: iounmap(regs); @@ -294,6 +455,15 @@ static int ehci_hcd_omap_remove(struct platform_device *pdev) disable_put_regulator(dev->platform_data); iounmap(hcd->regs); usb_put_hcd(hcd); + + clk_put(utmi_p1_fck); + clk_put(utmi_p2_fck); + clk_put(xclk60mhsp1_ck); + clk_put(xclk60mhsp2_ck); + clk_put(usbhost_p1_fck); + clk_put(usbhost_p2_fck); + clk_put(init_60m_fclk); + pm_runtime_put_sync(dev); pm_runtime_disable(dev); @@ -364,7 +534,7 @@ static const struct hc_driver ehci_omap_hc_driver = { * root hub support */ .hub_status_data = ehci_hub_status_data, - .hub_control = ehci_hub_control, + .hub_control = omap_ehci_hub_control, .bus_suspend = ehci_bus_suspend, .bus_resume = ehci_bus_resume, diff --git a/drivers/usb/host/ehci-pci.c b/drivers/usb/host/ehci-pci.c index bc94d7bf072d..123481793a47 100644 --- a/drivers/usb/host/ehci-pci.c +++ b/drivers/usb/host/ehci-pci.c @@ -144,14 +144,6 @@ static int ehci_pci_setup(struct usb_hcd *hcd) hcd->has_tt = 1; tdi_reset(ehci); } - if (pdev->subsystem_vendor == PCI_VENDOR_ID_ASUSTEK) { - /* EHCI #1 or #2 on 6 Series/C200 Series chipset */ - if (pdev->device == 0x1c26 || pdev->device == 0x1c2d) { - ehci_info(ehci, "broken D3 during system sleep on ASUS\n"); - hcd->broken_pci_sleep = 1; - device_set_wakeup_capable(&pdev->dev, false); - } - } break; case PCI_VENDOR_ID_TDI: if (pdev->device == PCI_DEVICE_ID_TDI_EHCI) { diff --git a/drivers/usb/host/ehci-sh.c b/drivers/usb/host/ehci-sh.c index ca819cdd0c5e..e7cb3925abf8 100644 --- a/drivers/usb/host/ehci-sh.c +++ b/drivers/usb/host/ehci-sh.c @@ -126,8 +126,7 @@ static int ehci_hcd_sh_probe(struct platform_device *pdev) goto fail_create_hcd; } - if (pdev->dev.platform_data != NULL) - pdata = pdev->dev.platform_data; + pdata = pdev->dev.platform_data; /* initialize hcd */ hcd = usb_create_hcd(&ehci_sh_hc_driver, &pdev->dev, diff --git a/drivers/usb/host/ehci-xilinx-of.c b/drivers/usb/host/ehci-xilinx-of.c index 9c2cc4633894..e9713d589e30 100644 --- a/drivers/usb/host/ehci-xilinx-of.c +++ b/drivers/usb/host/ehci-xilinx-of.c @@ -270,14 +270,12 @@ static int ehci_hcd_xilinx_of_remove(struct platform_device *op) * * Properly shutdown the hcd, call driver's shutdown routine. */ -static int ehci_hcd_xilinx_of_shutdown(struct platform_device *op) +static void ehci_hcd_xilinx_of_shutdown(struct platform_device *op) { struct usb_hcd *hcd = dev_get_drvdata(&op->dev); if (hcd->driver->shutdown) hcd->driver->shutdown(hcd); - - return 0; } diff --git a/drivers/usb/host/ehci.h b/drivers/usb/host/ehci.h index 2694ed6558d2..85c3572155d1 100644 --- a/drivers/usb/host/ehci.h +++ b/drivers/usb/host/ehci.h @@ -175,10 +175,6 @@ struct ehci_hcd { /* one per controller */ #ifdef DEBUG struct dentry *debug_dir; #endif - /* - * OTG controllers and transceivers need software interaction - */ - struct usb_phy *transceiver; }; /* convert between an HCD pointer and the corresponding EHCI_HCD */ diff --git a/drivers/usb/host/fhci-dbg.c b/drivers/usb/host/fhci-dbg.c index 6fe550049119..f238cb37305c 100644 --- a/drivers/usb/host/fhci-dbg.c +++ b/drivers/usb/host/fhci-dbg.c @@ -41,7 +41,7 @@ void fhci_dbg_isr(struct fhci_hcd *fhci, int usb_er) static int fhci_dfs_regs_show(struct seq_file *s, void *v) { struct fhci_hcd *fhci = s->private; - struct fhci_regs __iomem *regs = fhci->regs; + struct qe_usb_ctlr __iomem *regs = fhci->regs; seq_printf(s, "mode: 0x%x\n" "addr: 0x%x\n" @@ -50,11 +50,11 @@ static int fhci_dfs_regs_show(struct seq_file *s, void *v) "status: 0x%x\n" "SOF timer: %d\n" "frame number: %d\n" "lines status: 0x%x\n", - in_8(®s->usb_mod), in_8(®s->usb_addr), - in_8(®s->usb_comm), in_be16(®s->usb_ep[0]), - in_be16(®s->usb_event), in_be16(®s->usb_mask), - in_8(®s->usb_status), in_be16(®s->usb_sof_tmr), - in_be16(®s->usb_frame_num), + in_8(®s->usb_usmod), in_8(®s->usb_usadr), + in_8(®s->usb_uscom), in_be16(®s->usb_usep[0]), + in_be16(®s->usb_usber), in_be16(®s->usb_usbmr), + in_8(®s->usb_usbs), in_be16(®s->usb_ussft), + in_be16(®s->usb_usfrn), fhci_ioports_check_bus_state(fhci)); return 0; diff --git a/drivers/usb/host/fhci-hcd.c b/drivers/usb/host/fhci-hcd.c index d2623747b489..7da1a26bed2e 100644 --- a/drivers/usb/host/fhci-hcd.c +++ b/drivers/usb/host/fhci-hcd.c @@ -40,8 +40,8 @@ void fhci_start_sof_timer(struct fhci_hcd *fhci) /* clear frame_n */ out_be16(&fhci->pram->frame_num, 0); - out_be16(&fhci->regs->usb_sof_tmr, 0); - setbits8(&fhci->regs->usb_mod, USB_MODE_SFTE); + out_be16(&fhci->regs->usb_ussft, 0); + setbits8(&fhci->regs->usb_usmod, USB_MODE_SFTE); fhci_dbg(fhci, "<- %s\n", __func__); } @@ -50,7 +50,7 @@ void fhci_stop_sof_timer(struct fhci_hcd *fhci) { fhci_dbg(fhci, "-> %s\n", __func__); - clrbits8(&fhci->regs->usb_mod, USB_MODE_SFTE); + clrbits8(&fhci->regs->usb_usmod, USB_MODE_SFTE); gtm_stop_timer16(fhci->timer); fhci_dbg(fhci, "<- %s\n", __func__); @@ -58,7 +58,7 @@ void fhci_stop_sof_timer(struct fhci_hcd *fhci) u16 fhci_get_sof_timer_count(struct fhci_usb *usb) { - return be16_to_cpu(in_be16(&usb->fhci->regs->usb_sof_tmr) / 12); + return be16_to_cpu(in_be16(&usb->fhci->regs->usb_ussft) / 12); } /* initialize the endpoint zero */ @@ -88,8 +88,8 @@ void fhci_usb_enable_interrupt(struct fhci_usb *usb) enable_irq(fhci_to_hcd(fhci)->irq); /* initialize the event register and mask register */ - out_be16(&usb->fhci->regs->usb_event, 0xffff); - out_be16(&usb->fhci->regs->usb_mask, usb->saved_msk); + out_be16(&usb->fhci->regs->usb_usber, 0xffff); + out_be16(&usb->fhci->regs->usb_usbmr, usb->saved_msk); /* enable the timer interrupts */ enable_irq(fhci->timer->irq); @@ -109,7 +109,7 @@ void fhci_usb_disable_interrupt(struct fhci_usb *usb) /* disable the usb interrupt */ disable_irq_nosync(fhci_to_hcd(fhci)->irq); - out_be16(&usb->fhci->regs->usb_mask, 0); + out_be16(&usb->fhci->regs->usb_usbmr, 0); } usb->intr_nesting_cnt++; } @@ -119,9 +119,9 @@ static u32 fhci_usb_enable(struct fhci_hcd *fhci) { struct fhci_usb *usb = fhci->usb_lld; - out_be16(&usb->fhci->regs->usb_event, 0xffff); - out_be16(&usb->fhci->regs->usb_mask, usb->saved_msk); - setbits8(&usb->fhci->regs->usb_mod, USB_MODE_EN); + out_be16(&usb->fhci->regs->usb_usber, 0xffff); + out_be16(&usb->fhci->regs->usb_usbmr, usb->saved_msk); + setbits8(&usb->fhci->regs->usb_usmod, USB_MODE_EN); mdelay(100); @@ -141,7 +141,7 @@ static u32 fhci_usb_disable(struct fhci_hcd *fhci) usb->port_status == FHCI_PORT_LOW) fhci_device_disconnected_interrupt(fhci); - clrbits8(&usb->fhci->regs->usb_mod, USB_MODE_EN); + clrbits8(&usb->fhci->regs->usb_usmod, USB_MODE_EN); return 0; } @@ -285,13 +285,13 @@ static int fhci_usb_init(struct fhci_hcd *fhci) USB_E_IDLE_MASK | USB_E_RESET_MASK | USB_E_SFT_MASK | USB_E_MSF_MASK); - out_8(&usb->fhci->regs->usb_mod, USB_MODE_HOST | USB_MODE_EN); + out_8(&usb->fhci->regs->usb_usmod, USB_MODE_HOST | USB_MODE_EN); /* clearing the mask register */ - out_be16(&usb->fhci->regs->usb_mask, 0); + out_be16(&usb->fhci->regs->usb_usbmr, 0); /* initialing the event register */ - out_be16(&usb->fhci->regs->usb_event, 0xffff); + out_be16(&usb->fhci->regs->usb_usber, 0xffff); if (endpoint_zero_init(usb, DEFAULT_DATA_MEM, DEFAULT_RING_LEN) != 0) { fhci_usb_free(usb); @@ -745,8 +745,8 @@ static int __devinit of_fhci_probe(struct platform_device *ofdev) } /* Clear and disable any pending interrupts. */ - out_be16(&fhci->regs->usb_event, 0xffff); - out_be16(&fhci->regs->usb_mask, 0); + out_be16(&fhci->regs->usb_usber, 0xffff); + out_be16(&fhci->regs->usb_usbmr, 0); ret = usb_add_hcd(hcd, usb_irq, 0); if (ret < 0) diff --git a/drivers/usb/host/fhci-hub.c b/drivers/usb/host/fhci-hub.c index 348fe62e94f7..6af2512f8378 100644 --- a/drivers/usb/host/fhci-hub.c +++ b/drivers/usb/host/fhci-hub.c @@ -97,7 +97,7 @@ void fhci_port_disable(struct fhci_hcd *fhci) /* Enable IDLE since we want to know if something comes along */ usb->saved_msk |= USB_E_IDLE_MASK; - out_be16(&usb->fhci->regs->usb_mask, usb->saved_msk); + out_be16(&usb->fhci->regs->usb_usbmr, usb->saved_msk); /* check if during the disconnection process attached new device */ if (port_status == FHCI_PORT_WAITING) @@ -158,21 +158,21 @@ void fhci_port_reset(void *lld) fhci_stop_sof_timer(fhci); /* disable the USB controller */ - mode = in_8(&fhci->regs->usb_mod); - out_8(&fhci->regs->usb_mod, mode & (~USB_MODE_EN)); + mode = in_8(&fhci->regs->usb_usmod); + out_8(&fhci->regs->usb_usmod, mode & (~USB_MODE_EN)); /* disable idle interrupts */ - mask = in_be16(&fhci->regs->usb_mask); - out_be16(&fhci->regs->usb_mask, mask & (~USB_E_IDLE_MASK)); + mask = in_be16(&fhci->regs->usb_usbmr); + out_be16(&fhci->regs->usb_usbmr, mask & (~USB_E_IDLE_MASK)); fhci_io_port_generate_reset(fhci); /* enable interrupt on this endpoint */ - out_be16(&fhci->regs->usb_mask, mask); + out_be16(&fhci->regs->usb_usbmr, mask); /* enable the USB controller */ - mode = in_8(&fhci->regs->usb_mod); - out_8(&fhci->regs->usb_mod, mode | USB_MODE_EN); + mode = in_8(&fhci->regs->usb_usmod); + out_8(&fhci->regs->usb_usmod, mode | USB_MODE_EN); fhci_start_sof_timer(fhci); fhci_dbg(fhci, "<- %s\n", __func__); diff --git a/drivers/usb/host/fhci-sched.c b/drivers/usb/host/fhci-sched.c index 2df851b4bc7c..2dc8a40e39d7 100644 --- a/drivers/usb/host/fhci-sched.c +++ b/drivers/usb/host/fhci-sched.c @@ -132,8 +132,8 @@ void fhci_flush_all_transmissions(struct fhci_usb *usb) u8 mode; struct td *td; - mode = in_8(&usb->fhci->regs->usb_mod); - clrbits8(&usb->fhci->regs->usb_mod, USB_MODE_EN); + mode = in_8(&usb->fhci->regs->usb_usmod); + clrbits8(&usb->fhci->regs->usb_usmod, USB_MODE_EN); fhci_flush_bds(usb); @@ -147,9 +147,9 @@ void fhci_flush_all_transmissions(struct fhci_usb *usb) usb->actual_frame->frame_status = FRAME_END_TRANSMISSION; /* reset the event register */ - out_be16(&usb->fhci->regs->usb_event, 0xffff); + out_be16(&usb->fhci->regs->usb_usber, 0xffff); /* enable the USB controller */ - out_8(&usb->fhci->regs->usb_mod, mode | USB_MODE_EN); + out_8(&usb->fhci->regs->usb_usmod, mode | USB_MODE_EN); } /* @@ -414,7 +414,7 @@ static void sof_interrupt(struct fhci_hcd *fhci) usb->port_status = FHCI_PORT_FULL; /* Disable IDLE */ usb->saved_msk &= ~USB_E_IDLE_MASK; - out_be16(&usb->fhci->regs->usb_mask, usb->saved_msk); + out_be16(&usb->fhci->regs->usb_usbmr, usb->saved_msk); } gtm_set_exact_timer16(fhci->timer, usb->max_frame_usage, false); @@ -433,14 +433,14 @@ void fhci_device_disconnected_interrupt(struct fhci_hcd *fhci) fhci_dbg(fhci, "-> %s\n", __func__); fhci_usb_disable_interrupt(usb); - clrbits8(&usb->fhci->regs->usb_mod, USB_MODE_LSS); + clrbits8(&usb->fhci->regs->usb_usmod, USB_MODE_LSS); usb->port_status = FHCI_PORT_DISABLED; fhci_stop_sof_timer(fhci); /* Enable IDLE since we want to know if something comes along */ usb->saved_msk |= USB_E_IDLE_MASK; - out_be16(&usb->fhci->regs->usb_mask, usb->saved_msk); + out_be16(&usb->fhci->regs->usb_usbmr, usb->saved_msk); usb->vroot_hub->port.wPortStatus &= ~USB_PORT_STAT_CONNECTION; usb->vroot_hub->port.wPortChange |= USB_PORT_STAT_C_CONNECTION; @@ -473,7 +473,7 @@ void fhci_device_connected_interrupt(struct fhci_hcd *fhci) } usb->port_status = FHCI_PORT_LOW; - setbits8(&usb->fhci->regs->usb_mod, USB_MODE_LSS); + setbits8(&usb->fhci->regs->usb_usmod, USB_MODE_LSS); usb->vroot_hub->port.wPortStatus |= (USB_PORT_STAT_LOW_SPEED | USB_PORT_STAT_CONNECTION); @@ -491,7 +491,7 @@ void fhci_device_connected_interrupt(struct fhci_hcd *fhci) } usb->port_status = FHCI_PORT_FULL; - clrbits8(&usb->fhci->regs->usb_mod, USB_MODE_LSS); + clrbits8(&usb->fhci->regs->usb_usmod, USB_MODE_LSS); usb->vroot_hub->port.wPortStatus &= ~USB_PORT_STAT_LOW_SPEED; usb->vroot_hub->port.wPortStatus |= @@ -535,7 +535,7 @@ static void abort_transmission(struct fhci_usb *usb) /* issue stop Tx command */ qe_issue_cmd(QE_USB_STOP_TX, QE_CR_SUBBLOCK_USB, EP_ZERO, 0); /* flush Tx FIFOs */ - out_8(&usb->fhci->regs->usb_comm, USB_CMD_FLUSH_FIFO | EP_ZERO); + out_8(&usb->fhci->regs->usb_uscom, USB_CMD_FLUSH_FIFO | EP_ZERO); udelay(1000); /* reset Tx BDs */ fhci_flush_bds(usb); @@ -555,11 +555,11 @@ irqreturn_t fhci_irq(struct usb_hcd *hcd) usb = fhci->usb_lld; - usb_er |= in_be16(&usb->fhci->regs->usb_event) & - in_be16(&usb->fhci->regs->usb_mask); + usb_er |= in_be16(&usb->fhci->regs->usb_usber) & + in_be16(&usb->fhci->regs->usb_usbmr); /* clear event bits for next time */ - out_be16(&usb->fhci->regs->usb_event, usb_er); + out_be16(&usb->fhci->regs->usb_usber, usb_er); fhci_dbg_isr(fhci, usb_er); @@ -573,7 +573,7 @@ irqreturn_t fhci_irq(struct usb_hcd *hcd) /* Turn on IDLE since we want to disconnect */ usb->saved_msk |= USB_E_IDLE_MASK; - out_be16(&usb->fhci->regs->usb_event, + out_be16(&usb->fhci->regs->usb_usber, usb->saved_msk); } else if (usb->port_status == FHCI_PORT_DISABLED) { if (fhci_ioports_check_bus_state(fhci) == 1) @@ -611,7 +611,7 @@ irqreturn_t fhci_irq(struct usb_hcd *hcd) /* XXX usb->port_status = FHCI_PORT_WAITING; */ /* Disable IDLE */ usb->saved_msk &= ~USB_E_IDLE_MASK; - out_be16(&usb->fhci->regs->usb_mask, + out_be16(&usb->fhci->regs->usb_usbmr, usb->saved_msk); } else { fhci_dbg_isr(fhci, -1); diff --git a/drivers/usb/host/fhci-tds.c b/drivers/usb/host/fhci-tds.c index c5ed88199292..1498061f0aea 100644 --- a/drivers/usb/host/fhci-tds.c +++ b/drivers/usb/host/fhci-tds.c @@ -249,7 +249,7 @@ void fhci_init_ep_registers(struct fhci_usb *usb, struct endpoint *ep, u8 rt; /* set the endpoint registers according to the endpoint */ - out_be16(&usb->fhci->regs->usb_ep[0], + out_be16(&usb->fhci->regs->usb_usep[0], USB_TRANS_CTR | USB_EP_MF | USB_EP_RTE); out_be16(&usb->fhci->pram->ep_ptr[0], cpm_muram_offset(ep->ep_pram_ptr)); @@ -463,7 +463,7 @@ u32 fhci_host_transaction(struct fhci_usb *usb, cq_put(&ep->conf_frame_Q, pkt); if (cq_howmany(&ep->conf_frame_Q) == 1) - out_8(&usb->fhci->regs->usb_comm, USB_CMD_STR_FIFO); + out_8(&usb->fhci->regs->usb_uscom, USB_CMD_STR_FIFO); return 0; } @@ -535,8 +535,8 @@ void fhci_flush_actual_frame(struct fhci_usb *usb) struct endpoint *ep = usb->ep0; /* disable the USB controller */ - mode = in_8(&usb->fhci->regs->usb_mod); - out_8(&usb->fhci->regs->usb_mod, mode & ~USB_MODE_EN); + mode = in_8(&usb->fhci->regs->usb_usmod); + out_8(&usb->fhci->regs->usb_usmod, mode & ~USB_MODE_EN); tb_ptr = in_be16(&ep->ep_pram_ptr->tx_bd_ptr); td = cpm_muram_addr(tb_ptr); @@ -571,9 +571,9 @@ void fhci_flush_actual_frame(struct fhci_usb *usb) usb->actual_frame->frame_status = FRAME_TIMER_END_TRANSMISSION; /* reset the event register */ - out_be16(&usb->fhci->regs->usb_event, 0xffff); + out_be16(&usb->fhci->regs->usb_usber, 0xffff); /* enable the USB controller */ - out_8(&usb->fhci->regs->usb_mod, mode | USB_MODE_EN); + out_8(&usb->fhci->regs->usb_usmod, mode | USB_MODE_EN); } /* handles Tx confirm and Tx error interrupt */ @@ -613,7 +613,7 @@ void fhci_host_transmit_actual_frame(struct fhci_usb *usb) /* start transmit only if we have something in the TDs */ if (in_be16(&td->status) & TD_R) - out_8(&usb->fhci->regs->usb_comm, USB_CMD_STR_FIFO); + out_8(&usb->fhci->regs->usb_uscom, USB_CMD_STR_FIFO); if (in_be32(&ep->conf_td->buf_ptr) == DUMMY_BD_BUFFER) { out_be32(&old_td->buf_ptr, 0); diff --git a/drivers/usb/host/fhci.h b/drivers/usb/host/fhci.h index dc6939a44a1a..7cc1c32dc36c 100644 --- a/drivers/usb/host/fhci.h +++ b/drivers/usb/host/fhci.h @@ -28,6 +28,7 @@ #include <linux/usb.h> #include <linux/usb/hcd.h> #include <asm/qe.h> +#include <asm/immap_qe.h> #define USB_CLOCK 48000000 @@ -173,25 +174,6 @@ #define USB_E_TXB_MASK 0x0002 #define USB_E_RXB_MASK 0x0001 -/* Freescale USB Host controller registers */ -struct fhci_regs { - u8 usb_mod; /* mode register */ - u8 usb_addr; /* address register */ - u8 usb_comm; /* command register */ - u8 reserved1[1]; - __be16 usb_ep[4]; /* endpoint register */ - u8 reserved2[4]; - __be16 usb_event; /* event register */ - u8 reserved3[2]; - __be16 usb_mask; /* mask register */ - u8 reserved4[1]; - u8 usb_status; /* status register */ - __be16 usb_sof_tmr; /* Start Of Frame timer */ - u8 reserved5[2]; - __be16 usb_frame_num; /* frame number register */ - u8 reserved6[1]; -}; - /* Freescale USB HOST */ struct fhci_pram { __be16 ep_ptr[4]; /* Endpoint porter reg */ @@ -267,7 +249,7 @@ struct fhci_hcd { int gpios[NUM_GPIOS]; bool alow_gpios[NUM_GPIOS]; - struct fhci_regs __iomem *regs; /* I/O memory used to communicate */ + struct qe_usb_ctlr __iomem *regs; /* I/O memory used to communicate */ struct fhci_pram __iomem *pram; /* Parameter RAM */ struct gtm_timer *timer; diff --git a/drivers/usb/host/imx21-hcd.c b/drivers/usb/host/imx21-hcd.c index ff471c1c165e..f19e2690c232 100644 --- a/drivers/usb/host/imx21-hcd.c +++ b/drivers/usb/host/imx21-hcd.c @@ -1811,7 +1811,7 @@ static int imx21_remove(struct platform_device *pdev) usb_remove_hcd(hcd); if (res != NULL) { - clk_disable(imx21->clk); + clk_disable_unprepare(imx21->clk); clk_put(imx21->clk); iounmap(imx21->regs); release_mem_region(res->start, resource_size(res)); @@ -1884,7 +1884,7 @@ static int imx21_probe(struct platform_device *pdev) ret = clk_set_rate(imx21->clk, clk_round_rate(imx21->clk, 48000000)); if (ret) goto failed_clock_set; - ret = clk_enable(imx21->clk); + ret = clk_prepare_enable(imx21->clk); if (ret) goto failed_clock_enable; @@ -1900,7 +1900,7 @@ static int imx21_probe(struct platform_device *pdev) return 0; failed_add_hcd: - clk_disable(imx21->clk); + clk_disable_unprepare(imx21->clk); failed_clock_enable: failed_clock_set: clk_put(imx21->clk); diff --git a/drivers/usb/host/ohci-hub.c b/drivers/usb/host/ohci-hub.c index 836772dfabd3..2f3619eefefa 100644 --- a/drivers/usb/host/ohci-hub.c +++ b/drivers/usb/host/ohci-hub.c @@ -317,7 +317,7 @@ static int ohci_bus_resume (struct usb_hcd *hcd) } /* Carry out the final steps of resuming the controller device */ -static void ohci_finish_controller_resume(struct usb_hcd *hcd) +static void __maybe_unused ohci_finish_controller_resume(struct usb_hcd *hcd) { struct ohci_hcd *ohci = hcd_to_ohci(hcd); int port; diff --git a/drivers/usb/host/ohci-nxp.c b/drivers/usb/host/ohci-nxp.c index 1e364ec962fb..a446386bf779 100644 --- a/drivers/usb/host/ohci-nxp.c +++ b/drivers/usb/host/ohci-nxp.c @@ -43,16 +43,6 @@ #define USB_HOST_NEED_CLK_EN (1 << 21) #define PAD_CONTROL_LAST_DRIVEN (1 << 19) -#define USB_OTG_CLK_CTRL IO_ADDRESS(USB_CONFIG_BASE + 0xFF4) -#define USB_OTG_CLK_STAT IO_ADDRESS(USB_CONFIG_BASE + 0xFF8) - -/* USB_OTG_CLK_CTRL bit defines */ -#define AHB_M_CLOCK_ON (1 << 4) -#define OTG_CLOCK_ON (1 << 3) -#define I2C_CLOCK_ON (1 << 2) -#define DEV_CLOCK_ON (1 << 1) -#define HOST_CLOCK_ON (1 << 0) - #define USB_OTG_STAT_CONTROL IO_ADDRESS(USB_CONFIG_BASE + 0x110) /* USB_OTG_STAT_CONTROL bit defines */ @@ -72,7 +62,9 @@ static struct i2c_client *isp1301_i2c_client; extern int usb_disabled(void); -static struct clk *usb_clk; +static struct clk *usb_pll_clk; +static struct clk *usb_dev_clk; +static struct clk *usb_otg_clk; static void isp1301_configure_pnx4008(void) { @@ -249,8 +241,6 @@ static const struct hc_driver ohci_nxp_hc_driver = { .start_port_reset = ohci_start_port_reset, }; -#define USB_CLOCK_MASK (AHB_M_CLOCK_ON| OTG_CLOCK_ON | HOST_CLOCK_ON | I2C_CLOCK_ON) - static void nxp_set_usb_bits(void) { if (machine_is_pnx4008()) { @@ -327,41 +317,63 @@ static int __devinit usb_hcd_nxp_probe(struct platform_device *pdev) /* Enable AHB slave USB clock, needed for further USB clock control */ __raw_writel(USB_SLAVE_HCLK_EN | PAD_CONTROL_LAST_DRIVEN, USB_CTRL); - isp1301_configure(); - /* Enable USB PLL */ - usb_clk = clk_get(&pdev->dev, "ck_pll5"); - if (IS_ERR(usb_clk)) { + usb_pll_clk = clk_get(&pdev->dev, "ck_pll5"); + if (IS_ERR(usb_pll_clk)) { dev_err(&pdev->dev, "failed to acquire USB PLL\n"); - ret = PTR_ERR(usb_clk); + ret = PTR_ERR(usb_pll_clk); goto out1; } - ret = clk_enable(usb_clk); + ret = clk_enable(usb_pll_clk); if (ret < 0) { dev_err(&pdev->dev, "failed to start USB PLL\n"); goto out2; } - ret = clk_set_rate(usb_clk, 48000); + ret = clk_set_rate(usb_pll_clk, 48000); if (ret < 0) { dev_err(&pdev->dev, "failed to set USB clock rate\n"); goto out3; } + /* Enable USB device clock */ + usb_dev_clk = clk_get(&pdev->dev, "ck_usbd"); + if (IS_ERR(usb_dev_clk)) { + dev_err(&pdev->dev, "failed to acquire USB DEV Clock\n"); + ret = PTR_ERR(usb_dev_clk); + goto out4; + } + + ret = clk_enable(usb_dev_clk); + if (ret < 0) { + dev_err(&pdev->dev, "failed to start USB DEV Clock\n"); + goto out5; + } + + /* Enable USB otg clocks */ + usb_otg_clk = clk_get(&pdev->dev, "ck_usb_otg"); + if (IS_ERR(usb_otg_clk)) { + dev_err(&pdev->dev, "failed to acquire USB DEV Clock\n"); + ret = PTR_ERR(usb_dev_clk); + goto out6; + } + __raw_writel(__raw_readl(USB_CTRL) | USB_HOST_NEED_CLK_EN, USB_CTRL); - /* Set to enable all needed USB clocks */ - __raw_writel(USB_CLOCK_MASK, USB_OTG_CLK_CTRL); + ret = clk_enable(usb_otg_clk); + if (ret < 0) { + dev_err(&pdev->dev, "failed to start USB DEV Clock\n"); + goto out7; + } - while ((__raw_readl(USB_OTG_CLK_STAT) & USB_CLOCK_MASK) != - USB_CLOCK_MASK) ; + isp1301_configure(); hcd = usb_create_hcd(driver, &pdev->dev, dev_name(&pdev->dev)); if (!hcd) { dev_err(&pdev->dev, "Failed to allocate HC buffer\n"); ret = -ENOMEM; - goto out3; + goto out8; } /* Set all USB bits in the Start Enable register */ @@ -371,14 +383,14 @@ static int __devinit usb_hcd_nxp_probe(struct platform_device *pdev) if (!res) { dev_err(&pdev->dev, "Failed to get MEM resource\n"); ret = -ENOMEM; - goto out4; + goto out8; } hcd->regs = devm_request_and_ioremap(&pdev->dev, res); if (!hcd->regs) { dev_err(&pdev->dev, "Failed to devm_request_and_ioremap\n"); ret = -ENOMEM; - goto out4; + goto out8; } hcd->rsrc_start = res->start; hcd->rsrc_len = resource_size(res); @@ -386,7 +398,7 @@ static int __devinit usb_hcd_nxp_probe(struct platform_device *pdev) irq = platform_get_irq(pdev, 0); if (irq < 0) { ret = -ENXIO; - goto out4; + goto out8; } nxp_start_hc(); @@ -400,13 +412,21 @@ static int __devinit usb_hcd_nxp_probe(struct platform_device *pdev) return ret; nxp_stop_hc(); -out4: +out8: nxp_unset_usb_bits(); usb_put_hcd(hcd); +out7: + clk_disable(usb_otg_clk); +out6: + clk_put(usb_otg_clk); +out5: + clk_disable(usb_dev_clk); +out4: + clk_put(usb_dev_clk); out3: - clk_disable(usb_clk); + clk_disable(usb_pll_clk); out2: - clk_put(usb_clk); + clk_put(usb_pll_clk); out1: isp1301_i2c_client = NULL; out: @@ -422,8 +442,10 @@ static int usb_hcd_nxp_remove(struct platform_device *pdev) release_mem_region(hcd->rsrc_start, hcd->rsrc_len); usb_put_hcd(hcd); nxp_unset_usb_bits(); - clk_disable(usb_clk); - clk_put(usb_clk); + clk_disable(usb_pll_clk); + clk_put(usb_pll_clk); + clk_disable(usb_dev_clk); + clk_put(usb_dev_clk); i2c_unregister_device(isp1301_i2c_client); isp1301_i2c_client = NULL; diff --git a/drivers/usb/host/ohci-omap.c b/drivers/usb/host/ohci-omap.c index c7b06f504c60..076d2018e6df 100644 --- a/drivers/usb/host/ohci-omap.c +++ b/drivers/usb/host/ohci-omap.c @@ -168,14 +168,15 @@ static int omap_1510_local_bus_init(void) static void start_hnp(struct ohci_hcd *ohci) { - const unsigned port = ohci_to_hcd(ohci)->self.otg_port - 1; + struct usb_hcd *hcd = ohci_to_hcd(ohci); + const unsigned port = hcd->self.otg_port - 1; unsigned long flags; u32 l; - otg_start_hnp(ohci->transceiver->otg); + otg_start_hnp(hcd->phy->otg); local_irq_save(flags); - ohci->transceiver->state = OTG_STATE_A_SUSPEND; + hcd->phy->state = OTG_STATE_A_SUSPEND; writel (RH_PS_PSS, &ohci->regs->roothub.portstatus [port]); l = omap_readl(OTG_CTRL); l &= ~OTG_A_BUSREQ; @@ -212,18 +213,18 @@ static int ohci_omap_init(struct usb_hcd *hcd) #ifdef CONFIG_USB_OTG if (need_transceiver) { - ohci->transceiver = usb_get_phy(USB_PHY_TYPE_USB2); - if (!IS_ERR_OR_NULL(ohci->transceiver)) { - int status = otg_set_host(ohci->transceiver->otg, + hcd->phy = usb_get_phy(USB_PHY_TYPE_USB2); + if (!IS_ERR_OR_NULL(hcd->phy)) { + int status = otg_set_host(hcd->phy->otg, &ohci_to_hcd(ohci)->self); - dev_dbg(hcd->self.controller, "init %s transceiver, status %d\n", - ohci->transceiver->label, status); + dev_dbg(hcd->self.controller, "init %s phy, status %d\n", + hcd->phy->label, status); if (status) { - usb_put_phy(ohci->transceiver); + usb_put_phy(hcd->phy); return status; } } else { - dev_err(hcd->self.controller, "can't find transceiver\n"); + dev_err(hcd->self.controller, "can't find phy\n"); return -ENODEV; } ohci->start_hnp = start_hnp; @@ -404,9 +405,9 @@ usb_hcd_omap_remove (struct usb_hcd *hcd, struct platform_device *pdev) struct ohci_hcd *ohci = hcd_to_ohci (hcd); usb_remove_hcd(hcd); - if (!IS_ERR_OR_NULL(ohci->transceiver)) { - (void) otg_set_host(ohci->transceiver->otg, 0); - usb_put_phy(ohci->transceiver); + if (!IS_ERR_OR_NULL(hcd->phy)) { + (void) otg_set_host(hcd->phy->otg, 0); + usb_put_phy(hcd->phy); } if (machine_is_omap_osk()) gpio_free(9); diff --git a/drivers/usb/host/ohci.h b/drivers/usb/host/ohci.h index 1b19aea25a2b..d3299143d9e2 100644 --- a/drivers/usb/host/ohci.h +++ b/drivers/usb/host/ohci.h @@ -372,11 +372,6 @@ struct ohci_hcd { struct ed *ed_controltail; /* last in ctrl list */ struct ed *periodic [NUM_INTS]; /* shadow int_table */ - /* - * OTG controllers and transceivers need software interaction; - * other external transceivers should be software-transparent - */ - struct usb_phy *transceiver; void (*start_hnp)(struct ohci_hcd *ohci); /* diff --git a/drivers/usb/host/xhci-mem.c b/drivers/usb/host/xhci-mem.c index ec4338eec826..77689bd64cac 100644 --- a/drivers/usb/host/xhci-mem.c +++ b/drivers/usb/host/xhci-mem.c @@ -793,10 +793,9 @@ static void xhci_free_tt_info(struct xhci_hcd *xhci, struct xhci_virt_device *virt_dev, int slot_id) { - struct list_head *tt; struct list_head *tt_list_head; - struct list_head *tt_next; - struct xhci_tt_bw_info *tt_info; + struct xhci_tt_bw_info *tt_info, *next; + bool slot_found = false; /* If the device never made it past the Set Address stage, * it may not have the real_port set correctly. @@ -808,34 +807,16 @@ static void xhci_free_tt_info(struct xhci_hcd *xhci, } tt_list_head = &(xhci->rh_bw[virt_dev->real_port - 1].tts); - if (list_empty(tt_list_head)) - return; - - list_for_each(tt, tt_list_head) { - tt_info = list_entry(tt, struct xhci_tt_bw_info, tt_list); - if (tt_info->slot_id == slot_id) + list_for_each_entry_safe(tt_info, next, tt_list_head, tt_list) { + /* Multi-TT hubs will have more than one entry */ + if (tt_info->slot_id == slot_id) { + slot_found = true; + list_del(&tt_info->tt_list); + kfree(tt_info); + } else if (slot_found) { break; + } } - /* Cautionary measure in case the hub was disconnected before we - * stored the TT information. - */ - if (tt_info->slot_id != slot_id) - return; - - tt_next = tt->next; - tt_info = list_entry(tt, struct xhci_tt_bw_info, - tt_list); - /* Multi-TT hubs will have more than one entry */ - do { - list_del(tt); - kfree(tt_info); - tt = tt_next; - if (list_empty(tt_list_head)) - break; - tt_next = tt->next; - tt_info = list_entry(tt, struct xhci_tt_bw_info, - tt_list); - } while (tt_info->slot_id == slot_id); } int xhci_alloc_tt_info(struct xhci_hcd *xhci, @@ -1791,17 +1772,9 @@ void xhci_mem_cleanup(struct xhci_hcd *xhci) { struct pci_dev *pdev = to_pci_dev(xhci_to_hcd(xhci)->self.controller); struct dev_info *dev_info, *next; - struct list_head *tt_list_head; - struct list_head *tt; - struct list_head *endpoints; - struct list_head *ep, *q; - struct xhci_tt_bw_info *tt_info; - struct xhci_interval_bw_table *bwt; - struct xhci_virt_ep *virt_ep; - unsigned long flags; int size; - int i; + int i, j, num_ports; /* Free the Event Ring Segment Table and the actual Event Ring */ size = sizeof(struct xhci_erst_entry)*(xhci->erst.num_entries); @@ -1860,21 +1833,22 @@ void xhci_mem_cleanup(struct xhci_hcd *xhci) } spin_unlock_irqrestore(&xhci->lock, flags); - bwt = &xhci->rh_bw->bw_table; - for (i = 0; i < XHCI_MAX_INTERVAL; i++) { - endpoints = &bwt->interval_bw[i].endpoints; - list_for_each_safe(ep, q, endpoints) { - virt_ep = list_entry(ep, struct xhci_virt_ep, bw_endpoint_list); - list_del(&virt_ep->bw_endpoint_list); - kfree(virt_ep); + num_ports = HCS_MAX_PORTS(xhci->hcs_params1); + for (i = 0; i < num_ports; i++) { + struct xhci_interval_bw_table *bwt = &xhci->rh_bw[i].bw_table; + for (j = 0; j < XHCI_MAX_INTERVAL; j++) { + struct list_head *ep = &bwt->interval_bw[j].endpoints; + while (!list_empty(ep)) + list_del_init(ep->next); } } - tt_list_head = &xhci->rh_bw->tts; - list_for_each_safe(tt, q, tt_list_head) { - tt_info = list_entry(tt, struct xhci_tt_bw_info, tt_list); - list_del(tt); - kfree(tt_info); + for (i = 0; i < num_ports; i++) { + struct xhci_tt_bw_info *tt, *n; + list_for_each_entry_safe(tt, n, &xhci->rh_bw[i].tts, tt_list) { + list_del(&tt->tt_list); + kfree(tt); + } } xhci->num_usb2_ports = 0; diff --git a/drivers/usb/host/xhci.c b/drivers/usb/host/xhci.c index afdc73ee84a6..a979cd0dbe0f 100644 --- a/drivers/usb/host/xhci.c +++ b/drivers/usb/host/xhci.c @@ -795,8 +795,8 @@ int xhci_suspend(struct xhci_hcd *xhci) command = xhci_readl(xhci, &xhci->op_regs->command); command |= CMD_CSS; xhci_writel(xhci, command, &xhci->op_regs->command); - if (handshake(xhci, &xhci->op_regs->status, STS_SAVE, 0, 10*100)) { - xhci_warn(xhci, "WARN: xHC CMD_CSS timeout\n"); + if (handshake(xhci, &xhci->op_regs->status, STS_SAVE, 0, 10 * 1000)) { + xhci_warn(xhci, "WARN: xHC save state timeout\n"); spin_unlock_irq(&xhci->lock); return -ETIMEDOUT; } @@ -848,8 +848,8 @@ int xhci_resume(struct xhci_hcd *xhci, bool hibernated) command |= CMD_CRS; xhci_writel(xhci, command, &xhci->op_regs->command); if (handshake(xhci, &xhci->op_regs->status, - STS_RESTORE, 0, 10*100)) { - xhci_dbg(xhci, "WARN: xHC CMD_CSS timeout\n"); + STS_RESTORE, 0, 10 * 1000)) { + xhci_warn(xhci, "WARN: xHC restore state timeout\n"); spin_unlock_irq(&xhci->lock); return -ETIMEDOUT; } @@ -3906,7 +3906,7 @@ static u16 xhci_get_timeout_no_hub_lpm(struct usb_device *udev, default: dev_warn(&udev->dev, "%s: Can't get timeout for non-U1 or U2 state.\n", __func__); - return -EINVAL; + return USB3_LPM_DISABLED; } if (sel <= max_sel_pel && pel <= max_sel_pel) |
