Merge tag 'regulator-v6.2' of git://git.kernel.org/pub/scm/linux/kernel/git/broonie...
[linux-2.6-block.git] / drivers / regulator / core.c
index e8c00a884f1f13983e794459d3ce051290bd24dc..ace4ecc6d7c23253aa9dff82324d8dde7c302442 100644 (file)
@@ -1596,7 +1596,13 @@ static int set_machine_constraints(struct regulator_dev *rdev)
                if (rdev->supply_name && !rdev->supply)
                        return -EPROBE_DEFER;
 
-               if (rdev->supply) {
+               /* If supplying regulator has already been enabled,
+                * it's not intended to have use_count increment
+                * when rdev is only boot-on.
+                */
+               if (rdev->supply &&
+                   (rdev->constraints->always_on ||
+                    !regulator_is_enabled(rdev->supply))) {
                        ret = regulator_enable(rdev->supply);
                        if (ret < 0) {
                                _regulator_put(rdev->supply);
@@ -1640,6 +1646,7 @@ static int set_supply(struct regulator_dev *rdev,
 
        rdev->supply = create_regulator(supply_rdev, &rdev->dev, "SUPPLY");
        if (rdev->supply == NULL) {
+               module_put(supply_rdev->owner);
                err = -ENOMEM;
                return err;
        }
@@ -1813,7 +1820,7 @@ static struct regulator *create_regulator(struct regulator_dev *rdev,
 
        regulator = kzalloc(sizeof(*regulator), GFP_KERNEL);
        if (regulator == NULL) {
-               kfree(supply_name);
+               kfree_const(supply_name);
                return NULL;
        }
 
@@ -1943,6 +1950,7 @@ static struct regulator_dev *regulator_dev_lookup(struct device *dev,
                node = of_get_regulator(dev, supply);
                if (node) {
                        r = of_find_regulator_by_node(node);
+                       of_node_put(node);
                        if (r)
                                return r;
 
@@ -4778,22 +4786,8 @@ static int _notifier_call_chain(struct regulator_dev *rdev,
        return blocking_notifier_call_chain(&rdev->notifier, event, data);
 }
 
-/**
- * regulator_bulk_get - 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.  If any of the regulators cannot be
- * acquired then any regulators that were allocated will be freed
- * before returning to the caller.
- */
-int regulator_bulk_get(struct device *dev, int num_consumers,
-                      struct regulator_bulk_data *consumers)
+int _regulator_bulk_get(struct device *dev, int num_consumers,
+                       struct regulator_bulk_data *consumers, enum regulator_get_type get_type)
 {
        int i;
        int ret;
@@ -4802,8 +4796,8 @@ int regulator_bulk_get(struct device *dev, int num_consumers,
                consumers[i].consumer = NULL;
 
        for (i = 0; i < num_consumers; i++) {
-               consumers[i].consumer = regulator_get(dev,
-                                                     consumers[i].supply);
+               consumers[i].consumer = _regulator_get(dev,
+                                                      consumers[i].supply, get_type);
                if (IS_ERR(consumers[i].consumer)) {
                        ret = dev_err_probe(dev, PTR_ERR(consumers[i].consumer),
                                            "Failed to get supply '%s'",
@@ -4830,6 +4824,26 @@ err:
 
        return ret;
 }
+
+/**
+ * regulator_bulk_get - 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.  If any of the regulators cannot be
+ * acquired then any regulators that were allocated will be freed
+ * before returning to the caller.
+ */
+int regulator_bulk_get(struct device *dev, int num_consumers,
+                      struct regulator_bulk_data *consumers)
+{
+       return _regulator_bulk_get(dev, num_consumers, consumers, NORMAL_GET);
+}
 EXPORT_SYMBOL_GPL(regulator_bulk_get);
 
 static void regulator_bulk_enable_async(void *data, async_cookie_t cookie)
@@ -5396,6 +5410,7 @@ static struct regulator_coupler generic_regulator_coupler = {
 
 /**
  * regulator_register - register regulator
+ * @dev: the device that drive the regulator
  * @regulator_desc: regulator to register
  * @cfg: runtime configuration for regulator
  *
@@ -5404,7 +5419,8 @@ static struct regulator_coupler generic_regulator_coupler = {
  * or an ERR_PTR() on error.
  */
 struct regulator_dev *
-regulator_register(const struct regulator_desc *regulator_desc,
+regulator_register(struct device *dev,
+                  const struct regulator_desc *regulator_desc,
                   const struct regulator_config *cfg)
 {
        const struct regulator_init_data *init_data;
@@ -5413,7 +5429,6 @@ regulator_register(const struct regulator_desc *regulator_desc,
        struct regulator_dev *rdev;
        bool dangling_cfg_gpiod = false;
        bool dangling_of_gpiod = false;
-       struct device *dev;
        int ret, i;
        bool resolved_early = false;
 
@@ -5426,8 +5441,7 @@ regulator_register(const struct regulator_desc *regulator_desc,
                goto rinse;
        }
 
-       dev = cfg->dev;
-       WARN_ON(!dev);
+       WARN_ON(!dev || !cfg->dev);
 
        if (regulator_desc->name == NULL || regulator_desc->ops == NULL) {
                ret = -EINVAL;
@@ -5641,6 +5655,7 @@ unset_supplies:
        regulator_remove_coupling(rdev);
        mutex_unlock(&regulator_list_mutex);
 wash:
+       regulator_put(rdev->supply);
        kfree(rdev->coupling_desc.coupled_rdevs);
        mutex_lock(&regulator_list_mutex);
        regulator_ena_gpio_free(rdev);