summaryrefslogtreecommitdiff
path: root/drivers/phy/broadcom/phy-brcm-usb.c
diff options
context:
space:
mode:
authorAl Cooper <alcooperx@gmail.com>2020-01-03 13:18:11 -0500
committerKishon Vijay Abraham I <kishon@ti.com>2020-01-08 12:58:06 +0530
commitb0c0b66c0b432d3f3a1ae5849298ba9c7f1810c5 (patch)
tree51bc54504ebd3920872fe8259c27b551bdea7240 /drivers/phy/broadcom/phy-brcm-usb.c
parent5dfe1cec580829faa49842672a25481b104c26ef (diff)
phy: usb: Add support for wake and USB low power mode for 7211 S2/S5
Add support for 7211 USB wake. Disable all possible 7211 USB logic for S2/S5 if USB wake is not enabled. On the 7211, the XHCI wake signal was not connected properly and only goes to the USB1_USB1_CTRL_TP_DIAG1 diagonstic register. The workaround is to have VPU code running that polls for the proper bit in the DIAG register and to wake the system when the bit is asserted. Signed-off-by: Al Cooper <alcooperx@gmail.com> Reviewed-by: Florian Fainelli <f.fainelli@gmail.com> Signed-off-by: Kishon Vijay Abraham I <kishon@ti.com>
Diffstat (limited to 'drivers/phy/broadcom/phy-brcm-usb.c')
-rw-r--r--drivers/phy/broadcom/phy-brcm-usb.c25
1 files changed, 18 insertions, 7 deletions
diff --git a/drivers/phy/broadcom/phy-brcm-usb.c b/drivers/phy/broadcom/phy-brcm-usb.c
index 1ab44f54244b..491bbd46c5b3 100644
--- a/drivers/phy/broadcom/phy-brcm-usb.c
+++ b/drivers/phy/broadcom/phy-brcm-usb.c
@@ -535,16 +535,26 @@ static int brcm_usb_phy_suspend(struct device *dev)
struct brcm_usb_phy_data *priv = dev_get_drvdata(dev);
if (priv->init_count) {
+ priv->ini.wake_enabled = device_may_wakeup(dev);
if (priv->phys[BRCM_USB_PHY_3_0].inited)
brcm_usb_uninit_xhci(&priv->ini);
if (priv->phys[BRCM_USB_PHY_2_0].inited)
brcm_usb_uninit_eohci(&priv->ini);
brcm_usb_uninit_common(&priv->ini);
- brcm_usb_wake_enable(&priv->ini, true);
- if (priv->phys[BRCM_USB_PHY_3_0].inited)
- clk_disable_unprepare(priv->usb_30_clk);
- if (priv->phys[BRCM_USB_PHY_2_0].inited || !priv->has_eohci)
- clk_disable_unprepare(priv->usb_20_clk);
+
+ /*
+ * Handle the clocks unless needed for wake. This has
+ * to work for both older XHCI->3.0-clks, EOHCI->2.0-clks
+ * and newer XHCI->2.0-clks/3.0-clks.
+ */
+
+ if (!priv->ini.suspend_with_clocks) {
+ if (priv->phys[BRCM_USB_PHY_3_0].inited)
+ clk_disable_unprepare(priv->usb_30_clk);
+ if (priv->phys[BRCM_USB_PHY_2_0].inited ||
+ !priv->has_eohci)
+ clk_disable_unprepare(priv->usb_20_clk);
+ }
if (priv->wake_irq >= 0)
enable_irq_wake(priv->wake_irq);
}
@@ -557,7 +567,6 @@ static int brcm_usb_phy_resume(struct device *dev)
clk_prepare_enable(priv->usb_20_clk);
clk_prepare_enable(priv->usb_30_clk);
- brcm_usb_wake_enable(&priv->ini, false);
brcm_usb_init_ipp(&priv->ini);
/*
@@ -579,6 +588,8 @@ static int brcm_usb_phy_resume(struct device *dev)
} else if (priv->has_xhci) {
brcm_usb_uninit_xhci(&priv->ini);
clk_disable_unprepare(priv->usb_30_clk);
+ if (!priv->has_eohci)
+ clk_disable_unprepare(priv->usb_20_clk);
}
} else {
if (priv->has_xhci)
@@ -589,7 +600,7 @@ static int brcm_usb_phy_resume(struct device *dev)
clk_disable_unprepare(priv->usb_20_clk);
clk_disable_unprepare(priv->usb_30_clk);
}
-
+ priv->ini.wake_enabled = false;
return 0;
}
#endif /* CONFIG_PM_SLEEP */