regulator: pbias: Handle extended drain IO when changing omap36 PBIAS
authorAdam Ford <aford173@gmail.com>
Thu, 24 Jan 2019 20:33:36 +0000 (14:33 -0600)
committerTom Rini <trini@konsulko.com>
Fri, 1 Feb 2019 19:13:45 +0000 (14:13 -0500)
The OMAP36 and DM37 TRM state to disable extneded drain IO before
changing the PBIAS.  This patch does this before pmic writes if
the CONFIG_MMC_OMAP36XX_PINS flag is set and the cpu family is
omap36xx

Signed-off-by: Adam Ford <aford173@gmail.com>
drivers/power/regulator/pbias_regulator.c

index 366f97b38b72266dc297b1437615ef1202263f16..4ed3c94e03115e06286a1bb7f41186bdebfba605 100644 (file)
 #include <linux/bitops.h>
 #include <linux/ioport.h>
 #include <dm/read.h>
+#ifdef CONFIG_MMC_OMAP36XX_PINS
+#include <asm/arch/sys_proto.h>
+#include <asm/io.h>
+#include <asm/arch/mux.h>
+#endif
 
 struct pbias_reg_info {
        u32 enable;
@@ -223,8 +228,11 @@ static int pbias_regulator_get_value(struct udevice *dev)
 static int pbias_regulator_set_value(struct udevice *dev, int uV)
 {
        const struct pbias_reg_info *p = dev_get_priv(dev);
-       int rc;
+       int rc, ret;
        u32 reg;
+#ifdef CONFIG_MMC_OMAP36XX_PINS
+       u32 wkup_ctrl = readl(OMAP34XX_CTRL_WKUP_CTRL);
+#endif
 
        rc = pmic_read(dev->parent, 0, (uint8_t *)&reg, sizeof(reg));
        if (rc)
@@ -240,7 +248,23 @@ static int pbias_regulator_set_value(struct udevice *dev, int uV)
        debug("Setting %s voltage to %s\n", p->name,
              (reg & p->vmode) ? "3.0v" : "1.8v");
 
-       return pmic_write(dev->parent, 0, (uint8_t *)&reg, sizeof(reg));
+#ifdef CONFIG_MMC_OMAP36XX_PINS
+       if (get_cpu_family() == CPU_OMAP36XX) {
+               /* Disable extended drain IO before changing PBIAS */
+               wkup_ctrl &= ~OMAP34XX_CTRL_WKUP_CTRL_GPIO_IO_PWRDNZ;
+               writel(wkup_ctrl, OMAP34XX_CTRL_WKUP_CTRL);
+       }
+#endif
+       ret = pmic_write(dev->parent, 0, (uint8_t *)&reg, sizeof(reg));
+#ifdef CONFIG_MMC_OMAP36XX_PINS
+       if (get_cpu_family() == CPU_OMAP36XX) {
+               /* Enable extended drain IO after changing PBIAS */
+               writel(wkup_ctrl |
+                               OMAP34XX_CTRL_WKUP_CTRL_GPIO_IO_PWRDNZ,
+                               OMAP34XX_CTRL_WKUP_CTRL);
+       }
+#endif
+       return ret;
 }
 
 static int pbias_regulator_get_enable(struct udevice *dev)
@@ -264,9 +288,20 @@ static int pbias_regulator_set_enable(struct udevice *dev, bool enable)
        const struct pbias_reg_info *p = dev_get_priv(dev);
        int rc;
        u32 reg;
+#ifdef CONFIG_MMC_OMAP36XX_PINS
+       u32 wkup_ctrl = readl(OMAP34XX_CTRL_WKUP_CTRL);
+#endif
 
        debug("Turning %s %s\n", enable ? "on" : "off", p->name);
 
+#ifdef CONFIG_MMC_OMAP36XX_PINS
+       if (get_cpu_family() == CPU_OMAP36XX) {
+               /* Disable extended drain IO before changing PBIAS */
+               wkup_ctrl &= ~OMAP34XX_CTRL_WKUP_CTRL_GPIO_IO_PWRDNZ;
+               writel(wkup_ctrl, OMAP34XX_CTRL_WKUP_CTRL);
+       }
+#endif
+
        rc = pmic_read(dev->parent, 0, (uint8_t *)&reg, sizeof(reg));
        if (rc)
                return rc;
@@ -278,6 +313,16 @@ static int pbias_regulator_set_enable(struct udevice *dev, bool enable)
                reg |= p->disable_val;
 
        rc = pmic_write(dev->parent, 0, (uint8_t *)&reg, sizeof(reg));
+
+#ifdef CONFIG_MMC_OMAP36XX_PINS
+       if (get_cpu_family() == CPU_OMAP36XX) {
+               /* Enable extended drain IO after changing PBIAS */
+               writel(wkup_ctrl |
+                               OMAP34XX_CTRL_WKUP_CTRL_GPIO_IO_PWRDNZ,
+                               OMAP34XX_CTRL_WKUP_CTRL);
+       }
+#endif
+
        if (rc)
                return rc;