]> git.kernelconcepts.de Git - karo-tx-linux.git/commitdiff
pinctrl: pinmux: Release all taken pins in pinmux_enable_setting error paths
authorAxel Lin <axel.lin@ingics.com>
Sat, 10 Nov 2012 13:53:20 +0000 (21:53 +0800)
committerLinus Walleij <linus.walleij@linaro.org>
Sun, 11 Nov 2012 19:18:32 +0000 (20:18 +0100)
Currently pinmux_enable_setting does not release all taken pins if
ops->enable() returns error. This patch ensures all taken pins are
released in any error paths.

Signed-off-by: Axel Lin <axel.lin@ingics.com>
Signed-off-by: Linus Walleij <linus.walleij@linaro.org>
drivers/pinctrl/pinmux.c

index 0ef01ee2835ff350a088492ee7e16d740ed97eba..1a00658b3ea070f336333160411f1b01bbc8f96e 100644 (file)
@@ -409,11 +409,7 @@ int pinmux_enable_setting(struct pinctrl_setting const *setting)
                        dev_err(pctldev->dev,
                                "could not request pin %d on device %s\n",
                                pins[i], pinctrl_dev_get_name(pctldev));
-                       /* On error release all taken pins */
-                       i--; /* this pin just failed */
-                       for (; i >= 0; i--)
-                               pin_free(pctldev, pins[i], NULL);
-                       return -ENODEV;
+                       goto err_pin_request;
                }
        }
 
@@ -429,8 +425,26 @@ int pinmux_enable_setting(struct pinctrl_setting const *setting)
                desc->mux_setting = &(setting->data.mux);
        }
 
-       return ops->enable(pctldev, setting->data.mux.func,
-                          setting->data.mux.group);
+       ret = ops->enable(pctldev, setting->data.mux.func,
+                         setting->data.mux.group);
+
+       if (ret)
+               goto err_enable;
+
+       return 0;
+
+err_enable:
+       for (i = 0; i < num_pins; i++) {
+               desc = pin_desc_get(pctldev, pins[i]);
+               if (desc)
+                       desc->mux_setting = NULL;
+       }
+err_pin_request:
+       /* On error release all taken pins */
+       while (--i >= 0)
+               pin_free(pctldev, pins[i], NULL);
+
+       return ret;
 }
 
 void pinmux_disable_setting(struct pinctrl_setting const *setting)