Merge remote-tracking branch 'regulator/topic/alias' into regulator-next
authorMark Brown <broonie@linaro.org>
Thu, 24 Oct 2013 10:11:32 +0000 (11:11 +0100)
committerMark Brown <broonie@linaro.org>
Thu, 24 Oct 2013 10:11:32 +0000 (11:11 +0100)
55 files changed:
Documentation/driver-model/devres.txt
arch/arm/mach-s3c64xx/mach-crag6410.c
drivers/mfd/arizona-core.c
drivers/mfd/mfd-core.c
drivers/regulator/88pm8607.c
drivers/regulator/Makefile
drivers/regulator/aat2870-regulator.c
drivers/regulator/ad5398.c
drivers/regulator/anatop-regulator.c
drivers/regulator/arizona-ldo1.c
drivers/regulator/arizona-micsupp.c
drivers/regulator/as3711-regulator.c
drivers/regulator/core.c
drivers/regulator/da903x.c
drivers/regulator/da9052-regulator.c
drivers/regulator/da9055-regulator.c
drivers/regulator/devres.c [new file with mode: 0644]
drivers/regulator/fan53555.c
drivers/regulator/internal.h [new file with mode: 0644]
drivers/regulator/isl6271a-regulator.c
drivers/regulator/max1586.c
drivers/regulator/max77686.c
drivers/regulator/max77693.c
drivers/regulator/max8649.c
drivers/regulator/max8660.c
drivers/regulator/max8907-regulator.c
drivers/regulator/max8973-regulator.c
drivers/regulator/max8997.c
drivers/regulator/max8998.c
drivers/regulator/mc13783-regulator.c
drivers/regulator/mc13892-regulator.c
drivers/regulator/palmas-regulator.c
drivers/regulator/rc5t583-regulator.c
drivers/regulator/s2mps11.c
drivers/regulator/s5m8767.c
drivers/regulator/ti-abb-regulator.c
drivers/regulator/tps51632-regulator.c
drivers/regulator/tps62360-regulator.c
drivers/regulator/tps65023-regulator.c
drivers/regulator/tps6507x-regulator.c
drivers/regulator/tps65090-regulator.c
drivers/regulator/tps65217-regulator.c
drivers/regulator/tps6586x-regulator.c
drivers/regulator/tps65910-regulator.c
drivers/regulator/tps65912-regulator.c
drivers/regulator/tps80031-regulator.c
drivers/regulator/wm831x-dcdc.c
drivers/regulator/wm831x-isink.c
drivers/regulator/wm831x-ldo.c
drivers/regulator/wm8350-regulator.c
drivers/regulator/wm8400-regulator.c
drivers/regulator/wm8994-regulator.c
include/linux/mfd/core.h
include/linux/regulator/consumer.h
include/linux/regulator/driver.h

index fcb34a5..3d9c2a7 100644 (file)
@@ -283,6 +283,7 @@ REGULATOR
   devm_regulator_get()
   devm_regulator_put()
   devm_regulator_bulk_get()
+  devm_regulator_register()
 
 CLOCK
   devm_clk_get()
index eb8e5a1..f27ca3b 100644 (file)
@@ -310,10 +310,6 @@ static struct regulator_consumer_supply wallvdd_consumers[] = {
 
        REGULATOR_SUPPLY("SPKVDDL", "spi0.1"),
        REGULATOR_SUPPLY("SPKVDDR", "spi0.1"),
-       REGULATOR_SUPPLY("SPKVDDL", "wm5102-codec"),
-       REGULATOR_SUPPLY("SPKVDDR", "wm5102-codec"),
-       REGULATOR_SUPPLY("SPKVDDL", "wm5110-codec"),
-       REGULATOR_SUPPLY("SPKVDDR", "wm5110-codec"),
 
        REGULATOR_SUPPLY("DC1VDD", "0-0034"),
        REGULATOR_SUPPLY("DC2VDD", "0-0034"),
@@ -653,14 +649,6 @@ static struct regulator_consumer_supply pvdd_1v8_consumers[] = {
        REGULATOR_SUPPLY("DBVDD3", "spi0.1"),
        REGULATOR_SUPPLY("LDOVDD", "spi0.1"),
        REGULATOR_SUPPLY("CPVDD", "spi0.1"),
-
-       REGULATOR_SUPPLY("DBVDD2", "wm5102-codec"),
-       REGULATOR_SUPPLY("DBVDD3", "wm5102-codec"),
-       REGULATOR_SUPPLY("CPVDD", "wm5102-codec"),
-
-       REGULATOR_SUPPLY("DBVDD2", "wm5110-codec"),
-       REGULATOR_SUPPLY("DBVDD3", "wm5110-codec"),
-       REGULATOR_SUPPLY("CPVDD", "wm5110-codec"),
 };
 
 static struct regulator_init_data pvdd_1v8 = {
index 5ac3aa4..022b186 100644 (file)
@@ -569,13 +569,25 @@ static struct mfd_cell early_devs[] = {
        { .name = "arizona-ldo1" },
 };
 
+static const char *wm5102_supplies[] = {
+       "DBVDD2",
+       "DBVDD3",
+       "CPVDD",
+       "SPKVDDL",
+       "SPKVDDR",
+};
+
 static struct mfd_cell wm5102_devs[] = {
        { .name = "arizona-micsupp" },
        { .name = "arizona-extcon" },
        { .name = "arizona-gpio" },
        { .name = "arizona-haptics" },
        { .name = "arizona-pwm" },
-       { .name = "wm5102-codec" },
+       {
+               .name = "wm5102-codec",
+               .parent_supplies = wm5102_supplies,
+               .num_parent_supplies = ARRAY_SIZE(wm5102_supplies),
+       },
 };
 
 static struct mfd_cell wm5110_devs[] = {
@@ -584,7 +596,17 @@ static struct mfd_cell wm5110_devs[] = {
        { .name = "arizona-gpio" },
        { .name = "arizona-haptics" },
        { .name = "arizona-pwm" },
-       { .name = "wm5110-codec" },
+       {
+               .name = "wm5110-codec",
+               .parent_supplies = wm5102_supplies,
+               .num_parent_supplies = ARRAY_SIZE(wm5102_supplies),
+       },
+};
+
+static const char *wm8997_supplies[] = {
+       "DBVDD2",
+       "CPVDD",
+       "SPKVDD",
 };
 
 static struct mfd_cell wm8997_devs[] = {
@@ -593,7 +615,11 @@ static struct mfd_cell wm8997_devs[] = {
        { .name = "arizona-gpio" },
        { .name = "arizona-haptics" },
        { .name = "arizona-pwm" },
-       { .name = "wm8997-codec" },
+       {
+               .name = "wm8997-codec",
+               .parent_supplies = wm8997_supplies,
+               .num_parent_supplies = ARRAY_SIZE(wm8997_supplies),
+       },
 };
 
 int arizona_dev_init(struct arizona *arizona)
index f421586..adc8ea3 100644 (file)
@@ -20,6 +20,7 @@
 #include <linux/module.h>
 #include <linux/irqdomain.h>
 #include <linux/of.h>
+#include <linux/regulator/consumer.h>
 
 static struct device_type mfd_dev_type = {
        .name   = "mfd_device",
@@ -99,6 +100,13 @@ static int mfd_add_device(struct device *parent, int id,
        pdev->dev.dma_mask = parent->dma_mask;
        pdev->dev.dma_parms = parent->dma_parms;
 
+       ret = devm_regulator_bulk_register_supply_alias(
+                       &pdev->dev, cell->parent_supplies,
+                       parent, cell->parent_supplies,
+                       cell->num_parent_supplies);
+       if (ret < 0)
+               goto fail_res;
+
        if (parent->of_node && cell->of_compatible) {
                for_each_child_of_node(parent->of_node, np) {
                        if (of_device_is_compatible(np, cell->of_compatible)) {
@@ -112,12 +120,12 @@ static int mfd_add_device(struct device *parent, int id,
                ret = platform_device_add_data(pdev,
                                        cell->platform_data, cell->pdata_size);
                if (ret)
-                       goto fail_res;
+                       goto fail_alias;
        }
 
        ret = mfd_platform_add_cell(pdev, cell);
        if (ret)
-               goto fail_res;
+               goto fail_alias;
 
        for (r = 0; r < cell->num_resources; r++) {
                res[r].name = cell->resources[r].name;
@@ -152,17 +160,17 @@ static int mfd_add_device(struct device *parent, int id,
                if (!cell->ignore_resource_conflicts) {
                        ret = acpi_check_resource_conflict(&res[r]);
                        if (ret)
-                               goto fail_res;
+                               goto fail_alias;
                }
        }
 
        ret = platform_device_add_resources(pdev, res, cell->num_resources);
        if (ret)
-               goto fail_res;
+               goto fail_alias;
 
        ret = platform_device_add(pdev);
        if (ret)
-               goto fail_res;
+               goto fail_alias;
 
        if (cell->pm_runtime_no_callbacks)
                pm_runtime_no_callbacks(&pdev->dev);
@@ -171,6 +179,10 @@ static int mfd_add_device(struct device *parent, int id,
 
        return 0;
 
+fail_alias:
+       devm_regulator_bulk_unregister_supply_alias(&pdev->dev,
+                                                   cell->parent_supplies,
+                                                   cell->num_parent_supplies);
 fail_res:
        kfree(res);
 fail_device:
index 7023097..f704d83 100644 (file)
@@ -391,7 +391,8 @@ static int pm8607_regulator_probe(struct platform_device *pdev)
        else
                config.regmap = chip->regmap_companion;
 
-       info->regulator = regulator_register(&info->desc, &config);
+       info->regulator = devm_regulator_register(&pdev->dev, &info->desc,
+                                                 &config);
        if (IS_ERR(info->regulator)) {
                dev_err(&pdev->dev, "failed to register regulator %s\n",
                        info->desc.name);
@@ -402,14 +403,6 @@ static int pm8607_regulator_probe(struct platform_device *pdev)
        return 0;
 }
 
-static int pm8607_regulator_remove(struct platform_device *pdev)
-{
-       struct pm8607_regulator_info *info = platform_get_drvdata(pdev);
-
-       regulator_unregister(info->regulator);
-       return 0;
-}
-
 static struct platform_device_id pm8607_regulator_driver_ids[] = {
        {
                .name   = "88pm860x-regulator",
@@ -428,7 +421,6 @@ static struct platform_driver pm8607_regulator_driver = {
                .owner  = THIS_MODULE,
        },
        .probe          = pm8607_regulator_probe,
-       .remove         = pm8607_regulator_remove,
        .id_table       = pm8607_regulator_driver_ids,
 };
 
index 185cce2..69db4c8 100644 (file)
@@ -3,7 +3,7 @@
 #
 
 
-obj-$(CONFIG_REGULATOR) += core.o dummy.o fixed-helper.o helpers.o
+obj-$(CONFIG_REGULATOR) += core.o dummy.o fixed-helper.o helpers.o devres.o
 obj-$(CONFIG_OF) += of_regulator.o
 obj-$(CONFIG_REGULATOR_FIXED_VOLTAGE) += fixed.o
 obj-$(CONFIG_REGULATOR_VIRTUAL_CONSUMER) += virtual.o
index 881159d..f70a9bf 100644 (file)
@@ -176,7 +176,7 @@ static int aat2870_regulator_probe(struct platform_device *pdev)
        config.driver_data = ri;
        config.init_data = dev_get_platdata(&pdev->dev);
 
-       rdev = regulator_register(&ri->desc, &config);
+       rdev = devm_regulator_register(&pdev->dev, &ri->desc, &config);
        if (IS_ERR(rdev)) {
                dev_err(&pdev->dev, "Failed to register regulator %s\n",
                        ri->desc.name);
@@ -187,21 +187,12 @@ static int aat2870_regulator_probe(struct platform_device *pdev)
        return 0;
 }
 
-static int aat2870_regulator_remove(struct platform_device *pdev)
-{
-       struct regulator_dev *rdev = platform_get_drvdata(pdev);
-
-       regulator_unregister(rdev);
-       return 0;
-}
-
 static struct platform_driver aat2870_regulator_driver = {
        .driver = {
                .name   = "aat2870-regulator",
                .owner  = THIS_MODULE,
        },
        .probe  = aat2870_regulator_probe,
-       .remove = aat2870_regulator_remove,
 };
 
 static int __init aat2870_regulator_init(void)
index b2b203c..48016a0 100644 (file)
@@ -219,7 +219,6 @@ static int ad5398_probe(struct i2c_client *client,
        struct ad5398_chip_info *chip;
        const struct ad5398_current_data_format *df =
                        (struct ad5398_current_data_format *)id->driver_data;
-       int ret;
 
        if (!init_data)
                return -EINVAL;
@@ -240,33 +239,21 @@ static int ad5398_probe(struct i2c_client *client,
        chip->current_offset = df->current_offset;
        chip->current_mask = (chip->current_level - 1) << chip->current_offset;
 
-       chip->rdev = regulator_register(&ad5398_reg, &config);
+       chip->rdev = devm_regulator_register(&client->dev, &ad5398_reg,
+                                            &config);
        if (IS_ERR(chip->rdev)) {
-               ret = PTR_ERR(chip->rdev);
                dev_err(&client->dev, "failed to register %s %s\n",
                        id->name, ad5398_reg.name);
-               goto err;
+               return PTR_ERR(chip->rdev);
        }
 
        i2c_set_clientdata(client, chip);
        dev_dbg(&client->dev, "%s regulator driver is registered.\n", id->name);
        return 0;
-
-err:
-       return ret;
-}
-
-static int ad5398_remove(struct i2c_client *client)
-{
-       struct ad5398_chip_info *chip = i2c_get_clientdata(client);
-
-       regulator_unregister(chip->rdev);
-       return 0;
 }
 
 static struct i2c_driver ad5398_driver = {
        .probe = ad5398_probe,
-       .remove = ad5398_remove,
        .driver         = {
                .name   = "ad5398",
        },
index 0d4a8cc..e42bfd1 100644 (file)
@@ -200,7 +200,7 @@ static int anatop_regulator_probe(struct platform_device *pdev)
        config.regmap = sreg->anatop;
 
        /* register regulator */
-       rdev = regulator_register(rdesc, &config);
+       rdev = devm_regulator_register(dev, rdesc, &config);
        if (IS_ERR(rdev)) {
                dev_err(dev, "failed to register %s\n",
                        rdesc->name);
@@ -223,7 +223,6 @@ static int anatop_regulator_remove(struct platform_device *pdev)
        struct anatop_regulator *sreg = rdev_get_drvdata(rdev);
        const char *name = sreg->name;
 
-       regulator_unregister(rdev);
        kfree(name);
 
        return 0;
index 81d8681..4f6c205 100644 (file)
@@ -226,7 +226,7 @@ static int arizona_ldo1_probe(struct platform_device *pdev)
        else
                config.init_data = &ldo1->init_data;
 
-       ldo1->regulator = regulator_register(desc, &config);
+       ldo1->regulator = devm_regulator_register(&pdev->dev, desc, &config);
        if (IS_ERR(ldo1->regulator)) {
                ret = PTR_ERR(ldo1->regulator);
                dev_err(arizona->dev, "Failed to register LDO1 supply: %d\n",
@@ -239,18 +239,8 @@ static int arizona_ldo1_probe(struct platform_device *pdev)
        return 0;
 }
 
-static int arizona_ldo1_remove(struct platform_device *pdev)
-{
-       struct arizona_ldo1 *ldo1 = platform_get_drvdata(pdev);
-
-       regulator_unregister(ldo1->regulator);
-
-       return 0;
-}
-
 static struct platform_driver arizona_ldo1_driver = {
        .probe = arizona_ldo1_probe,
-       .remove = arizona_ldo1_remove,
        .driver         = {
                .name   = "arizona-ldo1",
                .owner  = THIS_MODULE,
index e87536b..724706a 100644 (file)
@@ -225,7 +225,9 @@ static int arizona_micsupp_probe(struct platform_device *pdev)
        regmap_update_bits(arizona->regmap, ARIZONA_MIC_CHARGE_PUMP_1,
                           ARIZONA_CPMIC_BYPASS, 0);
 
-       micsupp->regulator = regulator_register(&arizona_micsupp, &config);
+       micsupp->regulator = devm_regulator_register(&pdev->dev,
+                                                    &arizona_micsupp,
+                                                    &config);
        if (IS_ERR(micsupp->regulator)) {
                ret = PTR_ERR(micsupp->regulator);
                dev_err(arizona->dev, "Failed to register mic supply: %d\n",
@@ -238,18 +240,8 @@ static int arizona_micsupp_probe(struct platform_device *pdev)
        return 0;
 }
 
-static int arizona_micsupp_remove(struct platform_device *pdev)
-{
-       struct arizona_micsupp *micsupp = platform_get_drvdata(pdev);
-
-       regulator_unregister(micsupp->regulator);
-
-       return 0;
-}
-
 static struct platform_driver arizona_micsupp_driver = {
        .probe = arizona_micsupp_probe,
-       .remove = arizona_micsupp_remove,
        .driver         = {
                .name   = "arizona-micsupp",
                .owner  = THIS_MODULE,
index 8406cd7..fb27e6c 100644 (file)
@@ -273,33 +273,16 @@ static int as3711_regulator_probe(struct platform_device *pdev)
                config.regmap = as3711->regmap;
                config.of_node = of_node[id];
 
-               rdev = regulator_register(&ri->desc, &config);
+               rdev = devm_regulator_register(&pdev->dev, &ri->desc, &config);
                if (IS_ERR(rdev)) {
                        dev_err(&pdev->dev, "Failed to register regulator %s\n",
                                ri->desc.name);
-                       ret = PTR_ERR(rdev);
-                       goto eregreg;
+                       return PTR_ERR(rdev);
                }
                reg->rdev = rdev;
        }
        platform_set_drvdata(pdev, regs);
        return 0;
-
-eregreg:
-       while (--id >= 0)
-               regulator_unregister(regs[id].rdev);
-
-       return ret;
-}
-
-static int as3711_regulator_remove(struct platform_device *pdev)
-{
-       struct as3711_regulator *regs = platform_get_drvdata(pdev);
-       int id;
-
-       for (id = 0; id < AS3711_REGULATOR_NUM; ++id)
-               regulator_unregister(regs[id].rdev);
-       return 0;
 }
 
 static struct platform_driver as3711_regulator_driver = {
@@ -308,7 +291,6 @@ static struct platform_driver as3711_regulator_driver = {
                .owner  = THIS_MODULE,
        },
        .probe          = as3711_regulator_probe,
-       .remove         = as3711_regulator_remove,
 };
 
 static int __init as3711_regulator_init(void)
index a01b8b3..16427de 100644 (file)
@@ -36,6 +36,7 @@
 #include <trace/events/regulator.h>
 
 #include "dummy.h"
+#include "internal.h"
 
 #define rdev_crit(rdev, fmt, ...)                                      \
        pr_crit("%s: " fmt, rdev_get_name(rdev), ##__VA_ARGS__)
@@ -52,6 +53,7 @@ static DEFINE_MUTEX(regulator_list_mutex);
 static LIST_HEAD(regulator_list);
 static LIST_HEAD(regulator_map_list);
 static LIST_HEAD(regulator_ena_gpio_list);
+static LIST_HEAD(regulator_supply_alias_list);
 static bool has_full_constraints;
 static bool board_wants_dummy_regulator;
 
@@ -83,22 +85,16 @@ struct regulator_enable_gpio {
 };
 
 /*
- * struct regulator
+ * struct regulator_supply_alias
  *
- * One for each consumer device.
+ * Used to map lookups for a supply onto an alternative device.
  */
-struct regulator {
-       struct device *dev;
+struct regulator_supply_alias {
        struct list_head list;
-       unsigned int always_on:1;
-       unsigned int bypass:1;
-       int uA_load;
-       int min_uV;
-       int max_uV;
-       char *supply_name;
-       struct device_attribute dev_attr;
-       struct regulator_dev *rdev;
-       struct dentry *debugfs;
+       struct device *src_dev;
+       const char *src_supply;
+       struct device *alias_dev;
+       const char *alias_supply;
 };
 
 static int _regulator_is_enabled(struct regulator_dev *rdev);
@@ -1191,6 +1187,32 @@ static int _regulator_get_enable_time(struct regulator_dev *rdev)
        return rdev->desc->ops->enable_time(rdev);
 }
 
+static struct regulator_supply_alias *regulator_find_supply_alias(
+               struct device *dev, const char *supply)
+{
+       struct regulator_supply_alias *map;
+
+       list_for_each_entry(map, &regulator_supply_alias_list, list)
+               if (map->src_dev == dev && strcmp(map->src_supply, supply) == 0)
+                       return map;
+
+       return NULL;
+}
+
+static void regulator_supply_alias(struct device **dev, const char **supply)
+{
+       struct regulator_supply_alias *map;
+
+       map = regulator_find_supply_alias(*dev, *supply);
+       if (map) {
+               dev_dbg(*dev, "Mapping supply %s to %s,%s\n",
+                               *supply, map->alias_supply,
+                               dev_name(map->alias_dev));
+               *dev = map->alias_dev;
+               *supply = map->alias_supply;
+       }
+}
+
 static struct regulator_dev *regulator_dev_lookup(struct device *dev,
                                                  const char *supply,
                                                  int *ret)
@@ -1200,6 +1222,8 @@ static struct regulator_dev *regulator_dev_lookup(struct device *dev,
        struct regulator_map *map;
        const char *devname = NULL;
 
+       regulator_supply_alias(&dev, &supply);
+
        /* first do a dt based lookup */
        if (dev && dev->of_node) {
                node = of_get_regulator(dev, supply);
@@ -1353,40 +1377,6 @@ struct regulator *regulator_get(struct device *dev, const char *id)
 }
 EXPORT_SYMBOL_GPL(regulator_get);
 
-static void devm_regulator_release(struct device *dev, void *res)
-{
-       regulator_put(*(struct regulator **)res);
-}
-
-/**
- * devm_regulator_get - Resource managed regulator_get()
- * @dev: device for regulator "consumer"
- * @id: Supply name or regulator ID.
- *
- * Managed regulator_get(). Regulators returned from this function are
- * automatically regulator_put() on driver detach. See regulator_get() for more
- * information.
- */
-struct regulator *devm_regulator_get(struct device *dev, const char *id)
-{
-       struct regulator **ptr, *regulator;
-
-       ptr = devres_alloc(devm_regulator_release, sizeof(*ptr), GFP_KERNEL);
-       if (!ptr)
-               return ERR_PTR(-ENOMEM);
-
-       regulator = regulator_get(dev, id);
-       if (!IS_ERR(regulator)) {
-               *ptr = regulator;
-               devres_add(dev, ptr);
-       } else {
-               devres_free(ptr);
-       }
-
-       return regulator;
-}
-EXPORT_SYMBOL_GPL(devm_regulator_get);
-
 /**
  * regulator_get_exclusive - obtain exclusive access to a regulator.
  * @dev: device for regulator "consumer"
@@ -1443,36 +1433,6 @@ struct regulator *regulator_get_optional(struct device *dev, const char *id)
 }
 EXPORT_SYMBOL_GPL(regulator_get_optional);
 
-/**
- * devm_regulator_get_optional - Resource managed regulator_get_optional()
- * @dev: device for regulator "consumer"
- * @id: Supply name or regulator ID.
- *
- * Managed regulator_get_optional(). Regulators returned from this
- * function are automatically regulator_put() on driver detach. See
- * regulator_get_optional() for more information.
- */
-struct regulator *devm_regulator_get_optional(struct device *dev,
-                                             const char *id)
-{
-       struct regulator **ptr, *regulator;
-
-       ptr = devres_alloc(devm_regulator_release, sizeof(*ptr), GFP_KERNEL);
-       if (!ptr)
-               return ERR_PTR(-ENOMEM);
-
-       regulator = regulator_get_optional(dev, id);
-       if (!IS_ERR(regulator)) {
-               *ptr = regulator;
-               devres_add(dev, ptr);
-       } else {
-               devres_free(ptr);
-       }
-
-       return regulator;
-}
-EXPORT_SYMBOL_GPL(devm_regulator_get_optional);
-
 /* Locks held by regulator_put() */
 static void _regulator_put(struct regulator *regulator)
 {
@@ -1499,36 +1459,6 @@ static void _regulator_put(struct regulator *regulator)
 }
 
 /**
- * devm_regulator_get_exclusive - Resource managed regulator_get_exclusive()
- * @dev: device for regulator "consumer"
- * @id: Supply name or regulator ID.
- *
- * Managed regulator_get_exclusive(). Regulators returned from this function
- * are automatically regulator_put() on driver detach. See regulator_get() for
- * more information.
- */
-struct regulator *devm_regulator_get_exclusive(struct device *dev,
-                                              const char *id)
-{
-       struct regulator **ptr, *regulator;
-
-       ptr = devres_alloc(devm_regulator_release, sizeof(*ptr), GFP_KERNEL);
-       if (!ptr)
-               return ERR_PTR(-ENOMEM);
-
-       regulator = _regulator_get(dev, id, 1);
-       if (!IS_ERR(regulator)) {
-               *ptr = regulator;
-               devres_add(dev, ptr);
-       } else {
-               devres_free(ptr);
-       }
-
-       return regulator;
-}
-EXPORT_SYMBOL_GPL(devm_regulator_get_exclusive);
-
-/**
  * regulator_put - "free" the regulator source
  * @regulator: regulator source
  *
@@ -1544,34 +1474,133 @@ void regulator_put(struct regulator *regulator)
 }
 EXPORT_SYMBOL_GPL(regulator_put);
 
-static int devm_regulator_match(struct device *dev, void *res, void *data)
+/**
+ * regulator_register_supply_alias - Provide device alias for supply lookup
+ *
+ * @dev: device that will be given as the regulator "consumer"
+ * @id: Supply name or regulator ID
+ * @alias_dev: device that should be used to lookup the supply
+ * @alias_id: Supply name or regulator ID that should be used to lookup the
+ * supply
+ *
+ * All lookups for id on dev will instead be conducted for alias_id on
+ * alias_dev.
+ */
+int regulator_register_supply_alias(struct device *dev, const char *id,
+                                   struct device *alias_dev,
+                                   const char *alias_id)
 {
-       struct regulator **r = res;
-       if (!r || !*r) {
-               WARN_ON(!r || !*r);
-               return 0;
+       struct regulator_supply_alias *map;
+
+       map = regulator_find_supply_alias(dev, id);
+       if (map)
+               return -EEXIST;
+
+       map = kzalloc(sizeof(struct regulator_supply_alias), GFP_KERNEL);
+       if (!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, &regulator_supply_alias_list);
+
+       pr_info("Adding alias for supply %s,%s -> %s,%s\n",
+               id, dev_name(dev), alias_id, dev_name(alias_dev));
+
+       return 0;
+}
+EXPORT_SYMBOL_GPL(regulator_register_supply_alias);
+
+/**
+ * regulator_unregister_supply_alias - Remove device alias
+ *
+ * @dev: device that will be given as the regulator "consumer"
+ * @id: Supply name or regulator ID
+ *
+ * Remove a lookup alias if one exists for id on dev.
+ */
+void regulator_unregister_supply_alias(struct device *dev, const char *id)
+{
+       struct regulator_supply_alias *map;
+
+       map = regulator_find_supply_alias(dev, id);
+       if (map) {
+               list_del(&map->list);
+               kfree(map);
+       }
+}
+EXPORT_SYMBOL_GPL(regulator_unregister_supply_alias);
+
+/**
+ * regulator_bulk_register_supply_alias - register multiple aliases
+ *
+ * @dev: device that will be given as the regulator "consumer"
+ * @id: List of supply names or regulator IDs
+ * @alias_dev: device that should be used to lookup the supply
+ * @alias_id: List of supply names or regulator IDs that should be used to
+ * lookup the supply
+ * @num_id: Number of aliases to register
+ *
+ * @return 0 on success, an errno on failure.
+ *
+ * This helper function allows drivers to register several supply
+ * aliases in one operation.  If any of the aliases cannot be
+ * registered any aliases that were registered will be removed
+ * before returning to the caller.
+ */
+int regulator_bulk_register_supply_alias(struct device *dev, const char **id,
+                                        struct device *alias_dev,
+                                        const char **alias_id,
+                                        int num_id)
+{
+       int i;
+       int ret;
+
+       for (i = 0; i < num_id; ++i) {
+               ret = regulator_register_supply_alias(dev, id[i], alias_dev,
+                                                     alias_id[i]);
+               if (ret < 0)
+                       goto err;
        }
-       return *r == data;
+
+       return 0;
+
+err:
+       dev_err(dev,
+               "Failed to create supply alias %s,%s -> %s,%s\n",
+               id[i], dev_name(dev), alias_id[i], dev_name(alias_dev));
+
+       while (--i >= 0)
+               regulator_unregister_supply_alias(dev, id[i]);
+
+       return ret;
 }
+EXPORT_SYMBOL_GPL(regulator_bulk_register_supply_alias);
 
 /**
- * devm_regulator_put - Resource managed regulator_put()
- * @regulator: regulator to free
+ * regulator_bulk_unregister_supply_alias - unregister multiple aliases
+ *
+ * @dev: device that will be given as the regulator "consumer"
+ * @id: List of supply names or regulator IDs
+ * @num_id: Number of aliases to unregister
  *
- * Deallocate a regulator allocated with devm_regulator_get(). Normally
- * this function will not need to be called and the resource management
- * code will ensure that the resource is freed.
+ * This helper function allows drivers to unregister several supply
+ * aliases in one operation.
  */
-void devm_regulator_put(struct regulator *regulator)
+void regulator_bulk_unregister_supply_alias(struct device *dev,
+                                           const char **id,
+                                           int num_id)
 {
-       int rc;
+       int i;
 
-       rc = devres_release(regulator->dev, devm_regulator_release,
-                           devm_regulator_match, regulator);
-       if (rc != 0)
-               WARN_ON(rc);
+       for (i = 0; i < num_id; ++i)
+               regulator_unregister_supply_alias(dev, id[i]);
 }
-EXPORT_SYMBOL_GPL(devm_regulator_put);
+EXPORT_SYMBOL_GPL(regulator_bulk_unregister_supply_alias);
+
 
 /* Manage enable GPIO list. Same GPIO pin can be shared among regulators */
 static int regulator_ena_gpio_request(struct regulator_dev *rdev,
@@ -2912,52 +2941,6 @@ err:
 }
 EXPORT_SYMBOL_GPL(regulator_bulk_get);
 
-/**
- * devm_regulator_bulk_get - managed get multiple regulator consumers
- *
- * @dev:           Device to supply
- * @num_consumers: Number of consumers to register
- * @consumers:     Configuration of consumers; clients are stored here.
- *
- * @return 0 on success, an errno on failure.
- *
- * This helper function allows drivers to get several regulator
- * consumers in one operation with management, the regulators will
- * automatically be freed when the device is unbound.  If any of the
- * regulators cannot be acquired then any regulators that were
- * allocated will be freed before returning to the caller.
- */
-int devm_regulator_bulk_get(struct device *dev, int num_consumers,
-                           struct regulator_bulk_data *consumers)
-{
-       int i;
-       int ret;
-
-       for (i = 0; i < num_consumers; i++)
-               consumers[i].consumer = NULL;
-
-       for (i = 0; i < num_consumers; i++) {
-               consumers[i].consumer = devm_regulator_get(dev,
-                                                          consumers[i].supply);
-               if (IS_ERR(consumers[i].consumer)) {
-                       ret = PTR_ERR(consumers[i].consumer);
-                       dev_err(dev, "Failed to get supply '%s': %d\n",
-                               consumers[i].supply, ret);
-                       consumers[i].consumer = NULL;
-                       goto err;
-               }
-       }
-
-       return 0;
-
-err:
-       for (i = 0; i < num_consumers && consumers[i].consumer; i++)
-               devm_regulator_put(consumers[i].consumer);
-
-       return ret;
-}
-EXPORT_SYMBOL_GPL(devm_regulator_bulk_get);
-
 static void regulator_bulk_enable_async(void *data, async_cookie_t cookie)
 {
        struct regulator_bulk_data *bulk = data;
index f06854c..c61d96e 100644 (file)
@@ -463,7 +463,7 @@ static int da903x_regulator_probe(struct platform_device *pdev)
        config.init_data = dev_get_platdata(&pdev->dev);
        config.driver_data = ri;
 
-       rdev = regulator_register(&ri->desc, &config);
+       rdev = devm_regulator_register(&pdev->dev, &ri->desc, &config);
        if (IS_ERR(rdev)) {
                dev_err(&pdev->dev, "failed to register regulator %s\n",
                                ri->desc.name);
@@ -474,21 +474,12 @@ static int da903x_regulator_probe(struct platform_device *pdev)
        return 0;
 }
 
-static int da903x_regulator_remove(struct platform_device *pdev)
-{
-       struct regulator_dev *rdev = platform_get_drvdata(pdev);
-
-       regulator_unregister(rdev);
-       return 0;
-}
-
 static struct platform_driver da903x_regulator_driver = {
        .driver = {
                .name   = "da903x-regulator",
                .owner  = THIS_MODULE,
        },
        .probe          = da903x_regulator_probe,
-       .remove         = da903x_regulator_remove,
 };
 
 static int __init da903x_regulator_init(void)
index 1e4d483..c427e42 100644 (file)
@@ -389,8 +389,9 @@ static int da9052_regulator_probe(struct platform_device *pdev)
 #endif
        }
 
-       regulator->rdev = regulator_register(&regulator->info->reg_desc,
-                                            &config);
+       regulator->rdev = devm_regulator_register(&pdev->dev,
+                                                 &regulator->info->reg_desc,
+                                                 &config);
        if (IS_ERR(regulator->rdev)) {
                dev_err(&pdev->dev, "failed to register regulator %s\n",
                        regulator->info->reg_desc.name);
@@ -402,17 +403,8 @@ static int da9052_regulator_probe(struct platform_device *pdev)
        return 0;
 }
 
-static int da9052_regulator_remove(struct platform_device *pdev)
-{
-       struct da9052_regulator *regulator = platform_get_drvdata(pdev);
-
-       regulator_unregister(regulator->rdev);
-       return 0;
-}
-
 static struct platform_driver da9052_regulator_driver = {
        .probe = da9052_regulator_probe,
-       .remove = da9052_regulator_remove,
        .driver = {
                .name = "da9052-regulator",
                .owner = THIS_MODULE,
index 77b53e5..7f34020 100644 (file)
@@ -564,13 +564,13 @@ static int da9055_regulator_probe(struct platform_device *pdev)
        if (ret < 0)
                return ret;
 
-       regulator->rdev = regulator_register(&regulator->info->reg_desc,
-                                            &config);
+       regulator->rdev = devm_regulator_register(&pdev->dev,
+                                                 &regulator->info->reg_desc,
+                                                 &config);
        if (IS_ERR(regulator->rdev)) {
                dev_err(&pdev->dev, "Failed to register regulator %s\n",
                        regulator->info->reg_desc.name);
-               ret = PTR_ERR(regulator->rdev);
-               return ret;
+               return PTR_ERR(regulator->rdev);
        }
 
        /* Only LDO 5 and 6 has got the over current interrupt */
@@ -588,7 +588,7 @@ static int da9055_regulator_probe(struct platform_device *pdev)
                                dev_err(&pdev->dev,
                                "Failed to request Regulator IRQ %d: %d\n",
                                irq, ret);
-                               goto err_regulator;
+                               return ret;
                        }
                }
        }
@@ -596,24 +596,10 @@ static int da9055_regulator_probe(struct platform_device *pdev)
        platform_set_drvdata(pdev, regulator);
 
        return 0;
-
-err_regulator:
-       regulator_unregister(regulator->rdev);
-       return ret;
-}
-
-static int da9055_regulator_remove(struct platform_device *pdev)
-{
-       struct da9055_regulator *regulator = platform_get_drvdata(pdev);
-
-       regulator_unregister(regulator->rdev);
-
-       return 0;
 }
 
 static struct platform_driver da9055_regulator_driver = {
        .probe = da9055_regulator_probe,
-       .remove = da9055_regulator_remove,
        .driver = {
                .name = "da9055-regulator",
                .owner = THIS_MODULE,
diff --git a/drivers/regulator/devres.c b/drivers/regulator/devres.c
new file mode 100644 (file)
index 0000000..f44818b
--- /dev/null
@@ -0,0 +1,415 @@
+/*
+ * devres.c  --  Voltage/Current Regulator framework devres implementation.
+ *
+ * Copyright 2013 Linaro Ltd
+ *
+ *  This program is free software; you can redistribute  it and/or modify it
+ *  under  the terms of  the GNU General  Public License as published by the
+ *  Free Software Foundation;  either version 2 of the  License, or (at your
+ *  option) any later version.
+ *
+ */
+
+#include <linux/kernel.h>
+#include <linux/err.h>
+#include <linux/regmap.h>
+#include <linux/regulator/consumer.h>
+#include <linux/regulator/driver.h>
+#include <linux/module.h>
+
+#include "internal.h"
+
+enum {
+       NORMAL_GET,
+       EXCLUSIVE_GET,
+       OPTIONAL_GET,
+};
+
+static void devm_regulator_release(struct device *dev, void *res)
+{
+       regulator_put(*(struct regulator **)res);
+}
+
+static struct regulator *_devm_regulator_get(struct device *dev, const char *id,
+                                            int get_type)
+{
+       struct regulator **ptr, *regulator;
+
+       ptr = devres_alloc(devm_regulator_release, sizeof(*ptr), GFP_KERNEL);
+       if (!ptr)
+               return ERR_PTR(-ENOMEM);
+
+       switch (get_type) {
+       case NORMAL_GET:
+               regulator = regulator_get(dev, id);
+               break;
+       case EXCLUSIVE_GET:
+               regulator = regulator_get_exclusive(dev, id);
+               break;
+       case OPTIONAL_GET:
+               regulator = regulator_get_optional(dev, id);
+               break;
+       default:
+               regulator = ERR_PTR(-EINVAL);
+       }
+
+       if (!IS_ERR(regulator)) {
+               *ptr = regulator;
+               devres_add(dev, ptr);
+       } else {
+               devres_free(ptr);
+       }
+
+       return regulator;
+}
+
+/**
+ * devm_regulator_get - Resource managed regulator_get()
+ * @dev: device for regulator "consumer"
+ * @id: Supply name or regulator ID.
+ *
+ * Managed regulator_get(). Regulators returned from this function are
+ * automatically regulator_put() on driver detach. See regulator_get() for more
+ * information.
+ */
+struct regulator *devm_regulator_get(struct device *dev, const char *id)
+{
+       return _devm_regulator_get(dev, id, NORMAL_GET);
+}
+EXPORT_SYMBOL_GPL(devm_regulator_get);
+
+/**
+ * devm_regulator_get_exclusive - Resource managed regulator_get_exclusive()
+ * @dev: device for regulator "consumer"
+ * @id: Supply name or regulator ID.
+ *
+ * Managed regulator_get_exclusive(). Regulators returned from this function
+ * are automatically regulator_put() on driver detach. See regulator_get() for
+ * more information.
+ */
+struct regulator *devm_regulator_get_exclusive(struct device *dev,
+                                              const char *id)
+{
+       return _devm_regulator_get(dev, id, EXCLUSIVE_GET);
+}
+EXPORT_SYMBOL_GPL(devm_regulator_get_exclusive);
+
+/**
+ * devm_regulator_get_optional - Resource managed regulator_get_optional()
+ * @dev: device for regulator "consumer"
+ * @id: Supply name or regulator ID.
+ *
+ * Managed regulator_get_optional(). Regulators returned from this
+ * function are automatically regulator_put() on driver detach. See
+ * regulator_get_optional() for more information.
+ */
+struct regulator *devm_regulator_get_optional(struct device *dev,
+                                             const char *id)
+{
+       return _devm_regulator_get(dev, id, OPTIONAL_GET);
+}
+EXPORT_SYMBOL_GPL(devm_regulator_get_optional);
+
+static int devm_regulator_match(struct device *dev, void *res, void *data)
+{
+       struct regulator **r = res;
+       if (!r || !*r) {
+               WARN_ON(!r || !*r);
+               return 0;
+       }
+       return *r == data;
+}
+
+/**
+ * devm_regulator_put - Resource managed regulator_put()
+ * @regulator: regulator to free
+ *
+ * Deallocate a regulator allocated with devm_regulator_get(). Normally
+ * this function will not need to be called and the resource management
+ * code will ensure that the resource is freed.
+ */
+void devm_regulator_put(struct regulator *regulator)
+{
+       int rc;
+
+       rc = devres_release(regulator->dev, devm_regulator_release,
+                           devm_regulator_match, regulator);
+       if (rc != 0)
+               WARN_ON(rc);
+}
+EXPORT_SYMBOL_GPL(devm_regulator_put);
+
+/**
+ * devm_regulator_bulk_get - managed get multiple regulator consumers
+ *
+ * @dev:           Device to supply
+ * @num_consumers: Number of consumers to register
+ * @consumers:     Configuration of consumers; clients are stored here.
+ *
+ * @return 0 on success, an errno on failure.
+ *
+ * This helper function allows drivers to get several regulator
+ * consumers in one operation with management, the regulators will
+ * automatically be freed when the device is unbound.  If any of the
+ * regulators cannot be acquired then any regulators that were
+ * allocated will be freed before returning to the caller.
+ */
+int devm_regulator_bulk_get(struct device *dev, int num_consumers,
+                           struct regulator_bulk_data *consumers)
+{
+       int i;
+       int ret;
+
+       for (i = 0; i < num_consumers; i++)
+               consumers[i].consumer = NULL;
+
+       for (i = 0; i < num_consumers; i++) {
+               consumers[i].consumer = devm_regulator_get(dev,
+                                                          consumers[i].supply);
+               if (IS_ERR(consumers[i].consumer)) {
+                       ret = PTR_ERR(consumers[i].consumer);
+                       dev_err(dev, "Failed to get supply '%s': %d\n",
+                               consumers[i].supply, ret);
+                       consumers[i].consumer = NULL;
+                       goto err;
+               }
+       }
+
+       return 0;
+
+err:
+       for (i = 0; i < num_consumers && consumers[i].consumer; i++)
+               devm_regulator_put(consumers[i].consumer);
+
+       return ret;
+}
+EXPORT_SYMBOL_GPL(devm_regulator_bulk_get);
+
+static void devm_rdev_release(struct device *dev, void *res)
+{
+       regulator_unregister(*(struct regulator_dev **)res);
+}
+
+/**
+ * devm_regulator_register - Resource managed regulator_register()
+ * @regulator_desc: regulator to register
+ * @config: runtime configuration for regulator
+ *
+ * Called by regulator drivers to register a regulator.  Returns a
+ * valid pointer to struct regulator_dev on success or an ERR_PTR() on
+ * error.  The regulator will automatically be released when the device
+ * is unbound.
+ */
+struct regulator_dev *devm_regulator_register(struct device *dev,
+                                 const struct regulator_desc *regulator_desc,
+                                 const struct regulator_config *config)
+{
+       struct regulator_dev **ptr, *rdev;
+
+       ptr = devres_alloc(devm_rdev_release, sizeof(*ptr),
+                          GFP_KERNEL);
+       if (!ptr)
+               return ERR_PTR(-ENOMEM);
+
+       rdev = regulator_register(regulator_desc, config);
+       if (!IS_ERR(rdev)) {
+               *ptr = rdev;
+               devres_add(dev, ptr);
+       } else {
+               devres_free(ptr);
+       }
+
+       return rdev;
+}
+EXPORT_SYMBOL_GPL(devm_regulator_register);
+
+static int devm_rdev_match(struct device *dev, void *res, void *data)
+{
+       struct regulator_dev **r = res;
+       if (!r || !*r) {
+               WARN_ON(!r || !*r);
+               return 0;
+       }
+       return *r == data;
+}
+
+/**
+ * devm_regulator_unregister - Resource managed regulator_unregister()
+ * @regulator: regulator to free
+ *
+ * Unregister a regulator registered with devm_regulator_register().
+ * Normally this function will not need to be called and the resource
+ * management code will ensure that the resource is freed.
+ */
+void devm_regulator_unregister(struct device *dev, struct regulator_dev *rdev)
+{
+       int rc;
+
+       rc = devres_release(dev, devm_rdev_release, devm_rdev_match, rdev);
+       if (rc != 0)
+               WARN_ON(rc);
+}
+EXPORT_SYMBOL_GPL(devm_regulator_unregister);
+
+struct regulator_supply_alias_match {
+       struct device *dev;
+       const char *id;
+};
+
+static int devm_regulator_match_supply_alias(struct device *dev, void *res,
+                                            void *data)
+{
+       struct regulator_supply_alias_match *match = res;
+       struct regulator_supply_alias_match *target = data;
+
+       return match->dev == target->dev && strcmp(match->id, target->id) == 0;
+}
+
+static void devm_regulator_destroy_supply_alias(struct device *dev, void *res)
+{
+       struct regulator_supply_alias_match *match = res;
+
+       regulator_unregister_supply_alias(match->dev, match->id);
+}
+
+/**
+ * devm_regulator_register_supply_alias - Resource managed
+ * regulator_register_supply_alias()
+ *
+ * @dev: device that will be given as the regulator "consumer"
+ * @id: Supply name or regulator ID
+ * @alias_dev: device that should be used to lookup the supply
+ * @alias_id: Supply name or regulator ID that should be used to lookup the
+ * supply
+ *
+ * The supply alias will automatically be unregistered when the source
+ * device is unbound.
+ */
+int devm_regulator_register_supply_alias(struct device *dev, const char *id,
+                                        struct device *alias_dev,
+                                        const char *alias_id)
+{
+       struct regulator_supply_alias_match *match;
+       int ret;
+
+       match = devres_alloc(devm_regulator_destroy_supply_alias,
+                          sizeof(struct regulator_supply_alias_match),
+                          GFP_KERNEL);
+       if (!match)
+               return -ENOMEM;
+
+       match->dev = dev;
+       match->id = id;
+
+       ret = regulator_register_supply_alias(dev, id, alias_dev, alias_id);
+       if (ret < 0) {
+               devres_free(match);
+               return ret;
+       }
+
+       devres_add(dev, match);
+
+       return 0;
+}
+EXPORT_SYMBOL_GPL(devm_regulator_register_supply_alias);
+
+/**
+ * devm_regulator_unregister_supply_alias - Resource managed
+ * regulator_unregister_supply_alias()
+ *
+ * @dev: device that will be given as the regulator "consumer"
+ * @id: Supply name or regulator ID
+ *
+ * Unregister an alias registered with
+ * devm_regulator_register_supply_alias(). Normally this function
+ * will not need to be called and the resource management code
+ * will ensure that the resource is freed.
+ */
+void devm_regulator_unregister_supply_alias(struct device *dev, const char *id)
+{
+       struct regulator_supply_alias_match match;
+       int rc;
+
+       match.dev = dev;
+       match.id = id;
+
+       rc = devres_release(dev, devm_regulator_destroy_supply_alias,
+                           devm_regulator_match_supply_alias, &match);
+       if (rc != 0)
+               WARN_ON(rc);
+}
+EXPORT_SYMBOL_GPL(devm_regulator_unregister_supply_alias);
+
+/**
+ * devm_regulator_bulk_register_supply_alias - Managed register
+ * multiple aliases
+ *
+ * @dev: device that will be given as the regulator "consumer"
+ * @id: List of supply names or regulator IDs
+ * @alias_dev: device that should be used to lookup the supply
+ * @alias_id: List of supply names or regulator IDs that should be used to
+ * lookup the supply
+ * @num_id: Number of aliases to register
+ *
+ * @return 0 on success, an errno on failure.
+ *
+ * This helper function allows drivers to register several supply
+ * aliases in one operation, the aliases will be automatically
+ * unregisters when the source device is unbound.  If any of the
+ * aliases cannot be registered any aliases that were registered
+ * will be removed before returning to the caller.
+ */
+int devm_regulator_bulk_register_supply_alias(struct device *dev,
+                                             const char **id,
+                                             struct device *alias_dev,
+                                             const char **alias_id,
+                                             int num_id)
+{
+       int i;
+       int ret;
+
+       for (i = 0; i < num_id; ++i) {
+               ret = devm_regulator_register_supply_alias(dev, id[i],
+                                                          alias_dev,
+                                                          alias_id[i]);
+               if (ret < 0)
+                       goto err;
+       }
+
+       return 0;
+
+err:
+       dev_err(dev,
+               "Failed to create supply alias %s,%s -> %s,%s\n",
+               id[i], dev_name(dev), alias_id[i], dev_name(alias_dev));
+
+       while (--i >= 0)
+               devm_regulator_unregister_supply_alias(dev, id[i]);
+
+       return ret;
+}
+EXPORT_SYMBOL_GPL(devm_regulator_bulk_register_supply_alias);
+
+/**
+ * devm_regulator_bulk_unregister_supply_alias - Managed unregister
+ * multiple aliases
+ *
+ * @dev: device that will be given as the regulator "consumer"
+ * @id: List of supply names or regulator IDs
+ * @num_id: Number of aliases to unregister
+ *
+ * Unregister aliases registered with
+ * devm_regulator_bulk_register_supply_alias(). Normally this function
+ * will not need to be called and the resource management code
+ * will ensure that the resource is freed.
+ */
+void devm_regulator_bulk_unregister_supply_alias(struct device *dev,
+                                                const char **id,
+                                                int num_id)
+{
+       int i;
+
+       for (i = 0; i < num_id; ++i)
+               devm_regulator_unregister_supply_alias(dev, id[i]);
+}
+EXPORT_SYMBOL_GPL(devm_regulator_bulk_unregister_supply_alias);
index 70b7220..7ca3d9e 100644 (file)
@@ -218,9 +218,8 @@ static int fan53555_regulator_register(struct fan53555_device_info *di,
        rdesc->vsel_mask = VSEL_NSEL_MASK;
        rdesc->owner = THIS_MODULE;
 
-       di->rdev = regulator_register(&di->desc, config);
+       di->rdev = devm_regulator_register(di->dev, &di->desc, config);
        return PTR_ERR_OR_ZERO(di->rdev);
-
 }
 
 static struct regmap_config fan53555_regmap_config = {
@@ -291,14 +290,6 @@ static int fan53555_regulator_probe(struct i2c_client *client,
 
 }
 
-static int fan53555_regulator_remove(struct i2c_client *client)
-{
-       struct fan53555_device_info *di = i2c_get_clientdata(client);
-
-       regulator_unregister(di->rdev);
-       return 0;
-}
-
 static const struct i2c_device_id fan53555_id[] = {
        {"fan53555", -1},
        { },
@@ -309,7 +300,6 @@ static struct i2c_driver fan53555_regulator_driver = {
                .name = "fan53555-regulator",
        },
        .probe = fan53555_regulator_probe,
-       .remove = fan53555_regulator_remove,
        .id_table = fan53555_id,
 };
 
diff --git a/drivers/regulator/internal.h b/drivers/regulator/internal.h
new file mode 100644 (file)
index 0000000..84bbda1
--- /dev/null
@@ -0,0 +1,38 @@
+/*
+ * internal.h  --  Voltage/Current Regulator framework internal code
+ *
+ * Copyright 2007, 2008 Wolfson Microelectronics PLC.
+ * Copyright 2008 SlimLogic Ltd.
+ *
+ * Author: Liam Girdwood <lrg@slimlogic.co.uk>
+ *
+ *  This program is free software; you can redistribute  it and/or modify it
+ *  under  the terms of  the GNU General  Public License as published by the
+ *  Free Software Foundation;  either version 2 of the  License, or (at your
+ *  option) any later version.
+ *
+ */
+
+#ifndef __REGULATOR_INTERNAL_H
+#define __REGULATOR_INTERNAL_H
+
+/*
+ * struct regulator
+ *
+ * One for each consumer device.
+ */
+struct regulator {
+       struct device *dev;
+       struct list_head list;
+       unsigned int always_on:1;
+       unsigned int bypass:1;
+       int uA_load;
+       int min_uV;
+       int max_uV;
+       char *supply_name;
+       struct device_attribute dev_attr;
+       struct regulator_dev *rdev;
+       struct dentry *debugfs;
+};
+
+#endif
index 88c1a3a..6e5da95 100644 (file)
@@ -112,7 +112,7 @@ static int isl6271a_probe(struct i2c_client *i2c,
        struct regulator_config config = { };
        struct regulator_init_data *init_data   = dev_get_platdata(&i2c->dev);
        struct isl_pmic *pmic;
-       int err, i;
+       int i;
 
        if (!i2c_check_functionality(i2c->adapter, I2C_FUNC_SMBUS_BYTE_DATA))
                return -EIO;
@@ -133,32 +133,17 @@ static int isl6271a_probe(struct i2c_client *i2c,
                        config.init_data = NULL;
                config.driver_data = pmic;
 
-               pmic->rdev[i] = regulator_register(&isl_rd[i], &config);
+               pmic->rdev[i] = devm_regulator_register(&i2c->dev, &isl_rd[i],
+                                                       &config);
                if (IS_ERR(pmic->rdev[i])) {
                        dev_err(&i2c->dev, "failed to register %s\n", id->name);
-                       err = PTR_ERR(pmic->rdev[i]);
-                       goto error;
+                       return PTR_ERR(pmic->rdev[i]);
                }
        }
 
        i2c_set_clientdata(i2c, pmic);
 
        return 0;
-
-error:
-       while (--i >= 0)
-               regulator_unregister(pmic->rdev[i]);
-       return err;
-}
-
-static int isl6271a_remove(struct i2c_client *i2c)
-{
-       struct isl_pmic *pmic = i2c_get_clientdata(i2c);
-       int i;
-
-       for (i = 0; i < 3; i++)
-               regulator_unregister(pmic->rdev[i]);
-       return 0;
 }
 
 static const struct i2c_device_id isl6271a_id[] = {
@@ -174,7 +159,6 @@ static struct i2c_driver isl6271a_i2c_driver = {
                .owner = THIS_MODULE,
        },
        .probe = isl6271a_probe,
-       .remove = isl6271a_remove,
        .id_table = isl6271a_id,
 };
 
index 3a599ee..e242dd3 100644 (file)
@@ -166,7 +166,7 @@ static int max1586_pmic_probe(struct i2c_client *client,
        struct max1586_platform_data *pdata = dev_get_platdata(&client->dev);
        struct regulator_config config = { };
        struct max1586_data *max1586;
-       int i, id, ret = -ENOMEM;
+       int i, id;
 
        max1586 = devm_kzalloc(&client->dev, sizeof(struct max1586_data) +
                        sizeof(struct regulator_dev *) * (MAX1586_V6 + 1),
@@ -193,7 +193,7 @@ static int max1586_pmic_probe(struct i2c_client *client,
                        continue;
                if (id < MAX1586_V3 || id > MAX1586_V6) {
                        dev_err(&client->dev, "invalid regulator id %d\n", id);
-                       goto err;
+                       return -EINVAL;
                }
 
                if (id == MAX1586_V3) {
@@ -207,33 +207,18 @@ static int max1586_pmic_probe(struct i2c_client *client,
                config.init_data = pdata->subdevs[i].platform_data;
                config.driver_data = max1586;
 
-               rdev[i] = regulator_register(&max1586_reg[id], &config);
+               rdev[i] = devm_regulator_register(&client->dev,
+                                                 &max1586_reg[id], &config);
                if (IS_ERR(rdev[i])) {
-                       ret = PTR_ERR(rdev[i]);
                        dev_err(&client->dev, "failed to register %s\n",
                                max1586_reg[id].name);
-                       goto err;
+                       return PTR_ERR(rdev[i]);
                }
        }
 
        i2c_set_clientdata(client, max1586);
        dev_info(&client->dev, "Maxim 1586 regulator driver loaded\n");
        return 0;
-
-err:
-       while (--i >= 0)
-               regulator_unregister(rdev[i]);
-       return ret;
-}
-
-static int max1586_pmic_remove(struct i2c_client *client)
-{
-       struct max1586_data *max1586 = i2c_get_clientdata(client);
-       int i;
-
-       for (i = 0; i <= MAX1586_V6; i++)
-               regulator_unregister(max1586->rdev[i]);
-       return 0;
 }
 
 static const struct i2c_device_id max1586_id[] = {
@@ -244,7 +229,6 @@ MODULE_DEVICE_TABLE(i2c, max1586_id);
 
 static struct i2c_driver max1586_pmic_driver = {
        .probe = max1586_pmic_probe,
-       .remove = max1586_pmic_remove,
        .driver         = {
                .name   = "max1586",
                .owner  = THIS_MODULE,
index f563057..ae001cc 100644 (file)
@@ -478,32 +478,16 @@ static int max77686_pmic_probe(struct platform_device *pdev)
                config.of_node = pdata->regulators[i].of_node;
 
                max77686->opmode[i] = regulators[i].enable_mask;
-               max77686->rdev[i] = regulator_register(&regulators[i], &config);
+               max77686->rdev[i] = devm_regulator_register(&pdev->dev,
+                                               &regulators[i], &config);
                if (IS_ERR(max77686->rdev[i])) {
-                       ret = PTR_ERR(max77686->rdev[i]);
                        dev_err(&pdev->dev,
                                "regulator init failed for %d\n", i);
-                       max77686->rdev[i] = NULL;
-                       goto err;
+                       return PTR_ERR(max77686->rdev[i]);
                }
        }
 
        return 0;
-err:
-       while (--i >= 0)
-               regulator_unregister(max77686->rdev[i]);
-       return ret;
-}
-
-static int max77686_pmic_remove(struct platform_device *pdev)
-{
-       struct max77686_data *max77686 = platform_get_drvdata(pdev);
-       int i;
-
-       for (i = 0; i < MAX77686_REGULATORS; i++)
-               regulator_unregister(max77686->rdev[i]);
-
-       return 0;
 }
 
 static const struct platform_device_id max77686_pmic_id[] = {
@@ -518,7 +502,6 @@ static struct platform_driver max77686_pmic_driver = {
                .owner = THIS_MODULE,
        },
        .probe = max77686_pmic_probe,
-       .remove = max77686_pmic_remove,
        .id_table = max77686_pmic_id,
 };
 
index ce4b96c..feb20bf 100644 (file)
@@ -230,7 +230,7 @@ static int max77693_pmic_probe(struct platform_device *pdev)
        struct max77693_dev *iodev = dev_get_drvdata(pdev->dev.parent);
        struct max77693_pmic_dev *max77693_pmic;
        struct max77693_regulator_data *rdata = NULL;
-       int num_rdata, i, ret;
+       int num_rdata, i;
        struct regulator_config config;
 
        num_rdata = max77693_pmic_init_rdata(&pdev->dev, &rdata);
@@ -266,36 +266,16 @@ static int max77693_pmic_probe(struct platform_device *pdev)
                config.init_data = rdata[i].initdata;
                config.of_node = rdata[i].of_node;
 
-               max77693_pmic->rdev[i] = regulator_register(&regulators[id],
-                                                           &config);
+               max77693_pmic->rdev[i] = devm_regulator_register(&pdev->dev,
+                                               &regulators[id], &config);
                if (IS_ERR(max77693_pmic->rdev[i])) {
-                       ret = PTR_ERR(max77693_pmic->rdev[i]);
                        dev_err(max77693_pmic->dev,
                                "Failed to initialize regulator-%d\n", id);
-                       max77693_pmic->rdev[i] = NULL;
-                       goto err;
+                       return PTR_ERR(max77693_pmic->rdev[i]);
                }
        }
 
        return 0;
- err:
-       while (--i >= 0)
-               regulator_unregister(max77693_pmic->rdev[i]);
-
-       return ret;
-}
-
-static int max77693_pmic_remove(struct platform_device *pdev)
-{
-       struct max77693_pmic_dev *max77693_pmic = platform_get_drvdata(pdev);
-       struct regulator_dev **rdev = max77693_pmic->rdev;
-       int i;
-
-       for (i = 0; i < max77693_pmic->num_regulators; i++)
-               if (rdev[i])
-                       regulator_unregister(rdev[i]);
-
-       return 0;
 }
 
 static const struct platform_device_id max77693_pmic_id[] = {
@@ -311,7 +291,6 @@ static struct platform_driver max77693_pmic_driver = {
                   .owner = THIS_MODULE,
                   },
        .probe = max77693_pmic_probe,
-       .remove = max77693_pmic_remove,
        .id_table = max77693_pmic_id,
 };
 
index 19c6f08..7f049c9 100644 (file)
@@ -234,7 +234,8 @@ static int max8649_regulator_probe(struct i2c_client *client,
        config.driver_data = info;
        config.regmap = info->regmap;
 
-       info->regulator = regulator_register(&dcdc_desc, &config);
+       info->regulator = devm_regulator_register(&client->dev, &dcdc_desc,
+                                                 &config);
        if (IS_ERR(info->regulator)) {
                dev_err(info->dev, "failed to register regulator %s\n",
                        dcdc_desc.name);
@@ -244,16 +245,6 @@ static int max8649_regulator_probe(struct i2c_client *client,
        return 0;
 }
 
-static int max8649_regulator_remove(struct i2c_client *client)
-{
-       struct max8649_regulator_info *info = i2c_get_clientdata(client);
-
-       if (info)
-               regulator_unregister(info->regulator);
-
-       return 0;
-}
-
 static const struct i2c_device_id max8649_id[] = {
        { "max8649", 0 },
        { }
@@ -262,7 +253,6 @@ MODULE_DEVICE_TABLE(i2c, max8649_id);
 
 static struct i2c_driver max8649_driver = {
        .probe          = max8649_regulator_probe,
-       .remove         = max8649_regulator_remove,
        .driver         = {
                .name   = "max8649",
        },
index 144bcac..8d94d3d 100644 (file)
@@ -439,7 +439,7 @@ static int max8660_probe(struct i2c_client *client,
        for (i = 0; i < pdata->num_subdevs; i++) {
 
                if (!pdata->subdevs[i].platform_data)
-                       goto err_out;
+                       return ret;
 
                boot_on = pdata->subdevs[i].platform_data->constraints.boot_on;
 
@@ -465,7 +465,7 @@ static int max8660_probe(struct i2c_client *client,
                case MAX8660_V7:
                        if (type == MAX8661) {
                                dev_err(dev, "Regulator not on this chip!\n");
-                               goto err_out;
+                               return -EINVAL;
                        }
 
                        if (boot_on)
@@ -475,7 +475,7 @@ static int max8660_probe(struct i2c_client *client,
                default:
                        dev_err(dev, "invalid regulator %s\n",
                                 pdata->subdevs[i].name);
-                       goto err_out;
+                       return ret;
                }
        }
 
@@ -489,33 +489,18 @@ static int max8660_probe(struct i2c_client *client,
                config.of_node = of_node[i];
                config.driver_data = max8660;
 
-               rdev[i] = regulator_register(&max8660_reg[id], &config);
+               rdev[i] = devm_regulator_register(&client->dev,
+                                                 &max8660_reg[id], &config);
                if (IS_ERR(rdev[i])) {
                        ret = PTR_ERR(rdev[i]);
-                       dev_err(dev, "failed to register %s\n",
+                       dev_err(&client->dev, "failed to register %s\n",
                                max8660_reg[id].name);
-                       goto err_unregister;
+                       return PTR_ERR(rdev[i]);
                }
        }
 
        i2c_set_clientdata(client, max8660);
        return 0;
-
-err_unregister:
-       while (--i >= 0)
-               regulator_unregister(rdev[i]);
-err_out:
-       return ret;
-}
-
-static int max8660_remove(struct i2c_client *client)
-{
-       struct max8660 *max8660 = i2c_get_clientdata(client);
-       int i;
-
-       for (i = 0; i < MAX8660_V_END; i++)
-               regulator_unregister(max8660->rdev[i]);
-       return 0;
 }
 
 static const struct i2c_device_id max8660_id[] = {
@@ -527,7 +512,6 @@ MODULE_DEVICE_TABLE(i2c, max8660_id);
 
 static struct i2c_driver max8660_driver = {
        .probe = max8660_probe,
-       .remove = max8660_remove,
        .driver         = {
                .name   = "max8660",
                .owner  = THIS_MODULE,
index 4568c15..0c5fe6c 100644 (file)
@@ -350,33 +350,17 @@ static int max8907_regulator_probe(struct platform_device *pdev)
                                pmic->desc[i].ops = &max8907_out5v_hwctl_ops;
                }
 
-               pmic->rdev[i] = regulator_register(&pmic->desc[i], &config);
+               pmic->rdev[i] = devm_regulator_register(&pdev->dev,
+                                               &pmic->desc[i], &config);
                if (IS_ERR(pmic->rdev[i])) {
                        dev_err(&pdev->dev,
                                "failed to register %s regulator\n",
                                pmic->desc[i].name);
-                       ret = PTR_ERR(pmic->rdev[i]);
-                       goto err_unregister_regulator;
+                       return PTR_ERR(pmic->rdev[i]);
                }
        }
 
        return 0;
-
-err_unregister_regulator:
-       while (--i >= 0)
-               regulator_unregister(pmic->rdev[i]);
-       return ret;
-}
-
-static int max8907_regulator_remove(struct platform_device *pdev)
-{
-       struct max8907_regulator *pmic = platform_get_drvdata(pdev);
-       int i;
-
-       for (i = 0; i < MAX8907_NUM_REGULATORS; i++)
-               regulator_unregister(pmic->rdev[i]);
-
-       return 0;
 }
 
 static struct platform_driver max8907_regulator_driver = {
@@ -385,7 +369,6 @@ static struct platform_driver max8907_regulator_driver = {
                   .owner = THIS_MODULE,
                   },
        .probe = max8907_regulator_probe,
-       .remove = max8907_regulator_remove,
 };
 
 static int __init max8907_regulator_init(void)
index 5b77ab7..892aa1e 100644 (file)
@@ -467,7 +467,7 @@ static int max8973_probe(struct i2c_client *client,
        config.regmap = max->regmap;
 
        /* Register the regulators */
-       rdev = regulator_register(&max->desc, &config);
+       rdev = devm_regulator_register(&client->dev, &max->desc, &config);
        if (IS_ERR(rdev)) {
                ret = PTR_ERR(rdev);
                dev_err(max->dev, "regulator register failed, err %d\n", ret);
@@ -478,14 +478,6 @@ static int max8973_probe(struct i2c_client *client,
        return 0;
 }
 
-static int max8973_remove(struct i2c_client *client)
-{
-       struct max8973_chip *max = i2c_get_clientdata(client);
-
-       regulator_unregister(max->rdev);
-       return 0;
-}
-
 static const struct i2c_device_id max8973_id[] = {
        {.name = "max8973",},
        {},
@@ -499,7 +491,6 @@ static struct i2c_driver max8973_i2c_driver = {
                .owner = THIS_MODULE,
        },
        .probe = max8973_probe,
-       .remove = max8973_remove,
        .id_table = max8973_id,
 };
 
index df20069..bcd2488 100644 (file)
@@ -1081,7 +1081,7 @@ static int max8997_pmic_probe(struct platform_device *pdev)
                                        pdata->buck1_voltage[i] +
                                        buck1245_voltage_map_desc.step);
                if (ret < 0)
-                       goto err_out;
+                       return ret;
 
                max8997->buck2_vol[i] = ret =
                        max8997_get_voltage_proper_val(
@@ -1090,7 +1090,7 @@ static int max8997_pmic_probe(struct platform_device *pdev)
                                        pdata->buck2_voltage[i] +
                                        buck1245_voltage_map_desc.step);
                if (ret < 0)
-                       goto err_out;
+                       return ret;
 
                max8997->buck5_vol[i] = ret =
                        max8997_get_voltage_proper_val(
@@ -1099,7 +1099,7 @@ static int max8997_pmic_probe(struct platform_device *pdev)
                                        pdata->buck5_voltage[i] +
                                        buck1245_voltage_map_desc.step);
                if (ret < 0)
-                       goto err_out;
+                       return ret;
 
                if (max_buck1 < max8997->buck1_vol[i])
                        max_buck1 = max8997->buck1_vol[i];
@@ -1143,24 +1143,23 @@ static int max8997_pmic_probe(struct platform_device *pdev)
                                !gpio_is_valid(pdata->buck125_gpios[1]) ||
                                !gpio_is_valid(pdata->buck125_gpios[2])) {
                        dev_err(&pdev->dev, "GPIO NOT VALID\n");
-                       ret = -EINVAL;
-                       goto err_out;
+                       return -EINVAL;
                }
 
                ret = devm_gpio_request(&pdev->dev, pdata->buck125_gpios[0],
                                        "MAX8997 SET1");
                if (ret)
-                       goto err_out;
+                       return ret;
 
                ret = devm_gpio_request(&pdev->dev, pdata->buck125_gpios[1],
                                        "MAX8997 SET2");
                if (ret)
-                       goto err_out;
+                       return ret;
 
                ret = devm_gpio_request(&pdev->dev, pdata->buck125_gpios[2],
                                "MAX8997 SET3");
                if (ret)
-                       goto err_out;
+                       return ret;
 
                gpio_direction_output(pdata->buck125_gpios[0],
                                (max8997->buck125_gpioindex >> 2)
@@ -1205,33 +1204,16 @@ static int max8997_pmic_probe(struct platform_device *pdev)
                config.driver_data = max8997;
                config.of_node = pdata->regulators[i].reg_node;
 
-               rdev[i] = regulator_register(&regulators[id], &config);
+               rdev[i] = devm_regulator_register(&pdev->dev, &regulators[id],
+                                                 &config);
                if (IS_ERR(rdev[i])) {
-                       ret = PTR_ERR(rdev[i]);
                        dev_err(max8997->dev, "regulator init failed for %d\n",
                                        id);
-                       rdev[i] = NULL;
-                       goto err;
+                       return PTR_ERR(rdev[i]);
                }
        }
 
        return 0;
-err:
-       while (--i >= 0)
-               regulator_unregister(rdev[i]);
-err_out:
-       return ret;
-}
-
-static int max8997_pmic_remove(struct platform_device *pdev)
-{
-       struct max8997_data *max8997 = platform_get_drvdata(pdev);
-       struct regulator_dev **rdev = max8997->rdev;
-       int i;
-
-       for (i = 0; i < max8997->num_regulators; i++)
-               regulator_unregister(rdev[i]);
-       return 0;
 }
 
 static const struct platform_device_id max8997_pmic_id[] = {
@@ -1246,7 +1228,6 @@ static struct platform_driver max8997_pmic_driver = {
                .owner = THIS_MODULE,
        },
        .probe = max8997_pmic_probe,
-       .remove = max8997_pmic_remove,
        .id_table = max8997_pmic_id,
 };
 
index a4c53b2..ae3f065 100644 (file)
@@ -790,16 +790,14 @@ static int max8998_pmic_probe(struct platform_device *pdev)
                        dev_err(&pdev->dev,
                                "MAX8998 SET1 GPIO defined as 0 !\n");
                        WARN_ON(!pdata->buck1_set1);
-                       ret = -EIO;
-                       goto err_out;
+                       return -EIO;
                }
                /* Check if SET2 is not equal to 0 */
                if (!pdata->buck1_set2) {
                        dev_err(&pdev->dev,
                                "MAX8998 SET2 GPIO defined as 0 !\n");
                        WARN_ON(!pdata->buck1_set2);
-                       ret = -EIO;
-                       goto err_out;
+                       return -EIO;
                }
 
                gpio_request(pdata->buck1_set1, "MAX8998 BUCK1_SET1");
@@ -823,7 +821,7 @@ static int max8998_pmic_probe(struct platform_device *pdev)
                        ret = max8998_write_reg(i2c,
                                        MAX8998_REG_BUCK1_VOLTAGE1 + v, i);
                        if (ret)
-                               goto err_out;
+                               return ret;
                }
        }
 
@@ -833,8 +831,7 @@ static int max8998_pmic_probe(struct platform_device *pdev)
                        dev_err(&pdev->dev,
                                "MAX8998 SET3 GPIO defined as 0 !\n");
                        WARN_ON(!pdata->buck2_set3);
-                       ret = -EIO;
-                       goto err_out;
+                       return -EIO;
                }
                gpio_request(pdata->buck2_set3, "MAX8998 BUCK2_SET3");
                gpio_direction_output(pdata->buck2_set3,
@@ -852,7 +849,7 @@ static int max8998_pmic_probe(struct platform_device *pdev)
                        ret = max8998_write_reg(i2c,
                                        MAX8998_REG_BUCK2_VOLTAGE1 + v, i);
                        if (ret)
-                               goto err_out;
+                               return ret;
                }
        }
 
@@ -875,34 +872,19 @@ static int max8998_pmic_probe(struct platform_device *pdev)
                config.init_data = pdata->regulators[i].initdata;
                config.driver_data = max8998;
 
-               rdev[i] = regulator_register(&regulators[index], &config);
+               rdev[i] = devm_regulator_register(&pdev->dev,
+                                                 &regulators[index], &config);
                if (IS_ERR(rdev[i])) {
                        ret = PTR_ERR(rdev[i]);
                        dev_err(max8998->dev, "regulator %s init failed (%d)\n",
                                                regulators[index].name, ret);
                        rdev[i] = NULL;
-                       goto err;
+                       return ret;
                }
        }
 
 
        return 0;
-err:
-       while (--i >= 0)
-               regulator_unregister(rdev[i]);
-err_out:
-       return ret;
-}
-
-static int max8998_pmic_remove(struct platform_device *pdev)
-{
-       struct max8998_data *max8998 = platform_get_drvdata(pdev);
-       struct regulator_dev **rdev = max8998->rdev;
-       int i;
-
-       for (i = 0; i < max8998->num_regulators; i++)
-               regulator_unregister(rdev[i]);
-       return 0;
 }
 
 static const struct platform_device_id max8998_pmic_id[] = {
@@ -918,7 +900,6 @@ static struct platform_driver max8998_pmic_driver = {
                .owner = THIS_MODULE,
        },
        .probe = max8998_pmic_probe,
-       .remove = max8998_pmic_remove,
        .id_table = max8998_pmic_id,
 };
 
index 5ff99d2..f036b26 100644 (file)
@@ -400,7 +400,7 @@ static int mc13783_regulator_probe(struct platform_device *pdev)
                dev_get_platdata(&pdev->dev);
        struct mc13xxx_regulator_init_data *mc13xxx_data;
        struct regulator_config config = { };
-       int i, ret, num_regulators;
+       int i, num_regulators;
 
        num_regulators = mc13xxx_get_num_regulators_dt(pdev);
 
@@ -444,32 +444,16 @@ static int mc13783_regulator_probe(struct platform_device *pdev)
                config.driver_data = priv;
                config.of_node = node;
 
-               priv->regulators[i] = regulator_register(desc, &config);
+               priv->regulators[i] = devm_regulator_register(&pdev->dev, desc,
+                                                             &config);
                if (IS_ERR(priv->regulators[i])) {
                        dev_err(&pdev->dev, "failed to register regulator %s\n",
                                mc13783_regulators[i].desc.name);
-                       ret = PTR_ERR(priv->regulators[i]);
-                       goto err;
+                       return PTR_ERR(priv->regulators[i]);
                }
        }
 
        return 0;
-err:
-       while (--i >= 0)
-               regulator_unregister(priv->regulators[i]);
-
-       return ret;
-}
-
-static int mc13783_regulator_remove(struct platform_device *pdev)
-{
-       struct mc13xxx_regulator_priv *priv = platform_get_drvdata(pdev);
-       int i;
-
-       for (i = 0; i < priv->num_regulators; i++)
-               regulator_unregister(priv->regulators[i]);
-
-       return 0;
 }
 
 static struct platform_driver mc13783_regulator_driver = {
@@ -477,7 +461,6 @@ static struct platform_driver mc13783_regulator_driver = {
                .name   = "mc13783-regulator",
                .owner  = THIS_MODULE,
        },
-       .remove         = mc13783_regulator_remove,
        .probe          = mc13783_regulator_probe,
 };
 
index 1037e07..96c9f80 100644 (file)
@@ -611,43 +611,27 @@ static int mc13892_regulator_probe(struct platform_device *pdev)
                config.driver_data = priv;
                config.of_node = node;
 
-               priv->regulators[i] = regulator_register(desc, &config);
+               priv->regulators[i] = devm_regulator_register(&pdev->dev, desc,
+                                                             &config);
                if (IS_ERR(priv->regulators[i])) {
                        dev_err(&pdev->dev, "failed to register regulator %s\n",
                                mc13892_regulators[i].desc.name);
-                       ret = PTR_ERR(priv->regulators[i]);
-                       goto err;
+                       return PTR_ERR(priv->regulators[i]);
                }
        }
 
        return 0;
-err:
-       while (--i >= 0)
-               regulator_unregister(priv->regulators[i]);
-       return ret;
 
 err_unlock:
        mc13xxx_unlock(mc13892);
        return ret;
 }
 
-static int mc13892_regulator_remove(struct platform_device *pdev)
-{
-       struct mc13xxx_regulator_priv *priv = platform_get_drvdata(pdev);
-       int i;
-
-       for (i = 0; i < priv->num_regulators; i++)
-               regulator_unregister(priv->regulators[i]);
-
-       return 0;
-}
-
 static struct platform_driver mc13892_regulator_driver = {
        .driver = {
                .name   = "mc13892-regulator",
                .owner  = THIS_MODULE,
        },
-       .remove = mc13892_regulator_remove,
        .probe  = mc13892_regulator_probe,
 };
 
index 7e2b165..4f79c0d 100644 (file)
@@ -856,7 +856,7 @@ static int palmas_regulators_probe(struct platform_device *pdev)
                        if (ret < 0) {
                                dev_err(&pdev->dev,
                                        "reading TSTEP reg failed: %d\n", ret);
-                               goto err_unregister_regulator;
+                               return ret;
                        }
                        pmic->desc[id].ramp_delay =
                                        palmas_smps_ramp_delay[reg & 0x3];
@@ -868,7 +868,7 @@ static int palmas_regulators_probe(struct platform_device *pdev)
                        reg_init = pdata->reg_init[id];
                        ret = palmas_smps_init(palmas, id, reg_init);
                        if (ret)
-                               goto err_unregister_regulator;
+                               return ret;
                }
 
                /* Register the regulators */
@@ -909,7 +909,7 @@ static int palmas_regulators_probe(struct platform_device *pdev)
 
                        ret = palmas_smps_read(pmic->palmas, addr, &reg);
                        if (ret)
-                               goto err_unregister_regulator;
+                               return ret;
                        if (reg & PALMAS_SMPS12_VOLTAGE_RANGE)
                                pmic->range[id] = 1;
 
@@ -925,7 +925,7 @@ static int palmas_regulators_probe(struct platform_device *pdev)
                        addr = palmas_regs_info[id].ctrl_addr;
                        ret = palmas_smps_read(pmic->palmas, addr, &reg);
                        if (ret)
-                               goto err_unregister_regulator;
+                               return ret;
                        pmic->current_reg_mode[id] = reg &
                                        PALMAS_SMPS12_CTRL_MODE_ACTIVE_MASK;
                }
@@ -941,13 +941,13 @@ static int palmas_regulators_probe(struct platform_device *pdev)
                pmic->desc[id].supply_name = palmas_regs_info[id].sname;
                config.of_node = palmas_matches[id].of_node;
 
-               rdev = regulator_register(&pmic->desc[id], &config);
+               rdev = devm_regulator_register(&pdev->dev, &pmic->desc[id],
+                                              &config);
                if (IS_ERR(rdev)) {
                        dev_err(&pdev->dev,
                                "failed to register %s regulator\n",
                                pdev->name);
-                       ret = PTR_ERR(rdev);
-                       goto err_unregister_regulator;
+                       return PTR_ERR(rdev);
                }
 
                /* Save regulator for cleanup */
@@ -1015,13 +1015,13 @@ static int palmas_regulators_probe(struct platform_device *pdev)
                pmic->desc[id].supply_name = palmas_regs_info[id].sname;
                config.of_node = palmas_matches[id].of_node;
 
-               rdev = regulator_register(&pmic->desc[id], &config);
+               rdev = devm_regulator_register(&pdev->dev, &pmic->desc[id],
+                                              &config);
                if (IS_ERR(rdev)) {
                        dev_err(&pdev->dev,
                                "failed to register %s regulator\n",
                                pdev->name);
-                       ret = PTR_ERR(rdev);
-                       goto err_unregister_regulator;
+                       return PTR_ERR(rdev);
                }
 
                /* Save regulator for cleanup */
@@ -1037,31 +1037,14 @@ static int palmas_regulators_probe(struct platform_device *pdev)
                                else
                                        ret = palmas_extreg_init(palmas,
                                                        id, reg_init);
-                               if (ret) {
-                                       regulator_unregister(pmic->rdev[id]);
-                                       goto err_unregister_regulator;
-                               }
+                               if (ret)
+                                       return ret;
                        }
                }
        }
 
 
        return 0;
-
-err_unregister_regulator:
-       while (--id >= 0)
-               regulator_unregister(pmic->rdev[id]);
-       return ret;
-}
-
-static int palmas_regulators_remove(struct platform_device *pdev)
-{
-       struct palmas_pmic *pmic = platform_get_drvdata(pdev);
-       int id;
-
-       for (id = 0; id < PALMAS_NUM_REGS; id++)
-               regulator_unregister(pmic->rdev[id]);
-       return 0;
 }
 
 static struct of_device_id of_palmas_match_tbl[] = {
@@ -1083,7 +1066,6 @@ static struct platform_driver palmas_driver = {
                .owner = THIS_MODULE,
        },
        .probe = palmas_regulators_probe,
-       .remove = palmas_regulators_remove,
 };
 
 static int __init palmas_init(void)
index 5885b45..b58affb 100644 (file)
@@ -173,33 +173,16 @@ skip_ext_pwr_config:
                config.driver_data = reg;
                config.regmap = rc5t583->regmap;
 
-               rdev = regulator_register(&ri->desc, &config);
+               rdev = devm_regulator_register(&pdev->dev, &ri->desc, &config);
                if (IS_ERR(rdev)) {
                        dev_err(&pdev->dev, "Failed to register regulator %s\n",
                                                ri->desc.name);
-                       ret = PTR_ERR(rdev);
-                       goto clean_exit;
+                       return PTR_ERR(rdev);
                }
                reg->rdev = rdev;
        }
        platform_set_drvdata(pdev, regs);
        return 0;
-
-clean_exit:
-       while (--id >= 0)
-               regulator_unregister(regs[id].rdev);
-
-       return ret;
-}
-
-static int rc5t583_regulator_remove(struct platform_device *pdev)
-{
-       struct rc5t583_regulator *regs = platform_get_drvdata(pdev);
-       int id;
-
-       for (id = 0; id < RC5T583_REGULATOR_MAX; ++id)
-               regulator_unregister(regs[id].rdev);
-       return 0;
 }
 
 static struct platform_driver rc5t583_regulator_driver = {
@@ -208,7 +191,6 @@ static struct platform_driver rc5t583_regulator_driver = {
                .owner  = THIS_MODULE,
        },
        .probe          = rc5t583_regulator_probe,
-       .remove         = rc5t583_regulator_remove,
 };
 
 static int __init rc5t583_regulator_init(void)
index 5eba2ff..333677d 100644 (file)
@@ -448,33 +448,17 @@ common_reg:
                        config.of_node = rdata[i].of_node;
                }
 
-               s2mps11->rdev[i] = regulator_register(&regulators[i], &config);
+               s2mps11->rdev[i] = devm_regulator_register(&pdev->dev,
+                                               &regulators[i], &config);
                if (IS_ERR(s2mps11->rdev[i])) {
                        ret = PTR_ERR(s2mps11->rdev[i]);
                        dev_err(&pdev->dev, "regulator init failed for %d\n",
                                i);
-                       s2mps11->rdev[i] = NULL;
-                       goto err;
+                       return ret;
                }
        }
 
        return 0;
-err:
-       for (i = 0; i < S2MPS11_REGULATOR_MAX; i++)
-               regulator_unregister(s2mps11->rdev[i]);
-
-       return ret;
-}
-
-static int s2mps11_pmic_remove(struct platform_device *pdev)
-{
-       struct s2mps11_info *s2mps11 = platform_get_drvdata(pdev);
-       int i;
-
-       for (i = 0; i < S2MPS11_REGULATOR_MAX; i++)
-               regulator_unregister(s2mps11->rdev[i]);
-
-       return 0;
 }
 
 static const struct platform_device_id s2mps11_pmic_id[] = {
@@ -489,7 +473,6 @@ static struct platform_driver s2mps11_pmic_driver = {
                .owner = THIS_MODULE,
        },
        .probe = s2mps11_pmic_probe,
-       .remove = s2mps11_pmic_remove,
        .id_table = s2mps11_pmic_id,
 };
 
index c24448b..2297fdf 100644 (file)
@@ -910,34 +910,17 @@ static int s5m8767_pmic_probe(struct platform_device *pdev)
                config.regmap = iodev->regmap;
                config.of_node = pdata->regulators[i].reg_node;
 
-               rdev[i] = regulator_register(&regulators[id], &config);
+               rdev[i] = devm_regulator_register(&pdev->dev, &regulators[id],
+                                                 &config);
                if (IS_ERR(rdev[i])) {
                        ret = PTR_ERR(rdev[i]);
                        dev_err(s5m8767->dev, "regulator init failed for %d\n",
                                        id);
-                       rdev[i] = NULL;
-                       goto err;
+                       return ret;
                }
        }
 
        return 0;
-err:
-       for (i = 0; i < s5m8767->num_regulators; i++)
-               regulator_unregister(rdev[i]);
-
-       return ret;
-}
-
-static int s5m8767_pmic_remove(struct platform_device *pdev)
-{
-       struct s5m8767_info *s5m8767 = platform_get_drvdata(pdev);
-       struct regulator_dev **rdev = s5m8767->rdev;
-       int i;
-
-       for (i = 0; i < s5m8767->num_regulators; i++)
-               regulator_unregister(rdev[i]);
-
-       return 0;
 }
 
 static const struct platform_device_id s5m8767_pmic_id[] = {
@@ -952,7 +935,6 @@ static struct platform_driver s5m8767_pmic_driver = {
                .owner = THIS_MODULE,
        },
        .probe = s5m8767_pmic_probe,
-       .remove = s5m8767_pmic_remove,
        .id_table = s5m8767_pmic_id,
 };
 
index b993ec5..20aab8f 100644 (file)
@@ -708,39 +708,31 @@ static int ti_abb_probe(struct platform_device *pdev)
        match = of_match_device(ti_abb_of_match, dev);
        if (!match) {
                /* We do not expect this to happen */
-               ret = -ENODEV;
                dev_err(dev, "%s: Unable to match device\n", __func__);
-               goto err;
+               return -ENODEV;
        }
        if (!match->data) {
-               ret = -EINVAL;
                dev_err(dev, "%s: Bad data in match\n", __func__);
-               goto err;
+               return -EINVAL;
        }
 
        abb = devm_kzalloc(dev, sizeof(struct ti_abb), GFP_KERNEL);
-       if (!abb) {
-               dev_err(dev, "%s: Unable to allocate ABB struct\n", __func__);
-               ret = -ENOMEM;
-               goto err;
-       }
+       if (!abb)
+               return -ENOMEM;
        abb->regs = match->data;
 
        /* Map ABB resources */
        pname = "base-address";
        res = platform_get_resource_byname(pdev, IORESOURCE_MEM, pname);
        abb->base = devm_ioremap_resource(dev, res);
-       if (IS_ERR(abb->base)) {
-               ret = PTR_ERR(abb->base);
-               goto err;
-       }
+       if (IS_ERR(abb->base))
+               return PTR_ERR(abb->base);
 
        pname = "int-address";
        res = platform_get_resource_byname(pdev, IORESOURCE_MEM, pname);
        if (!res) {
                dev_err(dev, "Missing '%s' IO resource\n", pname);
-               ret = -ENODEV;
-               goto err;
+               return -ENODEV;
        }
        /*
         * We may have shared interrupt register offsets which are
@@ -750,8 +742,7 @@ static int ti_abb_probe(struct platform_device *pdev)
                                             resource_size(res));
        if (!abb->int_base) {
                dev_err(dev, "Unable to map '%s'\n", pname);
-               ret = -ENOMEM;
-               goto err;
+               return -ENOMEM;
        }
 
        /* Map Optional resources */
@@ -771,17 +762,14 @@ static int ti_abb_probe(struct platform_device *pdev)
                                               resource_size(res));
        if (!abb->efuse_base) {
                dev_err(dev, "Unable to map '%s'\n", pname);
-               ret = -ENOMEM;
-               goto err;
+               return -ENOMEM;
        }
 
        pname = "ldo-address";
        res = platform_get_resource_byname(pdev, IORESOURCE_MEM, pname);
        abb->ldo_base = devm_ioremap_resource(dev, res);
-       if (IS_ERR(abb->ldo_base)) {
-               ret = PTR_ERR(abb->ldo_base);
-               goto err;
-       }
+       if (IS_ERR(abb->ldo_base))
+               return PTR_ERR(abb->ldo_base);
 
        /* IF ldo_base is set, the following are mandatory */
        pname = "ti,ldovbb-override-mask";
@@ -790,12 +778,11 @@ static int ti_abb_probe(struct platform_device *pdev)
                                 &abb->ldovbb_override_mask);
        if (ret) {
                dev_err(dev, "Missing '%s' (%d)\n", pname, ret);
-               goto err;
+               return ret;
        }
        if (!abb->ldovbb_override_mask) {
                dev_err(dev, "Invalid property:'%s' set as 0!\n", pname);
-               ret = -EINVAL;
-               goto err;
+               return -EINVAL;
        }
 
        pname = "ti,ldovbb-vset-mask";
@@ -804,12 +791,11 @@ static int ti_abb_probe(struct platform_device *pdev)
                                 &abb->ldovbb_vset_mask);
        if (ret) {
                dev_err(dev, "Missing '%s' (%d)\n", pname, ret);
-               goto err;
+               return ret;
        }
        if (!abb->ldovbb_vset_mask) {
                dev_err(dev, "Invalid property:'%s' set as 0!\n", pname);
-               ret = -EINVAL;
-               goto err;
+               return -EINVAL;
        }
 
 skip_opt:
@@ -819,31 +805,29 @@ skip_opt:
                                 &abb->txdone_mask);
        if (ret) {
                dev_err(dev, "Missing '%s' (%d)\n", pname, ret);
-               goto err;
+               return ret;
        }
        if (!abb->txdone_mask) {
                dev_err(dev, "Invalid property:'%s' set as 0!\n", pname);
-               ret = -EINVAL;
-               goto err;
+               return -EINVAL;
        }
 
        initdata = of_get_regulator_init_data(dev, pdev->dev.of_node);
        if (!initdata) {
-               ret = -ENOMEM;
                dev_err(dev, "%s: Unable to alloc regulator init data\n",
                        __func__);
-               goto err;
+               return -ENOMEM;
        }
 
        /* init ABB opp_sel table */
        ret = ti_abb_init_table(dev, abb, initdata);
        if (ret)
-               goto err;
+               return ret;
 
        /* init ABB timing */
        ret = ti_abb_init_timings(dev, abb);
        if (ret)
-               goto err;
+               return ret;
 
        desc = &abb->rdesc;
        desc->name = dev_name(dev);
@@ -861,12 +845,12 @@ skip_opt:
        config.driver_data = abb;
        config.of_node = pdev->dev.of_node;
 
-       rdev = regulator_register(desc, &config);
+       rdev = devm_regulator_register(dev, desc, &config);
        if (IS_ERR(rdev)) {
                ret = PTR_ERR(rdev);
                dev_err(dev, "%s: failed to register regulator(%d)\n",
                        __func__, ret);
-               goto err;
+               return ret;
        }
        platform_set_drvdata(pdev, rdev);
 
@@ -874,31 +858,12 @@ skip_opt:
        ti_abb_rmw(abb->regs->sr2_en_mask, 1, abb->regs->setup_reg, abb->base);
 
        return 0;
-
-err:
-       dev_err(dev, "%s: Failed to initialize(%d)\n", __func__, ret);
-       return ret;
-}
-
-/**
- * ti_abb_remove() - cleanups
- * @pdev: ABB platform device
- *
- * Return: 0
- */
-static int ti_abb_remove(struct platform_device *pdev)
-{
-       struct regulator_dev *rdev = platform_get_drvdata(pdev);
-
-       regulator_unregister(rdev);
-       return 0;
 }
 
 MODULE_ALIAS("platform:ti_abb");
 
 static struct platform_driver ti_abb_driver = {
        .probe = ti_abb_probe,
-       .remove = ti_abb_remove,
        .driver = {
                   .name = "ti_abb",
                   .owner = THIS_MODULE,
index 9392a7c..b0a3f09 100644 (file)
@@ -343,7 +343,7 @@ static int tps51632_probe(struct i2c_client *client,
        config.regmap = tps->regmap;
        config.of_node = client->dev.of_node;
 
-       rdev = regulator_register(&tps->desc, &config);
+       rdev = devm_regulator_register(&client->dev, &tps->desc, &config);
        if (IS_ERR(rdev)) {
                dev_err(tps->dev, "regulator register failed\n");
                return PTR_ERR(rdev);
@@ -353,14 +353,6 @@ static int tps51632_probe(struct i2c_client *client,
        return 0;
 }
 
-static int tps51632_remove(struct i2c_client *client)
-{
-       struct tps51632_chip *tps = i2c_get_clientdata(client);
-
-       regulator_unregister(tps->rdev);
-       return 0;
-}
-
 static const struct i2c_device_id tps51632_id[] = {
        {.name = "tps51632",},
        {},
@@ -375,7 +367,6 @@ static struct i2c_driver tps51632_i2c_driver = {
                .of_match_table = of_match_ptr(tps51632_of_match),
        },
        .probe = tps51632_probe,
-       .remove = tps51632_remove,
        .id_table = tps51632_id,
 };
 
index 0b7ebb1..c2c0185 100644 (file)
@@ -476,7 +476,7 @@ static int tps62360_probe(struct i2c_client *client,
        config.of_node = client->dev.of_node;
 
        /* Register the regulators */
-       rdev = regulator_register(&tps->desc, &config);
+       rdev = devm_regulator_register(&client->dev, &tps->desc, &config);
        if (IS_ERR(rdev)) {
                dev_err(tps->dev,
                        "%s(): regulator register failed with err %s\n",
@@ -488,20 +488,6 @@ static int tps62360_probe(struct i2c_client *client,
        return 0;
 }
 
-/**
- * tps62360_remove - tps62360 driver i2c remove handler
- * @client: i2c driver client device structure
- *
- * Unregister TPS driver as an i2c client device driver
- */
-static int tps62360_remove(struct i2c_client *client)
-{
-       struct tps62360_chip *tps = i2c_get_clientdata(client);
-
-       regulator_unregister(tps->rdev);
-       return 0;
-}
-
 static void tps62360_shutdown(struct i2c_client *client)
 {
        struct tps62360_chip *tps = i2c_get_clientdata(client);
@@ -535,7 +521,6 @@ static struct i2c_driver tps62360_i2c_driver = {
                .of_match_table = of_match_ptr(tps62360_of_match),
        },
        .probe = tps62360_probe,
-       .remove = tps62360_remove,
        .shutdown = tps62360_shutdown,
        .id_table = tps62360_id,
 };
index a15263d..a957579 100644 (file)
@@ -277,12 +277,12 @@ static int tps_65023_probe(struct i2c_client *client,
                config.regmap = tps->regmap;
 
                /* Register the regulators */
-               rdev = regulator_register(&tps->desc[i], &config);
+               rdev = devm_regulator_register(&client->dev, &tps->desc[i],
+                                              &config);
                if (IS_ERR(rdev)) {
                        dev_err(&client->dev, "failed to register %s\n",
                                id->name);
-                       error = PTR_ERR(rdev);
-                       goto fail;
+                       return PTR_ERR(rdev);
                }
 
                /* Save regulator for cleanup */
@@ -296,21 +296,6 @@ static int tps_65023_probe(struct i2c_client *client,
                        TPS65023_REG_CTRL2_CORE_ADJ, TPS65023_REG_CTRL2_CORE_ADJ);
 
        return 0;
-
- fail:
-       while (--i >= 0)
-               regulator_unregister(tps->rdev[i]);
-       return error;
-}
-
-static int tps_65023_remove(struct i2c_client *client)
-{
-       struct tps_pmic *tps = i2c_get_clientdata(client);
-       int i;
-
-       for (i = 0; i < TPS65023_NUM_REGULATOR; i++)
-               regulator_unregister(tps->rdev[i]);
-       return 0;
 }
 
 static const struct tps_info tps65020_regs[] = {
@@ -430,7 +415,6 @@ static struct i2c_driver tps_65023_i2c_driver = {
                .owner = THIS_MODULE,
        },
        .probe = tps_65023_probe,
-       .remove = tps_65023_remove,
        .id_table = tps_65023_id,
 };
 
index 4117ff5..162a0fa 100644 (file)
@@ -508,13 +508,13 @@ static int tps6507x_pmic_probe(struct platform_device *pdev)
                        config.of_node = tps6507x_reg_matches[i].of_node;
                }
 
-               rdev = regulator_register(&tps->desc[i], &config);
+               rdev = devm_regulator_register(&pdev->dev, &tps->desc[i],
+                                              &config);
                if (IS_ERR(rdev)) {
                        dev_err(tps6507x_dev->dev,
                                "failed to register %s regulator\n",
                                pdev->name);
-                       error = PTR_ERR(rdev);
-                       goto fail;
+                       return PTR_ERR(rdev);
                }
 
                /* Save regulator for cleanup */
@@ -525,22 +525,6 @@ static int tps6507x_pmic_probe(struct platform_device *pdev)
        platform_set_drvdata(pdev, tps6507x_dev);
 
        return 0;
-
-fail:
-       while (--i >= 0)
-               regulator_unregister(tps->rdev[i]);
-       return error;
-}
-
-static int tps6507x_pmic_remove(struct platform_device *pdev)
-{
-       struct tps6507x_dev *tps6507x_dev = platform_get_drvdata(pdev);
-       struct tps6507x_pmic *tps = tps6507x_dev->pmic;
-       int i;
-
-       for (i = 0; i < TPS6507X_NUM_REGULATOR; i++)
-               regulator_unregister(tps->rdev[i]);
-       return 0;
 }
 
 static struct platform_driver tps6507x_pmic_driver = {
@@ -549,7 +533,6 @@ static struct platform_driver tps6507x_pmic_driver = {
                .owner = THIS_MODULE,
        },
        .probe = tps6507x_pmic_probe,
-       .remove = tps6507x_pmic_remove,
 };
 
 static int __init tps6507x_pmic_init(void)
index c8e7045..bd611cd 100644 (file)
@@ -279,7 +279,7 @@ static int tps65090_regulator_probe(struct platform_device *pdev)
                                if (ret < 0) {
                                        dev_err(&pdev->dev,
                                                "failed disable ext control\n");
-                                       goto scrub;
+                                       return ret;
                                }
                        }
                }
@@ -296,12 +296,11 @@ static int tps65090_regulator_probe(struct platform_device *pdev)
                else
                        config.of_node = NULL;
 
-               rdev = regulator_register(ri->desc, &config);
+               rdev = devm_regulator_register(&pdev->dev, ri->desc, &config);
                if (IS_ERR(rdev)) {
                        dev_err(&pdev->dev, "failed to register regulator %s\n",
                                ri->desc->name);
-                       ret = PTR_ERR(rdev);
-                       goto scrub;
+                       return PTR_ERR(rdev);
                }
                ri->rdev = rdev;
 
@@ -309,36 +308,13 @@ static int tps65090_regulator_probe(struct platform_device *pdev)
                if (tps_pdata && is_dcdc(num) && tps_pdata->reg_init_data &&
                                tps_pdata->enable_ext_control) {
                        ret = tps65090_config_ext_control(ri, true);
-                       if (ret < 0) {
-                               /* Increment num to get unregister rdev */
-                               num++;
-                               goto scrub;
-                       }
+                       if (ret < 0)
+                               return ret;
                }
        }
 
        platform_set_drvdata(pdev, pmic);
        return 0;
-
-scrub:
-       while (--num >= 0) {
-               ri = &pmic[num];
-               regulator_unregister(ri->rdev);
-       }
-       return ret;
-}
-
-static int tps65090_regulator_remove(struct platform_device *pdev)
-{
-       struct tps65090_regulator *pmic = platform_get_drvdata(pdev);
-       struct tps65090_regulator *ri;
-       int num;
-
-       for (num = 0; num < TPS65090_REGULATOR_MAX; ++num) {
-               ri = &pmic[num];
-               regulator_unregister(ri->rdev);
-       }
-       return 0;
 }
 
 static struct platform_driver tps65090_regulator_driver = {
@@ -347,7 +323,6 @@ static struct platform_driver tps65090_regulator_driver = {
                .owner  = THIS_MODULE,
        },
        .probe          = tps65090_regulator_probe,
-       .remove         = tps65090_regulator_remove,
 };
 
 static int __init tps65090_regulator_init(void)
index 90861d6..8860379 100644 (file)
@@ -233,7 +233,7 @@ static int tps65217_regulator_probe(struct platform_device *pdev)
        struct regulator_init_data *reg_data;
        struct regulator_dev *rdev;
        struct regulator_config config = { };
-       int i, ret;
+       int i;
 
        if (tps->dev->of_node)
                pdata = tps65217_parse_dt(pdev);
@@ -269,35 +269,18 @@ static int tps65217_regulator_probe(struct platform_device *pdev)
                if (tps->dev->of_node)
                        config.of_node = pdata->of_node[i];
 
-               rdev = regulator_register(&regulators[i], &config);
+               rdev = devm_regulator_register(&pdev->dev, &regulators[i],
+                                              &config);
                if (IS_ERR(rdev)) {
                        dev_err(tps->dev, "failed to register %s regulator\n",
                                pdev->name);
-                       ret = PTR_ERR(rdev);
-                       goto err_unregister_regulator;
+                       return PTR_ERR(rdev);
                }
 
                /* Save regulator for cleanup */
                tps->rdev[i] = rdev;
        }
        return 0;
-
-err_unregister_regulator:
-       while (--i >= 0)
-               regulator_unregister(tps->rdev[i]);
-
-       return ret;
-}
-
-static int tps65217_regulator_remove(struct platform_device *pdev)
-{
-       struct tps65217 *tps = platform_get_drvdata(pdev);
-       unsigned int i;
-
-       for (i = 0; i < TPS65217_NUM_REGULATOR; i++)
-               regulator_unregister(tps->rdev[i]);
-
-       return 0;
 }
 
 static struct platform_driver tps65217_regulator_driver = {
@@ -305,7 +288,6 @@ static struct platform_driver tps65217_regulator_driver = {
                .name = "tps65217-pmic",
        },
        .probe = tps65217_regulator_probe,
-       .remove = tps65217_regulator_remove,
 };
 
 static int __init tps65217_regulator_init(void)
index 2c9155b..45e5d68 100644 (file)
@@ -379,15 +379,14 @@ static int tps6586x_regulator_probe(struct platform_device *pdev)
                ri = find_regulator_info(id);
                if (!ri) {
                        dev_err(&pdev->dev, "invalid regulator ID specified\n");
-                       err = -EINVAL;
-                       goto fail;
+                       return -EINVAL;
                }
 
                err = tps6586x_regulator_preinit(pdev->dev.parent, ri);
                if (err) {
                        dev_err(&pdev->dev,
                                "regulator %d preinit failed, e %d\n", id, err);
-                       goto fail;
+                       return err;
                }
 
                config.dev = pdev->dev.parent;
@@ -397,12 +396,12 @@ static int tps6586x_regulator_probe(struct platform_device *pdev)
                if (tps6586x_reg_matches)
                        config.of_node = tps6586x_reg_matches[id].of_node;
 
-               rdev[id] = regulator_register(&ri->desc, &config);
+               rdev[id] = devm_regulator_register(&pdev->dev, &ri->desc,
+                                                  &config);
                if (IS_ERR(rdev[id])) {
                        dev_err(&pdev->dev, "failed to register regulator %s\n",
                                        ri->desc.name);
-                       err = PTR_ERR(rdev[id]);
-                       goto fail;
+                       return PTR_ERR(rdev[id]);
                }
 
                if (reg_data) {
@@ -411,30 +410,13 @@ static int tps6586x_regulator_probe(struct platform_device *pdev)
                        if (err < 0) {
                                dev_err(&pdev->dev,
                                        "Slew rate config failed, e %d\n", err);
-                               regulator_unregister(rdev[id]);
-                               goto fail;
+                               return err;
                        }
                }
        }
 
        platform_set_drvdata(pdev, rdev);
        return 0;
-
-fail:
-       while (--id >= 0)
-               regulator_unregister(rdev[id]);
-       return err;
-}
-
-static int tps6586x_regulator_remove(struct platform_device *pdev)
-{
-       struct regulator_dev **rdev = platform_get_drvdata(pdev);
-       int id = TPS6586X_ID_MAX_REGULATOR;
-
-       while (--id >= 0)
-               regulator_unregister(rdev[id]);
-
-       return 0;
 }
 
 static struct platform_driver tps6586x_regulator_driver = {
@@ -443,7 +425,6 @@ static struct platform_driver tps6586x_regulator_driver = {
                .owner  = THIS_MODULE,
        },
        .probe          = tps6586x_regulator_probe,
-       .remove         = tps6586x_regulator_remove,
 };
 
 static int __init tps6586x_regulator_init(void)
index 45c1644..b8167df 100644 (file)
@@ -1177,35 +1177,19 @@ static int tps65910_probe(struct platform_device *pdev)
                if (tps65910_reg_matches)
                        config.of_node = tps65910_reg_matches[i].of_node;
 
-               rdev = regulator_register(&pmic->desc[i], &config);
+               rdev = devm_regulator_register(&pdev->dev, &pmic->desc[i],
+                                              &config);
                if (IS_ERR(rdev)) {
                        dev_err(tps65910->dev,
                                "failed to register %s regulator\n",
                                pdev->name);
-                       err = PTR_ERR(rdev);
-                       goto err_unregister_regulator;
+                       return PTR_ERR(rdev);
                }
 
                /* Save regulator for cleanup */
                pmic->rdev[i] = rdev;
        }
        return 0;
-
-err_unregister_regulator:
-       while (--i >= 0)
-               regulator_unregister(pmic->rdev[i]);
-       return err;
-}
-
-static int tps65910_remove(struct platform_device *pdev)
-{
-       struct tps65910_reg *pmic = platform_get_drvdata(pdev);
-       int i;
-
-       for (i = 0; i < pmic->num_regulators; i++)
-               regulator_unregister(pmic->rdev[i]);
-
-       return 0;
 }
 
 static void tps65910_shutdown(struct platform_device *pdev)
@@ -1244,7 +1228,6 @@ static struct platform_driver tps65910_driver = {
                .owner = THIS_MODULE,
        },
        .probe = tps65910_probe,
-       .remove = tps65910_remove,
        .shutdown = tps65910_shutdown,
 };
 
index 281e52a..1ed4d04 100644 (file)
@@ -461,7 +461,7 @@ static int tps65912_probe(struct platform_device *pdev)
        struct regulator_dev *rdev;
        struct tps65912_reg *pmic;
        struct tps65912_board *pmic_plat_data;
-       int i, err;
+       int i;
 
        pmic_plat_data = dev_get_platdata(tps65912->dev);
        if (!pmic_plat_data)
@@ -504,34 +504,19 @@ static int tps65912_probe(struct platform_device *pdev)
                config.init_data = reg_data;
                config.driver_data = pmic;
 
-               rdev = regulator_register(&pmic->desc[i], &config);
+               rdev = devm_regulator_register(&pdev->dev, &pmic->desc[i],
+                                              &config);
                if (IS_ERR(rdev)) {
                        dev_err(tps65912->dev,
                                "failed to register %s regulator\n",
                                pdev->name);
-                       err = PTR_ERR(rdev);
-                       goto err;
+                       return PTR_ERR(rdev);
                }
 
                /* Save regulator for cleanup */
                pmic->rdev[i] = rdev;
        }
        return 0;
-
-err:
-       while (--i >= 0)
-               regulator_unregister(pmic->rdev[i]);
-       return err;
-}
-
-static int tps65912_remove(struct platform_device *pdev)
-{
-       struct tps65912_reg *tps65912_reg = platform_get_drvdata(pdev);
-       int i;
-
-       for (i = 0; i < TPS65912_NUM_REGULATOR; i++)
-               regulator_unregister(tps65912_reg->rdev[i]);
-       return 0;
 }
 
 static struct platform_driver tps65912_driver = {
@@ -540,7 +525,6 @@ static struct platform_driver tps65912_driver = {
                .owner = THIS_MODULE,
        },
        .probe = tps65912_probe,
-       .remove = tps65912_remove,
 };
 
 static int __init tps65912_init(void)
index 6511d0b..71f457a 100644 (file)
@@ -719,7 +719,7 @@ static int tps80031_regulator_probe(struct platform_device *pdev)
                        if (ret < 0) {
                                dev_err(&pdev->dev,
                                        "regulator config failed, e %d\n", ret);
-                               goto fail;
+                               return ret;
                        }
 
                        ret = tps80031_power_req_config(pdev->dev.parent,
@@ -727,41 +727,22 @@ static int tps80031_regulator_probe(struct platform_device *pdev)
                        if (ret < 0) {
                                dev_err(&pdev->dev,
                                        "pwr_req config failed, err %d\n", ret);
-                               goto fail;
+                               return ret;
                        }
                }
-               rdev = regulator_register(&ri->rinfo->desc, &config);
+               rdev = devm_regulator_register(&pdev->dev, &ri->rinfo->desc,
+                                              &config);
                if (IS_ERR(rdev)) {
                        dev_err(&pdev->dev,
                                "register regulator failed %s\n",
                                        ri->rinfo->desc.name);
-                       ret = PTR_ERR(rdev);
-                       goto fail;
+                       return PTR_ERR(rdev);
                }
                ri->rdev = rdev;
        }
 
        platform_set_drvdata(pdev, pmic);
        return 0;
-fail:
-       while (--num >= 0) {
-               ri = &pmic[num];
-               regulator_unregister(ri->rdev);
-       }
-       return ret;
-}
-
-static int tps80031_regulator_remove(struct platform_device *pdev)
-{
-       struct tps80031_regulator *pmic = platform_get_drvdata(pdev);
-       struct tps80031_regulator *ri = NULL;
-       int num;
-
-       for (num = 0; num < TPS80031_REGULATOR_MAX; ++num) {
-               ri = &pmic[num];
-               regulator_unregister(ri->rdev);
-       }
-       return 0;
 }
 
 static struct platform_driver tps80031_regulator_driver = {
@@ -770,7 +751,6 @@ static struct platform_driver tps80031_regulator_driver = {
                .owner  = THIS_MODULE,
        },
        .probe          = tps80031_regulator_probe,
-       .remove         = tps80031_regulator_remove,
 };
 
 static int __init tps80031_regulator_init(void)
index 11861cb..6823e6f 100644 (file)
@@ -387,8 +387,9 @@ static struct regulator_ops wm831x_buckv_ops = {
  * Set up DVS control.  We just log errors since we can still run
  * (with reduced performance) if we fail.
  */
-static void wm831x_buckv_dvs_init(struct wm831x_dcdc *dcdc,
-                                           struct wm831x_buckv_pdata *pdata)
+static void wm831x_buckv_dvs_init(struct platform_device *pdev,
+                                 struct wm831x_dcdc *dcdc,
+                                 struct wm831x_buckv_pdata *pdata)
 {
        struct wm831x *wm831x = dcdc->wm831x;
        int ret;
@@ -402,9 +403,9 @@ static void wm831x_buckv_dvs_init(struct wm831x_dcdc *dcdc,
         */
        dcdc->dvs_gpio_state = pdata->dvs_init_state;
 
-       ret = gpio_request_one(pdata->dvs_gpio,
-                              dcdc->dvs_gpio_state ? GPIOF_INIT_HIGH : 0,
-                              "DCDC DVS");
+       ret = devm_gpio_request_one(&pdev->dev, pdata->dvs_gpio,
+                                   dcdc->dvs_gpio_state ? GPIOF_INIT_HIGH : 0,
+                                   "DCDC DVS");
        if (ret < 0) {
                dev_err(wm831x->dev, "Failed to get %s DVS GPIO: %d\n",
                        dcdc->name, ret);
@@ -513,7 +514,8 @@ static int wm831x_buckv_probe(struct platform_device *pdev)
        dcdc->dvs_vsel = ret & WM831X_DC1_DVS_VSEL_MASK;
 
        if (pdata && pdata->dcdc[id])
-               wm831x_buckv_dvs_init(dcdc, pdata->dcdc[id]->driver_data);
+               wm831x_buckv_dvs_init(pdev, dcdc,
+                                     pdata->dcdc[id]->driver_data);
 
        config.dev = pdev->dev.parent;
        if (pdata)
@@ -521,7 +523,8 @@ static int wm831x_buckv_probe(struct platform_device *pdev)
        config.driver_data = dcdc;
        config.regmap = wm831x->regmap;
 
-       dcdc->regulator = regulator_register(&dcdc->desc, &config);
+       dcdc->regulator = devm_regulator_register(&pdev->dev, &dcdc->desc,
+                                                 &config);
        if (IS_ERR(dcdc->regulator)) {
                ret = PTR_ERR(dcdc->regulator);
                dev_err(wm831x->dev, "Failed to register DCDC%d: %d\n",
@@ -530,57 +533,35 @@ static int wm831x_buckv_probe(struct platform_device *pdev)
        }
 
        irq = wm831x_irq(wm831x, platform_get_irq_byname(pdev, "UV"));
-       ret = request_threaded_irq(irq, NULL, wm831x_dcdc_uv_irq,
-                                  IRQF_TRIGGER_RISING, dcdc->name, dcdc);
+       ret = devm_request_threaded_irq(&pdev->dev, irq, NULL,
+                                       wm831x_dcdc_uv_irq,
+                                       IRQF_TRIGGER_RISING, dcdc->name, dcdc);
        if (ret != 0) {
                dev_err(&pdev->dev, "Failed to request UV IRQ %d: %d\n",
                        irq, ret);
-               goto err_regulator;
+               goto err;
        }
 
        irq = wm831x_irq(wm831x, platform_get_irq_byname(pdev, "HC"));
-       ret = request_threaded_irq(irq, NULL, wm831x_dcdc_oc_irq,
-                                  IRQF_TRIGGER_RISING, dcdc->name, dcdc);
+       ret = devm_request_threaded_irq(&pdev->dev, irq, NULL,
+                                       wm831x_dcdc_oc_irq,
+                                       IRQF_TRIGGER_RISING, dcdc->name, dcdc);
        if (ret != 0) {
                dev_err(&pdev->dev, "Failed to request HC IRQ %d: %d\n",
                        irq, ret);
-               goto err_uv;
+               goto err;
        }
 
        platform_set_drvdata(pdev, dcdc);
 
        return 0;
 
-err_uv:
-       free_irq(wm831x_irq(wm831x, platform_get_irq_byname(pdev, "UV")),
-                dcdc);
-err_regulator:
-       regulator_unregister(dcdc->regulator);
 err:
-       if (dcdc->dvs_gpio)
-               gpio_free(dcdc->dvs_gpio);
        return ret;
 }
 
-static int wm831x_buckv_remove(struct platform_device *pdev)
-{
-       struct wm831x_dcdc *dcdc = platform_get_drvdata(pdev);
-       struct wm831x *wm831x = dcdc->wm831x;
-
-       free_irq(wm831x_irq(wm831x, platform_get_irq_byname(pdev, "HC")),
-                           dcdc);
-       free_irq(wm831x_irq(wm831x, platform_get_irq_byname(pdev, "UV")),
-                           dcdc);
-       regulator_unregister(dcdc->regulator);
-       if (dcdc->dvs_gpio)
-               gpio_free(dcdc->dvs_gpio);
-
-       return 0;
-}
-
 static struct platform_driver wm831x_buckv_driver = {
        .probe = wm831x_buckv_probe,
-       .remove = wm831x_buckv_remove,
        .driver         = {
                .name   = "wm831x-buckv",
                .owner  = THIS_MODULE,
@@ -681,7 +662,8 @@ static int wm831x_buckp_probe(struct platform_device *pdev)
        config.driver_data = dcdc;
        config.regmap = wm831x->regmap;
 
-       dcdc->regulator = regulator_register(&dcdc->desc, &config);
+       dcdc->regulator = devm_regulator_register(&pdev->dev, &dcdc->desc,
+                                                 &config);
        if (IS_ERR(dcdc->regulator)) {
                ret = PTR_ERR(dcdc->regulator);
                dev_err(wm831x->dev, "Failed to register DCDC%d: %d\n",
@@ -690,38 +672,25 @@ static int wm831x_buckp_probe(struct platform_device *pdev)
        }
 
        irq = wm831x_irq(wm831x, platform_get_irq_byname(pdev, "UV"));
-       ret = request_threaded_irq(irq, NULL, wm831x_dcdc_uv_irq,
-                                  IRQF_TRIGGER_RISING, dcdc->name, dcdc);
+       ret = devm_request_threaded_irq(&pdev->dev, irq, NULL,
+                                       wm831x_dcdc_uv_irq,
+                                       IRQF_TRIGGER_RISING, dcdc->name, dcdc);
        if (ret != 0) {
                dev_err(&pdev->dev, "Failed to request UV IRQ %d: %d\n",
                        irq, ret);
-               goto err_regulator;
+               goto err;
        }
 
        platform_set_drvdata(pdev, dcdc);
 
        return 0;
 
-err_regulator:
-       regulator_unregister(dcdc->regulator);
 err:
        return ret;
 }
 
-static int wm831x_buckp_remove(struct platform_device *pdev)
-{
-       struct wm831x_dcdc *dcdc = platform_get_drvdata(pdev);
-
-       free_irq(wm831x_irq(dcdc->wm831x, platform_get_irq_byname(pdev, "UV")),
-                           dcdc);
-       regulator_unregister(dcdc->regulator);
-
-       return 0;
-}
-
 static struct platform_driver wm831x_buckp_driver = {
        .probe = wm831x_buckp_probe,
-       .remove = wm831x_buckp_remove,
        .driver         = {
                .name   = "wm831x-buckp",
                .owner  = THIS_MODULE,
@@ -813,7 +782,8 @@ static int wm831x_boostp_probe(struct platform_device *pdev)
        config.driver_data = dcdc;
        config.regmap = wm831x->regmap;
 
-       dcdc->regulator = regulator_register(&dcdc->desc, &config);
+       dcdc->regulator = devm_regulator_register(&pdev->dev, &dcdc->desc,
+                                                 &config);
        if (IS_ERR(dcdc->regulator)) {
                ret = PTR_ERR(dcdc->regulator);
                dev_err(wm831x->dev, "Failed to register DCDC%d: %d\n",
@@ -822,39 +792,26 @@ static int wm831x_boostp_probe(struct platform_device *pdev)
        }
 
        irq = wm831x_irq(wm831x, platform_get_irq_byname(pdev, "UV"));
-       ret = request_threaded_irq(irq, NULL, wm831x_dcdc_uv_irq,
-                                  IRQF_TRIGGER_RISING, dcdc->name,
-                                  dcdc);
+       ret = devm_request_threaded_irq(&pdev->dev, irq, NULL,
+                                       wm831x_dcdc_uv_irq,
+                                       IRQF_TRIGGER_RISING, dcdc->name,
+                                       dcdc);
        if (ret != 0) {
                dev_err(&pdev->dev, "Failed to request UV IRQ %d: %d\n",
                        irq, ret);
-               goto err_regulator;
+               goto err;
        }
 
        platform_set_drvdata(pdev, dcdc);
 
        return 0;
 
-err_regulator:
-       regulator_unregister(dcdc->regulator);
 err:
        return ret;
 }
 
-static int wm831x_boostp_remove(struct platform_device *pdev)
-{
-       struct wm831x_dcdc *dcdc = platform_get_drvdata(pdev);
-
-       free_irq(wm831x_irq(dcdc->wm831x, platform_get_irq_byname(pdev, "UV")),
-                dcdc);
-       regulator_unregister(dcdc->regulator);
-
-       return 0;
-}
-
 static struct platform_driver wm831x_boostp_driver = {
        .probe = wm831x_boostp_probe,
-       .remove = wm831x_boostp_remove,
        .driver         = {
                .name   = "wm831x-boostp",
                .owner  = THIS_MODULE,
@@ -914,7 +871,8 @@ static int wm831x_epe_probe(struct platform_device *pdev)
        config.driver_data = dcdc;
        config.regmap = wm831x->regmap;
 
-       dcdc->regulator = regulator_register(&dcdc->desc, &config);
+       dcdc->regulator = devm_regulator_register(&pdev->dev, &dcdc->desc,
+                                                 &config);
        if (IS_ERR(dcdc->regulator)) {
                ret = PTR_ERR(dcdc->regulator);
                dev_err(wm831x->dev, "Failed to register EPE%d: %d\n",
@@ -930,18 +888,8 @@ err:
        return ret;
 }
 
-static int wm831x_epe_remove(struct platform_device *pdev)
-{
-       struct wm831x_dcdc *dcdc = platform_get_drvdata(pdev);
-
-       regulator_unregister(dcdc->regulator);
-
-       return 0;
-}
-
 static struct platform_driver wm831x_epe_driver = {
        .probe = wm831x_epe_probe,
-       .remove = wm831x_epe_remove,
        .driver         = {
                .name   = "wm831x-epe",
                .owner  = THIS_MODULE,
index 4eb373d..0339b88 100644 (file)
@@ -194,7 +194,8 @@ static int wm831x_isink_probe(struct platform_device *pdev)
        config.init_data = pdata->isink[id];
        config.driver_data = isink;
 
-       isink->regulator = regulator_register(&isink->desc, &config);
+       isink->regulator = devm_regulator_register(&pdev->dev, &isink->desc,
+                                                  &config);
        if (IS_ERR(isink->regulator)) {
                ret = PTR_ERR(isink->regulator);
                dev_err(wm831x->dev, "Failed to register ISINK%d: %d\n",
@@ -203,38 +204,26 @@ static int wm831x_isink_probe(struct platform_device *pdev)
        }
 
        irq = wm831x_irq(wm831x, platform_get_irq(pdev, 0));
-       ret = request_threaded_irq(irq, NULL, wm831x_isink_irq,
-                                  IRQF_TRIGGER_RISING, isink->name, isink);
+       ret = devm_request_threaded_irq(&pdev->dev, irq, NULL,
+                                       wm831x_isink_irq,
+                                       IRQF_TRIGGER_RISING, isink->name,
+                                       isink);
        if (ret != 0) {
                dev_err(&pdev->dev, "Failed to request ISINK IRQ %d: %d\n",
                        irq, ret);
-               goto err_regulator;
+               goto err;
        }
 
        platform_set_drvdata(pdev, isink);
 
        return 0;
 
-err_regulator:
-       regulator_unregister(isink->regulator);
 err:
        return ret;
 }
 
-static int wm831x_isink_remove(struct platform_device *pdev)
-{
-       struct wm831x_isink *isink = platform_get_drvdata(pdev);
-
-       free_irq(wm831x_irq(isink->wm831x, platform_get_irq(pdev, 0)), isink);
-
-       regulator_unregister(isink->regulator);
-
-       return 0;
-}
-
 static struct platform_driver wm831x_isink_driver = {
        .probe = wm831x_isink_probe,
-       .remove = wm831x_isink_remove,
        .driver         = {
                .name   = "wm831x-isink",
                .owner  = THIS_MODULE,
index 2205fbc..482ebe8 100644 (file)
@@ -279,7 +279,8 @@ static int wm831x_gp_ldo_probe(struct platform_device *pdev)
        config.driver_data = ldo;
        config.regmap = wm831x->regmap;
 
-       ldo->regulator = regulator_register(&ldo->desc, &config);
+       ldo->regulator = devm_regulator_register(&pdev->dev, &ldo->desc,
+                                                &config);
        if (IS_ERR(ldo->regulator)) {
                ret = PTR_ERR(ldo->regulator);
                dev_err(wm831x->dev, "Failed to register LDO%d: %d\n",
@@ -288,39 +289,26 @@ static int wm831x_gp_ldo_probe(struct platform_device *pdev)
        }
 
        irq = wm831x_irq(wm831x, platform_get_irq_byname(pdev, "UV"));
-       ret = request_threaded_irq(irq, NULL, wm831x_ldo_uv_irq,
-                                  IRQF_TRIGGER_RISING, ldo->name,
-                                  ldo);
+       ret = devm_request_threaded_irq(&pdev->dev, irq, NULL,
+                                       wm831x_ldo_uv_irq,
+                                       IRQF_TRIGGER_RISING, ldo->name,
+                                       ldo);
        if (ret != 0) {
                dev_err(&pdev->dev, "Failed to request UV IRQ %d: %d\n",
                        irq, ret);
-               goto err_regulator;
+               goto err;
        }
 
        platform_set_drvdata(pdev, ldo);
 
        return 0;
 
-err_regulator:
-       regulator_unregister(ldo->regulator);
 err:
        return ret;
 }
 
-static int wm831x_gp_ldo_remove(struct platform_device *pdev)
-{
-       struct wm831x_ldo *ldo = platform_get_drvdata(pdev);
-
-       free_irq(wm831x_irq(ldo->wm831x,
-                           platform_get_irq_byname(pdev, "UV")), ldo);
-       regulator_unregister(ldo->regulator);
-
-       return 0;
-}
-
 static struct platform_driver wm831x_gp_ldo_driver = {
        .probe = wm831x_gp_ldo_probe,
-       .remove = wm831x_gp_ldo_remove,
        .driver         = {
                .name   = "wm831x-ldo",
                .owner  = THIS_MODULE,
@@ -505,7 +493,8 @@ static int wm831x_aldo_probe(struct platform_device *pdev)
        config.driver_data = ldo;
        config.regmap = wm831x->regmap;
 
-       ldo->regulator = regulator_register(&ldo->desc, &config);
+       ldo->regulator = devm_regulator_register(&pdev->dev, &ldo->desc,
+                                                &config);
        if (IS_ERR(ldo->regulator)) {
                ret = PTR_ERR(ldo->regulator);
                dev_err(wm831x->dev, "Failed to register LDO%d: %d\n",
@@ -514,38 +503,25 @@ static int wm831x_aldo_probe(struct platform_device *pdev)
        }
 
        irq = wm831x_irq(wm831x, platform_get_irq_byname(pdev, "UV"));
-       ret = request_threaded_irq(irq, NULL, wm831x_ldo_uv_irq,
-                                  IRQF_TRIGGER_RISING, ldo->name, ldo);
+       ret = devm_request_threaded_irq(&pdev->dev, irq, NULL,
+                                       wm831x_ldo_uv_irq,
+                                       IRQF_TRIGGER_RISING, ldo->name, ldo);
        if (ret != 0) {
                dev_err(&pdev->dev, "Failed to request UV IRQ %d: %d\n",
                        irq, ret);
-               goto err_regulator;
+               goto err;
        }
 
        platform_set_drvdata(pdev, ldo);
 
        return 0;
 
-err_regulator:
-       regulator_unregister(ldo->regulator);
 err:
        return ret;
 }
 
-static int wm831x_aldo_remove(struct platform_device *pdev)
-{
-       struct wm831x_ldo *ldo = platform_get_drvdata(pdev);
-
-       free_irq(wm831x_irq(ldo->wm831x, platform_get_irq_byname(pdev, "UV")),
-                ldo);
-       regulator_unregister(ldo->regulator);
-
-       return 0;
-}
-
 static struct platform_driver wm831x_aldo_driver = {
        .probe = wm831x_aldo_probe,
-       .remove = wm831x_aldo_remove,
        .driver         = {
                .name   = "wm831x-aldo",
                .owner  = THIS_MODULE,
@@ -663,7 +639,8 @@ static int wm831x_alive_ldo_probe(struct platform_device *pdev)
        config.driver_data = ldo;
        config.regmap = wm831x->regmap;
 
-       ldo->regulator = regulator_register(&ldo->desc, &config);
+       ldo->regulator = devm_regulator_register(&pdev->dev, &ldo->desc,
+                                                &config);
        if (IS_ERR(ldo->regulator)) {
                ret = PTR_ERR(ldo->regulator);
                dev_err(wm831x->dev, "Failed to register LDO%d: %d\n",
@@ -679,18 +656,8 @@ err:
        return ret;
 }
 
-static int wm831x_alive_ldo_remove(struct platform_device *pdev)
-{
-       struct wm831x_ldo *ldo = platform_get_drvdata(pdev);
-
-       regulator_unregister(ldo->regulator);
-
-       return 0;
-}
-
 static struct platform_driver wm831x_alive_ldo_driver = {
        .probe = wm831x_alive_ldo_probe,
-       .remove = wm831x_alive_ldo_remove,
        .driver         = {
                .name   = "wm831x-alive-ldo",
                .owner  = THIS_MODULE,
index 61ca929..017e869 100644 (file)
@@ -1206,7 +1206,8 @@ static int wm8350_regulator_probe(struct platform_device *pdev)
        config.regmap = wm8350->regmap;
 
        /* register regulator */
-       rdev = regulator_register(&wm8350_reg[pdev->id], &config);
+       rdev = devm_regulator_register(&pdev->dev, &wm8350_reg[pdev->id],
+                                      &config);
        if (IS_ERR(rdev)) {
                dev_err(&pdev->dev, "failed to register %s\n",
                        wm8350_reg[pdev->id].name);
@@ -1217,7 +1218,6 @@ static int wm8350_regulator_probe(struct platform_device *pdev)
        ret = wm8350_register_irq(wm8350, wm8350_reg[pdev->id].irq,
                                  pmic_uv_handler, 0, "UV", rdev);
        if (ret < 0) {
-               regulator_unregister(rdev);
                dev_err(&pdev->dev, "failed to register regulator %s IRQ\n",
                        wm8350_reg[pdev->id].name);
                return ret;
@@ -1233,8 +1233,6 @@ static int wm8350_regulator_remove(struct platform_device *pdev)
 
        wm8350_free_irq(wm8350, wm8350_reg[pdev->id].irq, rdev);
 
-       regulator_unregister(rdev);
-
        return 0;
 }
 
index 58f51be..870b52f 100644 (file)
@@ -219,7 +219,8 @@ static int wm8400_regulator_probe(struct platform_device *pdev)
        config.driver_data = wm8400;
        config.regmap = wm8400->regmap;
 
-       rdev = regulator_register(&regulators[pdev->id], &config);
+       rdev = devm_regulator_register(&pdev->dev, &regulators[pdev->id],
+                                      &config);
        if (IS_ERR(rdev))
                return PTR_ERR(rdev);
 
@@ -228,21 +229,11 @@ static int wm8400_regulator_probe(struct platform_device *pdev)
        return 0;
 }
 
-static int wm8400_regulator_remove(struct platform_device *pdev)
-{
-       struct regulator_dev *rdev = platform_get_drvdata(pdev);
-
-       regulator_unregister(rdev);
-
-       return 0;
-}
-
 static struct platform_driver wm8400_regulator_driver = {
        .driver = {
                .name = "wm8400-regulator",
        },
        .probe = wm8400_regulator_probe,
-       .remove = wm8400_regulator_remove,
 };
 
 /**
index 5ee2a20..71c5911 100644 (file)
@@ -165,7 +165,9 @@ static int wm8994_ldo_probe(struct platform_device *pdev)
                ldo->init_data = *pdata->ldo[id].init_data;
        }
 
-       ldo->regulator = regulator_register(&wm8994_ldo_desc[id], &config);
+       ldo->regulator = devm_regulator_register(&pdev->dev,
+                                                &wm8994_ldo_desc[id],
+                                                &config);
        if (IS_ERR(ldo->regulator)) {
                ret = PTR_ERR(ldo->regulator);
                dev_err(wm8994->dev, "Failed to register LDO%d: %d\n",
@@ -181,18 +183,8 @@ err:
        return ret;
 }
 
-static int wm8994_ldo_remove(struct platform_device *pdev)
-{
-       struct wm8994_ldo *ldo = platform_get_drvdata(pdev);
-
-       regulator_unregister(ldo->regulator);
-
-       return 0;
-}
-
 static struct platform_driver wm8994_ldo_driver = {
        .probe = wm8994_ldo_probe,
-       .remove = wm8994_ldo_remove,
        .driver         = {
                .name   = "wm8994-ldo",
                .owner  = THIS_MODULE,
index cebe97e..7314fc4 100644 (file)
@@ -59,6 +59,12 @@ struct mfd_cell {
         * pm_runtime_no_callbacks().
         */
        bool                    pm_runtime_no_callbacks;
+
+       /* A list of regulator supplies that should be mapped to the MFD
+        * device rather than the child device when requested
+        */
+       const char              **parent_supplies;
+       int                     num_parent_supplies;
 };
 
 /*
index 27be915..e530681 100644 (file)
@@ -146,6 +146,32 @@ struct regulator *__must_check devm_regulator_get_optional(struct device *dev,
 void regulator_put(struct regulator *regulator);
 void devm_regulator_put(struct regulator *regulator);
 
+int regulator_register_supply_alias(struct device *dev, const char *id,
+                                   struct device *alias_dev,
+                                   const char *alias_id);
+void regulator_unregister_supply_alias(struct device *dev, const char *id);
+
+int regulator_bulk_register_supply_alias(struct device *dev, const char **id,
+                                        struct device *alias_dev,
+                                        const char **alias_id, int num_id);
+void regulator_bulk_unregister_supply_alias(struct device *dev,
+                                           const char **id, int num_id);
+
+int devm_regulator_register_supply_alias(struct device *dev, const char *id,
+                                        struct device *alias_dev,
+                                        const char *alias_id);
+void devm_regulator_unregister_supply_alias(struct device *dev,
+                                           const char *id);
+
+int devm_regulator_bulk_register_supply_alias(struct device *dev,
+                                             const char **id,
+                                             struct device *alias_dev,
+                                             const char **alias_id,
+                                             int num_id);
+void devm_regulator_bulk_unregister_supply_alias(struct device *dev,
+                                                const char **id,
+                                                int num_id);
+
 /* regulator output control and status */
 int __must_check regulator_enable(struct regulator *regulator);
 int regulator_disable(struct regulator *regulator);
@@ -250,6 +276,59 @@ static inline void devm_regulator_put(struct regulator *regulator)
 {
 }
 
+static inline int regulator_register_supply_alias(struct device *dev,
+                                                 const char *id,
+                                                 struct device *alias_dev,
+                                                 const char *alias_id)
+{
+       return 0;
+}
+
+static inline void regulator_unregister_supply_alias(struct device *dev,
+                                                   const char *id)
+{
+}
+
+static inline int regulator_bulk_register_supply_alias(struct device *dev,
+                                                      const char **id,
+                                                      struct device *alias_dev,
+                                                      const char **alias_id,
+                                                      int num_id)
+{
+       return 0;
+}
+
+static inline void regulator_bulk_unregister_supply_alias(struct device *dev,
+                                                         const char **id,
+                                                         int num_id)
+{
+}
+
+static inline int devm_regulator_register_supply_alias(struct device *dev,
+                                                      const char *id,
+                                                      struct device *alias_dev,
+                                                      const char *alias_id)
+{
+       return 0;
+}
+
+static inline void devm_regulator_unregister_supply_alias(struct device *dev,
+                                                         const char *id)
+{
+}
+
+static inline int devm_regulator_bulk_register_supply_alias(
+               struct device *dev, const char **id, struct device *alias_dev,
+               const char **alias_id, int num_id)
+{
+       return 0;
+}
+
+static inline void devm_regulator_bulk_unregister_supply_alias(
+               struct device *dev, const char **id, int num_id)
+{
+}
+
 static inline int regulator_enable(struct regulator *regulator)
 {
        return 0;
index 9bdad43..779b877 100644 (file)
@@ -336,7 +336,12 @@ struct regulator_dev {
 struct regulator_dev *
 regulator_register(const struct regulator_desc *regulator_desc,
                   const struct regulator_config *config);
+struct regulator_dev *
+devm_regulator_register(struct device *dev,
+                       const struct regulator_desc *regulator_desc,
+                       const struct regulator_config *config);
 void regulator_unregister(struct regulator_dev *rdev);
+void devm_regulator_unregister(struct device *dev, struct regulator_dev *rdev);
 
 int regulator_notifier_call_chain(struct regulator_dev *rdev,
                                  unsigned long event, void *data);