From 6a47b4da551a762217215aeeda22e46469c5868a Mon Sep 17 00:00:00 2001 From: Matti Vaittinen Date: Thu, 14 Feb 2019 11:38:05 +0200 Subject: [PATCH] regulator: add regulator_desc_list_voltage_linear_range Add regulator_desc_list_voltage_linear_range which can be used by drivers for getting the voltages before regulator is registered. This may be useful for drivers which need to fetch the voltage selectors at device-tree parsing callback. Signed-off-by: Matti Vaittinen Acked-by: Mark Brown Tested-by: Angus Ainslie Reviewed-by: Angus Ainslie Signed-off-by: Mark Brown --- drivers/regulator/helpers.c | 61 +++++++++++++++++++++----------- include/linux/regulator/driver.h | 6 ++++ 2 files changed, 46 insertions(+), 21 deletions(-) diff --git a/drivers/regulator/helpers.c b/drivers/regulator/helpers.c index 5686a1335bd3..68ac6017ef28 100644 --- a/drivers/regulator/helpers.c +++ b/drivers/regulator/helpers.c @@ -593,6 +593,45 @@ int regulator_list_voltage_pickable_linear_range(struct regulator_dev *rdev, } EXPORT_SYMBOL_GPL(regulator_list_voltage_pickable_linear_range); +/** + * regulator_desc_list_voltage_linear_range - List voltages for linear ranges + * + * @desc: Regulator desc for regulator which volatges are to be listed + * @selector: Selector to convert into a voltage + * + * Regulators with a series of simple linear mappings between voltages + * and selectors who have set linear_ranges in the regulator descriptor + * can use this function prior regulator registration to list voltages. + * This is useful when voltages need to be listed during device-tree + * parsing. + */ +int regulator_desc_list_voltage_linear_range(const struct regulator_desc *desc, + unsigned int selector) +{ + const struct regulator_linear_range *range; + int i; + + if (!desc->n_linear_ranges) { + BUG_ON(!desc->n_linear_ranges); + return -EINVAL; + } + + for (i = 0; i < desc->n_linear_ranges; i++) { + range = &desc->linear_ranges[i]; + + if (!(selector >= range->min_sel && + selector <= range->max_sel)) + continue; + + selector -= range->min_sel; + + return range->min_uV + (range->uV_step * selector); + } + + return -EINVAL; +} +EXPORT_SYMBOL_GPL(regulator_desc_list_voltage_linear_range); + /** * regulator_list_voltage_linear_range - List voltages for linear ranges * @@ -606,27 +645,7 @@ EXPORT_SYMBOL_GPL(regulator_list_voltage_pickable_linear_range); int regulator_list_voltage_linear_range(struct regulator_dev *rdev, unsigned int selector) { - const struct regulator_linear_range *range; - int i; - - if (!rdev->desc->n_linear_ranges) { - BUG_ON(!rdev->desc->n_linear_ranges); - return -EINVAL; - } - - for (i = 0; i < rdev->desc->n_linear_ranges; i++) { - range = &rdev->desc->linear_ranges[i]; - - if (!(selector >= range->min_sel && - selector <= range->max_sel)) - continue; - - selector -= range->min_sel; - - return range->min_uV + (range->uV_step * selector); - } - - return -EINVAL; + return regulator_desc_list_voltage_linear_range(rdev->desc, selector); } EXPORT_SYMBOL_GPL(regulator_list_voltage_linear_range); diff --git a/include/linux/regulator/driver.h b/include/linux/regulator/driver.h index 7f8345bff4e1..05efe2b057c1 100644 --- a/include/linux/regulator/driver.h +++ b/include/linux/regulator/driver.h @@ -539,4 +539,10 @@ void *regulator_get_init_drvdata(struct regulator_init_data *reg_init_data); void regulator_lock(struct regulator_dev *rdev); void regulator_unlock(struct regulator_dev *rdev); +/* + * Helper functions intended to be used by regulator drivers prior registering + * their regulators. + */ +int regulator_desc_list_voltage_linear_range(const struct regulator_desc *desc, + unsigned int selector); #endif