Re: [PATCH] usb: musb: support for OFF-mode

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



ext Sergei Shtylyov wrote:
Hello.

Arnaud Mandy wrote:

using a wrapper between the transceiver driver and the controller
driver to signal the controller driver to turn on/off the controller
when VBUS event is detected.

based-on: Heikki Krogerus <ext-heikki.krogerus@xxxxxxxxx>
Signed-off-by: Arnaud Mandy <ext-arnaud.2.mandy@xxxxxxxxx>

[...]

diff --git a/drivers/usb/musb/musb_core.h b/drivers/usb/musb/musb_core.h
index 1e3da4e..8105a47 100644
--- a/drivers/usb/musb/musb_core.h
+++ b/drivers/usb/musb/musb_core.h
@@ -448,6 +448,11 @@ struct musb {
 	struct usb_gadget	g;			/* the gadget */
 	struct usb_gadget_driver *gadget_driver;	/* its driver */
 #endif
+	/* true if off-mode is supported */
+	unsigned		off_mode_support:1;
+
+	/* true if off-mode is requested */
+	unsigned                off_mode:1;
/* true if we're using dma */
 	unsigned		use_dma:1;
@@ -498,8 +503,16 @@ extern void musb_platform_restore_context(struct musb *musb,
 #define musb_platform_save_context(m, x)	do {} while (0)
 #define musb_platform_restore_context(m, x)	do {} while (0)
 #endif
-
-#endif
+extern void musb_power_on_controller(struct musb *musb);
+extern void musb_power_off_controller(struct musb *musb);
+void musb_save_context(struct musb *musb);
+void musb_restore_context(struct musb *musb);
+#else
+static inline void musb_power_on_controller(struct musb *musb) {};
+static inline void musb_power_off_controller(struct musb *musb) {};
+static inline void musb_save_context(struct musb *musb) {};
+static inline void musb_restore_context(struct musb *musb) {};

What if CONFIG_PM is set for e.g. DaVinci configuration? You don't have these functions defined in davinci.c.



Correct, I thought the flag off_mode_support would help avoiding stub,
but it doesn't. will change it to stubs.

+#endif /* CONFIG_PM */
static inline void musb_set_vbus(struct musb *musb, int is_on)
 {
diff --git a/drivers/usb/musb/omap2430.c b/drivers/usb/musb/omap2430.c
index 21cff53..3cc894b 100644
--- a/drivers/usb/musb/omap2430.c
+++ b/drivers/usb/musb/omap2430.c
@@ -220,6 +220,9 @@ int __init musb_platform_init(struct musb *musb)
musb_platform_resume(musb); +#ifdef CONFIG_PM
+	musb->off_mode_support = 1;
+#endif
 	l = musb_readl(musb->mregs, OTG_SYSCONFIG);
 	l &= ~ENABLEWAKEUP;	/* disable wakeup */
 	l &= ~NOSTDBY;		/* remove possible nostdby */
@@ -271,7 +274,68 @@ void musb_platform_restore_context(struct musb *musb,
 	musb_writel(musb->mregs, OTG_SYSCONFIG, musb_context->otg_sysconfig);
 	musb_writel(musb->mregs, OTG_FORCESTDBY, musb_context->otg_forcestandby);
 }
-#endif
+
+void musb_power_off_controller(struct musb *musb)
+{
+	u32 l;
+
+	DBG(3, "allow OFF-mode\n");
+
+	l = musb_readl(musb->mregs, OTG_FORCESTDBY);
+	l |= ENABLEFORCE;	/* enable MSTANDBY */
+	musb_writel(musb->mregs, OTG_FORCESTDBY, l);
+
+	l = musb_readl(musb->mregs, OTG_FORCESTDBY);
+	l |= ENABLEWAKEUP;	/* enable wakeup */
+	l &= ~NOSTDBY;		/* disable nostdby */
+	l |= SMARTSTDBY;	/* enable smart standby */
+
+	l |= AUTOIDLE;		/* enable auto idle */
+	l &= ~NOIDLE;		/* disable noidle */
+	l |= SMARTIDLE;		/* enable smart idle */
+
+	musb_writel(musb->mregs, OTG_SYSCONFIG, l);
+
+	if (!cpu_is_omap3430())
+		l |= AUTOIDLE;		/* enable auto idle */
+	musb_writel(musb->mregs, OTG_SYSCONFIG, l);
+}
+EXPORT_SYMBOL_GPL(musb_power_off_controller);
+
+void musb_power_on_controller(struct musb *musb)
+{
+	u32 l;
+
+	DBG(3, "wake-up from OFF-mode\n");
+
+	l = musb_readl(musb->mregs, OTG_SYSCONFIG);
+	l &= ~ENABLEWAKEUP;	/* disable wakeup */
+	musb_writel(musb->mregs, OTG_SYSCONFIG, l);
+
+	l = musb_readl(musb->mregs, OTG_FORCESTDBY);
+	l &= ~ENABLEFORCE;	/* disable MSTANDBY */
+	musb_writel(musb->mregs, OTG_FORCESTDBY, l);
+
+	l = musb_readl(musb->mregs, OTG_SYSCONFIG);
+	l |= NOSTDBY;		/* enable nostdby */
+	l &= ~SMARTSTDBY;	/* disable smart standby */
+
+	l &= ~AUTOIDLE;		/* disable auto idle */
+	l |= NOIDLE;		/* enable noidle */
+	l &= ~SMARTIDLE;	/* disable smart idle */
+	musb_writel(musb->mregs, OTG_SYSCONFIG, l);
+
+	l = musb_readl(musb->mregs, OTG_INTERFSEL);
+	l |= ULPI_12PIN;
+	musb_writel(musb->mregs, OTG_INTERFSEL, l);
+
+	/* Restore register context */
+	musb->off_mode = 1;
+	musb_restore_context(musb);
+	musb->off_mode = 0;
+}
+EXPORT_SYMBOL_GPL(musb_power_on_controller);
+#endif /* CONFIG_PM */

I suggest that you rename these functions to musb_platform_power_{off|on}() to match the other functions defined in the glue layer, like musb_platform_set_mode(), etc.

Will do
Thanks for the comments.

WBR, Sergei


--
To unsubscribe from this list: send the line "unsubscribe linux-usb" in
the body of a message to majordomo@xxxxxxxxxxxxxxx
More majordomo info at  http://vger.kernel.org/majordomo-info.html

--
To unsubscribe from this list: send the line "unsubscribe linux-usb" in
the body of a message to majordomo@xxxxxxxxxxxxxxx
More majordomo info at  http://vger.kernel.org/majordomo-info.html

[Index of Archives]     [Linux Media]     [Linux Input]     [Linux Audio Users]     [Yosemite News]     [Linux Kernel]     [Linux SCSI]     [Old Linux USB Devel Archive]

  Powered by Linux