diff options
author | Jernej Skrabec <jernej.skrabec@siol.net> | 2021-01-11 23:11:33 +0300 |
---|---|---|
committer | Andre Przywara <andre.przywara@arm.com> | 2021-01-26 00:52:00 +0300 |
commit | fbd37d8d28450a29180a9df1e7546c7f0cb60a38 (patch) | |
tree | 07940707fb612830e408da77307f31d94b45cb6c /drivers/power/axp305.c | |
parent | e9ad1b8dc5c7bae5213309af7c49907bac5def73 (diff) | |
download | u-boot-fbd37d8d28450a29180a9df1e7546c7f0cb60a38.tar.xz |
sunxi: Add support for AXP305 PMIC
This PMIC can be found on H616 boards and it's very similar to AXP805
and AXP806.
Signed-off-by: Jernej Skrabec <jernej.skrabec@siol.net>
Reviewed-by: Andre Przywara <andre.przywara@arm.com>
Reviewed-by: Jaehoon Chung <jh80.chung@samsung.com>
Signed-off-by: Andre Przywara <andre.przywara@arm.com>
Diffstat (limited to 'drivers/power/axp305.c')
-rw-r--r-- | drivers/power/axp305.c | 83 |
1 files changed, 83 insertions, 0 deletions
diff --git a/drivers/power/axp305.c b/drivers/power/axp305.c new file mode 100644 index 0000000000..0191e4d427 --- /dev/null +++ b/drivers/power/axp305.c @@ -0,0 +1,83 @@ +// SPDX-License-Identifier: GPL-2.0+ +/* + * AXP305 driver + * + * (C) Copyright 2020 Jernej Skrabec <jernej.skrabec@siol.net> + * + * Based on axp221.c + * (C) Copyright 2014 Hans de Goede <hdegoede@redhat.com> + * (C) Copyright 2013 Oliver Schinagl <oliver@schinagl.nl> + */ + +#include <common.h> +#include <command.h> +#include <errno.h> +#include <asm/arch/pmic_bus.h> +#include <axp_pmic.h> + +#define AXP305_DCDC4_1600MV_OFFSET 46 + +static u8 axp305_mvolt_to_cfg(int mvolt, int min, int max, int div) +{ + if (mvolt < min) + mvolt = min; + else if (mvolt > max) + mvolt = max; + + return (mvolt - min) / div; +} + +int axp_set_dcdc4(unsigned int mvolt) +{ + int ret; + u8 cfg; + + if (mvolt >= 1600) + cfg = AXP305_DCDC4_1600MV_OFFSET + + axp305_mvolt_to_cfg(mvolt, 1600, 3300, 100); + else + cfg = axp305_mvolt_to_cfg(mvolt, 600, 1500, 20); + + if (mvolt == 0) + return pmic_bus_clrbits(AXP305_OUTPUT_CTRL1, + AXP305_OUTPUT_CTRL1_DCDCD_EN); + + ret = pmic_bus_write(AXP305_DCDCD_VOLTAGE, cfg); + if (ret) + return ret; + + return pmic_bus_setbits(AXP305_OUTPUT_CTRL1, + AXP305_OUTPUT_CTRL1_DCDCD_EN); +} + +int axp_init(void) +{ + u8 axp_chip_id; + int ret; + + ret = pmic_bus_init(); + if (ret) + return ret; + + ret = pmic_bus_read(AXP305_CHIP_VERSION, &axp_chip_id); + if (ret) + return ret; + + if ((axp_chip_id & AXP305_CHIP_VERSION_MASK) != 0x40) + return -ENODEV; + + return ret; +} + +#ifndef CONFIG_PSCI_RESET +int do_poweroff(struct cmd_tbl *cmdtp, int flag, int argc, char *const argv[]) +{ + pmic_bus_write(AXP305_SHUTDOWN, AXP305_POWEROFF); + + /* infinite loop during shutdown */ + while (1) {} + + /* not reached */ + return 0; +} +#endif |