summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorLuca Weiss <[email protected]>2026-03-18 13:46:27 +0100
committerCasey Connolly <[email protected]>2026-04-27 12:38:44 +0200
commit8e4fd3d1c31ff7df1dbc7771af16f0f87f5bade4 (patch)
tree1e5e39ec6b0e892937a87bc0d2889f011b55f5a7
parent16a16b55ce5fd75097bc07e7c0503b59b5401a81 (diff)
drivers: pinctrl: Add Qualcomm Milos TLMM driver
Add support for TLMM pin controller block (Top Level Mode Multiplexer) on Milos SoC, with support for special pins. Correct pin configuration is required for working debug UART and eMMC/SD cards. Reviewed-by: Sumit Garg <[email protected]> Signed-off-by: Luca Weiss <[email protected]> Link: https://patch.msgid.link/[email protected] Signed-off-by: Casey Connolly <[email protected]>
-rw-r--r--drivers/pinctrl/qcom/Kconfig8
-rw-r--r--drivers/pinctrl/qcom/Makefile1
-rw-r--r--drivers/pinctrl/qcom/pinctrl-milos.c103
3 files changed, 112 insertions, 0 deletions
diff --git a/drivers/pinctrl/qcom/Kconfig b/drivers/pinctrl/qcom/Kconfig
index 580308621b1..11e6763b5f3 100644
--- a/drivers/pinctrl/qcom/Kconfig
+++ b/drivers/pinctrl/qcom/Kconfig
@@ -54,6 +54,14 @@ config PINCTRL_QCOM_IPQ9574
Say Y here to enable support for pinctrl on the IPQ9574 SoC,
as well as the associated GPIO driver.
+config PINCTRL_QCOM_MILOS
+ bool "Qualcomm Milos Pinctrl"
+ default y if PINCTRL_QCOM_GENERIC
+ select PINCTRL_QCOM
+ help
+ Say Y here to enable support for pinctrl on the Snapdragon Milos SoC,
+ as well as the associated GPIO driver.
+
config PINCTRL_QCOM_QCM2290
bool "Qualcomm QCM2290 Pinctrl"
default y if PINCTRL_QCOM_GENERIC
diff --git a/drivers/pinctrl/qcom/Makefile b/drivers/pinctrl/qcom/Makefile
index b5a111605ed..4096c1aa491 100644
--- a/drivers/pinctrl/qcom/Makefile
+++ b/drivers/pinctrl/qcom/Makefile
@@ -8,6 +8,7 @@ obj-$(CONFIG_PINCTRL_QCOM_IPQ4019) += pinctrl-ipq4019.o
obj-$(CONFIG_PINCTRL_QCOM_IPQ5424) += pinctrl-ipq5424.o
obj-$(CONFIG_PINCTRL_QCOM_IPQ9574) += pinctrl-ipq9574.o
obj-$(CONFIG_PINCTRL_QCOM_APQ8096) += pinctrl-apq8096.o
+obj-$(CONFIG_PINCTRL_QCOM_MILOS) += pinctrl-milos.o
obj-$(CONFIG_PINCTRL_QCOM_QCM2290) += pinctrl-qcm2290.o
obj-$(CONFIG_PINCTRL_QCOM_QCS404) += pinctrl-qcs404.o
obj-$(CONFIG_PINCTRL_QCOM_QCS615) += pinctrl-qcs615.o
diff --git a/drivers/pinctrl/qcom/pinctrl-milos.c b/drivers/pinctrl/qcom/pinctrl-milos.c
new file mode 100644
index 00000000000..4f958fbfbf3
--- /dev/null
+++ b/drivers/pinctrl/qcom/pinctrl-milos.c
@@ -0,0 +1,103 @@
+// SPDX-License-Identifier: GPL-2.0+
+/*
+ * Qualcomm Milos pinctrl
+ *
+ * (C) Copyright 2024 Linaro Ltd.
+ * (C) Copyright 2026 Luca Weiss <[email protected]>
+ *
+ */
+
+#include <dm.h>
+
+#include "pinctrl-qcom.h"
+
+#define MAX_PIN_NAME_LEN 32
+static char pin_name[MAX_PIN_NAME_LEN] __section(".data");
+
+static const struct pinctrl_function msm_pinctrl_functions[] = {
+ {"qup0_se5", 1},
+ {"sdc2_clk", 1},
+ {"sdc2_cmd", 1},
+ {"sdc2_data", 1},
+ {"gpio", 0},
+};
+
+#define SDC_QDSD_PINGROUP(pg_name, ctl, pull, drv) \
+ { \
+ .name = pg_name, \
+ .ctl_reg = ctl, \
+ .io_reg = 0, \
+ .pull_bit = pull, \
+ .drv_bit = drv, \
+ .oe_bit = -1, \
+ .in_bit = -1, \
+ .out_bit = -1, \
+ }
+
+#define UFS_RESET(pg_name, ctl, io) \
+ { \
+ .name = pg_name, \
+ .ctl_reg = ctl, \
+ .io_reg = io, \
+ .pull_bit = 3, \
+ .drv_bit = 0, \
+ .oe_bit = -1, \
+ .in_bit = -1, \
+ .out_bit = 0, \
+ }
+
+static const struct msm_special_pin_data msm_special_pins_data[] = {
+ [0] = UFS_RESET("ufs_reset", 0xb4004, 0xb5000),
+ [1] = SDC_QDSD_PINGROUP("sdc2_clk", 0xab000, 0, 6),
+ [2] = SDC_QDSD_PINGROUP("sdc2_cmd", 0xab000, 12, 3),
+ [3] = SDC_QDSD_PINGROUP("sdc2_data", 0xab000, 9, 0),
+};
+
+static const char *milos_get_function_name(struct udevice *dev,
+ unsigned int selector)
+{
+ return msm_pinctrl_functions[selector].name;
+}
+
+static const char *milos_get_pin_name(struct udevice *dev,
+ unsigned int selector)
+{
+ if (selector >= 167 && selector <= 170)
+ snprintf(pin_name, MAX_PIN_NAME_LEN,
+ msm_special_pins_data[selector - 167].name);
+ else
+ snprintf(pin_name, MAX_PIN_NAME_LEN, "gpio%u", selector);
+
+ return pin_name;
+}
+
+static int milos_get_function_mux(__maybe_unused unsigned int pin,
+ unsigned int selector)
+{
+ return msm_pinctrl_functions[selector].val;
+}
+
+static struct msm_pinctrl_data milos_data = {
+ .pin_data = {
+ .pin_count = 171,
+ .special_pins_start = 167,
+ .special_pins_data = msm_special_pins_data,
+ },
+ .functions_count = ARRAY_SIZE(msm_pinctrl_functions),
+ .get_function_name = milos_get_function_name,
+ .get_function_mux = milos_get_function_mux,
+ .get_pin_name = milos_get_pin_name,
+};
+
+static const struct udevice_id msm_pinctrl_ids[] = {
+ { .compatible = "qcom,milos-tlmm", .data = (ulong)&milos_data },
+ { /* Sentinel */ }
+};
+
+U_BOOT_DRIVER(pinctrl_milos) = {
+ .name = "pinctrl_milos",
+ .id = UCLASS_NOP,
+ .of_match = msm_pinctrl_ids,
+ .ops = &msm_pinctrl_ops,
+ .bind = msm_pinctrl_bind,
+};