diff options
Diffstat (limited to 'drivers/regulator')
27 files changed, 3514 insertions, 661 deletions
diff --git a/drivers/regulator/Kconfig b/drivers/regulator/Kconfig index d84f3d054c59..d2335276cce5 100644 --- a/drivers/regulator/Kconfig +++ b/drivers/regulator/Kconfig @@ -500,6 +500,16 @@ config REGULATOR_ISL6271A help This driver supports ISL6271A voltage regulator chip. +config REGULATOR_FP9931 + tristate "FitiPower FP9931/JD9930 EPD regulator" + depends on I2C + select REGMAP_I2C + help + This driver supports the FP9931/JD9930 voltage regulator chip + which is used to provide power to Electronic Paper Displays + so it is found in E-Book readers. + If HWWON is enabled, it also provides temperature measurement. + config REGULATOR_LM363X tristate "TI LM363X voltage regulators" depends on MFD_TI_LMU @@ -881,6 +891,16 @@ config REGULATOR_MT6315 This driver supports the control of different power rails of device through regulator interface. +config REGULATOR_MT6316 + tristate "MT6316 SPMI PMIC regulator driver" + depends on SPMI + select REGMAP_SPMI + help + Say Y here to enable support for 2+2, 3+1 and 4 phase regulators + found in the MediaTek MT6316 BP, CP, DP, HP, VP and TP SPMI PMICs. + This driver supports the control of different power rails of device + through regulator interface. + config REGULATOR_MT6323 tristate "MediaTek MT6323 PMIC" depends on MFD_MT6397 @@ -944,6 +964,16 @@ config REGULATOR_MT6360 2-channel buck with Thermal Shutdown and Overload Protection 6-channel High PSRR and Low Dropout LDO. +config REGULATOR_MT6363 + tristate "MT6363 SPMI PMIC regulator driver" + depends on SPMI + select REGMAP_SPMI + help + Say Y here to enable support for regulators found in the MediaTek + MT6363 SPMI PMIC. + This driver supports the control of different power rails of device + through regulator interface. + config REGULATOR_MT6370 tristate "MT6370 SubPMIC Regulator" depends on MFD_MT6370 @@ -1086,6 +1116,15 @@ config REGULATOR_PV88090 Say y here to support the voltage regulators and convertors on PV88090 +config REGULATOR_PF1550 + tristate "NXP PF1550 regulator" + depends on MFD_PF1550 + help + Say y here to select this option to enable the regulators on + the PF1550 PMICs. + This driver controls the PF1550 regulators via I2C bus. + The regulators include three bucks and three ldos. + config REGULATOR_PWM tristate "PWM voltage regulator" depends on PWM @@ -1181,6 +1220,7 @@ config REGULATOR_RAA215300 config REGULATOR_RASPBERRYPI_TOUCHSCREEN_ATTINY tristate "Raspberry Pi 7-inch touchscreen panel ATTINY regulator" + depends on ARM || ARM64 || COMPILE_TEST depends on BACKLIGHT_CLASS_DEVICE depends on I2C depends on OF_GPIO @@ -1192,6 +1232,7 @@ config REGULATOR_RASPBERRYPI_TOUCHSCREEN_ATTINY config REGULATOR_RASPBERRYPI_TOUCHSCREEN_V2 tristate "Raspberry Pi 7-inch touchscreen panel V2 regulator" + depends on ARM || ARM64 || COMPILE_TEST depends on GPIOLIB depends on I2C && OF select GPIO_REGMAP diff --git a/drivers/regulator/Makefile b/drivers/regulator/Makefile index b3101376029d..1beba1493241 100644 --- a/drivers/regulator/Makefile +++ b/drivers/regulator/Makefile @@ -59,6 +59,7 @@ obj-$(CONFIG_REGULATOR_HI6421V600) += hi6421v600-regulator.o obj-$(CONFIG_REGULATOR_HI655X) += hi655x-regulator.o obj-$(CONFIG_REGULATOR_ISL6271A) += isl6271a-regulator.o obj-$(CONFIG_REGULATOR_ISL9305) += isl9305.o +obj-$(CONFIG_REGULATOR_FP9931) += fp9931.o obj-$(CONFIG_REGULATOR_LM363X) += lm363x-regulator.o obj-$(CONFIG_REGULATOR_LOCHNAGAR) += lochnagar-regulator.o obj-$(CONFIG_REGULATOR_LP3971) += lp3971.o @@ -105,6 +106,7 @@ obj-$(CONFIG_REGULATOR_MP886X) += mp886x.o obj-$(CONFIG_REGULATOR_MPQ7920) += mpq7920.o obj-$(CONFIG_REGULATOR_MT6311) += mt6311-regulator.o obj-$(CONFIG_REGULATOR_MT6315) += mt6315-regulator.o +obj-$(CONFIG_REGULATOR_MT6315) += mt6316-regulator.o obj-$(CONFIG_REGULATOR_MT6323) += mt6323-regulator.o obj-$(CONFIG_REGULATOR_MT6331) += mt6331-regulator.o obj-$(CONFIG_REGULATOR_MT6332) += mt6332-regulator.o @@ -112,6 +114,7 @@ obj-$(CONFIG_REGULATOR_MT6357) += mt6357-regulator.o obj-$(CONFIG_REGULATOR_MT6358) += mt6358-regulator.o obj-$(CONFIG_REGULATOR_MT6359) += mt6359-regulator.o obj-$(CONFIG_REGULATOR_MT6360) += mt6360-regulator.o +obj-$(CONFIG_REGULATOR_MT6363) += mt6363-regulator.o obj-$(CONFIG_REGULATOR_MT6370) += mt6370-regulator.o obj-$(CONFIG_REGULATOR_MT6380) += mt6380-regulator.o obj-$(CONFIG_REGULATOR_MT6397) += mt6397-regulator.o @@ -128,6 +131,7 @@ obj-$(CONFIG_REGULATOR_PALMAS) += palmas-regulator.o obj-$(CONFIG_REGULATOR_PCA9450) += pca9450-regulator.o obj-$(CONFIG_REGULATOR_PF0900) += pf0900-regulator.o obj-$(CONFIG_REGULATOR_PF9453) += pf9453-regulator.o +obj-$(CONFIG_REGULATOR_PF1550) += pf1550-regulator.o obj-$(CONFIG_REGULATOR_PF530X) += pf530x-regulator.o obj-$(CONFIG_REGULATOR_PF8X00) += pf8x00-regulator.o obj-$(CONFIG_REGULATOR_PFUZE100) += pfuze100-regulator.o diff --git a/drivers/regulator/arizona-micsupp.c b/drivers/regulator/arizona-micsupp.c index e250e5f3fcbc..be7208bc7409 100644 --- a/drivers/regulator/arizona-micsupp.c +++ b/drivers/regulator/arizona-micsupp.c @@ -48,7 +48,6 @@ static void arizona_micsupp_check_cp(struct work_struct *work) struct arizona_micsupp *micsupp = container_of(work, struct arizona_micsupp, check_cp_work); struct snd_soc_dapm_context *dapm = *micsupp->dapm; - struct snd_soc_component *component; const struct regulator_desc *desc = micsupp->desc; unsigned int val; int ret; @@ -61,14 +60,11 @@ static void arizona_micsupp_check_cp(struct work_struct *work) } if (dapm) { - component = snd_soc_dapm_to_component(dapm); - if ((val & (desc->enable_mask | desc->bypass_mask)) == desc->enable_mask) - snd_soc_component_force_enable_pin(component, - "MICSUPP"); + snd_soc_dapm_force_enable_pin(dapm, "MICSUPP"); else - snd_soc_component_disable_pin(component, "MICSUPP"); + snd_soc_dapm_disable_pin(dapm, "MICSUPP"); snd_soc_dapm_sync(dapm); } diff --git a/drivers/regulator/bd71815-regulator.c b/drivers/regulator/bd71815-regulator.c index 79fbb45297f6..8da57a7bb2f1 100644 --- a/drivers/regulator/bd71815-regulator.c +++ b/drivers/regulator/bd71815-regulator.c @@ -173,9 +173,9 @@ static int set_hw_dvs_levels(struct device_node *np, const struct regulator_desc *desc, struct regulator_config *cfg) { - struct bd71815_regulator *data; + const struct bd71815_regulator *data; - data = container_of(desc, struct bd71815_regulator, desc); + data = container_of_const(desc, struct bd71815_regulator, desc); return rohm_regulator_set_dvs_levels(data->dvs, np, desc, cfg->regmap); } @@ -195,10 +195,10 @@ static int buck12_set_hw_dvs_levels(struct device_node *np, const struct regulator_desc *desc, struct regulator_config *cfg) { - struct bd71815_regulator *data; + const struct bd71815_regulator *data; int ret = 0, val; - data = container_of(desc, struct bd71815_regulator, desc); + data = container_of_const(desc, struct bd71815_regulator, desc); if (of_property_present(np, "rohm,dvs-run-voltage") || of_property_present(np, "rohm,dvs-suspend-voltage") || diff --git a/drivers/regulator/bd71828-regulator.c b/drivers/regulator/bd71828-regulator.c index dd871ffe979c..87de87793fa1 100644 --- a/drivers/regulator/bd71828-regulator.c +++ b/drivers/regulator/bd71828-regulator.c @@ -95,9 +95,9 @@ static int buck_set_hw_dvs_levels(struct device_node *np, const struct regulator_desc *desc, struct regulator_config *cfg) { - struct bd71828_regulator_data *data; + const struct bd71828_regulator_data *data; - data = container_of(desc, struct bd71828_regulator_data, desc); + data = container_of_const(desc, struct bd71828_regulator_data, desc); return rohm_regulator_set_dvs_levels(&data->dvs, np, desc, cfg->regmap); } diff --git a/drivers/regulator/bd718x7-regulator.c b/drivers/regulator/bd718x7-regulator.c index ea9c4058ee6a..1b5997c8482e 100644 --- a/drivers/regulator/bd718x7-regulator.c +++ b/drivers/regulator/bd718x7-regulator.c @@ -698,9 +698,9 @@ static int buck_set_hw_dvs_levels(struct device_node *np, const struct regulator_desc *desc, struct regulator_config *cfg) { - struct bd718xx_regulator_data *data; + const struct bd718xx_regulator_data *data; - data = container_of(desc, struct bd718xx_regulator_data, desc); + data = container_of_const(desc, struct bd718xx_regulator_data, desc); return rohm_regulator_set_dvs_levels(&data->dvs, np, desc, cfg->regmap); } diff --git a/drivers/regulator/bd96801-regulator.c b/drivers/regulator/bd96801-regulator.c index 24d21172298b..129b20c33bad 100644 --- a/drivers/regulator/bd96801-regulator.c +++ b/drivers/regulator/bd96801-regulator.c @@ -337,12 +337,12 @@ static int ldo_map_notif(int irq, struct regulator_irq_data *rid, int i; for (i = 0; i < rid->num_states; i++) { - struct bd96801_regulator_data *rdata; + const struct bd96801_regulator_data *rdata; struct regulator_dev *rdev; rdev = rid->states[i].rdev; - rdata = container_of(rdev->desc, struct bd96801_regulator_data, - desc); + rdata = container_of_const(rdev->desc, struct bd96801_regulator_data, + desc); rid->states[i].notifs = regulator_err2notif(rdata->ldo_errs); rid->states[i].errors = rdata->ldo_errs; *dev_mask |= BIT(i); @@ -354,9 +354,9 @@ static int bd96801_list_voltage_lr(struct regulator_dev *rdev, unsigned int selector) { int voltage; - struct bd96801_regulator_data *data; + const struct bd96801_regulator_data *data; - data = container_of(rdev->desc, struct bd96801_regulator_data, desc); + data = container_of_const(rdev->desc, struct bd96801_regulator_data, desc); /* * The BD096801 has voltage setting in two registers. One giving the diff --git a/drivers/regulator/core.c b/drivers/regulator/core.c index dd7b10e768c0..f4987f54e01b 100644 --- a/drivers/regulator/core.c +++ b/drivers/regulator/core.c @@ -83,6 +83,19 @@ struct regulator_supply_alias { const char *alias_supply; }; +/* + * Work item used to forward regulator events. + * + * @work: workqueue entry + * @rdev: regulator device to notify (consumer receiving the forwarded event) + * @event: event code to be forwarded + */ +struct regulator_event_work { + struct work_struct work; + struct regulator_dev *rdev; + unsigned long event; +}; + static int _regulator_is_enabled(struct regulator_dev *rdev); static int _regulator_disable(struct regulator *regulator); static int _regulator_get_error_flags(struct regulator_dev *rdev, unsigned int *flags); @@ -1618,6 +1631,8 @@ static int set_machine_constraints(struct regulator_dev *rdev) * and we have control then make sure it is enabled. */ if (rdev->constraints->always_on || rdev->constraints->boot_on) { + bool supply_enabled = false; + /* If we want to enable this regulator, make sure that we know * the supplying regulator. */ @@ -1637,11 +1652,14 @@ static int set_machine_constraints(struct regulator_dev *rdev) rdev->supply = NULL; return ret; } + supply_enabled = true; } ret = _regulator_do_enable(rdev); if (ret < 0 && ret != -EINVAL) { rdev_err(rdev, "failed to enable: %pe\n", ERR_PTR(ret)); + if (supply_enabled) + regulator_disable(rdev->supply); return ret; } @@ -1659,6 +1677,104 @@ static int set_machine_constraints(struct regulator_dev *rdev) } /** + * regulator_event_work_fn - process a deferred regulator event + * @work: work_struct queued by the notifier + * + * Calls the regulator's notifier chain in process context while holding + * the rdev lock, then releases the device reference. + */ +static void regulator_event_work_fn(struct work_struct *work) +{ + struct regulator_event_work *rew = + container_of(work, struct regulator_event_work, work); + struct regulator_dev *rdev = rew->rdev; + int ret; + + regulator_lock(rdev); + ret = regulator_notifier_call_chain(rdev, rew->event, NULL); + regulator_unlock(rdev); + if (ret == NOTIFY_BAD) + dev_err(rdev_get_dev(rdev), "failed to forward regulator event\n"); + + put_device(rdev_get_dev(rdev)); + kfree(rew); +} + +/** + * regulator_event_forward_notifier - notifier callback for supply events + * @nb: notifier block embedded in the regulator + * @event: regulator event code + * @data: unused + * + * Packages the event into a work item and schedules it in process context. + * Takes a reference on @rdev->dev to pin the regulator until the work + * completes (see put_device() in the worker). + * + * Return: NOTIFY_OK on success, NOTIFY_DONE for events that are not forwarded. + */ +static int regulator_event_forward_notifier(struct notifier_block *nb, + unsigned long event, + void __always_unused *data) +{ + struct regulator_dev *rdev = container_of(nb, struct regulator_dev, + supply_fwd_nb); + struct regulator_event_work *rew; + + switch (event) { + case REGULATOR_EVENT_UNDER_VOLTAGE: + break; + default: + /* Only forward allowed events downstream. */ + return NOTIFY_DONE; + } + + rew = kmalloc(sizeof(*rew), GFP_ATOMIC); + if (!rew) + return NOTIFY_DONE; + + get_device(rdev_get_dev(rdev)); + rew->rdev = rdev; + rew->event = event; + INIT_WORK(&rew->work, regulator_event_work_fn); + + queue_work(system_highpri_wq, &rew->work); + + return NOTIFY_OK; +} + +/** + * register_regulator_event_forwarding - enable supply event forwarding + * @rdev: regulator device + * + * Registers a notifier on the regulator's supply so that supply events + * are forwarded to the consumer regulator via the deferred work handler. + * + * Return: 0 on success, -EALREADY if already enabled, or a negative error code. + */ +static int register_regulator_event_forwarding(struct regulator_dev *rdev) +{ + int ret; + + if (!rdev->supply) + return 0; /* top-level regulator: nothing to forward */ + + if (rdev->supply_fwd_nb.notifier_call) + return -EALREADY; + + rdev->supply_fwd_nb.notifier_call = regulator_event_forward_notifier; + + ret = regulator_register_notifier(rdev->supply, &rdev->supply_fwd_nb); + if (ret) { + dev_err(&rdev->dev, "failed to register supply notifier: %pe\n", + ERR_PTR(ret)); + rdev->supply_fwd_nb.notifier_call = NULL; + return ret; + } + + return 0; +} + +/** * set_supply - set regulator supply regulator * @rdev: regulator (locked) * @supply_rdev: supply regulator (locked)) @@ -1942,6 +2058,7 @@ static void regulator_supply_alias(struct device **dev, const char **supply) { struct regulator_supply_alias *map; + mutex_lock(®ulator_list_mutex); map = regulator_find_supply_alias(*dev, *supply); if (map) { dev_dbg(*dev, "Mapping supply %s to %s,%s\n", @@ -1950,6 +2067,7 @@ static void regulator_supply_alias(struct device **dev, const char **supply) *dev = map->alias_dev; *supply = map->alias_supply; } + mutex_unlock(®ulator_list_mutex); } static int regulator_match(struct device *dev, const void *data) @@ -2144,6 +2262,16 @@ static int regulator_resolve_supply(struct regulator_dev *rdev) goto out; } + /* + * Automatically register for event forwarding from the new supply. + * This creates the downstream propagation link for events like + * under-voltage. + */ + ret = register_regulator_event_forwarding(rdev); + if (ret < 0) + rdev_warn(rdev, "Failed to register event forwarding: %pe\n", + ERR_PTR(ret)); + regulator_unlock_two(rdev, r, &ww_ctx); /* rdev->supply was created in set_supply() */ @@ -2492,22 +2620,26 @@ int regulator_register_supply_alias(struct device *dev, const char *id, const char *alias_id) { struct regulator_supply_alias *map; + struct regulator_supply_alias *new_map; - map = regulator_find_supply_alias(dev, id); - if (map) - return -EEXIST; - - map = kzalloc(sizeof(struct regulator_supply_alias), GFP_KERNEL); - if (!map) + new_map = kzalloc(sizeof(struct regulator_supply_alias), GFP_KERNEL); + if (!new_map) return -ENOMEM; - map->src_dev = dev; - map->src_supply = id; - map->alias_dev = alias_dev; - map->alias_supply = alias_id; - - list_add(&map->list, ®ulator_supply_alias_list); + mutex_lock(®ulator_list_mutex); + map = regulator_find_supply_alias(dev, id); + if (map) { + mutex_unlock(®ulator_list_mutex); + kfree(new_map); + return -EEXIST; + } + new_map->src_dev = dev; + new_map->src_supply = id; + new_map->alias_dev = alias_dev; + new_map->alias_supply = alias_id; + list_add(&new_map->list, ®ulator_supply_alias_list); + mutex_unlock(®ulator_list_mutex); pr_info("Adding alias for supply %s,%s -> %s,%s\n", id, dev_name(dev), alias_id, dev_name(alias_dev)); @@ -2527,11 +2659,13 @@ void regulator_unregister_supply_alias(struct device *dev, const char *id) { struct regulator_supply_alias *map; + mutex_lock(®ulator_list_mutex); map = regulator_find_supply_alias(dev, id); if (map) { list_del(&map->list); kfree(map); } + mutex_unlock(®ulator_list_mutex); } EXPORT_SYMBOL_GPL(regulator_unregister_supply_alias); @@ -2616,6 +2750,13 @@ static int regulator_ena_gpio_request(struct regulator_dev *rdev, mutex_lock(®ulator_list_mutex); + if (gpiod_is_shared(gpiod)) + /* + * The sharing of this GPIO pin is managed internally by + * GPIOLIB. We don't need to keep track of its enable count. + */ + goto skip_compare; + list_for_each_entry(pin, ®ulator_ena_gpio_list, list) { if (gpiod_is_equal(pin->gpiod, gpiod)) { rdev_dbg(rdev, "GPIO is already used\n"); @@ -2628,6 +2769,7 @@ static int regulator_ena_gpio_request(struct regulator_dev *rdev, return -ENOMEM; } +skip_compare: pin = new_pin; new_pin = NULL; @@ -6031,6 +6173,9 @@ void regulator_unregister(struct regulator_dev *rdev) return; if (rdev->supply) { + regulator_unregister_notifier(rdev->supply, + &rdev->supply_fwd_nb); + while (rdev->use_count--) regulator_disable(rdev->supply); regulator_put(rdev->supply); diff --git a/drivers/regulator/fp9931.c b/drivers/regulator/fp9931.c new file mode 100644 index 000000000000..fef0bb07fd5d --- /dev/null +++ b/drivers/regulator/fp9931.c @@ -0,0 +1,551 @@ +// SPDX-License-Identifier: GPL-2.0-only +// Copyright (C) 2025 Andreas Kemnade + +/* Datasheet: https://www.fitipower.com/dl/file/flXa6hIchVeu0W3K */ + +#include <linux/cleanup.h> +#include <linux/completion.h> +#include <linux/gpio/consumer.h> +#include <linux/i2c.h> +#include <linux/module.h> +#include <linux/mutex.h> +#include <linux/hwmon.h> +#include <linux/pm_runtime.h> +#include <linux/property.h> +#include <linux/regulator/consumer.h> +#include <linux/regulator/driver.h> +#include <linux/regulator/machine.h> +#include <linux/regmap.h> + +#define FP9931_REG_TMST_VALUE 0 +#define FP9931_REG_VCOM_SETTING 1 +#define FP9931_REG_VPOSNEG_SETTING 2 +#define FP9931_REG_PWRON_DELAY 3 +#define FP9931_REG_CONTROL_REG1 11 + +#define PGOOD_TIMEOUT_MSECS 200 + +struct fp9931_data { + struct device *dev; + struct regmap *regmap; + struct regulator *vin_reg; + struct gpio_desc *pgood_gpio; + struct gpio_desc *en_gpio; + struct gpio_desc *en_ts_gpio; + struct completion pgood_completion; + int pgood_irq; +}; + +static const unsigned int VPOSNEG_table[] = { + 7040000, + 7040000, + 7040000, + 7040000, + 7040000, + 7040000, + 7260000, + 7490000, + 7710000, + 7930000, + 8150000, + 8380000, + 8600000, + 8820000, + 9040000, + 9270000, + 9490000, + 9710000, + 9940000, + 10160000, + 10380000, + 10600000, + 10830000, + 11050000, + 11270000, + 11490000, + 11720000, + 11940000, + 12160000, + 12380000, + 12610000, + 12830000, + 13050000, + 13280000, + 13500000, + 13720000, + 13940000, + 14170000, + 14390000, + 14610000, + 14830000, + 15060000, +}; + +static const struct hwmon_channel_info *fp9931_info[] = { + HWMON_CHANNEL_INFO(chip, HWMON_C_REGISTER_TZ), + HWMON_CHANNEL_INFO(temp, HWMON_T_INPUT), + NULL +}; + +static int setup_timings(struct fp9931_data *data) +{ + u32 tdly[4]; + u8 tdlys = 0; + int i; + int ret; + + ret = device_property_count_u32(data->dev, "fitipower,tdly-ms"); + if (ret == -EINVAL) /* property is optional */ + return 0; + + if (ret < 0) + return ret; + + if (ret != ARRAY_SIZE(tdly)) { + dev_err(data->dev, "invalid delay specification"); + return -EINVAL; + } + + ret = device_property_read_u32_array(data->dev, "fitipower,tdly-ms", + tdly, ARRAY_SIZE(tdly)); + if (ret) + return ret; + + for (i = ARRAY_SIZE(tdly) - 1; i >= 0; i--) { + if (tdly[i] > 4 || tdly[i] == 3) + return -EINVAL; + + if (tdly[i] == 4) /* convert from ms */ + tdly[i] = 3; + + tdlys <<= 2; + tdlys |= tdly[i]; + } + + ret = pm_runtime_resume_and_get(data->dev); + if (ret < 0) + return ret; + + ret = regmap_write(data->regmap, FP9931_REG_PWRON_DELAY, tdlys); + pm_runtime_put_autosuspend(data->dev); + + return ret; +} + +static int fp9931_hwmon_read(struct device *dev, enum hwmon_sensor_types type, + u32 attr, int channel, long *temp) +{ + struct fp9931_data *data = dev_get_drvdata(dev); + unsigned int val; + int ret; + + ret = pm_runtime_resume_and_get(data->dev); + if (ret < 0) + return ret; + + ret = regmap_read(data->regmap, FP9931_REG_TMST_VALUE, &val); + if (ret) + return ret; + + pm_runtime_put_autosuspend(data->dev); + *temp = (s8)val * 1000; + + return 0; +} + +static umode_t fp9931_hwmon_is_visible(const void *data, + enum hwmon_sensor_types type, + u32 attr, int channel) +{ + return 0444; +} + +static const struct hwmon_ops fp9931_hwmon_ops = { + .is_visible = fp9931_hwmon_is_visible, + .read = fp9931_hwmon_read, +}; + +static const struct hwmon_chip_info fp9931_chip_info = { + .ops = &fp9931_hwmon_ops, + .info = fp9931_info, +}; + +static int fp9931_runtime_suspend(struct device *dev) +{ + int ret = 0; + struct fp9931_data *data = dev_get_drvdata(dev); + + if (data->en_ts_gpio) + gpiod_set_value_cansleep(data->en_ts_gpio, 0); + + if (data->vin_reg) { + ret = regulator_disable(data->vin_reg); + regcache_mark_dirty(data->regmap); + } + + return ret; +} + +static int fp9931_runtime_resume(struct device *dev) +{ + int ret = 0; + struct fp9931_data *data = dev_get_drvdata(dev); + + if (data->vin_reg) + ret = regulator_enable(data->vin_reg); + + if (ret) + return ret; + + if (data->en_ts_gpio) { + gpiod_set_value_cansleep(data->en_ts_gpio, 1); + /* wait for one ADC conversion to have sane temperature */ + usleep_range(10000, 15000); + } + + ret = regcache_sync(data->regmap); + + return ret; +} + +static bool fp9931_volatile_reg(struct device *dev, unsigned int reg) +{ + return reg == FP9931_REG_TMST_VALUE; +} + +static const struct reg_default fp9931_reg_default = { + .reg = FP9931_REG_VCOM_SETTING, + .def = 0x80, +}; + +static const struct regmap_config regmap_config = { + .reg_bits = 8, + .val_bits = 8, + .max_register = 12, + .cache_type = REGCACHE_FLAT, + .volatile_reg = fp9931_volatile_reg, + .reg_defaults = &fp9931_reg_default, + .num_reg_defaults = 1, +}; + +static void disable_nopm(void *d) +{ + struct fp9931_data *data = d; + + fp9931_runtime_suspend(data->dev); +} + +static int fp9931_v3p3_enable(struct regulator_dev *rdev) +{ + struct fp9931_data *data = rdev_get_drvdata(rdev); + int ret; + + ret = pm_runtime_resume_and_get(data->dev); + if (ret < 0) + return ret; + + ret = regulator_enable_regmap(rdev); + if (ret < 0) + pm_runtime_put_autosuspend(data->dev); + + return ret; +} + +static int fp9931_v3p3_disable(struct regulator_dev *rdev) +{ + struct fp9931_data *data = rdev_get_drvdata(rdev); + int ret; + + ret = regulator_disable_regmap(rdev); + pm_runtime_put_autosuspend(data->dev); + + return ret; +} + +static int fp9931_v3p3_is_enabled(struct regulator_dev *rdev) +{ + struct fp9931_data *data = rdev_get_drvdata(rdev); + int ret; + + if (pm_runtime_status_suspended(data->dev)) + return 0; + + ret = pm_runtime_resume_and_get(data->dev); + if (ret < 0) + return 0; + + ret = regulator_is_enabled_regmap(rdev); + + pm_runtime_put_autosuspend(data->dev); + return ret; +} + +static const struct regulator_ops fp9931_v3p3ops = { + .list_voltage = regulator_list_voltage_linear, + .enable = fp9931_v3p3_enable, + .disable = fp9931_v3p3_disable, + .is_enabled = fp9931_v3p3_is_enabled, +}; + +static int fp9931_check_powergood(struct regulator_dev *rdev) +{ + struct fp9931_data *data = rdev_get_drvdata(rdev); + + if (pm_runtime_status_suspended(data->dev)) + return 0; + + return gpiod_get_value_cansleep(data->pgood_gpio); +} + +static int fp9931_get_voltage_sel(struct regulator_dev *rdev) +{ + struct fp9931_data *data = rdev_get_drvdata(rdev); + int ret; + + ret = pm_runtime_resume_and_get(data->dev); + if (ret < 0) + return ret; + + ret = regulator_get_voltage_sel_regmap(rdev); + pm_runtime_put_autosuspend(data->dev); + + return ret; +} + +static int fp9931_set_voltage_sel(struct regulator_dev *rdev, unsigned int selector) +{ + struct fp9931_data *data = rdev_get_drvdata(rdev); + int ret; + + ret = pm_runtime_resume_and_get(data->dev); + if (ret < 0) + return ret; + + ret = regulator_set_voltage_sel_regmap(rdev, selector); + pm_runtime_put_autosuspend(data->dev); + + return ret; +} + +static irqreturn_t pgood_handler(int irq, void *dev_id) +{ + struct fp9931_data *data = dev_id; + + complete(&data->pgood_completion); + + return IRQ_HANDLED; +} + +static int fp9931_set_enable(struct regulator_dev *rdev) +{ + struct fp9931_data *data = rdev_get_drvdata(rdev); + int ret; + + ret = pm_runtime_resume_and_get(data->dev); + if (ret < 0) + return ret; + + reinit_completion(&data->pgood_completion); + gpiod_set_value_cansleep(data->en_gpio, 1); + dev_dbg(data->dev, "turning on..."); + wait_for_completion_timeout(&data->pgood_completion, + msecs_to_jiffies(PGOOD_TIMEOUT_MSECS)); + dev_dbg(data->dev, "turned on"); + if (gpiod_get_value_cansleep(data->pgood_gpio) != 1) { + pm_runtime_put_autosuspend(data->dev); + return -ETIMEDOUT; + } + + return 0; +} + +static int fp9931_clear_enable(struct regulator_dev *rdev) +{ + struct fp9931_data *data = rdev_get_drvdata(rdev); + + gpiod_set_value_cansleep(data->en_gpio, 0); + pm_runtime_put_autosuspend(data->dev); + return 0; +} + +static const struct regulator_ops fp9931_vcom_ops = { + .list_voltage = regulator_list_voltage_linear, + .map_voltage = regulator_map_voltage_linear, + .enable = fp9931_set_enable, + .disable = fp9931_clear_enable, + .is_enabled = fp9931_check_powergood, + .set_voltage_sel = fp9931_set_voltage_sel, + .get_voltage_sel = fp9931_get_voltage_sel, +}; + +static const struct regulator_ops fp9931_vposneg_ops = { + .list_voltage = regulator_list_voltage_table, + .map_voltage = regulator_map_voltage_ascend, + /* gets enabled by enabling vcom, too */ + .is_enabled = fp9931_check_powergood, + .set_voltage_sel = fp9931_set_voltage_sel, + .get_voltage_sel = fp9931_get_voltage_sel, +}; + +static const struct regulator_desc regulators[] = { + { + .name = "v3p3", + .of_match = of_match_ptr("v3p3"), + .id = 0, + .ops = &fp9931_v3p3ops, + .type = REGULATOR_VOLTAGE, + .owner = THIS_MODULE, + .enable_reg = FP9931_REG_CONTROL_REG1, + .enable_mask = BIT(1), + .n_voltages = 1, + .min_uV = 3300000 + }, + { + .name = "vposneg", + .of_match = of_match_ptr("vposneg"), + .id = 1, + .ops = &fp9931_vposneg_ops, + .type = REGULATOR_VOLTAGE, + .owner = THIS_MODULE, + .n_voltages = ARRAY_SIZE(VPOSNEG_table), + .vsel_reg = FP9931_REG_VPOSNEG_SETTING, + .vsel_mask = 0x3F, + .volt_table = VPOSNEG_table, + }, + { + .name = "vcom", + .of_match = of_match_ptr("vcom"), + .id = 2, + .ops = &fp9931_vcom_ops, + .type = REGULATOR_VOLTAGE, + .owner = THIS_MODULE, + .n_voltages = 255, + .min_uV = 0, + .uV_step = 5000000 / 255, + .vsel_reg = FP9931_REG_VCOM_SETTING, + .vsel_mask = 0xFF + }, +}; + +static int fp9931_probe(struct i2c_client *client) +{ + struct fp9931_data *data; + struct regulator_config config = { }; + struct regulator_dev *rdev; + int ret = 0; + int i; + + data = devm_kzalloc(&client->dev, sizeof(*data), GFP_KERNEL); + data->regmap = devm_regmap_init_i2c(client, ®map_config); + if (IS_ERR(data->regmap)) + return dev_err_probe(&client->dev, PTR_ERR(data->regmap), + "failed to allocate regmap!\n"); + + data->vin_reg = devm_regulator_get_optional(&client->dev, "vin"); + if (IS_ERR(data->vin_reg)) + return dev_err_probe(&client->dev, PTR_ERR(data->vin_reg), + "failed to get vin regulator\n"); + + data->pgood_gpio = devm_gpiod_get(&client->dev, "pg", GPIOD_IN); + if (IS_ERR(data->pgood_gpio)) + return dev_err_probe(&client->dev, + PTR_ERR(data->pgood_gpio), + "failed to get power good gpio\n"); + + data->pgood_irq = gpiod_to_irq(data->pgood_gpio); + if (data->pgood_irq < 0) + return data->pgood_irq; + + data->en_gpio = devm_gpiod_get(&client->dev, "enable", GPIOD_OUT_LOW); + if (IS_ERR(data->en_gpio)) + return dev_err_probe(&client->dev, PTR_ERR(data->en_gpio), + "failed to get en gpio\n"); + + data->en_ts_gpio = devm_gpiod_get_optional(&client->dev, "en-ts", GPIOD_OUT_LOW); + if (IS_ERR(data->en_ts_gpio)) + return dev_err_probe(&client->dev, + PTR_ERR(data->en_ts_gpio), + "failed to get en gpio\n"); + + data->dev = &client->dev; + i2c_set_clientdata(client, data); + + init_completion(&data->pgood_completion); + + ret = devm_request_threaded_irq(&client->dev, data->pgood_irq, NULL, + pgood_handler, + IRQF_TRIGGER_RISING | IRQF_ONESHOT, + "PGOOD", data); + if (ret) + return dev_err_probe(&client->dev, ret, + "failed to request irq\n"); + + if (IS_ENABLED(CONFIG_PM)) { + devm_pm_runtime_enable(&client->dev); + pm_runtime_set_autosuspend_delay(&client->dev, 4000); + pm_runtime_use_autosuspend(&client->dev); + } else { + ret = fp9931_runtime_resume(&client->dev); + if (ret < 0) + return ret; + + devm_add_action_or_reset(&client->dev, disable_nopm, data); + } + + ret = setup_timings(data); + if (ret) + return dev_err_probe(&client->dev, ret, "failed to setup timings\n"); + + config.driver_data = data; + config.dev = &client->dev; + config.regmap = data->regmap; + + for (i = 0; i < ARRAY_SIZE(regulators); i++) { + rdev = devm_regulator_register(&client->dev, ®ulators[i], + &config); + if (IS_ERR(rdev)) + return dev_err_probe(&client->dev, PTR_ERR(rdev), + "failed to register %s regulator\n", + regulators[i].name); + } + + if (IS_REACHABLE(CONFIG_HWMON)) { + struct device *hwmon_dev; + + hwmon_dev = devm_hwmon_device_register_with_info(&client->dev, "fp9931", data, + &fp9931_chip_info, NULL); + if (IS_ERR(hwmon_dev)) + dev_notice(&client->dev, "failed to register hwmon\n"); + } + + return 0; +} + +static const struct dev_pm_ops fp9931_pm_ops = { + SET_RUNTIME_PM_OPS(fp9931_runtime_suspend, fp9931_runtime_resume, NULL) +}; + +static const struct of_device_id fp9931_dt_ids[] = { + { + .compatible = "fitipower,fp9931", + }, { + /* sentinel */ + } +}; +MODULE_DEVICE_TABLE(of, fp9931_dt_ids); + +static struct i2c_driver fp9931_i2c_driver = { + .driver = { + .name = "fp9931", + .of_match_table = fp9931_dt_ids, + .pm = &fp9931_pm_ops, + }, + .probe = fp9931_probe, +}; + +module_i2c_driver(fp9931_i2c_driver); + +/* Module information */ +MODULE_DESCRIPTION("FP9931 regulator driver"); +MODULE_LICENSE("GPL"); + diff --git a/drivers/regulator/hi6421-regulator.c b/drivers/regulator/hi6421-regulator.c index 69d24728d6a4..cd06030c3587 100644 --- a/drivers/regulator/hi6421-regulator.c +++ b/drivers/regulator/hi6421-regulator.c @@ -387,7 +387,7 @@ static unsigned int hi6421_regulator_ldo_get_mode(struct regulator_dev *rdev) const struct hi6421_regulator_info *info; unsigned int reg_val; - info = container_of(rdev->desc, struct hi6421_regulator_info, desc); + info = container_of_const(rdev->desc, struct hi6421_regulator_info, desc); regmap_read(rdev->regmap, rdev->desc->enable_reg, ®_val); if (reg_val & info->mode_mask) return REGULATOR_MODE_IDLE; @@ -400,7 +400,7 @@ static unsigned int hi6421_regulator_buck_get_mode(struct regulator_dev *rdev) const struct hi6421_regulator_info *info; unsigned int reg_val; - info = container_of(rdev->desc, struct hi6421_regulator_info, desc); + info = container_of_const(rdev->desc, struct hi6421_regulator_info, desc); regmap_read(rdev->regmap, rdev->desc->enable_reg, ®_val); if (reg_val & info->mode_mask) return REGULATOR_MODE_STANDBY; @@ -414,7 +414,7 @@ static int hi6421_regulator_ldo_set_mode(struct regulator_dev *rdev, const struct hi6421_regulator_info *info; unsigned int new_mode; - info = container_of(rdev->desc, struct hi6421_regulator_info, desc); + info = container_of_const(rdev->desc, struct hi6421_regulator_info, desc); switch (mode) { case REGULATOR_MODE_NORMAL: new_mode = 0; @@ -439,7 +439,7 @@ static int hi6421_regulator_buck_set_mode(struct regulator_dev *rdev, const struct hi6421_regulator_info *info; unsigned int new_mode; - info = container_of(rdev->desc, struct hi6421_regulator_info, desc); + info = container_of_const(rdev->desc, struct hi6421_regulator_info, desc); switch (mode) { case REGULATOR_MODE_NORMAL: new_mode = 0; @@ -464,7 +464,7 @@ hi6421_regulator_ldo_get_optimum_mode(struct regulator_dev *rdev, { const struct hi6421_regulator_info *info; - info = container_of(rdev->desc, struct hi6421_regulator_info, desc); + info = container_of_const(rdev->desc, struct hi6421_regulator_info, desc); if (load_uA > info->eco_microamp) return REGULATOR_MODE_NORMAL; diff --git a/drivers/regulator/hi6421v530-regulator.c b/drivers/regulator/hi6421v530-regulator.c index b3ebd1624814..1822f5daf6ce 100644 --- a/drivers/regulator/hi6421v530-regulator.c +++ b/drivers/regulator/hi6421v530-regulator.c @@ -110,7 +110,7 @@ static unsigned int hi6421v530_regulator_ldo_get_mode( const struct hi6421v530_regulator_info *info; unsigned int reg_val; - info = container_of(rdev->desc, struct hi6421v530_regulator_info, rdesc); + info = container_of_const(rdev->desc, struct hi6421v530_regulator_info, rdesc); regmap_read(rdev->regmap, rdev->desc->enable_reg, ®_val); if (reg_val & (info->mode_mask)) @@ -125,7 +125,7 @@ static int hi6421v530_regulator_ldo_set_mode(struct regulator_dev *rdev, const struct hi6421v530_regulator_info *info; unsigned int new_mode; - info = container_of(rdev->desc, struct hi6421v530_regulator_info, rdesc); + info = container_of_const(rdev->desc, struct hi6421v530_regulator_info, rdesc); switch (mode) { case REGULATOR_MODE_NORMAL: new_mode = 0; diff --git a/drivers/regulator/hi6421v600-regulator.c b/drivers/regulator/hi6421v600-regulator.c index e5f6fbfc9016..e7c8bc10cf24 100644 --- a/drivers/regulator/hi6421v600-regulator.c +++ b/drivers/regulator/hi6421v600-regulator.c @@ -121,7 +121,7 @@ static unsigned int hi6421_spmi_regulator_get_mode(struct regulator_dev *rdev) const struct hi6421_spmi_reg_info *sreg; unsigned int reg_val; - sreg = container_of(rdev->desc, struct hi6421_spmi_reg_info, desc); + sreg = container_of_const(rdev->desc, struct hi6421_spmi_reg_info, desc); regmap_read(rdev->regmap, rdev->desc->enable_reg, ®_val); if (reg_val & sreg->eco_mode_mask) @@ -136,7 +136,7 @@ static int hi6421_spmi_regulator_set_mode(struct regulator_dev *rdev, const struct hi6421_spmi_reg_info *sreg; unsigned int val; - sreg = container_of(rdev->desc, struct hi6421_spmi_reg_info, desc); + sreg = container_of_const(rdev->desc, struct hi6421_spmi_reg_info, desc); switch (mode) { case REGULATOR_MODE_NORMAL: val = 0; @@ -162,7 +162,7 @@ hi6421_spmi_regulator_get_optimum_mode(struct regulator_dev *rdev, { const struct hi6421_spmi_reg_info *sreg; - sreg = container_of(rdev->desc, struct hi6421_spmi_reg_info, desc); + sreg = container_of_const(rdev->desc, struct hi6421_spmi_reg_info, desc); if (!sreg->eco_uA || ((unsigned int)load_uA > sreg->eco_uA)) return REGULATOR_MODE_NORMAL; diff --git a/drivers/regulator/irq_helpers.c b/drivers/regulator/irq_helpers.c index 5742faee8071..5b3cfac28667 100644 --- a/drivers/regulator/irq_helpers.c +++ b/drivers/regulator/irq_helpers.c @@ -146,7 +146,7 @@ enable_out: reschedule: if (!d->high_prio) - mod_delayed_work(system_wq, &h->isr_work, + mod_delayed_work(system_dfl_wq, &h->isr_work, msecs_to_jiffies(tmo)); else mod_delayed_work(system_highpri_wq, &h->isr_work, diff --git a/drivers/regulator/max77650-regulator.c b/drivers/regulator/max77650-regulator.c index 7368f54f046d..a809264c77fc 100644 --- a/drivers/regulator/max77650-regulator.c +++ b/drivers/regulator/max77650-regulator.c @@ -68,7 +68,7 @@ static int max77650_regulator_is_enabled(struct regulator_dev *rdev) struct regmap *map; int val, rv, en; - rdesc = container_of(rdev->desc, struct max77650_regulator_desc, desc); + rdesc = container_of_const(rdev->desc, struct max77650_regulator_desc, desc); map = rdev_get_regmap(rdev); rv = regmap_read(map, rdesc->regB, &val); @@ -85,7 +85,7 @@ static int max77650_regulator_enable(struct regulator_dev *rdev) const struct max77650_regulator_desc *rdesc; struct regmap *map; - rdesc = container_of(rdev->desc, struct max77650_regulator_desc, desc); + rdesc = container_of_const(rdev->desc, struct max77650_regulator_desc, desc); map = rdev_get_regmap(rdev); return regmap_update_bits(map, rdesc->regB, @@ -98,7 +98,7 @@ static int max77650_regulator_disable(struct regulator_dev *rdev) const struct max77650_regulator_desc *rdesc; struct regmap *map; - rdesc = container_of(rdev->desc, struct max77650_regulator_desc, desc); + rdesc = container_of_const(rdev->desc, struct max77650_regulator_desc, desc); map = rdev_get_regmap(rdev); return regmap_update_bits(map, rdesc->regB, diff --git a/drivers/regulator/mt6315-regulator.c b/drivers/regulator/mt6315-regulator.c index 2608a6652d77..d3f93aae0fc5 100644 --- a/drivers/regulator/mt6315-regulator.c +++ b/drivers/regulator/mt6315-regulator.c @@ -80,7 +80,7 @@ static unsigned int mt6315_regulator_get_mode(struct regulator_dev *rdev) int ret, regval; u32 modeset_mask; - info = container_of(rdev->desc, struct mt6315_regulator_info, desc); + info = container_of_const(rdev->desc, struct mt6315_regulator_info, desc); modeset_mask = init->modeset_mask[rdev_get_id(rdev)]; ret = regmap_read(rdev->regmap, MT6315_BUCK_TOP_4PHASE_ANA_CON42, ®val); if (ret != 0) { @@ -111,7 +111,7 @@ static int mt6315_regulator_set_mode(struct regulator_dev *rdev, int ret, val, curr_mode; u32 modeset_mask; - info = container_of(rdev->desc, struct mt6315_regulator_info, desc); + info = container_of_const(rdev->desc, struct mt6315_regulator_info, desc); modeset_mask = init->modeset_mask[rdev_get_id(rdev)]; curr_mode = mt6315_regulator_get_mode(rdev); switch (mode) { @@ -165,7 +165,7 @@ static int mt6315_get_status(struct regulator_dev *rdev) int ret; u32 regval; - info = container_of(rdev->desc, struct mt6315_regulator_info, desc); + info = container_of_const(rdev->desc, struct mt6315_regulator_info, desc); ret = regmap_read(rdev->regmap, info->status_reg, ®val); if (ret < 0) { dev_err(&rdev->dev, "Failed to get enable reg: %d\n", ret); diff --git a/drivers/regulator/mt6316-regulator.c b/drivers/regulator/mt6316-regulator.c new file mode 100644 index 000000000000..952852bbe923 --- /dev/null +++ b/drivers/regulator/mt6316-regulator.c @@ -0,0 +1,345 @@ +// SPDX-License-Identifier: GPL-2.0 +// +// Copyright (c) 2024 MediaTek Inc. +// Copyright (c) 2025 Collabora Ltd +// AngeloGioacchino Del Regno <angelogioacchino.delregno@collabora.com> + +#include <linux/module.h> +#include <linux/of.h> +#include <linux/regmap.h> +#include <linux/spmi.h> + +#include <linux/regulator/driver.h> +#include <linux/regulator/machine.h> +#include <linux/regulator/of_regulator.h> + +#define MT6316_BUCK_MODE_AUTO 0 +#define MT6316_BUCK_MODE_FORCE_PWM 1 +#define MT6316_BUCK_MODE_LP 2 + +#define MT6316_CHIP_ID 0x20b +#define MT6316_BUCK_TOP_CON0 0x1440 +#define EN_SET_OFFSET 0x1 +#define EN_CLR_OFFSET 0x2 + +#define MT6316_BUCK_TOP_CON1 0x1443 + +#define MT6316_BUCK_TOP_ELR0 0x1448 +#define MT6316_BUCK_TOP_ELR2 0x144a +#define MT6316_BUCK_TOP_ELR4 0x144c +#define MT6316_BUCK_TOP_ELR6 0x144e +#define MT6316_VSEL_MASK GENMASK(8, 0) + +#define MT6316_VBUCK1_DBG 0x14a8 +#define MT6316_VBUCK2_DBG 0x1528 +#define MT6316_VBUCK3_DBG 0x15a8 +#define MT6316_VBUCK4_DBG 0x1628 +#define MT6316_BUCK_QI BIT(0) + +#define MT6316_BUCK_TOP_4PHASE_TOP_ANA_CON0 0x1688 +#define MT6316_BUCK_TOP_4PHASE_TOP_ELR_0 0x1690 + +enum mt6316_type { + MT6316_TYPE_2PHASE, + MT6316_TYPE_3PHASE, + MT6316_TYPE_4PHASE +}; + +/** + * struct mt6316_regulator_info - MT6316 regulators information + * @desc: Regulator description structure + * @debug_reg: Debug register for regulator status + * @lp_mode_reg: Low Power mode register (normal/idle) + * @lp_mode_mask: Low Power mode regulator mask + * @modeset_reg: AUTO/PWM mode register + * @modeset_mask: AUTO/PWM regulator mask + */ +struct mt6316_regulator_info { + struct regulator_desc desc; + u16 debug_reg; + u16 lp_mode_reg; + u16 lp_mode_mask; + u16 modeset_reg; + u16 modeset_mask; +}; + +#define MT6316_BUCK(match, vreg_id, min, max, step, vs_reg) \ +{ \ + .desc = { \ + .name = match, \ + .of_match = of_match_ptr(match), \ + .ops = &mt6316_vreg_setclr_ops, \ + .type = REGULATOR_VOLTAGE, \ + .owner = THIS_MODULE, \ + .n_voltages = (max - min) / step + 1, \ + .min_uV = min, \ + .uV_step = step, \ + .enable_reg = MT6316_BUCK_TOP_CON0, \ + .enable_mask = BIT(vreg_id - 1), \ + .vsel_reg = vs_reg, \ + .vsel_mask = MT6316_VSEL_MASK, \ + .of_map_mode = mt6316_map_mode, \ + }, \ + .lp_mode_reg = MT6316_BUCK_TOP_CON1, \ + .lp_mode_mask = BIT(vreg_id - 1), \ + .modeset_reg = MT6316_BUCK_TOP_4PHASE_TOP_ANA_CON0, \ + .modeset_mask = BIT(vreg_id - 1), \ + .debug_reg = MT6316_VBUCK##vreg_id##_DBG, \ +} + +/* Values in some MT6316 registers are big endian, 9 bits long... */ +static inline u16 mt6316_be9_to_cpu(u16 val) +{ + return ((val >> 8) & BIT(0)) | ((val & GENMASK(7, 0)) << 1); +} + +static inline u16 mt6316_cpu_to_be9(u16 val) +{ + return ((val & BIT(0)) << 8) | (val >> 1); +} + +static unsigned int mt6316_map_mode(u32 mode) +{ + switch (mode) { + case MT6316_BUCK_MODE_AUTO: + return REGULATOR_MODE_NORMAL; + case MT6316_BUCK_MODE_FORCE_PWM: + return REGULATOR_MODE_FAST; + case MT6316_BUCK_MODE_LP: + return REGULATOR_MODE_IDLE; + default: + return REGULATOR_MODE_INVALID; + } +} + +static int mt6316_vreg_enable_setclr(struct regulator_dev *rdev) +{ + return regmap_write(rdev->regmap, rdev->desc->enable_reg + EN_SET_OFFSET, + rdev->desc->enable_mask); +} + +static int mt6316_vreg_disable_setclr(struct regulator_dev *rdev) +{ + return regmap_write(rdev->regmap, rdev->desc->enable_reg + EN_CLR_OFFSET, + rdev->desc->enable_mask); +} + +static int mt6316_regulator_set_voltage_sel(struct regulator_dev *rdev, unsigned int selector) +{ + u16 val = mt6316_cpu_to_be9(selector); + + return regmap_bulk_write(rdev->regmap, rdev->desc->vsel_reg, &val, sizeof(val)); +} + +static int mt6316_regulator_get_voltage_sel(struct regulator_dev *rdev) +{ + u16 val; + int ret; + + ret = regmap_bulk_read(rdev->regmap, rdev->desc->vsel_reg, &val, sizeof(val)); + if (ret) + return ret; + + return mt6316_be9_to_cpu(val & rdev->desc->vsel_mask); +} + +static int mt6316_regulator_get_status(struct regulator_dev *rdev) +{ + struct mt6316_regulator_info *info = rdev_get_drvdata(rdev); + u32 val; + int ret; + + ret = regmap_read(rdev->regmap, info->debug_reg, &val); + if (ret) + return ret; + + return val & MT6316_BUCK_QI ? REGULATOR_STATUS_ON : REGULATOR_STATUS_OFF; +} + +static unsigned int mt6316_regulator_get_mode(struct regulator_dev *rdev) +{ + struct mt6316_regulator_info *info = rdev_get_drvdata(rdev); + unsigned int val; + int ret; + + ret = regmap_read(rdev->regmap, info->modeset_reg, &val); + if (ret) { + dev_err(&rdev->dev, "Failed to get mode: %d\n", ret); + return ret; + } + + if ((val & info->modeset_mask) == info->modeset_mask) + return REGULATOR_MODE_FAST; + + ret = regmap_read(rdev->regmap, info->lp_mode_reg, &val); + val &= info->lp_mode_mask; + if (ret) { + dev_err(&rdev->dev, "Failed to get lp mode: %d\n", ret); + return ret; + } + + return val ? REGULATOR_MODE_IDLE : REGULATOR_MODE_NORMAL; +} + +static int mt6316_regulator_set_mode(struct regulator_dev *rdev, + unsigned int mode) +{ + struct mt6316_regulator_info *info = rdev_get_drvdata(rdev); + struct regmap *regmap = rdev->regmap; + int cur_mode, ret; + + switch (mode) { + case REGULATOR_MODE_FAST: + ret = regmap_set_bits(regmap, info->modeset_reg, info->modeset_mask); + break; + case REGULATOR_MODE_NORMAL: + cur_mode = mt6316_regulator_get_mode(rdev); + if (cur_mode < 0) { + ret = cur_mode; + break; + } + + if (cur_mode == REGULATOR_MODE_FAST) { + ret = regmap_clear_bits(regmap, info->modeset_reg, info->modeset_mask); + break; + } else if (cur_mode == REGULATOR_MODE_IDLE) { + ret = regmap_clear_bits(regmap, info->lp_mode_reg, info->lp_mode_mask); + if (ret == 0) + usleep_range(100, 200); + } else { + ret = 0; + } + break; + case REGULATOR_MODE_IDLE: + ret = regmap_set_bits(regmap, info->lp_mode_reg, info->lp_mode_mask); + break; + default: + ret = -EINVAL; + } + + if (ret) { + dev_err(&rdev->dev, "Failed to set mode %u: %d\n", mode, ret); + return ret; + } + + return 0; +} + +static const struct regulator_ops mt6316_vreg_setclr_ops = { + .list_voltage = regulator_list_voltage_linear, + .map_voltage = regulator_map_voltage_linear, + .set_voltage_sel = mt6316_regulator_set_voltage_sel, + .get_voltage_sel = mt6316_regulator_get_voltage_sel, + .set_voltage_time_sel = regulator_set_voltage_time_sel, + .enable = mt6316_vreg_enable_setclr, + .disable = mt6316_vreg_disable_setclr, + .is_enabled = regulator_is_enabled_regmap, + .get_status = mt6316_regulator_get_status, + .set_mode = mt6316_regulator_set_mode, + .get_mode = mt6316_regulator_get_mode, +}; + +/* MT6316BP/VP - 2+2 phase buck */ +static struct mt6316_regulator_info mt6316bv_regulators[] = { + MT6316_BUCK("vbuck12", 1, 0, 1277500, 2500, MT6316_BUCK_TOP_ELR0), + MT6316_BUCK("vbuck34", 3, 0, 1277500, 2500, MT6316_BUCK_TOP_ELR4), +}; + +/* MT6316CP/HP/KP - 3+1 phase buck */ +static struct mt6316_regulator_info mt6316chk_regulators[] = { + MT6316_BUCK("vbuck124", 1, 0, 1277500, 2500, MT6316_BUCK_TOP_ELR0), + MT6316_BUCK("vbuck3", 3, 0, 1277500, 2500, MT6316_BUCK_TOP_ELR4), +}; + +/* MT6316DP/TP - 4 phase buck */ +static struct mt6316_regulator_info mt6316dt_regulators[] = { + MT6316_BUCK("vbuck1234", 1, 0, 1277500, 2500, MT6316_BUCK_TOP_ELR0), +}; + +static const struct regmap_config mt6316_spmi_regmap_config = { + .reg_bits = 16, + .val_bits = 8, + .max_register = 0x1700, + .fast_io = true, +}; + +static int mt6316_regulator_probe(struct spmi_device *sdev) +{ + struct regulator_config config = {}; + struct mt6316_regulator_info *info; + struct regulator_dev *rdev; + enum mt6316_type type; + int num_vregs, ret; + unsigned int i; + u32 chip_id; + + config.regmap = devm_regmap_init_spmi_ext(sdev, &mt6316_spmi_regmap_config); + if (IS_ERR(config.regmap)) + return PTR_ERR(config.regmap); + + /* + * The first read is expected to fail: this PMIC needs to be woken up + * and that can be done with any activity over the SPMI bus. + */ + regmap_read(config.regmap, MT6316_CHIP_ID, &chip_id); + + /* The second read, instead, shall not fail! */ + ret = regmap_read(config.regmap, MT6316_CHIP_ID, &chip_id); + if (ret) { + dev_err(&sdev->dev, "Cannot read Chip ID!\n"); + return ret; + } + dev_dbg(&sdev->dev, "Chip ID: 0x%x\n", chip_id); + + config.dev = &sdev->dev; + + type = (uintptr_t)device_get_match_data(&sdev->dev); + switch (type) { + case MT6316_TYPE_2PHASE: + info = mt6316bv_regulators; + num_vregs = ARRAY_SIZE(mt6316bv_regulators); + break; + case MT6316_TYPE_3PHASE: + info = mt6316chk_regulators; + num_vregs = ARRAY_SIZE(mt6316chk_regulators); + break; + case MT6316_TYPE_4PHASE: + info = mt6316dt_regulators; + num_vregs = ARRAY_SIZE(mt6316dt_regulators); + break; + default: + return -EINVAL; + } + + for (i = 0; i < num_vregs; i++) { + config.driver_data = &info[i]; + + rdev = devm_regulator_register(&sdev->dev, &info[i].desc, &config); + if (IS_ERR(rdev)) + return dev_err_probe(&sdev->dev, PTR_ERR(rdev), + "failed to register %s\n", info[i].desc.name); + } + + return 0; +} + +static const struct of_device_id mt6316_regulator_match[] = { + { .compatible = "mediatek,mt6316b-regulator", .data = (void *)MT6316_TYPE_2PHASE }, + { .compatible = "mediatek,mt6316c-regulator", .data = (void *)MT6316_TYPE_3PHASE }, + { .compatible = "mediatek,mt6316d-regulator", .data = (void *)MT6316_TYPE_4PHASE }, + { /* sentinel */ } +}; + +static struct spmi_driver mt6316_regulator_driver = { + .driver = { + .name = "mt6316-regulator", + .probe_type = PROBE_PREFER_ASYNCHRONOUS, + .of_match_table = mt6316_regulator_match, + }, + .probe = mt6316_regulator_probe, +}; +module_spmi_driver(mt6316_regulator_driver); + +MODULE_AUTHOR("AngeloGioacchino Del Regno <angelogioacchino.delregno@collabora.com>"); +MODULE_DESCRIPTION("Regulator Driver for MediaTek MT6316 PMIC"); +MODULE_LICENSE("GPL"); diff --git a/drivers/regulator/mt6358-regulator.c b/drivers/regulator/mt6358-regulator.c index e4745f616cea..2604f674be49 100644 --- a/drivers/regulator/mt6358-regulator.c +++ b/drivers/regulator/mt6358-regulator.c @@ -31,7 +31,7 @@ struct mt6358_regulator_info { u32 modeset_mask; }; -#define to_regulator_info(x) container_of((x), struct mt6358_regulator_info, desc) +#define to_regulator_info(x) container_of_const((x), struct mt6358_regulator_info, desc) #define MT6358_BUCK(match, vreg, supply, min, max, step, \ vosel_mask, _da_vsel_reg, _da_vsel_mask, \ diff --git a/drivers/regulator/mt6363-regulator.c b/drivers/regulator/mt6363-regulator.c new file mode 100644 index 000000000000..e0fbf92e7685 --- /dev/null +++ b/drivers/regulator/mt6363-regulator.c @@ -0,0 +1,938 @@ +// SPDX-License-Identifier: GPL-2.0 +// +// Copyright (c) 2024 MediaTek Inc. +// Copyright (c) 2025 Collabora Ltd +// AngeloGioacchino Del Regno <angelogioacchino.delregno@collabora.com> + +#include <linux/bitfield.h> +#include <linux/delay.h> +#include <linux/devm-helpers.h> +#include <linux/err.h> +#include <linux/interrupt.h> +#include <linux/irq.h> +#include <linux/irqdomain.h> +#include <linux/kernel.h> +#include <linux/module.h> +#include <linux/of.h> +#include <linux/of_device.h> +#include <linux/of_irq.h> +#include <linux/platform_device.h> +#include <linux/regmap.h> +#include <linux/spmi.h> + +#include <linux/regulator/driver.h> +#include <linux/regulator/machine.h> +#include <linux/regulator/mt6363-regulator.h> +#include <linux/regulator/of_regulator.h> + +#define MT6363_REGULATOR_MODE_NORMAL 0 +#define MT6363_REGULATOR_MODE_FCCM 1 +#define MT6363_REGULATOR_MODE_LP 2 +#define MT6363_REGULATOR_MODE_ULP 3 + +#define EN_SET_OFFSET 0x1 +#define EN_CLR_OFFSET 0x2 +#define OP_CFG_OFFSET 0x5 + +#define NORMAL_OP_CFG 0x10 +#define NORMAL_OP_EN 0x800000 + +#define OC_IRQ_ENABLE_DELAY_MS 10 + +/* Unlock keys for TMA and BUCK_TOP */ +#define MT6363_TMA_UNLOCK_VALUE 0x9c9c +#define MT6363_BUCK_TOP_UNLOCK_VALUE 0x5543 + +enum { + MT6363_ID_VBUCK1, + MT6363_ID_VBUCK2, + MT6363_ID_VBUCK3, + MT6363_ID_VBUCK4, + MT6363_ID_VBUCK5, + MT6363_ID_VBUCK6, + MT6363_ID_VBUCK7, + MT6363_ID_VS1, + MT6363_ID_VS2, + MT6363_ID_VS3, + MT6363_ID_VA12_1, + MT6363_ID_VA12_2, + MT6363_ID_VA15, + MT6363_ID_VAUX18, + MT6363_ID_VCN13, + MT6363_ID_VCN15, + MT6363_ID_VEMC, + MT6363_ID_VIO075, + MT6363_ID_VIO18, + MT6363_ID_VM18, + MT6363_ID_VSRAM_APU, + MT6363_ID_VSRAM_CPUB, + MT6363_ID_VSRAM_CPUM, + MT6363_ID_VSRAM_CPUL, + MT6363_ID_VSRAM_DIGRF, + MT6363_ID_VSRAM_MDFE, + MT6363_ID_VSRAM_MODEM, + MT6363_ID_VRF09, + MT6363_ID_VRF12, + MT6363_ID_VRF13, + MT6363_ID_VRF18, + MT6363_ID_VRFIO18, + MT6363_ID_VTREF18, + MT6363_ID_VUFS12, + MT6363_ID_VUFS18, +}; + +/** + * struct mt6363_regulator_info - MT6363 regulators information + * @desc: Regulator description structure + * @lp_mode_reg: Low Power mode register (normal/idle) + * @lp_mode_mask: Low Power mode regulator mask + * @hw_lp_mode_reg: Hardware voted Low Power mode register (normal/idle) + * @hw_lp_mode_mask: Hardware voted Low Power mode regulator mask + * @modeset_reg: AUTO/PWM mode register + * @modeset_mask: AUTO/PWM regulator mask + * @lp_imax_uA: Maximum load current (microamps), for Low Power mode only + * @op_en_reg: Operation mode enablement register + * @orig_op_en: Backup of a regulator's operation mode enablement register + * @orig_op_cfg: Backup of a regulator's operation mode configuration register + * @oc_work: Delayed work for enabling overcurrent IRQ + * @hwirq: PMIC-Internal HW Interrupt for overcurrent event + * @virq: Mapped Interrupt for overcurrent event + */ +struct mt6363_regulator_info { + struct regulator_desc desc; + u16 lp_mode_reg; + u16 lp_mode_mask; + u16 hw_lp_mode_reg; + u16 hw_lp_mode_mask; + u16 modeset_reg; + u16 modeset_mask; + int lp_imax_uA; + u16 op_en_reg; + u32 orig_op_en; + u8 orig_op_cfg; + struct delayed_work oc_work; + u8 hwirq; + int virq; +}; + +#define MT6363_BUCK(match, vreg, min, max, step, en_reg, lp_reg, \ + mset_reg, ocp_intn) \ +[MT6363_ID_##vreg] = { \ + .desc = { \ + .name = match, \ + .supply_name = "vsys-"match, \ + .of_match = of_match_ptr(match), \ + .ops = &mt6363_vreg_setclr_ops, \ + .type = REGULATOR_VOLTAGE, \ + .id = MT6363_ID_##vreg, \ + .owner = THIS_MODULE, \ + .n_voltages = (max - min) / step + 1, \ + .min_uV = min, \ + .uV_step = step, \ + .enable_reg = en_reg, \ + .enable_mask = BIT(MT6363_RG_BUCK_##vreg##_EN_BIT), \ + .vsel_reg = MT6363_RG_BUCK_##vreg##_VOSEL_ADDR, \ + .vsel_mask = MT6363_RG_BUCK_##vreg##_VOSEL_MASK, \ + .of_map_mode = mt6363_map_mode, \ + }, \ + .lp_mode_reg = lp_reg, \ + .lp_mode_mask = BIT(MT6363_RG_BUCK_##vreg##_LP_BIT), \ + .hw_lp_mode_reg = MT6363_BUCK_##vreg##_HW_LP_MODE, \ + .hw_lp_mode_mask = 0xc, \ + .modeset_reg = mset_reg, \ + .modeset_mask = BIT(MT6363_RG_##vreg##_FCCM_BIT), \ + .lp_imax_uA = 100000, \ + .op_en_reg = MT6363_BUCK_##vreg##_OP_EN_0, \ + .hwirq = ocp_intn, \ +} + +#define MT6363_LDO_LINEAR_OPS(match, vreg, in_sup, vops, min, max, \ + step, buck_reg, ocp_intn) \ +[MT6363_ID_##vreg] = { \ + .desc = { \ + .name = match, \ + .supply_name = in_sup, \ + .of_match = of_match_ptr(match), \ + .ops = &vops, \ + .type = REGULATOR_VOLTAGE, \ + .id = MT6363_ID_##vreg, \ + .owner = THIS_MODULE, \ + .n_voltages = (max - min) / step + 1, \ + .min_uV = min, \ + .uV_step = step, \ + .enable_reg = MT6363_RG_##buck_reg##_EN_ADDR, \ + .enable_mask = BIT(MT6363_RG_LDO_##vreg##_EN_BIT), \ + .vsel_reg = MT6363_RG_LDO_##vreg##_VOSEL_ADDR, \ + .vsel_mask = MT6363_RG_LDO_##vreg##_VOSEL_MASK, \ + .of_map_mode = mt6363_map_mode, \ + }, \ + .lp_mode_reg = MT6363_RG_##buck_reg##_LP_ADDR, \ + .lp_mode_mask = BIT(MT6363_RG_LDO_##vreg##_LP_BIT), \ + .hw_lp_mode_reg = MT6363_LDO_##vreg##_HW_LP_MODE, \ + .hw_lp_mode_mask = 0x4, \ + .hwirq = ocp_intn, \ +} + +#define MT6363_LDO_L_SC(match, vreg, inp, min, max, step, buck_reg, \ + ocp_intn) \ + MT6363_LDO_LINEAR_OPS(match, vreg, inp, mt6363_vreg_setclr_ops, \ + min, max, step, buck_reg, ocp_intn) + +#define MT6363_LDO_L(match, vreg, inp, min, max, step, buck_reg, \ + ocp_intn) \ + MT6363_LDO_LINEAR_OPS(match, vreg, inp, mt6363_ldo_linear_ops, \ + min, max, step, buck_reg, ocp_intn) + +#define MT6363_LDO_LINEAR_CAL_OPS(match, vreg, in_sup, vops, vrnum, \ + ocp_intn) \ +[MT6363_ID_##vreg] = { \ + .desc = { \ + .name = match, \ + .supply_name = in_sup, \ + .of_match = of_match_ptr(match), \ + .ops = &vops, \ + .type = REGULATOR_VOLTAGE, \ + .id = MT6363_ID_##vreg, \ + .owner = THIS_MODULE, \ + .n_voltages = ARRAY_SIZE(ldo_volt_ranges##vrnum) * 11, \ + .linear_ranges = ldo_volt_ranges##vrnum, \ + .n_linear_ranges = ARRAY_SIZE(ldo_volt_ranges##vrnum), \ + .linear_range_selectors_bitfield = ldos_cal_selectors, \ + .enable_reg = MT6363_RG_LDO_##vreg##_ADDR, \ + .enable_mask = BIT(MT6363_RG_LDO_##vreg##_EN_BIT), \ + .vsel_reg = MT6363_RG_##vreg##_VOCAL_ADDR, \ + .vsel_mask = MT6363_RG_##vreg##_VOCAL_MASK, \ + .vsel_range_reg = MT6363_RG_##vreg##_VOSEL_ADDR, \ + .vsel_range_mask = MT6363_RG_##vreg##_VOSEL_MASK, \ + .of_map_mode = mt6363_map_mode, \ + }, \ + .lp_mode_reg = MT6363_RG_LDO_##vreg##_ADDR, \ + .lp_mode_mask = BIT(MT6363_RG_LDO_##vreg##_LP_BIT), \ + .hw_lp_mode_reg = MT6363_LDO_##vreg##_HW_LP_MODE, \ + .hw_lp_mode_mask = 0x4, \ + .lp_imax_uA = 10000, \ + .op_en_reg = MT6363_LDO_##vreg##_OP_EN0, \ + .hwirq = ocp_intn, \ +} + +#define MT6363_LDO_VT(match, vreg, inp, vranges_num, ocp_intn) \ + MT6363_LDO_LINEAR_CAL_OPS(match, vreg, inp, mt6363_ldo_vtable_ops,\ + vranges_num, ocp_intn) + +static const unsigned int ldos_cal_selectors[] = { + 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15 +}; + +static const struct linear_range ldo_volt_ranges0[] = { + REGULATOR_LINEAR_RANGE(1200000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(1300000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(1500000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(1700000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(1800000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(2000000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(2500000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(2600000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(2700000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(2800000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(2900000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(3000000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(3100000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(3300000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(3400000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(3500000, 0, 10, 10000) +}; + +static const struct linear_range ldo_volt_ranges1[] = { + REGULATOR_LINEAR_RANGE(900000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(1000000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(1100000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(1200000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(1300000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(1700000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(1800000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(1810000, 0, 10, 10000) +}; + +static const struct linear_range ldo_volt_ranges2[] = { + REGULATOR_LINEAR_RANGE(1800000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(1900000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(2000000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(2100000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(2200000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(2300000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(2400000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(2500000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(2600000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(2700000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(2800000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(2900000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(3000000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(3100000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(3200000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(3300000, 0, 10, 10000) +}; + +static const struct linear_range ldo_volt_ranges3[] = { + REGULATOR_LINEAR_RANGE(600000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(700000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(800000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(900000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(1000000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(1100000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(1200000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(1300000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(1400000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(1500000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(1600000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(1700000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(1800000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(1900000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(2000000, 0, 10, 10000), + REGULATOR_LINEAR_RANGE(2100000, 0, 10, 10000) +}; + +static const struct linear_range ldo_volt_ranges4[] = { + REGULATOR_LINEAR_RANGE(550000, 0, 10, 5000), + REGULATOR_LINEAR_RANGE(600000, 0, 10, 5000), + REGULATOR_LINEAR_RANGE(650000, 0, 10, 5000), + REGULATOR_LINEAR_RANGE(700000, 0, 10, 5000), + REGULATOR_LINEAR_RANGE(750000, 0, 10, 5000), + REGULATOR_LINEAR_RANGE(800000, 0, 10, 5000), + REGULATOR_LINEAR_RANGE(900000, 0, 10, 5000), + REGULATOR_LINEAR_RANGE(950000, 0, 10, 5000), + REGULATOR_LINEAR_RANGE(1000000, 0, 10, 5000), + REGULATOR_LINEAR_RANGE(1050000, 0, 10, 5000), + REGULATOR_LINEAR_RANGE(1100000, 0, 10, 5000), + REGULATOR_LINEAR_RANGE(1150000, 0, 10, 5000), + REGULATOR_LINEAR_RANGE(1700000, 0, 10, 5000), + REGULATOR_LINEAR_RANGE(1750000, 0, 10, 5000), + REGULATOR_LINEAR_RANGE(1800000, 0, 10, 5000), + REGULATOR_LINEAR_RANGE(1850000, 0, 10, 5000) +}; + +static const struct linear_range ldo_volt_ranges5[] = { + REGULATOR_LINEAR_RANGE(600000, 0, 10, 5000), + REGULATOR_LINEAR_RANGE(650000, 0, 10, 5000), + REGULATOR_LINEAR_RANGE(700000, 0, 10, 5000), + REGULATOR_LINEAR_RANGE(750000, 0, 10, 5000), + REGULATOR_LINEAR_RANGE(800000, 0, 10, 5000) +}; + +static int mt6363_vreg_enable_setclr(struct regulator_dev *rdev) +{ + return regmap_write(rdev->regmap, rdev->desc->enable_reg + EN_SET_OFFSET, + rdev->desc->enable_mask); +} + +static int mt6363_vreg_disable_setclr(struct regulator_dev *rdev) +{ + return regmap_write(rdev->regmap, rdev->desc->enable_reg + EN_CLR_OFFSET, + rdev->desc->enable_mask); +} + +static inline unsigned int mt6363_map_mode(unsigned int mode) +{ + switch (mode) { + case MT6363_REGULATOR_MODE_NORMAL: + return REGULATOR_MODE_NORMAL; + case MT6363_REGULATOR_MODE_FCCM: + return REGULATOR_MODE_FAST; + case MT6363_REGULATOR_MODE_LP: + return REGULATOR_MODE_IDLE; + case MT6363_REGULATOR_MODE_ULP: + return REGULATOR_MODE_STANDBY; + default: + return REGULATOR_MODE_INVALID; + } +} + +static unsigned int mt6363_regulator_get_mode(struct regulator_dev *rdev) +{ + struct mt6363_regulator_info *info = rdev_get_drvdata(rdev); + unsigned int val; + int ret; + + if (info->modeset_reg) { + ret = regmap_read(rdev->regmap, info->modeset_reg, &val); + if (ret) { + dev_err(&rdev->dev, "Failed to get mt6363 mode: %d\n", ret); + return ret; + } + + if (val & info->modeset_mask) + return REGULATOR_MODE_FAST; + } else { + val = 0; + } + + ret = regmap_read(rdev->regmap, info->hw_lp_mode_reg, &val); + val &= info->hw_lp_mode_mask; + + if (ret) { + dev_err(&rdev->dev, "Failed to get lp mode: %d\n", ret); + return ret; + } + + if (val) + return REGULATOR_MODE_IDLE; + else + return REGULATOR_MODE_NORMAL; +} + +static int mt6363_buck_unlock(struct regmap *map, bool unlock) +{ + u16 buf = unlock ? MT6363_BUCK_TOP_UNLOCK_VALUE : 0; + + return regmap_bulk_write(map, MT6363_BUCK_TOP_KEY_PROT_LO, &buf, sizeof(buf)); +} + +static int mt6363_regulator_set_mode(struct regulator_dev *rdev, + unsigned int mode) +{ + struct mt6363_regulator_info *info = rdev_get_drvdata(rdev); + struct regmap *regmap = rdev->regmap; + int cur_mode, ret; + + if (!info->modeset_reg && mode == REGULATOR_MODE_FAST) + return -EOPNOTSUPP; + + switch (mode) { + case REGULATOR_MODE_FAST: + ret = mt6363_buck_unlock(regmap, true); + if (ret) + break; + + ret = regmap_set_bits(regmap, info->modeset_reg, info->modeset_mask); + + mt6363_buck_unlock(regmap, false); + break; + case REGULATOR_MODE_NORMAL: + cur_mode = mt6363_regulator_get_mode(rdev); + if (cur_mode < 0) { + ret = cur_mode; + break; + } + + if (cur_mode == REGULATOR_MODE_FAST) { + ret = mt6363_buck_unlock(regmap, true); + if (ret) + break; + + ret = regmap_clear_bits(regmap, info->modeset_reg, info->modeset_mask); + + mt6363_buck_unlock(regmap, false); + break; + } else if (cur_mode == REGULATOR_MODE_IDLE) { + ret = regmap_clear_bits(regmap, info->lp_mode_reg, info->lp_mode_mask); + if (ret == 0) + usleep_range(100, 200); + } else { + ret = 0; + } + break; + case REGULATOR_MODE_IDLE: + ret = regmap_set_bits(regmap, info->lp_mode_reg, info->lp_mode_mask); + break; + default: + ret = -EINVAL; + } + + if (ret) { + dev_err(&rdev->dev, "Failed to set mode %u: %d\n", mode, ret); + return ret; + } + + return 0; +} + +static int mt6363_regulator_set_load(struct regulator_dev *rdev, int load_uA) +{ + struct mt6363_regulator_info *info = rdev_get_drvdata(rdev); + unsigned int opmode_cfg, opmode_en; + int i, ret; + + if (!info->lp_imax_uA) + return -EINVAL; + + if (load_uA >= info->lp_imax_uA) { + ret = mt6363_regulator_set_mode(rdev, REGULATOR_MODE_NORMAL); + if (ret) + return ret; + + opmode_cfg = NORMAL_OP_CFG; + opmode_en = NORMAL_OP_EN; + } else { + opmode_cfg = info->orig_op_cfg; + opmode_en = info->orig_op_en; + } + + ret = regmap_write(rdev->regmap, info->op_en_reg + OP_CFG_OFFSET, opmode_cfg); + if (ret) + return ret; + + for (i = 0; i < 3; i++) { + ret = regmap_write(rdev->regmap, info->op_en_reg + i, + (opmode_en >> (i * 8)) & GENMASK(7, 0)); + if (ret) + return ret; + } + + return 0; +} + +static int mt6363_vemc_set_voltage_sel(struct regulator_dev *rdev, unsigned int sel) +{ + const u16 tma_unlock_key = MT6363_TMA_UNLOCK_VALUE; + const struct regulator_desc *rdesc = rdev->desc; + struct regmap *regmap = rdev->regmap; + unsigned int range, val; + int i, ret; + u16 mask; + + for (i = 0; i < rdesc->n_linear_ranges; i++) { + const struct linear_range *r = &rdesc->linear_ranges[i]; + unsigned int voltages_in_range = linear_range_values_in_range(r); + + if (sel < voltages_in_range) + break; + sel -= voltages_in_range; + } + + if (i == rdesc->n_linear_ranges) + return -EINVAL; + + ret = regmap_read(rdev->regmap, MT6363_TOP_TRAP, &val); + if (ret) + return ret; + + if (val > 1) + return -EINVAL; + + /* Unlock TMA for writing */ + ret = regmap_bulk_write(rdev->regmap, MT6363_TOP_TMA_KEY_L, + &tma_unlock_key, sizeof(tma_unlock_key)); + if (ret) + return ret; + + /* If HW trapping value is 1, use VEMC_VOSEL_1 instead of VEMC_VOSEL_0 */ + if (val == 1) { + mask = MT6363_RG_VEMC_VOSEL_1_MASK; + sel = FIELD_PREP(MT6363_RG_VEMC_VOSEL_1_MASK, sel); + } else { + mask = rdesc->vsel_mask; + } + + sel <<= ffs(rdesc->vsel_mask) - 1; + sel += rdesc->linear_ranges[i].min_sel; + + range = rdesc->linear_range_selectors_bitfield[i]; + range <<= ffs(rdesc->vsel_range_mask) - 1; + + /* Write to the vreg calibration register for voltage finetuning */ + ret = regmap_update_bits(regmap, rdesc->vsel_range_reg, + rdesc->vsel_range_mask, range); + if (ret) + goto lock_tma; + + /* Function must return the result of this write operation */ + ret = regmap_update_bits(regmap, rdesc->vsel_reg, mask, sel); + +lock_tma: + /* Unconditionally re-lock TMA */ + val = 0; + regmap_bulk_write(rdev->regmap, MT6363_TOP_TMA_KEY_L, &val, 2); + + return ret; +} + +static int mt6363_vemc_get_voltage_sel(struct regulator_dev *rdev) +{ + const struct regulator_desc *rdesc = rdev->desc; + unsigned int vosel, trap, calsel; + int vcal, vsel, range, ret; + + ret = regmap_read(rdev->regmap, rdesc->vsel_reg, &vosel); + if (ret) + return ret; + + ret = regmap_read(rdev->regmap, rdesc->vsel_range_reg, &calsel); + if (ret) + return ret; + + calsel &= rdesc->vsel_range_mask; + for (range = 0; range < rdesc->n_linear_ranges; range++) + if (rdesc->linear_range_selectors_bitfield[range] != calsel) + break; + + if (range == rdesc->n_linear_ranges) + return -EINVAL; + + ret = regmap_read(rdev->regmap, MT6363_TOP_TRAP, &trap); + if (ret) + return ret; + + /* If HW trapping value is 1, use VEMC_VOSEL_1 instead of VEMC_VOSEL_0 */ + if (trap > 1) + return -EINVAL; + else if (trap == 1) + vsel = FIELD_GET(MT6363_RG_VEMC_VOSEL_1_MASK, vosel); + else + vsel = vosel & rdesc->vsel_mask; + + vcal = linear_range_values_in_range_array(rdesc->linear_ranges, range); + + return vsel + vcal; +} + +static int mt6363_va15_set_voltage_sel(struct regulator_dev *rdev, unsigned int sel) +{ + struct regmap *regmap = rdev->regmap; + int ret; + + ret = mt6363_buck_unlock(regmap, true); + if (ret) + return ret; + + ret = regulator_set_voltage_sel_pickable_regmap(rdev, sel); + if (ret) + goto va15_unlock; + + ret = regmap_update_bits(regmap, MT6363_RG_BUCK_EFUSE_RSV1, + MT6363_RG_BUCK_EFUSE_RSV1_MASK, sel); + if (ret) + goto va15_unlock; + +va15_unlock: + mt6363_buck_unlock(rdev->regmap, false); + return ret; +} + +static void mt6363_oc_irq_enable_work(struct work_struct *work) +{ + struct delayed_work *dwork = to_delayed_work(work); + struct mt6363_regulator_info *info = + container_of(dwork, struct mt6363_regulator_info, oc_work); + + enable_irq(info->virq); +} + +static irqreturn_t mt6363_oc_isr(int irq, void *data) +{ + struct regulator_dev *rdev = (struct regulator_dev *)data; + struct mt6363_regulator_info *info = rdev_get_drvdata(rdev); + + disable_irq_nosync(info->virq); + + if (regulator_is_enabled_regmap(rdev)) + regulator_notifier_call_chain(rdev, REGULATOR_EVENT_OVER_CURRENT, NULL); + + schedule_delayed_work(&info->oc_work, msecs_to_jiffies(OC_IRQ_ENABLE_DELAY_MS)); + + return IRQ_HANDLED; +} + +static int mt6363_set_ocp(struct regulator_dev *rdev, int lim, int severity, bool enable) +{ + struct mt6363_regulator_info *info = rdev_get_drvdata(rdev); + + /* MT6363 supports only enabling protection and does not support limits */ + if (lim || severity != REGULATOR_SEVERITY_PROT || !enable) + return -EOPNOTSUPP; + + /* If there is no OCP interrupt, there's nothing to set */ + if (info->virq <= 0) + return -EOPNOTSUPP; + + return devm_request_threaded_irq(&rdev->dev, info->virq, NULL, + mt6363_oc_isr, IRQF_ONESHOT, + info->desc.name, rdev); +} + +static const struct regulator_ops mt6363_vreg_setclr_ops = { + .list_voltage = regulator_list_voltage_linear, + .map_voltage = regulator_map_voltage_linear, + .set_voltage_sel = regulator_set_voltage_sel_regmap, + .get_voltage_sel = regulator_get_voltage_sel_regmap, + .set_voltage_time_sel = regulator_set_voltage_time_sel, + .enable = mt6363_vreg_enable_setclr, + .disable = mt6363_vreg_disable_setclr, + .is_enabled = regulator_is_enabled_regmap, + .set_mode = mt6363_regulator_set_mode, + .get_mode = mt6363_regulator_get_mode, + .set_load = mt6363_regulator_set_load, + .set_over_current_protection = mt6363_set_ocp, +}; + +static const struct regulator_ops mt6363_ldo_linear_ops = { + .list_voltage = regulator_list_voltage_linear, + .map_voltage = regulator_map_voltage_linear, + .set_voltage_sel = regulator_set_voltage_sel_regmap, + .get_voltage_sel = regulator_get_voltage_sel_regmap, + .set_voltage_time_sel = regulator_set_voltage_time_sel, + .enable = regulator_enable_regmap, + .disable = regulator_disable_regmap, + .is_enabled = regulator_is_enabled_regmap, + .set_mode = mt6363_regulator_set_mode, + .get_mode = mt6363_regulator_get_mode, + .set_over_current_protection = mt6363_set_ocp, +}; + +static const struct regulator_ops mt6363_ldo_vtable_ops = { + .list_voltage = regulator_list_voltage_pickable_linear_range, + .map_voltage = regulator_map_voltage_pickable_linear_range, + .set_voltage_sel = regulator_set_voltage_sel_pickable_regmap, + .get_voltage_sel = regulator_get_voltage_sel_pickable_regmap, + .set_voltage_time_sel = regulator_set_voltage_time_sel, + .enable = regulator_enable_regmap, + .disable = regulator_disable_regmap, + .is_enabled = regulator_is_enabled_regmap, + .set_mode = mt6363_regulator_set_mode, + .get_mode = mt6363_regulator_get_mode, + .set_load = mt6363_regulator_set_load, + .set_over_current_protection = mt6363_set_ocp, +}; + +static const struct regulator_ops mt6363_ldo_vemc_ops = { + .list_voltage = regulator_list_voltage_pickable_linear_range, + .map_voltage = regulator_map_voltage_pickable_linear_range, + .set_voltage_sel = mt6363_vemc_set_voltage_sel, + .get_voltage_sel = mt6363_vemc_get_voltage_sel, + .set_voltage_time_sel = regulator_set_voltage_time_sel, + .enable = regulator_enable_regmap, + .disable = regulator_disable_regmap, + .is_enabled = regulator_is_enabled_regmap, + .set_mode = mt6363_regulator_set_mode, + .get_mode = mt6363_regulator_get_mode, + .set_load = mt6363_regulator_set_load, + .set_over_current_protection = mt6363_set_ocp, +}; + +static const struct regulator_ops mt6363_ldo_va15_ops = { + .list_voltage = regulator_list_voltage_pickable_linear_range, + .map_voltage = regulator_map_voltage_pickable_linear_range, + .set_voltage_sel = mt6363_va15_set_voltage_sel, + .get_voltage_sel = regulator_get_voltage_sel_pickable_regmap, + .set_voltage_time_sel = regulator_set_voltage_time_sel, + .enable = regulator_enable_regmap, + .disable = regulator_disable_regmap, + .is_enabled = regulator_is_enabled_regmap, + .set_mode = mt6363_regulator_set_mode, + .get_mode = mt6363_regulator_get_mode, + .set_load = mt6363_regulator_set_load, + .set_over_current_protection = mt6363_set_ocp, +}; + +/* The array is indexed by id(MT6363_ID_XXX) */ +static struct mt6363_regulator_info mt6363_regulators[] = { + MT6363_BUCK("vbuck1", VBUCK1, 0, 1193750, 6250, MT6363_RG_BUCK0_EN_ADDR, + MT6363_RG_BUCK0_LP_ADDR, MT6363_RG_BUCK0_FCCM_ADDR, 1), + MT6363_BUCK("vbuck2", VBUCK2, 0, 1193750, 6250, MT6363_RG_BUCK0_EN_ADDR, + MT6363_RG_BUCK0_LP_ADDR, MT6363_RG_BUCK0_FCCM_ADDR, 2), + MT6363_BUCK("vbuck3", VBUCK3, 0, 1193750, 6250, MT6363_RG_BUCK0_EN_ADDR, + MT6363_RG_BUCK0_LP_ADDR, MT6363_RG_BUCK0_FCCM_ADDR, 3), + MT6363_BUCK("vbuck4", VBUCK4, 0, 1193750, 6250, MT6363_RG_BUCK0_EN_ADDR, + MT6363_RG_BUCK0_LP_ADDR, MT6363_RG_BUCK0_1_FCCM_ADDR, 4), + MT6363_BUCK("vbuck5", VBUCK5, 0, 1193750, 6250, MT6363_RG_BUCK0_EN_ADDR, + MT6363_RG_BUCK0_LP_ADDR, MT6363_RG_BUCK0_1_FCCM_ADDR, 5), + MT6363_BUCK("vbuck6", VBUCK6, 0, 1193750, 6250, MT6363_RG_BUCK0_EN_ADDR, + MT6363_RG_BUCK0_LP_ADDR, MT6363_RG_BUCK0_1_FCCM_ADDR, 6), + MT6363_BUCK("vbuck7", VBUCK7, 0, 1193750, 6250, MT6363_RG_BUCK0_EN_ADDR, + MT6363_RG_BUCK0_LP_ADDR, MT6363_RG_BUCK0_1_FCCM_ADDR, 7), + MT6363_BUCK("vs1", VS1, 0, 2200000, 12500, MT6363_RG_BUCK1_EN_ADDR, + MT6363_RG_BUCK1_LP_ADDR, MT6363_RG_VS1_FCCM_ADDR, 8), + MT6363_BUCK("vs2", VS2, 0, 1600000, 12500, MT6363_RG_BUCK0_EN_ADDR, + MT6363_RG_BUCK0_LP_ADDR, MT6363_RG_BUCK0_FCCM_ADDR, 0), + MT6363_BUCK("vs3", VS3, 0, 1193750, 6250, MT6363_RG_BUCK1_EN_ADDR, + MT6363_RG_BUCK1_LP_ADDR, MT6363_RG_VS3_FCCM_ADDR, 9), + MT6363_LDO_VT("va12-1", VA12_1, "vs2-ldo2", 3, 37), + MT6363_LDO_VT("va12-2", VA12_2, "vs2-ldo2", 3, 38), + MT6363_LDO_LINEAR_CAL_OPS("va15", VA15, "vs1-ldo1", mt6363_ldo_va15_ops, 3, 39), + MT6363_LDO_VT("vaux18", VAUX18, "vsys-ldo1", 2, 31), + MT6363_LDO_VT("vcn13", VCN13, "vs2-ldo2", 1, 17), + MT6363_LDO_VT("vcn15", VCN15, "vs1-ldo2", 3, 16), + MT6363_LDO_LINEAR_CAL_OPS("vemc", VEMC, "vsys-ldo1", mt6363_ldo_vemc_ops, 0, 32), + MT6363_LDO_VT("vio0p75", VIO075, "vs1-ldo1", 5, 36), + MT6363_LDO_VT("vio18", VIO18, "vs1-ldo2", 3, 35), + MT6363_LDO_VT("vm18", VM18, "vs1-ldo1", 4, 40), + MT6363_LDO_L("vsram-apu", VSRAM_APU, "vs3-ldo1", 400000, 1193750, 6250, BUCK1, 30), + MT6363_LDO_L("vsram-cpub", VSRAM_CPUB, "vs2-ldo1", 400000, 1193750, 6250, BUCK1, 27), + MT6363_LDO_L("vsram-cpum", VSRAM_CPUM, "vs2-ldo1", 400000, 1193750, 6250, BUCK1, 28), + MT6363_LDO_L("vsram-cpul", VSRAM_CPUL, "vs2-ldo2", 400000, 1193750, 6250, BUCK1, 29), + MT6363_LDO_L_SC("vsram-digrf", VSRAM_DIGRF, "vs3-ldo1", 400000, 1193750, 6250, BUCK1, 23), + MT6363_LDO_L_SC("vsram-mdfe", VSRAM_MDFE, "vs3-ldo1", 400000, 1193750, 6250, BUCK1, 24), + MT6363_LDO_L_SC("vsram-modem", VSRAM_MODEM, "vs3-ldo2", 400000, 1193750, 6250, BUCK1, 25), + MT6363_LDO_VT("vrf0p9", VRF09, "vs3-ldo2", 1, 18), + MT6363_LDO_VT("vrf12", VRF12, "vs2-ldo1", 3, 19), + MT6363_LDO_VT("vrf13", VRF13, "vs2-ldo1", 1, 20), + MT6363_LDO_VT("vrf18", VRF18, "vs1-ldo1", 3, 21), + MT6363_LDO_VT("vrf-io18", VRFIO18, "vs1-ldo1", 3, 22), + MT6363_LDO_VT("vtref18", VTREF18, "vsys-ldo1", 2, 26), + MT6363_LDO_VT("vufs12", VUFS12, "vs2-ldo1", 4, 33), + MT6363_LDO_VT("vufs18", VUFS18, "vs1-ldo2", 3, 34), +}; + +static int mt6363_backup_op_setting(struct regmap *map, struct mt6363_regulator_info *info) +{ + unsigned int i, val; + int ret; + + ret = regmap_read(map, info->op_en_reg + OP_CFG_OFFSET, &val); + if (ret) + return ret; + + info->orig_op_cfg = val; + + for (i = 0; i < 3; i++) { + ret = regmap_read(map, info->op_en_reg + i, &val); + if (ret) + return ret; + + info->orig_op_en |= val << (i * 8); + } + + return 0; +} + +static void mt6363_irq_remove(void *data) +{ + int *virq = data; + + irq_dispose_mapping(*virq); +} + +static void mt6363_spmi_remove(void *data) +{ + struct spmi_device *sdev = data; + + spmi_device_remove(sdev); +}; + +static struct regmap *mt6363_spmi_register_regmap(struct device *dev) +{ + struct regmap_config mt6363_regmap_config = { + .reg_bits = 16, + .val_bits = 16, + .max_register = 0x1f90, + .fast_io = true, + }; + struct spmi_device *sdev, *sparent; + u32 base; + int ret; + + if (!dev->parent) + return ERR_PTR(-ENODEV); + + ret = device_property_read_u32(dev, "reg", &base); + if (ret) + return ERR_PTR(ret); + + sparent = to_spmi_device(dev->parent); + if (!sparent) + return ERR_PTR(-ENODEV); + + sdev = spmi_device_alloc(sparent->ctrl); + if (!sdev) + return ERR_PTR(-ENODEV); + + sdev->usid = sparent->usid; + dev_set_name(&sdev->dev, "%d-%02x-regulator", sdev->ctrl->nr, sdev->usid); + ret = device_add(&sdev->dev); + if (ret) { + put_device(&sdev->dev); + return ERR_PTR(ret); + }; + + ret = devm_add_action_or_reset(dev, mt6363_spmi_remove, sdev); + if (ret) + return ERR_PTR(ret); + + mt6363_regmap_config.reg_base = base; + + return devm_regmap_init_spmi_ext(sdev, &mt6363_regmap_config); +} + +static int mt6363_regulator_probe(struct platform_device *pdev) +{ + struct device_node *interrupt_parent; + struct regulator_config config = {}; + struct mt6363_regulator_info *info; + struct device *dev = &pdev->dev; + struct regulator_dev *rdev; + struct irq_domain *domain; + struct irq_fwspec fwspec; + struct spmi_device *sdev; + int i, ret; + + config.regmap = mt6363_spmi_register_regmap(dev); + if (IS_ERR(config.regmap)) + return dev_err_probe(dev, PTR_ERR(config.regmap), + "Cannot get regmap\n"); + config.dev = dev; + sdev = to_spmi_device(dev->parent); + + interrupt_parent = of_irq_find_parent(dev->of_node); + if (!interrupt_parent) + return dev_err_probe(dev, -EINVAL, "Cannot find IRQ parent\n"); + + domain = irq_find_host(interrupt_parent); + of_node_put(interrupt_parent); + fwspec.fwnode = domain->fwnode; + + fwspec.param_count = 3; + fwspec.param[0] = sdev->usid; + fwspec.param[2] = IRQ_TYPE_LEVEL_HIGH; + + for (i = 0; i < ARRAY_SIZE(mt6363_regulators); i++) { + info = &mt6363_regulators[i]; + + fwspec.param[1] = info->hwirq; + info->virq = irq_create_fwspec_mapping(&fwspec); + if (!info->virq) + return dev_err_probe(dev, -EINVAL, + "Failed to map IRQ%d\n", info->hwirq); + + ret = devm_add_action_or_reset(dev, mt6363_irq_remove, &info->virq); + if (ret) { + irq_dispose_mapping(info->hwirq); + return ret; + } + + config.driver_data = info; + INIT_DELAYED_WORK(&info->oc_work, mt6363_oc_irq_enable_work); + + rdev = devm_regulator_register(dev, &info->desc, &config); + if (IS_ERR(rdev)) + return dev_err_probe(dev, PTR_ERR(rdev), + "failed to register %s\n", info->desc.name); + + if (info->lp_imax_uA) { + ret = mt6363_backup_op_setting(config.regmap, info); + if (ret) { + dev_warn(dev, "Failed to backup op_setting for %s\n", + info->desc.name); + info->lp_imax_uA = 0; + } + } + } + + return 0; +} + +static const struct of_device_id mt6363_regulator_match[] = { + { .compatible = "mediatek,mt6363-regulator" }, + { /* sentinel */ } +}; + +static struct platform_driver mt6363_regulator_driver = { + .driver = { + .name = "mt6363-regulator", + .probe_type = PROBE_PREFER_ASYNCHRONOUS, + .of_match_table = mt6363_regulator_match, + }, + .probe = mt6363_regulator_probe, +}; +module_platform_driver(mt6363_regulator_driver); + +MODULE_AUTHOR("AngeloGioacchino Del Regno <angelogioacchino.delregno@collabora.com>"); +MODULE_DESCRIPTION("Regulator Driver for MediaTek MT6363 PMIC"); +MODULE_LICENSE("GPL"); diff --git a/drivers/regulator/of_regulator.c b/drivers/regulator/of_regulator.c index 32e88cada47a..33463926a2a6 100644 --- a/drivers/regulator/of_regulator.c +++ b/drivers/regulator/of_regulator.c @@ -79,10 +79,10 @@ static void of_get_regulator_prot_limits(struct device_node *np, static int of_get_regulation_constraints(struct device *dev, struct device_node *np, - struct regulator_init_data **init_data, + struct regulator_init_data *init_data, const struct regulator_desc *desc) { - struct regulation_constraints *constraints = &(*init_data)->constraints; + struct regulation_constraints *constraints = &init_data->constraints; struct regulator_state *suspend_state; struct device_node *suspend_np; unsigned int mode; @@ -359,7 +359,7 @@ struct regulator_init_data *of_get_regulator_init_data(struct device *dev, if (!init_data) return NULL; /* Out of memory? */ - if (of_get_regulation_constraints(dev, node, &init_data, desc)) + if (of_get_regulation_constraints(dev, node, init_data, desc)) return NULL; return init_data; diff --git a/drivers/regulator/pca9450-regulator.c b/drivers/regulator/pca9450-regulator.c index 4be270f4d6c3..5fa868264250 100644 --- a/drivers/regulator/pca9450-regulator.c +++ b/drivers/regulator/pca9450-regulator.c @@ -249,7 +249,7 @@ static int buck_set_dvs(const struct regulator_desc *desc, } if (ret == 0) { - struct pca9450_regulator_desc *regulator = container_of(desc, + const struct pca9450_regulator_desc *regulator = container_of_const(desc, struct pca9450_regulator_desc, desc); /* Enable DVS control through PMIC_STBY_REQ for this BUCK */ @@ -263,7 +263,7 @@ static int pca9450_set_dvs_levels(struct device_node *np, const struct regulator_desc *desc, struct regulator_config *cfg) { - struct pca9450_regulator_desc *data = container_of(desc, + const struct pca9450_regulator_desc *data = container_of_const(desc, struct pca9450_regulator_desc, desc); const struct pc9450_dvs_config *dvs = &data->dvs; unsigned int reg, mask; @@ -308,7 +308,7 @@ static inline unsigned int pca9450_map_mode(unsigned int mode) static int pca9450_buck_set_mode(struct regulator_dev *rdev, unsigned int mode) { - struct pca9450_regulator_desc *desc = container_of(rdev->desc, + const struct pca9450_regulator_desc *desc = container_of_const(rdev->desc, struct pca9450_regulator_desc, desc); const struct pc9450_dvs_config *dvs = &desc->dvs; int val; @@ -333,7 +333,7 @@ static int pca9450_buck_set_mode(struct regulator_dev *rdev, unsigned int mode) static unsigned int pca9450_buck_get_mode(struct regulator_dev *rdev) { - struct pca9450_regulator_desc *desc = container_of(rdev->desc, + const struct pca9450_regulator_desc *desc = container_of_const(rdev->desc, struct pca9450_regulator_desc, desc); const struct pc9450_dvs_config *dvs = &desc->dvs; int ret = 0, regval; @@ -355,6 +355,7 @@ static struct pca9450_regulator_desc pca9450a_regulators[] = { { .desc = { .name = "buck1", + .supply_name = "inb13", .of_match = of_match_ptr("BUCK1"), .regulators_node = of_match_ptr("regulators"), .id = PCA9450_BUCK1, @@ -388,6 +389,7 @@ static struct pca9450_regulator_desc pca9450a_regulators[] = { { .desc = { .name = "buck2", + .supply_name = "inb26", .of_match = of_match_ptr("BUCK2"), .regulators_node = of_match_ptr("regulators"), .id = PCA9450_BUCK2, @@ -421,6 +423,7 @@ static struct pca9450_regulator_desc pca9450a_regulators[] = { { .desc = { .name = "buck3", + .supply_name = "inb13", .of_match = of_match_ptr("BUCK3"), .regulators_node = of_match_ptr("regulators"), .id = PCA9450_BUCK3, @@ -454,6 +457,7 @@ static struct pca9450_regulator_desc pca9450a_regulators[] = { { .desc = { .name = "buck4", + .supply_name = "inb45", .of_match = of_match_ptr("BUCK4"), .regulators_node = of_match_ptr("regulators"), .id = PCA9450_BUCK4, @@ -478,6 +482,7 @@ static struct pca9450_regulator_desc pca9450a_regulators[] = { { .desc = { .name = "buck5", + .supply_name = "inb45", .of_match = of_match_ptr("BUCK5"), .regulators_node = of_match_ptr("regulators"), .id = PCA9450_BUCK5, @@ -502,6 +507,7 @@ static struct pca9450_regulator_desc pca9450a_regulators[] = { { .desc = { .name = "buck6", + .supply_name = "inb26", .of_match = of_match_ptr("BUCK6"), .regulators_node = of_match_ptr("regulators"), .id = PCA9450_BUCK6, @@ -526,6 +532,7 @@ static struct pca9450_regulator_desc pca9450a_regulators[] = { { .desc = { .name = "ldo1", + .supply_name = "inl1", .of_match = of_match_ptr("LDO1"), .regulators_node = of_match_ptr("regulators"), .id = PCA9450_LDO1, @@ -544,6 +551,7 @@ static struct pca9450_regulator_desc pca9450a_regulators[] = { { .desc = { .name = "ldo2", + .supply_name = "inl1", .of_match = of_match_ptr("LDO2"), .regulators_node = of_match_ptr("regulators"), .id = PCA9450_LDO2, @@ -562,6 +570,7 @@ static struct pca9450_regulator_desc pca9450a_regulators[] = { { .desc = { .name = "ldo3", + .supply_name = "inl1", .of_match = of_match_ptr("LDO3"), .regulators_node = of_match_ptr("regulators"), .id = PCA9450_LDO3, @@ -580,6 +589,7 @@ static struct pca9450_regulator_desc pca9450a_regulators[] = { { .desc = { .name = "ldo4", + .supply_name = "inl1", .of_match = of_match_ptr("LDO4"), .regulators_node = of_match_ptr("regulators"), .id = PCA9450_LDO4, @@ -598,6 +608,7 @@ static struct pca9450_regulator_desc pca9450a_regulators[] = { { .desc = { .name = "ldo5", + .supply_name = "inl1", .of_match = of_match_ptr("LDO5"), .regulators_node = of_match_ptr("regulators"), .id = PCA9450_LDO5, @@ -623,6 +634,7 @@ static struct pca9450_regulator_desc pca9450bc_regulators[] = { { .desc = { .name = "buck1", + .supply_name = "inb13", .of_match = of_match_ptr("BUCK1"), .regulators_node = of_match_ptr("regulators"), .id = PCA9450_BUCK1, @@ -656,6 +668,7 @@ static struct pca9450_regulator_desc pca9450bc_regulators[] = { { .desc = { .name = "buck2", + .supply_name = "inb26", .of_match = of_match_ptr("BUCK2"), .regulators_node = of_match_ptr("regulators"), .id = PCA9450_BUCK2, @@ -689,6 +702,7 @@ static struct pca9450_regulator_desc pca9450bc_regulators[] = { { .desc = { .name = "buck4", + .supply_name = "inb45", .of_match = of_match_ptr("BUCK4"), .regulators_node = of_match_ptr("regulators"), .id = PCA9450_BUCK4, @@ -713,6 +727,7 @@ static struct pca9450_regulator_desc pca9450bc_regulators[] = { { .desc = { .name = "buck5", + .supply_name = "inb45", .of_match = of_match_ptr("BUCK5"), .regulators_node = of_match_ptr("regulators"), .id = PCA9450_BUCK5, @@ -737,6 +752,7 @@ static struct pca9450_regulator_desc pca9450bc_regulators[] = { { .desc = { .name = "buck6", + .supply_name = "inb26", .of_match = of_match_ptr("BUCK6"), .regulators_node = of_match_ptr("regulators"), .id = PCA9450_BUCK6, @@ -761,6 +777,7 @@ static struct pca9450_regulator_desc pca9450bc_regulators[] = { { .desc = { .name = "ldo1", + .supply_name = "inl1", .of_match = of_match_ptr("LDO1"), .regulators_node = of_match_ptr("regulators"), .id = PCA9450_LDO1, @@ -779,6 +796,7 @@ static struct pca9450_regulator_desc pca9450bc_regulators[] = { { .desc = { .name = "ldo2", + .supply_name = "inl1", .of_match = of_match_ptr("LDO2"), .regulators_node = of_match_ptr("regulators"), .id = PCA9450_LDO2, @@ -797,6 +815,7 @@ static struct pca9450_regulator_desc pca9450bc_regulators[] = { { .desc = { .name = "ldo3", + .supply_name = "inl1", .of_match = of_match_ptr("LDO3"), .regulators_node = of_match_ptr("regulators"), .id = PCA9450_LDO3, @@ -815,6 +834,7 @@ static struct pca9450_regulator_desc pca9450bc_regulators[] = { { .desc = { .name = "ldo4", + .supply_name = "inl1", .of_match = of_match_ptr("LDO4"), .regulators_node = of_match_ptr("regulators"), .id = PCA9450_LDO4, @@ -833,6 +853,7 @@ static struct pca9450_regulator_desc pca9450bc_regulators[] = { { .desc = { .name = "ldo5", + .supply_name = "inl1", .of_match = of_match_ptr("LDO5"), .regulators_node = of_match_ptr("regulators"), .id = PCA9450_LDO5, @@ -854,6 +875,7 @@ static struct pca9450_regulator_desc pca9451a_regulators[] = { { .desc = { .name = "buck1", + .supply_name = "inb13", .of_match = of_match_ptr("BUCK1"), .regulators_node = of_match_ptr("regulators"), .id = PCA9450_BUCK1, @@ -886,6 +908,7 @@ static struct pca9450_regulator_desc pca9451a_regulators[] = { { .desc = { .name = "buck2", + .supply_name = "inb26", .of_match = of_match_ptr("BUCK2"), .regulators_node = of_match_ptr("regulators"), .id = PCA9450_BUCK2, @@ -918,6 +941,7 @@ static struct pca9450_regulator_desc pca9451a_regulators[] = { { .desc = { .name = "buck4", + .supply_name = "inb45", .of_match = of_match_ptr("BUCK4"), .regulators_node = of_match_ptr("regulators"), .id = PCA9450_BUCK4, @@ -942,6 +966,7 @@ static struct pca9450_regulator_desc pca9451a_regulators[] = { { .desc = { .name = "buck5", + .supply_name = "inb45", .of_match = of_match_ptr("BUCK5"), .regulators_node = of_match_ptr("regulators"), .id = PCA9450_BUCK5, @@ -966,6 +991,7 @@ static struct pca9450_regulator_desc pca9451a_regulators[] = { { .desc = { .name = "buck6", + .supply_name = "inb26", .of_match = of_match_ptr("BUCK6"), .regulators_node = of_match_ptr("regulators"), .id = PCA9450_BUCK6, @@ -990,6 +1016,7 @@ static struct pca9450_regulator_desc pca9451a_regulators[] = { { .desc = { .name = "ldo1", + .supply_name = "inl1", .of_match = of_match_ptr("LDO1"), .regulators_node = of_match_ptr("regulators"), .id = PCA9450_LDO1, @@ -1008,6 +1035,7 @@ static struct pca9450_regulator_desc pca9451a_regulators[] = { { .desc = { .name = "ldo3", + .supply_name = "inl1", .of_match = of_match_ptr("LDO3"), .regulators_node = of_match_ptr("regulators"), .id = PCA9450_LDO3, @@ -1026,6 +1054,7 @@ static struct pca9450_regulator_desc pca9451a_regulators[] = { { .desc = { .name = "ldo4", + .supply_name = "inl1", .of_match = of_match_ptr("LDO4"), .regulators_node = of_match_ptr("regulators"), .id = PCA9450_LDO4, @@ -1044,6 +1073,7 @@ static struct pca9450_regulator_desc pca9451a_regulators[] = { { .desc = { .name = "ldo5", + .supply_name = "inl1", .of_match = of_match_ptr("LDO5"), .regulators_node = of_match_ptr("regulators"), .id = PCA9450_LDO5, @@ -1117,6 +1147,143 @@ static int pca9450_i2c_restart_handler(struct sys_off_data *data) return 0; } +static int pca9450_of_init(struct pca9450 *pca9450) +{ + struct i2c_client *i2c = container_of(pca9450->dev, struct i2c_client, dev); + int ret; + unsigned int val; + unsigned int reset_ctrl; + unsigned int rstb_deb_ctrl; + unsigned int t_on_deb, t_off_deb; + unsigned int t_on_step, t_off_step; + unsigned int t_restart; + + if (of_property_read_bool(i2c->dev.of_node, "nxp,wdog_b-warm-reset")) + reset_ctrl = WDOG_B_CFG_WARM; + else + reset_ctrl = WDOG_B_CFG_COLD_LDO12; + + /* Set reset behavior on assertion of WDOG_B signal */ + ret = regmap_update_bits(pca9450->regmap, PCA9450_REG_RESET_CTRL, + WDOG_B_CFG_MASK, reset_ctrl); + if (ret) + return dev_err_probe(&i2c->dev, ret, "Failed to set WDOG_B reset behavior\n"); + + ret = of_property_read_u32(i2c->dev.of_node, "npx,pmic-rst-b-debounce-ms", &val); + if (ret == -EINVAL) + rstb_deb_ctrl = T_PMIC_RST_DEB_50MS; + else if (ret) + return ret; + else { + switch (val) { + case 10: rstb_deb_ctrl = T_PMIC_RST_DEB_10MS; break; + case 50: rstb_deb_ctrl = T_PMIC_RST_DEB_50MS; break; + case 100: rstb_deb_ctrl = T_PMIC_RST_DEB_100MS; break; + case 500: rstb_deb_ctrl = T_PMIC_RST_DEB_500MS; break; + case 1000: rstb_deb_ctrl = T_PMIC_RST_DEB_1S; break; + case 2000: rstb_deb_ctrl = T_PMIC_RST_DEB_2S; break; + case 4000: rstb_deb_ctrl = T_PMIC_RST_DEB_4S; break; + case 8000: rstb_deb_ctrl = T_PMIC_RST_DEB_8S; break; + default: return -EINVAL; + } + } + ret = regmap_update_bits(pca9450->regmap, PCA9450_REG_RESET_CTRL, + T_PMIC_RST_DEB_MASK, rstb_deb_ctrl); + if (ret) + return dev_err_probe(&i2c->dev, ret, "Failed to set PMIC_RST_B debounce time\n"); + + ret = of_property_read_u32(i2c->dev.of_node, "nxp,pmic-on-req-on-debounce-us", &val); + if (ret == -EINVAL) + t_on_deb = T_ON_DEB_20MS; + else if (ret) + return ret; + else { + switch (val) { + case 120: t_on_deb = T_ON_DEB_120US; break; + case 20000: t_on_deb = T_ON_DEB_20MS; break; + case 100000: t_on_deb = T_ON_DEB_100MS; break; + case 750000: t_on_deb = T_ON_DEB_750MS; break; + default: return -EINVAL; + } + } + + ret = of_property_read_u32(i2c->dev.of_node, "nxp,pmic-on-req-off-debounce-us", &val); + if (ret == -EINVAL) + t_off_deb = T_OFF_DEB_120US; + else if (ret) + return ret; + else { + switch (val) { + case 120: t_off_deb = T_OFF_DEB_120US; break; + case 2000: t_off_deb = T_OFF_DEB_2MS; break; + default: return -EINVAL; + } + } + + ret = of_property_read_u32(i2c->dev.of_node, "nxp,power-on-step-ms", &val); + if (ret == -EINVAL) + t_on_step = T_ON_STEP_2MS; + else if (ret) + return ret; + else { + switch (val) { + case 1: t_on_step = T_ON_STEP_1MS; break; + case 2: t_on_step = T_ON_STEP_2MS; break; + case 4: t_on_step = T_ON_STEP_4MS; break; + case 8: t_on_step = T_ON_STEP_8MS; break; + default: return -EINVAL; + } + } + + ret = of_property_read_u32(i2c->dev.of_node, "nxp,power-down-step-ms", &val); + if (ret == -EINVAL) + t_off_step = T_OFF_STEP_8MS; + else if (ret) + return ret; + else { + switch (val) { + case 2: t_off_step = T_OFF_STEP_2MS; break; + case 4: t_off_step = T_OFF_STEP_4MS; break; + case 8: t_off_step = T_OFF_STEP_8MS; break; + case 16: t_off_step = T_OFF_STEP_16MS; break; + default: return -EINVAL; + } + } + + ret = of_property_read_u32(i2c->dev.of_node, "nxp,restart-ms", &val); + if (ret == -EINVAL) + t_restart = T_RESTART_250MS; + else if (ret) + return ret; + else { + switch (val) { + case 250: t_restart = T_RESTART_250MS; break; + case 500: t_restart = T_RESTART_500MS; break; + default: return -EINVAL; + } + } + + ret = regmap_update_bits(pca9450->regmap, PCA9450_REG_PWRCTRL, + T_ON_DEB_MASK | T_OFF_DEB_MASK | T_ON_STEP_MASK | + T_OFF_STEP_MASK | T_RESTART_MASK, + t_on_deb | t_off_deb | t_on_step | + t_off_step | t_restart); + if (ret) + return dev_err_probe(&i2c->dev, ret, + "Failed to set PWR_CTRL debounce configuration\n"); + + if (of_property_read_bool(i2c->dev.of_node, "nxp,i2c-lt-enable")) { + /* Enable I2C Level Translator */ + ret = regmap_update_bits(pca9450->regmap, PCA9450_REG_CONFIG2, + I2C_LT_MASK, I2C_LT_ON_STANDBY_RUN); + if (ret) + return dev_err_probe(&i2c->dev, ret, + "Failed to enable I2C level translator\n"); + } + + return 0; +} + static int pca9450_i2c_probe(struct i2c_client *i2c) { enum pca9450_chip_type type = (unsigned int)(uintptr_t) @@ -1126,7 +1293,6 @@ static int pca9450_i2c_probe(struct i2c_client *i2c) struct regulator_dev *ldo5; struct pca9450 *pca9450; unsigned int device_id, i; - unsigned int reset_ctrl; int ret; pca9450 = devm_kzalloc(&i2c->dev, sizeof(struct pca9450), GFP_KERNEL); @@ -1224,25 +1390,9 @@ static int pca9450_i2c_probe(struct i2c_client *i2c) if (ret) return dev_err_probe(&i2c->dev, ret, "Failed to clear PRESET_EN bit\n"); - if (of_property_read_bool(i2c->dev.of_node, "nxp,wdog_b-warm-reset")) - reset_ctrl = WDOG_B_CFG_WARM; - else - reset_ctrl = WDOG_B_CFG_COLD_LDO12; - - /* Set reset behavior on assertion of WDOG_B signal */ - ret = regmap_update_bits(pca9450->regmap, PCA9450_REG_RESET_CTRL, - WDOG_B_CFG_MASK, reset_ctrl); + ret = pca9450_of_init(pca9450); if (ret) - return dev_err_probe(&i2c->dev, ret, "Failed to set WDOG_B reset behavior\n"); - - if (of_property_read_bool(i2c->dev.of_node, "nxp,i2c-lt-enable")) { - /* Enable I2C Level Translator */ - ret = regmap_update_bits(pca9450->regmap, PCA9450_REG_CONFIG2, - I2C_LT_MASK, I2C_LT_ON_STANDBY_RUN); - if (ret) - return dev_err_probe(&i2c->dev, ret, - "Failed to enable I2C level translator\n"); - } + return dev_err_probe(&i2c->dev, ret, "Unable to parse OF data\n"); /* * For LDO5 we need to be able to check the status of the SD_VSEL input in @@ -1251,10 +1401,9 @@ static int pca9450_i2c_probe(struct i2c_client *i2c) * to this signal (if SION bit is set in IOMUX). */ pca9450->sd_vsel_gpio = gpiod_get_optional(&ldo5->dev, "sd-vsel", GPIOD_IN); - if (IS_ERR(pca9450->sd_vsel_gpio)) { - dev_err(&i2c->dev, "Failed to get SD_VSEL GPIO\n"); - return ret; - } + if (IS_ERR(pca9450->sd_vsel_gpio)) + return dev_err_probe(&i2c->dev, PTR_ERR(pca9450->sd_vsel_gpio), + "Failed to get SD_VSEL GPIO\n"); pca9450->sd_vsel_fixed_low = of_property_read_bool(ldo5->dev.of_node, "nxp,sd-vsel-fixed-low"); diff --git a/drivers/regulator/pf1550-regulator.c b/drivers/regulator/pf1550-regulator.c new file mode 100644 index 000000000000..037b8ec94066 --- /dev/null +++ b/drivers/regulator/pf1550-regulator.c @@ -0,0 +1,429 @@ +// SPDX-License-Identifier: GPL-2.0 +// +// regulator driver for the PF1550 +// +// Copyright (C) 2016 Freescale Semiconductor, Inc. +// Robin Gong <yibin.gong@freescale.com> +// +// Portions Copyright (c) 2025 Savoir-faire Linux Inc. +// Samuel Kayode <samuel.kayode@savoirfairelinux.com> +// + +#include <linux/err.h> +#include <linux/interrupt.h> +#include <linux/mfd/pf1550.h> +#include <linux/module.h> +#include <linux/platform_device.h> +#include <linux/regulator/driver.h> +#include <linux/regulator/machine.h> + +#define PF1550_REGULATOR_IRQ_NR 11 +#define PF1550_MAX_REGULATOR 7 + +struct pf1550_desc { + struct regulator_desc desc; + unsigned char stby_reg; + unsigned char stby_mask; + unsigned char stby_enable_reg; + unsigned char stby_enable_mask; +}; + +struct pf1550_regulator_info { + struct device *dev; + const struct pf1550_ddata *pf1550; + struct pf1550_desc regulator_descs[PF1550_MAX_REGULATOR]; + struct regulator_dev *rdevs[PF1550_MAX_REGULATOR]; +}; + +static const int pf1550_sw12_volts[] = { + 1100000, 1200000, 1350000, 1500000, 1800000, 2500000, 3000000, 3300000, +}; + +static const int pf1550_ldo13_volts[] = { + 750000, 800000, 850000, 900000, 950000, 1000000, 1050000, 1100000, + 1150000, 1200000, 1250000, 1300000, 1350000, 1400000, 1450000, 1500000, + 1800000, 1900000, 2000000, 2100000, 2200000, 2300000, 2400000, 2500000, + 2600000, 2700000, 2800000, 2900000, 3000000, 3100000, 3200000, 3300000, +}; + +static int pf1550_set_ramp_delay(struct regulator_dev *rdev, int ramp_delay) +{ + int id = rdev_get_id(rdev); + unsigned int ramp_bits = 0; + int ret; + + if (id > PF1550_VREFDDR) + return -EACCES; + + if (ramp_delay < 0 || ramp_delay > 6250) + return -EINVAL; + + ramp_delay = 6250 / ramp_delay; + ramp_bits = ramp_delay >> 1; + + ret = regmap_update_bits(rdev->regmap, rdev->desc->vsel_reg + 4, 0x10, + ramp_bits << 4); + if (ret < 0) + dev_err(&rdev->dev, "ramp failed, err %d\n", ret); + + return ret; +} + +static int pf1550_set_suspend_enable(struct regulator_dev *rdev) +{ + const struct pf1550_desc *desc = container_of_const(rdev->desc, + struct pf1550_desc, + desc); + unsigned int val = desc->stby_enable_mask; + + return regmap_update_bits(rdev->regmap, desc->stby_enable_reg, + desc->stby_enable_mask, val); +} + +static int pf1550_set_suspend_disable(struct regulator_dev *rdev) +{ + const struct pf1550_desc *desc = container_of_const(rdev->desc, + struct pf1550_desc, + desc); + + return regmap_update_bits(rdev->regmap, desc->stby_enable_reg, + desc->stby_enable_mask, 0); +} + +static int pf1550_buck_set_table_suspend_voltage(struct regulator_dev *rdev, + int uV) +{ + const struct pf1550_desc *desc = container_of_const(rdev->desc, + struct pf1550_desc, + desc); + int ret; + + ret = regulator_map_voltage_ascend(rdev, uV, uV); + if (ret < 0) { + dev_err(rdev_get_dev(rdev), "failed to map %i uV\n", uV); + return ret; + } + + return regmap_update_bits(rdev->regmap, desc->stby_reg, + desc->stby_mask, ret); +} + +static int pf1550_buck_set_linear_suspend_voltage(struct regulator_dev *rdev, + int uV) +{ + const struct pf1550_desc *desc = container_of_const(rdev->desc, + struct pf1550_desc, + desc); + int ret; + + ret = regulator_map_voltage_linear(rdev, uV, uV); + if (ret < 0) { + dev_err(rdev_get_dev(rdev), "failed to map %i uV\n", uV); + return ret; + } + + return regmap_update_bits(rdev->regmap, desc->stby_reg, + desc->stby_mask, ret); +} + +static const struct regulator_ops pf1550_sw1_ops = { + .enable = regulator_enable_regmap, + .disable = regulator_disable_regmap, + .set_suspend_enable = pf1550_set_suspend_enable, + .set_suspend_disable = pf1550_set_suspend_disable, + .is_enabled = regulator_is_enabled_regmap, + .list_voltage = regulator_list_voltage_table, + .set_voltage_sel = regulator_set_voltage_sel_regmap, + .get_voltage_sel = regulator_get_voltage_sel_regmap, + .set_voltage_time_sel = regulator_set_voltage_time_sel, + .set_suspend_voltage = pf1550_buck_set_table_suspend_voltage, + .map_voltage = regulator_map_voltage_ascend, + .set_ramp_delay = pf1550_set_ramp_delay, +}; + +static const struct regulator_ops pf1550_sw2_ops = { + .enable = regulator_enable_regmap, + .disable = regulator_disable_regmap, + .set_suspend_enable = pf1550_set_suspend_enable, + .set_suspend_disable = pf1550_set_suspend_disable, + .is_enabled = regulator_is_enabled_regmap, + .list_voltage = regulator_list_voltage_linear, + .set_voltage_sel = regulator_set_voltage_sel_regmap, + .get_voltage_sel = regulator_get_voltage_sel_regmap, + .set_voltage_time_sel = regulator_set_voltage_time_sel, + .set_suspend_voltage = pf1550_buck_set_linear_suspend_voltage, + .map_voltage = regulator_map_voltage_linear, + .set_ramp_delay = pf1550_set_ramp_delay, +}; + +static const struct regulator_ops pf1550_ldo1_ops = { + .enable = regulator_enable_regmap, + .disable = regulator_disable_regmap, + .set_suspend_enable = pf1550_set_suspend_enable, + .set_suspend_disable = pf1550_set_suspend_disable, + .is_enabled = regulator_is_enabled_regmap, + .list_voltage = regulator_list_voltage_table, + .map_voltage = regulator_map_voltage_ascend, + .set_voltage_sel = regulator_set_voltage_sel_regmap, + .get_voltage_sel = regulator_get_voltage_sel_regmap, +}; + +static const struct regulator_ops pf1550_ldo2_ops = { + .enable = regulator_enable_regmap, + .disable = regulator_disable_regmap, + .set_suspend_enable = pf1550_set_suspend_enable, + .set_suspend_disable = pf1550_set_suspend_disable, + .is_enabled = regulator_is_enabled_regmap, + .list_voltage = regulator_list_voltage_linear, + .set_voltage_sel = regulator_set_voltage_sel_regmap, + .get_voltage_sel = regulator_get_voltage_sel_regmap, + .map_voltage = regulator_map_voltage_linear, +}; + +static const struct regulator_ops pf1550_fixed_ops = { + .enable = regulator_enable_regmap, + .disable = regulator_disable_regmap, + .set_suspend_enable = pf1550_set_suspend_enable, + .set_suspend_disable = pf1550_set_suspend_disable, + .is_enabled = regulator_is_enabled_regmap, + .list_voltage = regulator_list_voltage_linear, +}; + +#define PF_VREF(_chip, match, _name, voltage) { \ + .desc = { \ + .name = #_name, \ + .of_match = of_match_ptr(match), \ + .regulators_node = of_match_ptr("regulators"), \ + .n_voltages = 1, \ + .ops = &pf1550_fixed_ops, \ + .type = REGULATOR_VOLTAGE, \ + .id = _chip ## _ ## _name, \ + .owner = THIS_MODULE, \ + .min_uV = (voltage), \ + .enable_reg = _chip ## _PMIC_REG_ ## _name ## _CTRL, \ + .enable_mask = 0x1, \ + }, \ + .stby_enable_reg = _chip ## _PMIC_REG_ ## _name ## _CTRL, \ + .stby_enable_mask = 0x2, \ +} + +#define PF_SW(_chip, match, _name, min, max, mask, step) { \ + .desc = { \ + .name = #_name, \ + .of_match = of_match_ptr(match), \ + .regulators_node = of_match_ptr("regulators"), \ + .n_voltages = ((max) - (min)) / (step) + 1, \ + .ops = &pf1550_sw2_ops, \ + .type = REGULATOR_VOLTAGE, \ + .id = _chip ## _ ## _name, \ + .owner = THIS_MODULE, \ + .min_uV = (min), \ + .uV_step = (step), \ + .linear_min_sel = 0, \ + .vsel_reg = _chip ## _PMIC_REG_ ## _name ## _VOLT, \ + .vsel_mask = (mask), \ + .enable_reg = _chip ## _PMIC_REG_ ## _name ## _CTRL, \ + .enable_mask = 0x1, \ + }, \ + .stby_reg = _chip ## _PMIC_REG_ ## _name ## _STBY_VOLT, \ + .stby_mask = (mask), \ + .stby_enable_reg = _chip ## _PMIC_REG_ ## _name ## _CTRL, \ + .stby_enable_mask = 0x2, \ +} + +#define PF_LDO1(_chip, match, _name, mask, voltages) { \ + .desc = { \ + .name = #_name, \ + .of_match = of_match_ptr(match), \ + .regulators_node = of_match_ptr("regulators"), \ + .n_voltages = ARRAY_SIZE(voltages), \ + .ops = &pf1550_ldo1_ops, \ + .type = REGULATOR_VOLTAGE, \ + .id = _chip ## _ ## _name, \ + .owner = THIS_MODULE, \ + .volt_table = voltages, \ + .vsel_reg = _chip ## _PMIC_REG_ ## _name ## _VOLT, \ + .vsel_mask = (mask), \ + .enable_reg = _chip ## _PMIC_REG_ ## _name ## _CTRL, \ + .enable_mask = 0x1, \ + }, \ + .stby_enable_reg = _chip ## _PMIC_REG_ ## _name ## _CTRL, \ + .stby_enable_mask = 0x2, \ +} + +#define PF_LDO2(_chip, match, _name, mask, min, max, step) { \ + .desc = { \ + .name = #_name, \ + .of_match = of_match_ptr(match), \ + .regulators_node = of_match_ptr("regulators"), \ + .n_voltages = ((max) - (min)) / (step) + 1, \ + .ops = &pf1550_ldo2_ops, \ + .type = REGULATOR_VOLTAGE, \ + .id = _chip ## _ ## _name, \ + .owner = THIS_MODULE, \ + .min_uV = (min), \ + .uV_step = (step), \ + .linear_min_sel = 0, \ + .vsel_reg = _chip ## _PMIC_REG_ ## _name ## _VOLT, \ + .vsel_mask = (mask), \ + .enable_reg = _chip ## _PMIC_REG_ ## _name ## _CTRL, \ + .enable_mask = 0x1, \ + }, \ + .stby_enable_reg = _chip ## _PMIC_REG_ ## _name ## _CTRL, \ + .stby_enable_mask = 0x2, \ +} + +static struct pf1550_desc pf1550_regulators[] = { + PF_SW(PF1550, "sw1", SW1, 600000, 1387500, 0x3f, 12500), + PF_SW(PF1550, "sw2", SW2, 600000, 1387500, 0x3f, 12500), + PF_SW(PF1550, "sw3", SW3, 1800000, 3300000, 0xf, 100000), + PF_VREF(PF1550, "vrefddr", VREFDDR, 1200000), + PF_LDO1(PF1550, "ldo1", LDO1, 0x1f, pf1550_ldo13_volts), + PF_LDO2(PF1550, "ldo2", LDO2, 0xf, 1800000, 3300000, 100000), + PF_LDO1(PF1550, "ldo3", LDO3, 0x1f, pf1550_ldo13_volts), +}; + +static irqreturn_t pf1550_regulator_irq_handler(int irq, void *data) +{ + struct pf1550_regulator_info *info = data; + struct device *dev = info->dev; + struct platform_device *pdev = to_platform_device(dev); + int i, irq_type = -1; + unsigned int event; + + for (i = 0; i < PF1550_REGULATOR_IRQ_NR; i++) + if (irq == platform_get_irq(pdev, i)) + irq_type = i; + + switch (irq_type) { + /* The _LS interrupts indicate over-current event. The _HS interrupts + * which are more accurate and can detect catastrophic faults, issue + * an error event. The current limit FAULT interrupt is similar to the + * _HS' + */ + case PF1550_PMIC_IRQ_SW1_LS: + case PF1550_PMIC_IRQ_SW2_LS: + case PF1550_PMIC_IRQ_SW3_LS: + event = REGULATOR_EVENT_OVER_CURRENT_WARN; + for (i = 0; i < PF1550_MAX_REGULATOR; i++) + if (!strcmp(rdev_get_name(info->rdevs[i]), "SW3")) + regulator_notifier_call_chain(info->rdevs[i], + event, NULL); + break; + case PF1550_PMIC_IRQ_SW1_HS: + case PF1550_PMIC_IRQ_SW2_HS: + case PF1550_PMIC_IRQ_SW3_HS: + event = REGULATOR_EVENT_OVER_CURRENT; + for (i = 0; i < PF1550_MAX_REGULATOR; i++) + if (!strcmp(rdev_get_name(info->rdevs[i]), "SW3")) + regulator_notifier_call_chain(info->rdevs[i], + event, NULL); + break; + case PF1550_PMIC_IRQ_LDO1_FAULT: + case PF1550_PMIC_IRQ_LDO2_FAULT: + case PF1550_PMIC_IRQ_LDO3_FAULT: + event = REGULATOR_EVENT_OVER_CURRENT; + for (i = 0; i < PF1550_MAX_REGULATOR; i++) + if (!strcmp(rdev_get_name(info->rdevs[i]), "LDO3")) + regulator_notifier_call_chain(info->rdevs[i], + event, NULL); + break; + case PF1550_PMIC_IRQ_TEMP_110: + case PF1550_PMIC_IRQ_TEMP_125: + event = REGULATOR_EVENT_OVER_TEMP; + for (i = 0; i < PF1550_MAX_REGULATOR; i++) + regulator_notifier_call_chain(info->rdevs[i], + event, NULL); + break; + default: + dev_err(dev, "regulator interrupt: irq %d occurred\n", + irq_type); + } + + return IRQ_HANDLED; +} + +static int pf1550_regulator_probe(struct platform_device *pdev) +{ + const struct pf1550_ddata *pf1550 = dev_get_drvdata(pdev->dev.parent); + struct regulator_config config = { }; + struct pf1550_regulator_info *info; + int i, irq = -1, ret = 0; + + info = devm_kzalloc(&pdev->dev, sizeof(*info), GFP_KERNEL); + if (!info) + return -ENOMEM; + + config.regmap = dev_get_regmap(pf1550->dev, NULL); + if (!config.regmap) + return dev_err_probe(&pdev->dev, -ENODEV, + "failed to get parent regmap\n"); + + config.dev = pf1550->dev; + config.regmap = pf1550->regmap; + info->dev = &pdev->dev; + info->pf1550 = pf1550; + + memcpy(info->regulator_descs, pf1550_regulators, + sizeof(info->regulator_descs)); + + for (i = 0; i < ARRAY_SIZE(pf1550_regulators); i++) { + struct regulator_desc *desc; + + desc = &info->regulator_descs[i].desc; + + if ((desc->id == PF1550_SW2 && !pf1550->dvs2_enable) || + (desc->id == PF1550_SW1 && !pf1550->dvs1_enable)) { + /* OTP_SW2_DVS_ENB == 1? or OTP_SW1_DVS_ENB == 1? */ + desc->volt_table = pf1550_sw12_volts; + desc->n_voltages = ARRAY_SIZE(pf1550_sw12_volts); + desc->ops = &pf1550_sw1_ops; + } + + info->rdevs[i] = devm_regulator_register(&pdev->dev, desc, + &config); + if (IS_ERR(info->rdevs[i])) + return dev_err_probe(&pdev->dev, + PTR_ERR(info->rdevs[i]), + "failed to initialize regulator-%d\n", + i); + } + + platform_set_drvdata(pdev, info); + + for (i = 0; i < PF1550_REGULATOR_IRQ_NR; i++) { + irq = platform_get_irq(pdev, i); + if (irq < 0) + return irq; + + ret = devm_request_threaded_irq(&pdev->dev, irq, NULL, + pf1550_regulator_irq_handler, + IRQF_NO_SUSPEND, + "pf1550-regulator", info); + if (ret) + return dev_err_probe(&pdev->dev, ret, + "failed: irq request (IRQ: %d)\n", + i); + } + + return 0; +} + +static const struct platform_device_id pf1550_regulator_id[] = { + { "pf1550-regulator", }, + { /* sentinel */ } +}; +MODULE_DEVICE_TABLE(platform, pf1550_regulator_id); + +static struct platform_driver pf1550_regulator_driver = { + .driver = { + .name = "pf1550-regulator", + }, + .probe = pf1550_regulator_probe, + .id_table = pf1550_regulator_id, +}; +module_platform_driver(pf1550_regulator_driver); + +MODULE_DESCRIPTION("NXP PF1550 regulator driver"); +MODULE_AUTHOR("Robin Gong <yibin.gong@freescale.com>"); +MODULE_LICENSE("GPL"); diff --git a/drivers/regulator/pf9453-regulator.c b/drivers/regulator/pf9453-regulator.c index be627f49b617..779a6fdb0574 100644 --- a/drivers/regulator/pf9453-regulator.c +++ b/drivers/regulator/pf9453-regulator.c @@ -65,8 +65,7 @@ enum { #define PF9453_LDOSNVS_VOLTAGE_NUM 0x59 enum { - PF9453_REG_DEV_ID = 0x00, - PF9453_REG_OTP_VER = 0x01, + PF9453_REG_DEV_ID = 0x01, PF9453_REG_INT1 = 0x02, PF9453_REG_INT1_MASK = 0x03, PF9453_REG_INT1_STATUS = 0x04, @@ -120,7 +119,6 @@ enum { #define LDO_ENMODE_ONREQ_STBY_DPSTBY 0x03 /* PF9453_REG_BUCK1_CTRL bits */ -#define BUCK1_LPMODE 0x30 #define BUCK1_AD 0x08 #define BUCK1_FPWM 0x04 #define BUCK1_ENMODE_MASK GENMASK(1, 0) @@ -131,19 +129,16 @@ enum { #define BUCK2_RAMP_12P5MV 0x1 #define BUCK2_RAMP_6P25MV 0x2 #define BUCK2_RAMP_3P125MV 0x3 -#define BUCK2_LPMODE 0x30 #define BUCK2_AD 0x08 #define BUCK2_FPWM 0x04 #define BUCK2_ENMODE_MASK GENMASK(1, 0) /* PF9453_REG_BUCK3_CTRL bits */ -#define BUCK3_LPMODE 0x30 #define BUCK3_AD 0x08 #define BUCK3_FPWM 0x04 #define BUCK3_ENMODE_MASK GENMASK(1, 0) /* PF9453_REG_BUCK4_CTRL bits */ -#define BUCK4_LPMODE 0x30 #define BUCK4_AD 0x08 #define BUCK4_FPWM 0x04 #define BUCK4_ENMODE_MASK GENMASK(1, 0) @@ -192,13 +187,6 @@ enum { #define WDOG_B_CFG_WARM 0x40 #define WDOG_B_CFG_COLD 0x80 -/* PF9453_REG_CONFIG2 bits */ -#define I2C_LT_MASK GENMASK(1, 0) -#define I2C_LT_FORCE_DISABLE 0x00 -#define I2C_LT_ON_STANDBY_RUN 0x01 -#define I2C_LT_ON_RUN 0x02 -#define I2C_LT_FORCE_ENABLE 0x03 - static const struct regmap_range pf9453_status_range = { .range_min = PF9453_REG_INT1, .range_max = PF9453_REG_PWRON_STAT, @@ -301,13 +289,15 @@ static int pf9453_pmic_write(struct pf9453 *pf9453, unsigned int reg, u8 mask, u } /** - * pf9453_regulator_enable_regmap for regmap users + * pf9453_regulator_enable_regmap - enable regulator for regmap users * * @rdev: regulator to operate on * * Regulators that use regmap for their register I/O can set the * enable_reg and enable_mask fields in their descriptor and then use * this as their enable() operation, saving some code. + * + * Return: %0 on success, or negative errno. */ static int pf9453_regulator_enable_regmap(struct regulator_dev *rdev) { @@ -326,13 +316,15 @@ static int pf9453_regulator_enable_regmap(struct regulator_dev *rdev) } /** - * pf9453_regulator_disable_regmap for regmap users + * pf9453_regulator_disable_regmap - disable regulator for regmap users * * @rdev: regulator to operate on * * Regulators that use regmap for their register I/O can set the * enable_reg and enable_mask fields in their descriptor and then use * this as their disable() operation, saving some code. + * + * Return: %0 on success, or negative errno. */ static int pf9453_regulator_disable_regmap(struct regulator_dev *rdev) { @@ -351,7 +343,7 @@ static int pf9453_regulator_disable_regmap(struct regulator_dev *rdev) } /** - * pf9453_regulator_set_voltage_sel_regmap for regmap users + * pf9453_regulator_set_voltage_sel_regmap - set voltage for regmap users * * @rdev: regulator to operate on * @sel: Selector to set @@ -359,6 +351,8 @@ static int pf9453_regulator_disable_regmap(struct regulator_dev *rdev) * Regulators that use regmap for their register I/O can set the * vsel_reg and vsel_mask fields in their descriptor and then use this * as their set_voltage_vsel operation, saving some code. + * + * Return: %0 on success, or negative errno. */ static int pf9453_regulator_set_voltage_sel_regmap(struct regulator_dev *rdev, unsigned int sel) { @@ -409,7 +403,7 @@ static int find_closest_bigger(unsigned int target, const unsigned int *table, } /** - * pf9453_regulator_set_ramp_delay_regmap + * pf9453_regulator_set_ramp_delay_regmap - set ramp delay for regmap users * * @rdev: regulator to operate on * @ramp_delay: desired ramp delay value in microseconds @@ -417,6 +411,8 @@ static int find_closest_bigger(unsigned int target, const unsigned int *table, * Regulators that use regmap for their register I/O can set the ramp_reg * and ramp_mask fields in their descriptor and then use this as their * set_ramp_delay operation, saving some code. + * + * Return: %0 on success, or negative errno. */ static int pf9453_regulator_set_ramp_delay_regmap(struct regulator_dev *rdev, int ramp_delay) { @@ -536,21 +532,15 @@ static int buck_set_dvs(const struct regulator_desc *desc, } } - if (ret == 0) { - struct pf9453_regulator_desc *regulator = container_of(desc, - struct pf9453_regulator_desc, desc); - - /* Enable DVS control through PMIC_STBY_REQ for this BUCK */ - ret = pf9453_pmic_write(pf9453, regulator->desc.enable_reg, - BUCK2_LPMODE, BUCK2_LPMODE); - } return ret; } static int pf9453_set_dvs_levels(struct device_node *np, const struct regulator_desc *desc, struct regulator_config *cfg) { - struct pf9453_regulator_desc *data = container_of(desc, struct pf9453_regulator_desc, desc); + const struct pf9453_regulator_desc *data = container_of_const(desc, + struct pf9453_regulator_desc, + desc); struct pf9453 *pf9453 = dev_get_drvdata(cfg->dev); const struct pf9453_dvs_config *dvs = &data->dvs; unsigned int reg, mask; diff --git a/drivers/regulator/qcom-labibb-regulator.c b/drivers/regulator/qcom-labibb-regulator.c index ba3f9391565f..1b14015caca6 100644 --- a/drivers/regulator/qcom-labibb-regulator.c +++ b/drivers/regulator/qcom-labibb-regulator.c @@ -230,7 +230,7 @@ static void qcom_labibb_ocp_recovery_worker(struct work_struct *work) return; reschedule: - mod_delayed_work(system_wq, &vreg->ocp_recovery_work, + mod_delayed_work(system_dfl_wq, &vreg->ocp_recovery_work, msecs_to_jiffies(OCP_RECOVERY_INTERVAL_MS)); } @@ -510,7 +510,7 @@ reschedule: * taking action is not truly urgent anymore. */ vreg->sc_count++; - mod_delayed_work(system_wq, &vreg->sc_recovery_work, + mod_delayed_work(system_dfl_wq, &vreg->sc_recovery_work, msecs_to_jiffies(SC_RECOVERY_INTERVAL_MS)); } diff --git a/drivers/regulator/qcom-rpmh-regulator.c b/drivers/regulator/qcom-rpmh-regulator.c index 109f0aae09b1..6e4cb2871fca 100644 --- a/drivers/regulator/qcom-rpmh-regulator.c +++ b/drivers/regulator/qcom-rpmh-regulator.c @@ -1,6 +1,6 @@ // SPDX-License-Identifier: GPL-2.0 // Copyright (c) 2018-2021, The Linux Foundation. All rights reserved. -// Copyright (c) 2023 Qualcomm Innovation Center, Inc. All rights reserved. +// Copyright (c) Qualcomm Technologies, Inc. and/or its subsidiaries. #define pr_fmt(fmt) "%s: " fmt, __func__ @@ -32,6 +32,34 @@ enum rpmh_regulator_type { XOB, }; +/** + * enum regulator_hw_type - supported regulator types + * @SMPS: Switch mode power supply. + * @LDO: Linear Dropout regulator. + * @BOB: Buck/Boost type regulator. + * @VS: Simple voltage ON/OFF switch. + * @NUM_REGULATOR_TYPES: Number of regulator types. + */ +enum regulator_hw_type { + SMPS, + LDO, + BOB, + VS, + NUM_REGULATOR_TYPES, +}; + +struct resource_name_formats { + const char *rsc_name_fmt; + const char *rsc_name_fmt1; +}; + +static const struct resource_name_formats vreg_rsc_name_lookup[NUM_REGULATOR_TYPES] = { + [SMPS] = {"S%d%s", "smp%s%d"}, + [LDO] = {"L%d%s", "ldo%s%d"}, + [BOB] = {"B%d%s", "bob%s%d"}, + [VS] = {"VS%d%s", "vs%s%d"}, +}; + #define RPMH_REGULATOR_REG_VRM_VOLTAGE 0x0 #define RPMH_REGULATOR_REG_ENABLE 0x4 #define RPMH_REGULATOR_REG_VRM_MODE 0x8 @@ -64,6 +92,12 @@ enum rpmh_regulator_type { #define PMIC5_BOB_MODE_AUTO 6 #define PMIC5_BOB_MODE_PWM 7 +#define PMIC530_LDO_MODE_RETENTION 3 +#define PMIC530_LDO_MODE_LPM 4 +#define PMIC530_LDO_MODE_OPM 5 +#define PMIC530_LDO_MODE_HPM 7 + +#define PMIC_ID_LEN 4 /** * struct rpmh_vreg_hw_data - RPMh regulator hardware configurations * @regulator_type: RPMh accelerator type used to manage this @@ -136,17 +170,17 @@ struct rpmh_vreg { * struct rpmh_vreg_init_data - initialization data for an RPMh regulator * @name: Name for the regulator which also corresponds * to the device tree subnode name of the regulator - * @resource_name: RPMh regulator resource name format string. - * This must include exactly one field: '%s' which - * is filled at run-time with the PMIC ID provided - * by device tree property qcom,pmic-id. Example: - * "ldo%s1" for RPMh resource "ldoa1". + * @index: This is the index number of the regulator present + * on the PMIC. + * @vreg_hw_type: Regulator HW type enum, this must be BOB, SMPS, + * LDO, VS, based on the regulator HW type. * @supply_name: Parent supply regulator name * @hw_data: Configuration data for this PMIC regulator type */ struct rpmh_vreg_init_data { const char *name; - const char *resource_name; + enum regulator_hw_type vreg_hw_type; + int index; const char *supply_name; const struct rpmh_vreg_hw_data *hw_data; }; @@ -417,6 +451,7 @@ static int rpmh_regulator_init_vreg(struct rpmh_vreg *vreg, struct device *dev, { struct regulator_config reg_config = {}; char rpmh_resource_name[20] = ""; + const char *rsc_name; const struct rpmh_vreg_init_data *rpmh_data; struct regulator_init_data *init_data; struct regulator_dev *rdev; @@ -433,8 +468,16 @@ static int rpmh_regulator_init_vreg(struct rpmh_vreg *vreg, struct device *dev, return -EINVAL; } - scnprintf(rpmh_resource_name, sizeof(rpmh_resource_name), - rpmh_data->resource_name, pmic_id); + if (strnlen(pmic_id, PMIC_ID_LEN) > 1 && strnstr(pmic_id, "_E", PMIC_ID_LEN)) { + rsc_name = vreg_rsc_name_lookup[rpmh_data->vreg_hw_type].rsc_name_fmt; + scnprintf(rpmh_resource_name, sizeof(rpmh_resource_name), + rsc_name, rpmh_data->index, pmic_id); + + } else { + rsc_name = vreg_rsc_name_lookup[rpmh_data->vreg_hw_type].rsc_name_fmt1; + scnprintf(rpmh_resource_name, sizeof(rpmh_resource_name), + rsc_name, pmic_id, rpmh_data->index); + } vreg->addr = cmd_db_read_addr(rpmh_resource_name); if (!vreg->addr) { @@ -519,6 +562,14 @@ static const int pmic_mode_map_pmic5_ldo_hpm[REGULATOR_MODE_STANDBY + 1] = { [REGULATOR_MODE_FAST] = -EINVAL, }; +static const int pmic_mode_map_pmic530_ldo[REGULATOR_MODE_STANDBY + 1] = { + [REGULATOR_MODE_INVALID] = -EINVAL, + [REGULATOR_MODE_STANDBY] = PMIC530_LDO_MODE_RETENTION, + [REGULATOR_MODE_IDLE] = PMIC530_LDO_MODE_LPM, + [REGULATOR_MODE_NORMAL] = PMIC530_LDO_MODE_OPM, + [REGULATOR_MODE_FAST] = PMIC530_LDO_MODE_HPM, +}; + static unsigned int rpmh_regulator_pmic4_ldo_of_map_mode(unsigned int rpmh_mode) { unsigned int mode; @@ -541,6 +592,30 @@ static unsigned int rpmh_regulator_pmic4_ldo_of_map_mode(unsigned int rpmh_mode) return mode; } +static unsigned int rpmh_regulator_pmic530_ldo_of_map_mode(unsigned int rpmh_mode) +{ + unsigned int mode; + + switch (rpmh_mode) { + case RPMH_REGULATOR_MODE_HPM: + mode = REGULATOR_MODE_FAST; + break; + case RPMH_REGULATOR_MODE_AUTO: + mode = REGULATOR_MODE_NORMAL; + break; + case RPMH_REGULATOR_MODE_LPM: + mode = REGULATOR_MODE_IDLE; + break; + case RPMH_REGULATOR_MODE_RET: + mode = REGULATOR_MODE_STANDBY; + break; + default: + mode = REGULATOR_MODE_INVALID; + break; + } + return mode; +} + static const int pmic_mode_map_pmic4_smps[REGULATOR_MODE_STANDBY + 1] = { [REGULATOR_MODE_INVALID] = -EINVAL, [REGULATOR_MODE_STANDBY] = PMIC4_SMPS_MODE_RETENTION, @@ -904,671 +979,816 @@ static const struct rpmh_vreg_hw_data pmic5_bob = { .of_map_mode = rpmh_regulator_pmic4_bob_of_map_mode, }; -#define RPMH_VREG(_name, _resource_name, _hw_data, _supply_name) \ +static const struct rpmh_vreg_hw_data pmic5_nldo530 = { + .regulator_type = VRM, + .ops = &rpmh_regulator_vrm_drms_ops, + .voltage_ranges = (struct linear_range[]) { + REGULATOR_LINEAR_RANGE(320000, 0, 210, 8000), + }, + .n_linear_ranges = 1, + .n_voltages = 211, + .hpm_min_load_uA = 30000, + .pmic_mode_map = pmic_mode_map_pmic530_ldo, + .of_map_mode = rpmh_regulator_pmic530_ldo_of_map_mode, +}; + +static const struct rpmh_vreg_hw_data pmic5_pldo530_mvp150 = { + .regulator_type = VRM, + .ops = &rpmh_regulator_vrm_drms_ops, + .voltage_ranges = (struct linear_range[]) { + REGULATOR_LINEAR_RANGE(1504000, 0, 255, 8000), + }, + .n_linear_ranges = 1, + .n_voltages = 256, + .hpm_min_load_uA = 10000, + .pmic_mode_map = pmic_mode_map_pmic530_ldo, + .of_map_mode = rpmh_regulator_pmic530_ldo_of_map_mode, +}; + +static const struct rpmh_vreg_hw_data pmic5_pldo530_mvp300 = { + .regulator_type = VRM, + .ops = &rpmh_regulator_vrm_drms_ops, + .voltage_ranges = (struct linear_range[]) { + REGULATOR_LINEAR_RANGE(1504000, 0, 255, 8000), + }, + .n_linear_ranges = 1, + .n_voltages = 256, + .hpm_min_load_uA = 20000, + .pmic_mode_map = pmic_mode_map_pmic530_ldo, + .of_map_mode = rpmh_regulator_pmic530_ldo_of_map_mode, +}; + +static const struct rpmh_vreg_hw_data pmic5_pldo530_mvp600 = { + .regulator_type = VRM, + .ops = &rpmh_regulator_vrm_drms_ops, + .voltage_ranges = (struct linear_range[]) { + REGULATOR_LINEAR_RANGE(1504000, 0, 255, 8000), + }, + .n_linear_ranges = 1, + .n_voltages = 256, + .hpm_min_load_uA = 40000, + .pmic_mode_map = pmic_mode_map_pmic530_ldo, + .of_map_mode = rpmh_regulator_pmic530_ldo_of_map_mode, +}; + +static const struct rpmh_vreg_hw_data pmic5_ftsmps530 = { + .regulator_type = VRM, + .ops = &rpmh_regulator_vrm_ops, + .voltage_ranges = (struct linear_range[]) { + REGULATOR_LINEAR_RANGE(252000, 0, 305, 4000), + REGULATOR_LINEAR_RANGE(1480000, 306, 464, 8000), + }, + .n_linear_ranges = 2, + .n_voltages = 465, + .pmic_mode_map = pmic_mode_map_pmic5_smps, + .of_map_mode = rpmh_regulator_pmic4_smps_of_map_mode, +}; + +#define RPMH_VREG(_name, _vreg_hw_type, _index, _hw_data, _supply_name) \ { \ .name = _name, \ - .resource_name = _resource_name, \ + .vreg_hw_type = _vreg_hw_type, \ + .index = _index, \ .hw_data = _hw_data, \ .supply_name = _supply_name, \ } static const struct rpmh_vreg_init_data pm8998_vreg_data[] = { - RPMH_VREG("smps1", "smp%s1", &pmic4_ftsmps426, "vdd-s1"), - RPMH_VREG("smps2", "smp%s2", &pmic4_ftsmps426, "vdd-s2"), - RPMH_VREG("smps3", "smp%s3", &pmic4_hfsmps3, "vdd-s3"), - RPMH_VREG("smps4", "smp%s4", &pmic4_hfsmps3, "vdd-s4"), - RPMH_VREG("smps5", "smp%s5", &pmic4_hfsmps3, "vdd-s5"), - RPMH_VREG("smps6", "smp%s6", &pmic4_ftsmps426, "vdd-s6"), - RPMH_VREG("smps7", "smp%s7", &pmic4_ftsmps426, "vdd-s7"), - RPMH_VREG("smps8", "smp%s8", &pmic4_ftsmps426, "vdd-s8"), - RPMH_VREG("smps9", "smp%s9", &pmic4_ftsmps426, "vdd-s9"), - RPMH_VREG("smps10", "smp%s10", &pmic4_ftsmps426, "vdd-s10"), - RPMH_VREG("smps11", "smp%s11", &pmic4_ftsmps426, "vdd-s11"), - RPMH_VREG("smps12", "smp%s12", &pmic4_ftsmps426, "vdd-s12"), - RPMH_VREG("smps13", "smp%s13", &pmic4_ftsmps426, "vdd-s13"), - RPMH_VREG("ldo1", "ldo%s1", &pmic4_nldo, "vdd-l1-l27"), - RPMH_VREG("ldo2", "ldo%s2", &pmic4_nldo, "vdd-l2-l8-l17"), - RPMH_VREG("ldo3", "ldo%s3", &pmic4_nldo, "vdd-l3-l11"), - RPMH_VREG("ldo4", "ldo%s4", &pmic4_nldo, "vdd-l4-l5"), - RPMH_VREG("ldo5", "ldo%s5", &pmic4_nldo, "vdd-l4-l5"), - RPMH_VREG("ldo6", "ldo%s6", &pmic4_pldo, "vdd-l6"), - RPMH_VREG("ldo7", "ldo%s7", &pmic4_pldo_lv, "vdd-l7-l12-l14-l15"), - RPMH_VREG("ldo8", "ldo%s8", &pmic4_nldo, "vdd-l2-l8-l17"), - RPMH_VREG("ldo9", "ldo%s9", &pmic4_pldo, "vdd-l9"), - RPMH_VREG("ldo10", "ldo%s10", &pmic4_pldo, "vdd-l10-l23-l25"), - RPMH_VREG("ldo11", "ldo%s11", &pmic4_nldo, "vdd-l3-l11"), - RPMH_VREG("ldo12", "ldo%s12", &pmic4_pldo_lv, "vdd-l7-l12-l14-l15"), - RPMH_VREG("ldo13", "ldo%s13", &pmic4_pldo, "vdd-l13-l19-l21"), - RPMH_VREG("ldo14", "ldo%s14", &pmic4_pldo_lv, "vdd-l7-l12-l14-l15"), - RPMH_VREG("ldo15", "ldo%s15", &pmic4_pldo_lv, "vdd-l7-l12-l14-l15"), - RPMH_VREG("ldo16", "ldo%s16", &pmic4_pldo, "vdd-l16-l28"), - RPMH_VREG("ldo17", "ldo%s17", &pmic4_nldo, "vdd-l2-l8-l17"), - RPMH_VREG("ldo18", "ldo%s18", &pmic4_pldo, "vdd-l18-l22"), - RPMH_VREG("ldo19", "ldo%s19", &pmic4_pldo, "vdd-l13-l19-l21"), - RPMH_VREG("ldo20", "ldo%s20", &pmic4_pldo, "vdd-l20-l24"), - RPMH_VREG("ldo21", "ldo%s21", &pmic4_pldo, "vdd-l13-l19-l21"), - RPMH_VREG("ldo22", "ldo%s22", &pmic4_pldo, "vdd-l18-l22"), - RPMH_VREG("ldo23", "ldo%s23", &pmic4_pldo, "vdd-l10-l23-l25"), - RPMH_VREG("ldo24", "ldo%s24", &pmic4_pldo, "vdd-l20-l24"), - RPMH_VREG("ldo25", "ldo%s25", &pmic4_pldo, "vdd-l10-l23-l25"), - RPMH_VREG("ldo26", "ldo%s26", &pmic4_nldo, "vdd-l26"), - RPMH_VREG("ldo27", "ldo%s27", &pmic4_nldo, "vdd-l1-l27"), - RPMH_VREG("ldo28", "ldo%s28", &pmic4_pldo, "vdd-l16-l28"), - RPMH_VREG("lvs1", "vs%s1", &pmic4_lvs, "vin-lvs-1-2"), - RPMH_VREG("lvs2", "vs%s2", &pmic4_lvs, "vin-lvs-1-2"), + RPMH_VREG("smps1", SMPS, 1, &pmic4_ftsmps426, "vdd-s1"), + RPMH_VREG("smps2", SMPS, 2, &pmic4_ftsmps426, "vdd-s2"), + RPMH_VREG("smps3", SMPS, 3, &pmic4_hfsmps3, "vdd-s3"), + RPMH_VREG("smps4", SMPS, 4, &pmic4_hfsmps3, "vdd-s4"), + RPMH_VREG("smps5", SMPS, 5, &pmic4_hfsmps3, "vdd-s5"), + RPMH_VREG("smps6", SMPS, 6, &pmic4_ftsmps426, "vdd-s6"), + RPMH_VREG("smps7", SMPS, 7, &pmic4_ftsmps426, "vdd-s7"), + RPMH_VREG("smps8", SMPS, 8, &pmic4_ftsmps426, "vdd-s8"), + RPMH_VREG("smps9", SMPS, 9, &pmic4_ftsmps426, "vdd-s9"), + RPMH_VREG("smps10", SMPS, 10, &pmic4_ftsmps426, "vdd-s10"), + RPMH_VREG("smps11", SMPS, 11, &pmic4_ftsmps426, "vdd-s11"), + RPMH_VREG("smps12", SMPS, 12, &pmic4_ftsmps426, "vdd-s12"), + RPMH_VREG("smps13", SMPS, 13, &pmic4_ftsmps426, "vdd-s13"), + RPMH_VREG("ldo1", LDO, 1, &pmic4_nldo, "vdd-l1-l27"), + RPMH_VREG("ldo2", LDO, 2, &pmic4_nldo, "vdd-l2-l8-l17"), + RPMH_VREG("ldo3", LDO, 3, &pmic4_nldo, "vdd-l3-l11"), + RPMH_VREG("ldo4", LDO, 4, &pmic4_nldo, "vdd-l4-l5"), + RPMH_VREG("ldo5", LDO, 5, &pmic4_nldo, "vdd-l4-l5"), + RPMH_VREG("ldo6", LDO, 6, &pmic4_pldo, "vdd-l6"), + RPMH_VREG("ldo7", LDO, 7, &pmic4_pldo_lv, "vdd-l7-l12-l14-l15"), + RPMH_VREG("ldo8", LDO, 8, &pmic4_nldo, "vdd-l2-l8-l17"), + RPMH_VREG("ldo9", LDO, 9, &pmic4_pldo, "vdd-l9"), + RPMH_VREG("ldo10", LDO, 10, &pmic4_pldo, "vdd-l10-l23-l25"), + RPMH_VREG("ldo11", LDO, 11, &pmic4_nldo, "vdd-l3-l11"), + RPMH_VREG("ldo12", LDO, 12, &pmic4_pldo_lv, "vdd-l7-l12-l14-l15"), + RPMH_VREG("ldo13", LDO, 13, &pmic4_pldo, "vdd-l13-l19-l21"), + RPMH_VREG("ldo14", LDO, 14, &pmic4_pldo_lv, "vdd-l7-l12-l14-l15"), + RPMH_VREG("ldo15", LDO, 15, &pmic4_pldo_lv, "vdd-l7-l12-l14-l15"), + RPMH_VREG("ldo16", LDO, 16, &pmic4_pldo, "vdd-l16-l28"), + RPMH_VREG("ldo17", LDO, 17, &pmic4_nldo, "vdd-l2-l8-l17"), + RPMH_VREG("ldo18", LDO, 18, &pmic4_pldo, "vdd-l18-l22"), + RPMH_VREG("ldo19", LDO, 19, &pmic4_pldo, "vdd-l13-l19-l21"), + RPMH_VREG("ldo20", LDO, 20, &pmic4_pldo, "vdd-l20-l24"), + RPMH_VREG("ldo21", LDO, 21, &pmic4_pldo, "vdd-l13-l19-l21"), + RPMH_VREG("ldo22", LDO, 22, &pmic4_pldo, "vdd-l18-l22"), + RPMH_VREG("ldo23", LDO, 23, &pmic4_pldo, "vdd-l10-l23-l25"), + RPMH_VREG("ldo24", LDO, 24, &pmic4_pldo, "vdd-l20-l24"), + RPMH_VREG("ldo25", LDO, 25, &pmic4_pldo, "vdd-l10-l23-l25"), + RPMH_VREG("ldo26", LDO, 26, &pmic4_nldo, "vdd-l26"), + RPMH_VREG("ldo27", LDO, 27, &pmic4_nldo, "vdd-l1-l27"), + RPMH_VREG("ldo28", LDO, 28, &pmic4_pldo, "vdd-l16-l28"), + RPMH_VREG("lvs1", VS, 1, &pmic4_lvs, "vin-lvs-1-2"), + RPMH_VREG("lvs2", VS, 2, &pmic4_lvs, "vin-lvs-1-2"), {} }; static const struct rpmh_vreg_init_data pmg1110_vreg_data[] = { - RPMH_VREG("smps1", "smp%s1", &pmic5_ftsmps510, "vdd-s1"), + RPMH_VREG("smps1", SMPS, 1, &pmic5_ftsmps510, "vdd-s1"), {} }; static const struct rpmh_vreg_init_data pmi8998_vreg_data[] = { - RPMH_VREG("bob", "bob%s1", &pmic4_bob, "vdd-bob"), + RPMH_VREG("bob", BOB, 1, &pmic4_bob, "vdd-bob"), {} }; static const struct rpmh_vreg_init_data pm8005_vreg_data[] = { - RPMH_VREG("smps1", "smp%s1", &pmic4_ftsmps426, "vdd-s1"), - RPMH_VREG("smps2", "smp%s2", &pmic4_ftsmps426, "vdd-s2"), - RPMH_VREG("smps3", "smp%s3", &pmic4_ftsmps426, "vdd-s3"), - RPMH_VREG("smps4", "smp%s4", &pmic4_ftsmps426, "vdd-s4"), + RPMH_VREG("smps1", SMPS, 1, &pmic4_ftsmps426, "vdd-s1"), + RPMH_VREG("smps2", SMPS, 2, &pmic4_ftsmps426, "vdd-s2"), + RPMH_VREG("smps3", SMPS, 3, &pmic4_ftsmps426, "vdd-s3"), + RPMH_VREG("smps4", SMPS, 4, &pmic4_ftsmps426, "vdd-s4"), {} }; static const struct rpmh_vreg_init_data pm8150_vreg_data[] = { - RPMH_VREG("smps1", "smp%s1", &pmic5_ftsmps510, "vdd-s1"), - RPMH_VREG("smps2", "smp%s2", &pmic5_ftsmps510, "vdd-s2"), - RPMH_VREG("smps3", "smp%s3", &pmic5_ftsmps510, "vdd-s3"), - RPMH_VREG("smps4", "smp%s4", &pmic5_hfsmps510, "vdd-s4"), - RPMH_VREG("smps5", "smp%s5", &pmic5_hfsmps510, "vdd-s5"), - RPMH_VREG("smps6", "smp%s6", &pmic5_ftsmps510, "vdd-s6"), - RPMH_VREG("smps7", "smp%s7", &pmic5_ftsmps510, "vdd-s7"), - RPMH_VREG("smps8", "smp%s8", &pmic5_ftsmps510, "vdd-s8"), - RPMH_VREG("smps9", "smp%s9", &pmic5_ftsmps510, "vdd-s9"), - RPMH_VREG("smps10", "smp%s10", &pmic5_ftsmps510, "vdd-s10"), - RPMH_VREG("ldo1", "ldo%s1", &pmic5_nldo, "vdd-l1-l8-l11"), - RPMH_VREG("ldo2", "ldo%s2", &pmic5_pldo, "vdd-l2-l10"), - RPMH_VREG("ldo3", "ldo%s3", &pmic5_nldo, "vdd-l3-l4-l5-l18"), - RPMH_VREG("ldo4", "ldo%s4", &pmic5_nldo, "vdd-l3-l4-l5-l18"), - RPMH_VREG("ldo5", "ldo%s5", &pmic5_nldo, "vdd-l3-l4-l5-l18"), - RPMH_VREG("ldo6", "ldo%s6", &pmic5_nldo, "vdd-l6-l9"), - RPMH_VREG("ldo7", "ldo%s7", &pmic5_pldo, "vdd-l7-l12-l14-l15"), - RPMH_VREG("ldo8", "ldo%s8", &pmic5_nldo, "vdd-l1-l8-l11"), - RPMH_VREG("ldo9", "ldo%s9", &pmic5_nldo, "vdd-l6-l9"), - RPMH_VREG("ldo10", "ldo%s10", &pmic5_pldo, "vdd-l2-l10"), - RPMH_VREG("ldo11", "ldo%s11", &pmic5_nldo, "vdd-l1-l8-l11"), - RPMH_VREG("ldo12", "ldo%s12", &pmic5_pldo_lv, "vdd-l7-l12-l14-l15"), - RPMH_VREG("ldo13", "ldo%s13", &pmic5_pldo, "vdd-l13-l16-l17"), - RPMH_VREG("ldo14", "ldo%s14", &pmic5_pldo_lv, "vdd-l7-l12-l14-l15"), - RPMH_VREG("ldo15", "ldo%s15", &pmic5_pldo_lv, "vdd-l7-l12-l14-l15"), - RPMH_VREG("ldo16", "ldo%s16", &pmic5_pldo, "vdd-l13-l16-l17"), - RPMH_VREG("ldo17", "ldo%s17", &pmic5_pldo, "vdd-l13-l16-l17"), - RPMH_VREG("ldo18", "ldo%s18", &pmic5_nldo, "vdd-l3-l4-l5-l18"), + RPMH_VREG("smps1", SMPS, 1, &pmic5_ftsmps510, "vdd-s1"), + RPMH_VREG("smps2", SMPS, 2, &pmic5_ftsmps510, "vdd-s2"), + RPMH_VREG("smps3", SMPS, 3, &pmic5_ftsmps510, "vdd-s3"), + RPMH_VREG("smps4", SMPS, 4, &pmic5_hfsmps510, "vdd-s4"), + RPMH_VREG("smps5", SMPS, 5, &pmic5_hfsmps510, "vdd-s5"), + RPMH_VREG("smps6", SMPS, 6, &pmic5_ftsmps510, "vdd-s6"), + RPMH_VREG("smps7", SMPS, 7, &pmic5_ftsmps510, "vdd-s7"), + RPMH_VREG("smps8", SMPS, 8, &pmic5_ftsmps510, "vdd-s8"), + RPMH_VREG("smps9", SMPS, 9, &pmic5_ftsmps510, "vdd-s9"), + RPMH_VREG("smps10", SMPS, 10, &pmic5_ftsmps510, "vdd-s10"), + RPMH_VREG("ldo1", LDO, 1, &pmic5_nldo, "vdd-l1-l8-l11"), + RPMH_VREG("ldo2", LDO, 2, &pmic5_pldo, "vdd-l2-l10"), + RPMH_VREG("ldo3", LDO, 3, &pmic5_nldo, "vdd-l3-l4-l5-l18"), + RPMH_VREG("ldo4", LDO, 4, &pmic5_nldo, "vdd-l3-l4-l5-l18"), + RPMH_VREG("ldo5", LDO, 5, &pmic5_nldo, "vdd-l3-l4-l5-l18"), + RPMH_VREG("ldo6", LDO, 6, &pmic5_nldo, "vdd-l6-l9"), + RPMH_VREG("ldo7", LDO, 7, &pmic5_pldo, "vdd-l7-l12-l14-l15"), + RPMH_VREG("ldo8", LDO, 8, &pmic5_nldo, "vdd-l1-l8-l11"), + RPMH_VREG("ldo9", LDO, 9, &pmic5_nldo, "vdd-l6-l9"), + RPMH_VREG("ldo10", LDO, 10, &pmic5_pldo, "vdd-l2-l10"), + RPMH_VREG("ldo11", LDO, 11, &pmic5_nldo, "vdd-l1-l8-l11"), + RPMH_VREG("ldo12", LDO, 12, &pmic5_pldo_lv, "vdd-l7-l12-l14-l15"), + RPMH_VREG("ldo13", LDO, 13, &pmic5_pldo, "vdd-l13-l16-l17"), + RPMH_VREG("ldo14", LDO, 14, &pmic5_pldo_lv, "vdd-l7-l12-l14-l15"), + RPMH_VREG("ldo15", LDO, 15, &pmic5_pldo_lv, "vdd-l7-l12-l14-l15"), + RPMH_VREG("ldo16", LDO, 16, &pmic5_pldo, "vdd-l13-l16-l17"), + RPMH_VREG("ldo17", LDO, 17, &pmic5_pldo, "vdd-l13-l16-l17"), + RPMH_VREG("ldo18", LDO, 18, &pmic5_nldo, "vdd-l3-l4-l5-l18"), {} }; static const struct rpmh_vreg_init_data pm8150l_vreg_data[] = { - RPMH_VREG("smps1", "smp%s1", &pmic5_ftsmps510, "vdd-s1"), - RPMH_VREG("smps2", "smp%s2", &pmic5_ftsmps510, "vdd-s2"), - RPMH_VREG("smps3", "smp%s3", &pmic5_ftsmps510, "vdd-s3"), - RPMH_VREG("smps4", "smp%s4", &pmic5_ftsmps510, "vdd-s4"), - RPMH_VREG("smps5", "smp%s5", &pmic5_ftsmps510, "vdd-s5"), - RPMH_VREG("smps6", "smp%s6", &pmic5_ftsmps510, "vdd-s6"), - RPMH_VREG("smps7", "smp%s7", &pmic5_ftsmps510, "vdd-s7"), - RPMH_VREG("smps8", "smp%s8", &pmic5_hfsmps510, "vdd-s8"), - RPMH_VREG("ldo1", "ldo%s1", &pmic5_pldo_lv, "vdd-l1-l8"), - RPMH_VREG("ldo2", "ldo%s2", &pmic5_nldo, "vdd-l2-l3"), - RPMH_VREG("ldo3", "ldo%s3", &pmic5_nldo, "vdd-l2-l3"), - RPMH_VREG("ldo4", "ldo%s4", &pmic5_pldo, "vdd-l4-l5-l6"), - RPMH_VREG("ldo5", "ldo%s5", &pmic5_pldo, "vdd-l4-l5-l6"), - RPMH_VREG("ldo6", "ldo%s6", &pmic5_pldo, "vdd-l4-l5-l6"), - RPMH_VREG("ldo7", "ldo%s7", &pmic5_pldo, "vdd-l7-l11"), - RPMH_VREG("ldo8", "ldo%s8", &pmic5_pldo_lv, "vdd-l1-l8"), - RPMH_VREG("ldo9", "ldo%s9", &pmic5_pldo, "vdd-l9-l10"), - RPMH_VREG("ldo10", "ldo%s10", &pmic5_pldo, "vdd-l9-l10"), - RPMH_VREG("ldo11", "ldo%s11", &pmic5_pldo, "vdd-l7-l11"), - RPMH_VREG("bob", "bob%s1", &pmic5_bob, "vdd-bob"), + RPMH_VREG("smps1", SMPS, 1, &pmic5_ftsmps510, "vdd-s1"), + RPMH_VREG("smps2", SMPS, 2, &pmic5_ftsmps510, "vdd-s2"), + RPMH_VREG("smps3", SMPS, 3, &pmic5_ftsmps510, "vdd-s3"), + RPMH_VREG("smps4", SMPS, 4, &pmic5_ftsmps510, "vdd-s4"), + RPMH_VREG("smps5", SMPS, 5, &pmic5_ftsmps510, "vdd-s5"), + RPMH_VREG("smps6", SMPS, 6, &pmic5_ftsmps510, "vdd-s6"), + RPMH_VREG("smps7", SMPS, 7, &pmic5_ftsmps510, "vdd-s7"), + RPMH_VREG("smps8", SMPS, 8, &pmic5_hfsmps510, "vdd-s8"), + RPMH_VREG("ldo1", LDO, 1, &pmic5_pldo_lv, "vdd-l1-l8"), + RPMH_VREG("ldo2", LDO, 2, &pmic5_nldo, "vdd-l2-l3"), + RPMH_VREG("ldo3", LDO, 3, &pmic5_nldo, "vdd-l2-l3"), + RPMH_VREG("ldo4", LDO, 4, &pmic5_pldo, "vdd-l4-l5-l6"), + RPMH_VREG("ldo5", LDO, 5, &pmic5_pldo, "vdd-l4-l5-l6"), + RPMH_VREG("ldo6", LDO, 6, &pmic5_pldo, "vdd-l4-l5-l6"), + RPMH_VREG("ldo7", LDO, 7, &pmic5_pldo, "vdd-l7-l11"), + RPMH_VREG("ldo8", LDO, 8, &pmic5_pldo_lv, "vdd-l1-l8"), + RPMH_VREG("ldo9", LDO, 9, &pmic5_pldo, "vdd-l9-l10"), + RPMH_VREG("ldo10", LDO, 10, &pmic5_pldo, "vdd-l9-l10"), + RPMH_VREG("ldo11", LDO, 11, &pmic5_pldo, "vdd-l7-l11"), + RPMH_VREG("bob", BOB, 1, &pmic5_bob, "vdd-bob"), {} }; static const struct rpmh_vreg_init_data pmm8155au_vreg_data[] = { - RPMH_VREG("smps1", "smp%s1", &pmic5_ftsmps510, "vdd-s1"), - RPMH_VREG("smps2", "smp%s2", &pmic5_ftsmps510, "vdd-s2"), - RPMH_VREG("smps3", "smp%s3", &pmic5_ftsmps510, "vdd-s3"), - RPMH_VREG("smps4", "smp%s4", &pmic5_hfsmps510, "vdd-s4"), - RPMH_VREG("smps5", "smp%s5", &pmic5_hfsmps510, "vdd-s5"), - RPMH_VREG("smps6", "smp%s6", &pmic5_ftsmps510, "vdd-s6"), - RPMH_VREG("smps7", "smp%s7", &pmic5_ftsmps510, "vdd-s7"), - RPMH_VREG("smps8", "smp%s8", &pmic5_ftsmps510, "vdd-s8"), - RPMH_VREG("smps9", "smp%s9", &pmic5_ftsmps510, "vdd-s9"), - RPMH_VREG("smps10", "smp%s10", &pmic5_ftsmps510, "vdd-s10"), - RPMH_VREG("ldo1", "ldo%s1", &pmic5_nldo, "vdd-l1-l8-l11"), - RPMH_VREG("ldo2", "ldo%s2", &pmic5_pldo, "vdd-l2-l10"), - RPMH_VREG("ldo3", "ldo%s3", &pmic5_nldo, "vdd-l3-l4-l5-l18"), - RPMH_VREG("ldo4", "ldo%s4", &pmic5_nldo, "vdd-l3-l4-l5-l18"), - RPMH_VREG("ldo5", "ldo%s5", &pmic5_nldo, "vdd-l3-l4-l5-l18"), - RPMH_VREG("ldo6", "ldo%s6", &pmic5_nldo, "vdd-l6-l9"), - RPMH_VREG("ldo7", "ldo%s7", &pmic5_pldo_lv, "vdd-l7-l12-l14-l15"), - RPMH_VREG("ldo8", "ldo%s8", &pmic5_nldo, "vdd-l1-l8-l11"), - RPMH_VREG("ldo9", "ldo%s9", &pmic5_nldo, "vdd-l6-l9"), - RPMH_VREG("ldo10", "ldo%s10", &pmic5_pldo, "vdd-l2-l10"), - RPMH_VREG("ldo11", "ldo%s11", &pmic5_nldo, "vdd-l1-l8-l11"), - RPMH_VREG("ldo12", "ldo%s12", &pmic5_pldo_lv, "vdd-l7-l12-l14-l15"), - RPMH_VREG("ldo13", "ldo%s13", &pmic5_pldo, "vdd-l13-l16-l17"), - RPMH_VREG("ldo14", "ldo%s14", &pmic5_pldo_lv, "vdd-l7-l12-l14-l15"), - RPMH_VREG("ldo15", "ldo%s15", &pmic5_pldo_lv, "vdd-l7-l12-l14-l15"), - RPMH_VREG("ldo16", "ldo%s16", &pmic5_pldo, "vdd-l13-l16-l17"), - RPMH_VREG("ldo17", "ldo%s17", &pmic5_pldo, "vdd-l13-l16-l17"), - RPMH_VREG("ldo18", "ldo%s18", &pmic5_nldo, "vdd-l3-l4-l5-l18"), + RPMH_VREG("smps1", SMPS, 1, &pmic5_ftsmps510, "vdd-s1"), + RPMH_VREG("smps2", SMPS, 2, &pmic5_ftsmps510, "vdd-s2"), + RPMH_VREG("smps3", SMPS, 3, &pmic5_ftsmps510, "vdd-s3"), + RPMH_VREG("smps4", SMPS, 4, &pmic5_hfsmps510, "vdd-s4"), + RPMH_VREG("smps5", SMPS, 5, &pmic5_hfsmps510, "vdd-s5"), + RPMH_VREG("smps6", SMPS, 6, &pmic5_ftsmps510, "vdd-s6"), + RPMH_VREG("smps7", SMPS, 7, &pmic5_ftsmps510, "vdd-s7"), + RPMH_VREG("smps8", SMPS, 8, &pmic5_ftsmps510, "vdd-s8"), + RPMH_VREG("smps9", SMPS, 9, &pmic5_ftsmps510, "vdd-s9"), + RPMH_VREG("smps10", SMPS, 10, &pmic5_ftsmps510, "vdd-s10"), + RPMH_VREG("ldo1", LDO, 1, &pmic5_nldo, "vdd-l1-l8-l11"), + RPMH_VREG("ldo2", LDO, 2, &pmic5_pldo, "vdd-l2-l10"), + RPMH_VREG("ldo3", LDO, 3, &pmic5_nldo, "vdd-l3-l4-l5-l18"), + RPMH_VREG("ldo4", LDO, 4, &pmic5_nldo, "vdd-l3-l4-l5-l18"), + RPMH_VREG("ldo5", LDO, 5, &pmic5_nldo, "vdd-l3-l4-l5-l18"), + RPMH_VREG("ldo6", LDO, 6, &pmic5_nldo, "vdd-l6-l9"), + RPMH_VREG("ldo7", LDO, 7, &pmic5_pldo_lv, "vdd-l7-l12-l14-l15"), + RPMH_VREG("ldo8", LDO, 8, &pmic5_nldo, "vdd-l1-l8-l11"), + RPMH_VREG("ldo9", LDO, 9, &pmic5_nldo, "vdd-l6-l9"), + RPMH_VREG("ldo10", LDO, 10, &pmic5_pldo, "vdd-l2-l10"), + RPMH_VREG("ldo11", LDO, 11, &pmic5_nldo, "vdd-l1-l8-l11"), + RPMH_VREG("ldo12", LDO, 12, &pmic5_pldo_lv, "vdd-l7-l12-l14-l15"), + RPMH_VREG("ldo13", LDO, 13, &pmic5_pldo, "vdd-l13-l16-l17"), + RPMH_VREG("ldo14", LDO, 14, &pmic5_pldo_lv, "vdd-l7-l12-l14-l15"), + RPMH_VREG("ldo15", LDO, 15, &pmic5_pldo_lv, "vdd-l7-l12-l14-l15"), + RPMH_VREG("ldo16", LDO, 16, &pmic5_pldo, "vdd-l13-l16-l17"), + RPMH_VREG("ldo17", LDO, 17, &pmic5_pldo, "vdd-l13-l16-l17"), + RPMH_VREG("ldo18", LDO, 18, &pmic5_nldo, "vdd-l3-l4-l5-l18"), {} }; static const struct rpmh_vreg_init_data pmm8654au_vreg_data[] = { - RPMH_VREG("smps1", "smp%s1", &pmic5_ftsmps527, "vdd-s1"), - RPMH_VREG("smps2", "smp%s2", &pmic5_ftsmps527, "vdd-s2"), - RPMH_VREG("smps3", "smp%s3", &pmic5_ftsmps527, "vdd-s3"), - RPMH_VREG("smps4", "smp%s4", &pmic5_ftsmps527, "vdd-s4"), - RPMH_VREG("smps5", "smp%s5", &pmic5_ftsmps527, "vdd-s5"), - RPMH_VREG("smps6", "smp%s6", &pmic5_ftsmps527, "vdd-s6"), - RPMH_VREG("smps7", "smp%s7", &pmic5_ftsmps527, "vdd-s7"), - RPMH_VREG("smps8", "smp%s8", &pmic5_ftsmps527, "vdd-s8"), - RPMH_VREG("smps9", "smp%s9", &pmic5_ftsmps527, "vdd-s9"), - RPMH_VREG("ldo1", "ldo%s1", &pmic5_nldo515, "vdd-s9"), - RPMH_VREG("ldo2", "ldo%s2", &pmic5_nldo515, "vdd-l2-l3"), - RPMH_VREG("ldo3", "ldo%s3", &pmic5_nldo515, "vdd-l2-l3"), - RPMH_VREG("ldo4", "ldo%s4", &pmic5_nldo515, "vdd-s9"), - RPMH_VREG("ldo5", "ldo%s5", &pmic5_nldo515, "vdd-s9"), - RPMH_VREG("ldo6", "ldo%s6", &pmic5_nldo515, "vdd-l6-l7"), - RPMH_VREG("ldo7", "ldo%s7", &pmic5_nldo515, "vdd-l6-l7"), - RPMH_VREG("ldo8", "ldo%s8", &pmic5_pldo515_mv, "vdd-l8-l9"), - RPMH_VREG("ldo9", "ldo%s9", &pmic5_pldo, "vdd-l8-l9"), + RPMH_VREG("smps1", SMPS, 1, &pmic5_ftsmps527, "vdd-s1"), + RPMH_VREG("smps2", SMPS, 2, &pmic5_ftsmps527, "vdd-s2"), + RPMH_VREG("smps3", SMPS, 3, &pmic5_ftsmps527, "vdd-s3"), + RPMH_VREG("smps4", SMPS, 4, &pmic5_ftsmps527, "vdd-s4"), + RPMH_VREG("smps5", SMPS, 5, &pmic5_ftsmps527, "vdd-s5"), + RPMH_VREG("smps6", SMPS, 6, &pmic5_ftsmps527, "vdd-s6"), + RPMH_VREG("smps7", SMPS, 7, &pmic5_ftsmps527, "vdd-s7"), + RPMH_VREG("smps8", SMPS, 8, &pmic5_ftsmps527, "vdd-s8"), + RPMH_VREG("smps9", SMPS, 9, &pmic5_ftsmps527, "vdd-s9"), + RPMH_VREG("ldo1", LDO, 1, &pmic5_nldo515, "vdd-s9"), + RPMH_VREG("ldo2", LDO, 2, &pmic5_nldo515, "vdd-l2-l3"), + RPMH_VREG("ldo3", LDO, 3, &pmic5_nldo515, "vdd-l2-l3"), + RPMH_VREG("ldo4", LDO, 4, &pmic5_nldo515, "vdd-s9"), + RPMH_VREG("ldo5", LDO, 5, &pmic5_nldo515, "vdd-s9"), + RPMH_VREG("ldo6", LDO, 6, &pmic5_nldo515, "vdd-l6-l7"), + RPMH_VREG("ldo7", LDO, 7, &pmic5_nldo515, "vdd-l6-l7"), + RPMH_VREG("ldo8", LDO, 8, &pmic5_pldo515_mv, "vdd-l8-l9"), + RPMH_VREG("ldo9", LDO, 9, &pmic5_pldo, "vdd-l8-l9"), {} }; static const struct rpmh_vreg_init_data pm8350_vreg_data[] = { - RPMH_VREG("smps1", "smp%s1", &pmic5_ftsmps510, "vdd-s1"), - RPMH_VREG("smps2", "smp%s2", &pmic5_ftsmps510, "vdd-s2"), - RPMH_VREG("smps3", "smp%s3", &pmic5_ftsmps510, "vdd-s3"), - RPMH_VREG("smps4", "smp%s4", &pmic5_ftsmps510, "vdd-s4"), - RPMH_VREG("smps5", "smp%s5", &pmic5_ftsmps510, "vdd-s5"), - RPMH_VREG("smps6", "smp%s6", &pmic5_ftsmps510, "vdd-s6"), - RPMH_VREG("smps7", "smp%s7", &pmic5_ftsmps510, "vdd-s7"), - RPMH_VREG("smps8", "smp%s8", &pmic5_ftsmps510, "vdd-s8"), - RPMH_VREG("smps9", "smp%s9", &pmic5_ftsmps510, "vdd-s9"), - RPMH_VREG("smps10", "smp%s10", &pmic5_hfsmps510, "vdd-s10"), - RPMH_VREG("smps11", "smp%s11", &pmic5_hfsmps510, "vdd-s11"), - RPMH_VREG("smps12", "smp%s12", &pmic5_hfsmps510, "vdd-s12"), - RPMH_VREG("ldo1", "ldo%s1", &pmic5_nldo, "vdd-l1-l4"), - RPMH_VREG("ldo2", "ldo%s2", &pmic5_pldo, "vdd-l2-l7"), - RPMH_VREG("ldo3", "ldo%s3", &pmic5_nldo, "vdd-l3-l5"), - RPMH_VREG("ldo4", "ldo%s4", &pmic5_nldo, "vdd-l1-l4"), - RPMH_VREG("ldo5", "ldo%s5", &pmic5_nldo, "vdd-l3-l5"), - RPMH_VREG("ldo6", "ldo%s6", &pmic5_nldo, "vdd-l6-l9-l10"), - RPMH_VREG("ldo7", "ldo%s7", &pmic5_pldo, "vdd-l2-l7"), - RPMH_VREG("ldo8", "ldo%s8", &pmic5_nldo, "vdd-l8"), - RPMH_VREG("ldo9", "ldo%s9", &pmic5_nldo, "vdd-l6-l9-l10"), - RPMH_VREG("ldo10", "ldo%s10", &pmic5_nldo, "vdd-l6-l9-l10"), + RPMH_VREG("smps1", SMPS, 1, &pmic5_ftsmps510, "vdd-s1"), + RPMH_VREG("smps2", SMPS, 2, &pmic5_ftsmps510, "vdd-s2"), + RPMH_VREG("smps3", SMPS, 3, &pmic5_ftsmps510, "vdd-s3"), + RPMH_VREG("smps4", SMPS, 4, &pmic5_ftsmps510, "vdd-s4"), + RPMH_VREG("smps5", SMPS, 5, &pmic5_ftsmps510, "vdd-s5"), + RPMH_VREG("smps6", SMPS, 6, &pmic5_ftsmps510, "vdd-s6"), + RPMH_VREG("smps7", SMPS, 7, &pmic5_ftsmps510, "vdd-s7"), + RPMH_VREG("smps8", SMPS, 8, &pmic5_ftsmps510, "vdd-s8"), + RPMH_VREG("smps9", SMPS, 9, &pmic5_ftsmps510, "vdd-s9"), + RPMH_VREG("smps10", SMPS, 10, &pmic5_hfsmps510, "vdd-s10"), + RPMH_VREG("smps11", SMPS, 11, &pmic5_hfsmps510, "vdd-s11"), + RPMH_VREG("smps12", SMPS, 12, &pmic5_hfsmps510, "vdd-s12"), + RPMH_VREG("ldo1", LDO, 1, &pmic5_nldo, "vdd-l1-l4"), + RPMH_VREG("ldo2", LDO, 2, &pmic5_pldo, "vdd-l2-l7"), + RPMH_VREG("ldo3", LDO, 3, &pmic5_nldo, "vdd-l3-l5"), + RPMH_VREG("ldo4", LDO, 4, &pmic5_nldo, "vdd-l1-l4"), + RPMH_VREG("ldo5", LDO, 5, &pmic5_nldo, "vdd-l3-l5"), + RPMH_VREG("ldo6", LDO, 6, &pmic5_nldo, "vdd-l6-l9-l10"), + RPMH_VREG("ldo7", LDO, 7, &pmic5_pldo, "vdd-l2-l7"), + RPMH_VREG("ldo8", LDO, 8, &pmic5_nldo, "vdd-l8"), + RPMH_VREG("ldo9", LDO, 9, &pmic5_nldo, "vdd-l6-l9-l10"), + RPMH_VREG("ldo10", LDO, 10, &pmic5_nldo, "vdd-l6-l9-l10"), {} }; static const struct rpmh_vreg_init_data pm8350c_vreg_data[] = { - RPMH_VREG("smps1", "smp%s1", &pmic5_hfsmps515, "vdd-s1"), - RPMH_VREG("smps2", "smp%s2", &pmic5_ftsmps510, "vdd-s2"), - RPMH_VREG("smps3", "smp%s3", &pmic5_ftsmps510, "vdd-s3"), - RPMH_VREG("smps4", "smp%s4", &pmic5_ftsmps510, "vdd-s4"), - RPMH_VREG("smps5", "smp%s5", &pmic5_ftsmps510, "vdd-s5"), - RPMH_VREG("smps6", "smp%s6", &pmic5_ftsmps510, "vdd-s6"), - RPMH_VREG("smps7", "smp%s7", &pmic5_ftsmps510, "vdd-s7"), - RPMH_VREG("smps8", "smp%s8", &pmic5_ftsmps510, "vdd-s8"), - RPMH_VREG("smps9", "smp%s9", &pmic5_ftsmps510, "vdd-s9"), - RPMH_VREG("smps10", "smp%s10", &pmic5_ftsmps510, "vdd-s10"), - RPMH_VREG("ldo1", "ldo%s1", &pmic5_pldo_lv, "vdd-l1-l12"), - RPMH_VREG("ldo2", "ldo%s2", &pmic5_pldo_lv, "vdd-l2-l8"), - RPMH_VREG("ldo3", "ldo%s3", &pmic5_pldo, "vdd-l3-l4-l5-l7-l13"), - RPMH_VREG("ldo4", "ldo%s4", &pmic5_pldo, "vdd-l3-l4-l5-l7-l13"), - RPMH_VREG("ldo5", "ldo%s5", &pmic5_pldo, "vdd-l3-l4-l5-l7-l13"), - RPMH_VREG("ldo6", "ldo%s6", &pmic5_pldo, "vdd-l6-l9-l11"), - RPMH_VREG("ldo7", "ldo%s7", &pmic5_pldo, "vdd-l3-l4-l5-l7-l13"), - RPMH_VREG("ldo8", "ldo%s8", &pmic5_pldo_lv, "vdd-l2-l8"), - RPMH_VREG("ldo9", "ldo%s9", &pmic5_pldo, "vdd-l6-l9-l11"), - RPMH_VREG("ldo10", "ldo%s10", &pmic5_nldo, "vdd-l10"), - RPMH_VREG("ldo11", "ldo%s11", &pmic5_pldo, "vdd-l6-l9-l11"), - RPMH_VREG("ldo12", "ldo%s12", &pmic5_pldo_lv, "vdd-l1-l12"), - RPMH_VREG("ldo13", "ldo%s13", &pmic5_pldo, "vdd-l3-l4-l5-l7-l13"), - RPMH_VREG("bob", "bob%s1", &pmic5_bob, "vdd-bob"), + RPMH_VREG("smps1", SMPS, 1, &pmic5_hfsmps515, "vdd-s1"), + RPMH_VREG("smps2", SMPS, 2, &pmic5_ftsmps510, "vdd-s2"), + RPMH_VREG("smps3", SMPS, 3, &pmic5_ftsmps510, "vdd-s3"), + RPMH_VREG("smps4", SMPS, 4, &pmic5_ftsmps510, "vdd-s4"), + RPMH_VREG("smps5", SMPS, 5, &pmic5_ftsmps510, "vdd-s5"), + RPMH_VREG("smps6", SMPS, 6, &pmic5_ftsmps510, "vdd-s6"), + RPMH_VREG("smps7", SMPS, 7, &pmic5_ftsmps510, "vdd-s7"), + RPMH_VREG("smps8", SMPS, 8, &pmic5_ftsmps510, "vdd-s8"), + RPMH_VREG("smps9", SMPS, 9, &pmic5_ftsmps510, "vdd-s9"), + RPMH_VREG("smps10", SMPS, 10, &pmic5_ftsmps510, "vdd-s10"), + RPMH_VREG("ldo1", LDO, 1, &pmic5_pldo_lv, "vdd-l1-l12"), + RPMH_VREG("ldo2", LDO, 2, &pmic5_pldo_lv, "vdd-l2-l8"), + RPMH_VREG("ldo3", LDO, 3, &pmic5_pldo, "vdd-l3-l4-l5-l7-l13"), + RPMH_VREG("ldo4", LDO, 4, &pmic5_pldo, "vdd-l3-l4-l5-l7-l13"), + RPMH_VREG("ldo5", LDO, 5, &pmic5_pldo, "vdd-l3-l4-l5-l7-l13"), + RPMH_VREG("ldo6", LDO, 6, &pmic5_pldo, "vdd-l6-l9-l11"), + RPMH_VREG("ldo7", LDO, 7, &pmic5_pldo, "vdd-l3-l4-l5-l7-l13"), + RPMH_VREG("ldo8", LDO, 8, &pmic5_pldo_lv, "vdd-l2-l8"), + RPMH_VREG("ldo9", LDO, 9, &pmic5_pldo, "vdd-l6-l9-l11"), + RPMH_VREG("ldo10", LDO, 10, &pmic5_nldo, "vdd-l10"), + RPMH_VREG("ldo11", LDO, 11, &pmic5_pldo, "vdd-l6-l9-l11"), + RPMH_VREG("ldo12", LDO, 12, &pmic5_pldo_lv, "vdd-l1-l12"), + RPMH_VREG("ldo13", LDO, 13, &pmic5_pldo, "vdd-l3-l4-l5-l7-l13"), + RPMH_VREG("bob", BOB, 1, &pmic5_bob, "vdd-bob"), {} }; static const struct rpmh_vreg_init_data pm8450_vreg_data[] = { - RPMH_VREG("smps1", "smp%s1", &pmic5_ftsmps520, "vdd-s1"), - RPMH_VREG("smps2", "smp%s2", &pmic5_ftsmps520, "vdd-s2"), - RPMH_VREG("smps3", "smp%s3", &pmic5_ftsmps520, "vdd-s3"), - RPMH_VREG("smps4", "smp%s4", &pmic5_ftsmps520, "vdd-s4"), - RPMH_VREG("smps5", "smp%s5", &pmic5_ftsmps520, "vdd-s5"), - RPMH_VREG("smps6", "smp%s6", &pmic5_ftsmps520, "vdd-s6"), - RPMH_VREG("ldo1", "ldo%s1", &pmic5_nldo, "vdd-l1"), - RPMH_VREG("ldo2", "ldo%s2", &pmic5_nldo, "vdd-l2"), - RPMH_VREG("ldo3", "ldo%s3", &pmic5_nldo, "vdd-l3"), - RPMH_VREG("ldo4", "ldo%s4", &pmic5_pldo_lv, "vdd-l4"), + RPMH_VREG("smps1", SMPS, 1, &pmic5_ftsmps520, "vdd-s1"), + RPMH_VREG("smps2", SMPS, 2, &pmic5_ftsmps520, "vdd-s2"), + RPMH_VREG("smps3", SMPS, 3, &pmic5_ftsmps520, "vdd-s3"), + RPMH_VREG("smps4", SMPS, 4, &pmic5_ftsmps520, "vdd-s4"), + RPMH_VREG("smps5", SMPS, 5, &pmic5_ftsmps520, "vdd-s5"), + RPMH_VREG("smps6", SMPS, 6, &pmic5_ftsmps520, "vdd-s6"), + RPMH_VREG("ldo1", LDO, 1, &pmic5_nldo, "vdd-l1"), + RPMH_VREG("ldo2", LDO, 2, &pmic5_nldo, "vdd-l2"), + RPMH_VREG("ldo3", LDO, 3, &pmic5_nldo, "vdd-l3"), + RPMH_VREG("ldo4", LDO, 4, &pmic5_pldo_lv, "vdd-l4"), {} }; static const struct rpmh_vreg_init_data pm8550_vreg_data[] = { - RPMH_VREG("ldo1", "ldo%s1", &pmic5_nldo515, "vdd-l1-l4-l10"), - RPMH_VREG("ldo2", "ldo%s2", &pmic5_pldo, "vdd-l2-l13-l14"), - RPMH_VREG("ldo3", "ldo%s3", &pmic5_nldo515, "vdd-l3"), - RPMH_VREG("ldo4", "ldo%s4", &pmic5_nldo515, "vdd-l1-l4-l10"), - RPMH_VREG("ldo5", "ldo%s5", &pmic5_pldo, "vdd-l5-l16"), - RPMH_VREG("ldo6", "ldo%s6", &pmic5_pldo, "vdd-l6-l7"), - RPMH_VREG("ldo7", "ldo%s7", &pmic5_pldo, "vdd-l6-l7"), - RPMH_VREG("ldo8", "ldo%s8", &pmic5_pldo, "vdd-l8-l9"), - RPMH_VREG("ldo9", "ldo%s9", &pmic5_pldo, "vdd-l8-l9"), - RPMH_VREG("ldo10", "ldo%s10", &pmic5_nldo515, "vdd-l1-l4-l10"), - RPMH_VREG("ldo11", "ldo%s11", &pmic5_nldo515, "vdd-l11"), - RPMH_VREG("ldo12", "ldo%s12", &pmic5_nldo515, "vdd-l12"), - RPMH_VREG("ldo13", "ldo%s13", &pmic5_pldo, "vdd-l2-l13-l14"), - RPMH_VREG("ldo14", "ldo%s14", &pmic5_pldo, "vdd-l2-l13-l14"), - RPMH_VREG("ldo15", "ldo%s15", &pmic5_nldo515, "vdd-l15"), - RPMH_VREG("ldo16", "ldo%s16", &pmic5_pldo, "vdd-l5-l16"), - RPMH_VREG("ldo17", "ldo%s17", &pmic5_pldo, "vdd-l17"), - RPMH_VREG("bob1", "bob%s1", &pmic5_bob, "vdd-bob1"), - RPMH_VREG("bob2", "bob%s2", &pmic5_bob, "vdd-bob2"), + RPMH_VREG("ldo1", LDO, 1, &pmic5_nldo515, "vdd-l1-l4-l10"), + RPMH_VREG("ldo2", LDO, 2, &pmic5_pldo, "vdd-l2-l13-l14"), + RPMH_VREG("ldo3", LDO, 3, &pmic5_nldo515, "vdd-l3"), + RPMH_VREG("ldo4", LDO, 4, &pmic5_nldo515, "vdd-l1-l4-l10"), + RPMH_VREG("ldo5", LDO, 5, &pmic5_pldo, "vdd-l5-l16"), + RPMH_VREG("ldo6", LDO, 6, &pmic5_pldo, "vdd-l6-l7"), + RPMH_VREG("ldo7", LDO, 7, &pmic5_pldo, "vdd-l6-l7"), + RPMH_VREG("ldo8", LDO, 8, &pmic5_pldo, "vdd-l8-l9"), + RPMH_VREG("ldo9", LDO, 9, &pmic5_pldo, "vdd-l8-l9"), + RPMH_VREG("ldo10", LDO, 10, &pmic5_nldo515, "vdd-l1-l4-l10"), + RPMH_VREG("ldo11", LDO, 11, &pmic5_nldo515, "vdd-l11"), + RPMH_VREG("ldo12", LDO, 12, &pmic5_nldo515, "vdd-l12"), + RPMH_VREG("ldo13", LDO, 13, &pmic5_pldo, "vdd-l2-l13-l14"), + RPMH_VREG("ldo14", LDO, 14, &pmic5_pldo, "vdd-l2-l13-l14"), + RPMH_VREG("ldo15", LDO, 15, &pmic5_nldo515, "vdd-l15"), + RPMH_VREG("ldo16", LDO, 16, &pmic5_pldo, "vdd-l5-l16"), + RPMH_VREG("ldo17", LDO, 17, &pmic5_pldo, "vdd-l17"), + RPMH_VREG("bob1", BOB, 1, &pmic5_bob, "vdd-bob1"), + RPMH_VREG("bob2", BOB, 2, &pmic5_bob, "vdd-bob2"), {} }; static const struct rpmh_vreg_init_data pm8550vs_vreg_data[] = { - RPMH_VREG("smps1", "smp%s1", &pmic5_ftsmps525, "vdd-s1"), - RPMH_VREG("smps2", "smp%s2", &pmic5_ftsmps525, "vdd-s2"), - RPMH_VREG("smps3", "smp%s3", &pmic5_ftsmps525, "vdd-s3"), - RPMH_VREG("smps4", "smp%s4", &pmic5_ftsmps525, "vdd-s4"), - RPMH_VREG("smps5", "smp%s5", &pmic5_ftsmps525, "vdd-s5"), - RPMH_VREG("smps6", "smp%s6", &pmic5_ftsmps525, "vdd-s6"), - RPMH_VREG("ldo1", "ldo%s1", &pmic5_nldo515, "vdd-l1"), - RPMH_VREG("ldo2", "ldo%s2", &pmic5_nldo515, "vdd-l2"), - RPMH_VREG("ldo3", "ldo%s3", &pmic5_nldo515, "vdd-l3"), + RPMH_VREG("smps1", SMPS, 1, &pmic5_ftsmps525, "vdd-s1"), + RPMH_VREG("smps2", SMPS, 2, &pmic5_ftsmps525, "vdd-s2"), + RPMH_VREG("smps3", SMPS, 3, &pmic5_ftsmps525, "vdd-s3"), + RPMH_VREG("smps4", SMPS, 4, &pmic5_ftsmps525, "vdd-s4"), + RPMH_VREG("smps5", SMPS, 5, &pmic5_ftsmps525, "vdd-s5"), + RPMH_VREG("smps6", SMPS, 6, &pmic5_ftsmps525, "vdd-s6"), + RPMH_VREG("ldo1", LDO, 1, &pmic5_nldo515, "vdd-l1"), + RPMH_VREG("ldo2", LDO, 2, &pmic5_nldo515, "vdd-l2"), + RPMH_VREG("ldo3", LDO, 3, &pmic5_nldo515, "vdd-l3"), {} }; static const struct rpmh_vreg_init_data pm8550ve_vreg_data[] = { - RPMH_VREG("smps1", "smp%s1", &pmic5_ftsmps525, "vdd-s1"), - RPMH_VREG("smps2", "smp%s2", &pmic5_ftsmps525, "vdd-s2"), - RPMH_VREG("smps3", "smp%s3", &pmic5_ftsmps525, "vdd-s3"), - RPMH_VREG("smps4", "smp%s4", &pmic5_ftsmps525, "vdd-s4"), - RPMH_VREG("smps5", "smp%s5", &pmic5_ftsmps525, "vdd-s5"), - RPMH_VREG("smps6", "smp%s6", &pmic5_ftsmps525, "vdd-s6"), - RPMH_VREG("smps7", "smp%s7", &pmic5_ftsmps525, "vdd-s7"), - RPMH_VREG("smps8", "smp%s8", &pmic5_ftsmps525, "vdd-s8"), - RPMH_VREG("ldo1", "ldo%s1", &pmic5_nldo515, "vdd-l1"), - RPMH_VREG("ldo2", "ldo%s2", &pmic5_nldo515, "vdd-l2"), - RPMH_VREG("ldo3", "ldo%s3", &pmic5_nldo515, "vdd-l3"), + RPMH_VREG("smps1", SMPS, 1, &pmic5_ftsmps525, "vdd-s1"), + RPMH_VREG("smps2", SMPS, 2, &pmic5_ftsmps525, "vdd-s2"), + RPMH_VREG("smps3", SMPS, 3, &pmic5_ftsmps525, "vdd-s3"), + RPMH_VREG("smps4", SMPS, 4, &pmic5_ftsmps525, "vdd-s4"), + RPMH_VREG("smps5", SMPS, 5, &pmic5_ftsmps525, "vdd-s5"), + RPMH_VREG("smps6", SMPS, 6, &pmic5_ftsmps525, "vdd-s6"), + RPMH_VREG("smps7", SMPS, 7, &pmic5_ftsmps525, "vdd-s7"), + RPMH_VREG("smps8", SMPS, 8, &pmic5_ftsmps525, "vdd-s8"), + RPMH_VREG("ldo1", LDO, 1, &pmic5_nldo515, "vdd-l1"), + RPMH_VREG("ldo2", LDO, 2, &pmic5_nldo515, "vdd-l2"), + RPMH_VREG("ldo3", LDO, 3, &pmic5_nldo515, "vdd-l3"), {} }; static const struct rpmh_vreg_init_data pmc8380_vreg_data[] = { - RPMH_VREG("smps1", "smp%s1", &pmic5_ftsmps525, "vdd-s1"), - RPMH_VREG("smps2", "smp%s2", &pmic5_ftsmps525, "vdd-s2"), - RPMH_VREG("smps3", "smp%s3", &pmic5_ftsmps525, "vdd-s3"), - RPMH_VREG("smps4", "smp%s4", &pmic5_ftsmps525, "vdd-s4"), - RPMH_VREG("smps5", "smp%s5", &pmic5_ftsmps525, "vdd-s5"), - RPMH_VREG("smps6", "smp%s6", &pmic5_ftsmps525, "vdd-s6"), - RPMH_VREG("smps7", "smp%s7", &pmic5_ftsmps525, "vdd-s7"), - RPMH_VREG("smps8", "smp%s8", &pmic5_ftsmps525, "vdd-s8"), - RPMH_VREG("ldo1", "ldo%s1", &pmic5_nldo515, "vdd-l1"), - RPMH_VREG("ldo2", "ldo%s2", &pmic5_nldo515, "vdd-l2"), - RPMH_VREG("ldo3", "ldo%s3", &pmic5_nldo515, "vdd-l3"), + RPMH_VREG("smps1", SMPS, 1, &pmic5_ftsmps525, "vdd-s1"), + RPMH_VREG("smps2", SMPS, 2, &pmic5_ftsmps525, "vdd-s2"), + RPMH_VREG("smps3", SMPS, 3, &pmic5_ftsmps525, "vdd-s3"), + RPMH_VREG("smps4", SMPS, 4, &pmic5_ftsmps525, "vdd-s4"), + RPMH_VREG("smps5", SMPS, 5, &pmic5_ftsmps525, "vdd-s5"), + RPMH_VREG("smps6", SMPS, 6, &pmic5_ftsmps525, "vdd-s6"), + RPMH_VREG("smps7", SMPS, 7, &pmic5_ftsmps525, "vdd-s7"), + RPMH_VREG("smps8", SMPS, 8, &pmic5_ftsmps525, "vdd-s8"), + RPMH_VREG("ldo1", LDO, 1, &pmic5_nldo515, "vdd-l1"), + RPMH_VREG("ldo2", LDO, 2, &pmic5_nldo515, "vdd-l2"), + RPMH_VREG("ldo3", LDO, 3, &pmic5_nldo515, "vdd-l3"), {} }; static const struct rpmh_vreg_init_data pm8009_vreg_data[] = { - RPMH_VREG("smps1", "smp%s1", &pmic5_hfsmps510, "vdd-s1"), - RPMH_VREG("smps2", "smp%s2", &pmic5_hfsmps515, "vdd-s2"), - RPMH_VREG("ldo1", "ldo%s1", &pmic5_nldo, "vdd-l1"), - RPMH_VREG("ldo2", "ldo%s2", &pmic5_nldo, "vdd-l2"), - RPMH_VREG("ldo3", "ldo%s3", &pmic5_nldo, "vdd-l3"), - RPMH_VREG("ldo4", "ldo%s4", &pmic5_nldo, "vdd-l4"), - RPMH_VREG("ldo5", "ldo%s5", &pmic5_pldo, "vdd-l5-l6"), - RPMH_VREG("ldo6", "ldo%s6", &pmic5_pldo, "vdd-l5-l6"), - RPMH_VREG("ldo7", "ldo%s7", &pmic5_pldo_lv, "vdd-l7"), + RPMH_VREG("smps1", SMPS, 1, &pmic5_hfsmps510, "vdd-s1"), + RPMH_VREG("smps2", SMPS, 2, &pmic5_hfsmps515, "vdd-s2"), + RPMH_VREG("ldo1", LDO, 1, &pmic5_nldo, "vdd-l1"), + RPMH_VREG("ldo2", LDO, 2, &pmic5_nldo, "vdd-l2"), + RPMH_VREG("ldo3", LDO, 3, &pmic5_nldo, "vdd-l3"), + RPMH_VREG("ldo4", LDO, 4, &pmic5_nldo, "vdd-l4"), + RPMH_VREG("ldo5", LDO, 5, &pmic5_pldo, "vdd-l5-l6"), + RPMH_VREG("ldo6", LDO, 6, &pmic5_pldo, "vdd-l5-l6"), + RPMH_VREG("ldo7", LDO, 7, &pmic5_pldo_lv, "vdd-l7"), {} }; static const struct rpmh_vreg_init_data pm8009_1_vreg_data[] = { - RPMH_VREG("smps1", "smp%s1", &pmic5_hfsmps510, "vdd-s1"), - RPMH_VREG("smps2", "smp%s2", &pmic5_hfsmps515_1, "vdd-s2"), - RPMH_VREG("ldo1", "ldo%s1", &pmic5_nldo, "vdd-l1"), - RPMH_VREG("ldo2", "ldo%s2", &pmic5_nldo, "vdd-l2"), - RPMH_VREG("ldo3", "ldo%s3", &pmic5_nldo, "vdd-l3"), - RPMH_VREG("ldo4", "ldo%s4", &pmic5_nldo, "vdd-l4"), - RPMH_VREG("ldo5", "ldo%s5", &pmic5_pldo, "vdd-l5-l6"), - RPMH_VREG("ldo6", "ldo%s6", &pmic5_pldo, "vdd-l5-l6"), - RPMH_VREG("ldo7", "ldo%s7", &pmic5_pldo_lv, "vdd-l7"), + RPMH_VREG("smps1", SMPS, 1, &pmic5_hfsmps510, "vdd-s1"), + RPMH_VREG("smps2", SMPS, 2, &pmic5_hfsmps515_1, "vdd-s2"), + RPMH_VREG("ldo1", LDO, 1, &pmic5_nldo, "vdd-l1"), + RPMH_VREG("ldo2", LDO, 2, &pmic5_nldo, "vdd-l2"), + RPMH_VREG("ldo3", LDO, 3, &pmic5_nldo, "vdd-l3"), + RPMH_VREG("ldo4", LDO, 4, &pmic5_nldo, "vdd-l4"), + RPMH_VREG("ldo5", LDO, 5, &pmic5_pldo, "vdd-l5-l6"), + RPMH_VREG("ldo6", LDO, 6, &pmic5_pldo, "vdd-l5-l6"), + RPMH_VREG("ldo7", LDO, 7, &pmic5_pldo_lv, "vdd-l7"), {} }; static const struct rpmh_vreg_init_data pm8010_vreg_data[] = { - RPMH_VREG("ldo1", "ldo%s1", &pmic5_nldo502, "vdd-l1-l2"), - RPMH_VREG("ldo2", "ldo%s2", &pmic5_nldo502, "vdd-l1-l2"), - RPMH_VREG("ldo3", "ldo%s3", &pmic5_pldo502ln, "vdd-l3-l4"), - RPMH_VREG("ldo4", "ldo%s4", &pmic5_pldo502ln, "vdd-l3-l4"), - RPMH_VREG("ldo5", "ldo%s5", &pmic5_pldo502, "vdd-l5"), - RPMH_VREG("ldo6", "ldo%s6", &pmic5_pldo502ln, "vdd-l6"), - RPMH_VREG("ldo7", "ldo%s7", &pmic5_pldo502, "vdd-l7"), + RPMH_VREG("ldo1", LDO, 1, &pmic5_nldo502, "vdd-l1-l2"), + RPMH_VREG("ldo2", LDO, 2, &pmic5_nldo502, "vdd-l1-l2"), + RPMH_VREG("ldo3", LDO, 3, &pmic5_pldo502ln, "vdd-l3-l4"), + RPMH_VREG("ldo4", LDO, 4, &pmic5_pldo502ln, "vdd-l3-l4"), + RPMH_VREG("ldo5", LDO, 5, &pmic5_pldo502, "vdd-l5"), + RPMH_VREG("ldo6", LDO, 6, &pmic5_pldo502ln, "vdd-l6"), + RPMH_VREG("ldo7", LDO, 7, &pmic5_pldo502, "vdd-l7"), }; static const struct rpmh_vreg_init_data pm6150_vreg_data[] = { - RPMH_VREG("smps1", "smp%s1", &pmic5_ftsmps510, "vdd-s1"), - RPMH_VREG("smps2", "smp%s2", &pmic5_ftsmps510, "vdd-s2"), - RPMH_VREG("smps3", "smp%s3", &pmic5_ftsmps510, "vdd-s3"), - RPMH_VREG("smps4", "smp%s4", &pmic5_hfsmps510, "vdd-s4"), - RPMH_VREG("smps5", "smp%s5", &pmic5_hfsmps510, "vdd-s5"), - RPMH_VREG("ldo1", "ldo%s1", &pmic5_nldo, "vdd-l1"), - RPMH_VREG("ldo2", "ldo%s2", &pmic5_nldo, "vdd-l2-l3"), - RPMH_VREG("ldo3", "ldo%s3", &pmic5_nldo, "vdd-l2-l3"), - RPMH_VREG("ldo4", "ldo%s4", &pmic5_nldo, "vdd-l4-l7-l8"), - RPMH_VREG("ldo5", "ldo%s5", &pmic5_pldo, "vdd-l5-l16-l17-l18-l19"), - RPMH_VREG("ldo6", "ldo%s6", &pmic5_nldo, "vdd-l6"), - RPMH_VREG("ldo7", "ldo%s7", &pmic5_nldo, "vdd-l4-l7-l8"), - RPMH_VREG("ldo8", "ldo%s8", &pmic5_nldo, "vdd-l4-l7-l8"), - RPMH_VREG("ldo9", "ldo%s9", &pmic5_nldo, "vdd-l9"), - RPMH_VREG("ldo10", "ldo%s10", &pmic5_pldo_lv, "vdd-l10-l14-l15"), - RPMH_VREG("ldo11", "ldo%s11", &pmic5_pldo_lv, "vdd-l11-l12-l13"), - RPMH_VREG("ldo12", "ldo%s12", &pmic5_pldo_lv, "vdd-l11-l12-l13"), - RPMH_VREG("ldo13", "ldo%s13", &pmic5_pldo_lv, "vdd-l11-l12-l13"), - RPMH_VREG("ldo14", "ldo%s14", &pmic5_pldo_lv, "vdd-l10-l14-l15"), - RPMH_VREG("ldo15", "ldo%s15", &pmic5_pldo_lv, "vdd-l10-l14-l15"), - RPMH_VREG("ldo16", "ldo%s16", &pmic5_pldo, "vdd-l5-l16-l17-l18-l19"), - RPMH_VREG("ldo17", "ldo%s17", &pmic5_pldo, "vdd-l5-l16-l17-l18-l19"), - RPMH_VREG("ldo18", "ldo%s18", &pmic5_pldo, "vdd-l5-l16-l17-l18-l19"), - RPMH_VREG("ldo19", "ldo%s19", &pmic5_pldo, "vdd-l5-l16-l17-l18-l19"), + RPMH_VREG("smps1", SMPS, 1, &pmic5_ftsmps510, "vdd-s1"), + RPMH_VREG("smps2", SMPS, 2, &pmic5_ftsmps510, "vdd-s2"), + RPMH_VREG("smps3", SMPS, 3, &pmic5_ftsmps510, "vdd-s3"), + RPMH_VREG("smps4", SMPS, 4, &pmic5_hfsmps510, "vdd-s4"), + RPMH_VREG("smps5", SMPS, 5, &pmic5_hfsmps510, "vdd-s5"), + RPMH_VREG("ldo1", LDO, 1, &pmic5_nldo, "vdd-l1"), + RPMH_VREG("ldo2", LDO, 2, &pmic5_nldo, "vdd-l2-l3"), + RPMH_VREG("ldo3", LDO, 3, &pmic5_nldo, "vdd-l2-l3"), + RPMH_VREG("ldo4", LDO, 4, &pmic5_nldo, "vdd-l4-l7-l8"), + RPMH_VREG("ldo5", LDO, 5, &pmic5_pldo, "vdd-l5-l16-l17-l18-l19"), + RPMH_VREG("ldo6", LDO, 6, &pmic5_nldo, "vdd-l6"), + RPMH_VREG("ldo7", LDO, 7, &pmic5_nldo, "vdd-l4-l7-l8"), + RPMH_VREG("ldo8", LDO, 8, &pmic5_nldo, "vdd-l4-l7-l8"), + RPMH_VREG("ldo9", LDO, 9, &pmic5_nldo, "vdd-l9"), + RPMH_VREG("ldo10", LDO, 10, &pmic5_pldo_lv, "vdd-l10-l14-l15"), + RPMH_VREG("ldo11", LDO, 11, &pmic5_pldo_lv, "vdd-l11-l12-l13"), + RPMH_VREG("ldo12", LDO, 12, &pmic5_pldo_lv, "vdd-l11-l12-l13"), + RPMH_VREG("ldo13", LDO, 13, &pmic5_pldo_lv, "vdd-l11-l12-l13"), + RPMH_VREG("ldo14", LDO, 14, &pmic5_pldo_lv, "vdd-l10-l14-l15"), + RPMH_VREG("ldo15", LDO, 15, &pmic5_pldo_lv, "vdd-l10-l14-l15"), + RPMH_VREG("ldo16", LDO, 16, &pmic5_pldo, "vdd-l5-l16-l17-l18-l19"), + RPMH_VREG("ldo17", LDO, 17, &pmic5_pldo, "vdd-l5-l16-l17-l18-l19"), + RPMH_VREG("ldo18", LDO, 18, &pmic5_pldo, "vdd-l5-l16-l17-l18-l19"), + RPMH_VREG("ldo19", LDO, 19, &pmic5_pldo, "vdd-l5-l16-l17-l18-l19"), {} }; static const struct rpmh_vreg_init_data pm6150l_vreg_data[] = { - RPMH_VREG("smps1", "smp%s1", &pmic5_ftsmps510, "vdd-s1"), - RPMH_VREG("smps2", "smp%s2", &pmic5_ftsmps510, "vdd-s2"), - RPMH_VREG("smps3", "smp%s3", &pmic5_ftsmps510, "vdd-s3"), - RPMH_VREG("smps4", "smp%s4", &pmic5_ftsmps510, "vdd-s4"), - RPMH_VREG("smps5", "smp%s5", &pmic5_ftsmps510, "vdd-s5"), - RPMH_VREG("smps6", "smp%s6", &pmic5_ftsmps510, "vdd-s6"), - RPMH_VREG("smps7", "smp%s7", &pmic5_ftsmps510, "vdd-s7"), - RPMH_VREG("smps8", "smp%s8", &pmic5_hfsmps510, "vdd-s8"), - RPMH_VREG("ldo1", "ldo%s1", &pmic5_pldo_lv, "vdd-l1-l8"), - RPMH_VREG("ldo2", "ldo%s2", &pmic5_nldo, "vdd-l2-l3"), - RPMH_VREG("ldo3", "ldo%s3", &pmic5_nldo, "vdd-l2-l3"), - RPMH_VREG("ldo4", "ldo%s4", &pmic5_pldo, "vdd-l4-l5-l6"), - RPMH_VREG("ldo5", "ldo%s5", &pmic5_pldo, "vdd-l4-l5-l6"), - RPMH_VREG("ldo6", "ldo%s6", &pmic5_pldo, "vdd-l4-l5-l6"), - RPMH_VREG("ldo7", "ldo%s7", &pmic5_pldo, "vdd-l7-l11"), - RPMH_VREG("ldo8", "ldo%s8", &pmic5_pldo, "vdd-l1-l8"), - RPMH_VREG("ldo9", "ldo%s9", &pmic5_pldo, "vdd-l9-l10"), - RPMH_VREG("ldo10", "ldo%s10", &pmic5_pldo, "vdd-l9-l10"), - RPMH_VREG("ldo11", "ldo%s11", &pmic5_pldo, "vdd-l7-l11"), - RPMH_VREG("bob", "bob%s1", &pmic5_bob, "vdd-bob"), + RPMH_VREG("smps1", SMPS, 1, &pmic5_ftsmps510, "vdd-s1"), + RPMH_VREG("smps2", SMPS, 2, &pmic5_ftsmps510, "vdd-s2"), + RPMH_VREG("smps3", SMPS, 3, &pmic5_ftsmps510, "vdd-s3"), + RPMH_VREG("smps4", SMPS, 4, &pmic5_ftsmps510, "vdd-s4"), + RPMH_VREG("smps5", SMPS, 5, &pmic5_ftsmps510, "vdd-s5"), + RPMH_VREG("smps6", SMPS, 6, &pmic5_ftsmps510, "vdd-s6"), + RPMH_VREG("smps7", SMPS, 7, &pmic5_ftsmps510, "vdd-s7"), + RPMH_VREG("smps8", SMPS, 8, &pmic5_hfsmps510, "vdd-s8"), + RPMH_VREG("ldo1", LDO, 1, &pmic5_pldo_lv, "vdd-l1-l8"), + RPMH_VREG("ldo2", LDO, 2, &pmic5_nldo, "vdd-l2-l3"), + RPMH_VREG("ldo3", LDO, 3, &pmic5_nldo, "vdd-l2-l3"), + RPMH_VREG("ldo4", LDO, 4, &pmic5_pldo, "vdd-l4-l5-l6"), + RPMH_VREG("ldo5", LDO, 5, &pmic5_pldo, "vdd-l4-l5-l6"), + RPMH_VREG("ldo6", LDO, 6, &pmic5_pldo, "vdd-l4-l5-l6"), + RPMH_VREG("ldo7", LDO, 7, &pmic5_pldo, "vdd-l7-l11"), + RPMH_VREG("ldo8", LDO, 8, &pmic5_pldo, "vdd-l1-l8"), + RPMH_VREG("ldo9", LDO, 9, &pmic5_pldo, "vdd-l9-l10"), + RPMH_VREG("ldo10", LDO, 10, &pmic5_pldo, "vdd-l9-l10"), + RPMH_VREG("ldo11", LDO, 11, &pmic5_pldo, "vdd-l7-l11"), + RPMH_VREG("bob", BOB, 1, &pmic5_bob, "vdd-bob"), {} }; static const struct rpmh_vreg_init_data pm6350_vreg_data[] = { - RPMH_VREG("smps1", "smp%s1", &pmic5_ftsmps510, NULL), - RPMH_VREG("smps2", "smp%s2", &pmic5_hfsmps510, NULL), + RPMH_VREG("smps1", SMPS, 1, &pmic5_ftsmps510, NULL), + RPMH_VREG("smps2", SMPS, 2, &pmic5_hfsmps510, NULL), /* smps3 - smps5 not configured */ - RPMH_VREG("ldo1", "ldo%s1", &pmic5_nldo, NULL), - RPMH_VREG("ldo2", "ldo%s2", &pmic5_pldo, NULL), - RPMH_VREG("ldo3", "ldo%s3", &pmic5_pldo, NULL), - RPMH_VREG("ldo4", "ldo%s4", &pmic5_nldo, NULL), - RPMH_VREG("ldo5", "ldo%s5", &pmic5_pldo, NULL), - RPMH_VREG("ldo6", "ldo%s6", &pmic5_pldo, NULL), - RPMH_VREG("ldo7", "ldo%s7", &pmic5_pldo, NULL), - RPMH_VREG("ldo8", "ldo%s8", &pmic5_pldo, NULL), - RPMH_VREG("ldo9", "ldo%s9", &pmic5_pldo, NULL), - RPMH_VREG("ldo10", "ldo%s10", &pmic5_pldo, NULL), - RPMH_VREG("ldo11", "ldo%s11", &pmic5_pldo, NULL), - RPMH_VREG("ldo12", "ldo%s12", &pmic5_pldo, NULL), - RPMH_VREG("ldo13", "ldo%s13", &pmic5_nldo, NULL), - RPMH_VREG("ldo14", "ldo%s14", &pmic5_pldo, NULL), - RPMH_VREG("ldo15", "ldo%s15", &pmic5_nldo, NULL), - RPMH_VREG("ldo16", "ldo%s16", &pmic5_nldo, NULL), + RPMH_VREG("ldo1", LDO, 1, &pmic5_nldo, NULL), + RPMH_VREG("ldo2", LDO, 2, &pmic5_pldo, NULL), + RPMH_VREG("ldo3", LDO, 3, &pmic5_pldo, NULL), + RPMH_VREG("ldo4", LDO, 4, &pmic5_nldo, NULL), + RPMH_VREG("ldo5", LDO, 5, &pmic5_pldo, NULL), + RPMH_VREG("ldo6", LDO, 6, &pmic5_pldo, NULL), + RPMH_VREG("ldo7", LDO, 7, &pmic5_pldo, NULL), + RPMH_VREG("ldo8", LDO, 8, &pmic5_pldo, NULL), + RPMH_VREG("ldo9", LDO, 9, &pmic5_pldo, NULL), + RPMH_VREG("ldo10", LDO, 10, &pmic5_pldo, NULL), + RPMH_VREG("ldo11", LDO, 11, &pmic5_pldo, NULL), + RPMH_VREG("ldo12", LDO, 12, &pmic5_pldo, NULL), + RPMH_VREG("ldo13", LDO, 13, &pmic5_nldo, NULL), + RPMH_VREG("ldo14", LDO, 14, &pmic5_pldo, NULL), + RPMH_VREG("ldo15", LDO, 15, &pmic5_nldo, NULL), + RPMH_VREG("ldo16", LDO, 16, &pmic5_nldo, NULL), /* ldo17 not configured */ - RPMH_VREG("ldo18", "ldo%s18", &pmic5_nldo, NULL), - RPMH_VREG("ldo19", "ldo%s19", &pmic5_nldo, NULL), - RPMH_VREG("ldo20", "ldo%s20", &pmic5_nldo, NULL), - RPMH_VREG("ldo21", "ldo%s21", &pmic5_nldo, NULL), - RPMH_VREG("ldo22", "ldo%s22", &pmic5_nldo, NULL), + RPMH_VREG("ldo18", LDO, 18, &pmic5_nldo, NULL), + RPMH_VREG("ldo19", LDO, 19, &pmic5_nldo, NULL), + RPMH_VREG("ldo20", LDO, 20, &pmic5_nldo, NULL), + RPMH_VREG("ldo21", LDO, 21, &pmic5_nldo, NULL), + RPMH_VREG("ldo22", LDO, 22, &pmic5_nldo, NULL), +}; + +static const struct rpmh_vreg_init_data pmcx0102_vreg_data[] = { + RPMH_VREG("smps1", SMPS, 1, &pmic5_ftsmps530, "vdd-s1"), + RPMH_VREG("smps2", SMPS, 2, &pmic5_ftsmps530, "vdd-s2"), + RPMH_VREG("smps3", SMPS, 3, &pmic5_ftsmps530, "vdd-s3"), + RPMH_VREG("smps4", SMPS, 4, &pmic5_ftsmps530, "vdd-s4"), + RPMH_VREG("smps5", SMPS, 5, &pmic5_ftsmps530, "vdd-s5"), + RPMH_VREG("smps6", SMPS, 6, &pmic5_ftsmps530, "vdd-s6"), + RPMH_VREG("smps7", SMPS, 7, &pmic5_ftsmps530, "vdd-s7"), + RPMH_VREG("smps8", SMPS, 8, &pmic5_ftsmps530, "vdd-s8"), + RPMH_VREG("smps9", SMPS, 9, &pmic5_ftsmps530, "vdd-s9"), + RPMH_VREG("smps10", SMPS, 10, &pmic5_ftsmps530, "vdd-s10"), + RPMH_VREG("ldo1", LDO, 1, &pmic5_nldo530, "vdd-l1"), + RPMH_VREG("ldo2", LDO, 2, &pmic5_nldo530, "vdd-l2"), + RPMH_VREG("ldo3", LDO, 3, &pmic5_nldo530, "vdd-l3"), + RPMH_VREG("ldo4", LDO, 4, &pmic5_nldo530, "vdd-l4"), + {} +}; + +static const struct rpmh_vreg_init_data pmh0101_vreg_data[] = { + RPMH_VREG("ldo1", LDO, 1, &pmic5_nldo530, "vdd-l1-l4-l10"), + RPMH_VREG("ldo2", LDO, 2, &pmic5_pldo530_mvp300, "vdd-l2-l13-l14"), + RPMH_VREG("ldo3", LDO, 3, &pmic5_nldo530, "vdd-l3-l11"), + RPMH_VREG("ldo4", LDO, 4, &pmic5_nldo530, "vdd-l1-l4-l10"), + RPMH_VREG("ldo5", LDO, 5, &pmic5_pldo530_mvp150, "vdd-l5-l16"), + RPMH_VREG("ldo6", LDO, 6, &pmic5_pldo530_mvp300, "vdd-l6-l7"), + RPMH_VREG("ldo7", LDO, 7, &pmic5_pldo530_mvp300, "vdd-l6-l7"), + RPMH_VREG("ldo8", LDO, 8, &pmic5_pldo530_mvp150, "vdd-l8-l9"), + RPMH_VREG("ldo9", LDO, 9, &pmic5_pldo515_mv, "vdd-l8-l9"), + RPMH_VREG("ldo10", LDO, 10, &pmic5_nldo530, "vdd-l1-l4-l10"), + RPMH_VREG("ldo11", LDO, 11, &pmic5_nldo530, "vdd-l3-l11"), + RPMH_VREG("ldo12", LDO, 12, &pmic5_nldo530, "vdd-l12"), + RPMH_VREG("ldo13", LDO, 13, &pmic5_pldo530_mvp150, "vdd-l2-l13-l14"), + RPMH_VREG("ldo14", LDO, 14, &pmic5_pldo530_mvp150, "vdd-l2-l13-l14"), + RPMH_VREG("ldo15", LDO, 15, &pmic5_nldo530, "vdd-l15"), + RPMH_VREG("ldo16", LDO, 15, &pmic5_pldo530_mvp600, "vdd-l5-l16"), + RPMH_VREG("ldo17", LDO, 17, &pmic5_pldo515_mv, "vdd-l17"), + RPMH_VREG("ldo18", LDO, 18, &pmic5_nldo530, "vdd-l18"), + RPMH_VREG("bob1", BOB, 1, &pmic5_bob, "vdd-bob1"), + RPMH_VREG("bob2", BOB, 2, &pmic5_bob, "vdd-bob2"), + {} +}; + +static const struct rpmh_vreg_init_data pmh0104_vreg_data[] = { + RPMH_VREG("smps1", SMPS, 1, &pmic5_ftsmps530, "vdd-s1"), + RPMH_VREG("smps2", SMPS, 2, &pmic5_ftsmps530, "vdd-s2"), + RPMH_VREG("smps3", SMPS, 3, &pmic5_ftsmps530, "vdd-s3"), + RPMH_VREG("smps4", SMPS, 4, &pmic5_ftsmps530, "vdd-s4"), + {} +}; + +static const struct rpmh_vreg_init_data pmh0110_vreg_data[] = { + RPMH_VREG("smps1", SMPS, 1, &pmic5_ftsmps530, "vdd-s1"), + RPMH_VREG("smps2", SMPS, 2, &pmic5_ftsmps530, "vdd-s2"), + RPMH_VREG("smps3", SMPS, 3, &pmic5_ftsmps530, "vdd-s3"), + RPMH_VREG("smps4", SMPS, 4, &pmic5_ftsmps530, "vdd-s4"), + RPMH_VREG("smps5", SMPS, 5, &pmic5_ftsmps530, "vdd-s5"), + RPMH_VREG("smps6", SMPS, 6, &pmic5_ftsmps530, "vdd-s6"), + RPMH_VREG("smps7", SMPS, 7, &pmic5_ftsmps530, "vdd-s7"), + RPMH_VREG("smps8", SMPS, 8, &pmic5_ftsmps530, "vdd-s8"), + RPMH_VREG("smps9", SMPS, 9, &pmic5_ftsmps530, "vdd-s9"), + RPMH_VREG("smps10", SMPS, 10, &pmic5_ftsmps530, "vdd-s10"), + RPMH_VREG("ldo1", LDO, 1, &pmic5_nldo530, "vdd-l1"), + RPMH_VREG("ldo2", LDO, 2, &pmic5_nldo530, "vdd-l2"), + RPMH_VREG("ldo3", LDO, 3, &pmic5_nldo530, "vdd-l3"), + RPMH_VREG("ldo4", LDO, 4, &pmic5_nldo530, "vdd-l4"), + {} }; static const struct rpmh_vreg_init_data pmx55_vreg_data[] = { - RPMH_VREG("smps1", "smp%s1", &pmic5_ftsmps510, "vdd-s1"), - RPMH_VREG("smps2", "smp%s2", &pmic5_hfsmps510, "vdd-s2"), - RPMH_VREG("smps3", "smp%s3", &pmic5_hfsmps510, "vdd-s3"), - RPMH_VREG("smps4", "smp%s4", &pmic5_hfsmps510, "vdd-s4"), - RPMH_VREG("smps5", "smp%s5", &pmic5_hfsmps510, "vdd-s5"), - RPMH_VREG("smps6", "smp%s6", &pmic5_ftsmps510, "vdd-s6"), - RPMH_VREG("smps7", "smp%s7", &pmic5_hfsmps510, "vdd-s7"), - RPMH_VREG("ldo1", "ldo%s1", &pmic5_nldo, "vdd-l1-l2"), - RPMH_VREG("ldo2", "ldo%s2", &pmic5_nldo, "vdd-l1-l2"), - RPMH_VREG("ldo3", "ldo%s3", &pmic5_nldo, "vdd-l3-l9"), - RPMH_VREG("ldo4", "ldo%s4", &pmic5_nldo, "vdd-l4-l12"), - RPMH_VREG("ldo5", "ldo%s5", &pmic5_pldo, "vdd-l5-l6"), - RPMH_VREG("ldo6", "ldo%s6", &pmic5_pldo, "vdd-l5-l6"), - RPMH_VREG("ldo7", "ldo%s7", &pmic5_nldo, "vdd-l7-l8"), - RPMH_VREG("ldo8", "ldo%s8", &pmic5_nldo, "vdd-l7-l8"), - RPMH_VREG("ldo9", "ldo%s9", &pmic5_nldo, "vdd-l3-l9"), - RPMH_VREG("ldo10", "ldo%s10", &pmic5_pldo, "vdd-l10-l11-l13"), - RPMH_VREG("ldo11", "ldo%s11", &pmic5_pldo, "vdd-l10-l11-l13"), - RPMH_VREG("ldo12", "ldo%s12", &pmic5_nldo, "vdd-l4-l12"), - RPMH_VREG("ldo13", "ldo%s13", &pmic5_pldo, "vdd-l10-l11-l13"), - RPMH_VREG("ldo14", "ldo%s14", &pmic5_nldo, "vdd-l14"), - RPMH_VREG("ldo15", "ldo%s15", &pmic5_nldo, "vdd-l15"), - RPMH_VREG("ldo16", "ldo%s16", &pmic5_pldo, "vdd-l16"), + RPMH_VREG("smps1", SMPS, 1, &pmic5_ftsmps510, "vdd-s1"), + RPMH_VREG("smps2", SMPS, 2, &pmic5_hfsmps510, "vdd-s2"), + RPMH_VREG("smps3", SMPS, 3, &pmic5_hfsmps510, "vdd-s3"), + RPMH_VREG("smps4", SMPS, 4, &pmic5_hfsmps510, "vdd-s4"), + RPMH_VREG("smps5", SMPS, 5, &pmic5_hfsmps510, "vdd-s5"), + RPMH_VREG("smps6", SMPS, 6, &pmic5_ftsmps510, "vdd-s6"), + RPMH_VREG("smps7", SMPS, 7, &pmic5_hfsmps510, "vdd-s7"), + RPMH_VREG("ldo1", LDO, 1, &pmic5_nldo, "vdd-l1-l2"), + RPMH_VREG("ldo2", LDO, 2, &pmic5_nldo, "vdd-l1-l2"), + RPMH_VREG("ldo3", LDO, 3, &pmic5_nldo, "vdd-l3-l9"), + RPMH_VREG("ldo4", LDO, 4, &pmic5_nldo, "vdd-l4-l12"), + RPMH_VREG("ldo5", LDO, 5, &pmic5_pldo, "vdd-l5-l6"), + RPMH_VREG("ldo6", LDO, 6, &pmic5_pldo, "vdd-l5-l6"), + RPMH_VREG("ldo7", LDO, 7, &pmic5_nldo, "vdd-l7-l8"), + RPMH_VREG("ldo8", LDO, 8, &pmic5_nldo, "vdd-l7-l8"), + RPMH_VREG("ldo9", LDO, 9, &pmic5_nldo, "vdd-l3-l9"), + RPMH_VREG("ldo10", LDO, 10, &pmic5_pldo, "vdd-l10-l11-l13"), + RPMH_VREG("ldo11", LDO, 11, &pmic5_pldo, "vdd-l10-l11-l13"), + RPMH_VREG("ldo12", LDO, 12, &pmic5_nldo, "vdd-l4-l12"), + RPMH_VREG("ldo13", LDO, 13, &pmic5_pldo, "vdd-l10-l11-l13"), + RPMH_VREG("ldo14", LDO, 14, &pmic5_nldo, "vdd-l14"), + RPMH_VREG("ldo15", LDO, 15, &pmic5_nldo, "vdd-l15"), + RPMH_VREG("ldo16", LDO, 16, &pmic5_pldo, "vdd-l16"), {} }; static const struct rpmh_vreg_init_data pmx65_vreg_data[] = { - RPMH_VREG("smps1", "smp%s1", &pmic5_ftsmps510, "vdd-s1"), - RPMH_VREG("smps2", "smp%s2", &pmic5_hfsmps510, "vdd-s2"), - RPMH_VREG("smps3", "smp%s3", &pmic5_hfsmps510, "vdd-s3"), - RPMH_VREG("smps4", "smp%s4", &pmic5_hfsmps510, "vdd-s4"), - RPMH_VREG("smps5", "smp%s5", &pmic5_hfsmps510, "vdd-s5"), - RPMH_VREG("smps6", "smp%s6", &pmic5_ftsmps510, "vdd-s6"), - RPMH_VREG("smps7", "smp%s7", &pmic5_hfsmps510, "vdd-s7"), - RPMH_VREG("smps8", "smp%s8", &pmic5_hfsmps510, "vdd-s8"), - RPMH_VREG("ldo1", "ldo%s1", &pmic5_nldo, "vdd-l1"), - RPMH_VREG("ldo2", "ldo%s2", &pmic5_nldo, "vdd-l2-l18"), - RPMH_VREG("ldo3", "ldo%s3", &pmic5_nldo, "vdd-l3"), - RPMH_VREG("ldo4", "ldo%s4", &pmic5_nldo, "vdd-l4"), - RPMH_VREG("ldo5", "ldo%s5", &pmic5_pldo, "vdd-l5-l6-l16"), - RPMH_VREG("ldo6", "ldo%s6", &pmic5_pldo, "vdd-l5-l6-l16"), - RPMH_VREG("ldo7", "ldo%s7", &pmic5_nldo, "vdd-l7"), - RPMH_VREG("ldo8", "ldo%s8", &pmic5_nldo, "vdd-l8-l9"), - RPMH_VREG("ldo9", "ldo%s9", &pmic5_nldo, "vdd-l8-l9"), - RPMH_VREG("ldo10", "ldo%s10", &pmic5_pldo, "vdd-l10"), - RPMH_VREG("ldo11", "ldo%s11", &pmic5_pldo, "vdd-l11-l13"), - RPMH_VREG("ldo12", "ldo%s12", &pmic5_nldo, "vdd-l12"), - RPMH_VREG("ldo13", "ldo%s13", &pmic5_pldo, "vdd-l11-l13"), - RPMH_VREG("ldo14", "ldo%s14", &pmic5_nldo, "vdd-l14"), - RPMH_VREG("ldo15", "ldo%s15", &pmic5_nldo, "vdd-l15"), - RPMH_VREG("ldo16", "ldo%s16", &pmic5_pldo, "vdd-l5-l6-l16"), - RPMH_VREG("ldo17", "ldo%s17", &pmic5_nldo, "vdd-l17"), + RPMH_VREG("smps1", SMPS, 1, &pmic5_ftsmps510, "vdd-s1"), + RPMH_VREG("smps2", SMPS, 2, &pmic5_hfsmps510, "vdd-s2"), + RPMH_VREG("smps3", SMPS, 3, &pmic5_hfsmps510, "vdd-s3"), + RPMH_VREG("smps4", SMPS, 4, &pmic5_hfsmps510, "vdd-s4"), + RPMH_VREG("smps5", SMPS, 5, &pmic5_hfsmps510, "vdd-s5"), + RPMH_VREG("smps6", SMPS, 6, &pmic5_ftsmps510, "vdd-s6"), + RPMH_VREG("smps7", SMPS, 7, &pmic5_hfsmps510, "vdd-s7"), + RPMH_VREG("smps8", SMPS, 8, &pmic5_hfsmps510, "vdd-s8"), + RPMH_VREG("ldo1", LDO, 1, &pmic5_nldo, "vdd-l1"), + RPMH_VREG("ldo2", LDO, 2, &pmic5_nldo, "vdd-l2-l18"), + RPMH_VREG("ldo3", LDO, 3, &pmic5_nldo, "vdd-l3"), + RPMH_VREG("ldo4", LDO, 4, &pmic5_nldo, "vdd-l4"), + RPMH_VREG("ldo5", LDO, 5, &pmic5_pldo, "vdd-l5-l6-l16"), + RPMH_VREG("ldo6", LDO, 6, &pmic5_pldo, "vdd-l5-l6-l16"), + RPMH_VREG("ldo7", LDO, 7, &pmic5_nldo, "vdd-l7"), + RPMH_VREG("ldo8", LDO, 8, &pmic5_nldo, "vdd-l8-l9"), + RPMH_VREG("ldo9", LDO, 9, &pmic5_nldo, "vdd-l8-l9"), + RPMH_VREG("ldo10", LDO, 10, &pmic5_pldo, "vdd-l10"), + RPMH_VREG("ldo11", LDO, 11, &pmic5_pldo, "vdd-l11-l13"), + RPMH_VREG("ldo12", LDO, 12, &pmic5_nldo, "vdd-l12"), + RPMH_VREG("ldo13", LDO, 13, &pmic5_pldo, "vdd-l11-l13"), + RPMH_VREG("ldo14", LDO, 14, &pmic5_nldo, "vdd-l14"), + RPMH_VREG("ldo15", LDO, 15, &pmic5_nldo, "vdd-l15"), + RPMH_VREG("ldo16", LDO, 16, &pmic5_pldo, "vdd-l5-l6-l16"), + RPMH_VREG("ldo17", LDO, 17, &pmic5_nldo, "vdd-l17"), /* ldo18 not configured */ - RPMH_VREG("ldo19", "ldo%s19", &pmic5_nldo, "vdd-l19"), - RPMH_VREG("ldo20", "ldo%s20", &pmic5_nldo, "vdd-l20"), - RPMH_VREG("ldo21", "ldo%s21", &pmic5_nldo, "vdd-l21"), + RPMH_VREG("ldo19", LDO, 19, &pmic5_nldo, "vdd-l19"), + RPMH_VREG("ldo20", LDO, 20, &pmic5_nldo, "vdd-l20"), + RPMH_VREG("ldo21", LDO, 21, &pmic5_nldo, "vdd-l21"), {} }; static const struct rpmh_vreg_init_data pmx75_vreg_data[] = { - RPMH_VREG("smps1", "smp%s1", &pmic5_ftsmps525, "vdd-s1"), - RPMH_VREG("smps2", "smp%s2", &pmic5_ftsmps525, "vdd-s2"), - RPMH_VREG("smps3", "smp%s3", &pmic5_ftsmps525, "vdd-s3"), - RPMH_VREG("smps4", "smp%s4", &pmic5_ftsmps525, "vdd-s4"), - RPMH_VREG("smps5", "smp%s5", &pmic5_ftsmps525, "vdd-s5"), - RPMH_VREG("smps6", "smp%s6", &pmic5_ftsmps525, "vdd-s6"), - RPMH_VREG("smps7", "smp%s7", &pmic5_ftsmps525, "vdd-s7"), - RPMH_VREG("smps8", "smp%s8", &pmic5_ftsmps525, "vdd-s8"), - RPMH_VREG("smps9", "smp%s9", &pmic5_ftsmps525, "vdd-s9"), - RPMH_VREG("smps10", "smp%s10", &pmic5_ftsmps525, "vdd-s10"), - RPMH_VREG("ldo1", "ldo%s1", &pmic5_nldo515, "vdd-l1"), - RPMH_VREG("ldo2", "ldo%s2", &pmic5_nldo515, "vdd-l2-18"), - RPMH_VREG("ldo3", "ldo%s3", &pmic5_nldo515, "vdd-l3"), - RPMH_VREG("ldo4", "ldo%s4", &pmic5_nldo515, "vdd-l4-l16"), - RPMH_VREG("ldo5", "ldo%s5", &pmic5_pldo_lv, "vdd-l5-l6"), - RPMH_VREG("ldo6", "ldo%s6", &pmic5_pldo_lv, "vdd-l5-l6"), - RPMH_VREG("ldo7", "ldo%s7", &pmic5_nldo515, "vdd-l7"), - RPMH_VREG("ldo8", "ldo%s8", &pmic5_nldo515, "vdd-l8-l9"), - RPMH_VREG("ldo9", "ldo%s9", &pmic5_nldo515, "vdd-l8-l9"), - RPMH_VREG("ldo10", "ldo%s10", &pmic5_pldo, "vdd-l10"), - RPMH_VREG("ldo11", "ldo%s11", &pmic5_pldo, "vdd-l11-l13"), - RPMH_VREG("ldo12", "ldo%s12", &pmic5_nldo515, "vdd-l12"), - RPMH_VREG("ldo13", "ldo%s13", &pmic5_pldo, "vdd-l11-l13"), - RPMH_VREG("ldo14", "ldo%s14", &pmic5_nldo515, "vdd-l14"), - RPMH_VREG("ldo15", "ldo%s15", &pmic5_nldo515, "vdd-l15"), - RPMH_VREG("ldo16", "ldo%s16", &pmic5_nldo515, "vdd-l4-l16"), - RPMH_VREG("ldo17", "ldo%s17", &pmic5_nldo515, "vdd-l17"), + RPMH_VREG("smps1", SMPS, 1, &pmic5_ftsmps525, "vdd-s1"), + RPMH_VREG("smps2", SMPS, 2, &pmic5_ftsmps525, "vdd-s2"), + RPMH_VREG("smps3", SMPS, 3, &pmic5_ftsmps525, "vdd-s3"), + RPMH_VREG("smps4", SMPS, 4, &pmic5_ftsmps525, "vdd-s4"), + RPMH_VREG("smps5", SMPS, 5, &pmic5_ftsmps525, "vdd-s5"), + RPMH_VREG("smps6", SMPS, 6, &pmic5_ftsmps525, "vdd-s6"), + RPMH_VREG("smps7", SMPS, 7, &pmic5_ftsmps525, "vdd-s7"), + RPMH_VREG("smps8", SMPS, 8, &pmic5_ftsmps525, "vdd-s8"), + RPMH_VREG("smps9", SMPS, 9, &pmic5_ftsmps525, "vdd-s9"), + RPMH_VREG("smps10", SMPS, 10, &pmic5_ftsmps525, "vdd-s10"), + RPMH_VREG("ldo1", LDO, 1, &pmic5_nldo515, "vdd-l1"), + RPMH_VREG("ldo2", LDO, 2, &pmic5_nldo515, "vdd-l2-18"), + RPMH_VREG("ldo3", LDO, 3, &pmic5_nldo515, "vdd-l3"), + RPMH_VREG("ldo4", LDO, 4, &pmic5_nldo515, "vdd-l4-l16"), + RPMH_VREG("ldo5", LDO, 5, &pmic5_pldo_lv, "vdd-l5-l6"), + RPMH_VREG("ldo6", LDO, 6, &pmic5_pldo_lv, "vdd-l5-l6"), + RPMH_VREG("ldo7", LDO, 7, &pmic5_nldo515, "vdd-l7"), + RPMH_VREG("ldo8", LDO, 8, &pmic5_nldo515, "vdd-l8-l9"), + RPMH_VREG("ldo9", LDO, 9, &pmic5_nldo515, "vdd-l8-l9"), + RPMH_VREG("ldo10", LDO, 10, &pmic5_pldo, "vdd-l10"), + RPMH_VREG("ldo11", LDO, 11, &pmic5_pldo, "vdd-l11-l13"), + RPMH_VREG("ldo12", LDO, 12, &pmic5_nldo515, "vdd-l12"), + RPMH_VREG("ldo13", LDO, 13, &pmic5_pldo, "vdd-l11-l13"), + RPMH_VREG("ldo14", LDO, 14, &pmic5_nldo515, "vdd-l14"), + RPMH_VREG("ldo15", LDO, 15, &pmic5_nldo515, "vdd-l15"), + RPMH_VREG("ldo16", LDO, 16, &pmic5_nldo515, "vdd-l4-l16"), + RPMH_VREG("ldo17", LDO, 17, &pmic5_nldo515, "vdd-l17"), /* ldo18 not configured */ - RPMH_VREG("ldo19", "ldo%s19", &pmic5_nldo515, "vdd-l19"), - RPMH_VREG("ldo20", "ldo%s20", &pmic5_nldo515, "vdd-l20-l21"), - RPMH_VREG("ldo21", "ldo%s21", &pmic5_nldo515, "vdd-l20-l21"), + RPMH_VREG("ldo19", LDO, 19, &pmic5_nldo515, "vdd-l19"), + RPMH_VREG("ldo20", LDO, 20, &pmic5_nldo515, "vdd-l20-l21"), + RPMH_VREG("ldo21", LDO, 21, &pmic5_nldo515, "vdd-l20-l21"), }; static const struct rpmh_vreg_init_data pm7325_vreg_data[] = { - RPMH_VREG("smps1", "smp%s1", &pmic5_hfsmps510, "vdd-s1"), - RPMH_VREG("smps2", "smp%s2", &pmic5_ftsmps520, "vdd-s2"), - RPMH_VREG("smps3", "smp%s3", &pmic5_ftsmps520, "vdd-s3"), - RPMH_VREG("smps4", "smp%s4", &pmic5_ftsmps520, "vdd-s4"), - RPMH_VREG("smps5", "smp%s5", &pmic5_ftsmps520, "vdd-s5"), - RPMH_VREG("smps6", "smp%s6", &pmic5_ftsmps520, "vdd-s6"), - RPMH_VREG("smps7", "smp%s7", &pmic5_ftsmps520, "vdd-s7"), - RPMH_VREG("smps8", "smp%s8", &pmic5_hfsmps510, "vdd-s8"), - RPMH_VREG("ldo1", "ldo%s1", &pmic5_nldo, "vdd-l1-l4-l12-l15"), - RPMH_VREG("ldo2", "ldo%s2", &pmic5_pldo, "vdd-l2-l7"), - RPMH_VREG("ldo3", "ldo%s3", &pmic5_nldo, "vdd-l3"), - RPMH_VREG("ldo4", "ldo%s4", &pmic5_nldo, "vdd-l1-l4-l12-l15"), - RPMH_VREG("ldo5", "ldo%s5", &pmic5_nldo, "vdd-l5"), - RPMH_VREG("ldo6", "ldo%s6", &pmic5_nldo, "vdd-l6-l9-l10"), - RPMH_VREG("ldo7", "ldo%s7", &pmic5_pldo, "vdd-l2-l7"), - RPMH_VREG("ldo8", "ldo%s8", &pmic5_nldo, "vdd-l8"), - RPMH_VREG("ldo9", "ldo%s9", &pmic5_nldo, "vdd-l6-l9-l10"), - RPMH_VREG("ldo10", "ldo%s10", &pmic5_nldo, "vdd-l6-l9-l10"), - RPMH_VREG("ldo11", "ldo%s11", &pmic5_pldo_lv, "vdd-l11-l17-l18-l19"), - RPMH_VREG("ldo12", "ldo%s12", &pmic5_nldo, "vdd-l1-l4-l12-l15"), - RPMH_VREG("ldo13", "ldo%s13", &pmic5_nldo, "vdd-l13"), - RPMH_VREG("ldo14", "ldo%s14", &pmic5_nldo, "vdd-l14-l16"), - RPMH_VREG("ldo15", "ldo%s15", &pmic5_nldo, "vdd-l1-l4-l12-l15"), - RPMH_VREG("ldo16", "ldo%s16", &pmic5_nldo, "vdd-l14-l16"), - RPMH_VREG("ldo17", "ldo%s17", &pmic5_pldo_lv, "vdd-l11-l17-l18-l19"), - RPMH_VREG("ldo18", "ldo%s18", &pmic5_pldo_lv, "vdd-l11-l17-l18-l19"), - RPMH_VREG("ldo19", "ldo%s19", &pmic5_pldo_lv, "vdd-l11-l17-l18-l19"), + RPMH_VREG("smps1", SMPS, 1, &pmic5_hfsmps510, "vdd-s1"), + RPMH_VREG("smps2", SMPS, 2, &pmic5_ftsmps520, "vdd-s2"), + RPMH_VREG("smps3", SMPS, 3, &pmic5_ftsmps520, "vdd-s3"), + RPMH_VREG("smps4", SMPS, 4, &pmic5_ftsmps520, "vdd-s4"), + RPMH_VREG("smps5", SMPS, 5, &pmic5_ftsmps520, "vdd-s5"), + RPMH_VREG("smps6", SMPS, 6, &pmic5_ftsmps520, "vdd-s6"), + RPMH_VREG("smps7", SMPS, 7, &pmic5_ftsmps520, "vdd-s7"), + RPMH_VREG("smps8", SMPS, 8, &pmic5_hfsmps510, "vdd-s8"), + RPMH_VREG("ldo1", LDO, 1, &pmic5_nldo, "vdd-l1-l4-l12-l15"), + RPMH_VREG("ldo2", LDO, 2, &pmic5_pldo, "vdd-l2-l7"), + RPMH_VREG("ldo3", LDO, 3, &pmic5_nldo, "vdd-l3"), + RPMH_VREG("ldo4", LDO, 4, &pmic5_nldo, "vdd-l1-l4-l12-l15"), + RPMH_VREG("ldo5", LDO, 5, &pmic5_nldo, "vdd-l5"), + RPMH_VREG("ldo6", LDO, 6, &pmic5_nldo, "vdd-l6-l9-l10"), + RPMH_VREG("ldo7", LDO, 7, &pmic5_pldo, "vdd-l2-l7"), + RPMH_VREG("ldo8", LDO, 8, &pmic5_nldo, "vdd-l8"), + RPMH_VREG("ldo9", LDO, 9, &pmic5_nldo, "vdd-l6-l9-l10"), + RPMH_VREG("ldo10", LDO, 10, &pmic5_nldo, "vdd-l6-l9-l10"), + RPMH_VREG("ldo11", LDO, 11, &pmic5_pldo_lv, "vdd-l11-l17-l18-l19"), + RPMH_VREG("ldo12", LDO, 12, &pmic5_nldo, "vdd-l1-l4-l12-l15"), + RPMH_VREG("ldo13", LDO, 13, &pmic5_nldo, "vdd-l13"), + RPMH_VREG("ldo14", LDO, 14, &pmic5_nldo, "vdd-l14-l16"), + RPMH_VREG("ldo15", LDO, 15, &pmic5_nldo, "vdd-l1-l4-l12-l15"), + RPMH_VREG("ldo16", LDO, 16, &pmic5_nldo, "vdd-l14-l16"), + RPMH_VREG("ldo17", LDO, 17, &pmic5_pldo_lv, "vdd-l11-l17-l18-l19"), + RPMH_VREG("ldo18", LDO, 18, &pmic5_pldo_lv, "vdd-l11-l17-l18-l19"), + RPMH_VREG("ldo19", LDO, 19, &pmic5_pldo_lv, "vdd-l11-l17-l18-l19"), {} }; static const struct rpmh_vreg_init_data pm7550_vreg_data[] = { - RPMH_VREG("smps1", "smp%s1", &pmic5_ftsmps525, "vdd-s1"), - RPMH_VREG("smps2", "smp%s2", &pmic5_ftsmps525, "vdd-s2"), - RPMH_VREG("smps3", "smp%s3", &pmic5_ftsmps525, "vdd-s3"), - RPMH_VREG("smps4", "smp%s4", &pmic5_ftsmps525, "vdd-s4"), - RPMH_VREG("smps5", "smp%s5", &pmic5_ftsmps525, "vdd-s5"), - RPMH_VREG("smps6", "smp%s6", &pmic5_ftsmps525, "vdd-s6"), - RPMH_VREG("ldo1", "ldo%s1", &pmic5_nldo515, "vdd-l1"), - RPMH_VREG("ldo2", "ldo%s2", &pmic5_nldo515, "vdd-l2-l3"), - RPMH_VREG("ldo3", "ldo%s3", &pmic5_nldo515, "vdd-l2-l3"), - RPMH_VREG("ldo4", "ldo%s4", &pmic5_nldo515, "vdd-l4-l5"), - RPMH_VREG("ldo5", "ldo%s5", &pmic5_nldo515, "vdd-l4-l5"), - RPMH_VREG("ldo6", "ldo%s6", &pmic5_nldo515, "vdd-l6"), - RPMH_VREG("ldo7", "ldo%s7", &pmic5_nldo515, "vdd-l7"), - RPMH_VREG("ldo8", "ldo%s8", &pmic5_nldo515, "vdd-l8"), - RPMH_VREG("ldo9", "ldo%s9", &pmic5_nldo515, "vdd-l9-l10"), - RPMH_VREG("ldo10", "ldo%s10", &pmic5_nldo515, "vdd-l9-l10"), - RPMH_VREG("ldo11", "ldo%s11", &pmic5_nldo515, "vdd-l11"), - RPMH_VREG("ldo12", "ldo%s12", &pmic5_pldo515_mv, "vdd-l12-l14"), - RPMH_VREG("ldo13", "ldo%s13", &pmic5_pldo515_mv, "vdd-l13-l16"), - RPMH_VREG("ldo14", "ldo%s14", &pmic5_pldo, "vdd-l12-l14"), - RPMH_VREG("ldo15", "ldo%s15", &pmic5_pldo, "vdd-l15-l17-l18-l19-l20-l21-l22-l23"), - RPMH_VREG("ldo16", "ldo%s16", &pmic5_pldo, "vdd-l13-l16"), - RPMH_VREG("ldo17", "ldo%s17", &pmic5_pldo, "vdd-l15-l17-l18-l19-l20-l21-l22-l23"), - RPMH_VREG("ldo18", "ldo%s18", &pmic5_pldo, "vdd-l15-l17-l18-l19-l20-l21-l22-l23"), - RPMH_VREG("ldo19", "ldo%s19", &pmic5_pldo, "vdd-l15-l17-l18-l19-l20-l21-l22-l23"), - RPMH_VREG("ldo20", "ldo%s20", &pmic5_pldo, "vdd-l15-l17-l18-l19-l20-l21-l22-l23"), - RPMH_VREG("ldo21", "ldo%s21", &pmic5_pldo, "vdd-l15-l17-l18-l19-l20-l21-l22-l23"), - RPMH_VREG("ldo22", "ldo%s22", &pmic5_pldo, "vdd-l15-l17-l18-l19-l20-l21-l22-l23"), - RPMH_VREG("ldo23", "ldo%s23", &pmic5_pldo, "vdd-l15-l17-l18-l19-l20-l21-l22-l23"), - RPMH_VREG("bob", "bob%s1", &pmic5_bob, "vdd-bob"), + RPMH_VREG("smps1", SMPS, 1, &pmic5_ftsmps525, "vdd-s1"), + RPMH_VREG("smps2", SMPS, 2, &pmic5_ftsmps525, "vdd-s2"), + RPMH_VREG("smps3", SMPS, 3, &pmic5_ftsmps525, "vdd-s3"), + RPMH_VREG("smps4", SMPS, 4, &pmic5_ftsmps525, "vdd-s4"), + RPMH_VREG("smps5", SMPS, 5, &pmic5_ftsmps525, "vdd-s5"), + RPMH_VREG("smps6", SMPS, 6, &pmic5_ftsmps525, "vdd-s6"), + RPMH_VREG("ldo1", LDO, 1, &pmic5_nldo515, "vdd-l1"), + RPMH_VREG("ldo2", LDO, 2, &pmic5_nldo515, "vdd-l2-l3"), + RPMH_VREG("ldo3", LDO, 3, &pmic5_nldo515, "vdd-l2-l3"), + RPMH_VREG("ldo4", LDO, 4, &pmic5_nldo515, "vdd-l4-l5"), + RPMH_VREG("ldo5", LDO, 5, &pmic5_nldo515, "vdd-l4-l5"), + RPMH_VREG("ldo6", LDO, 6, &pmic5_nldo515, "vdd-l6"), + RPMH_VREG("ldo7", LDO, 7, &pmic5_nldo515, "vdd-l7"), + RPMH_VREG("ldo8", LDO, 8, &pmic5_nldo515, "vdd-l8"), + RPMH_VREG("ldo9", LDO, 9, &pmic5_nldo515, "vdd-l9-l10"), + RPMH_VREG("ldo10", LDO, 10, &pmic5_nldo515, "vdd-l9-l10"), + RPMH_VREG("ldo11", LDO, 11, &pmic5_nldo515, "vdd-l11"), + RPMH_VREG("ldo12", LDO, 12, &pmic5_pldo515_mv, "vdd-l12-l14"), + RPMH_VREG("ldo13", LDO, 13, &pmic5_pldo515_mv, "vdd-l13-l16"), + RPMH_VREG("ldo14", LDO, 14, &pmic5_pldo, "vdd-l12-l14"), + RPMH_VREG("ldo15", LDO, 15, &pmic5_pldo, "vdd-l15-l17-l18-l19-l20-l21-l22-l23"), + RPMH_VREG("ldo16", LDO, 16, &pmic5_pldo, "vdd-l13-l16"), + RPMH_VREG("ldo17", LDO, 17, &pmic5_pldo, "vdd-l15-l17-l18-l19-l20-l21-l22-l23"), + RPMH_VREG("ldo18", LDO, 18, &pmic5_pldo, "vdd-l15-l17-l18-l19-l20-l21-l22-l23"), + RPMH_VREG("ldo19", LDO, 19, &pmic5_pldo, "vdd-l15-l17-l18-l19-l20-l21-l22-l23"), + RPMH_VREG("ldo20", LDO, 20, &pmic5_pldo, "vdd-l15-l17-l18-l19-l20-l21-l22-l23"), + RPMH_VREG("ldo21", LDO, 21, &pmic5_pldo, "vdd-l15-l17-l18-l19-l20-l21-l22-l23"), + RPMH_VREG("ldo22", LDO, 22, &pmic5_pldo, "vdd-l15-l17-l18-l19-l20-l21-l22-l23"), + RPMH_VREG("ldo23", LDO, 23, &pmic5_pldo, "vdd-l15-l17-l18-l19-l20-l21-l22-l23"), + RPMH_VREG("bob", BOB, 1, &pmic5_bob, "vdd-bob"), {} }; static const struct rpmh_vreg_init_data pmr735a_vreg_data[] = { - RPMH_VREG("smps1", "smp%s1", &pmic5_ftsmps520, "vdd-s1"), - RPMH_VREG("smps2", "smp%s2", &pmic5_ftsmps520, "vdd-s2"), - RPMH_VREG("smps3", "smp%s3", &pmic5_hfsmps515, "vdd-s3"), - RPMH_VREG("ldo1", "ldo%s1", &pmic5_nldo, "vdd-l1-l2"), - RPMH_VREG("ldo2", "ldo%s2", &pmic5_nldo, "vdd-l1-l2"), - RPMH_VREG("ldo3", "ldo%s3", &pmic5_nldo, "vdd-l3"), - RPMH_VREG("ldo4", "ldo%s4", &pmic5_pldo_lv, "vdd-l4"), - RPMH_VREG("ldo5", "ldo%s5", &pmic5_nldo, "vdd-l5-l6"), - RPMH_VREG("ldo6", "ldo%s6", &pmic5_nldo, "vdd-l5-l6"), - RPMH_VREG("ldo7", "ldo%s7", &pmic5_pldo, "vdd-l7-bob"), + RPMH_VREG("smps1", SMPS, 1, &pmic5_ftsmps520, "vdd-s1"), + RPMH_VREG("smps2", SMPS, 2, &pmic5_ftsmps520, "vdd-s2"), + RPMH_VREG("smps3", SMPS, 3, &pmic5_hfsmps515, "vdd-s3"), + RPMH_VREG("ldo1", LDO, 1, &pmic5_nldo, "vdd-l1-l2"), + RPMH_VREG("ldo2", LDO, 2, &pmic5_nldo, "vdd-l1-l2"), + RPMH_VREG("ldo3", LDO, 3, &pmic5_nldo, "vdd-l3"), + RPMH_VREG("ldo4", LDO, 4, &pmic5_pldo_lv, "vdd-l4"), + RPMH_VREG("ldo5", LDO, 5, &pmic5_nldo, "vdd-l5-l6"), + RPMH_VREG("ldo6", LDO, 6, &pmic5_nldo, "vdd-l5-l6"), + RPMH_VREG("ldo7", LDO, 7, &pmic5_pldo, "vdd-l7-bob"), {} }; static const struct rpmh_vreg_init_data pmr735b_vreg_data[] = { - RPMH_VREG("ldo1", "ldo%s1", &pmic5_nldo, "vdd-l1-l2"), - RPMH_VREG("ldo2", "ldo%s2", &pmic5_nldo, "vdd-l1-l2"), - RPMH_VREG("ldo3", "ldo%s3", &pmic5_nldo, "vdd-l3"), - RPMH_VREG("ldo4", "ldo%s4", &pmic5_pldo_lv, "vdd-l4"), - RPMH_VREG("ldo5", "ldo%s5", &pmic5_nldo, "vdd-l5"), - RPMH_VREG("ldo6", "ldo%s6", &pmic5_nldo, "vdd-l6"), - RPMH_VREG("ldo7", "ldo%s7", &pmic5_nldo, "vdd-l7-l8"), - RPMH_VREG("ldo8", "ldo%s8", &pmic5_nldo, "vdd-l7-l8"), - RPMH_VREG("ldo9", "ldo%s9", &pmic5_nldo, "vdd-l9"), - RPMH_VREG("ldo10", "ldo%s10", &pmic5_pldo_lv, "vdd-l10"), - RPMH_VREG("ldo11", "ldo%s11", &pmic5_nldo, "vdd-l11"), - RPMH_VREG("ldo12", "ldo%s12", &pmic5_nldo, "vdd-l12"), + RPMH_VREG("ldo1", LDO, 1, &pmic5_nldo, "vdd-l1-l2"), + RPMH_VREG("ldo2", LDO, 2, &pmic5_nldo, "vdd-l1-l2"), + RPMH_VREG("ldo3", LDO, 3, &pmic5_nldo, "vdd-l3"), + RPMH_VREG("ldo4", LDO, 4, &pmic5_pldo_lv, "vdd-l4"), + RPMH_VREG("ldo5", LDO, 5, &pmic5_nldo, "vdd-l5"), + RPMH_VREG("ldo6", LDO, 6, &pmic5_nldo, "vdd-l6"), + RPMH_VREG("ldo7", LDO, 7, &pmic5_nldo, "vdd-l7-l8"), + RPMH_VREG("ldo8", LDO, 8, &pmic5_nldo, "vdd-l7-l8"), + RPMH_VREG("ldo9", LDO, 9, &pmic5_nldo, "vdd-l9"), + RPMH_VREG("ldo10", LDO, 10, &pmic5_pldo_lv, "vdd-l10"), + RPMH_VREG("ldo11", LDO, 11, &pmic5_nldo, "vdd-l11"), + RPMH_VREG("ldo12", LDO, 12, &pmic5_nldo, "vdd-l12"), + {} +}; + +static const struct rpmh_vreg_init_data pmr735d_vreg_data[] = { + RPMH_VREG("ldo1", LDO, 1, &pmic5_nldo515, "vdd-l1-l2-l5"), + RPMH_VREG("ldo2", LDO, 2, &pmic5_nldo515, "vdd-l1-l2-l5"), + RPMH_VREG("ldo3", LDO, 3, &pmic5_nldo515, "vdd-l3-l4"), + RPMH_VREG("ldo4", LDO, 4, &pmic5_nldo515, "vdd-l3-l4"), + RPMH_VREG("ldo5", LDO, 5, &pmic5_nldo515, "vdd-l1-l2-l5"), + RPMH_VREG("ldo6", LDO, 6, &pmic5_nldo515, "vdd-l6"), + RPMH_VREG("ldo7", LDO, 7, &pmic5_nldo515, "vdd-l7"), {} }; static const struct rpmh_vreg_init_data pm660_vreg_data[] = { - RPMH_VREG("smps1", "smp%s1", &pmic4_ftsmps426, "vdd-s1"), - RPMH_VREG("smps2", "smp%s2", &pmic4_ftsmps426, "vdd-s2"), - RPMH_VREG("smps3", "smp%s3", &pmic4_ftsmps426, "vdd-s3"), - RPMH_VREG("smps4", "smp%s4", &pmic4_hfsmps3, "vdd-s4"), - RPMH_VREG("smps5", "smp%s5", &pmic4_hfsmps3, "vdd-s5"), - RPMH_VREG("smps6", "smp%s6", &pmic4_hfsmps3, "vdd-s6"), - RPMH_VREG("ldo1", "ldo%s1", &pmic4_nldo, "vdd-l1-l6-l7"), - RPMH_VREG("ldo2", "ldo%s2", &pmic4_nldo, "vdd-l2-l3"), - RPMH_VREG("ldo3", "ldo%s3", &pmic4_nldo, "vdd-l2-l3"), + RPMH_VREG("smps1", SMPS, 1, &pmic4_ftsmps426, "vdd-s1"), + RPMH_VREG("smps2", SMPS, 2, &pmic4_ftsmps426, "vdd-s2"), + RPMH_VREG("smps3", SMPS, 3, &pmic4_ftsmps426, "vdd-s3"), + RPMH_VREG("smps4", SMPS, 4, &pmic4_hfsmps3, "vdd-s4"), + RPMH_VREG("smps5", SMPS, 5, &pmic4_hfsmps3, "vdd-s5"), + RPMH_VREG("smps6", SMPS, 6, &pmic4_hfsmps3, "vdd-s6"), + RPMH_VREG("ldo1", LDO, 1, &pmic4_nldo, "vdd-l1-l6-l7"), + RPMH_VREG("ldo2", LDO, 2, &pmic4_nldo, "vdd-l2-l3"), + RPMH_VREG("ldo3", LDO, 3, &pmic4_nldo, "vdd-l2-l3"), /* ldo4 is inaccessible on PM660 */ - RPMH_VREG("ldo5", "ldo%s5", &pmic4_nldo, "vdd-l5"), - RPMH_VREG("ldo6", "ldo%s6", &pmic4_nldo, "vdd-l1-l6-l7"), - RPMH_VREG("ldo7", "ldo%s7", &pmic4_nldo, "vdd-l1-l6-l7"), - RPMH_VREG("ldo8", "ldo%s8", &pmic4_pldo_lv, "vdd-l8-l9-l10-l11-l12-l13-l14"), - RPMH_VREG("ldo9", "ldo%s9", &pmic4_pldo_lv, "vdd-l8-l9-l10-l11-l12-l13-l14"), - RPMH_VREG("ldo10", "ldo%s10", &pmic4_pldo_lv, "vdd-l8-l9-l10-l11-l12-l13-l14"), - RPMH_VREG("ldo11", "ldo%s11", &pmic4_pldo_lv, "vdd-l8-l9-l10-l11-l12-l13-l14"), - RPMH_VREG("ldo12", "ldo%s12", &pmic4_pldo_lv, "vdd-l8-l9-l10-l11-l12-l13-l14"), - RPMH_VREG("ldo13", "ldo%s13", &pmic4_pldo_lv, "vdd-l8-l9-l10-l11-l12-l13-l14"), - RPMH_VREG("ldo14", "ldo%s14", &pmic4_pldo_lv, "vdd-l8-l9-l10-l11-l12-l13-l14"), - RPMH_VREG("ldo15", "ldo%s15", &pmic4_pldo, "vdd-l15-l16-l17-l18-l19"), - RPMH_VREG("ldo16", "ldo%s16", &pmic4_pldo, "vdd-l15-l16-l17-l18-l19"), - RPMH_VREG("ldo17", "ldo%s17", &pmic4_pldo, "vdd-l15-l16-l17-l18-l19"), - RPMH_VREG("ldo18", "ldo%s18", &pmic4_pldo, "vdd-l15-l16-l17-l18-l19"), - RPMH_VREG("ldo19", "ldo%s19", &pmic4_pldo, "vdd-l15-l16-l17-l18-l19"), + RPMH_VREG("ldo5", LDO, 5, &pmic4_nldo, "vdd-l5"), + RPMH_VREG("ldo6", LDO, 6, &pmic4_nldo, "vdd-l1-l6-l7"), + RPMH_VREG("ldo7", LDO, 7, &pmic4_nldo, "vdd-l1-l6-l7"), + RPMH_VREG("ldo8", LDO, 8, &pmic4_pldo_lv, "vdd-l8-l9-l10-l11-l12-l13-l14"), + RPMH_VREG("ldo9", LDO, 9, &pmic4_pldo_lv, "vdd-l8-l9-l10-l11-l12-l13-l14"), + RPMH_VREG("ldo10", LDO, 10, &pmic4_pldo_lv, "vdd-l8-l9-l10-l11-l12-l13-l14"), + RPMH_VREG("ldo11", LDO, 11, &pmic4_pldo_lv, "vdd-l8-l9-l10-l11-l12-l13-l14"), + RPMH_VREG("ldo12", LDO, 12, &pmic4_pldo_lv, "vdd-l8-l9-l10-l11-l12-l13-l14"), + RPMH_VREG("ldo13", LDO, 13, &pmic4_pldo_lv, "vdd-l8-l9-l10-l11-l12-l13-l14"), + RPMH_VREG("ldo14", LDO, 14, &pmic4_pldo_lv, "vdd-l8-l9-l10-l11-l12-l13-l14"), + RPMH_VREG("ldo15", LDO, 15, &pmic4_pldo, "vdd-l15-l16-l17-l18-l19"), + RPMH_VREG("ldo16", LDO, 16, &pmic4_pldo, "vdd-l15-l16-l17-l18-l19"), + RPMH_VREG("ldo17", LDO, 17, &pmic4_pldo, "vdd-l15-l16-l17-l18-l19"), + RPMH_VREG("ldo18", LDO, 18, &pmic4_pldo, "vdd-l15-l16-l17-l18-l19"), + RPMH_VREG("ldo19", LDO, 19, &pmic4_pldo, "vdd-l15-l16-l17-l18-l19"), {} }; static const struct rpmh_vreg_init_data pm660l_vreg_data[] = { - RPMH_VREG("smps1", "smp%s1", &pmic4_ftsmps426, "vdd-s1"), - RPMH_VREG("smps2", "smp%s2", &pmic4_ftsmps426, "vdd-s2"), - RPMH_VREG("smps3", "smp%s3", &pmic4_ftsmps426, "vdd-s3-s4"), - RPMH_VREG("smps5", "smp%s5", &pmic4_ftsmps426, "vdd-s5"), - RPMH_VREG("ldo1", "ldo%s1", &pmic4_nldo, "vdd-l1-l9-l10"), - RPMH_VREG("ldo2", "ldo%s2", &pmic4_pldo, "vdd-l2"), - RPMH_VREG("ldo3", "ldo%s3", &pmic4_pldo, "vdd-l3-l5-l7-l8"), - RPMH_VREG("ldo4", "ldo%s4", &pmic4_pldo, "vdd-l4-l6"), - RPMH_VREG("ldo5", "ldo%s5", &pmic4_pldo, "vdd-l3-l5-l7-l8"), - RPMH_VREG("ldo6", "ldo%s6", &pmic4_pldo, "vdd-l4-l6"), - RPMH_VREG("ldo7", "ldo%s7", &pmic4_pldo, "vdd-l3-l5-l7-l8"), - RPMH_VREG("ldo8", "ldo%s8", &pmic4_pldo, "vdd-l3-l5-l7-l8"), - RPMH_VREG("bob", "bob%s1", &pmic4_bob, "vdd-bob"), + RPMH_VREG("smps1", SMPS, 1, &pmic4_ftsmps426, "vdd-s1"), + RPMH_VREG("smps2", SMPS, 2, &pmic4_ftsmps426, "vdd-s2"), + RPMH_VREG("smps3", SMPS, 3, &pmic4_ftsmps426, "vdd-s3-s4"), + RPMH_VREG("smps5", SMPS, 5, &pmic4_ftsmps426, "vdd-s5"), + RPMH_VREG("ldo1", LDO, 1, &pmic4_nldo, "vdd-l1-l9-l10"), + RPMH_VREG("ldo2", LDO, 2, &pmic4_pldo, "vdd-l2"), + RPMH_VREG("ldo3", LDO, 3, &pmic4_pldo, "vdd-l3-l5-l7-l8"), + RPMH_VREG("ldo4", LDO, 4, &pmic4_pldo, "vdd-l4-l6"), + RPMH_VREG("ldo5", LDO, 5, &pmic4_pldo, "vdd-l3-l5-l7-l8"), + RPMH_VREG("ldo6", LDO, 6, &pmic4_pldo, "vdd-l4-l6"), + RPMH_VREG("ldo7", LDO, 7, &pmic4_pldo, "vdd-l3-l5-l7-l8"), + RPMH_VREG("ldo8", LDO, 8, &pmic4_pldo, "vdd-l3-l5-l7-l8"), + RPMH_VREG("bob", BOB, 1, &pmic4_bob, "vdd-bob"), {} }; @@ -1690,6 +1910,22 @@ static const struct of_device_id __maybe_unused rpmh_regulator_match_table[] = { .data = pmc8380_vreg_data, }, { + .compatible = "qcom,pmcx0102-rpmh-regulators", + .data = pmcx0102_vreg_data, + }, + { + .compatible = "qcom,pmh0101-rpmh-regulators", + .data = pmh0101_vreg_data, + }, + { + .compatible = "qcom,pmh0104-rpmh-regulators", + .data = pmh0104_vreg_data, + }, + { + .compatible = "qcom,pmh0110-rpmh-regulators", + .data = pmh0110_vreg_data, + }, + { .compatible = "qcom,pmm8155au-rpmh-regulators", .data = pmm8155au_vreg_data, }, @@ -1726,6 +1962,10 @@ static const struct of_device_id __maybe_unused rpmh_regulator_match_table[] = { .data = pmr735b_vreg_data, }, { + .compatible = "qcom,pmr735d-rpmh-regulators", + .data = pmr735d_vreg_data, + }, + { .compatible = "qcom,pm660-rpmh-regulators", .data = pm660_vreg_data, }, diff --git a/drivers/regulator/renesas-usb-vbus-regulator.c b/drivers/regulator/renesas-usb-vbus-regulator.c index dec7cac5e8d5..9ba791bd72ec 100644 --- a/drivers/regulator/renesas-usb-vbus-regulator.c +++ b/drivers/regulator/renesas-usb-vbus-regulator.c @@ -7,12 +7,10 @@ #include <linux/module.h> #include <linux/err.h> -#include <linux/kernel.h> #include <linux/of.h> #include <linux/platform_device.h> #include <linux/regmap.h> #include <linux/regulator/driver.h> -#include <linux/regulator/of_regulator.h> static const struct regulator_ops rzg2l_usb_vbus_reg_ops = { .enable = regulator_enable_regmap, diff --git a/drivers/regulator/rtq2208-regulator.c b/drivers/regulator/rtq2208-regulator.c index 9cde7181b0f0..f669a562f036 100644 --- a/drivers/regulator/rtq2208-regulator.c +++ b/drivers/regulator/rtq2208-regulator.c @@ -53,7 +53,7 @@ #define RTQ2208_MASK_BUCKPH_GROUP1 GENMASK(6, 4) #define RTQ2208_MASK_BUCKPH_GROUP2 GENMASK(2, 0) #define RTQ2208_MASK_LDO2_OPT0 BIT(7) -#define RTQ2208_MASK_LDO2_OPT1 BIT(6) +#define RTQ2208_MASK_LDO2_OPT1 BIT(7) #define RTQ2208_MASK_LDO1_FIXED BIT(6) /* Size */ @@ -543,14 +543,14 @@ static int rtq2208_regulator_check(struct device *dev, int *num, int *regulator_ switch (FIELD_GET(RTQ2208_MASK_BUCKPH_GROUP2, buck_phase)) { case 2: - rtq2208_used_table[RTQ2208_BUCK_F] = true; + rtq2208_used_table[RTQ2208_BUCK_H] = true; fallthrough; case 1: rtq2208_used_table[RTQ2208_BUCK_E] = true; fallthrough; case 0: case 3: - rtq2208_used_table[RTQ2208_BUCK_H] = true; + rtq2208_used_table[RTQ2208_BUCK_F] = true; fallthrough; default: rtq2208_used_table[RTQ2208_BUCK_G] = true; diff --git a/drivers/regulator/sy7636a-regulator.c b/drivers/regulator/sy7636a-regulator.c index 27e3d939b7bb..551647bc1052 100644 --- a/drivers/regulator/sy7636a-regulator.c +++ b/drivers/regulator/sy7636a-regulator.c @@ -12,6 +12,7 @@ #include <linux/mfd/sy7636a.h> #include <linux/module.h> #include <linux/platform_device.h> +#include <linux/regulator/consumer.h> #include <linux/regulator/driver.h> #include <linux/regulator/machine.h> #include <linux/regmap.h> @@ -19,6 +20,8 @@ struct sy7636a_data { struct regmap *regmap; struct gpio_desc *pgood_gpio; + struct gpio_desc *en_gpio; + struct gpio_desc *vcom_en_gpio; }; static int sy7636a_get_vcom_voltage_op(struct regulator_dev *rdev) @@ -98,6 +101,30 @@ static int sy7636a_regulator_probe(struct platform_device *pdev) data->regmap = regmap; data->pgood_gpio = gdp; + ret = devm_regulator_get_enable_optional(&pdev->dev, "vin"); + if (ret) + return dev_err_probe(&pdev->dev, ret, + "failed to get vin regulator\n"); + + data->en_gpio = devm_gpiod_get_optional(&pdev->dev, "enable", + GPIOD_OUT_HIGH); + if (IS_ERR(data->en_gpio)) + return dev_err_probe(&pdev->dev, + PTR_ERR(data->en_gpio), + "failed to get en gpio\n"); + + /* Let VCOM just follow the default power on sequence */ + data->vcom_en_gpio = devm_gpiod_get_optional(&pdev->dev, + "vcom-en", GPIOD_OUT_LOW); + if (IS_ERR(data->vcom_en_gpio)) + return dev_err_probe(&pdev->dev, + PTR_ERR(data->vcom_en_gpio), + "failed to get vcom-en gpio\n"); + + /* if chip was not enabled, give it time to wake up */ + if (data->en_gpio) + usleep_range(2500, 4000); + platform_set_drvdata(pdev, data); ret = regmap_write(regmap, SY7636A_REG_POWER_ON_DELAY_TIME, 0x0); |
