From a0a83eb407ef17dae9a286d86ee2a437f6adb4c2 Mon Sep 17 00:00:00 2001 From: Srinivas Kandagatla Date: Wed, 10 Oct 2012 19:36:46 +0100 Subject: [PATCH 01/26] usb: musb: am35x: use module_platform_driver macro This patch removes some code duplication by using module_platform_driver. Signed-off-by: Srinivas Kandagatla Signed-off-by: Felipe Balbi --- drivers/usb/musb/am35x.c | 13 +------------ 1 file changed, 1 insertion(+), 12 deletions(-) diff --git a/drivers/usb/musb/am35x.c b/drivers/usb/musb/am35x.c index 457f25e62c51..89b128bdbca4 100644 --- a/drivers/usb/musb/am35x.c +++ b/drivers/usb/musb/am35x.c @@ -648,15 +648,4 @@ static struct platform_driver am35x_driver = { MODULE_DESCRIPTION("AM35x MUSB Glue Layer"); MODULE_AUTHOR("Ajay Kumar Gupta "); MODULE_LICENSE("GPL v2"); - -static int __init am35x_init(void) -{ - return platform_driver_register(&am35x_driver); -} -module_init(am35x_init); - -static void __exit am35x_exit(void) -{ - platform_driver_unregister(&am35x_driver); -} -module_exit(am35x_exit); +module_platform_driver(am35x_driver); From 692373e128f16da708ec6ddf80ee5b5bb3761ef9 Mon Sep 17 00:00:00 2001 From: Srinivas Kandagatla Date: Wed, 10 Oct 2012 19:36:52 +0100 Subject: [PATCH 02/26] usb: musb: blackfin: use module_platform_driver macro This patch removes some code duplication by using module_platform_driver. Signed-off-by: Srinivas Kandagatla Signed-off-by: Felipe Balbi --- drivers/usb/musb/blackfin.c | 13 +------------ 1 file changed, 1 insertion(+), 12 deletions(-) diff --git a/drivers/usb/musb/blackfin.c b/drivers/usb/musb/blackfin.c index e8cff9bb9d23..8c16a22e1718 100644 --- a/drivers/usb/musb/blackfin.c +++ b/drivers/usb/musb/blackfin.c @@ -585,15 +585,4 @@ static struct platform_driver bfin_driver = { MODULE_DESCRIPTION("Blackfin MUSB Glue Layer"); MODULE_AUTHOR("Bryan Wy "); MODULE_LICENSE("GPL v2"); - -static int __init bfin_init(void) -{ - return platform_driver_register(&bfin_driver); -} -module_init(bfin_init); - -static void __exit bfin_exit(void) -{ - platform_driver_unregister(&bfin_driver); -} -module_exit(bfin_exit); +module_platform_driver(bfin_driver); From 0b07734d5e0096458acf19b2e6b0585ad5006b86 Mon Sep 17 00:00:00 2001 From: Srinivas Kandagatla Date: Wed, 10 Oct 2012 19:36:59 +0100 Subject: [PATCH 03/26] usb: musb: da8xx: use module_platform_driver macro This patch removes some code duplication by using module_platform_driver. Signed-off-by: Srinivas Kandagatla Signed-off-by: Felipe Balbi --- drivers/usb/musb/da8xx.c | 13 +------------ 1 file changed, 1 insertion(+), 12 deletions(-) diff --git a/drivers/usb/musb/da8xx.c b/drivers/usb/musb/da8xx.c index 8bc44b76eec2..2366b818443b 100644 --- a/drivers/usb/musb/da8xx.c +++ b/drivers/usb/musb/da8xx.c @@ -593,15 +593,4 @@ static struct platform_driver da8xx_driver = { MODULE_DESCRIPTION("DA8xx/OMAP-L1x MUSB Glue Layer"); MODULE_AUTHOR("Sergei Shtylyov "); MODULE_LICENSE("GPL v2"); - -static int __init da8xx_init(void) -{ - return platform_driver_register(&da8xx_driver); -} -module_init(da8xx_init); - -static void __exit da8xx_exit(void) -{ - platform_driver_unregister(&da8xx_driver); -} -module_exit(da8xx_exit); +module_platform_driver(da8xx_driver); From 8d92f6d46c73bbc10310a38784f130527dfcf8a1 Mon Sep 17 00:00:00 2001 From: Srinivas Kandagatla Date: Wed, 10 Oct 2012 19:37:07 +0100 Subject: [PATCH 04/26] usb: musb: davinci: use module_platform_driver macro This patch removes some code duplication by using module_platform_driver. Signed-off-by: Srinivas Kandagatla Signed-off-by: Felipe Balbi --- drivers/usb/musb/davinci.c | 13 +------------ 1 file changed, 1 insertion(+), 12 deletions(-) diff --git a/drivers/usb/musb/davinci.c b/drivers/usb/musb/davinci.c index 606bfd00cde6..62785bf0f95a 100644 --- a/drivers/usb/musb/davinci.c +++ b/drivers/usb/musb/davinci.c @@ -625,15 +625,4 @@ static struct platform_driver davinci_driver = { MODULE_DESCRIPTION("DaVinci MUSB Glue Layer"); MODULE_AUTHOR("Felipe Balbi "); MODULE_LICENSE("GPL v2"); - -static int __init davinci_init(void) -{ - return platform_driver_register(&davinci_driver); -} -module_init(davinci_init); - -static void __exit davinci_exit(void) -{ - platform_driver_unregister(&davinci_driver); -} -module_exit(davinci_exit); +module_platform_driver(davinci_driver); From 01380c081eada4fa4a2e52ef9ea2b16eaddbfc46 Mon Sep 17 00:00:00 2001 From: Srinivas Kandagatla Date: Wed, 10 Oct 2012 19:37:14 +0100 Subject: [PATCH 05/26] usb: musb: tusb6010: use module_platform_driver macro This patch removes some code duplication by using module_platform_driver. Signed-off-by: Srinivas Kandagatla Signed-off-by: Felipe Balbi --- drivers/usb/musb/tusb6010.c | 13 +------------ 1 file changed, 1 insertion(+), 12 deletions(-) diff --git a/drivers/usb/musb/tusb6010.c b/drivers/usb/musb/tusb6010.c index dc4d75ea13ad..39ece28019fd 100644 --- a/drivers/usb/musb/tusb6010.c +++ b/drivers/usb/musb/tusb6010.c @@ -1251,15 +1251,4 @@ static struct platform_driver tusb_driver = { MODULE_DESCRIPTION("TUSB6010 MUSB Glue Layer"); MODULE_AUTHOR("Felipe Balbi "); MODULE_LICENSE("GPL v2"); - -static int __init tusb_init(void) -{ - return platform_driver_register(&tusb_driver); -} -module_init(tusb_init); - -static void __exit tusb_exit(void) -{ - platform_driver_unregister(&tusb_driver); -} -module_exit(tusb_exit); +module_platform_driver(tusb_driver); From 0e7090a626eb6205c123f735a879065702a08cb8 Mon Sep 17 00:00:00 2001 From: Srinivas Kandagatla Date: Wed, 10 Oct 2012 19:37:21 +0100 Subject: [PATCH 06/26] usb: musb: ux500: use module_platform_driver macro This patch removes some code duplication by using module_platform_driver. Signed-off-by: Srinivas Kandagatla Signed-off-by: Felipe Balbi --- drivers/usb/musb/ux500.c | 13 +------------ 1 file changed, 1 insertion(+), 12 deletions(-) diff --git a/drivers/usb/musb/ux500.c b/drivers/usb/musb/ux500.c index d62a91fedc22..be1430ad60ee 100644 --- a/drivers/usb/musb/ux500.c +++ b/drivers/usb/musb/ux500.c @@ -219,15 +219,4 @@ static struct platform_driver ux500_driver = { MODULE_DESCRIPTION("UX500 MUSB Glue Layer"); MODULE_AUTHOR("Mian Yousaf Kaukab "); MODULE_LICENSE("GPL v2"); - -static int __init ux500_init(void) -{ - return platform_driver_register(&ux500_driver); -} -module_init(ux500_init); - -static void __exit ux500_exit(void) -{ - platform_driver_unregister(&ux500_driver); -} -module_exit(ux500_exit); +module_platform_driver(ux500_driver); From 562915153140292b8c59bcab12f039b3aef78cb5 Mon Sep 17 00:00:00 2001 From: Wei Yongjun Date: Tue, 23 Oct 2012 13:24:51 +0800 Subject: [PATCH 07/26] usb: musb: am35x: use platform_device_unregister in am35x_remove() platform_device_unregister() only calls platform_device_del() and platform_device_put(), thus use platform_device_unregister() to simplify the code. Also the documents in platform.c shows that platform_device_del and platform_device_put must _only_ be externally called in error cases. All other usage is a bug. dpatch engine is used to auto generate this patch. (https://github.com/weiyj/dpatch) Signed-off-by: Wei Yongjun Signed-off-by: Felipe Balbi --- drivers/usb/musb/am35x.c | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/drivers/usb/musb/am35x.c b/drivers/usb/musb/am35x.c index 89b128bdbca4..fdfd779c35b3 100644 --- a/drivers/usb/musb/am35x.c +++ b/drivers/usb/musb/am35x.c @@ -572,8 +572,7 @@ static int __devexit am35x_remove(struct platform_device *pdev) struct am35x_glue *glue = platform_get_drvdata(pdev); musb_put_id(&pdev->dev, glue->musb->id); - platform_device_del(glue->musb); - platform_device_put(glue->musb); + platform_device_unregister(glue->musb); clk_disable(glue->clk); clk_disable(glue->phy_clk); clk_put(glue->clk); From 01e40da08ca1fd6febcfbac819dbf07ad80bf2af Mon Sep 17 00:00:00 2001 From: Wei Yongjun Date: Tue, 23 Oct 2012 13:26:00 +0800 Subject: [PATCH 08/26] usb: musb: blackfin: use platform_device_unregister in bfin_remove() platform_device_unregister() only calls platform_device_del() and platform_device_put(), thus use platform_device_unregister() to simplify the code. Also the documents in platform.c shows that platform_device_del and platform_device_put must _only_ be externally called in error cases. All other usage is a bug. dpatch engine is used to auto generate this patch. (https://github.com/weiyj/dpatch) Signed-off-by: Wei Yongjun Signed-off-by: Felipe Balbi --- drivers/usb/musb/blackfin.c | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/drivers/usb/musb/blackfin.c b/drivers/usb/musb/blackfin.c index 8c16a22e1718..307e726a2bd7 100644 --- a/drivers/usb/musb/blackfin.c +++ b/drivers/usb/musb/blackfin.c @@ -528,8 +528,7 @@ static int __devexit bfin_remove(struct platform_device *pdev) struct bfin_glue *glue = platform_get_drvdata(pdev); musb_put_id(&pdev->dev, glue->musb->id); - platform_device_del(glue->musb); - platform_device_put(glue->musb); + platform_device_unregister(glue->musb); kfree(glue); return 0; From b59e906c57403d5c55abb43c3602ffbb72b3ae60 Mon Sep 17 00:00:00 2001 From: Wei Yongjun Date: Tue, 23 Oct 2012 13:26:15 +0800 Subject: [PATCH 09/26] usb: musb: da8xx: use platform_device_unregister in da8xx_remove() platform_device_unregister() only calls platform_device_del() and platform_device_put(), thus use platform_device_unregister() to simplify the code. Also the documents in platform.c shows that platform_device_del and platform_device_put must _only_ be externally called in error cases. All other usage is a bug. dpatch engine is used to auto generate this patch. (https://github.com/weiyj/dpatch) Signed-off-by: Wei Yongjun Signed-off-by: Felipe Balbi --- drivers/usb/musb/da8xx.c | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/drivers/usb/musb/da8xx.c b/drivers/usb/musb/da8xx.c index 2366b818443b..e94f556c6aea 100644 --- a/drivers/usb/musb/da8xx.c +++ b/drivers/usb/musb/da8xx.c @@ -573,8 +573,7 @@ static int __devexit da8xx_remove(struct platform_device *pdev) struct da8xx_glue *glue = platform_get_drvdata(pdev); musb_put_id(&pdev->dev, glue->musb->id); - platform_device_del(glue->musb); - platform_device_put(glue->musb); + platform_device_unregister(glue->musb); clk_disable(glue->clk); clk_put(glue->clk); kfree(glue); From 12a71f5b1ce510335c720443b6eec691ed3cf906 Mon Sep 17 00:00:00 2001 From: Wei Yongjun Date: Tue, 23 Oct 2012 13:35:46 +0800 Subject: [PATCH 10/26] usb: musb: davinci: use platform_device_unregister in davinci_remove() platform_device_unregister() only calls platform_device_del() and platform_device_put(), thus use platform_device_unregister() to simplify the code. Also the documents in platform.c shows that platform_device_del and platform_device_put must _only_ be externally called in error cases. All other usage is a bug. dpatch engine is used to auto generate this patch. (https://github.com/weiyj/dpatch) Signed-off-by: Wei Yongjun Signed-off-by: Felipe Balbi --- drivers/usb/musb/davinci.c | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/drivers/usb/musb/davinci.c b/drivers/usb/musb/davinci.c index 62785bf0f95a..959a6d71e1d5 100644 --- a/drivers/usb/musb/davinci.c +++ b/drivers/usb/musb/davinci.c @@ -605,8 +605,7 @@ static int __devexit davinci_remove(struct platform_device *pdev) struct davinci_glue *glue = platform_get_drvdata(pdev); musb_put_id(&pdev->dev, glue->musb->id); - platform_device_del(glue->musb); - platform_device_put(glue->musb); + platform_device_unregister(glue->musb); clk_disable(glue->clk); clk_put(glue->clk); kfree(glue); From b415c8fa9ee46f07a5a8c0dbf34c75519290a912 Mon Sep 17 00:00:00 2001 From: Wei Yongjun Date: Tue, 23 Oct 2012 13:36:06 +0800 Subject: [PATCH 11/26] usb: musb: dsps: use platform_device_unregister in dsps_delete_musb_pdev() platform_device_unregister() only calls platform_device_del() and platform_device_put(), thus use platform_device_unregister() to simplify the code. Also the documents in platform.c shows that platform_device_del and platform_device_put must _only_ be externally called in error cases. All other usage is a bug. dpatch engine is used to auto generate this patch. (https://github.com/weiyj/dpatch) Signed-off-by: Wei Yongjun Signed-off-by: Felipe Balbi --- drivers/usb/musb/musb_dsps.c | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/drivers/usb/musb/musb_dsps.c b/drivers/usb/musb/musb_dsps.c index 444346e1e10d..828d2a216d94 100644 --- a/drivers/usb/musb/musb_dsps.c +++ b/drivers/usb/musb/musb_dsps.c @@ -565,8 +565,7 @@ err0: static void dsps_delete_musb_pdev(struct dsps_glue *glue, u8 id) { musb_put_id(glue->dev, glue->musb[id]->id); - platform_device_del(glue->musb[id]); - platform_device_put(glue->musb[id]); + platform_device_unregister(glue->musb[id]); } static int __devinit dsps_probe(struct platform_device *pdev) From a81a01f9feab302504c3e43fbece99fd7f578df8 Mon Sep 17 00:00:00 2001 From: Wei Yongjun Date: Tue, 23 Oct 2012 13:36:20 +0800 Subject: [PATCH 12/26] usb: musb: tusb6010: use platform_device_unregister in tusb_remove() platform_device_unregister() only calls platform_device_del() and platform_device_put(), thus use platform_device_unregister() to simplify the code. Also the documents in platform.c shows that platform_device_del and platform_device_put must _only_ be externally called in error cases. All other usage is a bug. dpatch engine is used to auto generate this patch. (https://github.com/weiyj/dpatch) Signed-off-by: Wei Yongjun Signed-off-by: Felipe Balbi --- drivers/usb/musb/tusb6010.c | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/drivers/usb/musb/tusb6010.c b/drivers/usb/musb/tusb6010.c index 39ece28019fd..4454561c6f57 100644 --- a/drivers/usb/musb/tusb6010.c +++ b/drivers/usb/musb/tusb6010.c @@ -1233,8 +1233,7 @@ static int __devexit tusb_remove(struct platform_device *pdev) struct tusb6010_glue *glue = platform_get_drvdata(pdev); musb_put_id(&pdev->dev, glue->musb->id); - platform_device_del(glue->musb); - platform_device_put(glue->musb); + platform_device_unregister(glue->musb); kfree(glue); return 0; From 4b0de6f38362960460d3693f122c6abe6bb0704b Mon Sep 17 00:00:00 2001 From: Wei Yongjun Date: Tue, 23 Oct 2012 13:36:43 +0800 Subject: [PATCH 13/26] usb: musb: ux500: use platform_device_unregister in ux500_remove() platform_device_unregister() only calls platform_device_del() and platform_device_put(), thus use platform_device_unregister() to simplify the code. Also the documents in platform.c shows that platform_device_del and platform_device_put must _only_ be externally called in error cases. All other usage is a bug. dpatch engine is used to auto generate this patch. (https://github.com/weiyj/dpatch) Signed-off-by: Wei Yongjun Signed-off-by: Felipe Balbi --- drivers/usb/musb/ux500.c | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/drivers/usb/musb/ux500.c b/drivers/usb/musb/ux500.c index be1430ad60ee..4197f307ae0f 100644 --- a/drivers/usb/musb/ux500.c +++ b/drivers/usb/musb/ux500.c @@ -159,8 +159,7 @@ static int __devexit ux500_remove(struct platform_device *pdev) struct ux500_glue *glue = platform_get_drvdata(pdev); musb_put_id(&pdev->dev, glue->musb->id); - platform_device_del(glue->musb); - platform_device_put(glue->musb); + platform_device_unregister(glue->musb); clk_disable(glue->clk); clk_put(glue->clk); kfree(glue); From b11e94d03726c5dbee0d9a841a025313504e90f4 Mon Sep 17 00:00:00 2001 From: Sebastian Andrzej Siewior Date: Tue, 30 Oct 2012 19:52:23 +0100 Subject: [PATCH 14/26] usb: musb: read MUSB_POWER register only when required. This is part of the workaround for AM35x advisory Advisory 1.1.20. The advisory says that the IPSS bridge can't handle 8 & 16 bit read access. An 8bit read access to MUSB_POWER results in an 32bit read access which also reads INTRTX and therefore may lose interrupts. This patch tries to minimize reads to MUSB_POWER and perform them only when required. Signed-off-by: Sebastian Andrzej Siewior Signed-off-by: Felipe Balbi --- drivers/usb/musb/musb_core.c | 15 ++++++++------- 1 file changed, 8 insertions(+), 7 deletions(-) diff --git a/drivers/usb/musb/musb_core.c b/drivers/usb/musb/musb_core.c index bb56a0e8b23b..d156fe8bebfa 100644 --- a/drivers/usb/musb/musb_core.c +++ b/drivers/usb/musb/musb_core.c @@ -467,12 +467,12 @@ void musb_hnp_stop(struct musb *musb) */ static irqreturn_t musb_stage0_irq(struct musb *musb, u8 int_usb, - u8 devctl, u8 power) + u8 devctl) { struct usb_otg *otg = musb->xceiv->otg; irqreturn_t handled = IRQ_NONE; - dev_dbg(musb->controller, "<== Power=%02x, DevCtl=%02x, int_usb=0x%x\n", power, devctl, + dev_dbg(musb->controller, "<== DevCtl=%02x, int_usb=0x%x\n", devctl, int_usb); /* in host mode, the peripheral may issue remote wakeup. @@ -485,6 +485,7 @@ static irqreturn_t musb_stage0_irq(struct musb *musb, u8 int_usb, if (devctl & MUSB_DEVCTL_HM) { void __iomem *mbase = musb->mregs; + u8 power; switch (musb->xceiv->state) { case OTG_STATE_A_SUSPEND: @@ -492,6 +493,7 @@ static irqreturn_t musb_stage0_irq(struct musb *musb, u8 int_usb, * will stop RESUME signaling */ + power = musb_readb(musb->mregs, MUSB_POWER); if (power & MUSB_POWER_SUSPENDM) { /* spurious */ musb->int_usb &= ~MUSB_INTR_SUSPEND; @@ -655,8 +657,8 @@ static irqreturn_t musb_stage0_irq(struct musb *musb, u8 int_usb, } if (int_usb & MUSB_INTR_SUSPEND) { - dev_dbg(musb->controller, "SUSPEND (%s) devctl %02x power %02x\n", - otg_state_string(musb->xceiv->state), devctl, power); + dev_dbg(musb->controller, "SUSPEND (%s) devctl %02x\n", + otg_state_string(musb->xceiv->state), devctl); handled = IRQ_HANDLED; switch (musb->xceiv->state) { @@ -1560,12 +1562,11 @@ static irqreturn_t generic_interrupt(int irq, void *__hci) irqreturn_t musb_interrupt(struct musb *musb) { irqreturn_t retval = IRQ_NONE; - u8 devctl, power; + u8 devctl; int ep_num; u32 reg; devctl = musb_readb(musb->mregs, MUSB_DEVCTL); - power = musb_readb(musb->mregs, MUSB_POWER); dev_dbg(musb->controller, "** IRQ %s usb%04x tx%04x rx%04x\n", (devctl & MUSB_DEVCTL_HM) ? "host" : "peripheral", @@ -1576,7 +1577,7 @@ irqreturn_t musb_interrupt(struct musb *musb) */ if (musb->int_usb) retval |= musb_stage0_irq(musb, musb->int_usb, - devctl, power); + devctl); /* "stage 1" is handling endpoint irqs */ From 515ba29cd7b571da45365e4db80c1b6905869ef3 Mon Sep 17 00:00:00 2001 From: Sebastian Andrzej Siewior Date: Tue, 30 Oct 2012 19:52:24 +0100 Subject: [PATCH 15/26] usb: musb: avoid FADDR read access This is part of the workaround for AM35x advisory Advisory 1.1.20. The advisory says that the IPSS bridge can't handle 8 & 16 bit read access. An 8bit read access to FADDR results in an 32bit read access which also reads INTRTX and therefore may lose interrupts. This patch removes any reads to FADDR as they are not really required. Signed-off-by: Sebastian Andrzej Siewior Signed-off-by: Felipe Balbi --- drivers/usb/musb/musb_gadget.c | 3 +-- drivers/usb/musb/musb_gadget_ep0.c | 6 ++---- 2 files changed, 3 insertions(+), 6 deletions(-) diff --git a/drivers/usb/musb/musb_gadget.c b/drivers/usb/musb/musb_gadget.c index d0b87e7b4abf..b430f158e668 100644 --- a/drivers/usb/musb/musb_gadget.c +++ b/drivers/usb/musb/musb_gadget.c @@ -2154,10 +2154,9 @@ __acquires(musb->lock) u8 devctl = musb_readb(mbase, MUSB_DEVCTL); u8 power; - dev_dbg(musb->controller, "<== %s addr=%x driver '%s'\n", + dev_dbg(musb->controller, "<== %s driver '%s'\n", (devctl & MUSB_DEVCTL_BDEVICE) ? "B-Device" : "A-Device", - musb_readb(mbase, MUSB_FADDR), musb->gadget_driver ? musb->gadget_driver->driver.name : NULL diff --git a/drivers/usb/musb/musb_gadget_ep0.c b/drivers/usb/musb/musb_gadget_ep0.c index e40d7647caf1..c9c1ac4e075f 100644 --- a/drivers/usb/musb/musb_gadget_ep0.c +++ b/drivers/usb/musb/musb_gadget_ep0.c @@ -673,10 +673,8 @@ irqreturn_t musb_g_ep0_irq(struct musb *musb) csr = musb_readw(regs, MUSB_CSR0); len = musb_readb(regs, MUSB_COUNT0); - dev_dbg(musb->controller, "csr %04x, count %d, myaddr %d, ep0stage %s\n", - csr, len, - musb_readb(mbase, MUSB_FADDR), - decode_ep0stage(musb->ep0_state)); + dev_dbg(musb->controller, "csr %04x, count %d, ep0stage %s\n", + csr, len, decode_ep0stage(musb->ep0_state)); if (csr & MUSB_CSR0_P_DATAEND) { /* From af5ec14d40e0da1de17fcca2b41c76fae5c2cb9d Mon Sep 17 00:00:00 2001 From: Sebastian Andrzej Siewior Date: Tue, 30 Oct 2012 19:52:25 +0100 Subject: [PATCH 16/26] usb: musb: Perform only write access on MUSB_INTRRXE This is part of the workaround for AM35x advisory Advisory 1.1.20. The advisory says that the IPSS bridge can't handle 8 & 16 bit read access. An 16bit read access to MUSB_INTRRXE results in an 32bit read access which also reads INTRUSB and therefore may lose interrupts. This patch uses a shadow register of MUSB_INTRRXE so we only perform write access to it. Signed-off-by: Sebastian Andrzej Siewior Signed-off-by: Felipe Balbi --- drivers/usb/musb/musb_core.c | 10 ++++++---- drivers/usb/musb/musb_core.h | 3 ++- drivers/usb/musb/musb_gadget.c | 10 ++++------ 3 files changed, 12 insertions(+), 11 deletions(-) diff --git a/drivers/usb/musb/musb_core.c b/drivers/usb/musb/musb_core.c index d156fe8bebfa..7ff1986e5e52 100644 --- a/drivers/usb/musb/musb_core.c +++ b/drivers/usb/musb/musb_core.c @@ -725,7 +725,8 @@ static irqreturn_t musb_stage0_irq(struct musb *musb, u8 int_usb, /* REVISIT HNP; just force disconnect */ } musb_writew(musb->mregs, MUSB_INTRTXE, musb->epmask); - musb_writew(musb->mregs, MUSB_INTRRXE, musb->epmask & 0xfffe); + musb->intrrxe = musb->epmask & 0xfffe; + musb_writew(musb->mregs, MUSB_INTRRXE, musb->intrrxe); musb_writeb(musb->mregs, MUSB_INTRUSBE, 0xf7); musb->port1_status &= ~(USB_PORT_STAT_LOW_SPEED |USB_PORT_STAT_HIGH_SPEED @@ -947,7 +948,8 @@ void musb_start(struct musb *musb) /* Set INT enable registers, enable interrupts */ musb_writew(regs, MUSB_INTRTXE, musb->epmask); - musb_writew(regs, MUSB_INTRRXE, musb->epmask & 0xfffe); + musb->intrrxe = musb->epmask & 0xfffe; + musb_writew(regs, MUSB_INTRRXE, musb->intrrxe); musb_writeb(regs, MUSB_INTRUSBE, 0xf7); musb_writeb(regs, MUSB_TESTMODE, 0); @@ -986,6 +988,7 @@ static void musb_generic_disable(struct musb *musb) /* disable interrupts */ musb_writeb(mbase, MUSB_INTRUSBE, 0); musb_writew(mbase, MUSB_INTRTXE, 0); + musb->intrrxe = 0; musb_writew(mbase, MUSB_INTRRXE, 0); /* off */ @@ -2122,7 +2125,6 @@ static void musb_save_context(struct musb *musb) musb->context.busctl = musb_read_ulpi_buscontrol(musb->mregs); musb->context.power = musb_readb(musb_base, MUSB_POWER); musb->context.intrtxe = musb_readw(musb_base, MUSB_INTRTXE); - musb->context.intrrxe = musb_readw(musb_base, MUSB_INTRRXE); musb->context.intrusbe = musb_readb(musb_base, MUSB_INTRUSBE); musb->context.index = musb_readb(musb_base, MUSB_INDEX); musb->context.devctl = musb_readb(musb_base, MUSB_DEVCTL); @@ -2196,7 +2198,7 @@ static void musb_restore_context(struct musb *musb) musb_write_ulpi_buscontrol(musb->mregs, musb->context.busctl); musb_writeb(musb_base, MUSB_POWER, musb->context.power); musb_writew(musb_base, MUSB_INTRTXE, musb->context.intrtxe); - musb_writew(musb_base, MUSB_INTRRXE, musb->context.intrrxe); + musb_writew(musb_base, MUSB_INTRRXE, musb->intrrxe); musb_writeb(musb_base, MUSB_INTRUSBE, musb->context.intrusbe); musb_writeb(musb_base, MUSB_DEVCTL, musb->context.devctl); diff --git a/drivers/usb/musb/musb_core.h b/drivers/usb/musb/musb_core.h index c158aacd6de8..60b92cbdc7f7 100644 --- a/drivers/usb/musb/musb_core.h +++ b/drivers/usb/musb/musb_core.h @@ -288,7 +288,7 @@ struct musb_csr_regs { struct musb_context_registers { u8 power; - u16 intrtxe, intrrxe; + u16 intrtxe; u8 intrusbe; u16 frame; u8 index, testmode; @@ -313,6 +313,7 @@ struct musb { struct work_struct irq_work; u16 hwvers; + u16 intrrxe; /* this hub status bit is reserved by USB 2.0 and not seen by usbcore */ #define MUSB_PORT_STAT_RESUME (1 << 31) diff --git a/drivers/usb/musb/musb_gadget.c b/drivers/usb/musb/musb_gadget.c index b430f158e668..bb684f0f790d 100644 --- a/drivers/usb/musb/musb_gadget.c +++ b/drivers/usb/musb/musb_gadget.c @@ -1108,7 +1108,6 @@ static int musb_gadget_enable(struct usb_ep *ep, musb_writew(regs, MUSB_TXCSR, csr); } else { - u16 int_rxe = musb_readw(mbase, MUSB_INTRRXE); if (hw_ep->is_shared_fifo) musb_ep->is_in = 0; @@ -1120,8 +1119,8 @@ static int musb_gadget_enable(struct usb_ep *ep, goto fail; } - int_rxe |= (1 << epnum); - musb_writew(mbase, MUSB_INTRRXE, int_rxe); + musb->intrrxe |= (1 << epnum); + musb_writew(mbase, MUSB_INTRRXE, musb->intrrxe); /* REVISIT if can_bulk_combine() use by updating "tmp" * likewise high bandwidth periodic rx @@ -1214,9 +1213,8 @@ static int musb_gadget_disable(struct usb_ep *ep) musb_writew(musb->mregs, MUSB_INTRTXE, int_txe); musb_writew(epio, MUSB_TXMAXP, 0); } else { - u16 int_rxe = musb_readw(musb->mregs, MUSB_INTRRXE); - int_rxe &= ~(1 << epnum); - musb_writew(musb->mregs, MUSB_INTRRXE, int_rxe); + musb->intrrxe &= ~(1 << epnum); + musb_writew(musb->mregs, MUSB_INTRRXE, musb->intrrxe); musb_writew(epio, MUSB_RXMAXP, 0); } From b18d26f6ad8f00ea5f7c6a12ea52627ca3c3c6e2 Mon Sep 17 00:00:00 2001 From: Sebastian Andrzej Siewior Date: Tue, 30 Oct 2012 19:52:26 +0100 Subject: [PATCH 17/26] usb: musb: Perform only write access on MUSB_INTRTXE This is part of the workaround for AM35x advisory Advisory 1.1.20. The advisory says that the IPSS bridge can't handle 8 & 16 bit read access. An 16bit read access to MUSB_INTRTXE results in an 32bit read access which also reads INTRRX and therefore may lose interrupts. This patch uses a shadow register of MUSB_INTRTXE so we only perform write access to it. Signed-off-by: Sebastian Andrzej Siewior Signed-off-by: Felipe Balbi --- drivers/usb/musb/musb_core.c | 10 ++++++---- drivers/usb/musb/musb_core.h | 2 +- drivers/usb/musb/musb_gadget.c | 17 +++++++---------- drivers/usb/musb/musb_host.c | 2 +- 4 files changed, 15 insertions(+), 16 deletions(-) diff --git a/drivers/usb/musb/musb_core.c b/drivers/usb/musb/musb_core.c index 7ff1986e5e52..25a0d8e1be51 100644 --- a/drivers/usb/musb/musb_core.c +++ b/drivers/usb/musb/musb_core.c @@ -724,7 +724,8 @@ static irqreturn_t musb_stage0_irq(struct musb *musb, u8 int_usb, if (is_peripheral_active(musb)) { /* REVISIT HNP; just force disconnect */ } - musb_writew(musb->mregs, MUSB_INTRTXE, musb->epmask); + musb->intrtxe = musb->epmask; + musb_writew(musb->mregs, MUSB_INTRTXE, musb->intrtxe); musb->intrrxe = musb->epmask & 0xfffe; musb_writew(musb->mregs, MUSB_INTRRXE, musb->intrrxe); musb_writeb(musb->mregs, MUSB_INTRUSBE, 0xf7); @@ -947,7 +948,8 @@ void musb_start(struct musb *musb) dev_dbg(musb->controller, "<== devctl %02x\n", devctl); /* Set INT enable registers, enable interrupts */ - musb_writew(regs, MUSB_INTRTXE, musb->epmask); + musb->intrtxe = musb->epmask; + musb_writew(regs, MUSB_INTRTXE, musb->intrtxe); musb->intrrxe = musb->epmask & 0xfffe; musb_writew(regs, MUSB_INTRRXE, musb->intrrxe); musb_writeb(regs, MUSB_INTRUSBE, 0xf7); @@ -987,6 +989,7 @@ static void musb_generic_disable(struct musb *musb) /* disable interrupts */ musb_writeb(mbase, MUSB_INTRUSBE, 0); + musb->intrtxe = 0; musb_writew(mbase, MUSB_INTRTXE, 0); musb->intrrxe = 0; musb_writew(mbase, MUSB_INTRRXE, 0); @@ -2124,7 +2127,6 @@ static void musb_save_context(struct musb *musb) musb->context.testmode = musb_readb(musb_base, MUSB_TESTMODE); musb->context.busctl = musb_read_ulpi_buscontrol(musb->mregs); musb->context.power = musb_readb(musb_base, MUSB_POWER); - musb->context.intrtxe = musb_readw(musb_base, MUSB_INTRTXE); musb->context.intrusbe = musb_readb(musb_base, MUSB_INTRUSBE); musb->context.index = musb_readb(musb_base, MUSB_INDEX); musb->context.devctl = musb_readb(musb_base, MUSB_DEVCTL); @@ -2197,7 +2199,7 @@ static void musb_restore_context(struct musb *musb) musb_writeb(musb_base, MUSB_TESTMODE, musb->context.testmode); musb_write_ulpi_buscontrol(musb->mregs, musb->context.busctl); musb_writeb(musb_base, MUSB_POWER, musb->context.power); - musb_writew(musb_base, MUSB_INTRTXE, musb->context.intrtxe); + musb_writew(musb_base, MUSB_INTRTXE, musb->intrtxe); musb_writew(musb_base, MUSB_INTRRXE, musb->intrrxe); musb_writeb(musb_base, MUSB_INTRUSBE, musb->context.intrusbe); musb_writeb(musb_base, MUSB_DEVCTL, musb->context.devctl); diff --git a/drivers/usb/musb/musb_core.h b/drivers/usb/musb/musb_core.h index 60b92cbdc7f7..0cef3ceb52c3 100644 --- a/drivers/usb/musb/musb_core.h +++ b/drivers/usb/musb/musb_core.h @@ -288,7 +288,6 @@ struct musb_csr_regs { struct musb_context_registers { u8 power; - u16 intrtxe; u8 intrusbe; u16 frame; u8 index, testmode; @@ -314,6 +313,7 @@ struct musb { u16 hwvers; u16 intrrxe; + u16 intrtxe; /* this hub status bit is reserved by USB 2.0 and not seen by usbcore */ #define MUSB_PORT_STAT_RESUME (1 << 31) diff --git a/drivers/usb/musb/musb_gadget.c b/drivers/usb/musb/musb_gadget.c index bb684f0f790d..28b9790e84ea 100644 --- a/drivers/usb/musb/musb_gadget.c +++ b/drivers/usb/musb/musb_gadget.c @@ -1068,7 +1068,6 @@ static int musb_gadget_enable(struct usb_ep *ep, */ musb_ep_select(mbase, epnum); if (usb_endpoint_dir_in(desc)) { - u16 int_txe = musb_readw(mbase, MUSB_INTRTXE); if (hw_ep->is_shared_fifo) musb_ep->is_in = 1; @@ -1080,8 +1079,8 @@ static int musb_gadget_enable(struct usb_ep *ep, goto fail; } - int_txe |= (1 << epnum); - musb_writew(mbase, MUSB_INTRTXE, int_txe); + musb->intrtxe |= (1 << epnum); + musb_writew(mbase, MUSB_INTRTXE, musb->intrtxe); /* REVISIT if can_bulk_split(), use by updating "tmp"; * likewise high bandwidth periodic tx @@ -1208,9 +1207,8 @@ static int musb_gadget_disable(struct usb_ep *ep) /* zero the endpoint sizes */ if (musb_ep->is_in) { - u16 int_txe = musb_readw(musb->mregs, MUSB_INTRTXE); - int_txe &= ~(1 << epnum); - musb_writew(musb->mregs, MUSB_INTRTXE, int_txe); + musb->intrtxe &= ~(1 << epnum); + musb_writew(musb->mregs, MUSB_INTRTXE, musb->intrtxe); musb_writew(epio, MUSB_TXMAXP, 0); } else { musb->intrrxe &= ~(1 << epnum); @@ -1530,7 +1528,7 @@ static void musb_gadget_fifo_flush(struct usb_ep *ep) void __iomem *epio = musb->endpoints[epnum].regs; void __iomem *mbase; unsigned long flags; - u16 csr, int_txe; + u16 csr; mbase = musb->mregs; @@ -1538,8 +1536,7 @@ static void musb_gadget_fifo_flush(struct usb_ep *ep) musb_ep_select(mbase, (u8) epnum); /* disable interrupts */ - int_txe = musb_readw(mbase, MUSB_INTRTXE); - musb_writew(mbase, MUSB_INTRTXE, int_txe & ~(1 << epnum)); + musb_writew(mbase, MUSB_INTRTXE, musb->intrtxe & ~(1 << epnum)); if (musb_ep->is_in) { csr = musb_readw(epio, MUSB_TXCSR); @@ -1563,7 +1560,7 @@ static void musb_gadget_fifo_flush(struct usb_ep *ep) } /* re-enable interrupt */ - musb_writew(mbase, MUSB_INTRTXE, int_txe); + musb_writew(mbase, MUSB_INTRTXE, musb->intrtxe); spin_unlock_irqrestore(&musb->lock, flags); } diff --git a/drivers/usb/musb/musb_host.c b/drivers/usb/musb/musb_host.c index 3df6a76b851d..e9f0fd9ddd2d 100644 --- a/drivers/usb/musb/musb_host.c +++ b/drivers/usb/musb/musb_host.c @@ -740,7 +740,7 @@ static void musb_ep_program(struct musb *musb, u8 epnum, csr = musb_readw(epio, MUSB_TXCSR); /* disable interrupt in case we flush */ - int_txe = musb_readw(mbase, MUSB_INTRTXE); + int_txe = musb->intrtxe; musb_writew(mbase, MUSB_INTRTXE, int_txe & ~(1 << epnum)); /* general endpoint setup */ From 2f7711642559851c187d09795a3eb51c2bde36ec Mon Sep 17 00:00:00 2001 From: Sebastian Andrzej Siewior Date: Wed, 31 Oct 2012 16:12:43 +0100 Subject: [PATCH 18/26] usb: musb: remove hand-crafted id handling This replaced the handcrafted id handling by the PLATFORM_DEVID_AUTO value which should do the same thing. This patch probably also fixes ux500 because I did not find the "musbid" variable to remove. And we close a tiny-unlikely race window becuase the old code gave the id back before device was destroyed in the remove case. [ balbi@ti.com : fixed up two failed hunks when applying patch ] Cc: B, Ravi Cc: Santhapuri, Damodar Cc: Mian Yousaf Kaukab Cc: Bob Liu Signed-off-by: Sebastian Andrzej Siewior Signed-off-by: Felipe Balbi --- drivers/usb/musb/am35x.c | 18 ++---------------- drivers/usb/musb/blackfin.c | 20 +++----------------- drivers/usb/musb/da8xx.c | 18 ++---------------- drivers/usb/musb/davinci.c | 18 ++---------------- drivers/usb/musb/musb_core.c | 30 ------------------------------ drivers/usb/musb/musb_core.h | 2 -- drivers/usb/musb/musb_dsps.c | 26 +++++--------------------- drivers/usb/musb/omap2430.c | 26 ++++++-------------------- drivers/usb/musb/tusb6010.c | 20 +++----------------- drivers/usb/musb/ux500.c | 18 ++---------------- 10 files changed, 25 insertions(+), 171 deletions(-) diff --git a/drivers/usb/musb/am35x.c b/drivers/usb/musb/am35x.c index fdfd779c35b3..3ff30b9a5894 100644 --- a/drivers/usb/musb/am35x.c +++ b/drivers/usb/musb/am35x.c @@ -459,7 +459,6 @@ static int __devinit am35x_probe(struct platform_device *pdev) struct clk *clk; int ret = -ENOMEM; - int musbid; glue = kzalloc(sizeof(*glue), GFP_KERNEL); if (!glue) { @@ -467,18 +466,10 @@ static int __devinit am35x_probe(struct platform_device *pdev) goto err0; } - /* get the musb id */ - musbid = musb_get_id(&pdev->dev, GFP_KERNEL); - if (musbid < 0) { - dev_err(&pdev->dev, "failed to allocate musb id\n"); - ret = -ENOMEM; - goto err1; - } - - musb = platform_device_alloc("musb-hdrc", musbid); + musb = platform_device_alloc("musb-hdrc", PLATFORM_DEVID_AUTO); if (!musb) { dev_err(&pdev->dev, "failed to allocate musb device\n"); - goto err2; + goto err1; } phy_clk = clk_get(&pdev->dev, "fck"); @@ -507,7 +498,6 @@ static int __devinit am35x_probe(struct platform_device *pdev) goto err6; } - musb->id = musbid; musb->dev.parent = &pdev->dev; musb->dev.dma_mask = &am35x_dmamask; musb->dev.coherent_dma_mask = am35x_dmamask; @@ -557,9 +547,6 @@ err4: err3: platform_device_put(musb); -err2: - musb_put_id(&pdev->dev, musbid); - err1: kfree(glue); @@ -571,7 +558,6 @@ static int __devexit am35x_remove(struct platform_device *pdev) { struct am35x_glue *glue = platform_get_drvdata(pdev); - musb_put_id(&pdev->dev, glue->musb->id); platform_device_unregister(glue->musb); clk_disable(glue->clk); clk_disable(glue->phy_clk); diff --git a/drivers/usb/musb/blackfin.c b/drivers/usb/musb/blackfin.c index 307e726a2bd7..7e4d60a41728 100644 --- a/drivers/usb/musb/blackfin.c +++ b/drivers/usb/musb/blackfin.c @@ -455,7 +455,6 @@ static int __devinit bfin_probe(struct platform_device *pdev) struct bfin_glue *glue; int ret = -ENOMEM; - int musbid; glue = kzalloc(sizeof(*glue), GFP_KERNEL); if (!glue) { @@ -463,21 +462,12 @@ static int __devinit bfin_probe(struct platform_device *pdev) goto err0; } - /* get the musb id */ - musbid = musb_get_id(&pdev->dev, GFP_KERNEL); - if (musbid < 0) { - dev_err(&pdev->dev, "failed to allocate musb id\n"); - ret = -ENOMEM; + musb = platform_device_alloc("musb-hdrc", PLATFORM_DEVID_AUTO); + if (!musb) { + dev_err(&pdev->dev, "failed to allocate musb device\n"); goto err1; } - musb = platform_device_alloc("musb-hdrc", musbid); - if (!musb) { - dev_err(&pdev->dev, "failed to allocate musb device\n"); - goto err2; - } - - musb->id = musbid; musb->dev.parent = &pdev->dev; musb->dev.dma_mask = &bfin_dmamask; musb->dev.coherent_dma_mask = bfin_dmamask; @@ -513,9 +503,6 @@ static int __devinit bfin_probe(struct platform_device *pdev) err3: platform_device_put(musb); -err2: - musb_put_id(&pdev->dev, musbid); - err1: kfree(glue); @@ -527,7 +514,6 @@ static int __devexit bfin_remove(struct platform_device *pdev) { struct bfin_glue *glue = platform_get_drvdata(pdev); - musb_put_id(&pdev->dev, glue->musb->id); platform_device_unregister(glue->musb); kfree(glue); diff --git a/drivers/usb/musb/da8xx.c b/drivers/usb/musb/da8xx.c index e94f556c6aea..67b8ae704e9a 100644 --- a/drivers/usb/musb/da8xx.c +++ b/drivers/usb/musb/da8xx.c @@ -480,7 +480,6 @@ static int __devinit da8xx_probe(struct platform_device *pdev) struct clk *clk; int ret = -ENOMEM; - int musbid; glue = kzalloc(sizeof(*glue), GFP_KERNEL); if (!glue) { @@ -488,18 +487,10 @@ static int __devinit da8xx_probe(struct platform_device *pdev) goto err0; } - /* get the musb id */ - musbid = musb_get_id(&pdev->dev, GFP_KERNEL); - if (musbid < 0) { - dev_err(&pdev->dev, "failed to allocate musb id\n"); - ret = -ENOMEM; - goto err1; - } - - musb = platform_device_alloc("musb-hdrc", musbid); + musb = platform_device_alloc("musb-hdrc", PLATFORM_DEVID_AUTO); if (!musb) { dev_err(&pdev->dev, "failed to allocate musb device\n"); - goto err2; + goto err1; } clk = clk_get(&pdev->dev, "usb20"); @@ -515,7 +506,6 @@ static int __devinit da8xx_probe(struct platform_device *pdev) goto err4; } - musb->id = musbid; musb->dev.parent = &pdev->dev; musb->dev.dma_mask = &da8xx_dmamask; musb->dev.coherent_dma_mask = da8xx_dmamask; @@ -558,9 +548,6 @@ err4: err3: platform_device_put(musb); -err2: - musb_put_id(&pdev->dev, musbid); - err1: kfree(glue); @@ -572,7 +559,6 @@ static int __devexit da8xx_remove(struct platform_device *pdev) { struct da8xx_glue *glue = platform_get_drvdata(pdev); - musb_put_id(&pdev->dev, glue->musb->id); platform_device_unregister(glue->musb); clk_disable(glue->clk); clk_put(glue->clk); diff --git a/drivers/usb/musb/davinci.c b/drivers/usb/musb/davinci.c index 959a6d71e1d5..b3c0a943950c 100644 --- a/drivers/usb/musb/davinci.c +++ b/drivers/usb/musb/davinci.c @@ -512,7 +512,6 @@ static int __devinit davinci_probe(struct platform_device *pdev) struct clk *clk; int ret = -ENOMEM; - int musbid; glue = kzalloc(sizeof(*glue), GFP_KERNEL); if (!glue) { @@ -520,18 +519,10 @@ static int __devinit davinci_probe(struct platform_device *pdev) goto err0; } - /* get the musb id */ - musbid = musb_get_id(&pdev->dev, GFP_KERNEL); - if (musbid < 0) { - dev_err(&pdev->dev, "failed to allocate musb id\n"); - ret = -ENOMEM; - goto err1; - } - - musb = platform_device_alloc("musb-hdrc", musbid); + musb = platform_device_alloc("musb-hdrc", PLATFORM_DEVID_AUTO); if (!musb) { dev_err(&pdev->dev, "failed to allocate musb device\n"); - goto err2; + goto err1; } clk = clk_get(&pdev->dev, "usb"); @@ -547,7 +538,6 @@ static int __devinit davinci_probe(struct platform_device *pdev) goto err4; } - musb->id = musbid; musb->dev.parent = &pdev->dev; musb->dev.dma_mask = &davinci_dmamask; musb->dev.coherent_dma_mask = davinci_dmamask; @@ -590,9 +580,6 @@ err4: err3: platform_device_put(musb); -err2: - musb_put_id(&pdev->dev, musbid); - err1: kfree(glue); @@ -604,7 +591,6 @@ static int __devexit davinci_remove(struct platform_device *pdev) { struct davinci_glue *glue = platform_get_drvdata(pdev); - musb_put_id(&pdev->dev, glue->musb->id); platform_device_unregister(glue->musb); clk_disable(glue->clk); clk_put(glue->clk); diff --git a/drivers/usb/musb/musb_core.c b/drivers/usb/musb/musb_core.c index 25a0d8e1be51..78037bfad96e 100644 --- a/drivers/usb/musb/musb_core.c +++ b/drivers/usb/musb/musb_core.c @@ -116,7 +116,6 @@ #define MUSB_DRIVER_NAME "musb-hdrc" const char musb_driver_name[] = MUSB_DRIVER_NAME; -static DEFINE_IDA(musb_ida); MODULE_DESCRIPTION(DRIVER_INFO); MODULE_AUTHOR(DRIVER_AUTHOR); @@ -133,35 +132,6 @@ static inline struct musb *dev_to_musb(struct device *dev) /*-------------------------------------------------------------------------*/ -int musb_get_id(struct device *dev, gfp_t gfp_mask) -{ - int ret; - int id; - - ret = ida_pre_get(&musb_ida, gfp_mask); - if (!ret) { - dev_err(dev, "failed to reserve resource for id\n"); - return -ENOMEM; - } - - ret = ida_get_new(&musb_ida, &id); - if (ret < 0) { - dev_err(dev, "failed to allocate a new id\n"); - return ret; - } - - return id; -} -EXPORT_SYMBOL_GPL(musb_get_id); - -void musb_put_id(struct device *dev, int id) -{ - - dev_dbg(dev, "removing id %d\n", id); - ida_remove(&musb_ida, id); -} -EXPORT_SYMBOL_GPL(musb_put_id); - #ifndef CONFIG_BLACKFIN static int musb_ulpi_read(struct usb_phy *phy, u32 offset) { diff --git a/drivers/usb/musb/musb_core.h b/drivers/usb/musb/musb_core.h index 0cef3ceb52c3..7fb4819a6f11 100644 --- a/drivers/usb/musb/musb_core.h +++ b/drivers/usb/musb/musb_core.h @@ -522,8 +522,6 @@ extern const char musb_driver_name[]; extern void musb_start(struct musb *musb); extern void musb_stop(struct musb *musb); -extern int musb_get_id(struct device *dev, gfp_t gfp_mask); -extern void musb_put_id(struct device *dev, int id); extern void musb_write_fifo(struct musb_hw_ep *ep, u16 len, const u8 *src); extern void musb_read_fifo(struct musb_hw_ep *ep, u16 len, u8 *dst); diff --git a/drivers/usb/musb/musb_dsps.c b/drivers/usb/musb/musb_dsps.c index 828d2a216d94..2d2cd37bc7ba 100644 --- a/drivers/usb/musb/musb_dsps.c +++ b/drivers/usb/musb/musb_dsps.c @@ -459,7 +459,7 @@ static int __devinit dsps_create_musb_pdev(struct dsps_glue *glue, u8 id) struct resource *res; struct resource resources[2]; char res_name[10]; - int ret, musbid; + int ret; /* get memory resource */ sprintf(res_name, "musb%d", id); @@ -484,22 +484,14 @@ static int __devinit dsps_create_musb_pdev(struct dsps_glue *glue, u8 id) resources[1] = *res; resources[1].name = "mc"; - /* get the musb id */ - musbid = musb_get_id(dev, GFP_KERNEL); - if (musbid < 0) { - dev_err(dev, "failed to allocate musb id\n"); - ret = -ENOMEM; - goto err0; - } /* allocate the child platform device */ - musb = platform_device_alloc("musb-hdrc", musbid); + musb = platform_device_alloc("musb-hdrc", PLATFORM_DEVID_AUTO); if (!musb) { dev_err(dev, "failed to allocate musb device\n"); ret = -ENOMEM; - goto err1; + goto err0; } - musb->id = musbid; musb->dev.parent = dev; musb->dev.dma_mask = &musb_dmamask; musb->dev.coherent_dma_mask = musb_dmamask; @@ -556,18 +548,10 @@ static int __devinit dsps_create_musb_pdev(struct dsps_glue *glue, u8 id) err2: platform_device_put(musb); -err1: - musb_put_id(dev, musbid); err0: return ret; } -static void dsps_delete_musb_pdev(struct dsps_glue *glue, u8 id) -{ - musb_put_id(glue->dev, glue->musb[id]->id); - platform_device_unregister(glue->musb[id]); -} - static int __devinit dsps_probe(struct platform_device *pdev) { struct device_node *np = pdev->dev.of_node; @@ -627,7 +611,7 @@ static int __devinit dsps_probe(struct platform_device *pdev) dev_err(&pdev->dev, "failed to create child pdev\n"); /* release resources of previously created instances */ for (i--; i >= 0 ; i--) - dsps_delete_musb_pdev(glue, i); + platform_device_unregister(glue->musb[i]); goto err3; } } @@ -652,7 +636,7 @@ static int __devexit dsps_remove(struct platform_device *pdev) /* delete the child platform device */ for (i = 0; i < wrp->instances ; i++) - dsps_delete_musb_pdev(glue, i); + platform_device_unregister(glue->musb[i]); /* disable usbss clocks */ pm_runtime_put(&pdev->dev); diff --git a/drivers/usb/musb/omap2430.c b/drivers/usb/musb/omap2430.c index a538fe17a966..dddd8f71a176 100644 --- a/drivers/usb/musb/omap2430.c +++ b/drivers/usb/musb/omap2430.c @@ -478,7 +478,6 @@ static int __devinit omap2430_probe(struct platform_device *pdev) struct musb_hdrc_config *config; struct resource *res; int ret = -ENOMEM; - int musbid; glue = devm_kzalloc(&pdev->dev, sizeof(*glue), GFP_KERNEL); if (!glue) { @@ -486,21 +485,12 @@ static int __devinit omap2430_probe(struct platform_device *pdev) goto err0; } - /* get the musb id */ - musbid = musb_get_id(&pdev->dev, GFP_KERNEL); - if (musbid < 0) { - dev_err(&pdev->dev, "failed to allocate musb id\n"); - ret = -ENOMEM; + musb = platform_device_alloc("musb-hdrc", PLATFORM_DEVID_AUTO); + if (!musb) { + dev_err(&pdev->dev, "failed to allocate musb device\n"); goto err0; } - musb = platform_device_alloc("musb-hdrc", musbid); - if (!musb) { - dev_err(&pdev->dev, "failed to allocate musb device\n"); - goto err1; - } - - musb->id = musbid; musb->dev.parent = &pdev->dev; musb->dev.dma_mask = &omap2430_dmamask; musb->dev.coherent_dma_mask = omap2430_dmamask; @@ -521,7 +511,7 @@ static int __devinit omap2430_probe(struct platform_device *pdev) dev_err(&pdev->dev, "failed to allocate musb platfrom data\n"); ret = -ENOMEM; - goto err1; + goto err2; } data = devm_kzalloc(&pdev->dev, sizeof(*data), GFP_KERNEL); @@ -529,14 +519,14 @@ static int __devinit omap2430_probe(struct platform_device *pdev) dev_err(&pdev->dev, "failed to allocate musb board data\n"); ret = -ENOMEM; - goto err1; + goto err2; } config = devm_kzalloc(&pdev->dev, sizeof(*config), GFP_KERNEL); if (!data) { dev_err(&pdev->dev, "failed to allocate musb hdrc config\n"); - goto err1; + goto err2; } of_property_read_u32(np, "mode", (u32 *)&pdata->mode); @@ -589,9 +579,6 @@ static int __devinit omap2430_probe(struct platform_device *pdev) err2: platform_device_put(musb); -err1: - musb_put_id(&pdev->dev, musbid); - err0: return ret; } @@ -601,7 +588,6 @@ static int __devexit omap2430_remove(struct platform_device *pdev) struct omap2430_glue *glue = platform_get_drvdata(pdev); cancel_work_sync(&glue->omap_musb_mailbox_work); - musb_put_id(&pdev->dev, glue->musb->id); platform_device_unregister(glue->musb); return 0; diff --git a/drivers/usb/musb/tusb6010.c b/drivers/usb/musb/tusb6010.c index 4454561c6f57..812719b683d1 100644 --- a/drivers/usb/musb/tusb6010.c +++ b/drivers/usb/musb/tusb6010.c @@ -1160,7 +1160,6 @@ static int __devinit tusb_probe(struct platform_device *pdev) struct tusb6010_glue *glue; int ret = -ENOMEM; - int musbid; glue = kzalloc(sizeof(*glue), GFP_KERNEL); if (!glue) { @@ -1168,21 +1167,12 @@ static int __devinit tusb_probe(struct platform_device *pdev) goto err0; } - /* get the musb id */ - musbid = musb_get_id(&pdev->dev, GFP_KERNEL); - if (musbid < 0) { - dev_err(&pdev->dev, "failed to allocate musb id\n"); - ret = -ENOMEM; + musb = platform_device_alloc("musb-hdrc", PLATFORM_DEVID_AUTO); + if (!musb) { + dev_err(&pdev->dev, "failed to allocate musb device\n"); goto err1; } - musb = platform_device_alloc("musb-hdrc", musbid); - if (!musb) { - dev_err(&pdev->dev, "failed to allocate musb device\n"); - goto err2; - } - - musb->id = musbid; musb->dev.parent = &pdev->dev; musb->dev.dma_mask = &tusb_dmamask; musb->dev.coherent_dma_mask = tusb_dmamask; @@ -1218,9 +1208,6 @@ static int __devinit tusb_probe(struct platform_device *pdev) err3: platform_device_put(musb); -err2: - musb_put_id(&pdev->dev, musbid); - err1: kfree(glue); @@ -1232,7 +1219,6 @@ static int __devexit tusb_remove(struct platform_device *pdev) { struct tusb6010_glue *glue = platform_get_drvdata(pdev); - musb_put_id(&pdev->dev, glue->musb->id); platform_device_unregister(glue->musb); kfree(glue); diff --git a/drivers/usb/musb/ux500.c b/drivers/usb/musb/ux500.c index 4197f307ae0f..5e9053eb4298 100644 --- a/drivers/usb/musb/ux500.c +++ b/drivers/usb/musb/ux500.c @@ -65,7 +65,6 @@ static int __devinit ux500_probe(struct platform_device *pdev) struct platform_device *musb; struct ux500_glue *glue; struct clk *clk; - int ret = -ENOMEM; glue = kzalloc(sizeof(*glue), GFP_KERNEL); @@ -74,18 +73,10 @@ static int __devinit ux500_probe(struct platform_device *pdev) goto err0; } - /* get the musb id */ - musbid = musb_get_id(&pdev->dev, GFP_KERNEL); - if (musbid < 0) { - dev_err(&pdev->dev, "failed to allocate musb id\n"); - ret = -ENOMEM; - goto err1; - } - - musb = platform_device_alloc("musb-hdrc", musbid); + musb = platform_device_alloc("musb-hdrc", PLATFORM_DEVID_AUTO); if (!musb) { dev_err(&pdev->dev, "failed to allocate musb device\n"); - goto err2; + goto err1; } clk = clk_get(&pdev->dev, "usb"); @@ -101,7 +92,6 @@ static int __devinit ux500_probe(struct platform_device *pdev) goto err4; } - musb->id = musbid; musb->dev.parent = &pdev->dev; musb->dev.dma_mask = pdev->dev.dma_mask; musb->dev.coherent_dma_mask = pdev->dev.coherent_dma_mask; @@ -144,9 +134,6 @@ err4: err3: platform_device_put(musb); -err2: - musb_put_id(&pdev->dev, musbid); - err1: kfree(glue); @@ -158,7 +145,6 @@ static int __devexit ux500_remove(struct platform_device *pdev) { struct ux500_glue *glue = platform_get_drvdata(pdev); - musb_put_id(&pdev->dev, glue->musb->id); platform_device_unregister(glue->musb); clk_disable(glue->clk); clk_put(glue->clk); From 12fc9266dec3706ece7c4aafefc60d429149c3bd Mon Sep 17 00:00:00 2001 From: Afzal Mohammed Date: Fri, 2 Nov 2012 22:02:28 +0530 Subject: [PATCH 19/26] usb: musb: dsps: remove platform callback dsps wrapper is dt only, it cannot execute platform callbacks. Presence of this would cause NULL dereference, hence remove it. Signed-off-by: Afzal Mohammed Signed-off-by: Felipe Balbi --- drivers/usb/musb/musb_dsps.c | 26 -------------------------- 1 file changed, 26 deletions(-) diff --git a/drivers/usb/musb/musb_dsps.c b/drivers/usb/musb/musb_dsps.c index 2d2cd37bc7ba..465bbf7e384d 100644 --- a/drivers/usb/musb/musb_dsps.c +++ b/drivers/usb/musb/musb_dsps.c @@ -365,11 +365,9 @@ static irqreturn_t dsps_interrupt(int irq, void *hci) static int dsps_musb_init(struct musb *musb) { struct device *dev = musb->controller; - struct musb_hdrc_platform_data *plat = dev->platform_data; struct platform_device *pdev = to_platform_device(dev); struct dsps_glue *glue = dev_get_drvdata(dev->parent); const struct dsps_musb_wrapper *wrp = glue->wrp; - struct omap_musb_board_data *data = plat->board_data; void __iomem *reg_base = musb->ctrl_base; u32 rev, val; int status; @@ -394,10 +392,6 @@ static int dsps_musb_init(struct musb *musb) /* Reset the musb */ dsps_writel(reg_base, wrp->control, (1 << wrp->reset)); - /* Start the on-chip PHY and its PLL. */ - if (data->set_phy_power) - data->set_phy_power(1); - musb->isr = dsps_interrupt; /* reset the otgdisable bit, needed for host mode to work */ @@ -418,17 +412,11 @@ err0: static int dsps_musb_exit(struct musb *musb) { struct device *dev = musb->controller; - struct musb_hdrc_platform_data *plat = dev->platform_data; - struct omap_musb_board_data *data = plat->board_data; struct platform_device *pdev = to_platform_device(dev); struct dsps_glue *glue = dev_get_drvdata(dev->parent); del_timer_sync(&glue->timer[pdev->id]); - /* Shutdown the on-chip PHY and its PLL. */ - if (data->set_phy_power) - data->set_phy_power(0); - /* NOP driver needs change if supporting dual instance */ usb_put_phy(musb->xceiv); usb_nop_xceiv_unregister(); @@ -649,25 +637,11 @@ static int __devexit dsps_remove(struct platform_device *pdev) #ifdef CONFIG_PM_SLEEP static int dsps_suspend(struct device *dev) { - struct musb_hdrc_platform_data *plat = dev->platform_data; - struct omap_musb_board_data *data = plat->board_data; - - /* Shutdown the on-chip PHY and its PLL. */ - if (data->set_phy_power) - data->set_phy_power(0); - return 0; } static int dsps_resume(struct device *dev) { - struct musb_hdrc_platform_data *plat = dev->platform_data; - struct omap_musb_board_data *data = plat->board_data; - - /* Start the on-chip PHY and its PLL. */ - if (data->set_phy_power) - data->set_phy_power(1); - return 0; } #endif From 3b46dd76a9b3ce25a5177f61eed844f85ddb3ca6 Mon Sep 17 00:00:00 2001 From: Afzal Mohammed Date: Fri, 2 Nov 2012 22:02:35 +0530 Subject: [PATCH 20/26] usb: musb: dsps: reduce musb instance to one Currently multiple phy's of the same type are not supported, hence reduce musb instances to one. This helps in supporting at least one instance of musb, rather than having none. Even without this, it was observed that both instances were working (by luck), but this holds good iff wrapper is part of Image. And it is not correct for both controller's to be associated with same phy, here it was working because phy is a nop one. And having wrapper as a module and rmmod'ing would crash. This can be reverted once multi phy support for same type is available and driver is enhanced to make use of it. Signed-off-by: Afzal Mohammed Signed-off-by: Felipe Balbi --- drivers/usb/musb/musb_dsps.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/usb/musb/musb_dsps.c b/drivers/usb/musb/musb_dsps.c index 465bbf7e384d..72d74601798d 100644 --- a/drivers/usb/musb/musb_dsps.c +++ b/drivers/usb/musb/musb_dsps.c @@ -676,7 +676,7 @@ static const struct dsps_musb_wrapper ti81xx_driver_data __devinitconst = { .rxep_bitmap = (0xfffe << 16), .musb_core_offset = 0x400, .poll_seconds = 2, - .instances = 2, + .instances = 1, }; static const struct platform_device_id musb_dsps_id_table[] __devinitconst = { From 3e594b18f1871a758812aa5e705873012cabf0e8 Mon Sep 17 00:00:00 2001 From: Afzal Mohammed Date: Fri, 2 Nov 2012 22:02:41 +0530 Subject: [PATCH 21/26] usb: musb: dsps: get resources by index dsps wrapper is now dt only. This requires that resources be obtained using index and not name, modify accordingly. Signed-off-by: Afzal Mohammed Signed-off-by: Felipe Balbi --- drivers/usb/musb/musb_dsps.c | 14 ++++++-------- 1 file changed, 6 insertions(+), 8 deletions(-) diff --git a/drivers/usb/musb/musb_dsps.c b/drivers/usb/musb/musb_dsps.c index 72d74601798d..b159fc92f846 100644 --- a/drivers/usb/musb/musb_dsps.c +++ b/drivers/usb/musb/musb_dsps.c @@ -449,22 +449,20 @@ static int __devinit dsps_create_musb_pdev(struct dsps_glue *glue, u8 id) char res_name[10]; int ret; - /* get memory resource */ - sprintf(res_name, "musb%d", id); - res = platform_get_resource_byname(pdev, IORESOURCE_MEM, res_name); + /* first resource is for usbss, so start index from 1 */ + res = platform_get_resource(pdev, IORESOURCE_MEM, id + 1); if (!res) { - dev_err(dev, "%s get mem resource failed\n", res_name); + dev_err(dev, "failed to get memory for instance %d\n", id); ret = -ENODEV; goto err0; } res->parent = NULL; resources[0] = *res; - /* get irq resource */ - sprintf(res_name, "musb%d-irq", id); - res = platform_get_resource_byname(pdev, IORESOURCE_IRQ, res_name); + /* first resource is for usbss, so start index from 1 */ + res = platform_get_resource(pdev, IORESOURCE_IRQ, id + 1); if (!res) { - dev_err(dev, "%s get irq resource failed\n", res_name); + dev_err(dev, "failed to get irq for instance %d\n", id); ret = -ENODEV; goto err0; } From c68bb4c679e68b2814bc5de812665fbd37f8a9b1 Mon Sep 17 00:00:00 2001 From: "Santhapuri, Damodar" Date: Fri, 2 Nov 2012 22:02:53 +0530 Subject: [PATCH 22/26] usb: musb: dsps: control module handling (quirk) am335x uses nop transceiver driver and need to enable builtin phy by writing into usb_ctrl register available in system control module register space. This is being added at musb glue driver layer until a separate system control module driver is available. Proper solution is to make use of control module driver, but it is not expected to be ready soon. Other options available are providing control module register space as memory resource via DT or using omap hwmod. DT approach has been rejected by Rob Herring, while resources are being moved from hwmod to DT. And both of the above approaches require that control module registers be configured in wrapper itself requring a quirk in driver as well as DT or hwmod. Here another option is used, providing driver with control module register physical address. Even though this a hack, there is no other option left till control module driver is ready. As of now only am335x is using dsps wrapper, and so driver is made aware of am335x control module physical address. Please note that this is a temporary arrangment till omap control module driver is available. [afzal@ti.com: limit quirk to dsps wrapper] Signed-off-by: Santhapuri, Damodar Signed-off-by: Ajay Kumar Gupta Signed-off-by: Ravi Babu Signed-off-by: Afzal Mohammed Signed-off-by: Felipe Balbi --- drivers/usb/musb/musb_dsps.c | 69 ++++++++++++++++++++++++++++++++++++ 1 file changed, 69 insertions(+) diff --git a/drivers/usb/musb/musb_dsps.c b/drivers/usb/musb/musb_dsps.c index b159fc92f846..6053af1f57c1 100644 --- a/drivers/usb/musb/musb_dsps.c +++ b/drivers/usb/musb/musb_dsps.c @@ -124,8 +124,44 @@ struct dsps_glue { const struct dsps_musb_wrapper *wrp; /* wrapper register offsets */ struct timer_list timer[2]; /* otg_workaround timer */ unsigned long last_timer[2]; /* last timer data for each instance */ + u32 __iomem *usb_ctrl[2]; }; +#define DSPS_AM33XX_CONTROL_MODULE_PHYS_0 0x44e10620 +#define DSPS_AM33XX_CONTROL_MODULE_PHYS_1 0x44e10628 + +static const resource_size_t dsps_control_module_phys[] = { + DSPS_AM33XX_CONTROL_MODULE_PHYS_0, + DSPS_AM33XX_CONTROL_MODULE_PHYS_1, +}; + +/** + * musb_dsps_phy_control - phy on/off + * @glue: struct dsps_glue * + * @id: musb instance + * @on: flag for phy to be switched on or off + * + * This is to enable the PHY using usb_ctrl register in system control + * module space. + * + * XXX: This function will be removed once we have a seperate driver for + * control module + */ +static void musb_dsps_phy_control(struct dsps_glue *glue, u8 id, u8 on) +{ + u32 usbphycfg; + + usbphycfg = readl(glue->usb_ctrl[id]); + + if (on) { + usbphycfg &= ~(USBPHY_CM_PWRDN | USBPHY_OTG_PWRDN); + usbphycfg |= USBPHY_OTGVDET_EN | USBPHY_OTGSESSEND_EN; + } else { + usbphycfg |= USBPHY_CM_PWRDN | USBPHY_OTG_PWRDN; + } + + writel(usbphycfg, glue->usb_ctrl[id]); +} /** * dsps_musb_enable - enable interrupts */ @@ -392,6 +428,9 @@ static int dsps_musb_init(struct musb *musb) /* Reset the musb */ dsps_writel(reg_base, wrp->control, (1 << wrp->reset)); + /* Start the on-chip PHY and its PLL. */ + musb_dsps_phy_control(glue, pdev->id, 1); + musb->isr = dsps_interrupt; /* reset the otgdisable bit, needed for host mode to work */ @@ -417,6 +456,9 @@ static int dsps_musb_exit(struct musb *musb) del_timer_sync(&glue->timer[pdev->id]); + /* Shutdown the on-chip PHY and its PLL. */ + musb_dsps_phy_control(glue, pdev->id, 0); + /* NOP driver needs change if supporting dual instance */ usb_put_phy(musb->xceiv); usb_nop_xceiv_unregister(); @@ -449,6 +491,17 @@ static int __devinit dsps_create_musb_pdev(struct dsps_glue *glue, u8 id) char res_name[10]; int ret; + resources[0].start = dsps_control_module_phys[id]; + resources[0].end = resources[0].start + SZ_4 - 1; + resources[0].flags = IORESOURCE_MEM; + + glue->usb_ctrl[id] = devm_request_and_ioremap(&pdev->dev, resources); + if (glue->usb_ctrl[id] == NULL) { + dev_err(dev, "Failed to obtain usb_ctrl%d memory\n", id); + ret = -ENODEV; + goto err0; + } + /* first resource is for usbss, so start index from 1 */ res = platform_get_resource(pdev, IORESOURCE_MEM, id + 1); if (!res) { @@ -635,11 +688,27 @@ static int __devexit dsps_remove(struct platform_device *pdev) #ifdef CONFIG_PM_SLEEP static int dsps_suspend(struct device *dev) { + struct platform_device *pdev = to_platform_device(dev->parent); + struct dsps_glue *glue = platform_get_drvdata(pdev); + const struct dsps_musb_wrapper *wrp = glue->wrp; + int i; + + for (i = 0; i < wrp->instances; i++) + musb_dsps_phy_control(glue, i, 0); + return 0; } static int dsps_resume(struct device *dev) { + struct platform_device *pdev = to_platform_device(dev->parent); + struct dsps_glue *glue = platform_get_drvdata(pdev); + const struct dsps_musb_wrapper *wrp = glue->wrp; + int i; + + for (i = 0; i < wrp->instances; i++) + musb_dsps_phy_control(glue, i, 1); + return 0; } #endif From 8b416b0b25d5d8ddb3a91c1d20e1373582c50405 Mon Sep 17 00:00:00 2001 From: Sergei Shtylyov Date: Mon, 5 Nov 2012 22:26:40 +0300 Subject: [PATCH 23/26] usb: musb: cppi_dma: export cppi_interrupt() Now that DaVinci glue layer can be modular, we must export cppi_interrupt() that it may call... Cc: stable@vger.kernel.org # 3.0+ Signed-off-by: Sergei Shtylyov Signed-off-by: Felipe Balbi --- drivers/usb/musb/cppi_dma.c | 1 + 1 file changed, 1 insertion(+) diff --git a/drivers/usb/musb/cppi_dma.c b/drivers/usb/musb/cppi_dma.c index e19da82b4782..3a6c2fd1f913 100644 --- a/drivers/usb/musb/cppi_dma.c +++ b/drivers/usb/musb/cppi_dma.c @@ -1314,6 +1314,7 @@ irqreturn_t cppi_interrupt(int irq, void *dev_id) return IRQ_HANDLED; } +EXPORT_SYMBOL_GPL(cppi_interrupt); /* Instantiate a software object representing a DMA controller. */ struct dma_controller *__devinit From baef653a500476ccb2d08cf4bb648c56c0170e21 Mon Sep 17 00:00:00 2001 From: Philippe De Swert Date: Tue, 6 Nov 2012 15:32:13 +0200 Subject: [PATCH 24/26] usb: musb: remove generic_interrupt This patch is based on the discussion of a previous patch to fix an issue where the omap2430 musb driver is not working for N9/N950. Moving all the interrupt handling to the devices. Avoids inclusion of generic interrupt and breakage due to sometimes misleading CONFIG options. This makes sure usb always works if on of the subdrivers is chosen. Tested on Nokia N9/N950. Partially clean up CONFIG_SOC_OMAP3430 which is not necessary in the cases where I removed it. Also helps with the removal work of those options that Tony Lindgren predicted would happen at some point. Signed-off-by: Philippe De Swert Signed-off-by: Felipe Balbi --- drivers/usb/musb/musb_core.c | 31 ++----------------------------- drivers/usb/musb/musbhsdma.h | 4 ---- drivers/usb/musb/omap2430.c | 22 ++++++++++++++++++++++ drivers/usb/musb/ux500.c | 22 ++++++++++++++++++++++ 4 files changed, 46 insertions(+), 33 deletions(-) diff --git a/drivers/usb/musb/musb_core.c b/drivers/usb/musb/musb_core.c index 78037bfad96e..774d8154a286 100644 --- a/drivers/usb/musb/musb_core.c +++ b/drivers/usb/musb/musb_core.c @@ -1501,33 +1501,6 @@ static int __devinit musb_core_init(u16 musb_type, struct musb *musb) /*-------------------------------------------------------------------------*/ -#if defined(CONFIG_SOC_OMAP2430) || defined(CONFIG_SOC_OMAP3430) || \ - defined(CONFIG_ARCH_OMAP4) || defined(CONFIG_ARCH_U8500) - -static irqreturn_t generic_interrupt(int irq, void *__hci) -{ - unsigned long flags; - irqreturn_t retval = IRQ_NONE; - struct musb *musb = __hci; - - spin_lock_irqsave(&musb->lock, flags); - - musb->int_usb = musb_readb(musb->mregs, MUSB_INTRUSB); - musb->int_tx = musb_readw(musb->mregs, MUSB_INTRTX); - musb->int_rx = musb_readw(musb->mregs, MUSB_INTRRX); - - if (musb->int_usb || musb->int_tx || musb->int_rx) - retval = musb_interrupt(musb); - - spin_unlock_irqrestore(&musb->lock, flags); - - return retval; -} - -#else -#define generic_interrupt NULL -#endif - /* * handle all the irqs defined by the HDRC core. for now we expect: other * irq sources (phy, dma, etc) will be handled first, musb->int_* values @@ -1896,7 +1869,8 @@ musb_init_controller(struct device *dev, int nIrq, void __iomem *ctrl) musb->ops = plat->platform_ops; /* The musb_platform_init() call: - * - adjusts musb->mregs and musb->isr if needed, + * - adjusts musb->mregs + * - sets the musb->isr * - may initialize an integrated tranceiver * - initializes musb->xceiv, usually by otg_get_phy() * - stops powering VBUS @@ -1906,7 +1880,6 @@ musb_init_controller(struct device *dev, int nIrq, void __iomem *ctrl) * external/discrete ones in various flavors (twl4030 family, * isp1504, non-OTG, etc) mostly hooking up through ULPI. */ - musb->isr = generic_interrupt; status = musb_platform_init(musb); if (status < 0) goto fail1; diff --git a/drivers/usb/musb/musbhsdma.h b/drivers/usb/musb/musbhsdma.h index 320fd4afb93f..f7b13fd25257 100644 --- a/drivers/usb/musb/musbhsdma.h +++ b/drivers/usb/musb/musbhsdma.h @@ -31,10 +31,6 @@ * */ -#if defined(CONFIG_SOC_OMAP2430) || defined(CONFIG_SOC_OMAP3430) -#include "omap2430.h" -#endif - #ifndef CONFIG_BLACKFIN #define MUSB_HSDMA_BASE 0x200 diff --git a/drivers/usb/musb/omap2430.c b/drivers/usb/musb/omap2430.c index dddd8f71a176..32f531e7a2e6 100644 --- a/drivers/usb/musb/omap2430.c +++ b/drivers/usb/musb/omap2430.c @@ -333,6 +333,26 @@ static void omap_musb_mailbox_work(struct work_struct *mailbox_work) omap_musb_set_mailbox(glue); } +static irqreturn_t omap2430_musb_interrupt(int irq, void *__hci) +{ + unsigned long flags; + irqreturn_t retval = IRQ_NONE; + struct musb *musb = __hci; + + spin_lock_irqsave(&musb->lock, flags); + + musb->int_usb = musb_readb(musb->mregs, MUSB_INTRUSB); + musb->int_tx = musb_readw(musb->mregs, MUSB_INTRTX); + musb->int_rx = musb_readw(musb->mregs, MUSB_INTRRX); + + if (musb->int_usb || musb->int_tx || musb->int_rx) + retval = musb_interrupt(musb); + + spin_unlock_irqrestore(&musb->lock, flags); + + return retval; +} + static int omap2430_musb_init(struct musb *musb) { u32 l; @@ -352,6 +372,8 @@ static int omap2430_musb_init(struct musb *musb) return -ENODEV; } + musb->isr = omap2430_musb_interrupt; + status = pm_runtime_get_sync(dev); if (status < 0) { dev_err(dev, "pm_runtime_get_sync FAILED %d\n", status); diff --git a/drivers/usb/musb/ux500.c b/drivers/usb/musb/ux500.c index 5e9053eb4298..286f1be6594a 100644 --- a/drivers/usb/musb/ux500.c +++ b/drivers/usb/musb/ux500.c @@ -36,6 +36,26 @@ struct ux500_glue { }; #define glue_to_musb(g) platform_get_drvdata(g->musb) +static irqreturn_t ux500_musb_interrupt(int irq, void *__hci) +{ + unsigned long flags; + irqreturn_t retval = IRQ_NONE; + struct musb *musb = __hci; + + spin_lock_irqsave(&musb->lock, flags); + + musb->int_usb = musb_readb(musb->mregs, MUSB_INTRUSB); + musb->int_tx = musb_readw(musb->mregs, MUSB_INTRTX); + musb->int_rx = musb_readw(musb->mregs, MUSB_INTRRX); + + if (musb->int_usb || musb->int_tx || musb->int_rx) + retval = musb_interrupt(musb); + + spin_unlock_irqrestore(&musb->lock, flags); + + return retval; +} + static int ux500_musb_init(struct musb *musb) { musb->xceiv = usb_get_phy(USB_PHY_TYPE_USB2); @@ -44,6 +64,8 @@ static int ux500_musb_init(struct musb *musb) return -ENODEV; } + musb->isr = ux500_musb_interrupt; + return 0; } From d75542263a0b005876d112bbf9ffb23180cc3149 Mon Sep 17 00:00:00 2001 From: Afzal Mohammed Date: Tue, 6 Nov 2012 20:47:24 +0530 Subject: [PATCH 25/26] Revert "usb: musb: dsps: remove explicit NOP device creation" This reverts commit d8c3ef256f88b7c6ecd673d03073b5645be9c5e4. Above mentioned change was made along with multi usb phy change and adding DT support for nop transceiver. But other two changes did not make it to mainline. This in effect makes dsps musb wrapper unusable even for single instance. Hence revert it so that at least single instance can be supported. Cc: stable@vger.kernel.org # v3.7 Signed-off-by: Afzal Mohammed Signed-off-by: Felipe Balbi --- drivers/usb/musb/musb_dsps.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/drivers/usb/musb/musb_dsps.c b/drivers/usb/musb/musb_dsps.c index 6053af1f57c1..e770f7984b5f 100644 --- a/drivers/usb/musb/musb_dsps.c +++ b/drivers/usb/musb/musb_dsps.c @@ -411,7 +411,8 @@ static int dsps_musb_init(struct musb *musb) /* mentor core register starts at offset of 0x400 from musb base */ musb->mregs += wrp->musb_core_offset; - /* Get the NOP PHY */ + /* NOP driver needs change if supporting dual instance */ + usb_nop_xceiv_register(); musb->xceiv = usb_get_phy(USB_PHY_TYPE_USB2); if (IS_ERR_OR_NULL(musb->xceiv)) return -ENODEV; From d928cd2ef8f7f4194e479d4a66452901ec82ccda Mon Sep 17 00:00:00 2001 From: Afzal Mohammed Date: Tue, 6 Nov 2012 20:47:35 +0530 Subject: [PATCH 26/26] usb: musb: dsps: document dt bindings properly DT bindings normally use '-' (hyphens) instead of '_' (underscore), driver has it the proper way, but binding documentation does not reflect it, fix it. Signed-off-by: Afzal Mohammed Signed-off-by: Felipe Balbi --- Documentation/devicetree/bindings/usb/am33xx-usb.txt | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/Documentation/devicetree/bindings/usb/am33xx-usb.txt b/Documentation/devicetree/bindings/usb/am33xx-usb.txt index ca8fa56e9f03..a92250512a4e 100644 --- a/Documentation/devicetree/bindings/usb/am33xx-usb.txt +++ b/Documentation/devicetree/bindings/usb/am33xx-usb.txt @@ -3,12 +3,12 @@ AM33XX MUSB GLUE - ti,hwmods : must be "usb_otg_hs" - multipoint : Should be "1" indicating the musb controller supports multipoint. This is a MUSB configuration-specific setting. - - num_eps : Specifies the number of endpoints. This is also a + - num-eps : Specifies the number of endpoints. This is also a MUSB configuration-specific setting. Should be set to "16" - - ram_bits : Specifies the ram address size. Should be set to "12" - - port0_mode : Should be "3" to represent OTG. "1" signifies HOST and "2" + - ram-bits : Specifies the ram address size. Should be set to "12" + - port0-mode : Should be "3" to represent OTG. "1" signifies HOST and "2" represents PERIPHERAL. - - port1_mode : Should be "1" to represent HOST. "3" signifies OTG and "2" + - port1-mode : Should be "1" to represent HOST. "3" signifies OTG and "2" represents PERIPHERAL. - power : Should be "250". This signifies the controller can supply upto 500mA when operating in host mode.