Merge branch 'usbhost_runtime_pm_14_devel_3.3' of git://git.pwsan.com/linux-2.6 into...
authorTony Lindgren <tony@atomide.com>
Sat, 17 Dec 2011 00:11:03 +0000 (16:11 -0800)
committerTony Lindgren <tony@atomide.com>
Sat, 17 Dec 2011 00:11:03 +0000 (16:11 -0800)
arch/arm/mach-omap2/clock3xxx_data.c
arch/arm/mach-omap2/clock44xx_data.c
arch/arm/mach-omap2/usb-host.c
arch/arm/plat-omap/include/plat/usb.h
drivers/mfd/omap-usb-host.c
drivers/usb/host/ehci-omap.c
drivers/usb/host/ohci-omap3.c

index 4e1b1a2f0537808d08437f0ea36571ba35580cbb..9d59451446d9cf5e53de021f9d503dbd1e2dcb3a 100644 (file)
@@ -3297,7 +3297,7 @@ static struct omap_clk omap3xxx_clks[] = {
        CLK(NULL,       "cpefuse_fck",  &cpefuse_fck,   CK_3430ES2PLUS | CK_AM35XX | CK_36XX),
        CLK(NULL,       "ts_fck",       &ts_fck,        CK_3430ES2PLUS | CK_AM35XX | CK_36XX),
        CLK(NULL,       "usbtll_fck",   &usbtll_fck,    CK_3430ES2PLUS | CK_AM35XX | CK_36XX),
-       CLK("usbhs-omap.0",     "usbtll_fck",   &usbtll_fck,    CK_3430ES2PLUS | CK_AM35XX | CK_36XX),
+       CLK("usbhs_omap",       "usbtll_fck",   &usbtll_fck,    CK_3430ES2PLUS | CK_AM35XX | CK_36XX),
        CLK("omap-mcbsp.1",     "prcm_fck",     &core_96m_fck,  CK_3XXX),
        CLK("omap-mcbsp.5",     "prcm_fck",     &core_96m_fck,  CK_3XXX),
        CLK(NULL,       "core_96m_fck", &core_96m_fck,  CK_3XXX),
@@ -3333,7 +3333,7 @@ static struct omap_clk omap3xxx_clks[] = {
        CLK(NULL,       "pka_ick",      &pka_ick,       CK_34XX | CK_36XX),
        CLK(NULL,       "core_l4_ick",  &core_l4_ick,   CK_3XXX),
        CLK(NULL,       "usbtll_ick",   &usbtll_ick,    CK_3430ES2PLUS | CK_AM35XX | CK_36XX),
-       CLK("usbhs-omap.0",     "usbtll_ick",   &usbtll_ick,    CK_3430ES2PLUS | CK_AM35XX | CK_36XX),
+       CLK("usbhs_omap",       "usbtll_ick",   &usbtll_ick,    CK_3430ES2PLUS | CK_AM35XX | CK_36XX),
        CLK("omap_hsmmc.2",     "ick",  &mmchs3_ick,    CK_3430ES2PLUS | CK_AM35XX | CK_36XX),
        CLK(NULL,       "icr_ick",      &icr_ick,       CK_34XX | CK_36XX),
        CLK("omap-aes", "ick",  &aes2_ick,      CK_34XX | CK_36XX),
@@ -3379,20 +3379,18 @@ static struct omap_clk omap3xxx_clks[] = {
        CLK(NULL,       "cam_ick",      &cam_ick,       CK_34XX | CK_36XX),
        CLK(NULL,       "csi2_96m_fck", &csi2_96m_fck,  CK_34XX | CK_36XX),
        CLK(NULL,       "usbhost_120m_fck", &usbhost_120m_fck, CK_3430ES2PLUS | CK_AM35XX | CK_36XX),
-       CLK("usbhs-omap.0",     "hs_fck", &usbhost_120m_fck, CK_3430ES2PLUS | CK_AM35XX | CK_36XX),
        CLK(NULL,       "usbhost_48m_fck", &usbhost_48m_fck, CK_3430ES2PLUS | CK_AM35XX | CK_36XX),
-       CLK("usbhs-omap.0",     "fs_fck", &usbhost_48m_fck, CK_3430ES2PLUS | CK_AM35XX | CK_36XX),
        CLK(NULL,       "usbhost_ick",  &usbhost_ick,   CK_3430ES2PLUS | CK_AM35XX | CK_36XX),
-       CLK("usbhs-omap.0",     "usbhost_ick",  &usbhost_ick,   CK_3430ES2PLUS | CK_AM35XX | CK_36XX),
-       CLK("usbhs-omap.0",     "utmi_p1_gfclk",        &dummy_ck,      CK_3XXX),
-       CLK("usbhs-omap.0",     "utmi_p2_gfclk",        &dummy_ck,      CK_3XXX),
-       CLK("usbhs-omap.0",     "xclk60mhsp1_ck",       &dummy_ck,      CK_3XXX),
-       CLK("usbhs-omap.0",     "xclk60mhsp2_ck",       &dummy_ck,      CK_3XXX),
-       CLK("usbhs-omap.0",     "usb_host_hs_utmi_p1_clk",      &dummy_ck,      CK_3XXX),
-       CLK("usbhs-omap.0",     "usb_host_hs_utmi_p2_clk",      &dummy_ck,      CK_3XXX),
-       CLK("usbhs-omap.0",     "usb_tll_hs_usb_ch0_clk",       &dummy_ck,      CK_3XXX),
-       CLK("usbhs-omap.0",     "usb_tll_hs_usb_ch1_clk",       &dummy_ck,      CK_3XXX),
-       CLK("usbhs-omap.0",     "init_60m_fclk",        &dummy_ck,      CK_3XXX),
+       CLK("usbhs_omap",       "usbhost_ick",  &usbhost_ick,   CK_3430ES2PLUS | CK_AM35XX | CK_36XX),
+       CLK("usbhs_omap",       "utmi_p1_gfclk",        &dummy_ck,      CK_3XXX),
+       CLK("usbhs_omap",       "utmi_p2_gfclk",        &dummy_ck,      CK_3XXX),
+       CLK("usbhs_omap",       "xclk60mhsp1_ck",       &dummy_ck,      CK_3XXX),
+       CLK("usbhs_omap",       "xclk60mhsp2_ck",       &dummy_ck,      CK_3XXX),
+       CLK("usbhs_omap",       "usb_host_hs_utmi_p1_clk",      &dummy_ck,      CK_3XXX),
+       CLK("usbhs_omap",       "usb_host_hs_utmi_p2_clk",      &dummy_ck,      CK_3XXX),
+       CLK("usbhs_omap",       "usb_tll_hs_usb_ch0_clk",       &dummy_ck,      CK_3XXX),
+       CLK("usbhs_omap",       "usb_tll_hs_usb_ch1_clk",       &dummy_ck,      CK_3XXX),
+       CLK("usbhs_omap",       "init_60m_fclk",        &dummy_ck,      CK_3XXX),
        CLK(NULL,       "usim_fck",     &usim_fck,      CK_3430ES2PLUS | CK_36XX),
        CLK(NULL,       "gpt1_fck",     &gpt1_fck,      CK_3XXX),
        CLK(NULL,       "wkup_32k_fck", &wkup_32k_fck,  CK_3XXX),
index 0798a802497a543dbfc2bff9b71da28772ffa6be..c8a1b2740778f0a2570922007726841d05d39f50 100644 (file)
@@ -3295,7 +3295,7 @@ static struct omap_clk omap44xx_clks[] = {
        CLK(NULL,       "uart2_fck",                    &uart2_fck,     CK_443X),
        CLK(NULL,       "uart3_fck",                    &uart3_fck,     CK_443X),
        CLK(NULL,       "uart4_fck",                    &uart4_fck,     CK_443X),
-       CLK("usbhs-omap.0",     "fs_fck",               &usb_host_fs_fck,       CK_443X),
+       CLK("usbhs_omap",       "fs_fck",               &usb_host_fs_fck,       CK_443X),
        CLK(NULL,       "utmi_p1_gfclk",                &utmi_p1_gfclk, CK_443X),
        CLK(NULL,       "usb_host_hs_utmi_p1_clk",      &usb_host_hs_utmi_p1_clk,       CK_443X),
        CLK(NULL,       "utmi_p2_gfclk",                &utmi_p2_gfclk, CK_443X),
@@ -3306,7 +3306,7 @@ static struct omap_clk omap44xx_clks[] = {
        CLK(NULL,       "usb_host_hs_hsic60m_p2_clk",   &usb_host_hs_hsic60m_p2_clk,    CK_443X),
        CLK(NULL,       "usb_host_hs_hsic480m_p2_clk",  &usb_host_hs_hsic480m_p2_clk,   CK_443X),
        CLK(NULL,       "usb_host_hs_func48mclk",       &usb_host_hs_func48mclk,        CK_443X),
-       CLK("usbhs-omap.0",     "hs_fck",               &usb_host_hs_fck,       CK_443X),
+       CLK("usbhs_omap",       "hs_fck",               &usb_host_hs_fck,       CK_443X),
        CLK(NULL,       "otg_60m_gfclk",                &otg_60m_gfclk, CK_443X),
        CLK(NULL,       "usb_otg_hs_xclk",              &usb_otg_hs_xclk,       CK_443X),
        CLK("musb-omap2430",    "ick",                          &usb_otg_hs_ick,        CK_443X),
@@ -3314,7 +3314,7 @@ static struct omap_clk omap44xx_clks[] = {
        CLK(NULL,       "usb_tll_hs_usb_ch2_clk",       &usb_tll_hs_usb_ch2_clk,        CK_443X),
        CLK(NULL,       "usb_tll_hs_usb_ch0_clk",       &usb_tll_hs_usb_ch0_clk,        CK_443X),
        CLK(NULL,       "usb_tll_hs_usb_ch1_clk",       &usb_tll_hs_usb_ch1_clk,        CK_443X),
-       CLK("usbhs-omap.0",     "usbtll_ick",           &usb_tll_hs_ick,        CK_443X),
+       CLK("usbhs_omap",       "usbtll_ick",           &usb_tll_hs_ick,        CK_443X),
        CLK(NULL,       "usim_ck",                      &usim_ck,       CK_443X),
        CLK(NULL,       "usim_fclk",                    &usim_fclk,     CK_443X),
        CLK(NULL,       "usim_fck",                     &usim_fck,      CK_443X),
@@ -3374,8 +3374,8 @@ static struct omap_clk omap44xx_clks[] = {
        CLK(NULL,       "uart2_ick",                    &dummy_ck,      CK_443X),
        CLK(NULL,       "uart3_ick",                    &dummy_ck,      CK_443X),
        CLK(NULL,       "uart4_ick",                    &dummy_ck,      CK_443X),
-       CLK("usbhs-omap.0",     "usbhost_ick",          &dummy_ck,              CK_443X),
-       CLK("usbhs-omap.0",     "usbtll_fck",           &dummy_ck,      CK_443X),
+       CLK("usbhs_omap",       "usbhost_ick",          &dummy_ck,              CK_443X),
+       CLK("usbhs_omap",       "usbtll_fck",           &dummy_ck,      CK_443X),
        CLK("omap_wdt", "ick",                          &dummy_ck,      CK_443X),
        CLK("omap_timer.1",     "32k_ck",       &sys_32k_ck,    CK_443X),
        CLK("omap_timer.2",     "32k_ck",       &sys_32k_ck,    CK_443X),
index 89ae29847c59c11254f15a84e907c61018f70765..771dc781b746377707c23f01b2cff2516711f6ec 100644 (file)
 #include <mach/hardware.h>
 #include <mach/irqs.h>
 #include <plat/usb.h>
+#include <plat/omap_device.h>
 
 #include "mux.h"
 
 #ifdef CONFIG_MFD_OMAP_USB_HOST
 
-#define OMAP_USBHS_DEVICE      "usbhs-omap"
-
-static struct resource usbhs_resources[] = {
-       {
-               .name   = "uhh",
-               .flags  = IORESOURCE_MEM,
-       },
-       {
-               .name   = "tll",
-               .flags  = IORESOURCE_MEM,
-       },
-       {
-               .name   = "ehci",
-               .flags  = IORESOURCE_MEM,
-       },
-       {
-               .name   = "ehci-irq",
-               .flags  = IORESOURCE_IRQ,
-       },
-       {
-               .name   = "ohci",
-               .flags  = IORESOURCE_MEM,
-       },
-       {
-               .name   = "ohci-irq",
-               .flags  = IORESOURCE_IRQ,
-       }
-};
-
-static struct platform_device usbhs_device = {
-       .name           = OMAP_USBHS_DEVICE,
-       .id             = 0,
-       .num_resources  = ARRAY_SIZE(usbhs_resources),
-       .resource       = usbhs_resources,
-};
+#define OMAP_USBHS_DEVICE      "usbhs_omap"
+#define        USBHS_UHH_HWMODNAME     "usb_host_hs"
+#define USBHS_TLL_HWMODNAME    "usb_tll_hs"
 
 static struct usbhs_omap_platform_data         usbhs_data;
 static struct ehci_hcd_omap_platform_data      ehci_data;
 static struct ohci_hcd_omap_platform_data      ohci_data;
 
+static struct omap_device_pm_latency omap_uhhtll_latency[] = {
+         {
+               .deactivate_func = omap_device_idle_hwmods,
+               .activate_func   = omap_device_enable_hwmods,
+               .flags = OMAP_DEVICE_LATENCY_AUTO_ADJUST,
+         },
+};
+
 /* MUX settings for EHCI pins */
 /*
  * setup_ehci_io_mux - initialize IO pad mux for USBHOST
@@ -508,7 +485,10 @@ static void setup_4430ohci_io_mux(const enum usbhs_omap_port_mode *port_mode)
 
 void __init usbhs_init(const struct usbhs_omap_board_data *pdata)
 {
-       int     i;
+       struct omap_hwmod       *oh[2];
+       struct omap_device      *od;
+       int                     bus_id = -1;
+       int                     i;
 
        for (i = 0; i < OMAP3_HS_USB_PORTS; i++) {
                usbhs_data.port_mode[i] = pdata->port_mode[i];
@@ -523,44 +503,34 @@ void __init usbhs_init(const struct usbhs_omap_board_data *pdata)
        usbhs_data.ohci_data = &ohci_data;
 
        if (cpu_is_omap34xx()) {
-               usbhs_resources[0].start = OMAP34XX_UHH_CONFIG_BASE;
-               usbhs_resources[0].end = OMAP34XX_UHH_CONFIG_BASE + SZ_1K - 1;
-               usbhs_resources[1].start = OMAP34XX_USBTLL_BASE;
-               usbhs_resources[1].end = OMAP34XX_USBTLL_BASE + SZ_4K - 1;
-               usbhs_resources[2].start        = OMAP34XX_EHCI_BASE;
-               usbhs_resources[2].end  = OMAP34XX_EHCI_BASE + SZ_1K - 1;
-               usbhs_resources[3].start = INT_34XX_EHCI_IRQ;
-               usbhs_resources[4].start        = OMAP34XX_OHCI_BASE;
-               usbhs_resources[4].end  = OMAP34XX_OHCI_BASE + SZ_1K - 1;
-               usbhs_resources[5].start = INT_34XX_OHCI_IRQ;
                setup_ehci_io_mux(pdata->port_mode);
                setup_ohci_io_mux(pdata->port_mode);
        } else if (cpu_is_omap44xx()) {
-               usbhs_resources[0].start = OMAP44XX_UHH_CONFIG_BASE;
-               usbhs_resources[0].end = OMAP44XX_UHH_CONFIG_BASE + SZ_1K - 1;
-               usbhs_resources[1].start = OMAP44XX_USBTLL_BASE;
-               usbhs_resources[1].end = OMAP44XX_USBTLL_BASE + SZ_4K - 1;
-               usbhs_resources[2].start = OMAP44XX_HSUSB_EHCI_BASE;
-               usbhs_resources[2].end = OMAP44XX_HSUSB_EHCI_BASE + SZ_1K - 1;
-               usbhs_resources[3].start = OMAP44XX_IRQ_EHCI;
-               usbhs_resources[4].start = OMAP44XX_HSUSB_OHCI_BASE;
-               usbhs_resources[4].end = OMAP44XX_HSUSB_OHCI_BASE + SZ_1K - 1;
-               usbhs_resources[5].start = OMAP44XX_IRQ_OHCI;
                setup_4430ehci_io_mux(pdata->port_mode);
                setup_4430ohci_io_mux(pdata->port_mode);
        }
 
-       if (platform_device_add_data(&usbhs_device,
-                               &usbhs_data, sizeof(usbhs_data)) < 0) {
-               printk(KERN_ERR "USBHS platform_device_add_data failed\n");
-               goto init_end;
+       oh[0] = omap_hwmod_lookup(USBHS_UHH_HWMODNAME);
+       if (!oh[0]) {
+               pr_err("Could not look up %s\n", USBHS_UHH_HWMODNAME);
+               return;
        }
 
-       if (platform_device_register(&usbhs_device) < 0)
-               printk(KERN_ERR "USBHS platform_device_register failed\n");
+       oh[1] = omap_hwmod_lookup(USBHS_TLL_HWMODNAME);
+       if (!oh[1]) {
+               pr_err("Could not look up %s\n", USBHS_TLL_HWMODNAME);
+               return;
+       }
 
-init_end:
-       return;
+       od = omap_device_build_ss(OMAP_USBHS_DEVICE, bus_id, oh, 2,
+                               (void *)&usbhs_data, sizeof(usbhs_data),
+                               omap_uhhtll_latency,
+                               ARRAY_SIZE(omap_uhhtll_latency), false);
+       if (IS_ERR(od)) {
+               pr_err("Could not build hwmod devices %s,%s\n",
+                       USBHS_UHH_HWMODNAME, USBHS_TLL_HWMODNAME);
+               return;
+       }
 }
 
 #else
@@ -570,5 +540,3 @@ void __init usbhs_init(const struct usbhs_omap_board_data *pdata)
 }
 
 #endif
-
-
index 17d3c939775c7164e2c246f8a150bb212bbb0647..2b66dc266bcfba119ef5f6e678d8ce1fae9d48fe 100644 (file)
@@ -100,9 +100,6 @@ extern void usb_musb_init(struct omap_musb_board_data *board_data);
 
 extern void usbhs_init(const struct usbhs_omap_board_data *pdata);
 
-extern int omap_usbhs_enable(struct device *dev);
-extern void omap_usbhs_disable(struct device *dev);
-
 extern int omap4430_phy_power(struct device *dev, int ID, int on);
 extern int omap4430_phy_set_clk(struct device *dev, int on);
 extern int omap4430_phy_init(struct device *dev);
index 86e14583a08276fd7f76dddd3afe3433f1dfa9a8..3f565ef3e149438c86a0054f354627231a2258b2 100644 (file)
@@ -27,8 +27,9 @@
 #include <linux/spinlock.h>
 #include <linux/gpio.h>
 #include <plat/usb.h>
+#include <linux/pm_runtime.h>
 
-#define USBHS_DRIVER_NAME      "usbhs-omap"
+#define USBHS_DRIVER_NAME      "usbhs_omap"
 #define OMAP_EHCI_DEVICE       "ehci-omap"
 #define OMAP_OHCI_DEVICE       "ohci-omap3"
 
 
 
 struct usbhs_hcd_omap {
-       struct clk                      *usbhost_ick;
-       struct clk                      *usbhost_hs_fck;
-       struct clk                      *usbhost_fs_fck;
        struct clk                      *xclk60mhsp1_ck;
        struct clk                      *xclk60mhsp2_ck;
        struct clk                      *utmi_p1_fck;
@@ -159,8 +157,7 @@ struct usbhs_hcd_omap {
        struct clk                      *usbhost_p2_fck;
        struct clk                      *usbtll_p2_fck;
        struct clk                      *init_60m_fclk;
-       struct clk                      *usbtll_fck;
-       struct clk                      *usbtll_ick;
+       struct clk                      *ehci_logic_fck;
 
        void __iomem                    *uhh_base;
        void __iomem                    *tll_base;
@@ -169,7 +166,6 @@ struct usbhs_hcd_omap {
 
        u32                             usbhs_rev;
        spinlock_t                      lock;
-       int                             count;
 };
 /*-------------------------------------------------------------------------*/
 
@@ -319,269 +315,6 @@ err_end:
        return ret;
 }
 
-/**
- * usbhs_omap_probe - initialize TI-based HCDs
- *
- * Allocates basic resources for this USB host controller.
- */
-static int __devinit usbhs_omap_probe(struct platform_device *pdev)
-{
-       struct device                   *dev =  &pdev->dev;
-       struct usbhs_omap_platform_data *pdata = dev->platform_data;
-       struct usbhs_hcd_omap           *omap;
-       struct resource                 *res;
-       int                             ret = 0;
-       int                             i;
-
-       if (!pdata) {
-               dev_err(dev, "Missing platform data\n");
-               ret = -ENOMEM;
-               goto end_probe;
-       }
-
-       omap = kzalloc(sizeof(*omap), GFP_KERNEL);
-       if (!omap) {
-               dev_err(dev, "Memory allocation failed\n");
-               ret = -ENOMEM;
-               goto end_probe;
-       }
-
-       spin_lock_init(&omap->lock);
-
-       for (i = 0; i < OMAP3_HS_USB_PORTS; i++)
-               omap->platdata.port_mode[i] = pdata->port_mode[i];
-
-       omap->platdata.ehci_data = pdata->ehci_data;
-       omap->platdata.ohci_data = pdata->ohci_data;
-
-       omap->usbhost_ick = clk_get(dev, "usbhost_ick");
-       if (IS_ERR(omap->usbhost_ick)) {
-               ret =  PTR_ERR(omap->usbhost_ick);
-               dev_err(dev, "usbhost_ick failed error:%d\n", ret);
-               goto err_end;
-       }
-
-       omap->usbhost_hs_fck = clk_get(dev, "hs_fck");
-       if (IS_ERR(omap->usbhost_hs_fck)) {
-               ret = PTR_ERR(omap->usbhost_hs_fck);
-               dev_err(dev, "usbhost_hs_fck failed error:%d\n", ret);
-               goto err_usbhost_ick;
-       }
-
-       omap->usbhost_fs_fck = clk_get(dev, "fs_fck");
-       if (IS_ERR(omap->usbhost_fs_fck)) {
-               ret = PTR_ERR(omap->usbhost_fs_fck);
-               dev_err(dev, "usbhost_fs_fck failed error:%d\n", ret);
-               goto err_usbhost_hs_fck;
-       }
-
-       omap->usbtll_fck = clk_get(dev, "usbtll_fck");
-       if (IS_ERR(omap->usbtll_fck)) {
-               ret = PTR_ERR(omap->usbtll_fck);
-               dev_err(dev, "usbtll_fck failed error:%d\n", ret);
-               goto err_usbhost_fs_fck;
-       }
-
-       omap->usbtll_ick = clk_get(dev, "usbtll_ick");
-       if (IS_ERR(omap->usbtll_ick)) {
-               ret = PTR_ERR(omap->usbtll_ick);
-               dev_err(dev, "usbtll_ick failed error:%d\n", ret);
-               goto err_usbtll_fck;
-       }
-
-       omap->utmi_p1_fck = clk_get(dev, "utmi_p1_gfclk");
-       if (IS_ERR(omap->utmi_p1_fck)) {
-               ret = PTR_ERR(omap->utmi_p1_fck);
-               dev_err(dev, "utmi_p1_gfclk failed error:%d\n", ret);
-               goto err_usbtll_ick;
-       }
-
-       omap->xclk60mhsp1_ck = clk_get(dev, "xclk60mhsp1_ck");
-       if (IS_ERR(omap->xclk60mhsp1_ck)) {
-               ret = PTR_ERR(omap->xclk60mhsp1_ck);
-               dev_err(dev, "xclk60mhsp1_ck failed error:%d\n", ret);
-               goto err_utmi_p1_fck;
-       }
-
-       omap->utmi_p2_fck = clk_get(dev, "utmi_p2_gfclk");
-       if (IS_ERR(omap->utmi_p2_fck)) {
-               ret = PTR_ERR(omap->utmi_p2_fck);
-               dev_err(dev, "utmi_p2_gfclk failed error:%d\n", ret);
-               goto err_xclk60mhsp1_ck;
-       }
-
-       omap->xclk60mhsp2_ck = clk_get(dev, "xclk60mhsp2_ck");
-       if (IS_ERR(omap->xclk60mhsp2_ck)) {
-               ret = PTR_ERR(omap->xclk60mhsp2_ck);
-               dev_err(dev, "xclk60mhsp2_ck failed error:%d\n", ret);
-               goto err_utmi_p2_fck;
-       }
-
-       omap->usbhost_p1_fck = clk_get(dev, "usb_host_hs_utmi_p1_clk");
-       if (IS_ERR(omap->usbhost_p1_fck)) {
-               ret = PTR_ERR(omap->usbhost_p1_fck);
-               dev_err(dev, "usbhost_p1_fck failed error:%d\n", ret);
-               goto err_xclk60mhsp2_ck;
-       }
-
-       omap->usbtll_p1_fck = clk_get(dev, "usb_tll_hs_usb_ch0_clk");
-       if (IS_ERR(omap->usbtll_p1_fck)) {
-               ret = PTR_ERR(omap->usbtll_p1_fck);
-               dev_err(dev, "usbtll_p1_fck failed error:%d\n", ret);
-               goto err_usbhost_p1_fck;
-       }
-
-       omap->usbhost_p2_fck = clk_get(dev, "usb_host_hs_utmi_p2_clk");
-       if (IS_ERR(omap->usbhost_p2_fck)) {
-               ret = PTR_ERR(omap->usbhost_p2_fck);
-               dev_err(dev, "usbhost_p2_fck failed error:%d\n", ret);
-               goto err_usbtll_p1_fck;
-       }
-
-       omap->usbtll_p2_fck = clk_get(dev, "usb_tll_hs_usb_ch1_clk");
-       if (IS_ERR(omap->usbtll_p2_fck)) {
-               ret = PTR_ERR(omap->usbtll_p2_fck);
-               dev_err(dev, "usbtll_p2_fck failed error:%d\n", ret);
-               goto err_usbhost_p2_fck;
-       }
-
-       omap->init_60m_fclk = clk_get(dev, "init_60m_fclk");
-       if (IS_ERR(omap->init_60m_fclk)) {
-               ret = PTR_ERR(omap->init_60m_fclk);
-               dev_err(dev, "init_60m_fclk failed error:%d\n", ret);
-               goto err_usbtll_p2_fck;
-       }
-
-       res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "uhh");
-       if (!res) {
-               dev_err(dev, "UHH EHCI get resource failed\n");
-               ret = -ENODEV;
-               goto err_init_60m_fclk;
-       }
-
-       omap->uhh_base = ioremap(res->start, resource_size(res));
-       if (!omap->uhh_base) {
-               dev_err(dev, "UHH ioremap failed\n");
-               ret = -ENOMEM;
-               goto err_init_60m_fclk;
-       }
-
-       res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "tll");
-       if (!res) {
-               dev_err(dev, "UHH EHCI get resource failed\n");
-               ret = -ENODEV;
-               goto err_tll;
-       }
-
-       omap->tll_base = ioremap(res->start, resource_size(res));
-       if (!omap->tll_base) {
-               dev_err(dev, "TLL ioremap failed\n");
-               ret = -ENOMEM;
-               goto err_tll;
-       }
-
-       platform_set_drvdata(pdev, omap);
-
-       ret = omap_usbhs_alloc_children(pdev);
-       if (ret) {
-               dev_err(dev, "omap_usbhs_alloc_children failed\n");
-               goto err_alloc;
-       }
-
-       goto end_probe;
-
-err_alloc:
-       iounmap(omap->tll_base);
-
-err_tll:
-       iounmap(omap->uhh_base);
-
-err_init_60m_fclk:
-       clk_put(omap->init_60m_fclk);
-
-err_usbtll_p2_fck:
-       clk_put(omap->usbtll_p2_fck);
-
-err_usbhost_p2_fck:
-       clk_put(omap->usbhost_p2_fck);
-
-err_usbtll_p1_fck:
-       clk_put(omap->usbtll_p1_fck);
-
-err_usbhost_p1_fck:
-       clk_put(omap->usbhost_p1_fck);
-
-err_xclk60mhsp2_ck:
-       clk_put(omap->xclk60mhsp2_ck);
-
-err_utmi_p2_fck:
-       clk_put(omap->utmi_p2_fck);
-
-err_xclk60mhsp1_ck:
-       clk_put(omap->xclk60mhsp1_ck);
-
-err_utmi_p1_fck:
-       clk_put(omap->utmi_p1_fck);
-
-err_usbtll_ick:
-       clk_put(omap->usbtll_ick);
-
-err_usbtll_fck:
-       clk_put(omap->usbtll_fck);
-
-err_usbhost_fs_fck:
-       clk_put(omap->usbhost_fs_fck);
-
-err_usbhost_hs_fck:
-       clk_put(omap->usbhost_hs_fck);
-
-err_usbhost_ick:
-       clk_put(omap->usbhost_ick);
-
-err_end:
-       kfree(omap);
-
-end_probe:
-       return ret;
-}
-
-/**
- * usbhs_omap_remove - shutdown processing for UHH & TLL HCDs
- * @pdev: USB Host Controller being removed
- *
- * Reverses the effect of usbhs_omap_probe().
- */
-static int __devexit usbhs_omap_remove(struct platform_device *pdev)
-{
-       struct usbhs_hcd_omap *omap = platform_get_drvdata(pdev);
-
-       if (omap->count != 0) {
-               dev_err(&pdev->dev,
-                       "Either EHCI or OHCI is still using usbhs core\n");
-               return -EBUSY;
-       }
-
-       iounmap(omap->tll_base);
-       iounmap(omap->uhh_base);
-       clk_put(omap->init_60m_fclk);
-       clk_put(omap->usbtll_p2_fck);
-       clk_put(omap->usbhost_p2_fck);
-       clk_put(omap->usbtll_p1_fck);
-       clk_put(omap->usbhost_p1_fck);
-       clk_put(omap->xclk60mhsp2_ck);
-       clk_put(omap->utmi_p2_fck);
-       clk_put(omap->xclk60mhsp1_ck);
-       clk_put(omap->utmi_p1_fck);
-       clk_put(omap->usbtll_ick);
-       clk_put(omap->usbtll_fck);
-       clk_put(omap->usbhost_fs_fck);
-       clk_put(omap->usbhost_hs_fck);
-       clk_put(omap->usbhost_ick);
-       kfree(omap);
-
-       return 0;
-}
-
 static bool is_ohci_port(enum usbhs_omap_port_mode pmode)
 {
        switch (pmode) {
@@ -689,30 +422,85 @@ static void usbhs_omap_tll_init(struct device *dev, u8 tll_channel_count)
        }
 }
 
-static int usbhs_enable(struct device *dev)
+static int usbhs_runtime_resume(struct device *dev)
 {
        struct usbhs_hcd_omap           *omap = dev_get_drvdata(dev);
        struct usbhs_omap_platform_data *pdata = &omap->platdata;
-       unsigned long                   flags = 0;
-       int                             ret = 0;
-       unsigned long                   timeout;
-       unsigned                        reg;
+       unsigned long                   flags;
+
+       dev_dbg(dev, "usbhs_runtime_resume\n");
 
-       dev_dbg(dev, "starting TI HSUSB Controller\n");
        if (!pdata) {
                dev_dbg(dev, "missing platform_data\n");
                return  -ENODEV;
        }
 
        spin_lock_irqsave(&omap->lock, flags);
-       if (omap->count > 0)
-               goto end_count;
 
-       clk_enable(omap->usbhost_ick);
-       clk_enable(omap->usbhost_hs_fck);
-       clk_enable(omap->usbhost_fs_fck);
-       clk_enable(omap->usbtll_fck);
-       clk_enable(omap->usbtll_ick);
+       if (omap->ehci_logic_fck && !IS_ERR(omap->ehci_logic_fck))
+               clk_enable(omap->ehci_logic_fck);
+
+       if (is_ehci_tll_mode(pdata->port_mode[0])) {
+               clk_enable(omap->usbhost_p1_fck);
+               clk_enable(omap->usbtll_p1_fck);
+       }
+       if (is_ehci_tll_mode(pdata->port_mode[1])) {
+               clk_enable(omap->usbhost_p2_fck);
+               clk_enable(omap->usbtll_p2_fck);
+       }
+       clk_enable(omap->utmi_p1_fck);
+       clk_enable(omap->utmi_p2_fck);
+
+       spin_unlock_irqrestore(&omap->lock, flags);
+
+       return 0;
+}
+
+static int usbhs_runtime_suspend(struct device *dev)
+{
+       struct usbhs_hcd_omap           *omap = dev_get_drvdata(dev);
+       struct usbhs_omap_platform_data *pdata = &omap->platdata;
+       unsigned long                   flags;
+
+       dev_dbg(dev, "usbhs_runtime_suspend\n");
+
+       if (!pdata) {
+               dev_dbg(dev, "missing platform_data\n");
+               return  -ENODEV;
+       }
+
+       spin_lock_irqsave(&omap->lock, flags);
+
+       if (is_ehci_tll_mode(pdata->port_mode[0])) {
+               clk_disable(omap->usbhost_p1_fck);
+               clk_disable(omap->usbtll_p1_fck);
+       }
+       if (is_ehci_tll_mode(pdata->port_mode[1])) {
+               clk_disable(omap->usbhost_p2_fck);
+               clk_disable(omap->usbtll_p2_fck);
+       }
+       clk_disable(omap->utmi_p2_fck);
+       clk_disable(omap->utmi_p1_fck);
+
+       if (omap->ehci_logic_fck && !IS_ERR(omap->ehci_logic_fck))
+               clk_disable(omap->ehci_logic_fck);
+
+       spin_unlock_irqrestore(&omap->lock, flags);
+
+       return 0;
+}
+
+static void omap_usbhs_init(struct device *dev)
+{
+       struct usbhs_hcd_omap           *omap = dev_get_drvdata(dev);
+       struct usbhs_omap_platform_data *pdata = &omap->platdata;
+       unsigned long                   flags;
+       unsigned                        reg;
+
+       dev_dbg(dev, "starting TI HSUSB Controller\n");
+
+       pm_runtime_get_sync(dev);
+       spin_lock_irqsave(&omap->lock, flags);
 
        if (pdata->ehci_data->phy_reset) {
                if (gpio_is_valid(pdata->ehci_data->reset_gpio_port[0])) {
@@ -736,50 +524,6 @@ static int usbhs_enable(struct device *dev)
        omap->usbhs_rev = usbhs_read(omap->uhh_base, OMAP_UHH_REVISION);
        dev_dbg(dev, "OMAP UHH_REVISION 0x%x\n", omap->usbhs_rev);
 
-       /* perform TLL soft reset, and wait until reset is complete */
-       usbhs_write(omap->tll_base, OMAP_USBTLL_SYSCONFIG,
-                       OMAP_USBTLL_SYSCONFIG_SOFTRESET);
-
-       /* Wait for TLL reset to complete */
-       timeout = jiffies + msecs_to_jiffies(1000);
-       while (!(usbhs_read(omap->tll_base, OMAP_USBTLL_SYSSTATUS)
-                       & OMAP_USBTLL_SYSSTATUS_RESETDONE)) {
-               cpu_relax();
-
-               if (time_after(jiffies, timeout)) {
-                       dev_dbg(dev, "operation timed out\n");
-                       ret = -EINVAL;
-                       goto err_tll;
-               }
-       }
-
-       dev_dbg(dev, "TLL RESET DONE\n");
-
-       /* (1<<3) = no idle mode only for initial debugging */
-       usbhs_write(omap->tll_base, OMAP_USBTLL_SYSCONFIG,
-                       OMAP_USBTLL_SYSCONFIG_ENAWAKEUP |
-                       OMAP_USBTLL_SYSCONFIG_SIDLEMODE |
-                       OMAP_USBTLL_SYSCONFIG_AUTOIDLE);
-
-       /* Put UHH in NoIdle/NoStandby mode */
-       reg = usbhs_read(omap->uhh_base, OMAP_UHH_SYSCONFIG);
-       if (is_omap_usbhs_rev1(omap)) {
-               reg |= (OMAP_UHH_SYSCONFIG_ENAWAKEUP
-                               | OMAP_UHH_SYSCONFIG_SIDLEMODE
-                               | OMAP_UHH_SYSCONFIG_CACTIVITY
-                               | OMAP_UHH_SYSCONFIG_MIDLEMODE);
-               reg &= ~OMAP_UHH_SYSCONFIG_AUTOIDLE;
-
-
-       } else if (is_omap_usbhs_rev2(omap)) {
-               reg &= ~OMAP4_UHH_SYSCONFIG_IDLEMODE_CLEAR;
-               reg |= OMAP4_UHH_SYSCONFIG_NOIDLE;
-               reg &= ~OMAP4_UHH_SYSCONFIG_STDBYMODE_CLEAR;
-               reg |= OMAP4_UHH_SYSCONFIG_NOSTDBY;
-       }
-
-       usbhs_write(omap->uhh_base, OMAP_UHH_SYSCONFIG, reg);
-
        reg = usbhs_read(omap->uhh_base, OMAP_UHH_HOSTCONFIG);
        /* setup ULPI bypass and burst configurations */
        reg |= (OMAP_UHH_HOSTCONFIG_INCR4_BURST_EN
@@ -825,49 +569,6 @@ static int usbhs_enable(struct device *dev)
                reg &= ~OMAP4_P1_MODE_CLEAR;
                reg &= ~OMAP4_P2_MODE_CLEAR;
 
-               if (is_ehci_phy_mode(pdata->port_mode[0])) {
-                       ret = clk_set_parent(omap->utmi_p1_fck,
-                                               omap->xclk60mhsp1_ck);
-                       if (ret != 0) {
-                               dev_err(dev, "xclk60mhsp1_ck set parent"
-                               "failed error:%d\n", ret);
-                               goto err_tll;
-                       }
-               } else if (is_ehci_tll_mode(pdata->port_mode[0])) {
-                       ret = clk_set_parent(omap->utmi_p1_fck,
-                                               omap->init_60m_fclk);
-                       if (ret != 0) {
-                               dev_err(dev, "init_60m_fclk set parent"
-                               "failed error:%d\n", ret);
-                               goto err_tll;
-                       }
-                       clk_enable(omap->usbhost_p1_fck);
-                       clk_enable(omap->usbtll_p1_fck);
-               }
-
-               if (is_ehci_phy_mode(pdata->port_mode[1])) {
-                       ret = clk_set_parent(omap->utmi_p2_fck,
-                                               omap->xclk60mhsp2_ck);
-                       if (ret != 0) {
-                               dev_err(dev, "xclk60mhsp1_ck set parent"
-                                       "failed error:%d\n", ret);
-                               goto err_tll;
-                       }
-               } else if (is_ehci_tll_mode(pdata->port_mode[1])) {
-                       ret = clk_set_parent(omap->utmi_p2_fck,
-                                               omap->init_60m_fclk);
-                       if (ret != 0) {
-                               dev_err(dev, "init_60m_fclk set parent"
-                               "failed error:%d\n", ret);
-                               goto err_tll;
-                       }
-                       clk_enable(omap->usbhost_p2_fck);
-                       clk_enable(omap->usbtll_p2_fck);
-               }
-
-               clk_enable(omap->utmi_p1_fck);
-               clk_enable(omap->utmi_p2_fck);
-
                if (is_ehci_tll_mode(pdata->port_mode[0]) ||
                        (is_ohci_port(pdata->port_mode[0])))
                        reg |= OMAP4_P1_MODE_TLL;
@@ -913,12 +614,15 @@ static int usbhs_enable(struct device *dev)
                                (pdata->ehci_data->reset_gpio_port[1], 1);
        }
 
-end_count:
-       omap->count++;
        spin_unlock_irqrestore(&omap->lock, flags);
-       return 0;
+       pm_runtime_put_sync(dev);
+}
+
+static void omap_usbhs_deinit(struct device *dev)
+{
+       struct usbhs_hcd_omap           *omap = dev_get_drvdata(dev);
+       struct usbhs_omap_platform_data *pdata = &omap->platdata;
 
-err_tll:
        if (pdata->ehci_data->phy_reset) {
                if (gpio_is_valid(pdata->ehci_data->reset_gpio_port[0]))
                        gpio_free(pdata->ehci_data->reset_gpio_port[0]);
@@ -926,123 +630,272 @@ err_tll:
                if (gpio_is_valid(pdata->ehci_data->reset_gpio_port[1]))
                        gpio_free(pdata->ehci_data->reset_gpio_port[1]);
        }
-
-       clk_disable(omap->usbtll_ick);
-       clk_disable(omap->usbtll_fck);
-       clk_disable(omap->usbhost_fs_fck);
-       clk_disable(omap->usbhost_hs_fck);
-       clk_disable(omap->usbhost_ick);
-       spin_unlock_irqrestore(&omap->lock, flags);
-       return ret;
 }
 
-static void usbhs_disable(struct device *dev)
+
+/**
+ * usbhs_omap_probe - initialize TI-based HCDs
+ *
+ * Allocates basic resources for this USB host controller.
+ */
+static int __devinit usbhs_omap_probe(struct platform_device *pdev)
 {
-       struct usbhs_hcd_omap           *omap = dev_get_drvdata(dev);
-       struct usbhs_omap_platform_data *pdata = &omap->platdata;
-       unsigned long                   flags = 0;
-       unsigned long                   timeout;
+       struct device                   *dev =  &pdev->dev;
+       struct usbhs_omap_platform_data *pdata = dev->platform_data;
+       struct usbhs_hcd_omap           *omap;
+       struct resource                 *res;
+       int                             ret = 0;
+       int                             i;
 
-       dev_dbg(dev, "stopping TI HSUSB Controller\n");
+       if (!pdata) {
+               dev_err(dev, "Missing platform data\n");
+               ret = -ENOMEM;
+               goto end_probe;
+       }
 
-       spin_lock_irqsave(&omap->lock, flags);
+       omap = kzalloc(sizeof(*omap), GFP_KERNEL);
+       if (!omap) {
+               dev_err(dev, "Memory allocation failed\n");
+               ret = -ENOMEM;
+               goto end_probe;
+       }
 
-       if (omap->count == 0)
-               goto end_disble;
+       spin_lock_init(&omap->lock);
 
-       omap->count--;
+       for (i = 0; i < OMAP3_HS_USB_PORTS; i++)
+               omap->platdata.port_mode[i] = pdata->port_mode[i];
+
+       omap->platdata.ehci_data = pdata->ehci_data;
+       omap->platdata.ohci_data = pdata->ohci_data;
 
-       if (omap->count != 0)
-               goto end_disble;
+       pm_runtime_enable(dev);
 
-       /* Reset OMAP modules for insmod/rmmod to work */
-       usbhs_write(omap->uhh_base, OMAP_UHH_SYSCONFIG,
-                       is_omap_usbhs_rev2(omap) ?
-                       OMAP4_UHH_SYSCONFIG_SOFTRESET :
-                       OMAP_UHH_SYSCONFIG_SOFTRESET);
 
-       timeout = jiffies + msecs_to_jiffies(100);
-       while (!(usbhs_read(omap->uhh_base, OMAP_UHH_SYSSTATUS)
-                               & (1 << 0))) {
-               cpu_relax();
+       for (i = 0; i < OMAP3_HS_USB_PORTS; i++)
+               if (is_ehci_phy_mode(i) || is_ehci_tll_mode(i) ||
+                       is_ehci_hsic_mode(i)) {
+                       omap->ehci_logic_fck = clk_get(dev, "ehci_logic_fck");
+                       if (IS_ERR(omap->ehci_logic_fck)) {
+                               ret = PTR_ERR(omap->ehci_logic_fck);
+                               dev_warn(dev, "ehci_logic_fck failed:%d\n",
+                                        ret);
+                       }
+                       break;
+               }
 
-               if (time_after(jiffies, timeout))
-                       dev_dbg(dev, "operation timed out\n");
+       omap->utmi_p1_fck = clk_get(dev, "utmi_p1_gfclk");
+       if (IS_ERR(omap->utmi_p1_fck)) {
+               ret = PTR_ERR(omap->utmi_p1_fck);
+               dev_err(dev, "utmi_p1_gfclk failed error:%d\n", ret);
+               goto err_end;
        }
 
-       while (!(usbhs_read(omap->uhh_base, OMAP_UHH_SYSSTATUS)
-                               & (1 << 1))) {
-               cpu_relax();
+       omap->xclk60mhsp1_ck = clk_get(dev, "xclk60mhsp1_ck");
+       if (IS_ERR(omap->xclk60mhsp1_ck)) {
+               ret = PTR_ERR(omap->xclk60mhsp1_ck);
+               dev_err(dev, "xclk60mhsp1_ck failed error:%d\n", ret);
+               goto err_utmi_p1_fck;
+       }
 
-               if (time_after(jiffies, timeout))
-                       dev_dbg(dev, "operation timed out\n");
+       omap->utmi_p2_fck = clk_get(dev, "utmi_p2_gfclk");
+       if (IS_ERR(omap->utmi_p2_fck)) {
+               ret = PTR_ERR(omap->utmi_p2_fck);
+               dev_err(dev, "utmi_p2_gfclk failed error:%d\n", ret);
+               goto err_xclk60mhsp1_ck;
        }
 
-       while (!(usbhs_read(omap->uhh_base, OMAP_UHH_SYSSTATUS)
-                               & (1 << 2))) {
-               cpu_relax();
+       omap->xclk60mhsp2_ck = clk_get(dev, "xclk60mhsp2_ck");
+       if (IS_ERR(omap->xclk60mhsp2_ck)) {
+               ret = PTR_ERR(omap->xclk60mhsp2_ck);
+               dev_err(dev, "xclk60mhsp2_ck failed error:%d\n", ret);
+               goto err_utmi_p2_fck;
+       }
 
-               if (time_after(jiffies, timeout))
-                       dev_dbg(dev, "operation timed out\n");
+       omap->usbhost_p1_fck = clk_get(dev, "usb_host_hs_utmi_p1_clk");
+       if (IS_ERR(omap->usbhost_p1_fck)) {
+               ret = PTR_ERR(omap->usbhost_p1_fck);
+               dev_err(dev, "usbhost_p1_fck failed error:%d\n", ret);
+               goto err_xclk60mhsp2_ck;
        }
 
-       usbhs_write(omap->tll_base, OMAP_USBTLL_SYSCONFIG, (1 << 1));
+       omap->usbtll_p1_fck = clk_get(dev, "usb_tll_hs_usb_ch0_clk");
+       if (IS_ERR(omap->usbtll_p1_fck)) {
+               ret = PTR_ERR(omap->usbtll_p1_fck);
+               dev_err(dev, "usbtll_p1_fck failed error:%d\n", ret);
+               goto err_usbhost_p1_fck;
+       }
 
-       while (!(usbhs_read(omap->tll_base, OMAP_USBTLL_SYSSTATUS)
-                               & (1 << 0))) {
-               cpu_relax();
+       omap->usbhost_p2_fck = clk_get(dev, "usb_host_hs_utmi_p2_clk");
+       if (IS_ERR(omap->usbhost_p2_fck)) {
+               ret = PTR_ERR(omap->usbhost_p2_fck);
+               dev_err(dev, "usbhost_p2_fck failed error:%d\n", ret);
+               goto err_usbtll_p1_fck;
+       }
 
-               if (time_after(jiffies, timeout))
-                       dev_dbg(dev, "operation timed out\n");
+       omap->usbtll_p2_fck = clk_get(dev, "usb_tll_hs_usb_ch1_clk");
+       if (IS_ERR(omap->usbtll_p2_fck)) {
+               ret = PTR_ERR(omap->usbtll_p2_fck);
+               dev_err(dev, "usbtll_p2_fck failed error:%d\n", ret);
+               goto err_usbhost_p2_fck;
        }
 
-       if (is_omap_usbhs_rev2(omap)) {
-               if (is_ehci_tll_mode(pdata->port_mode[0]))
-                       clk_disable(omap->usbtll_p1_fck);
-               if (is_ehci_tll_mode(pdata->port_mode[1]))
-                       clk_disable(omap->usbtll_p2_fck);
-               clk_disable(omap->utmi_p2_fck);
-               clk_disable(omap->utmi_p1_fck);
+       omap->init_60m_fclk = clk_get(dev, "init_60m_fclk");
+       if (IS_ERR(omap->init_60m_fclk)) {
+               ret = PTR_ERR(omap->init_60m_fclk);
+               dev_err(dev, "init_60m_fclk failed error:%d\n", ret);
+               goto err_usbtll_p2_fck;
        }
 
-       clk_disable(omap->usbtll_ick);
-       clk_disable(omap->usbtll_fck);
-       clk_disable(omap->usbhost_fs_fck);
-       clk_disable(omap->usbhost_hs_fck);
-       clk_disable(omap->usbhost_ick);
+       if (is_ehci_phy_mode(pdata->port_mode[0])) {
+               /* for OMAP3 , the clk set paretn fails */
+               ret = clk_set_parent(omap->utmi_p1_fck,
+                                       omap->xclk60mhsp1_ck);
+               if (ret != 0)
+                       dev_err(dev, "xclk60mhsp1_ck set parent"
+                               "failed error:%d\n", ret);
+       } else if (is_ehci_tll_mode(pdata->port_mode[0])) {
+               ret = clk_set_parent(omap->utmi_p1_fck,
+                                       omap->init_60m_fclk);
+               if (ret != 0)
+                       dev_err(dev, "init_60m_fclk set parent"
+                               "failed error:%d\n", ret);
+       }
 
-       /* The gpio_free migh sleep; so unlock the spinlock */
-       spin_unlock_irqrestore(&omap->lock, flags);
+       if (is_ehci_phy_mode(pdata->port_mode[1])) {
+               ret = clk_set_parent(omap->utmi_p2_fck,
+                                       omap->xclk60mhsp2_ck);
+               if (ret != 0)
+                       dev_err(dev, "xclk60mhsp2_ck set parent"
+                                       "failed error:%d\n", ret);
+       } else if (is_ehci_tll_mode(pdata->port_mode[1])) {
+               ret = clk_set_parent(omap->utmi_p2_fck,
+                                               omap->init_60m_fclk);
+               if (ret != 0)
+                       dev_err(dev, "init_60m_fclk set parent"
+                               "failed error:%d\n", ret);
+       }
 
-       if (pdata->ehci_data->phy_reset) {
-               if (gpio_is_valid(pdata->ehci_data->reset_gpio_port[0]))
-                       gpio_free(pdata->ehci_data->reset_gpio_port[0]);
+       res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "uhh");
+       if (!res) {
+               dev_err(dev, "UHH EHCI get resource failed\n");
+               ret = -ENODEV;
+               goto err_init_60m_fclk;
+       }
 
-               if (gpio_is_valid(pdata->ehci_data->reset_gpio_port[1]))
-                       gpio_free(pdata->ehci_data->reset_gpio_port[1]);
+       omap->uhh_base = ioremap(res->start, resource_size(res));
+       if (!omap->uhh_base) {
+               dev_err(dev, "UHH ioremap failed\n");
+               ret = -ENOMEM;
+               goto err_init_60m_fclk;
        }
-       return;
 
-end_disble:
-       spin_unlock_irqrestore(&omap->lock, flags);
-}
+       res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "tll");
+       if (!res) {
+               dev_err(dev, "UHH EHCI get resource failed\n");
+               ret = -ENODEV;
+               goto err_tll;
+       }
 
-int omap_usbhs_enable(struct device *dev)
-{
-       return  usbhs_enable(dev->parent);
+       omap->tll_base = ioremap(res->start, resource_size(res));
+       if (!omap->tll_base) {
+               dev_err(dev, "TLL ioremap failed\n");
+               ret = -ENOMEM;
+               goto err_tll;
+       }
+
+       platform_set_drvdata(pdev, omap);
+
+       ret = omap_usbhs_alloc_children(pdev);
+       if (ret) {
+               dev_err(dev, "omap_usbhs_alloc_children failed\n");
+               goto err_alloc;
+       }
+
+       omap_usbhs_init(dev);
+
+       goto end_probe;
+
+err_alloc:
+       iounmap(omap->tll_base);
+
+err_tll:
+       iounmap(omap->uhh_base);
+
+err_init_60m_fclk:
+       clk_put(omap->init_60m_fclk);
+
+err_usbtll_p2_fck:
+       clk_put(omap->usbtll_p2_fck);
+
+err_usbhost_p2_fck:
+       clk_put(omap->usbhost_p2_fck);
+
+err_usbtll_p1_fck:
+       clk_put(omap->usbtll_p1_fck);
+
+err_usbhost_p1_fck:
+       clk_put(omap->usbhost_p1_fck);
+
+err_xclk60mhsp2_ck:
+       clk_put(omap->xclk60mhsp2_ck);
+
+err_utmi_p2_fck:
+       clk_put(omap->utmi_p2_fck);
+
+err_xclk60mhsp1_ck:
+       clk_put(omap->xclk60mhsp1_ck);
+
+err_utmi_p1_fck:
+       clk_put(omap->utmi_p1_fck);
+
+err_end:
+       clk_put(omap->ehci_logic_fck);
+       pm_runtime_disable(dev);
+       kfree(omap);
+
+end_probe:
+       return ret;
 }
-EXPORT_SYMBOL_GPL(omap_usbhs_enable);
 
-void omap_usbhs_disable(struct device *dev)
+/**
+ * usbhs_omap_remove - shutdown processing for UHH & TLL HCDs
+ * @pdev: USB Host Controller being removed
+ *
+ * Reverses the effect of usbhs_omap_probe().
+ */
+static int __devexit usbhs_omap_remove(struct platform_device *pdev)
 {
-       usbhs_disable(dev->parent);
+       struct usbhs_hcd_omap *omap = platform_get_drvdata(pdev);
+
+       omap_usbhs_deinit(&pdev->dev);
+       iounmap(omap->tll_base);
+       iounmap(omap->uhh_base);
+       clk_put(omap->init_60m_fclk);
+       clk_put(omap->usbtll_p2_fck);
+       clk_put(omap->usbhost_p2_fck);
+       clk_put(omap->usbtll_p1_fck);
+       clk_put(omap->usbhost_p1_fck);
+       clk_put(omap->xclk60mhsp2_ck);
+       clk_put(omap->utmi_p2_fck);
+       clk_put(omap->xclk60mhsp1_ck);
+       clk_put(omap->utmi_p1_fck);
+       clk_put(omap->ehci_logic_fck);
+       pm_runtime_disable(&pdev->dev);
+       kfree(omap);
+
+       return 0;
 }
-EXPORT_SYMBOL_GPL(omap_usbhs_disable);
+
+static const struct dev_pm_ops usbhsomap_dev_pm_ops = {
+       .runtime_suspend        = usbhs_runtime_suspend,
+       .runtime_resume         = usbhs_runtime_resume,
+};
 
 static struct platform_driver usbhs_omap_driver = {
        .driver = {
                .name           = (char *)usbhs_driver_name,
                .owner          = THIS_MODULE,
+               .pm             = &usbhsomap_dev_pm_ops,
        },
        .remove         = __exit_p(usbhs_omap_remove),
 };
index e39b0297bad1806a2e2cb49e2a5047e026847dc6..568cefbd63a2a58bbd787141e2294ff1d7805ba7 100644 (file)
@@ -41,6 +41,7 @@
 #include <linux/usb/ulpi.h>
 #include <plat/usb.h>
 #include <linux/regulator/consumer.h>
+#include <linux/pm_runtime.h>
 
 /* EHCI Register Set */
 #define EHCI_INSNREG04                                 (0xA0)
@@ -190,11 +191,8 @@ static int ehci_hcd_omap_probe(struct platform_device *pdev)
                }
        }
 
-       ret = omap_usbhs_enable(dev);
-       if (ret) {
-               dev_err(dev, "failed to start usbhs with err %d\n", ret);
-               goto err_enable;
-       }
+       pm_runtime_enable(dev);
+       pm_runtime_get_sync(dev);
 
        /*
         * An undocumented "feature" in the OMAP3 EHCI controller,
@@ -240,11 +238,8 @@ static int ehci_hcd_omap_probe(struct platform_device *pdev)
        return 0;
 
 err_add_hcd:
-       omap_usbhs_disable(dev);
-
-err_enable:
        disable_put_regulator(pdata);
-       usb_put_hcd(hcd);
+       pm_runtime_put_sync(dev);
 
 err_io:
        iounmap(regs);
@@ -266,10 +261,12 @@ static int ehci_hcd_omap_remove(struct platform_device *pdev)
        struct usb_hcd *hcd     = dev_get_drvdata(dev);
 
        usb_remove_hcd(hcd);
-       omap_usbhs_disable(dev);
        disable_put_regulator(dev->platform_data);
        iounmap(hcd->regs);
        usb_put_hcd(hcd);
+       pm_runtime_put_sync(dev);
+       pm_runtime_disable(dev);
+
        return 0;
 }
 
index 516ebc4d6cc29a820c13d3ee4578d3c6e49c2ad8..1b8133b6e451a7a30965eae265a4106c3050521f 100644 (file)
@@ -31,6 +31,7 @@
 
 #include <linux/platform_device.h>
 #include <plat/usb.h>
+#include <linux/pm_runtime.h>
 
 /*-------------------------------------------------------------------------*/
 
@@ -134,7 +135,7 @@ static int __devinit ohci_hcd_omap3_probe(struct platform_device *pdev)
        int                     irq;
 
        if (usb_disabled())
-               goto err_end;
+               return -ENODEV;
 
        if (!dev->parent) {
                dev_err(dev, "Missing parent device\n");
@@ -172,11 +173,8 @@ static int __devinit ohci_hcd_omap3_probe(struct platform_device *pdev)
        hcd->rsrc_len = resource_size(res);
        hcd->regs =  regs;
 
-       ret = omap_usbhs_enable(dev);
-       if (ret) {
-               dev_dbg(dev, "failed to start ohci\n");
-               goto err_end;
-       }
+       pm_runtime_enable(dev);
+       pm_runtime_get_sync(dev);
 
        ohci_hcd_init(hcd_to_ohci(hcd));
 
@@ -189,9 +187,7 @@ static int __devinit ohci_hcd_omap3_probe(struct platform_device *pdev)
        return 0;
 
 err_add_hcd:
-       omap_usbhs_disable(dev);
-
-err_end:
+       pm_runtime_put_sync(dev);
        usb_put_hcd(hcd);
 
 err_io:
@@ -220,9 +216,9 @@ static int __devexit ohci_hcd_omap3_remove(struct platform_device *pdev)
 
        iounmap(hcd->regs);
        usb_remove_hcd(hcd);
-       omap_usbhs_disable(dev);
+       pm_runtime_put_sync(dev);
+       pm_runtime_disable(dev);
        usb_put_hcd(hcd);
-
        return 0;
 }