194d53084SVikas Manocha #include <common.h>
294d53084SVikas Manocha #include <dm.h>
394d53084SVikas Manocha #include <dm/pinctrl.h>
4075b0185SBenjamin Gaignard #include <hwspinlock.h>
577417102SVikas Manocha #include <asm/arch/gpio.h>
677417102SVikas Manocha #include <asm/gpio.h>
777417102SVikas Manocha #include <asm/io.h>
894d53084SVikas Manocha
994d53084SVikas Manocha DECLARE_GLOBAL_DATA_PTR;
1094d53084SVikas Manocha
1158fb3c8dSVikas Manocha #define MAX_PINS_ONE_IP 70
1277417102SVikas Manocha #define MODE_BITS_MASK 3
1377417102SVikas Manocha #define OSPEED_MASK 3
1477417102SVikas Manocha #define PUPD_MASK 3
1577417102SVikas Manocha #define OTYPE_MSK 1
1677417102SVikas Manocha #define AFR_MASK 0xF
1777417102SVikas Manocha
188f651ca6SPatrice Chotard struct stm32_pinctrl_priv {
19075b0185SBenjamin Gaignard struct hwspinlock hws;
208f651ca6SPatrice Chotard int pinctrl_ngpios;
218f651ca6SPatrice Chotard struct list_head gpio_dev;
228f651ca6SPatrice Chotard };
238f651ca6SPatrice Chotard
248f651ca6SPatrice Chotard struct stm32_gpio_bank {
258f651ca6SPatrice Chotard struct udevice *gpio_dev;
268f651ca6SPatrice Chotard struct list_head list;
278f651ca6SPatrice Chotard };
288f651ca6SPatrice Chotard
29075b0185SBenjamin Gaignard #ifndef CONFIG_SPL_BUILD
30075b0185SBenjamin Gaignard
314ff1c20bSPatrice Chotard static char pin_name[PINNAME_SIZE];
32b42d938cSPatrice Chotard #define PINMUX_MODE_COUNT 5
33b42d938cSPatrice Chotard static const char * const pinmux_mode[PINMUX_MODE_COUNT] = {
34b42d938cSPatrice Chotard "gpio input",
35b42d938cSPatrice Chotard "gpio output",
36b42d938cSPatrice Chotard "analog",
37b42d938cSPatrice Chotard "unknown",
38b42d938cSPatrice Chotard "alt function",
39b42d938cSPatrice Chotard };
40b42d938cSPatrice Chotard
stm32_pinctrl_get_af(struct udevice * dev,unsigned int offset)41b42d938cSPatrice Chotard static int stm32_pinctrl_get_af(struct udevice *dev, unsigned int offset)
42b42d938cSPatrice Chotard {
43b42d938cSPatrice Chotard struct stm32_gpio_priv *priv = dev_get_priv(dev);
44b42d938cSPatrice Chotard struct stm32_gpio_regs *regs = priv->regs;
45b42d938cSPatrice Chotard u32 af;
46b42d938cSPatrice Chotard u32 alt_shift = (offset % 8) * 4;
47b42d938cSPatrice Chotard u32 alt_index = offset / 8;
48b42d938cSPatrice Chotard
49b42d938cSPatrice Chotard af = (readl(®s->afr[alt_index]) &
50b42d938cSPatrice Chotard GENMASK(alt_shift + 3, alt_shift)) >> alt_shift;
51b42d938cSPatrice Chotard
52b42d938cSPatrice Chotard return af;
53b42d938cSPatrice Chotard }
54b42d938cSPatrice Chotard
stm32_populate_gpio_dev_list(struct udevice * dev)5504355041SPatrice Chotard static int stm32_populate_gpio_dev_list(struct udevice *dev)
5604355041SPatrice Chotard {
5704355041SPatrice Chotard struct stm32_pinctrl_priv *priv = dev_get_priv(dev);
5804355041SPatrice Chotard struct udevice *gpio_dev;
5904355041SPatrice Chotard struct udevice *child;
6004355041SPatrice Chotard struct stm32_gpio_bank *gpio_bank;
6104355041SPatrice Chotard int ret;
6204355041SPatrice Chotard
6304355041SPatrice Chotard /*
6404355041SPatrice Chotard * parse pin-controller sub-nodes (ie gpio bank nodes) and fill
6504355041SPatrice Chotard * a list with all gpio device reference which belongs to the
6604355041SPatrice Chotard * current pin-controller. This list is used to find pin_name and
6704355041SPatrice Chotard * pin muxing
6804355041SPatrice Chotard */
6904355041SPatrice Chotard list_for_each_entry(child, &dev->child_head, sibling_node) {
7004355041SPatrice Chotard ret = uclass_get_device_by_name(UCLASS_GPIO, child->name,
7104355041SPatrice Chotard &gpio_dev);
7204355041SPatrice Chotard if (ret < 0)
7304355041SPatrice Chotard continue;
7404355041SPatrice Chotard
7504355041SPatrice Chotard gpio_bank = malloc(sizeof(*gpio_bank));
7604355041SPatrice Chotard if (!gpio_bank) {
7704355041SPatrice Chotard dev_err(dev, "Not enough memory\n");
7804355041SPatrice Chotard return -ENOMEM;
7904355041SPatrice Chotard }
8004355041SPatrice Chotard
8104355041SPatrice Chotard gpio_bank->gpio_dev = gpio_dev;
8204355041SPatrice Chotard list_add_tail(&gpio_bank->list, &priv->gpio_dev);
8304355041SPatrice Chotard }
8404355041SPatrice Chotard
8504355041SPatrice Chotard return 0;
8604355041SPatrice Chotard }
8704355041SPatrice Chotard
stm32_pinctrl_get_pins_count(struct udevice * dev)888f651ca6SPatrice Chotard static int stm32_pinctrl_get_pins_count(struct udevice *dev)
898f651ca6SPatrice Chotard {
908f651ca6SPatrice Chotard struct stm32_pinctrl_priv *priv = dev_get_priv(dev);
918f651ca6SPatrice Chotard struct gpio_dev_priv *uc_priv;
928f651ca6SPatrice Chotard struct stm32_gpio_bank *gpio_bank;
938f651ca6SPatrice Chotard
948f651ca6SPatrice Chotard /*
958f651ca6SPatrice Chotard * if get_pins_count has already been executed once on this
968f651ca6SPatrice Chotard * pin-controller, no need to run it again
978f651ca6SPatrice Chotard */
988f651ca6SPatrice Chotard if (priv->pinctrl_ngpios)
998f651ca6SPatrice Chotard return priv->pinctrl_ngpios;
1008f651ca6SPatrice Chotard
10104355041SPatrice Chotard if (list_empty(&priv->gpio_dev))
10204355041SPatrice Chotard stm32_populate_gpio_dev_list(dev);
1038f651ca6SPatrice Chotard /*
1048f651ca6SPatrice Chotard * walk through all banks to retrieve the pin-controller
1058f651ca6SPatrice Chotard * pins number
1068f651ca6SPatrice Chotard */
1078f651ca6SPatrice Chotard list_for_each_entry(gpio_bank, &priv->gpio_dev, list) {
1088f651ca6SPatrice Chotard uc_priv = dev_get_uclass_priv(gpio_bank->gpio_dev);
1098f651ca6SPatrice Chotard
1108f651ca6SPatrice Chotard priv->pinctrl_ngpios += uc_priv->gpio_count;
1118f651ca6SPatrice Chotard }
1128f651ca6SPatrice Chotard
1138f651ca6SPatrice Chotard return priv->pinctrl_ngpios;
1148f651ca6SPatrice Chotard }
1158f651ca6SPatrice Chotard
stm32_pinctrl_get_gpio_dev(struct udevice * dev,unsigned int selector,unsigned int * idx)1164ff1c20bSPatrice Chotard static struct udevice *stm32_pinctrl_get_gpio_dev(struct udevice *dev,
117*530b63c2SPatrice Chotard unsigned int selector,
118*530b63c2SPatrice Chotard unsigned int *idx)
1194ff1c20bSPatrice Chotard {
1204ff1c20bSPatrice Chotard struct stm32_pinctrl_priv *priv = dev_get_priv(dev);
1214ff1c20bSPatrice Chotard struct stm32_gpio_bank *gpio_bank;
1224ff1c20bSPatrice Chotard struct gpio_dev_priv *uc_priv;
123*530b63c2SPatrice Chotard int pin_count = 0;
1244ff1c20bSPatrice Chotard
12504355041SPatrice Chotard if (list_empty(&priv->gpio_dev))
12604355041SPatrice Chotard stm32_populate_gpio_dev_list(dev);
12704355041SPatrice Chotard
1284ff1c20bSPatrice Chotard /* look up for the bank which owns the requested pin */
1294ff1c20bSPatrice Chotard list_for_each_entry(gpio_bank, &priv->gpio_dev, list) {
1304ff1c20bSPatrice Chotard uc_priv = dev_get_uclass_priv(gpio_bank->gpio_dev);
1314ff1c20bSPatrice Chotard
132*530b63c2SPatrice Chotard if (selector < (pin_count + uc_priv->gpio_count)) {
133*530b63c2SPatrice Chotard /*
134*530b63c2SPatrice Chotard * we found the bank, convert pin selector to
135*530b63c2SPatrice Chotard * gpio bank index
136*530b63c2SPatrice Chotard */
137*530b63c2SPatrice Chotard *idx = stm32_offset_to_index(gpio_bank->gpio_dev,
138*530b63c2SPatrice Chotard selector - pin_count);
139*530b63c2SPatrice Chotard if (*idx < 0)
140*530b63c2SPatrice Chotard return NULL;
1414ff1c20bSPatrice Chotard
142*530b63c2SPatrice Chotard return gpio_bank->gpio_dev;
143*530b63c2SPatrice Chotard }
144*530b63c2SPatrice Chotard pin_count += uc_priv->gpio_count;
1454ff1c20bSPatrice Chotard }
1464ff1c20bSPatrice Chotard
1474ff1c20bSPatrice Chotard return NULL;
1484ff1c20bSPatrice Chotard }
1494ff1c20bSPatrice Chotard
stm32_pinctrl_get_pin_name(struct udevice * dev,unsigned int selector)1504ff1c20bSPatrice Chotard static const char *stm32_pinctrl_get_pin_name(struct udevice *dev,
1514ff1c20bSPatrice Chotard unsigned int selector)
1524ff1c20bSPatrice Chotard {
1534ff1c20bSPatrice Chotard struct gpio_dev_priv *uc_priv;
1544ff1c20bSPatrice Chotard struct udevice *gpio_dev;
155*530b63c2SPatrice Chotard unsigned int gpio_idx;
1564ff1c20bSPatrice Chotard
1574ff1c20bSPatrice Chotard /* look up for the bank which owns the requested pin */
158*530b63c2SPatrice Chotard gpio_dev = stm32_pinctrl_get_gpio_dev(dev, selector, &gpio_idx);
1594ff1c20bSPatrice Chotard if (!gpio_dev) {
1604ff1c20bSPatrice Chotard snprintf(pin_name, PINNAME_SIZE, "Error");
1614ff1c20bSPatrice Chotard } else {
1624ff1c20bSPatrice Chotard uc_priv = dev_get_uclass_priv(gpio_dev);
1634ff1c20bSPatrice Chotard
1644ff1c20bSPatrice Chotard snprintf(pin_name, PINNAME_SIZE, "%s%d",
1654ff1c20bSPatrice Chotard uc_priv->bank_name,
166*530b63c2SPatrice Chotard gpio_idx);
1674ff1c20bSPatrice Chotard }
1684ff1c20bSPatrice Chotard
1694ff1c20bSPatrice Chotard return pin_name;
1704ff1c20bSPatrice Chotard }
171b42d938cSPatrice Chotard
stm32_pinctrl_get_pin_muxing(struct udevice * dev,unsigned int selector,char * buf,int size)172b42d938cSPatrice Chotard static int stm32_pinctrl_get_pin_muxing(struct udevice *dev,
173b42d938cSPatrice Chotard unsigned int selector,
174b42d938cSPatrice Chotard char *buf,
175b42d938cSPatrice Chotard int size)
176b42d938cSPatrice Chotard {
177b42d938cSPatrice Chotard struct udevice *gpio_dev;
178b42d938cSPatrice Chotard const char *label;
179b42d938cSPatrice Chotard int mode;
180b42d938cSPatrice Chotard int af_num;
181*530b63c2SPatrice Chotard unsigned int gpio_idx;
182b42d938cSPatrice Chotard
183b42d938cSPatrice Chotard /* look up for the bank which owns the requested pin */
184*530b63c2SPatrice Chotard gpio_dev = stm32_pinctrl_get_gpio_dev(dev, selector, &gpio_idx);
185b42d938cSPatrice Chotard
186b42d938cSPatrice Chotard if (!gpio_dev)
187b42d938cSPatrice Chotard return -ENODEV;
188b42d938cSPatrice Chotard
189*530b63c2SPatrice Chotard mode = gpio_get_raw_function(gpio_dev, gpio_idx, &label);
190b42d938cSPatrice Chotard
191*530b63c2SPatrice Chotard dev_dbg(dev, "selector = %d gpio_idx = %d mode = %d\n",
192*530b63c2SPatrice Chotard selector, gpio_idx, mode);
193b42d938cSPatrice Chotard
194b42d938cSPatrice Chotard
195b42d938cSPatrice Chotard switch (mode) {
196b42d938cSPatrice Chotard case GPIOF_UNKNOWN:
197b42d938cSPatrice Chotard /* should never happen */
198b42d938cSPatrice Chotard return -EINVAL;
199b42d938cSPatrice Chotard case GPIOF_UNUSED:
200b42d938cSPatrice Chotard snprintf(buf, size, "%s", pinmux_mode[mode]);
201b42d938cSPatrice Chotard break;
202b42d938cSPatrice Chotard case GPIOF_FUNC:
203*530b63c2SPatrice Chotard af_num = stm32_pinctrl_get_af(gpio_dev, gpio_idx);
204b42d938cSPatrice Chotard snprintf(buf, size, "%s %d", pinmux_mode[mode], af_num);
205b42d938cSPatrice Chotard break;
206b42d938cSPatrice Chotard case GPIOF_OUTPUT:
207b42d938cSPatrice Chotard case GPIOF_INPUT:
208b42d938cSPatrice Chotard snprintf(buf, size, "%s %s",
209b42d938cSPatrice Chotard pinmux_mode[mode], label ? label : "");
210b42d938cSPatrice Chotard break;
211b42d938cSPatrice Chotard }
212b42d938cSPatrice Chotard
213b42d938cSPatrice Chotard return 0;
214b42d938cSPatrice Chotard }
215b42d938cSPatrice Chotard
216075b0185SBenjamin Gaignard #endif
217075b0185SBenjamin Gaignard
stm32_pinctrl_probe(struct udevice * dev)2188f651ca6SPatrice Chotard int stm32_pinctrl_probe(struct udevice *dev)
2198f651ca6SPatrice Chotard {
2208f651ca6SPatrice Chotard struct stm32_pinctrl_priv *priv = dev_get_priv(dev);
2218f651ca6SPatrice Chotard int ret;
2228f651ca6SPatrice Chotard
2238f651ca6SPatrice Chotard INIT_LIST_HEAD(&priv->gpio_dev);
2248f651ca6SPatrice Chotard
225075b0185SBenjamin Gaignard /* hwspinlock property is optional, just log the error */
226075b0185SBenjamin Gaignard ret = hwspinlock_get_by_index(dev, 0, &priv->hws);
227075b0185SBenjamin Gaignard if (ret)
228075b0185SBenjamin Gaignard debug("%s: hwspinlock_get_by_index may have failed (%d)\n",
229075b0185SBenjamin Gaignard __func__, ret);
230075b0185SBenjamin Gaignard
2318f651ca6SPatrice Chotard return 0;
2328f651ca6SPatrice Chotard }
2338f651ca6SPatrice Chotard
stm32_gpio_config(struct gpio_desc * desc,const struct stm32_gpio_ctl * ctl)23477417102SVikas Manocha static int stm32_gpio_config(struct gpio_desc *desc,
23577417102SVikas Manocha const struct stm32_gpio_ctl *ctl)
23677417102SVikas Manocha {
23777417102SVikas Manocha struct stm32_gpio_priv *priv = dev_get_priv(desc->dev);
23877417102SVikas Manocha struct stm32_gpio_regs *regs = priv->regs;
239075b0185SBenjamin Gaignard struct stm32_pinctrl_priv *ctrl_priv;
240075b0185SBenjamin Gaignard int ret;
24177417102SVikas Manocha u32 index;
24277417102SVikas Manocha
24377417102SVikas Manocha if (!ctl || ctl->af > 15 || ctl->mode > 3 || ctl->otype > 1 ||
24477417102SVikas Manocha ctl->pupd > 2 || ctl->speed > 3)
24577417102SVikas Manocha return -EINVAL;
24677417102SVikas Manocha
247075b0185SBenjamin Gaignard ctrl_priv = dev_get_priv(dev_get_parent(desc->dev));
248075b0185SBenjamin Gaignard ret = hwspinlock_lock_timeout(&ctrl_priv->hws, 10);
249075b0185SBenjamin Gaignard if (ret == -ETIME) {
250075b0185SBenjamin Gaignard dev_err(desc->dev, "HWSpinlock timeout\n");
251075b0185SBenjamin Gaignard return ret;
252075b0185SBenjamin Gaignard }
253075b0185SBenjamin Gaignard
25477417102SVikas Manocha index = (desc->offset & 0x07) * 4;
25577417102SVikas Manocha clrsetbits_le32(®s->afr[desc->offset >> 3], AFR_MASK << index,
25677417102SVikas Manocha ctl->af << index);
25777417102SVikas Manocha
25877417102SVikas Manocha index = desc->offset * 2;
25977417102SVikas Manocha clrsetbits_le32(®s->moder, MODE_BITS_MASK << index,
26077417102SVikas Manocha ctl->mode << index);
26177417102SVikas Manocha clrsetbits_le32(®s->ospeedr, OSPEED_MASK << index,
26277417102SVikas Manocha ctl->speed << index);
26377417102SVikas Manocha clrsetbits_le32(®s->pupdr, PUPD_MASK << index, ctl->pupd << index);
26477417102SVikas Manocha
26577417102SVikas Manocha index = desc->offset;
26677417102SVikas Manocha clrsetbits_le32(®s->otyper, OTYPE_MSK << index, ctl->otype << index);
26777417102SVikas Manocha
268075b0185SBenjamin Gaignard hwspinlock_unlock(&ctrl_priv->hws);
269075b0185SBenjamin Gaignard
27077417102SVikas Manocha return 0;
27177417102SVikas Manocha }
2728aeba629SPatrick Delaunay
prep_gpio_dsc(struct stm32_gpio_dsc * gpio_dsc,u32 port_pin)27394d53084SVikas Manocha static int prep_gpio_dsc(struct stm32_gpio_dsc *gpio_dsc, u32 port_pin)
27494d53084SVikas Manocha {
2758aeba629SPatrick Delaunay gpio_dsc->port = (port_pin & 0x1F000) >> 12;
27694d53084SVikas Manocha gpio_dsc->pin = (port_pin & 0x0F00) >> 8;
27794d53084SVikas Manocha debug("%s: GPIO:port= %d, pin= %d\n", __func__, gpio_dsc->port,
27894d53084SVikas Manocha gpio_dsc->pin);
27994d53084SVikas Manocha
28094d53084SVikas Manocha return 0;
28194d53084SVikas Manocha }
28294d53084SVikas Manocha
prep_gpio_ctl(struct stm32_gpio_ctl * gpio_ctl,u32 gpio_fn,int node)28394d53084SVikas Manocha static int prep_gpio_ctl(struct stm32_gpio_ctl *gpio_ctl, u32 gpio_fn, int node)
28494d53084SVikas Manocha {
28594d53084SVikas Manocha gpio_fn &= 0x00FF;
28677417102SVikas Manocha gpio_ctl->af = 0;
28794d53084SVikas Manocha
28894d53084SVikas Manocha switch (gpio_fn) {
28994d53084SVikas Manocha case 0:
29094d53084SVikas Manocha gpio_ctl->mode = STM32_GPIO_MODE_IN;
29194d53084SVikas Manocha break;
29294d53084SVikas Manocha case 1 ... 16:
29394d53084SVikas Manocha gpio_ctl->mode = STM32_GPIO_MODE_AF;
29494d53084SVikas Manocha gpio_ctl->af = gpio_fn - 1;
29594d53084SVikas Manocha break;
29694d53084SVikas Manocha case 17:
29794d53084SVikas Manocha gpio_ctl->mode = STM32_GPIO_MODE_AN;
29894d53084SVikas Manocha break;
29994d53084SVikas Manocha default:
30094d53084SVikas Manocha gpio_ctl->mode = STM32_GPIO_MODE_OUT;
30194d53084SVikas Manocha break;
30294d53084SVikas Manocha }
30394d53084SVikas Manocha
30494d53084SVikas Manocha gpio_ctl->speed = fdtdec_get_int(gd->fdt_blob, node, "slew-rate", 0);
30594d53084SVikas Manocha
30694d53084SVikas Manocha if (fdtdec_get_bool(gd->fdt_blob, node, "drive-open-drain"))
30794d53084SVikas Manocha gpio_ctl->otype = STM32_GPIO_OTYPE_OD;
30894d53084SVikas Manocha else
30994d53084SVikas Manocha gpio_ctl->otype = STM32_GPIO_OTYPE_PP;
31094d53084SVikas Manocha
31194d53084SVikas Manocha if (fdtdec_get_bool(gd->fdt_blob, node, "bias-pull-up"))
31294d53084SVikas Manocha gpio_ctl->pupd = STM32_GPIO_PUPD_UP;
31394d53084SVikas Manocha else if (fdtdec_get_bool(gd->fdt_blob, node, "bias-pull-down"))
31494d53084SVikas Manocha gpio_ctl->pupd = STM32_GPIO_PUPD_DOWN;
31594d53084SVikas Manocha else
31694d53084SVikas Manocha gpio_ctl->pupd = STM32_GPIO_PUPD_NO;
31794d53084SVikas Manocha
31894d53084SVikas Manocha debug("%s: gpio fn= %d, slew-rate= %x, op type= %x, pull-upd is = %x\n",
31994d53084SVikas Manocha __func__, gpio_fn, gpio_ctl->speed, gpio_ctl->otype,
32094d53084SVikas Manocha gpio_ctl->pupd);
32194d53084SVikas Manocha
32294d53084SVikas Manocha return 0;
32394d53084SVikas Manocha }
32494d53084SVikas Manocha
stm32_pinctrl_config(int offset)325ad0376e0SChristophe Kerello static int stm32_pinctrl_config(int offset)
32694d53084SVikas Manocha {
32758fb3c8dSVikas Manocha u32 pin_mux[MAX_PINS_ONE_IP];
32894d53084SVikas Manocha int rv, len;
32994d53084SVikas Manocha
33094d53084SVikas Manocha /*
33194d53084SVikas Manocha * check for "pinmux" property in each subnode (e.g. pins1 and pins2 for
33294d53084SVikas Manocha * usart1) of pin controller phandle "pinctrl-0"
33394d53084SVikas Manocha * */
334ad0376e0SChristophe Kerello fdt_for_each_subnode(offset, gd->fdt_blob, offset) {
33594d53084SVikas Manocha struct stm32_gpio_dsc gpio_dsc;
33694d53084SVikas Manocha struct stm32_gpio_ctl gpio_ctl;
33794d53084SVikas Manocha int i;
33894d53084SVikas Manocha
339ad0376e0SChristophe Kerello len = fdtdec_get_int_array_count(gd->fdt_blob, offset,
34094d53084SVikas Manocha "pinmux", pin_mux,
34194d53084SVikas Manocha ARRAY_SIZE(pin_mux));
342ad0376e0SChristophe Kerello debug("%s: no of pinmux entries= %d\n", __func__, len);
34394d53084SVikas Manocha if (len < 0)
34494d53084SVikas Manocha return -EINVAL;
34594d53084SVikas Manocha for (i = 0; i < len; i++) {
346280057bdSVikas Manocha struct gpio_desc desc;
3478aeba629SPatrick Delaunay
34894d53084SVikas Manocha debug("%s: pinmux = %x\n", __func__, *(pin_mux + i));
34994d53084SVikas Manocha prep_gpio_dsc(&gpio_dsc, *(pin_mux + i));
350ad0376e0SChristophe Kerello prep_gpio_ctl(&gpio_ctl, *(pin_mux + i), offset);
351280057bdSVikas Manocha rv = uclass_get_device_by_seq(UCLASS_GPIO,
3528aeba629SPatrick Delaunay gpio_dsc.port,
3538aeba629SPatrick Delaunay &desc.dev);
354280057bdSVikas Manocha if (rv)
355280057bdSVikas Manocha return rv;
356280057bdSVikas Manocha desc.offset = gpio_dsc.pin;
357280057bdSVikas Manocha rv = stm32_gpio_config(&desc, &gpio_ctl);
35894d53084SVikas Manocha debug("%s: rv = %d\n\n", __func__, rv);
35994d53084SVikas Manocha if (rv)
36094d53084SVikas Manocha return rv;
36194d53084SVikas Manocha }
36294d53084SVikas Manocha }
36394d53084SVikas Manocha
36494d53084SVikas Manocha return 0;
36594d53084SVikas Manocha }
36694d53084SVikas Manocha
367bb44b968SChristophe Kerello #if CONFIG_IS_ENABLED(PINCTRL_FULL)
stm32_pinctrl_set_state(struct udevice * dev,struct udevice * config)368bb44b968SChristophe Kerello static int stm32_pinctrl_set_state(struct udevice *dev, struct udevice *config)
369bb44b968SChristophe Kerello {
370bb44b968SChristophe Kerello return stm32_pinctrl_config(dev_of_offset(config));
371bb44b968SChristophe Kerello }
372bb44b968SChristophe Kerello #else /* PINCTRL_FULL */
stm32_pinctrl_set_state_simple(struct udevice * dev,struct udevice * periph)373ad0376e0SChristophe Kerello static int stm32_pinctrl_set_state_simple(struct udevice *dev,
374ad0376e0SChristophe Kerello struct udevice *periph)
375ad0376e0SChristophe Kerello {
376ad0376e0SChristophe Kerello const void *fdt = gd->fdt_blob;
377ad0376e0SChristophe Kerello const fdt32_t *list;
378ad0376e0SChristophe Kerello uint32_t phandle;
379ad0376e0SChristophe Kerello int config_node;
380ad0376e0SChristophe Kerello int size, i, ret;
381ad0376e0SChristophe Kerello
382ad0376e0SChristophe Kerello list = fdt_getprop(fdt, dev_of_offset(periph), "pinctrl-0", &size);
383ad0376e0SChristophe Kerello if (!list)
384ad0376e0SChristophe Kerello return -EINVAL;
385ad0376e0SChristophe Kerello
386ad0376e0SChristophe Kerello debug("%s: periph->name = %s\n", __func__, periph->name);
387ad0376e0SChristophe Kerello
388ad0376e0SChristophe Kerello size /= sizeof(*list);
389ad0376e0SChristophe Kerello for (i = 0; i < size; i++) {
390ad0376e0SChristophe Kerello phandle = fdt32_to_cpu(*list++);
391ad0376e0SChristophe Kerello
392ad0376e0SChristophe Kerello config_node = fdt_node_offset_by_phandle(fdt, phandle);
393ad0376e0SChristophe Kerello if (config_node < 0) {
3949b643e31SMasahiro Yamada pr_err("prop pinctrl-0 index %d invalid phandle\n", i);
395ad0376e0SChristophe Kerello return -EINVAL;
396ad0376e0SChristophe Kerello }
397ad0376e0SChristophe Kerello
398ad0376e0SChristophe Kerello ret = stm32_pinctrl_config(config_node);
399ad0376e0SChristophe Kerello if (ret)
400ad0376e0SChristophe Kerello return ret;
401ad0376e0SChristophe Kerello }
402ad0376e0SChristophe Kerello
403ad0376e0SChristophe Kerello return 0;
404ad0376e0SChristophe Kerello }
405bb44b968SChristophe Kerello #endif /* PINCTRL_FULL */
406ad0376e0SChristophe Kerello
40794d53084SVikas Manocha static struct pinctrl_ops stm32_pinctrl_ops = {
408bb44b968SChristophe Kerello #if CONFIG_IS_ENABLED(PINCTRL_FULL)
409bb44b968SChristophe Kerello .set_state = stm32_pinctrl_set_state,
410bb44b968SChristophe Kerello #else /* PINCTRL_FULL */
41194d53084SVikas Manocha .set_state_simple = stm32_pinctrl_set_state_simple,
412bb44b968SChristophe Kerello #endif /* PINCTRL_FULL */
4138f651ca6SPatrice Chotard #ifndef CONFIG_SPL_BUILD
4144ff1c20bSPatrice Chotard .get_pin_name = stm32_pinctrl_get_pin_name,
4158f651ca6SPatrice Chotard .get_pins_count = stm32_pinctrl_get_pins_count,
416b42d938cSPatrice Chotard .get_pin_muxing = stm32_pinctrl_get_pin_muxing,
4178f651ca6SPatrice Chotard #endif
41894d53084SVikas Manocha };
41994d53084SVikas Manocha
42094d53084SVikas Manocha static const struct udevice_id stm32_pinctrl_ids[] = {
42198693c22SPatrice Chotard { .compatible = "st,stm32f429-pinctrl" },
42298693c22SPatrice Chotard { .compatible = "st,stm32f469-pinctrl" },
42394d53084SVikas Manocha { .compatible = "st,stm32f746-pinctrl" },
424092e72cbSPatrice Chotard { .compatible = "st,stm32h743-pinctrl" },
4258aeba629SPatrick Delaunay { .compatible = "st,stm32mp157-pinctrl" },
4268aeba629SPatrick Delaunay { .compatible = "st,stm32mp157-z-pinctrl" },
42794d53084SVikas Manocha { }
42894d53084SVikas Manocha };
42994d53084SVikas Manocha
43094d53084SVikas Manocha U_BOOT_DRIVER(pinctrl_stm32) = {
43194d53084SVikas Manocha .name = "pinctrl_stm32",
43294d53084SVikas Manocha .id = UCLASS_PINCTRL,
43394d53084SVikas Manocha .of_match = stm32_pinctrl_ids,
43494d53084SVikas Manocha .ops = &stm32_pinctrl_ops,
43594d53084SVikas Manocha .bind = dm_scan_fdt_dev,
4368f651ca6SPatrice Chotard .probe = stm32_pinctrl_probe,
4378f651ca6SPatrice Chotard .priv_auto_alloc_size = sizeof(struct stm32_pinctrl_priv),
43894d53084SVikas Manocha };
439