pinctrl: sunxi: dt: Consider pin base when calculating bank number from pin
authorChen-Yu Tsai <wens@csie.org>
Sat, 7 Jun 2025 13:52:03 +0000 (21:52 +0800)
committerLinus Walleij <linus.walleij@linaro.org>
Tue, 10 Jun 2025 12:35:40 +0000 (14:35 +0200)
In prepare_function_table() when the pinctrl function table IRQ entries
are generated, the pin bank is calculated from the absolute pin number;
however the IRQ bank mux array is indexed from the first pin bank of the
controller. For R_PIO controllers, this means the absolute pin bank is
way off from the relative pin bank used for array indexing.

Correct this by taking into account the pin base of the controller.

Fixes: f5e2cd34b12f ("pinctrl: sunxi: allow reading mux values from DT")
Signed-off-by: Chen-Yu Tsai <wens@csie.org>
Link: https://lore.kernel.org/20250607135203.2085226-1-wens@kernel.org
Signed-off-by: Linus Walleij <linus.walleij@linaro.org>
drivers/pinctrl/sunxi/pinctrl-sunxi-dt.c

index 1833078f68776ca0c4b9fe49e3f0fe9e6b385eb7..4e34b0cd3b73aad2ba99a9e87d83f5003c32a214 100644 (file)
@@ -143,7 +143,7 @@ static struct sunxi_desc_pin *init_pins_table(struct device *dev,
  */
 static int prepare_function_table(struct device *dev, struct device_node *pnode,
                                  struct sunxi_desc_pin *pins, int npins,
-                                 const u8 *irq_bank_muxes)
+                                 unsigned pin_base, const u8 *irq_bank_muxes)
 {
        struct device_node *node;
        struct property *prop;
@@ -166,7 +166,7 @@ static int prepare_function_table(struct device *dev, struct device_node *pnode,
         */
        for (i = 0; i < npins; i++) {
                struct sunxi_desc_pin *pin = &pins[i];
-               int bank = pin->pin.number / PINS_PER_BANK;
+               int bank = (pin->pin.number - pin_base) / PINS_PER_BANK;
 
                if (irq_bank_muxes[bank]) {
                        pin->variant++;
@@ -211,7 +211,7 @@ static int prepare_function_table(struct device *dev, struct device_node *pnode,
        last_bank = 0;
        for (i = 0; i < npins; i++) {
                struct sunxi_desc_pin *pin = &pins[i];
-               int bank = pin->pin.number / PINS_PER_BANK;
+               int bank = (pin->pin.number - pin_base) / PINS_PER_BANK;
                int lastfunc = pin->variant + 1;
                int irq_mux = irq_bank_muxes[bank];
 
@@ -353,7 +353,7 @@ int sunxi_pinctrl_dt_table_init(struct platform_device *pdev,
                return PTR_ERR(pins);
 
        ret = prepare_function_table(&pdev->dev, pnode, pins, desc->npins,
-                                    irq_bank_muxes);
+                                    desc->pin_base, irq_bank_muxes);
        if (ret)
                return ret;