[<prev] [next>] [<thread-prev] [thread-next>] [day] [month] [year] [list]
Message-Id: <20220504065252.6955-5-zev@bewilderbeest.net>
Date: Tue, 3 May 2022 23:52:51 -0700
From: Zev Weiss <zev@...ilderbeest.net>
To: Mark Brown <broonie@...nel.org>,
Liam Girdwood <lgirdwood@...il.com>
Cc: Zev Weiss <zev@...ilderbeest.net>, linux-kernel@...r.kernel.org,
Greg Kroah-Hartman <gregkh@...uxfoundation.org>,
openbmc@...ts.ozlabs.org
Subject: [PATCH 5/6] regulator: core: Add external get type
EXTERNAL_GET is similar to EXCLUSIVE_GET, but requires opt-in
agreement from the supply (whose constraints must designate it as
external_output). It is intended for use only within the regulator
subsystem, and hence is not exposed in the public headers.
Signed-off-by: Zev Weiss <zev@...ilderbeest.net>
---
drivers/regulator/core.c | 16 +++++++++++++---
drivers/regulator/devres.c | 7 +++++++
drivers/regulator/internal.h | 3 +++
3 files changed, 23 insertions(+), 3 deletions(-)
diff --git a/drivers/regulator/core.c b/drivers/regulator/core.c
index b7617926336f..d873606eb41f 100644
--- a/drivers/regulator/core.c
+++ b/drivers/regulator/core.c
@@ -2087,6 +2087,7 @@ struct regulator *_regulator_get(struct device *dev, const char *id,
struct regulator_dev *rdev;
struct regulator *regulator;
struct device_link *link;
+ bool is_external;
int ret;
if (get_type >= MAX_GET_TYPE) {
@@ -2129,8 +2130,9 @@ struct regulator *_regulator_get(struct device *dev, const char *id,
break;
case EXCLUSIVE_GET:
+ case EXTERNAL_GET:
dev_warn(dev,
- "dummy supplies not allowed for exclusive requests\n");
+ "dummy supplies not allowed for exclusive or external requests\n");
fallthrough;
default:
@@ -2144,12 +2146,20 @@ struct regulator *_regulator_get(struct device *dev, const char *id,
return regulator;
}
- if (get_type == EXCLUSIVE_GET && rdev->open_count) {
+ if ((get_type == EXCLUSIVE_GET || get_type == EXTERNAL_GET) && rdev->open_count) {
regulator = ERR_PTR(-EBUSY);
put_device(&rdev->dev);
return regulator;
}
+ /* EXTERNAL_GET is valid if and only if the regulator is designated for external output */
+ is_external = rdev->constraints && rdev->constraints->external_output;
+ if ((get_type == EXTERNAL_GET) != is_external) {
+ regulator = ERR_PTR(-EINVAL);
+ put_device(&rdev->dev);
+ return regulator;
+ }
+
mutex_lock(®ulator_list_mutex);
ret = (rdev->coupling_desc.n_resolved != rdev->coupling_desc.n_coupled);
mutex_unlock(®ulator_list_mutex);
@@ -2182,7 +2192,7 @@ struct regulator *_regulator_get(struct device *dev, const char *id,
}
rdev->open_count++;
- if (get_type == EXCLUSIVE_GET) {
+ if (get_type == EXCLUSIVE_GET || get_type == EXTERNAL_GET) {
rdev->exclusive = 1;
ret = _regulator_is_enabled(rdev);
diff --git a/drivers/regulator/devres.c b/drivers/regulator/devres.c
index 9113233f41cd..36df9e9ff175 100644
--- a/drivers/regulator/devres.c
+++ b/drivers/regulator/devres.c
@@ -70,6 +70,13 @@ struct regulator *devm_regulator_get_exclusive(struct device *dev,
}
EXPORT_SYMBOL_GPL(devm_regulator_get_exclusive);
+/* For regulator-core internal use only */
+struct regulator *devm_regulator_get_external(struct device *dev,
+ const char *id)
+{
+ return _devm_regulator_get(dev, id, EXTERNAL_GET);
+}
+
/**
* devm_regulator_get_optional - Resource managed regulator_get_optional()
* @dev: device to supply
diff --git a/drivers/regulator/internal.h b/drivers/regulator/internal.h
index 1e9c71642143..c176a416c571 100644
--- a/drivers/regulator/internal.h
+++ b/drivers/regulator/internal.h
@@ -116,10 +116,13 @@ static inline bool of_check_coupling_data(struct regulator_dev *rdev)
enum regulator_get_type {
NORMAL_GET,
EXCLUSIVE_GET,
+ EXTERNAL_GET,
OPTIONAL_GET,
MAX_GET_TYPE
};
struct regulator *_regulator_get(struct device *dev, const char *id,
enum regulator_get_type get_type);
+struct regulator *devm_regulator_get_external(struct device *dev,
+ const char *id);
#endif
--
2.36.0
Powered by blists - more mailing lists