[PATCH v7 7/9] gpio: regmap: Add set_config callback

Yu-Chun Lin <[email protected]>
Newsgroups org.kernel.vger.linux-gpio,org.kernel.vger.linux-iio,org.kernel.vger.linux-kernel
Message-ID <[email protected]>
Add a new set_config callback to allow drivers to implement
hardware-specific configuration such as debounce settings, or other
platform-specific GPIO properties.

Signed-off-by: Yu-Chun Lin <[email protected]>
---
Changes in v7:
- Drop the reviewed by tag from Andy due to the signature changes.
- Add 'struct gpio_regmap' as the first parameter to the set_config callback.
- Add wrapper to bridge gpio_chip to gpio_regmap.
---
 drivers/gpio/gpio-regmap.c  | 16 ++++++++++++++++
 include/linux/gpio/regmap.h |  6 ++++++
 2 files changed, 22 insertions(+)

diff --git a/drivers/gpio/gpio-regmap.c b/drivers/gpio/gpio-regmap.c
index 8f58b272b870..98cfdd890069 100644
--- a/drivers/gpio/gpio-regmap.c
+++ b/drivers/gpio/gpio-regmap.c
@@ -51,6 +51,9 @@ struct gpio_regmap {
 			   unsigned int reg, unsigned int *mask,
 			   unsigned int *val);
 
+	int (*set_config)(struct gpio_regmap *gpio, struct gpio_chip *chip,
+			  unsigned int offset, unsigned long config);
+
 	void *driver_data;
 };
 
@@ -317,6 +320,15 @@ static int gpio_regmap_direction_output(struct gpio_chip *chip,
 	return gpio_regmap_set_direction(chip, offset, true);
 }
 
+static int gpio_regmap_set_config(struct gpio_chip *chip,
+				  unsigned int offset,
+				  unsigned long cfg)
+{
+	struct gpio_regmap *gpio = gpiochip_get_data(chip);
+
+	return gpio->set_config(gpio, chip, offset, cfg);
+}
+
 int gpio_regmap_reqres_irq(struct gpio_regmap *gpio, unsigned int offset)
 {
 	return gpiochip_reqres_irq(&gpio->gpio_chip, offset);
@@ -386,6 +398,7 @@ struct gpio_regmap *gpio_regmap_register(const struct gpio_regmap_config *config
 	gpio->reg_clr_base = config->reg_clr_base;
 	gpio->reg_dir_in_base = config->reg_dir_in_base;
 	gpio->reg_dir_out_base = config->reg_dir_out_base;
+	gpio->set_config = config->set_config;
 
 	chip = &gpio->gpio_chip;
 	chip->parent = config->parent;
@@ -455,6 +468,9 @@ struct gpio_regmap *gpio_regmap_register(const struct gpio_regmap_config *config
 
 	gpio->value_xlate = config->value_xlate;
 
+	if (config->set_config)
+		chip->set_config = gpio_regmap_set_config;
+
 	ret = gpiochip_add_data(chip, gpio);
 	if (ret < 0)
 		goto err_free_bitmap_output;
diff --git a/include/linux/gpio/regmap.h b/include/linux/gpio/regmap.h
index b77d6371cd9c..4bf4319ec12e 100644
--- a/include/linux/gpio/regmap.h
+++ b/include/linux/gpio/regmap.h
@@ -93,6 +93,9 @@ enum gpio_regmap_operation {
  *			mask before writing. This allows driver-specific logic
  *			to append additional bits (like write-enable masks)
  *			dynamically based on the current operation.
+ * @set_config:		(Optional) Callback for setting GPIO configuration such
+ *			as debounce, drive strength, or other hardware specific
+ *			settings.
  * @drvdata:		(Optional) Pointer to driver specific data which is
  *			not used by gpio-remap but is provided "as is" to the
  *			driver callback(s).
@@ -154,6 +157,9 @@ struct gpio_regmap_config {
 			   unsigned int base, unsigned int offset, unsigned int reg,
 			   unsigned int *mask, unsigned int *val);
 
+	int (*set_config)(struct gpio_regmap *gpio, struct gpio_chip *chip,
+			  unsigned int offset, unsigned long config);
+
 	void *drvdata;
 };
 
-- 
2.43.0
lmpx.com only provides a reader for public news (NNTP) servers. It is not affiliated with the servers or forums shown here and is not responsible for the content of articles, which is written by their respective authors.