diff options
author | Chunfeng Yun <chunfeng.yun@mediatek.com> | 2021-07-15 17:07:57 +0800 |
---|---|---|
committer | Greg Kroah-Hartman <gregkh@linuxfoundation.org> | 2021-07-27 15:58:37 +0200 |
commit | 427c66422e14b8468ee005aa6edf76ef0c2a8fc2 (patch) | |
tree | 67b8054585d58c8c06f69f47fd2107a5b341c51a /drivers/usb/mtu3/mtu3_plat.c | |
parent | 6244831543ec269f40ed9032bb8194c089049718 (diff) | |
download | linux-next-427c66422e14b8468ee005aa6edf76ef0c2a8fc2.tar.gz |
usb: mtu3: support suspend/resume for device mode
Support suspend/resume for device mode if the device is not
connected with a host, otherwise reject to suspend.
Signed-off-by: Chunfeng Yun <chunfeng.yun@mediatek.com>
Link: https://lore.kernel.org/r/1626340078-29111-13-git-send-email-chunfeng.yun@mediatek.com
Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
Diffstat (limited to 'drivers/usb/mtu3/mtu3_plat.c')
-rw-r--r-- | drivers/usb/mtu3/mtu3_plat.c | 47 |
1 files changed, 35 insertions, 12 deletions
diff --git a/drivers/usb/mtu3/mtu3_plat.c b/drivers/usb/mtu3/mtu3_plat.c index 2be890f84c94..e174ada689f2 100644 --- a/drivers/usb/mtu3/mtu3_plat.c +++ b/drivers/usb/mtu3/mtu3_plat.c @@ -421,21 +421,32 @@ static int mtu3_remove(struct platform_device *pdev) return 0; } -/* - * when support dual-role mode, we reject suspend when - * it works as device mode; - */ static int mtu3_suspend_common(struct device *dev, pm_message_t msg) { struct ssusb_mtk *ssusb = dev_get_drvdata(dev); + int ret = 0; dev_dbg(dev, "%s\n", __func__); - /* REVISIT: disconnect it for only device mode? */ - if (!ssusb->is_host) - return 0; + switch (ssusb->dr_mode) { + case USB_DR_MODE_PERIPHERAL: + ret = ssusb_gadget_suspend(ssusb, msg); + if (ret) + return ret; - ssusb_host_suspend(ssusb); + break; + case USB_DR_MODE_HOST: + ssusb_host_suspend(ssusb); + break; + case USB_DR_MODE_OTG: + if (!ssusb->is_host) + return 0; + + ssusb_host_suspend(ssusb); + break; + default: + return -EINVAL; + } ssusb_phy_power_off(ssusb); clk_bulk_disable_unprepare(BULK_CLKS_CNT, ssusb->clks); ssusb_wakeup_set(ssusb, true); @@ -450,9 +461,6 @@ static int mtu3_resume_common(struct device *dev, pm_message_t msg) dev_dbg(dev, "%s\n", __func__); - if (!ssusb->is_host) - return 0; - ssusb_wakeup_set(ssusb, false); ret = clk_bulk_prepare_enable(BULK_CLKS_CNT, ssusb->clks); if (ret) @@ -462,7 +470,22 @@ static int mtu3_resume_common(struct device *dev, pm_message_t msg) if (ret) goto phy_err; - ssusb_host_resume(ssusb, false); + switch (ssusb->dr_mode) { + case USB_DR_MODE_PERIPHERAL: + ssusb_gadget_resume(ssusb, msg); + break; + case USB_DR_MODE_HOST: + ssusb_host_resume(ssusb, false); + break; + case USB_DR_MODE_OTG: + if (!ssusb->is_host) + return 0; + + ssusb_host_resume(ssusb, true); + break; + default: + return -EINVAL; + } return 0; |