[RFC PATCH 04/23] sunxi: pinctrl: Implement pin configuration

Samuel Holland samuel at sholland.org
Thu Oct 21 06:55:21 CEST 2021


The sunxi pinctrl hardware has bias and drive control. Add driver
support for configuring those options.

Signed-off-by: Samuel Holland <samuel at sholland.org>
---

 drivers/pinctrl/sunxi/Kconfig         |  1 +
 drivers/pinctrl/sunxi/pinctrl-sunxi.c | 53 +++++++++++++++++++++++++++
 2 files changed, 54 insertions(+)

diff --git a/drivers/pinctrl/sunxi/Kconfig b/drivers/pinctrl/sunxi/Kconfig
index bd251c20c3..bb0ddeedc4 100644
--- a/drivers/pinctrl/sunxi/Kconfig
+++ b/drivers/pinctrl/sunxi/Kconfig
@@ -5,6 +5,7 @@ if ARCH_SUNXI
 config PINCTRL_SUNXI
 	select PINCTRL_FULL
 	select PINCTRL_GENERIC
+	select PINCONF
 	select PINMUX
 	bool
 
diff --git a/drivers/pinctrl/sunxi/pinctrl-sunxi.c b/drivers/pinctrl/sunxi/pinctrl-sunxi.c
index e67c276a33..0ec3f7426c 100644
--- a/drivers/pinctrl/sunxi/pinctrl-sunxi.c
+++ b/drivers/pinctrl/sunxi/pinctrl-sunxi.c
@@ -66,6 +66,56 @@ static int sunxi_pinctrl_pinmux_set(struct udevice *dev, uint pin_selector,
 	return 0;
 }
 
+static const struct pinconf_param sunxi_pinctrl_pinconf_params[] = {
+	{ "bias-disable",	PIN_CONFIG_BIAS_DISABLE,	 0 },
+	{ "bias-pull-down",	PIN_CONFIG_BIAS_PULL_DOWN,	 2 },
+	{ "bias-pull-up",	PIN_CONFIG_BIAS_PULL_UP,	 1 },
+	{ "drive-strength",	PIN_CONFIG_DRIVE_STRENGTH,	10 },
+};
+
+static int sunxi_pinctrl_pinconf_set_pull(struct sunxi_pinctrl_plat *plat,
+					  uint bank, uint pin, uint bias)
+{
+	struct sunxi_gpio *regs = &plat->base[bank];
+
+	sunxi_gpio_set_pull_bank(regs, pin, bias);
+
+	return 0;
+}
+
+static int sunxi_pinctrl_pinconf_set_drive(struct sunxi_pinctrl_plat *plat,
+					   uint bank, uint pin, uint drive)
+{
+	struct sunxi_gpio *regs = &plat->base[bank];
+
+	if (drive < 10 || drive > 40)
+		return -EINVAL;
+
+	/* Convert mA to the register value, rounding down. */
+	sunxi_gpio_set_drv_bank(regs, pin, drive / 10 - 1);
+
+	return 0;
+}
+
+static int sunxi_pinctrl_pinconf_set(struct udevice *dev, uint pin_selector,
+				     uint param, uint val)
+{
+	struct sunxi_pinctrl_plat *plat = dev_get_plat(dev);
+	int bank = pin_selector / SUNXI_GPIOS_PER_BANK;
+	int pin  = pin_selector % SUNXI_GPIOS_PER_BANK;
+
+	switch (param) {
+	case PIN_CONFIG_BIAS_DISABLE:
+	case PIN_CONFIG_BIAS_PULL_DOWN:
+	case PIN_CONFIG_BIAS_PULL_UP:
+		return sunxi_pinctrl_pinconf_set_pull(plat, bank, pin, val);
+	case PIN_CONFIG_DRIVE_STRENGTH:
+		return sunxi_pinctrl_pinconf_set_drive(plat, bank, pin, val);
+	}
+
+	return -EINVAL;
+}
+
 static int sunxi_pinctrl_get_pin_muxing(struct udevice *dev, uint pin_selector,
 					char *buf, int size)
 {
@@ -98,6 +148,9 @@ const struct pinctrl_ops sunxi_pinctrl_ops = {
 	.get_functions_count	= sunxi_pinctrl_get_functions_count,
 	.get_function_name	= sunxi_pinctrl_get_function_name,
 	.pinmux_set		= sunxi_pinctrl_pinmux_set,
+	.pinconf_num_params	= ARRAY_SIZE(sunxi_pinctrl_pinconf_params),
+	.pinconf_params		= sunxi_pinctrl_pinconf_params,
+	.pinconf_set		= sunxi_pinctrl_pinconf_set,
 	.set_state		= pinctrl_generic_set_state,
 	.get_pin_muxing		= sunxi_pinctrl_get_pin_muxing,
 };
-- 
2.32.0



More information about the U-Boot mailing list