1
0
Fork 0

MLK-24527-6 usb: dwc3: imx8mp: add imx8mp specific dwc3 platform data

With new platform data introduced, we can use it to pass set_role_post
api and various quirks to dwc3 core driver, and remove the dependency
of dwc3 instance when probe, this can resolve the problem if this
dwc3-imx8mp driver as module load before the dwc3 core driver loaded.

Reviewed-by: Peter Chen <peter.chen@nxp.com>
Signed-off-by: Li Jun <jun.li@nxp.com>
(cherry picked from commit 1b47d2e3f6090835aedaf04dc538e74f63d130e3)
5.4-rM2-2.2.x-imx-squashed
Li Jun 2020-08-20 17:40:38 +08:00
parent 27dfd22242
commit ac4236b058
1 changed files with 32 additions and 22 deletions

View File

@ -53,6 +53,9 @@ static void dwc_imx8mp_wakeup_enable(struct dwc3_imx8mp *dwc_imx)
struct dwc3 *dwc = platform_get_drvdata(dwc_imx->dwc3);
u32 val;
if (!dwc)
return;
val = readl(dwc_imx->glue_base + USB_WAKEUP_CTRL);
if ((dwc->current_dr_role == DWC3_GCTL_PRTCAP_HOST) && dwc->xhci)
@ -96,6 +99,12 @@ static irqreturn_t dwc3_imx8mp_interrupt(int irq, void *_dwc_imx)
disable_irq_nosync(dwc_imx->irq);
dwc_imx->wakeup_pending = true;
if (!dwc) {
pm_runtime_resume(dwc_imx->dev);
return IRQ_HANDLED;
}
/*
* runtime resume xhci or gadget, dwc3_imx8mp itself
* as parent device will be resumed firstly by pm core
@ -129,12 +138,31 @@ static void dwc3_imx8mp_set_role_post(struct dwc3 *dwc, u32 role)
}
}
static struct xhci_plat_priv dwc3_imx8mp_xhci_priv = {
.quirks = XHCI_NO_64BIT_SUPPORT |
XHCI_MISSING_CAS |
XHCI_SKIP_PHY_INIT,
};
static struct dwc3_platform_data dwc3_imx8mp_pdata = {
.xhci_priv = &dwc3_imx8mp_xhci_priv,
.set_role_post = dwc3_imx8mp_set_role_post,
.quirks = DWC3_SOFT_ITP_SYNC,
};
static struct of_dev_auxdata dwc3_imx8mp_auxdata[] = {
{
.compatible = "snps,dwc3",
.platform_data = &dwc3_imx8mp_pdata,
},
{},
};
static int dwc3_imx8mp_probe(struct platform_device *pdev)
{
struct device *dev = &pdev->dev;
struct device_node *dwc3_np, *node = dev->of_node;
struct dwc3_imx8mp *dwc_imx;
struct dwc3 *dwc;
int error, irq;
if (!node) {
@ -190,7 +218,7 @@ static int dwc3_imx8mp_probe(struct platform_device *pdev)
goto disable_clks;
}
error = of_platform_populate(node, NULL, NULL, dev);
error = of_platform_populate(node, NULL, dwc3_imx8mp_auxdata, dev);
if (error) {
dev_err(&pdev->dev, "failed to create dwc3 core\n");
goto disable_clks;
@ -202,25 +230,7 @@ static int dwc3_imx8mp_probe(struct platform_device *pdev)
error = -ENODEV;
goto depopulate;
}
dwc = platform_get_drvdata(dwc_imx->dwc3);
if (!dwc) {
error = -EPROBE_DEFER;
goto depopulate;
}
dwc->priv_data = devm_kzalloc(dev, sizeof(struct dwc3_priv_data),
GFP_KERNEL);
if (!dwc->priv_data) {
error = -ENOMEM;
goto depopulate;
}
dwc->priv_data->set_role_post = dwc3_imx8mp_set_role_post;
if (dwc->dr_mode == USB_DR_MODE_HOST)
dwc->priv_data->set_role_post(dwc, DWC3_GCTL_PRTCAP_HOST);
else if (dwc->dr_mode == USB_DR_MODE_PERIPHERAL)
dwc->priv_data->set_role_post(dwc, DWC3_GCTL_PRTCAP_DEVICE);
of_node_put(dwc3_np);
device_set_wakeup_capable(dev, true);
pm_runtime_set_active(dev);
@ -287,7 +297,7 @@ static int dwc3_imx8mp_resume(struct dwc3_imx8mp *dwc_imx, pm_message_t msg)
if (dwc_imx->wakeup_pending) {
dwc_imx->wakeup_pending = false;
if (dwc->current_dr_role == DWC3_GCTL_PRTCAP_DEVICE) {
if (dwc && dwc->current_dr_role == DWC3_GCTL_PRTCAP_DEVICE) {
pm_runtime_mark_last_busy(dwc->dev);
pm_runtime_put_autosuspend(dwc->dev);
}