diff --git a/target/linux/generic/backport-6.1/880-v6.3-mfd-axp20x-Fix-order-of-pek-rise-and-fall-events.patch b/target/linux/generic/backport-6.1/880-v6.3-mfd-axp20x-Fix-order-of-pek-rise-and-fall-events.patch new file mode 100644 index 00000000000..23681ba9374 --- /dev/null +++ b/target/linux/generic/backport-6.1/880-v6.3-mfd-axp20x-Fix-order-of-pek-rise-and-fall-events.patch @@ -0,0 +1,80 @@ +From 8781ba7f45695af3ab8e8d1b55a31f527c9201a3 Mon Sep 17 00:00:00 2001 +From: Aren Moynihan +Date: Thu, 8 Dec 2022 17:02:26 -0500 +Subject: [PATCH] mfd: axp20x: Fix order of pek rise and fall events + +The power button can get "stuck" if the rising edge and falling edge irq +are read in the same pass. This can often be triggered when resuming +from suspend if the power button is released before the kernel handles +the interrupt. + +Swapping the order of the rise and fall events makes sure that the press +event is handled first, which prevents this situation. + +Signed-off-by: Aren Moynihan +Reviewed-by: Samuel Holland +Tested-by: Samuel Holland +Acked-by: Chen-Yu Tsai +Signed-off-by: Lee Jones +Link: https://lore.kernel.org/r/20221208220225.635414-1-aren@peacevolution.org +--- + include/linux/mfd/axp20x.h | 15 ++++++++++----- + 1 file changed, 10 insertions(+), 5 deletions(-) + +--- a/include/linux/mfd/axp20x.h ++++ b/include/linux/mfd/axp20x.h +@@ -432,8 +432,9 @@ enum { + AXP152_IRQ_PEK_SHORT, + AXP152_IRQ_PEK_LONG, + AXP152_IRQ_TIMER, +- AXP152_IRQ_PEK_RIS_EDGE, ++ /* out of bit order to make sure the press event is handled first */ + AXP152_IRQ_PEK_FAL_EDGE, ++ AXP152_IRQ_PEK_RIS_EDGE, + AXP152_IRQ_GPIO3_INPUT, + AXP152_IRQ_GPIO2_INPUT, + AXP152_IRQ_GPIO1_INPUT, +@@ -472,8 +473,9 @@ enum { + AXP20X_IRQ_LOW_PWR_LVL1, + AXP20X_IRQ_LOW_PWR_LVL2, + AXP20X_IRQ_TIMER, +- AXP20X_IRQ_PEK_RIS_EDGE, ++ /* out of bit order to make sure the press event is handled first */ + AXP20X_IRQ_PEK_FAL_EDGE, ++ AXP20X_IRQ_PEK_RIS_EDGE, + AXP20X_IRQ_GPIO3_INPUT, + AXP20X_IRQ_GPIO2_INPUT, + AXP20X_IRQ_GPIO1_INPUT, +@@ -502,8 +504,9 @@ enum axp22x_irqs { + AXP22X_IRQ_LOW_PWR_LVL1, + AXP22X_IRQ_LOW_PWR_LVL2, + AXP22X_IRQ_TIMER, +- AXP22X_IRQ_PEK_RIS_EDGE, ++ /* out of bit order to make sure the press event is handled first */ + AXP22X_IRQ_PEK_FAL_EDGE, ++ AXP22X_IRQ_PEK_RIS_EDGE, + AXP22X_IRQ_GPIO1_INPUT, + AXP22X_IRQ_GPIO0_INPUT, + }; +@@ -571,8 +574,9 @@ enum axp803_irqs { + AXP803_IRQ_LOW_PWR_LVL1, + AXP803_IRQ_LOW_PWR_LVL2, + AXP803_IRQ_TIMER, +- AXP803_IRQ_PEK_RIS_EDGE, ++ /* out of bit order to make sure the press event is handled first */ + AXP803_IRQ_PEK_FAL_EDGE, ++ AXP803_IRQ_PEK_RIS_EDGE, + AXP803_IRQ_PEK_SHORT, + AXP803_IRQ_PEK_LONG, + AXP803_IRQ_PEK_OVER_OFF, +@@ -623,8 +627,9 @@ enum axp809_irqs { + AXP809_IRQ_LOW_PWR_LVL1, + AXP809_IRQ_LOW_PWR_LVL2, + AXP809_IRQ_TIMER, +- AXP809_IRQ_PEK_RIS_EDGE, ++ /* out of bit order to make sure the press event is handled first */ + AXP809_IRQ_PEK_FAL_EDGE, ++ AXP809_IRQ_PEK_RIS_EDGE, + AXP809_IRQ_PEK_SHORT, + AXP809_IRQ_PEK_LONG, + AXP809_IRQ_PEK_OVER_OFF, diff --git a/target/linux/generic/backport-6.1/881-v6.3-mfd-axp20x-Switch-to-the-sys-off-handler-API.patch b/target/linux/generic/backport-6.1/881-v6.3-mfd-axp20x-Switch-to-the-sys-off-handler-API.patch new file mode 100644 index 00000000000..b742276c8ad --- /dev/null +++ b/target/linux/generic/backport-6.1/881-v6.3-mfd-axp20x-Switch-to-the-sys-off-handler-API.patch @@ -0,0 +1,82 @@ +From 1b1305e95e85624f538ec56db9acf88e2d3d7397 Mon Sep 17 00:00:00 2001 +From: Samuel Holland +Date: Wed, 28 Dec 2022 10:27:52 -0600 +Subject: [PATCH] mfd: axp20x: Switch to the sys-off handler API + +This removes a layer of indirection through pm_power_off() and allows +the PMIC handler to be used as a fallback when firmware power off fails. +This happens on boards like the Clockwork DevTerm R-01 where OpenSBI +does not know how to use the PMIC to power off the board. + +Move the check for AXP288 to avoid registering a dummy handler. + +Signed-off-by: Samuel Holland +[Lee: Removed superfluous new line] +Signed-off-by: Lee Jones +Link: https://lore.kernel.org/r/20221228162752.14204-1-samuel@sholland.org +--- + drivers/mfd/axp20x.c | 27 +++++++++++---------------- + 1 file changed, 11 insertions(+), 16 deletions(-) + +--- a/drivers/mfd/axp20x.c ++++ b/drivers/mfd/axp20x.c +@@ -23,7 +23,7 @@ + #include + #include + #include +-#include ++#include + #include + #include + +@@ -832,17 +832,16 @@ static const struct mfd_cell axp813_cell + }, + }; + +-static struct axp20x_dev *axp20x_pm_power_off; +-static void axp20x_power_off(void) ++static int axp20x_power_off(struct sys_off_data *data) + { +- if (axp20x_pm_power_off->variant == AXP288_ID) +- return; ++ struct axp20x_dev *axp20x = data->cb_data; + +- regmap_write(axp20x_pm_power_off->regmap, AXP20X_OFF_CTRL, +- AXP20X_OFF); ++ regmap_write(axp20x->regmap, AXP20X_OFF_CTRL, AXP20X_OFF); + + /* Give capacitors etc. time to drain to avoid kernel panic msg. */ + mdelay(500); ++ ++ return NOTIFY_DONE; + } + + int axp20x_match_device(struct axp20x_dev *axp20x) +@@ -1009,10 +1008,11 @@ int axp20x_device_probe(struct axp20x_de + return ret; + } + +- if (!pm_power_off) { +- axp20x_pm_power_off = axp20x; +- pm_power_off = axp20x_power_off; +- } ++ if (axp20x->variant != AXP288_ID) ++ devm_register_sys_off_handler(axp20x->dev, ++ SYS_OFF_MODE_POWER_OFF, ++ SYS_OFF_PRIO_DEFAULT, ++ axp20x_power_off, axp20x); + + dev_info(axp20x->dev, "AXP20X driver loaded\n"); + +@@ -1022,11 +1022,6 @@ EXPORT_SYMBOL(axp20x_device_probe); + + void axp20x_device_remove(struct axp20x_dev *axp20x) + { +- if (axp20x == axp20x_pm_power_off) { +- axp20x_pm_power_off = NULL; +- pm_power_off = NULL; +- } +- + mfd_remove_devices(axp20x->dev); + regmap_del_irq_chip(axp20x->irq, axp20x->regmap_irqc); + } diff --git a/target/linux/generic/backport-6.1/882-v6.3-mfd-axp20x-Fix-axp288-writable-ranges.patch b/target/linux/generic/backport-6.1/882-v6.3-mfd-axp20x-Fix-axp288-writable-ranges.patch new file mode 100644 index 00000000000..b84815e1a85 --- /dev/null +++ b/target/linux/generic/backport-6.1/882-v6.3-mfd-axp20x-Fix-axp288-writable-ranges.patch @@ -0,0 +1,28 @@ +From 2405fbfb384ef39e9560d76d3f6e4c90519f90aa Mon Sep 17 00:00:00 2001 +From: Hans de Goede +Date: Wed, 29 Mar 2023 22:55:44 +0200 +Subject: [PATCH] mfd: axp20x: Fix axp288 writable-ranges + +Register AXP288_POWER_REASON is writable and needs to be written +to reset the reset- / power-on-reason bits. + +Add it to the axp288 writable-ranges so that the extcon-axp288 +driver can properly clear the reset- / power-on-reason bits. + +Signed-off-by: Hans de Goede +Signed-off-by: Lee Jones +Link: https://lore.kernel.org/r/20230329205544.1051393-1-hdegoede@redhat.com +--- + drivers/mfd/axp20x.c | 1 + + 1 file changed, 1 insertion(+) + +--- a/drivers/mfd/axp20x.c ++++ b/drivers/mfd/axp20x.c +@@ -119,6 +119,7 @@ static const struct regmap_access_table + + /* AXP288 ranges are shared with the AXP803, as they cover the same range */ + static const struct regmap_range axp288_writeable_ranges[] = { ++ regmap_reg_range(AXP288_POWER_REASON, AXP288_POWER_REASON), + regmap_reg_range(AXP20X_DATACACHE(0), AXP20X_IRQ6_STATE), + regmap_reg_range(AXP20X_DCDC_MODE, AXP288_FG_TUNE5), + }; diff --git a/target/linux/generic/backport-6.1/883-v6.4-mfd-axp20x-Add-support-for-AXP15060-PMIC.patch b/target/linux/generic/backport-6.1/883-v6.4-mfd-axp20x-Add-support-for-AXP15060-PMIC.patch new file mode 100644 index 00000000000..83ef60aecd7 --- /dev/null +++ b/target/linux/generic/backport-6.1/883-v6.4-mfd-axp20x-Add-support-for-AXP15060-PMIC.patch @@ -0,0 +1,343 @@ +From e0f8ad2a705367518b5c56bf9d6da89681467c02 Mon Sep 17 00:00:00 2001 +From: Shengyu Qu +Date: Fri, 21 Apr 2023 23:08:15 +0800 +Subject: [PATCH] mfd: axp20x: Add support for AXP15060 PMIC + +The AXP15060 is a PMIC chip produced by X-Powers, and could be connected +via an I2C bus. + +Describe the regmap and the MFD bits, along with the registers exposed +via I2C. Eventually advertise the device using a new compatible string +and add support for power off the system. + +The driver would disable PEK function if IRQ is not configured in device +tree, since some boards (For example, Starfive Visionfive 2) didn't +connect IRQ line of PMIC to SOC. + +GPIO function isn't enabled in this commit, since its configuration +operation is different from any existing AXP PMICs and needs +logic modification on existing driver. GPIO support might come in later +patches. + +Signed-off-by: Shengyu Qu +Reviewed-by: Krzysztof Kozlowski +Signed-off-by: Lee Jones +Link: https://lore.kernel.org/r/TY3P286MB261162D57695AC8164ED50E298609@TY3P286MB2611.JPNP286.PROD.OUTLOOK.COM +--- + drivers/mfd/axp20x-i2c.c | 2 + + drivers/mfd/axp20x.c | 107 +++++++++++++++++++++++++++++++++++++ + include/linux/mfd/axp20x.h | 85 +++++++++++++++++++++++++++++ + 3 files changed, 194 insertions(+) + +--- a/drivers/mfd/axp20x-i2c.c ++++ b/drivers/mfd/axp20x-i2c.c +@@ -66,6 +66,7 @@ static const struct of_device_id axp20x_ + { .compatible = "x-powers,axp223", .data = (void *)AXP223_ID }, + { .compatible = "x-powers,axp803", .data = (void *)AXP803_ID }, + { .compatible = "x-powers,axp806", .data = (void *)AXP806_ID }, ++ { .compatible = "x-powers,axp15060", .data = (void *)AXP15060_ID }, + { }, + }; + MODULE_DEVICE_TABLE(of, axp20x_i2c_of_match); +@@ -79,6 +80,7 @@ static const struct i2c_device_id axp20x + { "axp223", 0 }, + { "axp803", 0 }, + { "axp806", 0 }, ++ { "axp15060", 0 }, + { }, + }; + MODULE_DEVICE_TABLE(i2c, axp20x_i2c_id); +--- a/drivers/mfd/axp20x.c ++++ b/drivers/mfd/axp20x.c +@@ -43,6 +43,7 @@ static const char * const axp20x_model_n + "AXP806", + "AXP809", + "AXP813", ++ "AXP15060", + }; + + static const struct regmap_range axp152_writeable_ranges[] = { +@@ -169,6 +170,31 @@ static const struct regmap_access_table + .n_yes_ranges = ARRAY_SIZE(axp806_volatile_ranges), + }; + ++static const struct regmap_range axp15060_writeable_ranges[] = { ++ regmap_reg_range(AXP15060_PWR_OUT_CTRL1, AXP15060_DCDC_MODE_CTRL2), ++ regmap_reg_range(AXP15060_OUTPUT_MONITOR_DISCHARGE, AXP15060_CPUSLDO_V_CTRL), ++ regmap_reg_range(AXP15060_PWR_WAKEUP_CTRL, AXP15060_PWR_DISABLE_DOWN_SEQ), ++ regmap_reg_range(AXP15060_PEK_KEY, AXP15060_PEK_KEY), ++ regmap_reg_range(AXP15060_IRQ1_EN, AXP15060_IRQ2_EN), ++ regmap_reg_range(AXP15060_IRQ1_STATE, AXP15060_IRQ2_STATE), ++}; ++ ++static const struct regmap_range axp15060_volatile_ranges[] = { ++ regmap_reg_range(AXP15060_STARTUP_SRC, AXP15060_STARTUP_SRC), ++ regmap_reg_range(AXP15060_PWR_WAKEUP_CTRL, AXP15060_PWR_DISABLE_DOWN_SEQ), ++ regmap_reg_range(AXP15060_IRQ1_STATE, AXP15060_IRQ2_STATE), ++}; ++ ++static const struct regmap_access_table axp15060_writeable_table = { ++ .yes_ranges = axp15060_writeable_ranges, ++ .n_yes_ranges = ARRAY_SIZE(axp15060_writeable_ranges), ++}; ++ ++static const struct regmap_access_table axp15060_volatile_table = { ++ .yes_ranges = axp15060_volatile_ranges, ++ .n_yes_ranges = ARRAY_SIZE(axp15060_volatile_ranges), ++}; ++ + static const struct resource axp152_pek_resources[] = { + DEFINE_RES_IRQ_NAMED(AXP152_IRQ_PEK_RIS_EDGE, "PEK_DBR"), + DEFINE_RES_IRQ_NAMED(AXP152_IRQ_PEK_FAL_EDGE, "PEK_DBF"), +@@ -237,6 +263,11 @@ static const struct resource axp809_pek_ + DEFINE_RES_IRQ_NAMED(AXP809_IRQ_PEK_FAL_EDGE, "PEK_DBF"), + }; + ++static const struct resource axp15060_pek_resources[] = { ++ DEFINE_RES_IRQ_NAMED(AXP15060_IRQ_PEK_RIS_EDGE, "PEK_DBR"), ++ DEFINE_RES_IRQ_NAMED(AXP15060_IRQ_PEK_FAL_EDGE, "PEK_DBF"), ++}; ++ + static const struct regmap_config axp152_regmap_config = { + .reg_bits = 8, + .val_bits = 8, +@@ -282,6 +313,15 @@ static const struct regmap_config axp806 + .cache_type = REGCACHE_RBTREE, + }; + ++static const struct regmap_config axp15060_regmap_config = { ++ .reg_bits = 8, ++ .val_bits = 8, ++ .wr_table = &axp15060_writeable_table, ++ .volatile_table = &axp15060_volatile_table, ++ .max_register = AXP15060_IRQ2_STATE, ++ .cache_type = REGCACHE_RBTREE, ++}; ++ + #define INIT_REGMAP_IRQ(_variant, _irq, _off, _mask) \ + [_variant##_IRQ_##_irq] = { .reg_offset = (_off), .mask = BIT(_mask) } + +@@ -503,6 +543,23 @@ static const struct regmap_irq axp809_re + INIT_REGMAP_IRQ(AXP809, GPIO0_INPUT, 4, 0), + }; + ++static const struct regmap_irq axp15060_regmap_irqs[] = { ++ INIT_REGMAP_IRQ(AXP15060, DIE_TEMP_HIGH_LV1, 0, 0), ++ INIT_REGMAP_IRQ(AXP15060, DIE_TEMP_HIGH_LV2, 0, 1), ++ INIT_REGMAP_IRQ(AXP15060, DCDC1_V_LOW, 0, 2), ++ INIT_REGMAP_IRQ(AXP15060, DCDC2_V_LOW, 0, 3), ++ INIT_REGMAP_IRQ(AXP15060, DCDC3_V_LOW, 0, 4), ++ INIT_REGMAP_IRQ(AXP15060, DCDC4_V_LOW, 0, 5), ++ INIT_REGMAP_IRQ(AXP15060, DCDC5_V_LOW, 0, 6), ++ INIT_REGMAP_IRQ(AXP15060, DCDC6_V_LOW, 0, 7), ++ INIT_REGMAP_IRQ(AXP15060, PEK_LONG, 1, 0), ++ INIT_REGMAP_IRQ(AXP15060, PEK_SHORT, 1, 1), ++ INIT_REGMAP_IRQ(AXP15060, GPIO1_INPUT, 1, 2), ++ INIT_REGMAP_IRQ(AXP15060, PEK_FAL_EDGE, 1, 3), ++ INIT_REGMAP_IRQ(AXP15060, PEK_RIS_EDGE, 1, 4), ++ INIT_REGMAP_IRQ(AXP15060, GPIO2_INPUT, 1, 5), ++}; ++ + static const struct regmap_irq_chip axp152_regmap_irq_chip = { + .name = "axp152_irq_chip", + .status_base = AXP152_IRQ1_STATE, +@@ -589,6 +646,17 @@ static const struct regmap_irq_chip axp8 + .num_regs = 5, + }; + ++static const struct regmap_irq_chip axp15060_regmap_irq_chip = { ++ .name = "axp15060", ++ .status_base = AXP15060_IRQ1_STATE, ++ .ack_base = AXP15060_IRQ1_STATE, ++ .unmask_base = AXP15060_IRQ1_EN, ++ .init_ack_masked = true, ++ .irqs = axp15060_regmap_irqs, ++ .num_irqs = ARRAY_SIZE(axp15060_regmap_irqs), ++ .num_regs = 2, ++}; ++ + static const struct mfd_cell axp20x_cells[] = { + { + .name = "axp20x-gpio", +@@ -833,6 +901,23 @@ static const struct mfd_cell axp813_cell + }, + }; + ++static const struct mfd_cell axp15060_cells[] = { ++ { ++ .name = "axp221-pek", ++ .num_resources = ARRAY_SIZE(axp15060_pek_resources), ++ .resources = axp15060_pek_resources, ++ }, { ++ .name = "axp20x-regulator", ++ }, ++}; ++ ++/* For boards that don't have IRQ line connected to SOC. */ ++static const struct mfd_cell axp_regulator_only_cells[] = { ++ { ++ .name = "axp20x-regulator", ++ }, ++}; ++ + static int axp20x_power_off(struct sys_off_data *data) + { + struct axp20x_dev *axp20x = data->cb_data; +@@ -942,6 +1027,28 @@ int axp20x_match_device(struct axp20x_de + */ + axp20x->regmap_irq_chip = &axp803_regmap_irq_chip; + break; ++ case AXP15060_ID: ++ /* ++ * Don't register the power key part if there is no interrupt ++ * line. ++ * ++ * Since most use cases of AXP PMICs are Allwinner SOCs, board ++ * designers follow Allwinner's reference design and connects ++ * IRQ line to SOC, there's no need for those variants to deal ++ * with cases that IRQ isn't connected. However, AXP15660 is ++ * used by some other vendors' SOCs that didn't connect IRQ ++ * line, we need to deal with this case. ++ */ ++ if (axp20x->irq > 0) { ++ axp20x->nr_cells = ARRAY_SIZE(axp15060_cells); ++ axp20x->cells = axp15060_cells; ++ } else { ++ axp20x->nr_cells = ARRAY_SIZE(axp_regulator_only_cells); ++ axp20x->cells = axp_regulator_only_cells; ++ } ++ axp20x->regmap_cfg = &axp15060_regmap_config; ++ axp20x->regmap_irq_chip = &axp15060_regmap_irq_chip; ++ break; + default: + dev_err(dev, "unsupported AXP20X ID %lu\n", axp20x->variant); + return -EINVAL; +--- a/include/linux/mfd/axp20x.h ++++ b/include/linux/mfd/axp20x.h +@@ -21,6 +21,7 @@ enum axp20x_variants { + AXP806_ID, + AXP809_ID, + AXP813_ID, ++ AXP15060_ID, + NR_AXP20X_VARIANTS, + }; + +@@ -131,6 +132,39 @@ enum axp20x_variants { + /* Other DCDC regulator control registers are the same as AXP803 */ + #define AXP813_DCDC7_V_OUT 0x26 + ++#define AXP15060_STARTUP_SRC 0x00 ++#define AXP15060_PWR_OUT_CTRL1 0x10 ++#define AXP15060_PWR_OUT_CTRL2 0x11 ++#define AXP15060_PWR_OUT_CTRL3 0x12 ++#define AXP15060_DCDC1_V_CTRL 0x13 ++#define AXP15060_DCDC2_V_CTRL 0x14 ++#define AXP15060_DCDC3_V_CTRL 0x15 ++#define AXP15060_DCDC4_V_CTRL 0x16 ++#define AXP15060_DCDC5_V_CTRL 0x17 ++#define AXP15060_DCDC6_V_CTRL 0x18 ++#define AXP15060_ALDO1_V_CTRL 0x19 ++#define AXP15060_DCDC_MODE_CTRL1 0x1a ++#define AXP15060_DCDC_MODE_CTRL2 0x1b ++#define AXP15060_OUTPUT_MONITOR_DISCHARGE 0x1e ++#define AXP15060_IRQ_PWROK_VOFF 0x1f ++#define AXP15060_ALDO2_V_CTRL 0x20 ++#define AXP15060_ALDO3_V_CTRL 0x21 ++#define AXP15060_ALDO4_V_CTRL 0x22 ++#define AXP15060_ALDO5_V_CTRL 0x23 ++#define AXP15060_BLDO1_V_CTRL 0x24 ++#define AXP15060_BLDO2_V_CTRL 0x25 ++#define AXP15060_BLDO3_V_CTRL 0x26 ++#define AXP15060_BLDO4_V_CTRL 0x27 ++#define AXP15060_BLDO5_V_CTRL 0x28 ++#define AXP15060_CLDO1_V_CTRL 0x29 ++#define AXP15060_CLDO2_V_CTRL 0x2a ++#define AXP15060_CLDO3_V_CTRL 0x2b ++#define AXP15060_CLDO4_V_CTRL 0x2d ++#define AXP15060_CPUSLDO_V_CTRL 0x2e ++#define AXP15060_PWR_WAKEUP_CTRL 0x31 ++#define AXP15060_PWR_DISABLE_DOWN_SEQ 0x32 ++#define AXP15060_PEK_KEY 0x36 ++ + /* Interrupt */ + #define AXP152_IRQ1_EN 0x40 + #define AXP152_IRQ2_EN 0x41 +@@ -152,6 +186,11 @@ enum axp20x_variants { + #define AXP20X_IRQ5_STATE 0x4c + #define AXP20X_IRQ6_STATE 0x4d + ++#define AXP15060_IRQ1_EN 0x40 ++#define AXP15060_IRQ2_EN 0x41 ++#define AXP15060_IRQ1_STATE 0x48 ++#define AXP15060_IRQ2_STATE 0x49 ++ + /* ADC */ + #define AXP20X_ACIN_V_ADC_H 0x56 + #define AXP20X_ACIN_V_ADC_L 0x57 +@@ -222,6 +261,8 @@ enum axp20x_variants { + #define AXP22X_GPIO_STATE 0x94 + #define AXP22X_GPIO_PULL_DOWN 0x95 + ++#define AXP15060_CLDO4_GPIO2_MODESET 0x2c ++ + /* Battery */ + #define AXP20X_CHRG_CC_31_24 0xb0 + #define AXP20X_CHRG_CC_23_16 0xb1 +@@ -419,6 +460,33 @@ enum { + AXP813_REG_ID_MAX, + }; + ++enum { ++ AXP15060_DCDC1 = 0, ++ AXP15060_DCDC2, ++ AXP15060_DCDC3, ++ AXP15060_DCDC4, ++ AXP15060_DCDC5, ++ AXP15060_DCDC6, ++ AXP15060_ALDO1, ++ AXP15060_ALDO2, ++ AXP15060_ALDO3, ++ AXP15060_ALDO4, ++ AXP15060_ALDO5, ++ AXP15060_BLDO1, ++ AXP15060_BLDO2, ++ AXP15060_BLDO3, ++ AXP15060_BLDO4, ++ AXP15060_BLDO5, ++ AXP15060_CLDO1, ++ AXP15060_CLDO2, ++ AXP15060_CLDO3, ++ AXP15060_CLDO4, ++ AXP15060_CPUSLDO, ++ AXP15060_SW, ++ AXP15060_RTC_LDO, ++ AXP15060_REG_ID_MAX, ++}; ++ + /* IRQs */ + enum { + AXP152_IRQ_LDO0IN_CONNECT = 1, +@@ -637,6 +705,23 @@ enum axp809_irqs { + AXP809_IRQ_GPIO0_INPUT, + }; + ++enum axp15060_irqs { ++ AXP15060_IRQ_DIE_TEMP_HIGH_LV1 = 1, ++ AXP15060_IRQ_DIE_TEMP_HIGH_LV2, ++ AXP15060_IRQ_DCDC1_V_LOW, ++ AXP15060_IRQ_DCDC2_V_LOW, ++ AXP15060_IRQ_DCDC3_V_LOW, ++ AXP15060_IRQ_DCDC4_V_LOW, ++ AXP15060_IRQ_DCDC5_V_LOW, ++ AXP15060_IRQ_DCDC6_V_LOW, ++ AXP15060_IRQ_PEK_LONG, ++ AXP15060_IRQ_PEK_SHORT, ++ AXP15060_IRQ_GPIO1_INPUT, ++ AXP15060_IRQ_PEK_FAL_EDGE, ++ AXP15060_IRQ_PEK_RIS_EDGE, ++ AXP15060_IRQ_GPIO2_INPUT, ++}; ++ + struct axp20x_dev { + struct device *dev; + int irq; diff --git a/target/linux/generic/backport-6.1/884-v6.5-mfd-axp20x-Add-support-for-AXP313a-PMIC.patch b/target/linux/generic/backport-6.1/884-v6.5-mfd-axp20x-Add-support-for-AXP313a-PMIC.patch new file mode 100644 index 00000000000..c9470eacec7 --- /dev/null +++ b/target/linux/generic/backport-6.1/884-v6.5-mfd-axp20x-Add-support-for-AXP313a-PMIC.patch @@ -0,0 +1,256 @@ +From 75c8cb2f4cb218aaf4ea68cab08d6dbc96eeae15 Mon Sep 17 00:00:00 2001 +From: Martin Botka +Date: Wed, 24 May 2023 01:00:10 +0100 +Subject: [PATCH] mfd: axp20x: Add support for AXP313a PMIC + +The AXP313a is a PMIC chip produced by X-Powers, it can be connected via +an I2C bus. +The name AXP1530 seems to appear as well, and this is what is used in +the BSP driver. From all we know it's the same chip, just a different +name. However we have only seen AXP313a chips in the wild, so go with +this name. + +Compared to the other AXP PMICs it's a rather simple affair: just three +DCDC converters, three LDOs, and no battery charging support. + +Describe the regmap and the MFD bits, along with the registers exposed +via I2C. Aside from the various regulators, also describe the power key +interrupts, and adjust the shutdown handler routine to use a different +register than the other PMICs. +Eventually advertise the device using the new compatible string. + +Signed-off-by: Martin Botka +Signed-off-by: Andre Przywara +Reviewed-by: Chen-Yu Tsai +Link: https://lore.kernel.org/r/20230524000012.15028-2-andre.przywara@arm.com +Signed-off-by: Lee Jones +--- + drivers/mfd/axp20x-i2c.c | 2 + + drivers/mfd/axp20x.c | 78 +++++++++++++++++++++++++++++++++++++- + include/linux/mfd/axp20x.h | 32 ++++++++++++++++ + 3 files changed, 111 insertions(+), 1 deletion(-) + +--- a/drivers/mfd/axp20x-i2c.c ++++ b/drivers/mfd/axp20x-i2c.c +@@ -64,6 +64,7 @@ static const struct of_device_id axp20x_ + { .compatible = "x-powers,axp209", .data = (void *)AXP209_ID }, + { .compatible = "x-powers,axp221", .data = (void *)AXP221_ID }, + { .compatible = "x-powers,axp223", .data = (void *)AXP223_ID }, ++ { .compatible = "x-powers,axp313a", .data = (void *)AXP313A_ID }, + { .compatible = "x-powers,axp803", .data = (void *)AXP803_ID }, + { .compatible = "x-powers,axp806", .data = (void *)AXP806_ID }, + { .compatible = "x-powers,axp15060", .data = (void *)AXP15060_ID }, +@@ -78,6 +79,7 @@ static const struct i2c_device_id axp20x + { "axp209", 0 }, + { "axp221", 0 }, + { "axp223", 0 }, ++ { "axp313a", 0 }, + { "axp803", 0 }, + { "axp806", 0 }, + { "axp15060", 0 }, +--- a/drivers/mfd/axp20x.c ++++ b/drivers/mfd/axp20x.c +@@ -39,6 +39,7 @@ static const char * const axp20x_model_n + "AXP221", + "AXP223", + "AXP288", ++ "AXP313a", + "AXP803", + "AXP806", + "AXP809", +@@ -156,6 +157,25 @@ static const struct regmap_range axp806_ + regmap_reg_range(AXP806_REG_ADDR_EXT, AXP806_REG_ADDR_EXT), + }; + ++static const struct regmap_range axp313a_writeable_ranges[] = { ++ regmap_reg_range(AXP313A_ON_INDICATE, AXP313A_IRQ_STATE), ++}; ++ ++static const struct regmap_range axp313a_volatile_ranges[] = { ++ regmap_reg_range(AXP313A_SHUTDOWN_CTRL, AXP313A_SHUTDOWN_CTRL), ++ regmap_reg_range(AXP313A_IRQ_STATE, AXP313A_IRQ_STATE), ++}; ++ ++static const struct regmap_access_table axp313a_writeable_table = { ++ .yes_ranges = axp313a_writeable_ranges, ++ .n_yes_ranges = ARRAY_SIZE(axp313a_writeable_ranges), ++}; ++ ++static const struct regmap_access_table axp313a_volatile_table = { ++ .yes_ranges = axp313a_volatile_ranges, ++ .n_yes_ranges = ARRAY_SIZE(axp313a_volatile_ranges), ++}; ++ + static const struct regmap_range axp806_volatile_ranges[] = { + regmap_reg_range(AXP20X_IRQ1_STATE, AXP20X_IRQ2_STATE), + }; +@@ -248,6 +268,11 @@ static const struct resource axp288_fuel + DEFINE_RES_IRQ(AXP288_IRQ_WL1), + }; + ++static const struct resource axp313a_pek_resources[] = { ++ DEFINE_RES_IRQ_NAMED(AXP313A_IRQ_PEK_RIS_EDGE, "PEK_DBR"), ++ DEFINE_RES_IRQ_NAMED(AXP313A_IRQ_PEK_FAL_EDGE, "PEK_DBF"), ++}; ++ + static const struct resource axp803_pek_resources[] = { + DEFINE_RES_IRQ_NAMED(AXP803_IRQ_PEK_RIS_EDGE, "PEK_DBR"), + DEFINE_RES_IRQ_NAMED(AXP803_IRQ_PEK_FAL_EDGE, "PEK_DBF"), +@@ -304,6 +329,15 @@ static const struct regmap_config axp288 + .cache_type = REGCACHE_RBTREE, + }; + ++static const struct regmap_config axp313a_regmap_config = { ++ .reg_bits = 8, ++ .val_bits = 8, ++ .wr_table = &axp313a_writeable_table, ++ .volatile_table = &axp313a_volatile_table, ++ .max_register = AXP313A_IRQ_STATE, ++ .cache_type = REGCACHE_RBTREE, ++}; ++ + static const struct regmap_config axp806_regmap_config = { + .reg_bits = 8, + .val_bits = 8, +@@ -456,6 +490,16 @@ static const struct regmap_irq axp288_re + INIT_REGMAP_IRQ(AXP288, BC_USB_CHNG, 5, 1), + }; + ++static const struct regmap_irq axp313a_regmap_irqs[] = { ++ INIT_REGMAP_IRQ(AXP313A, PEK_RIS_EDGE, 0, 7), ++ INIT_REGMAP_IRQ(AXP313A, PEK_FAL_EDGE, 0, 6), ++ INIT_REGMAP_IRQ(AXP313A, PEK_SHORT, 0, 5), ++ INIT_REGMAP_IRQ(AXP313A, PEK_LONG, 0, 4), ++ INIT_REGMAP_IRQ(AXP313A, DCDC3_V_LOW, 0, 3), ++ INIT_REGMAP_IRQ(AXP313A, DCDC2_V_LOW, 0, 2), ++ INIT_REGMAP_IRQ(AXP313A, DIE_TEMP_HIGH, 0, 0), ++}; ++ + static const struct regmap_irq axp803_regmap_irqs[] = { + INIT_REGMAP_IRQ(AXP803, ACIN_OVER_V, 0, 7), + INIT_REGMAP_IRQ(AXP803, ACIN_PLUGIN, 0, 6), +@@ -610,6 +654,17 @@ static const struct regmap_irq_chip axp2 + + }; + ++static const struct regmap_irq_chip axp313a_regmap_irq_chip = { ++ .name = "axp313a_irq_chip", ++ .status_base = AXP313A_IRQ_STATE, ++ .ack_base = AXP313A_IRQ_STATE, ++ .unmask_base = AXP313A_IRQ_EN, ++ .init_ack_masked = true, ++ .irqs = axp313a_regmap_irqs, ++ .num_irqs = ARRAY_SIZE(axp313a_regmap_irqs), ++ .num_regs = 1, ++}; ++ + static const struct regmap_irq_chip axp803_regmap_irq_chip = { + .name = "axp803", + .status_base = AXP20X_IRQ1_STATE, +@@ -752,6 +807,11 @@ static const struct mfd_cell axp152_cell + }, + }; + ++static struct mfd_cell axp313a_cells[] = { ++ MFD_CELL_NAME("axp20x-regulator"), ++ MFD_CELL_RES("axp313a-pek", axp313a_pek_resources), ++}; ++ + static const struct resource axp288_adc_resources[] = { + DEFINE_RES_IRQ_NAMED(AXP288_IRQ_GPADC, "GPADC"), + }; +@@ -921,8 +981,18 @@ static const struct mfd_cell axp_regulat + static int axp20x_power_off(struct sys_off_data *data) + { + struct axp20x_dev *axp20x = data->cb_data; ++ unsigned int shutdown_reg; + +- regmap_write(axp20x->regmap, AXP20X_OFF_CTRL, AXP20X_OFF); ++ switch (axp20x->variant) { ++ case AXP313A_ID: ++ shutdown_reg = AXP313A_SHUTDOWN_CTRL; ++ break; ++ default: ++ shutdown_reg = AXP20X_OFF_CTRL; ++ break; ++ } ++ ++ regmap_write(axp20x->regmap, shutdown_reg, AXP20X_OFF); + + /* Give capacitors etc. time to drain to avoid kernel panic msg. */ + mdelay(500); +@@ -985,6 +1055,12 @@ int axp20x_match_device(struct axp20x_de + axp20x->regmap_irq_chip = &axp288_regmap_irq_chip; + axp20x->irq_flags = IRQF_TRIGGER_LOW; + break; ++ case AXP313A_ID: ++ axp20x->nr_cells = ARRAY_SIZE(axp313a_cells); ++ axp20x->cells = axp313a_cells; ++ axp20x->regmap_cfg = &axp313a_regmap_config; ++ axp20x->regmap_irq_chip = &axp313a_regmap_irq_chip; ++ break; + case AXP803_ID: + axp20x->nr_cells = ARRAY_SIZE(axp803_cells); + axp20x->cells = axp803_cells; +--- a/include/linux/mfd/axp20x.h ++++ b/include/linux/mfd/axp20x.h +@@ -17,6 +17,7 @@ enum axp20x_variants { + AXP221_ID, + AXP223_ID, + AXP288_ID, ++ AXP313A_ID, + AXP803_ID, + AXP806_ID, + AXP809_ID, +@@ -92,6 +93,17 @@ enum axp20x_variants { + #define AXP22X_ALDO3_V_OUT 0x2a + #define AXP22X_CHRG_CTRL3 0x35 + ++#define AXP313A_ON_INDICATE 0x00 ++#define AXP313A_OUTPUT_CONTROL 0x10 ++#define AXP313A_DCDC1_CONRTOL 0x13 ++#define AXP313A_DCDC2_CONRTOL 0x14 ++#define AXP313A_DCDC3_CONRTOL 0x15 ++#define AXP313A_ALDO1_CONRTOL 0x16 ++#define AXP313A_DLDO1_CONRTOL 0x17 ++#define AXP313A_SHUTDOWN_CTRL 0x1a ++#define AXP313A_IRQ_EN 0x20 ++#define AXP313A_IRQ_STATE 0x21 ++ + #define AXP806_STARTUP_SRC 0x00 + #define AXP806_CHIP_ID 0x03 + #define AXP806_PWR_OUT_CTRL1 0x10 +@@ -364,6 +376,16 @@ enum { + }; + + enum { ++ AXP313A_DCDC1 = 0, ++ AXP313A_DCDC2, ++ AXP313A_DCDC3, ++ AXP313A_ALDO1, ++ AXP313A_DLDO1, ++ AXP313A_RTC_LDO, ++ AXP313A_REG_ID_MAX, ++}; ++ ++enum { + AXP806_DCDCA = 0, + AXP806_DCDCB, + AXP806_DCDCC, +@@ -616,6 +638,16 @@ enum axp288_irqs { + AXP288_IRQ_BC_USB_CHNG, + }; + ++enum axp313a_irqs { ++ AXP313A_IRQ_DIE_TEMP_HIGH, ++ AXP313A_IRQ_DCDC2_V_LOW = 2, ++ AXP313A_IRQ_DCDC3_V_LOW, ++ AXP313A_IRQ_PEK_LONG, ++ AXP313A_IRQ_PEK_SHORT, ++ AXP313A_IRQ_PEK_FAL_EDGE, ++ AXP313A_IRQ_PEK_RIS_EDGE, ++}; ++ + enum axp803_irqs { + AXP803_IRQ_ACIN_OVER_V = 1, + AXP803_IRQ_ACIN_PLUGIN, diff --git a/target/linux/generic/backport-6.1/885-v6.5-regulator-axp20x-Add-support-for-AXP313a-variant.patch b/target/linux/generic/backport-6.1/885-v6.5-regulator-axp20x-Add-support-for-AXP313a-variant.patch new file mode 100644 index 00000000000..91f1b398244 --- /dev/null +++ b/target/linux/generic/backport-6.1/885-v6.5-regulator-axp20x-Add-support-for-AXP313a-variant.patch @@ -0,0 +1,129 @@ +From 60fd7eb89670d2636ac3156881acbd103c6eba6a Mon Sep 17 00:00:00 2001 +From: Martin Botka +Date: Wed, 24 May 2023 01:00:11 +0100 +Subject: [PATCH] regulator: axp20x: Add support for AXP313a variant + +The AXP313a is your typical I2C controlled PMIC, although in a lighter +fashion compared to the other X-Powers PMICs: it has only three DCDC +rails, three LDOs, and no battery charging support. + +The AXP313a datasheet does not describe a register to change the DCDC +switching frequency, and talks of it being fixed at 3 MHz. Check that +the property allowing to change that frequency is absent from the DT, +and bail out otherwise. + +The third LDO, RTCLDO, is fixed, and cannot even be turned on or off, +programmatically. On top of that, its voltage is customisable (either +1.8V or 3.3V), which we cannot describe easily using the existing +regulator wrapper functions. This should be fixed properly, using +regulator-{min,max}-microvolt in the DT, but this requires more changes +to the code. As some other PMICs (AXP2xx, AXP803) seem to paper over the +same problem as well, we follow suit here and pretend it's a fixed 1.8V +regulator. A proper fix can follow later. The BSP code seems to ignore +this regulator altogether. + +Describe the AXP313A's voltage settings and switch registers, how the +voltages are encoded, and connect this to the MFD device via its +regulator ID. + +Signed-off-by: Martin Botka +Signed-off-by: Andre Przywara +Reviewed-by: Chen-Yu Tsai +Reviewed-by: Mark Brown +Tested-by: Shengyu Qu +Link: https://lore.kernel.org/r/20230524000012.15028-3-andre.przywara@arm.com +Signed-off-by: Mark Brown +--- + drivers/regulator/axp20x-regulator.c | 60 ++++++++++++++++++++++++++++ + 1 file changed, 60 insertions(+) + +--- a/drivers/regulator/axp20x-regulator.c ++++ b/drivers/regulator/axp20x-regulator.c +@@ -134,6 +134,11 @@ + #define AXP22X_PWR_OUT_DLDO4_MASK BIT_MASK(6) + #define AXP22X_PWR_OUT_ALDO3_MASK BIT_MASK(7) + ++#define AXP313A_DCDC1_NUM_VOLTAGES 107 ++#define AXP313A_DCDC23_NUM_VOLTAGES 88 ++#define AXP313A_DCDC_V_OUT_MASK GENMASK(6, 0) ++#define AXP313A_LDO_V_OUT_MASK GENMASK(4, 0) ++ + #define AXP803_PWR_OUT_DCDC1_MASK BIT_MASK(0) + #define AXP803_PWR_OUT_DCDC2_MASK BIT_MASK(1) + #define AXP803_PWR_OUT_DCDC3_MASK BIT_MASK(2) +@@ -638,6 +643,48 @@ static const struct regulator_desc axp22 + .ops = &axp20x_ops_sw, + }; + ++static const struct linear_range axp313a_dcdc1_ranges[] = { ++ REGULATOR_LINEAR_RANGE(500000, 0, 70, 10000), ++ REGULATOR_LINEAR_RANGE(1220000, 71, 87, 20000), ++ REGULATOR_LINEAR_RANGE(1600000, 88, 106, 100000), ++}; ++ ++static const struct linear_range axp313a_dcdc2_ranges[] = { ++ REGULATOR_LINEAR_RANGE(500000, 0, 70, 10000), ++ REGULATOR_LINEAR_RANGE(1220000, 71, 87, 20000), ++}; ++ ++/* ++ * This is deviating from the datasheet. The values here are taken from the ++ * BSP driver and have been confirmed by measurements. ++ */ ++static const struct linear_range axp313a_dcdc3_ranges[] = { ++ REGULATOR_LINEAR_RANGE(500000, 0, 70, 10000), ++ REGULATOR_LINEAR_RANGE(1220000, 71, 102, 20000), ++}; ++ ++static const struct regulator_desc axp313a_regulators[] = { ++ AXP_DESC_RANGES(AXP313A, DCDC1, "dcdc1", "vin1", ++ axp313a_dcdc1_ranges, AXP313A_DCDC1_NUM_VOLTAGES, ++ AXP313A_DCDC1_CONRTOL, AXP313A_DCDC_V_OUT_MASK, ++ AXP313A_OUTPUT_CONTROL, BIT(0)), ++ AXP_DESC_RANGES(AXP313A, DCDC2, "dcdc2", "vin2", ++ axp313a_dcdc2_ranges, AXP313A_DCDC23_NUM_VOLTAGES, ++ AXP313A_DCDC2_CONRTOL, AXP313A_DCDC_V_OUT_MASK, ++ AXP313A_OUTPUT_CONTROL, BIT(1)), ++ AXP_DESC_RANGES(AXP313A, DCDC3, "dcdc3", "vin3", ++ axp313a_dcdc3_ranges, AXP313A_DCDC23_NUM_VOLTAGES, ++ AXP313A_DCDC3_CONRTOL, AXP313A_DCDC_V_OUT_MASK, ++ AXP313A_OUTPUT_CONTROL, BIT(2)), ++ AXP_DESC(AXP313A, ALDO1, "aldo1", "vin1", 500, 3500, 100, ++ AXP313A_ALDO1_CONRTOL, AXP313A_LDO_V_OUT_MASK, ++ AXP313A_OUTPUT_CONTROL, BIT(3)), ++ AXP_DESC(AXP313A, DLDO1, "dldo1", "vin1", 500, 3500, 100, ++ AXP313A_DLDO1_CONRTOL, AXP313A_LDO_V_OUT_MASK, ++ AXP313A_OUTPUT_CONTROL, BIT(4)), ++ AXP_DESC_FIXED(AXP313A, RTC_LDO, "rtc-ldo", "vin1", 1800), ++}; ++ + /* DCDC ranges shared with AXP813 */ + static const struct linear_range axp803_dcdc234_ranges[] = { + REGULATOR_LINEAR_RANGE(500000, +@@ -1040,6 +1087,15 @@ static int axp20x_set_dcdc_freq(struct p + def = 3000; + step = 150; + break; ++ case AXP313A_ID: ++ /* The DCDC PWM frequency seems to be fixed to 3 MHz. */ ++ if (dcdcfreq != 0) { ++ dev_err(&pdev->dev, ++ "DCDC frequency on AXP313a is fixed to 3 MHz.\n"); ++ return -EINVAL; ++ } ++ ++ return 0; + default: + dev_err(&pdev->dev, + "Setting DCDC frequency for unsupported AXP variant\n"); +@@ -1232,6 +1288,10 @@ static int axp20x_regulator_probe(struct + drivevbus = of_property_read_bool(pdev->dev.parent->of_node, + "x-powers,drive-vbus-en"); + break; ++ case AXP313A_ID: ++ regulators = axp313a_regulators; ++ nregulators = AXP313A_REG_ID_MAX; ++ break; + case AXP803_ID: + regulators = axp803_regulators; + nregulators = AXP803_REG_ID_MAX; diff --git a/target/linux/starfive/patches-6.1/0118-driver-regulator-axp20x-Support-AXP15060-variant.patch b/target/linux/generic/backport-6.1/886-v6.5-regulator-axp20x-Add-AXP15060-support.patch similarity index 74% rename from target/linux/starfive/patches-6.1/0118-driver-regulator-axp20x-Support-AXP15060-variant.patch rename to target/linux/generic/backport-6.1/886-v6.5-regulator-axp20x-Add-AXP15060-support.patch index ccb277b3a01..6af09204af2 100644 --- a/target/linux/starfive/patches-6.1/0118-driver-regulator-axp20x-Support-AXP15060-variant.patch +++ b/target/linux/generic/backport-6.1/886-v6.5-regulator-axp20x-Add-AXP15060-support.patch @@ -1,30 +1,35 @@ -From 1b017f3376a5df4a2cd5a120c16723e777fc9a36 Mon Sep 17 00:00:00 2001 -From: "ziv.xu" -Date: Fri, 4 Aug 2023 13:55:23 +0800 -Subject: [PATCH 118/122] driver: regulator: axp20x: Support AXP15060 variant. +From 9e72869d0fe12aba8cd489e485d93912b3f5c248 Mon Sep 17 00:00:00 2001 +From: Shengyu Qu +Date: Wed, 24 May 2023 01:00:12 +0100 +Subject: [PATCH] regulator: axp20x: Add AXP15060 support -Add axp15060 variant support to axp20x +The AXP15060 is a typical I2C-controlled PMIC, seen on multiple boards +with different default register value. Current driver is tested on +Starfive Visionfive 2. -Signed-off-by: ziv.xu +The RTCLDO is fixed, and cannot even be turned on or off. On top of +that, its voltage is customisable (either 1.8V or 3.3V). We pretend it's +a fixed 1.8V regulator since other AXP driver also do like this. Also, +BSP code ignores this regulator and it's not used according to VF2 +schematic. + +Describe the AXP15060's voltage settings and switch registers, how the +voltages are encoded, and connect this to the MFD device via its +regulator ID. + +Signed-off-by: Shengyu Qu +Signed-off-by: Andre Przywara +Reviewed-by: Mark Brown +Tested-by: Shengyu Qu +Link: https://lore.kernel.org/r/20230524000012.15028-4-andre.przywara@arm.com +Signed-off-by: Mark Brown --- - drivers/regulator/axp20x-regulator.c | 291 ++++++++++++++++++++++++++- - 1 file changed, 283 insertions(+), 8 deletions(-) + drivers/regulator/axp20x-regulator.c | 232 +++++++++++++++++++++++++-- + 1 file changed, 223 insertions(+), 9 deletions(-) --- a/drivers/regulator/axp20x-regulator.c +++ b/drivers/regulator/axp20x-regulator.c -@@ -134,6 +134,11 @@ - #define AXP22X_PWR_OUT_DLDO4_MASK BIT_MASK(6) - #define AXP22X_PWR_OUT_ALDO3_MASK BIT_MASK(7) - -+#define AXP313A_DCDC1_NUM_VOLTAGES 107 -+#define AXP313A_DCDC23_NUM_VOLTAGES 88 -+#define AXP313A_DCDC_V_OUT_MASK GENMASK(6, 0) -+#define AXP313A_LDO_V_OUT_MASK GENMASK(4, 0) -+ - #define AXP803_PWR_OUT_DCDC1_MASK BIT_MASK(0) - #define AXP803_PWR_OUT_DCDC2_MASK BIT_MASK(1) - #define AXP803_PWR_OUT_DCDC3_MASK BIT_MASK(2) -@@ -270,6 +275,74 @@ +@@ -275,6 +275,74 @@ #define AXP813_PWR_OUT_DCDC7_MASK BIT_MASK(6) @@ -99,56 +104,7 @@ Signed-off-by: ziv.xu #define AXP_DESC_IO(_family, _id, _match, _supply, _min, _max, _step, _vreg, \ _vmask, _ereg, _emask, _enable_val, _disable_val) \ [_family##_##_id] = { \ -@@ -638,6 +711,48 @@ static const struct regulator_desc axp22 - .ops = &axp20x_ops_sw, - }; - -+static const struct linear_range axp313a_dcdc1_ranges[] = { -+ REGULATOR_LINEAR_RANGE(500000, 0, 70, 10000), -+ REGULATOR_LINEAR_RANGE(1220000, 71, 87, 20000), -+ REGULATOR_LINEAR_RANGE(1600000, 88, 106, 100000), -+}; -+ -+static const struct linear_range axp313a_dcdc2_ranges[] = { -+ REGULATOR_LINEAR_RANGE(500000, 0, 70, 10000), -+ REGULATOR_LINEAR_RANGE(1220000, 71, 87, 20000), -+}; -+ -+/* -+ * This is deviating from the datasheet. The values here are taken from the -+ * BSP driver and have been confirmed by measurements. -+ */ -+static const struct linear_range axp313a_dcdc3_ranges[] = { -+ REGULATOR_LINEAR_RANGE(500000, 0, 70, 10000), -+ REGULATOR_LINEAR_RANGE(1220000, 71, 102, 20000), -+}; -+ -+static const struct regulator_desc axp313a_regulators[] = { -+ AXP_DESC_RANGES(AXP313A, DCDC1, "dcdc1", "vin1", -+ axp313a_dcdc1_ranges, AXP313A_DCDC1_NUM_VOLTAGES, -+ AXP313A_DCDC1_CONRTOL, AXP313A_DCDC_V_OUT_MASK, -+ AXP313A_OUTPUT_CONTROL, BIT(0)), -+ AXP_DESC_RANGES(AXP313A, DCDC2, "dcdc2", "vin2", -+ axp313a_dcdc2_ranges, AXP313A_DCDC23_NUM_VOLTAGES, -+ AXP313A_DCDC2_CONRTOL, AXP313A_DCDC_V_OUT_MASK, -+ AXP313A_OUTPUT_CONTROL, BIT(1)), -+ AXP_DESC_RANGES(AXP313A, DCDC3, "dcdc3", "vin3", -+ axp313a_dcdc3_ranges, AXP313A_DCDC23_NUM_VOLTAGES, -+ AXP313A_DCDC3_CONRTOL, AXP313A_DCDC_V_OUT_MASK, -+ AXP313A_OUTPUT_CONTROL, BIT(2)), -+ AXP_DESC(AXP313A, ALDO1, "aldo1", "vin1", 500, 3500, 100, -+ AXP313A_ALDO1_CONRTOL, AXP313A_LDO_V_OUT_MASK, -+ AXP313A_OUTPUT_CONTROL, BIT(3)), -+ AXP_DESC(AXP313A, DLDO1, "dldo1", "vin1", 500, 3500, 100, -+ AXP313A_DLDO1_CONRTOL, AXP313A_LDO_V_OUT_MASK, -+ AXP313A_OUTPUT_CONTROL, BIT(4)), -+ AXP_DESC_FIXED(AXP313A, RTC_LDO, "rtc-ldo", "vin1", 1800), -+}; -+ - /* DCDC ranges shared with AXP813 */ - static const struct linear_range axp803_dcdc234_ranges[] = { - REGULATOR_LINEAR_RANGE(500000, -@@ -1001,6 +1116,104 @@ static const struct regulator_desc axp81 +@@ -1048,6 +1116,104 @@ static const struct regulator_desc axp81 AXP22X_PWR_OUT_CTRL2, AXP22X_PWR_OUT_DC1SW_MASK), }; @@ -253,24 +209,20 @@ Signed-off-by: ziv.xu static int axp20x_set_dcdc_freq(struct platform_device *pdev, u32 dcdcfreq) { struct axp20x_dev *axp20x = dev_get_drvdata(pdev->dev.parent); -@@ -1040,6 +1253,16 @@ static int axp20x_set_dcdc_freq(struct p - def = 3000; +@@ -1088,10 +1254,11 @@ static int axp20x_set_dcdc_freq(struct p step = 150; break; -+ case AXP313A_ID: + case AXP313A_ID: + case AXP15060_ID: -+ /* The DCDC PWM frequency seems to be fixed to 3 MHz. */ -+ if (dcdcfreq != 0) { -+ dev_err(&pdev->dev, + /* The DCDC PWM frequency seems to be fixed to 3 MHz. */ + if (dcdcfreq != 0) { + dev_err(&pdev->dev, +- "DCDC frequency on AXP313a is fixed to 3 MHz.\n"); + "DCDC frequency on this PMIC is fixed to 3 MHz.\n"); -+ return -EINVAL; -+ } -+ -+ return 0; - default: - dev_err(&pdev->dev, - "Setting DCDC frequency for unsupported AXP variant\n"); -@@ -1145,6 +1368,15 @@ static int axp20x_set_dcdc_workmode(stru + return -EINVAL; + } + +@@ -1201,6 +1368,15 @@ static int axp20x_set_dcdc_workmode(stru workmode <<= id - AXP813_DCDC1; break; @@ -286,7 +238,7 @@ Signed-off-by: ziv.xu default: /* should not happen */ WARN_ON(1); -@@ -1164,7 +1396,7 @@ static bool axp20x_is_polyphase_slave(st +@@ -1220,7 +1396,7 @@ static bool axp20x_is_polyphase_slave(st /* * Currently in our supported AXP variants, only AXP803, AXP806, @@ -295,7 +247,7 @@ Signed-off-by: ziv.xu */ switch (axp20x->variant) { case AXP803_ID: -@@ -1196,6 +1428,17 @@ static bool axp20x_is_polyphase_slave(st +@@ -1252,6 +1428,17 @@ static bool axp20x_is_polyphase_slave(st } break; @@ -313,7 +265,7 @@ Signed-off-by: ziv.xu default: return false; } -@@ -1217,6 +1460,7 @@ static int axp20x_regulator_probe(struct +@@ -1273,6 +1460,7 @@ static int axp20x_regulator_probe(struct u32 workmode; const char *dcdc1_name = axp22x_regulators[AXP22X_DCDC1].name; const char *dcdc5_name = axp22x_regulators[AXP22X_DCDC5].name; @@ -321,18 +273,7 @@ Signed-off-by: ziv.xu bool drivevbus = false; switch (axp20x->variant) { -@@ -1232,6 +1476,10 @@ static int axp20x_regulator_probe(struct - drivevbus = of_property_read_bool(pdev->dev.parent->of_node, - "x-powers,drive-vbus-en"); - break; -+ case AXP313A_ID: -+ regulators = axp313a_regulators; -+ nregulators = AXP313A_REG_ID_MAX; -+ break; - case AXP803_ID: - regulators = axp803_regulators; - nregulators = AXP803_REG_ID_MAX; -@@ -1252,6 +1500,10 @@ static int axp20x_regulator_probe(struct +@@ -1312,6 +1500,10 @@ static int axp20x_regulator_probe(struct drivevbus = of_property_read_bool(pdev->dev.parent->of_node, "x-powers,drive-vbus-en"); break; @@ -343,7 +284,7 @@ Signed-off-by: ziv.xu default: dev_err(&pdev->dev, "Unsupported AXP variant: %ld\n", axp20x->variant); -@@ -1278,8 +1530,9 @@ static int axp20x_regulator_probe(struct +@@ -1338,8 +1530,9 @@ static int axp20x_regulator_probe(struct continue; /* @@ -355,7 +296,7 @@ Signed-off-by: ziv.xu * * We always register the regulators in proper sequence, * so the supply names are correctly read. See the last -@@ -1288,7 +1541,8 @@ static int axp20x_regulator_probe(struct +@@ -1348,7 +1541,8 @@ static int axp20x_regulator_probe(struct */ if ((regulators == axp22x_regulators && i == AXP22X_DC1SW) || (regulators == axp803_regulators && i == AXP803_DC1SW) || @@ -365,7 +306,7 @@ Signed-off-by: ziv.xu new_desc = devm_kzalloc(&pdev->dev, sizeof(*desc), GFP_KERNEL); if (!new_desc) -@@ -1300,7 +1554,8 @@ static int axp20x_regulator_probe(struct +@@ -1360,7 +1554,8 @@ static int axp20x_regulator_probe(struct } if ((regulators == axp22x_regulators && i == AXP22X_DC5LDO) || @@ -375,7 +316,7 @@ Signed-off-by: ziv.xu new_desc = devm_kzalloc(&pdev->dev, sizeof(*desc), GFP_KERNEL); if (!new_desc) -@@ -1311,6 +1566,18 @@ static int axp20x_regulator_probe(struct +@@ -1371,6 +1566,18 @@ static int axp20x_regulator_probe(struct desc = new_desc; } @@ -394,7 +335,7 @@ Signed-off-by: ziv.xu rdev = devm_regulator_register(&pdev->dev, desc, &config); if (IS_ERR(rdev)) { dev_err(&pdev->dev, "Failed to register %s\n", -@@ -1329,19 +1596,26 @@ static int axp20x_regulator_probe(struct +@@ -1389,19 +1596,26 @@ static int axp20x_regulator_probe(struct } /* @@ -424,11 +365,3 @@ Signed-off-by: ziv.xu } if (drivevbus) { -@@ -1364,6 +1638,7 @@ static struct platform_driver axp20x_reg - .probe = axp20x_regulator_probe, - .driver = { - .name = "axp20x-regulator", -+ .probe_type = PROBE_PREFER_ASYNCHRONOUS, - }, - }; - diff --git a/target/linux/generic/backport-6.1/887-v6.5-mfd-axp20x-Add-support-for-AXP192.patch b/target/linux/generic/backport-6.1/887-v6.5-mfd-axp20x-Add-support-for-AXP192.patch new file mode 100644 index 00000000000..d75b4e74534 --- /dev/null +++ b/target/linux/generic/backport-6.1/887-v6.5-mfd-axp20x-Add-support-for-AXP192.patch @@ -0,0 +1,383 @@ +From 63eeabbc9dbddd7381409feccd9082e5ffabfe59 Mon Sep 17 00:00:00 2001 +From: Aidan MacDonald +Date: Thu, 11 May 2023 10:26:08 +0100 +Subject: [PATCH] mfd: axp20x: Add support for AXP192 + +The AXP192 PMIC is similar to the AXP202/AXP209, but with different +regulators, additional GPIOs, and a different IRQ register layout. + +Signed-off-by: Aidan MacDonald +Link: https://lore.kernel.org/r/20230511092609.76183-1-aidanmacdonald.0x0@gmail.com +Signed-off-by: Lee Jones +--- + drivers/mfd/axp20x-i2c.c | 2 + + drivers/mfd/axp20x.c | 141 +++++++++++++++++++++++++++++++++++++ + include/linux/mfd/axp20x.h | 84 ++++++++++++++++++++++ + 3 files changed, 227 insertions(+) + +--- a/drivers/mfd/axp20x-i2c.c ++++ b/drivers/mfd/axp20x-i2c.c +@@ -60,6 +60,7 @@ static void axp20x_i2c_remove(struct i2c + #ifdef CONFIG_OF + static const struct of_device_id axp20x_i2c_of_match[] = { + { .compatible = "x-powers,axp152", .data = (void *)AXP152_ID }, ++ { .compatible = "x-powers,axp192", .data = (void *)AXP192_ID }, + { .compatible = "x-powers,axp202", .data = (void *)AXP202_ID }, + { .compatible = "x-powers,axp209", .data = (void *)AXP209_ID }, + { .compatible = "x-powers,axp221", .data = (void *)AXP221_ID }, +@@ -75,6 +76,7 @@ MODULE_DEVICE_TABLE(of, axp20x_i2c_of_ma + + static const struct i2c_device_id axp20x_i2c_id[] = { + { "axp152", 0 }, ++ { "axp192", 0 }, + { "axp202", 0 }, + { "axp209", 0 }, + { "axp221", 0 }, +--- a/drivers/mfd/axp20x.c ++++ b/drivers/mfd/axp20x.c +@@ -34,6 +34,7 @@ + + static const char * const axp20x_model_names[] = { + "AXP152", ++ "AXP192", + "AXP202", + "AXP209", + "AXP221", +@@ -94,6 +95,35 @@ static const struct regmap_access_table + .n_yes_ranges = ARRAY_SIZE(axp20x_volatile_ranges), + }; + ++static const struct regmap_range axp192_writeable_ranges[] = { ++ regmap_reg_range(AXP192_DATACACHE(0), AXP192_DATACACHE(5)), ++ regmap_reg_range(AXP192_PWR_OUT_CTRL, AXP192_IRQ5_STATE), ++ regmap_reg_range(AXP20X_DCDC_MODE, AXP192_N_RSTO_CTRL), ++ regmap_reg_range(AXP20X_CC_CTRL, AXP20X_CC_CTRL), ++}; ++ ++static const struct regmap_range axp192_volatile_ranges[] = { ++ regmap_reg_range(AXP20X_PWR_INPUT_STATUS, AXP192_USB_OTG_STATUS), ++ regmap_reg_range(AXP192_IRQ1_STATE, AXP192_IRQ4_STATE), ++ regmap_reg_range(AXP192_IRQ5_STATE, AXP192_IRQ5_STATE), ++ regmap_reg_range(AXP20X_ACIN_V_ADC_H, AXP20X_IPSOUT_V_HIGH_L), ++ regmap_reg_range(AXP20X_TIMER_CTRL, AXP20X_TIMER_CTRL), ++ regmap_reg_range(AXP192_GPIO2_0_STATE, AXP192_GPIO2_0_STATE), ++ regmap_reg_range(AXP192_GPIO4_3_STATE, AXP192_GPIO4_3_STATE), ++ regmap_reg_range(AXP192_N_RSTO_CTRL, AXP192_N_RSTO_CTRL), ++ regmap_reg_range(AXP20X_CHRG_CC_31_24, AXP20X_CC_CTRL), ++}; ++ ++static const struct regmap_access_table axp192_writeable_table = { ++ .yes_ranges = axp192_writeable_ranges, ++ .n_yes_ranges = ARRAY_SIZE(axp192_writeable_ranges), ++}; ++ ++static const struct regmap_access_table axp192_volatile_table = { ++ .yes_ranges = axp192_volatile_ranges, ++ .n_yes_ranges = ARRAY_SIZE(axp192_volatile_ranges), ++}; ++ + /* AXP22x ranges are shared with the AXP809, as they cover the same range */ + static const struct regmap_range axp22x_writeable_ranges[] = { + regmap_reg_range(AXP20X_DATACACHE(0), AXP20X_IRQ5_STATE), +@@ -220,6 +250,19 @@ static const struct resource axp152_pek_ + DEFINE_RES_IRQ_NAMED(AXP152_IRQ_PEK_FAL_EDGE, "PEK_DBF"), + }; + ++static const struct resource axp192_ac_power_supply_resources[] = { ++ DEFINE_RES_IRQ_NAMED(AXP192_IRQ_ACIN_PLUGIN, "ACIN_PLUGIN"), ++ DEFINE_RES_IRQ_NAMED(AXP192_IRQ_ACIN_REMOVAL, "ACIN_REMOVAL"), ++ DEFINE_RES_IRQ_NAMED(AXP192_IRQ_ACIN_OVER_V, "ACIN_OVER_V"), ++}; ++ ++static const struct resource axp192_usb_power_supply_resources[] = { ++ DEFINE_RES_IRQ_NAMED(AXP192_IRQ_VBUS_PLUGIN, "VBUS_PLUGIN"), ++ DEFINE_RES_IRQ_NAMED(AXP192_IRQ_VBUS_REMOVAL, "VBUS_REMOVAL"), ++ DEFINE_RES_IRQ_NAMED(AXP192_IRQ_VBUS_VALID, "VBUS_VALID"), ++ DEFINE_RES_IRQ_NAMED(AXP192_IRQ_VBUS_NOT_VALID, "VBUS_NOT_VALID"), ++}; ++ + static const struct resource axp20x_ac_power_supply_resources[] = { + DEFINE_RES_IRQ_NAMED(AXP20X_IRQ_ACIN_PLUGIN, "ACIN_PLUGIN"), + DEFINE_RES_IRQ_NAMED(AXP20X_IRQ_ACIN_REMOVAL, "ACIN_REMOVAL"), +@@ -302,6 +345,15 @@ static const struct regmap_config axp152 + .cache_type = REGCACHE_RBTREE, + }; + ++static const struct regmap_config axp192_regmap_config = { ++ .reg_bits = 8, ++ .val_bits = 8, ++ .wr_table = &axp192_writeable_table, ++ .volatile_table = &axp192_volatile_table, ++ .max_register = AXP20X_CC_CTRL, ++ .cache_type = REGCACHE_RBTREE, ++}; ++ + static const struct regmap_config axp20x_regmap_config = { + .reg_bits = 8, + .val_bits = 8, +@@ -379,6 +431,42 @@ static const struct regmap_irq axp152_re + INIT_REGMAP_IRQ(AXP152, GPIO0_INPUT, 2, 0), + }; + ++static const struct regmap_irq axp192_regmap_irqs[] = { ++ INIT_REGMAP_IRQ(AXP192, ACIN_OVER_V, 0, 7), ++ INIT_REGMAP_IRQ(AXP192, ACIN_PLUGIN, 0, 6), ++ INIT_REGMAP_IRQ(AXP192, ACIN_REMOVAL, 0, 5), ++ INIT_REGMAP_IRQ(AXP192, VBUS_OVER_V, 0, 4), ++ INIT_REGMAP_IRQ(AXP192, VBUS_PLUGIN, 0, 3), ++ INIT_REGMAP_IRQ(AXP192, VBUS_REMOVAL, 0, 2), ++ INIT_REGMAP_IRQ(AXP192, VBUS_V_LOW, 0, 1), ++ INIT_REGMAP_IRQ(AXP192, BATT_PLUGIN, 1, 7), ++ INIT_REGMAP_IRQ(AXP192, BATT_REMOVAL, 1, 6), ++ INIT_REGMAP_IRQ(AXP192, BATT_ENT_ACT_MODE, 1, 5), ++ INIT_REGMAP_IRQ(AXP192, BATT_EXIT_ACT_MODE, 1, 4), ++ INIT_REGMAP_IRQ(AXP192, CHARG, 1, 3), ++ INIT_REGMAP_IRQ(AXP192, CHARG_DONE, 1, 2), ++ INIT_REGMAP_IRQ(AXP192, BATT_TEMP_HIGH, 1, 1), ++ INIT_REGMAP_IRQ(AXP192, BATT_TEMP_LOW, 1, 0), ++ INIT_REGMAP_IRQ(AXP192, DIE_TEMP_HIGH, 2, 7), ++ INIT_REGMAP_IRQ(AXP192, CHARG_I_LOW, 2, 6), ++ INIT_REGMAP_IRQ(AXP192, DCDC1_V_LONG, 2, 5), ++ INIT_REGMAP_IRQ(AXP192, DCDC2_V_LONG, 2, 4), ++ INIT_REGMAP_IRQ(AXP192, DCDC3_V_LONG, 2, 3), ++ INIT_REGMAP_IRQ(AXP192, PEK_SHORT, 2, 1), ++ INIT_REGMAP_IRQ(AXP192, PEK_LONG, 2, 0), ++ INIT_REGMAP_IRQ(AXP192, N_OE_PWR_ON, 3, 7), ++ INIT_REGMAP_IRQ(AXP192, N_OE_PWR_OFF, 3, 6), ++ INIT_REGMAP_IRQ(AXP192, VBUS_VALID, 3, 5), ++ INIT_REGMAP_IRQ(AXP192, VBUS_NOT_VALID, 3, 4), ++ INIT_REGMAP_IRQ(AXP192, VBUS_SESS_VALID, 3, 3), ++ INIT_REGMAP_IRQ(AXP192, VBUS_SESS_END, 3, 2), ++ INIT_REGMAP_IRQ(AXP192, LOW_PWR_LVL, 3, 0), ++ INIT_REGMAP_IRQ(AXP192, TIMER, 4, 7), ++ INIT_REGMAP_IRQ(AXP192, GPIO2_INPUT, 4, 2), ++ INIT_REGMAP_IRQ(AXP192, GPIO1_INPUT, 4, 1), ++ INIT_REGMAP_IRQ(AXP192, GPIO0_INPUT, 4, 0), ++}; ++ + static const struct regmap_irq axp20x_regmap_irqs[] = { + INIT_REGMAP_IRQ(AXP20X, ACIN_OVER_V, 0, 7), + INIT_REGMAP_IRQ(AXP20X, ACIN_PLUGIN, 0, 6), +@@ -616,6 +704,32 @@ static const struct regmap_irq_chip axp1 + .num_regs = 3, + }; + ++static unsigned int axp192_get_irq_reg(struct regmap_irq_chip_data *data, ++ unsigned int base, int index) ++{ ++ /* linear mapping for IRQ1 to IRQ4 */ ++ if (index < 4) ++ return base + index; ++ ++ /* handle IRQ5 separately */ ++ if (base == AXP192_IRQ1_EN) ++ return AXP192_IRQ5_EN; ++ ++ return AXP192_IRQ5_STATE; ++} ++ ++static const struct regmap_irq_chip axp192_regmap_irq_chip = { ++ .name = "axp192_irq_chip", ++ .status_base = AXP192_IRQ1_STATE, ++ .ack_base = AXP192_IRQ1_STATE, ++ .unmask_base = AXP192_IRQ1_EN, ++ .init_ack_masked = true, ++ .irqs = axp192_regmap_irqs, ++ .num_irqs = ARRAY_SIZE(axp192_regmap_irqs), ++ .num_regs = 5, ++ .get_irq_reg = axp192_get_irq_reg, ++}; ++ + static const struct regmap_irq_chip axp20x_regmap_irq_chip = { + .name = "axp20x_irq_chip", + .status_base = AXP20X_IRQ1_STATE, +@@ -712,6 +826,27 @@ static const struct regmap_irq_chip axp1 + .num_regs = 2, + }; + ++static const struct mfd_cell axp192_cells[] = { ++ { ++ .name = "axp192-adc", ++ .of_compatible = "x-powers,axp192-adc", ++ }, { ++ .name = "axp20x-battery-power-supply", ++ .of_compatible = "x-powers,axp192-battery-power-supply", ++ }, { ++ .name = "axp20x-ac-power-supply", ++ .of_compatible = "x-powers,axp202-ac-power-supply", ++ .num_resources = ARRAY_SIZE(axp192_ac_power_supply_resources), ++ .resources = axp192_ac_power_supply_resources, ++ }, { ++ .name = "axp20x-usb-power-supply", ++ .of_compatible = "x-powers,axp192-usb-power-supply", ++ .num_resources = ARRAY_SIZE(axp192_usb_power_supply_resources), ++ .resources = axp192_usb_power_supply_resources, ++ }, ++ { .name = "axp20x-regulator" }, ++}; ++ + static const struct mfd_cell axp20x_cells[] = { + { + .name = "axp20x-gpio", +@@ -1029,6 +1164,12 @@ int axp20x_match_device(struct axp20x_de + axp20x->regmap_cfg = &axp152_regmap_config; + axp20x->regmap_irq_chip = &axp152_regmap_irq_chip; + break; ++ case AXP192_ID: ++ axp20x->nr_cells = ARRAY_SIZE(axp192_cells); ++ axp20x->cells = axp192_cells; ++ axp20x->regmap_cfg = &axp192_regmap_config; ++ axp20x->regmap_irq_chip = &axp192_regmap_irq_chip; ++ break; + case AXP202_ID: + case AXP209_ID: + axp20x->nr_cells = ARRAY_SIZE(axp20x_cells); +--- a/include/linux/mfd/axp20x.h ++++ b/include/linux/mfd/axp20x.h +@@ -12,6 +12,7 @@ + + enum axp20x_variants { + AXP152_ID = 0, ++ AXP192_ID, + AXP202_ID, + AXP209_ID, + AXP221_ID, +@@ -26,6 +27,7 @@ enum axp20x_variants { + NR_AXP20X_VARIANTS, + }; + ++#define AXP192_DATACACHE(m) (0x06 + (m)) + #define AXP20X_DATACACHE(m) (0x04 + (m)) + + /* Power supply */ +@@ -47,6 +49,13 @@ enum axp20x_variants { + #define AXP152_DCDC_FREQ 0x37 + #define AXP152_DCDC_MODE 0x80 + ++#define AXP192_USB_OTG_STATUS 0x04 ++#define AXP192_PWR_OUT_CTRL 0x12 ++#define AXP192_DCDC2_V_OUT 0x23 ++#define AXP192_DCDC1_V_OUT 0x26 ++#define AXP192_DCDC3_V_OUT 0x27 ++#define AXP192_LDO2_3_V_OUT 0x28 ++ + #define AXP20X_PWR_INPUT_STATUS 0x00 + #define AXP20X_PWR_OP_MODE 0x01 + #define AXP20X_USB_OTG_STATUS 0x02 +@@ -185,6 +194,17 @@ enum axp20x_variants { + #define AXP152_IRQ2_STATE 0x49 + #define AXP152_IRQ3_STATE 0x4a + ++#define AXP192_IRQ1_EN 0x40 ++#define AXP192_IRQ2_EN 0x41 ++#define AXP192_IRQ3_EN 0x42 ++#define AXP192_IRQ4_EN 0x43 ++#define AXP192_IRQ1_STATE 0x44 ++#define AXP192_IRQ2_STATE 0x45 ++#define AXP192_IRQ3_STATE 0x46 ++#define AXP192_IRQ4_STATE 0x47 ++#define AXP192_IRQ5_EN 0x4a ++#define AXP192_IRQ5_STATE 0x4d ++ + #define AXP20X_IRQ1_EN 0x40 + #define AXP20X_IRQ2_EN 0x41 + #define AXP20X_IRQ3_EN 0x42 +@@ -204,6 +224,11 @@ enum axp20x_variants { + #define AXP15060_IRQ2_STATE 0x49 + + /* ADC */ ++#define AXP192_GPIO2_V_ADC_H 0x68 ++#define AXP192_GPIO2_V_ADC_L 0x69 ++#define AXP192_GPIO3_V_ADC_H 0x6a ++#define AXP192_GPIO3_V_ADC_L 0x6b ++ + #define AXP20X_ACIN_V_ADC_H 0x56 + #define AXP20X_ACIN_V_ADC_L 0x57 + #define AXP20X_ACIN_I_ADC_H 0x58 +@@ -233,6 +258,8 @@ enum axp20x_variants { + #define AXP20X_IPSOUT_V_HIGH_L 0x7f + + /* Power supply */ ++#define AXP192_GPIO30_IN_RANGE 0x85 ++ + #define AXP20X_DCDC_MODE 0x80 + #define AXP20X_ADC_EN1 0x82 + #define AXP20X_ADC_EN2 0x83 +@@ -261,6 +288,16 @@ enum axp20x_variants { + #define AXP152_PWM1_FREQ_Y 0x9c + #define AXP152_PWM1_DUTY_CYCLE 0x9d + ++#define AXP192_GPIO0_CTRL 0x90 ++#define AXP192_LDO_IO0_V_OUT 0x91 ++#define AXP192_GPIO1_CTRL 0x92 ++#define AXP192_GPIO2_CTRL 0x93 ++#define AXP192_GPIO2_0_STATE 0x94 ++#define AXP192_GPIO4_3_CTRL 0x95 ++#define AXP192_GPIO4_3_STATE 0x96 ++#define AXP192_GPIO2_0_PULL 0x97 ++#define AXP192_N_RSTO_CTRL 0x9e ++ + #define AXP20X_GPIO0_CTRL 0x90 + #define AXP20X_LDO5_V_OUT 0x91 + #define AXP20X_GPIO1_CTRL 0x92 +@@ -341,6 +378,17 @@ enum axp20x_variants { + + /* Regulators IDs */ + enum { ++ AXP192_DCDC1 = 0, ++ AXP192_DCDC2, ++ AXP192_DCDC3, ++ AXP192_LDO1, ++ AXP192_LDO2, ++ AXP192_LDO3, ++ AXP192_LDO_IO0, ++ AXP192_REG_ID_MAX ++}; ++ ++enum { + AXP20X_LDO1 = 0, + AXP20X_LDO2, + AXP20X_LDO3, +@@ -531,6 +579,42 @@ enum { + AXP152_IRQ_GPIO0_INPUT, + }; + ++enum axp192_irqs { ++ AXP192_IRQ_ACIN_OVER_V = 1, ++ AXP192_IRQ_ACIN_PLUGIN, ++ AXP192_IRQ_ACIN_REMOVAL, ++ AXP192_IRQ_VBUS_OVER_V, ++ AXP192_IRQ_VBUS_PLUGIN, ++ AXP192_IRQ_VBUS_REMOVAL, ++ AXP192_IRQ_VBUS_V_LOW, ++ AXP192_IRQ_BATT_PLUGIN, ++ AXP192_IRQ_BATT_REMOVAL, ++ AXP192_IRQ_BATT_ENT_ACT_MODE, ++ AXP192_IRQ_BATT_EXIT_ACT_MODE, ++ AXP192_IRQ_CHARG, ++ AXP192_IRQ_CHARG_DONE, ++ AXP192_IRQ_BATT_TEMP_HIGH, ++ AXP192_IRQ_BATT_TEMP_LOW, ++ AXP192_IRQ_DIE_TEMP_HIGH, ++ AXP192_IRQ_CHARG_I_LOW, ++ AXP192_IRQ_DCDC1_V_LONG, ++ AXP192_IRQ_DCDC2_V_LONG, ++ AXP192_IRQ_DCDC3_V_LONG, ++ AXP192_IRQ_PEK_SHORT = 22, ++ AXP192_IRQ_PEK_LONG, ++ AXP192_IRQ_N_OE_PWR_ON, ++ AXP192_IRQ_N_OE_PWR_OFF, ++ AXP192_IRQ_VBUS_VALID, ++ AXP192_IRQ_VBUS_NOT_VALID, ++ AXP192_IRQ_VBUS_SESS_VALID, ++ AXP192_IRQ_VBUS_SESS_END, ++ AXP192_IRQ_LOW_PWR_LVL = 31, ++ AXP192_IRQ_TIMER, ++ AXP192_IRQ_GPIO2_INPUT = 37, ++ AXP192_IRQ_GPIO1_INPUT, ++ AXP192_IRQ_GPIO0_INPUT, ++}; ++ + enum { + AXP20X_IRQ_ACIN_OVER_V = 1, + AXP20X_IRQ_ACIN_PLUGIN, diff --git a/target/linux/starfive/patches-6.1/0117-driver-mfd-axp20x-Add-support-for-AXP15060.patch b/target/linux/starfive/patches-6.1/0117-driver-mfd-axp20x-Add-support-for-AXP15060.patch deleted file mode 100644 index 18ad298065f..00000000000 --- a/target/linux/starfive/patches-6.1/0117-driver-mfd-axp20x-Add-support-for-AXP15060.patch +++ /dev/null @@ -1,1014 +0,0 @@ -From e62161318f2fe3e396fc31c50d210e99bec83021 Mon Sep 17 00:00:00 2001 -From: "ziv.xu" -Date: Fri, 4 Aug 2023 13:53:10 +0800 -Subject: [PATCH 117/122] driver: mfd: axp20x: Add support for AXP15060 - -axp20x add support for AXP15060 - -Signed-off-by: ziv.xu ---- - drivers/mfd/axp20x-i2c.c | 2 + - drivers/mfd/axp20x.c | 373 ++++++++++++++++++++++++++++++++++--- - include/linux/mfd/axp20x.h | 218 +++++++++++++++++++++- - 3 files changed, 557 insertions(+), 36 deletions(-) - ---- a/drivers/mfd/axp20x-i2c.c -+++ b/drivers/mfd/axp20x-i2c.c -@@ -66,6 +66,7 @@ static const struct of_device_id axp20x_ - { .compatible = "x-powers,axp223", .data = (void *)AXP223_ID }, - { .compatible = "x-powers,axp803", .data = (void *)AXP803_ID }, - { .compatible = "x-powers,axp806", .data = (void *)AXP806_ID }, -+ { .compatible = "x-powers,axp15060", .data = (void *)AXP15060_ID }, - { }, - }; - MODULE_DEVICE_TABLE(of, axp20x_i2c_of_match); -@@ -79,6 +80,7 @@ static const struct i2c_device_id axp20x - { "axp223", 0 }, - { "axp803", 0 }, - { "axp806", 0 }, -+ { "axp15060", 0 }, - { }, - }; - MODULE_DEVICE_TABLE(i2c, axp20x_i2c_id); ---- a/drivers/mfd/axp20x.c -+++ b/drivers/mfd/axp20x.c -@@ -23,7 +23,7 @@ - #include - #include - #include --#include -+#include - #include - #include - -@@ -34,15 +34,18 @@ - - static const char * const axp20x_model_names[] = { - "AXP152", -+ "AXP192", - "AXP202", - "AXP209", - "AXP221", - "AXP223", - "AXP288", -+ "AXP313a", - "AXP803", - "AXP806", - "AXP809", - "AXP813", -+ "AXP15060", - }; - - static const struct regmap_range axp152_writeable_ranges[] = { -@@ -92,6 +95,35 @@ static const struct regmap_access_table - .n_yes_ranges = ARRAY_SIZE(axp20x_volatile_ranges), - }; - -+static const struct regmap_range axp192_writeable_ranges[] = { -+ regmap_reg_range(AXP192_DATACACHE(0), AXP192_DATACACHE(5)), -+ regmap_reg_range(AXP192_PWR_OUT_CTRL, AXP192_IRQ5_STATE), -+ regmap_reg_range(AXP20X_DCDC_MODE, AXP192_N_RSTO_CTRL), -+ regmap_reg_range(AXP20X_CC_CTRL, AXP20X_CC_CTRL), -+}; -+ -+static const struct regmap_range axp192_volatile_ranges[] = { -+ regmap_reg_range(AXP20X_PWR_INPUT_STATUS, AXP192_USB_OTG_STATUS), -+ regmap_reg_range(AXP192_IRQ1_STATE, AXP192_IRQ4_STATE), -+ regmap_reg_range(AXP192_IRQ5_STATE, AXP192_IRQ5_STATE), -+ regmap_reg_range(AXP20X_ACIN_V_ADC_H, AXP20X_IPSOUT_V_HIGH_L), -+ regmap_reg_range(AXP20X_TIMER_CTRL, AXP20X_TIMER_CTRL), -+ regmap_reg_range(AXP192_GPIO2_0_STATE, AXP192_GPIO2_0_STATE), -+ regmap_reg_range(AXP192_GPIO4_3_STATE, AXP192_GPIO4_3_STATE), -+ regmap_reg_range(AXP192_N_RSTO_CTRL, AXP192_N_RSTO_CTRL), -+ regmap_reg_range(AXP20X_CHRG_CC_31_24, AXP20X_CC_CTRL), -+}; -+ -+static const struct regmap_access_table axp192_writeable_table = { -+ .yes_ranges = axp192_writeable_ranges, -+ .n_yes_ranges = ARRAY_SIZE(axp192_writeable_ranges), -+}; -+ -+static const struct regmap_access_table axp192_volatile_table = { -+ .yes_ranges = axp192_volatile_ranges, -+ .n_yes_ranges = ARRAY_SIZE(axp192_volatile_ranges), -+}; -+ - /* AXP22x ranges are shared with the AXP809, as they cover the same range */ - static const struct regmap_range axp22x_writeable_ranges[] = { - regmap_reg_range(AXP20X_DATACACHE(0), AXP20X_IRQ5_STATE), -@@ -119,6 +151,7 @@ static const struct regmap_access_table - - /* AXP288 ranges are shared with the AXP803, as they cover the same range */ - static const struct regmap_range axp288_writeable_ranges[] = { -+ regmap_reg_range(AXP288_POWER_REASON, AXP288_POWER_REASON), - regmap_reg_range(AXP20X_DATACACHE(0), AXP20X_IRQ6_STATE), - regmap_reg_range(AXP20X_DCDC_MODE, AXP288_FG_TUNE5), - }; -@@ -154,6 +187,25 @@ static const struct regmap_range axp806_ - regmap_reg_range(AXP806_REG_ADDR_EXT, AXP806_REG_ADDR_EXT), - }; - -+static const struct regmap_range axp313a_writeable_ranges[] = { -+ regmap_reg_range(AXP313A_ON_INDICATE, AXP313A_IRQ_STATE), -+}; -+ -+static const struct regmap_range axp313a_volatile_ranges[] = { -+ regmap_reg_range(AXP313A_SHUTDOWN_CTRL, AXP313A_SHUTDOWN_CTRL), -+ regmap_reg_range(AXP313A_IRQ_STATE, AXP313A_IRQ_STATE), -+}; -+ -+static const struct regmap_access_table axp313a_writeable_table = { -+ .yes_ranges = axp313a_writeable_ranges, -+ .n_yes_ranges = ARRAY_SIZE(axp313a_writeable_ranges), -+}; -+ -+static const struct regmap_access_table axp313a_volatile_table = { -+ .yes_ranges = axp313a_volatile_ranges, -+ .n_yes_ranges = ARRAY_SIZE(axp313a_volatile_ranges), -+}; -+ - static const struct regmap_range axp806_volatile_ranges[] = { - regmap_reg_range(AXP20X_IRQ1_STATE, AXP20X_IRQ2_STATE), - }; -@@ -168,11 +220,49 @@ static const struct regmap_access_table - .n_yes_ranges = ARRAY_SIZE(axp806_volatile_ranges), - }; - -+static const struct regmap_range axp15060_writeable_ranges[] = { -+ regmap_reg_range(AXP15060_PWR_OUT_CTRL1, AXP15060_DCDC_MODE_CTRL2), -+ regmap_reg_range(AXP15060_OUTPUT_MONITOR_DISCHARGE, AXP15060_CPUSLDO_V_CTRL), -+ regmap_reg_range(AXP15060_PWR_WAKEUP_CTRL, AXP15060_PWR_DISABLE_DOWN_SEQ), -+ regmap_reg_range(AXP15060_PEK_KEY, AXP15060_PEK_KEY), -+ regmap_reg_range(AXP15060_IRQ1_EN, AXP15060_IRQ2_EN), -+ regmap_reg_range(AXP15060_IRQ1_STATE, AXP15060_IRQ2_STATE), -+}; -+ -+static const struct regmap_range axp15060_volatile_ranges[] = { -+ regmap_reg_range(AXP15060_STARTUP_SRC, AXP15060_STARTUP_SRC), -+ regmap_reg_range(AXP15060_PWR_WAKEUP_CTRL, AXP15060_PWR_DISABLE_DOWN_SEQ), -+ regmap_reg_range(AXP15060_IRQ1_STATE, AXP15060_IRQ2_STATE), -+}; -+ -+static const struct regmap_access_table axp15060_writeable_table = { -+ .yes_ranges = axp15060_writeable_ranges, -+ .n_yes_ranges = ARRAY_SIZE(axp15060_writeable_ranges), -+}; -+ -+static const struct regmap_access_table axp15060_volatile_table = { -+ .yes_ranges = axp15060_volatile_ranges, -+ .n_yes_ranges = ARRAY_SIZE(axp15060_volatile_ranges), -+}; -+ - static const struct resource axp152_pek_resources[] = { - DEFINE_RES_IRQ_NAMED(AXP152_IRQ_PEK_RIS_EDGE, "PEK_DBR"), - DEFINE_RES_IRQ_NAMED(AXP152_IRQ_PEK_FAL_EDGE, "PEK_DBF"), - }; - -+static const struct resource axp192_ac_power_supply_resources[] = { -+ DEFINE_RES_IRQ_NAMED(AXP192_IRQ_ACIN_PLUGIN, "ACIN_PLUGIN"), -+ DEFINE_RES_IRQ_NAMED(AXP192_IRQ_ACIN_REMOVAL, "ACIN_REMOVAL"), -+ DEFINE_RES_IRQ_NAMED(AXP192_IRQ_ACIN_OVER_V, "ACIN_OVER_V"), -+}; -+ -+static const struct resource axp192_usb_power_supply_resources[] = { -+ DEFINE_RES_IRQ_NAMED(AXP192_IRQ_VBUS_PLUGIN, "VBUS_PLUGIN"), -+ DEFINE_RES_IRQ_NAMED(AXP192_IRQ_VBUS_REMOVAL, "VBUS_REMOVAL"), -+ DEFINE_RES_IRQ_NAMED(AXP192_IRQ_VBUS_VALID, "VBUS_VALID"), -+ DEFINE_RES_IRQ_NAMED(AXP192_IRQ_VBUS_NOT_VALID, "VBUS_NOT_VALID"), -+}; -+ - static const struct resource axp20x_ac_power_supply_resources[] = { - DEFINE_RES_IRQ_NAMED(AXP20X_IRQ_ACIN_PLUGIN, "ACIN_PLUGIN"), - DEFINE_RES_IRQ_NAMED(AXP20X_IRQ_ACIN_REMOVAL, "ACIN_REMOVAL"), -@@ -221,6 +311,11 @@ static const struct resource axp288_fuel - DEFINE_RES_IRQ(AXP288_IRQ_WL1), - }; - -+static const struct resource axp313a_pek_resources[] = { -+ DEFINE_RES_IRQ_NAMED(AXP313A_IRQ_PEK_RIS_EDGE, "PEK_DBR"), -+ DEFINE_RES_IRQ_NAMED(AXP313A_IRQ_PEK_FAL_EDGE, "PEK_DBF"), -+}; -+ - static const struct resource axp803_pek_resources[] = { - DEFINE_RES_IRQ_NAMED(AXP803_IRQ_PEK_RIS_EDGE, "PEK_DBR"), - DEFINE_RES_IRQ_NAMED(AXP803_IRQ_PEK_FAL_EDGE, "PEK_DBF"), -@@ -236,6 +331,11 @@ static const struct resource axp809_pek_ - DEFINE_RES_IRQ_NAMED(AXP809_IRQ_PEK_FAL_EDGE, "PEK_DBF"), - }; - -+static const struct resource axp15060_pek_resources[] = { -+ DEFINE_RES_IRQ_NAMED(AXP15060_IRQ_PEK_RIS_EDGE, "PEK_DBR"), -+ DEFINE_RES_IRQ_NAMED(AXP15060_IRQ_PEK_FAL_EDGE, "PEK_DBF"), -+}; -+ - static const struct regmap_config axp152_regmap_config = { - .reg_bits = 8, - .val_bits = 8, -@@ -245,6 +345,15 @@ static const struct regmap_config axp152 - .cache_type = REGCACHE_RBTREE, - }; - -+static const struct regmap_config axp192_regmap_config = { -+ .reg_bits = 8, -+ .val_bits = 8, -+ .wr_table = &axp192_writeable_table, -+ .volatile_table = &axp192_volatile_table, -+ .max_register = AXP20X_CC_CTRL, -+ .cache_type = REGCACHE_RBTREE, -+}; -+ - static const struct regmap_config axp20x_regmap_config = { - .reg_bits = 8, - .val_bits = 8, -@@ -272,6 +381,15 @@ static const struct regmap_config axp288 - .cache_type = REGCACHE_RBTREE, - }; - -+static const struct regmap_config axp313a_regmap_config = { -+ .reg_bits = 8, -+ .val_bits = 8, -+ .wr_table = &axp313a_writeable_table, -+ .volatile_table = &axp313a_volatile_table, -+ .max_register = AXP313A_IRQ_STATE, -+ .cache_type = REGCACHE_RBTREE, -+}; -+ - static const struct regmap_config axp806_regmap_config = { - .reg_bits = 8, - .val_bits = 8, -@@ -281,6 +399,15 @@ static const struct regmap_config axp806 - .cache_type = REGCACHE_RBTREE, - }; - -+static const struct regmap_config axp15060_regmap_config = { -+ .reg_bits = 8, -+ .val_bits = 8, -+ .wr_table = &axp15060_writeable_table, -+ .volatile_table = &axp15060_volatile_table, -+ .max_register = AXP15060_IRQ2_STATE, -+ .cache_type = REGCACHE_RBTREE, -+}; -+ - #define INIT_REGMAP_IRQ(_variant, _irq, _off, _mask) \ - [_variant##_IRQ_##_irq] = { .reg_offset = (_off), .mask = BIT(_mask) } - -@@ -304,6 +431,42 @@ static const struct regmap_irq axp152_re - INIT_REGMAP_IRQ(AXP152, GPIO0_INPUT, 2, 0), - }; - -+static const struct regmap_irq axp192_regmap_irqs[] = { -+ INIT_REGMAP_IRQ(AXP192, ACIN_OVER_V, 0, 7), -+ INIT_REGMAP_IRQ(AXP192, ACIN_PLUGIN, 0, 6), -+ INIT_REGMAP_IRQ(AXP192, ACIN_REMOVAL, 0, 5), -+ INIT_REGMAP_IRQ(AXP192, VBUS_OVER_V, 0, 4), -+ INIT_REGMAP_IRQ(AXP192, VBUS_PLUGIN, 0, 3), -+ INIT_REGMAP_IRQ(AXP192, VBUS_REMOVAL, 0, 2), -+ INIT_REGMAP_IRQ(AXP192, VBUS_V_LOW, 0, 1), -+ INIT_REGMAP_IRQ(AXP192, BATT_PLUGIN, 1, 7), -+ INIT_REGMAP_IRQ(AXP192, BATT_REMOVAL, 1, 6), -+ INIT_REGMAP_IRQ(AXP192, BATT_ENT_ACT_MODE, 1, 5), -+ INIT_REGMAP_IRQ(AXP192, BATT_EXIT_ACT_MODE, 1, 4), -+ INIT_REGMAP_IRQ(AXP192, CHARG, 1, 3), -+ INIT_REGMAP_IRQ(AXP192, CHARG_DONE, 1, 2), -+ INIT_REGMAP_IRQ(AXP192, BATT_TEMP_HIGH, 1, 1), -+ INIT_REGMAP_IRQ(AXP192, BATT_TEMP_LOW, 1, 0), -+ INIT_REGMAP_IRQ(AXP192, DIE_TEMP_HIGH, 2, 7), -+ INIT_REGMAP_IRQ(AXP192, CHARG_I_LOW, 2, 6), -+ INIT_REGMAP_IRQ(AXP192, DCDC1_V_LONG, 2, 5), -+ INIT_REGMAP_IRQ(AXP192, DCDC2_V_LONG, 2, 4), -+ INIT_REGMAP_IRQ(AXP192, DCDC3_V_LONG, 2, 3), -+ INIT_REGMAP_IRQ(AXP192, PEK_SHORT, 2, 1), -+ INIT_REGMAP_IRQ(AXP192, PEK_LONG, 2, 0), -+ INIT_REGMAP_IRQ(AXP192, N_OE_PWR_ON, 3, 7), -+ INIT_REGMAP_IRQ(AXP192, N_OE_PWR_OFF, 3, 6), -+ INIT_REGMAP_IRQ(AXP192, VBUS_VALID, 3, 5), -+ INIT_REGMAP_IRQ(AXP192, VBUS_NOT_VALID, 3, 4), -+ INIT_REGMAP_IRQ(AXP192, VBUS_SESS_VALID, 3, 3), -+ INIT_REGMAP_IRQ(AXP192, VBUS_SESS_END, 3, 2), -+ INIT_REGMAP_IRQ(AXP192, LOW_PWR_LVL, 3, 0), -+ INIT_REGMAP_IRQ(AXP192, TIMER, 4, 7), -+ INIT_REGMAP_IRQ(AXP192, GPIO2_INPUT, 4, 2), -+ INIT_REGMAP_IRQ(AXP192, GPIO1_INPUT, 4, 1), -+ INIT_REGMAP_IRQ(AXP192, GPIO0_INPUT, 4, 0), -+}; -+ - static const struct regmap_irq axp20x_regmap_irqs[] = { - INIT_REGMAP_IRQ(AXP20X, ACIN_OVER_V, 0, 7), - INIT_REGMAP_IRQ(AXP20X, ACIN_PLUGIN, 0, 6), -@@ -415,6 +578,16 @@ static const struct regmap_irq axp288_re - INIT_REGMAP_IRQ(AXP288, BC_USB_CHNG, 5, 1), - }; - -+static const struct regmap_irq axp313a_regmap_irqs[] = { -+ INIT_REGMAP_IRQ(AXP313A, PEK_RIS_EDGE, 0, 7), -+ INIT_REGMAP_IRQ(AXP313A, PEK_FAL_EDGE, 0, 6), -+ INIT_REGMAP_IRQ(AXP313A, PEK_SHORT, 0, 5), -+ INIT_REGMAP_IRQ(AXP313A, PEK_LONG, 0, 4), -+ INIT_REGMAP_IRQ(AXP313A, DCDC3_V_LOW, 0, 3), -+ INIT_REGMAP_IRQ(AXP313A, DCDC2_V_LOW, 0, 2), -+ INIT_REGMAP_IRQ(AXP313A, DIE_TEMP_HIGH, 0, 0), -+}; -+ - static const struct regmap_irq axp803_regmap_irqs[] = { - INIT_REGMAP_IRQ(AXP803, ACIN_OVER_V, 0, 7), - INIT_REGMAP_IRQ(AXP803, ACIN_PLUGIN, 0, 6), -@@ -502,24 +675,65 @@ static const struct regmap_irq axp809_re - INIT_REGMAP_IRQ(AXP809, GPIO0_INPUT, 4, 0), - }; - -+static const struct regmap_irq axp15060_regmap_irqs[] = { -+ INIT_REGMAP_IRQ(AXP15060, DIE_TEMP_HIGH_LV1, 0, 0), -+ INIT_REGMAP_IRQ(AXP15060, DIE_TEMP_HIGH_LV2, 0, 1), -+ INIT_REGMAP_IRQ(AXP15060, DCDC1_V_LOW, 0, 2), -+ INIT_REGMAP_IRQ(AXP15060, DCDC2_V_LOW, 0, 3), -+ INIT_REGMAP_IRQ(AXP15060, DCDC3_V_LOW, 0, 4), -+ INIT_REGMAP_IRQ(AXP15060, DCDC4_V_LOW, 0, 5), -+ INIT_REGMAP_IRQ(AXP15060, DCDC5_V_LOW, 0, 6), -+ INIT_REGMAP_IRQ(AXP15060, DCDC6_V_LOW, 0, 7), -+ INIT_REGMAP_IRQ(AXP15060, PEK_LONG, 1, 0), -+ INIT_REGMAP_IRQ(AXP15060, PEK_SHORT, 1, 1), -+ INIT_REGMAP_IRQ(AXP15060, GPIO1_INPUT, 1, 2), -+ INIT_REGMAP_IRQ(AXP15060, PEK_FAL_EDGE, 1, 3), -+ INIT_REGMAP_IRQ(AXP15060, PEK_RIS_EDGE, 1, 4), -+ INIT_REGMAP_IRQ(AXP15060, GPIO2_INPUT, 1, 5), -+}; -+ - static const struct regmap_irq_chip axp152_regmap_irq_chip = { - .name = "axp152_irq_chip", - .status_base = AXP152_IRQ1_STATE, - .ack_base = AXP152_IRQ1_STATE, -- .mask_base = AXP152_IRQ1_EN, -- .mask_invert = true, -+ .unmask_base = AXP152_IRQ1_EN, - .init_ack_masked = true, - .irqs = axp152_regmap_irqs, - .num_irqs = ARRAY_SIZE(axp152_regmap_irqs), - .num_regs = 3, - }; - -+static unsigned int axp192_get_irq_reg(struct regmap_irq_chip_data *data, -+ unsigned int base, int index) -+{ -+ /* linear mapping for IRQ1 to IRQ4 */ -+ if (index < 4) -+ return base + index; -+ -+ /* handle IRQ5 separately */ -+ if (base == AXP192_IRQ1_EN) -+ return AXP192_IRQ5_EN; -+ -+ return AXP192_IRQ5_STATE; -+} -+ -+static const struct regmap_irq_chip axp192_regmap_irq_chip = { -+ .name = "axp192_irq_chip", -+ .status_base = AXP192_IRQ1_STATE, -+ .ack_base = AXP192_IRQ1_STATE, -+ .unmask_base = AXP192_IRQ1_EN, -+ .init_ack_masked = true, -+ .irqs = axp192_regmap_irqs, -+ .num_irqs = ARRAY_SIZE(axp192_regmap_irqs), -+ .num_regs = 5, -+ .get_irq_reg = axp192_get_irq_reg, -+}; -+ - static const struct regmap_irq_chip axp20x_regmap_irq_chip = { - .name = "axp20x_irq_chip", - .status_base = AXP20X_IRQ1_STATE, - .ack_base = AXP20X_IRQ1_STATE, -- .mask_base = AXP20X_IRQ1_EN, -- .mask_invert = true, -+ .unmask_base = AXP20X_IRQ1_EN, - .init_ack_masked = true, - .irqs = axp20x_regmap_irqs, - .num_irqs = ARRAY_SIZE(axp20x_regmap_irqs), -@@ -531,8 +745,7 @@ static const struct regmap_irq_chip axp2 - .name = "axp22x_irq_chip", - .status_base = AXP20X_IRQ1_STATE, - .ack_base = AXP20X_IRQ1_STATE, -- .mask_base = AXP20X_IRQ1_EN, -- .mask_invert = true, -+ .unmask_base = AXP20X_IRQ1_EN, - .init_ack_masked = true, - .irqs = axp22x_regmap_irqs, - .num_irqs = ARRAY_SIZE(axp22x_regmap_irqs), -@@ -543,8 +756,7 @@ static const struct regmap_irq_chip axp2 - .name = "axp288_irq_chip", - .status_base = AXP20X_IRQ1_STATE, - .ack_base = AXP20X_IRQ1_STATE, -- .mask_base = AXP20X_IRQ1_EN, -- .mask_invert = true, -+ .unmask_base = AXP20X_IRQ1_EN, - .init_ack_masked = true, - .irqs = axp288_regmap_irqs, - .num_irqs = ARRAY_SIZE(axp288_regmap_irqs), -@@ -552,12 +764,22 @@ static const struct regmap_irq_chip axp2 - - }; - -+static const struct regmap_irq_chip axp313a_regmap_irq_chip = { -+ .name = "axp313a_irq_chip", -+ .status_base = AXP313A_IRQ_STATE, -+ .ack_base = AXP313A_IRQ_STATE, -+ .unmask_base = AXP313A_IRQ_EN, -+ .init_ack_masked = true, -+ .irqs = axp313a_regmap_irqs, -+ .num_irqs = ARRAY_SIZE(axp313a_regmap_irqs), -+ .num_regs = 1, -+}; -+ - static const struct regmap_irq_chip axp803_regmap_irq_chip = { - .name = "axp803", - .status_base = AXP20X_IRQ1_STATE, - .ack_base = AXP20X_IRQ1_STATE, -- .mask_base = AXP20X_IRQ1_EN, -- .mask_invert = true, -+ .unmask_base = AXP20X_IRQ1_EN, - .init_ack_masked = true, - .irqs = axp803_regmap_irqs, - .num_irqs = ARRAY_SIZE(axp803_regmap_irqs), -@@ -568,8 +790,7 @@ static const struct regmap_irq_chip axp8 - .name = "axp806", - .status_base = AXP20X_IRQ1_STATE, - .ack_base = AXP20X_IRQ1_STATE, -- .mask_base = AXP20X_IRQ1_EN, -- .mask_invert = true, -+ .unmask_base = AXP20X_IRQ1_EN, - .init_ack_masked = true, - .irqs = axp806_regmap_irqs, - .num_irqs = ARRAY_SIZE(axp806_regmap_irqs), -@@ -580,14 +801,45 @@ static const struct regmap_irq_chip axp8 - .name = "axp809", - .status_base = AXP20X_IRQ1_STATE, - .ack_base = AXP20X_IRQ1_STATE, -- .mask_base = AXP20X_IRQ1_EN, -- .mask_invert = true, -+ .unmask_base = AXP20X_IRQ1_EN, - .init_ack_masked = true, - .irqs = axp809_regmap_irqs, - .num_irqs = ARRAY_SIZE(axp809_regmap_irqs), - .num_regs = 5, - }; - -+static const struct regmap_irq_chip axp15060_regmap_irq_chip = { -+ .name = "axp15060", -+ .status_base = AXP15060_IRQ1_STATE, -+ .ack_base = AXP15060_IRQ1_STATE, -+ .unmask_base = AXP15060_IRQ1_EN, -+ .init_ack_masked = true, -+ .irqs = axp15060_regmap_irqs, -+ .num_irqs = ARRAY_SIZE(axp15060_regmap_irqs), -+ .num_regs = 2, -+}; -+ -+static const struct mfd_cell axp192_cells[] = { -+ { -+ .name = "axp192-adc", -+ .of_compatible = "x-powers,axp192-adc", -+ }, { -+ .name = "axp20x-battery-power-supply", -+ .of_compatible = "x-powers,axp192-battery-power-supply", -+ }, { -+ .name = "axp20x-ac-power-supply", -+ .of_compatible = "x-powers,axp202-ac-power-supply", -+ .num_resources = ARRAY_SIZE(axp192_ac_power_supply_resources), -+ .resources = axp192_ac_power_supply_resources, -+ }, { -+ .name = "axp20x-usb-power-supply", -+ .of_compatible = "x-powers,axp192-usb-power-supply", -+ .num_resources = ARRAY_SIZE(axp192_usb_power_supply_resources), -+ .resources = axp192_usb_power_supply_resources, -+ }, -+ { .name = "axp20x-regulator" }, -+}; -+ - static const struct mfd_cell axp20x_cells[] = { - { - .name = "axp20x-gpio", -@@ -683,6 +935,11 @@ static const struct mfd_cell axp152_cell - }, - }; - -+static struct mfd_cell axp313a_cells[] = { -+ MFD_CELL_NAME("axp20x-regulator"), -+ MFD_CELL_RES("axp313a-pek", axp313a_pek_resources), -+}; -+ - static const struct resource axp288_adc_resources[] = { - DEFINE_RES_IRQ_NAMED(AXP288_IRQ_GPADC, "GPADC"), - }; -@@ -832,17 +1089,43 @@ static const struct mfd_cell axp813_cell - }, - }; - --static struct axp20x_dev *axp20x_pm_power_off; --static void axp20x_power_off(void) -+static const struct mfd_cell axp15060_cells[] = { -+ { -+ .name = "axp221-pek", -+ .num_resources = ARRAY_SIZE(axp15060_pek_resources), -+ .resources = axp15060_pek_resources, -+ }, { -+ .name = "axp20x-regulator", -+ }, -+}; -+ -+/* For boards that don't have IRQ line connected to SOC. */ -+static const struct mfd_cell axp_regulator_only_cells[] = { -+ { -+ .name = "axp20x-regulator", -+ }, -+}; -+ -+static int axp20x_power_off(struct sys_off_data *data) - { -- if (axp20x_pm_power_off->variant == AXP288_ID) -- return; -+ struct axp20x_dev *axp20x = data->cb_data; -+ unsigned int shutdown_reg; - -- regmap_write(axp20x_pm_power_off->regmap, AXP20X_OFF_CTRL, -- AXP20X_OFF); -+ switch (axp20x->variant) { -+ case AXP313A_ID: -+ shutdown_reg = AXP313A_SHUTDOWN_CTRL; -+ break; -+ default: -+ shutdown_reg = AXP20X_OFF_CTRL; -+ break; -+ } -+ -+ regmap_write(axp20x->regmap, shutdown_reg, AXP20X_OFF); - - /* Give capacitors etc. time to drain to avoid kernel panic msg. */ - mdelay(500); -+ -+ return NOTIFY_DONE; - } - - int axp20x_match_device(struct axp20x_dev *axp20x) -@@ -874,6 +1157,12 @@ int axp20x_match_device(struct axp20x_de - axp20x->regmap_cfg = &axp152_regmap_config; - axp20x->regmap_irq_chip = &axp152_regmap_irq_chip; - break; -+ case AXP192_ID: -+ axp20x->nr_cells = ARRAY_SIZE(axp192_cells); -+ axp20x->cells = axp192_cells; -+ axp20x->regmap_cfg = &axp192_regmap_config; -+ axp20x->regmap_irq_chip = &axp192_regmap_irq_chip; -+ break; - case AXP202_ID: - case AXP209_ID: - axp20x->nr_cells = ARRAY_SIZE(axp20x_cells); -@@ -900,6 +1189,12 @@ int axp20x_match_device(struct axp20x_de - axp20x->regmap_irq_chip = &axp288_regmap_irq_chip; - axp20x->irq_flags = IRQF_TRIGGER_LOW; - break; -+ case AXP313A_ID: -+ axp20x->nr_cells = ARRAY_SIZE(axp313a_cells); -+ axp20x->cells = axp313a_cells; -+ axp20x->regmap_cfg = &axp313a_regmap_config; -+ axp20x->regmap_irq_chip = &axp313a_regmap_irq_chip; -+ break; - case AXP803_ID: - axp20x->nr_cells = ARRAY_SIZE(axp803_cells); - axp20x->cells = axp803_cells; -@@ -942,6 +1237,28 @@ int axp20x_match_device(struct axp20x_de - */ - axp20x->regmap_irq_chip = &axp803_regmap_irq_chip; - break; -+ case AXP15060_ID: -+ /* -+ * Don't register the power key part if there is no interrupt -+ * line. -+ * -+ * Since most use cases of AXP PMICs are Allwinner SOCs, board -+ * designers follow Allwinner's reference design and connects -+ * IRQ line to SOC, there's no need for those variants to deal -+ * with cases that IRQ isn't connected. However, AXP15660 is -+ * used by some other vendors' SOCs that didn't connect IRQ -+ * line, we need to deal with this case. -+ */ -+ if (axp20x->irq > 0) { -+ axp20x->nr_cells = ARRAY_SIZE(axp15060_cells); -+ axp20x->cells = axp15060_cells; -+ } else { -+ axp20x->nr_cells = ARRAY_SIZE(axp_regulator_only_cells); -+ axp20x->cells = axp_regulator_only_cells; -+ } -+ axp20x->regmap_cfg = &axp15060_regmap_config; -+ axp20x->regmap_irq_chip = &axp15060_regmap_irq_chip; -+ break; - default: - dev_err(dev, "unsupported AXP20X ID %lu\n", axp20x->variant); - return -EINVAL; -@@ -1009,10 +1326,11 @@ int axp20x_device_probe(struct axp20x_de - return ret; - } - -- if (!pm_power_off) { -- axp20x_pm_power_off = axp20x; -- pm_power_off = axp20x_power_off; -- } -+ if (axp20x->variant != AXP288_ID) -+ devm_register_sys_off_handler(axp20x->dev, -+ SYS_OFF_MODE_POWER_OFF, -+ SYS_OFF_PRIO_DEFAULT, -+ axp20x_power_off, axp20x); - - dev_info(axp20x->dev, "AXP20X driver loaded\n"); - -@@ -1022,11 +1340,6 @@ EXPORT_SYMBOL(axp20x_device_probe); - - void axp20x_device_remove(struct axp20x_dev *axp20x) - { -- if (axp20x == axp20x_pm_power_off) { -- axp20x_pm_power_off = NULL; -- pm_power_off = NULL; -- } -- - mfd_remove_devices(axp20x->dev); - regmap_del_irq_chip(axp20x->irq, axp20x->regmap_irqc); - } ---- a/include/linux/mfd/axp20x.h -+++ b/include/linux/mfd/axp20x.h -@@ -12,18 +12,22 @@ - - enum axp20x_variants { - AXP152_ID = 0, -+ AXP192_ID, - AXP202_ID, - AXP209_ID, - AXP221_ID, - AXP223_ID, - AXP288_ID, -+ AXP313A_ID, - AXP803_ID, - AXP806_ID, - AXP809_ID, - AXP813_ID, -+ AXP15060_ID, - NR_AXP20X_VARIANTS, - }; - -+#define AXP192_DATACACHE(m) (0x06 + (m)) - #define AXP20X_DATACACHE(m) (0x04 + (m)) - - /* Power supply */ -@@ -45,6 +49,13 @@ enum axp20x_variants { - #define AXP152_DCDC_FREQ 0x37 - #define AXP152_DCDC_MODE 0x80 - -+#define AXP192_USB_OTG_STATUS 0x04 -+#define AXP192_PWR_OUT_CTRL 0x12 -+#define AXP192_DCDC2_V_OUT 0x23 -+#define AXP192_DCDC1_V_OUT 0x26 -+#define AXP192_DCDC3_V_OUT 0x27 -+#define AXP192_LDO2_3_V_OUT 0x28 -+ - #define AXP20X_PWR_INPUT_STATUS 0x00 - #define AXP20X_PWR_OP_MODE 0x01 - #define AXP20X_USB_OTG_STATUS 0x02 -@@ -91,6 +102,17 @@ enum axp20x_variants { - #define AXP22X_ALDO3_V_OUT 0x2a - #define AXP22X_CHRG_CTRL3 0x35 - -+#define AXP313A_ON_INDICATE 0x00 -+#define AXP313A_OUTPUT_CONTROL 0x10 -+#define AXP313A_DCDC1_CONRTOL 0x13 -+#define AXP313A_DCDC2_CONRTOL 0x14 -+#define AXP313A_DCDC3_CONRTOL 0x15 -+#define AXP313A_ALDO1_CONRTOL 0x16 -+#define AXP313A_DLDO1_CONRTOL 0x17 -+#define AXP313A_SHUTDOWN_CTRL 0x1a -+#define AXP313A_IRQ_EN 0x20 -+#define AXP313A_IRQ_STATE 0x21 -+ - #define AXP806_STARTUP_SRC 0x00 - #define AXP806_CHIP_ID 0x03 - #define AXP806_PWR_OUT_CTRL1 0x10 -@@ -131,6 +153,39 @@ enum axp20x_variants { - /* Other DCDC regulator control registers are the same as AXP803 */ - #define AXP813_DCDC7_V_OUT 0x26 - -+#define AXP15060_STARTUP_SRC 0x00 -+#define AXP15060_PWR_OUT_CTRL1 0x10 -+#define AXP15060_PWR_OUT_CTRL2 0x11 -+#define AXP15060_PWR_OUT_CTRL3 0x12 -+#define AXP15060_DCDC1_V_CTRL 0x13 -+#define AXP15060_DCDC2_V_CTRL 0x14 -+#define AXP15060_DCDC3_V_CTRL 0x15 -+#define AXP15060_DCDC4_V_CTRL 0x16 -+#define AXP15060_DCDC5_V_CTRL 0x17 -+#define AXP15060_DCDC6_V_CTRL 0x18 -+#define AXP15060_ALDO1_V_CTRL 0x19 -+#define AXP15060_DCDC_MODE_CTRL1 0x1a -+#define AXP15060_DCDC_MODE_CTRL2 0x1b -+#define AXP15060_OUTPUT_MONITOR_DISCHARGE 0x1e -+#define AXP15060_IRQ_PWROK_VOFF 0x1f -+#define AXP15060_ALDO2_V_CTRL 0x20 -+#define AXP15060_ALDO3_V_CTRL 0x21 -+#define AXP15060_ALDO4_V_CTRL 0x22 -+#define AXP15060_ALDO5_V_CTRL 0x23 -+#define AXP15060_BLDO1_V_CTRL 0x24 -+#define AXP15060_BLDO2_V_CTRL 0x25 -+#define AXP15060_BLDO3_V_CTRL 0x26 -+#define AXP15060_BLDO4_V_CTRL 0x27 -+#define AXP15060_BLDO5_V_CTRL 0x28 -+#define AXP15060_CLDO1_V_CTRL 0x29 -+#define AXP15060_CLDO2_V_CTRL 0x2a -+#define AXP15060_CLDO3_V_CTRL 0x2b -+#define AXP15060_CLDO4_V_CTRL 0x2d -+#define AXP15060_CPUSLDO_V_CTRL 0x2e -+#define AXP15060_PWR_WAKEUP_CTRL 0x31 -+#define AXP15060_PWR_DISABLE_DOWN_SEQ 0x32 -+#define AXP15060_PEK_KEY 0x36 -+ - /* Interrupt */ - #define AXP152_IRQ1_EN 0x40 - #define AXP152_IRQ2_EN 0x41 -@@ -139,6 +194,17 @@ enum axp20x_variants { - #define AXP152_IRQ2_STATE 0x49 - #define AXP152_IRQ3_STATE 0x4a - -+#define AXP192_IRQ1_EN 0x40 -+#define AXP192_IRQ2_EN 0x41 -+#define AXP192_IRQ3_EN 0x42 -+#define AXP192_IRQ4_EN 0x43 -+#define AXP192_IRQ1_STATE 0x44 -+#define AXP192_IRQ2_STATE 0x45 -+#define AXP192_IRQ3_STATE 0x46 -+#define AXP192_IRQ4_STATE 0x47 -+#define AXP192_IRQ5_EN 0x4a -+#define AXP192_IRQ5_STATE 0x4d -+ - #define AXP20X_IRQ1_EN 0x40 - #define AXP20X_IRQ2_EN 0x41 - #define AXP20X_IRQ3_EN 0x42 -@@ -152,7 +218,17 @@ enum axp20x_variants { - #define AXP20X_IRQ5_STATE 0x4c - #define AXP20X_IRQ6_STATE 0x4d - -+#define AXP15060_IRQ1_EN 0x40 -+#define AXP15060_IRQ2_EN 0x41 -+#define AXP15060_IRQ1_STATE 0x48 -+#define AXP15060_IRQ2_STATE 0x49 -+ - /* ADC */ -+#define AXP192_GPIO2_V_ADC_H 0x68 -+#define AXP192_GPIO2_V_ADC_L 0x69 -+#define AXP192_GPIO3_V_ADC_H 0x6a -+#define AXP192_GPIO3_V_ADC_L 0x6b -+ - #define AXP20X_ACIN_V_ADC_H 0x56 - #define AXP20X_ACIN_V_ADC_L 0x57 - #define AXP20X_ACIN_I_ADC_H 0x58 -@@ -182,6 +258,8 @@ enum axp20x_variants { - #define AXP20X_IPSOUT_V_HIGH_L 0x7f - - /* Power supply */ -+#define AXP192_GPIO30_IN_RANGE 0x85 -+ - #define AXP20X_DCDC_MODE 0x80 - #define AXP20X_ADC_EN1 0x82 - #define AXP20X_ADC_EN2 0x83 -@@ -210,6 +288,16 @@ enum axp20x_variants { - #define AXP152_PWM1_FREQ_Y 0x9c - #define AXP152_PWM1_DUTY_CYCLE 0x9d - -+#define AXP192_GPIO0_CTRL 0x90 -+#define AXP192_LDO_IO0_V_OUT 0x91 -+#define AXP192_GPIO1_CTRL 0x92 -+#define AXP192_GPIO2_CTRL 0x93 -+#define AXP192_GPIO2_0_STATE 0x94 -+#define AXP192_GPIO4_3_CTRL 0x95 -+#define AXP192_GPIO4_3_STATE 0x96 -+#define AXP192_GPIO2_0_PULL 0x97 -+#define AXP192_N_RSTO_CTRL 0x9e -+ - #define AXP20X_GPIO0_CTRL 0x90 - #define AXP20X_LDO5_V_OUT 0x91 - #define AXP20X_GPIO1_CTRL 0x92 -@@ -222,6 +310,8 @@ enum axp20x_variants { - #define AXP22X_GPIO_STATE 0x94 - #define AXP22X_GPIO_PULL_DOWN 0x95 - -+#define AXP15060_CLDO4_GPIO2_MODESET 0x2c -+ - /* Battery */ - #define AXP20X_CHRG_CC_31_24 0xb0 - #define AXP20X_CHRG_CC_23_16 0xb1 -@@ -288,6 +378,17 @@ enum axp20x_variants { - - /* Regulators IDs */ - enum { -+ AXP192_DCDC1 = 0, -+ AXP192_DCDC2, -+ AXP192_DCDC3, -+ AXP192_LDO1, -+ AXP192_LDO2, -+ AXP192_LDO3, -+ AXP192_LDO_IO0, -+ AXP192_REG_ID_MAX -+}; -+ -+enum { - AXP20X_LDO1 = 0, - AXP20X_LDO2, - AXP20X_LDO3, -@@ -323,6 +424,16 @@ enum { - }; - - enum { -+ AXP313A_DCDC1 = 0, -+ AXP313A_DCDC2, -+ AXP313A_DCDC3, -+ AXP313A_ALDO1, -+ AXP313A_DLDO1, -+ AXP313A_RTC_LDO, -+ AXP313A_REG_ID_MAX, -+}; -+ -+enum { - AXP806_DCDCA = 0, - AXP806_DCDCB, - AXP806_DCDCC, -@@ -419,6 +530,33 @@ enum { - AXP813_REG_ID_MAX, - }; - -+enum { -+ AXP15060_DCDC1 = 0, -+ AXP15060_DCDC2, -+ AXP15060_DCDC3, -+ AXP15060_DCDC4, -+ AXP15060_DCDC5, -+ AXP15060_DCDC6, -+ AXP15060_ALDO1, -+ AXP15060_ALDO2, -+ AXP15060_ALDO3, -+ AXP15060_ALDO4, -+ AXP15060_ALDO5, -+ AXP15060_BLDO1, -+ AXP15060_BLDO2, -+ AXP15060_BLDO3, -+ AXP15060_BLDO4, -+ AXP15060_BLDO5, -+ AXP15060_CLDO1, -+ AXP15060_CLDO2, -+ AXP15060_CLDO3, -+ AXP15060_CLDO4, -+ AXP15060_CPUSLDO, -+ AXP15060_SW, -+ AXP15060_RTC_LDO, -+ AXP15060_REG_ID_MAX, -+}; -+ - /* IRQs */ - enum { - AXP152_IRQ_LDO0IN_CONNECT = 1, -@@ -432,14 +570,51 @@ enum { - AXP152_IRQ_PEK_SHORT, - AXP152_IRQ_PEK_LONG, - AXP152_IRQ_TIMER, -- AXP152_IRQ_PEK_RIS_EDGE, -+ /* out of bit order to make sure the press event is handled first */ - AXP152_IRQ_PEK_FAL_EDGE, -+ AXP152_IRQ_PEK_RIS_EDGE, - AXP152_IRQ_GPIO3_INPUT, - AXP152_IRQ_GPIO2_INPUT, - AXP152_IRQ_GPIO1_INPUT, - AXP152_IRQ_GPIO0_INPUT, - }; - -+enum axp192_irqs { -+ AXP192_IRQ_ACIN_OVER_V = 1, -+ AXP192_IRQ_ACIN_PLUGIN, -+ AXP192_IRQ_ACIN_REMOVAL, -+ AXP192_IRQ_VBUS_OVER_V, -+ AXP192_IRQ_VBUS_PLUGIN, -+ AXP192_IRQ_VBUS_REMOVAL, -+ AXP192_IRQ_VBUS_V_LOW, -+ AXP192_IRQ_BATT_PLUGIN, -+ AXP192_IRQ_BATT_REMOVAL, -+ AXP192_IRQ_BATT_ENT_ACT_MODE, -+ AXP192_IRQ_BATT_EXIT_ACT_MODE, -+ AXP192_IRQ_CHARG, -+ AXP192_IRQ_CHARG_DONE, -+ AXP192_IRQ_BATT_TEMP_HIGH, -+ AXP192_IRQ_BATT_TEMP_LOW, -+ AXP192_IRQ_DIE_TEMP_HIGH, -+ AXP192_IRQ_CHARG_I_LOW, -+ AXP192_IRQ_DCDC1_V_LONG, -+ AXP192_IRQ_DCDC2_V_LONG, -+ AXP192_IRQ_DCDC3_V_LONG, -+ AXP192_IRQ_PEK_SHORT = 22, -+ AXP192_IRQ_PEK_LONG, -+ AXP192_IRQ_N_OE_PWR_ON, -+ AXP192_IRQ_N_OE_PWR_OFF, -+ AXP192_IRQ_VBUS_VALID, -+ AXP192_IRQ_VBUS_NOT_VALID, -+ AXP192_IRQ_VBUS_SESS_VALID, -+ AXP192_IRQ_VBUS_SESS_END, -+ AXP192_IRQ_LOW_PWR_LVL = 31, -+ AXP192_IRQ_TIMER, -+ AXP192_IRQ_GPIO2_INPUT = 37, -+ AXP192_IRQ_GPIO1_INPUT, -+ AXP192_IRQ_GPIO0_INPUT, -+}; -+ - enum { - AXP20X_IRQ_ACIN_OVER_V = 1, - AXP20X_IRQ_ACIN_PLUGIN, -@@ -472,8 +647,9 @@ enum { - AXP20X_IRQ_LOW_PWR_LVL1, - AXP20X_IRQ_LOW_PWR_LVL2, - AXP20X_IRQ_TIMER, -- AXP20X_IRQ_PEK_RIS_EDGE, -+ /* out of bit order to make sure the press event is handled first */ - AXP20X_IRQ_PEK_FAL_EDGE, -+ AXP20X_IRQ_PEK_RIS_EDGE, - AXP20X_IRQ_GPIO3_INPUT, - AXP20X_IRQ_GPIO2_INPUT, - AXP20X_IRQ_GPIO1_INPUT, -@@ -502,8 +678,9 @@ enum axp22x_irqs { - AXP22X_IRQ_LOW_PWR_LVL1, - AXP22X_IRQ_LOW_PWR_LVL2, - AXP22X_IRQ_TIMER, -- AXP22X_IRQ_PEK_RIS_EDGE, -+ /* out of bit order to make sure the press event is handled first */ - AXP22X_IRQ_PEK_FAL_EDGE, -+ AXP22X_IRQ_PEK_RIS_EDGE, - AXP22X_IRQ_GPIO1_INPUT, - AXP22X_IRQ_GPIO0_INPUT, - }; -@@ -545,6 +722,16 @@ enum axp288_irqs { - AXP288_IRQ_BC_USB_CHNG, - }; - -+enum axp313a_irqs { -+ AXP313A_IRQ_DIE_TEMP_HIGH, -+ AXP313A_IRQ_DCDC2_V_LOW = 2, -+ AXP313A_IRQ_DCDC3_V_LOW, -+ AXP313A_IRQ_PEK_LONG, -+ AXP313A_IRQ_PEK_SHORT, -+ AXP313A_IRQ_PEK_FAL_EDGE, -+ AXP313A_IRQ_PEK_RIS_EDGE, -+}; -+ - enum axp803_irqs { - AXP803_IRQ_ACIN_OVER_V = 1, - AXP803_IRQ_ACIN_PLUGIN, -@@ -571,8 +758,9 @@ enum axp803_irqs { - AXP803_IRQ_LOW_PWR_LVL1, - AXP803_IRQ_LOW_PWR_LVL2, - AXP803_IRQ_TIMER, -- AXP803_IRQ_PEK_RIS_EDGE, -+ /* out of bit order to make sure the press event is handled first */ - AXP803_IRQ_PEK_FAL_EDGE, -+ AXP803_IRQ_PEK_RIS_EDGE, - AXP803_IRQ_PEK_SHORT, - AXP803_IRQ_PEK_LONG, - AXP803_IRQ_PEK_OVER_OFF, -@@ -623,8 +811,9 @@ enum axp809_irqs { - AXP809_IRQ_LOW_PWR_LVL1, - AXP809_IRQ_LOW_PWR_LVL2, - AXP809_IRQ_TIMER, -- AXP809_IRQ_PEK_RIS_EDGE, -+ /* out of bit order to make sure the press event is handled first */ - AXP809_IRQ_PEK_FAL_EDGE, -+ AXP809_IRQ_PEK_RIS_EDGE, - AXP809_IRQ_PEK_SHORT, - AXP809_IRQ_PEK_LONG, - AXP809_IRQ_PEK_OVER_OFF, -@@ -632,6 +821,23 @@ enum axp809_irqs { - AXP809_IRQ_GPIO0_INPUT, - }; - -+enum axp15060_irqs { -+ AXP15060_IRQ_DIE_TEMP_HIGH_LV1 = 1, -+ AXP15060_IRQ_DIE_TEMP_HIGH_LV2, -+ AXP15060_IRQ_DCDC1_V_LOW, -+ AXP15060_IRQ_DCDC2_V_LOW, -+ AXP15060_IRQ_DCDC3_V_LOW, -+ AXP15060_IRQ_DCDC4_V_LOW, -+ AXP15060_IRQ_DCDC5_V_LOW, -+ AXP15060_IRQ_DCDC6_V_LOW, -+ AXP15060_IRQ_PEK_LONG, -+ AXP15060_IRQ_PEK_SHORT, -+ AXP15060_IRQ_GPIO1_INPUT, -+ AXP15060_IRQ_PEK_FAL_EDGE, -+ AXP15060_IRQ_PEK_RIS_EDGE, -+ AXP15060_IRQ_GPIO2_INPUT, -+}; -+ - struct axp20x_dev { - struct device *dev; - int irq; -@@ -698,4 +904,4 @@ int axp20x_device_probe(struct axp20x_de - */ - void axp20x_device_remove(struct axp20x_dev *axp20x); - --#endif /* __LINUX_MFD_AXP20X_H */ -+#endif /* __LINUX_MFD_AXP20X_H */ -\ No newline at end of file