
Add support for the x-powers axp152 pmic which is found on most A10s boards.
Signed-off-by: Henrik Nordstrom henrik@henriknordstrom.net Signed-off-by: Ian Campbell ijc@hellion.org.uk Signed-off-by: Hans de Goede hdegoede@redhat.com --- board/sunxi/board.c | 10 ++++ boards.cfg | 2 +- drivers/power/Makefile | 1 + drivers/power/axp152.c | 122 +++++++++++++++++++++++++++++++++++++++++++++++++ include/axp152.h | 11 +++++ 5 files changed, 145 insertions(+), 1 deletion(-) create mode 100644 drivers/power/axp152.c create mode 100644 include/axp152.h
diff --git a/board/sunxi/board.c b/board/sunxi/board.c index 309bbd2..c6d4b3c 100644 --- a/board/sunxi/board.c +++ b/board/sunxi/board.c @@ -12,6 +12,9 @@ */
#include <common.h> +#ifdef CONFIG_AXP152_POWER +#include <axp152.h> +#endif #ifdef CONFIG_AXP209_POWER #include <axp209.h> #endif @@ -122,6 +125,13 @@ void sunxi_board_init(void) int power_failed = 0; unsigned long ramsize;
+#ifdef CONFIG_AXP152_POWER + power_failed = axp152_init(); + power_failed |= axp152_set_dcdc2(1400); + power_failed |= axp152_set_dcdc3(1500); + power_failed |= axp152_set_dcdc4(1250); + power_failed |= axp152_set_ldo2(3000); +#endif #ifdef CONFIG_AXP209_POWER power_failed |= axp209_init(); power_failed |= axp209_set_dcdc2(1400); diff --git a/boards.cfg b/boards.cfg index 72585a9..f4f870a 100644 --- a/boards.cfg +++ b/boards.cfg @@ -384,7 +384,7 @@ Active arm armv7 sunxi - sunxi Active arm armv7 sunxi - sunxi Cubieboard sun4i:CUBIEBOARD,SPL,AXP209_POWER Hans de Goede hdegoede@redhat.com Active arm armv7 sunxi - sunxi Cubietruck sun7i:CUBIETRUCK,SPL,AXP209_POWER,SUNXI_GMAC,RGMII Hans de Goede hdegoede@redhat.com Active arm armv7 sunxi - sunxi Cubietruck_FEL sun7i:CUBIETRUCK,SPL_FEL,AXP209_POWER,SUNXI_GMAC,RGMII Hans de Goede hdegoede@redhat.com -Active arm armv7 sunxi - sunxi r7-tv-dongle sun5i:R7DONGLE,SPL Hans de Goede hdegoede@redhat.com +Active arm armv7 sunxi - sunxi r7-tv-dongle sun5i:R7DONGLE,SPL,AXP152_POWER Hans de Goede hdegoede@redhat.com Active arm armv7 u8500 st-ericsson snowball snowball - Mathieu Poirier mathieu.poirier@linaro.org Active arm armv7 u8500 st-ericsson u8500 u8500_href - - Active arm armv7 vf610 freescale vf610twr vf610twr vf610twr:IMX_CONFIG=board/freescale/vf610twr/imximage.cfg Alison Wang b18965@freescale.com diff --git a/drivers/power/Makefile b/drivers/power/Makefile index 063ac8f..dc64e4d 100644 --- a/drivers/power/Makefile +++ b/drivers/power/Makefile @@ -5,6 +5,7 @@ # SPDX-License-Identifier: GPL-2.0+ #
+obj-$(CONFIG_AXP152_POWER) += axp152.o obj-$(CONFIG_AXP209_POWER) += axp209.o obj-$(CONFIG_EXYNOS_TMU) += exynos-tmu.o obj-$(CONFIG_FTPMU010_POWER) += ftpmu010.o diff --git a/drivers/power/axp152.c b/drivers/power/axp152.c new file mode 100644 index 0000000..a7a7909 --- /dev/null +++ b/drivers/power/axp152.c @@ -0,0 +1,122 @@ +/* + * (C) Copyright 2012 + * Henrik Nordstrom henrik@henriknordstrom.net + * + * SPDX-License-Identifier: GPL-2.0+ + */ +#include <common.h> +#include <i2c.h> +#include <axp152.h> + +enum axp152_reg { + AXP152_CHIP_VERSION = 0x3, + AXP152_DCDC2_VOLTAGE = 0x23, + AXP152_DCDC3_VOLTAGE = 0x27, + AXP152_DCDC4_VOLTAGE = 0x2B, + AXP152_LDO2_VOLTAGE = 0x2A, + AXP152_SHUTDOWN = 0x32, +}; + +int axp152_write(enum axp152_reg reg, u8 val) +{ + return i2c_write(0x30, reg, 1, &val, 1); +} + +int axp152_read(enum axp152_reg reg, u8 *val) +{ + return i2c_read(0x30, reg, 1, val, 1); +} + +int axp152_set_dcdc2(int mvolt) +{ + int target = (mvolt - 700) / 25; + int rc; + u8 current; + + if (target < 0) + target = 0; + if (target > (1<<6)-1) + target = (1<<6)-1; + /* Do we really need to be this gentle? It has built-in voltage slope */ + while ((rc = axp152_read(AXP152_DCDC2_VOLTAGE, ¤t)) == 0 && + current != target) { + if (current < target) + current++; + else + current--; + rc = axp152_write(AXP152_DCDC2_VOLTAGE, current); + if (rc) + break; + } + return rc; +} + +int axp152_set_dcdc3(int mvolt) +{ + int target = (mvolt - 700) / 50; + u8 reg; + int rc; + + if (target < 0) + target = 0; + if (target > (1<<6)-1) + target = (1<<6)-1; + rc = axp152_write(AXP152_DCDC3_VOLTAGE, target); + rc |= axp152_read(AXP152_DCDC3_VOLTAGE, ®); + return rc; +} + +int axp152_set_dcdc4(int mvolt) +{ + int target = (mvolt - 700) / 25; + u8 reg; + int rc; + + if (target < 0) + target = 0; + if (target > (1<<7)-1) + target = (1<<7)-1; + rc = axp152_write(AXP152_DCDC4_VOLTAGE, target); + rc |= axp152_read(AXP152_DCDC4_VOLTAGE, ®); + return rc; +} + +int axp152_set_ldo2(int mvolt) +{ + int target = (mvolt - 700) / 100; + int rc; + u8 reg; + + if (target < 0) + target = 0; + if (target > 31) + target = 31; + rc = axp152_write(AXP152_LDO2_VOLTAGE, target); + rc |= axp152_read(AXP152_LDO2_VOLTAGE, ®); + return rc; +} + +void axp152_poweroff(void) +{ + u8 val; + + if (axp152_read(AXP152_SHUTDOWN, &val) != 0) + return; + val |= 1 << 7; + if (axp152_write(AXP152_SHUTDOWN, val) != 0) + return; + udelay(10000); /* wait for power to drain */ +} + +int axp152_init(void) +{ + u8 ver; + int rc; + + rc = axp152_read(AXP152_CHIP_VERSION, &ver); + if (rc) + return rc; + if (ver != 0x05) + return -1; + return 0; +} diff --git a/include/axp152.h b/include/axp152.h new file mode 100644 index 0000000..b34c194 --- /dev/null +++ b/include/axp152.h @@ -0,0 +1,11 @@ +/* + * (C) Copyright 2012 Henrik Nordstrom henrik@henriknordstrom.net + * + * SPDX-License-Identifier: GPL-2.0+ + */ +int axp152_set_dcdc2(int mvolt); +int axp152_set_dcdc3(int mvolt); +int axp152_set_dcdc4(int mvolt); +int axp152_set_ldo2(int mvolt); +void axp152_poweroff(void); +int axp152_init(void);