aboutsummaryrefslogtreecommitdiffstats
path: root/drivers
diff options
context:
space:
mode:
authorLinus Walleij <linus.walleij@linaro.org>2012-12-11 08:14:32 -0500
committerLinus Walleij <linus.walleij@linaro.org>2013-01-11 15:48:05 -0500
commit89216494ae23dc0071a2b7f8d8264cee55cc211d (patch)
tree74849c0f680c35876f82aa276bfa90b6c887a9f1 /drivers
parent9931faca02c604c22335f5a935a501bb2ace6e20 (diff)
pinctrl: skip deferral of hogs
Up until now, as hogs were always taken at the end of the pin control device registration, it didn't cause any problem. But when starting to hog pins from the device core it will cause deferral of the pin controller device itself since the default pin fetch is done *before* the device probes, so let's fix this annoyance (which is also aesthetically ugly). Also take some care to make sure that if any one map entry results in a deferral rather than a failure, then that deferral will take precedence. Reviewed-by: Stephen Warren <swarren@nvidia.com> Signed-off-by: Linus Walleij <linus.walleij@linaro.org>
Diffstat (limited to 'drivers')
-rw-r--r--drivers/pinctrl/core.c27
1 files changed, 24 insertions, 3 deletions
diff --git a/drivers/pinctrl/core.c b/drivers/pinctrl/core.c
index 59f5a965bdc4..5b4885c27d12 100644
--- a/drivers/pinctrl/core.c
+++ b/drivers/pinctrl/core.c
@@ -609,13 +609,16 @@ static int add_setting(struct pinctrl *p, struct pinctrl_map const *map)
609 609
610 setting->pctldev = get_pinctrl_dev_from_devname(map->ctrl_dev_name); 610 setting->pctldev = get_pinctrl_dev_from_devname(map->ctrl_dev_name);
611 if (setting->pctldev == NULL) { 611 if (setting->pctldev == NULL) {
612 dev_info(p->dev, "unknown pinctrl device %s in map entry, deferring probe",
613 map->ctrl_dev_name);
614 kfree(setting); 612 kfree(setting);
613 /* Do not defer probing of hogs (circular loop) */
614 if (!strcmp(map->ctrl_dev_name, map->dev_name))
615 return -ENODEV;
615 /* 616 /*
616 * OK let us guess that the driver is not there yet, and 617 * OK let us guess that the driver is not there yet, and
617 * let's defer obtaining this pinctrl handle to later... 618 * let's defer obtaining this pinctrl handle to later...
618 */ 619 */
620 dev_info(p->dev, "unknown pinctrl device %s in map entry, deferring probe",
621 map->ctrl_dev_name);
619 return -EPROBE_DEFER; 622 return -EPROBE_DEFER;
620 } 623 }
621 624
@@ -694,11 +697,29 @@ static struct pinctrl *create_pinctrl(struct device *dev)
694 continue; 697 continue;
695 698
696 ret = add_setting(p, map); 699 ret = add_setting(p, map);
697 if (ret < 0) { 700 /*
701 * At this point the adding of a setting may:
702 *
703 * - Defer, if the pinctrl device is not yet available
704 * - Fail, if the pinctrl device is not yet available,
705 * AND the setting is a hog. We cannot defer that, since
706 * the hog will kick in immediately after the device
707 * is registered.
708 *
709 * If the error returned was not -EPROBE_DEFER then we
710 * accumulate the errors to see if we end up with
711 * an -EPROBE_DEFER later, as that is the worst case.
712 */
713 if (ret == -EPROBE_DEFER) {
698 pinctrl_put_locked(p, false); 714 pinctrl_put_locked(p, false);
699 return ERR_PTR(ret); 715 return ERR_PTR(ret);
700 } 716 }
701 } 717 }
718 if (ret < 0) {
719 /* If some other error than deferral occured, return here */
720 pinctrl_put_locked(p, false);
721 return ERR_PTR(ret);
722 }
702 723
703 /* Add the pinctrl handle to the global list */ 724 /* Add the pinctrl handle to the global list */
704 list_add_tail(&p->node, &pinctrl_list); 725 list_add_tail(&p->node, &pinctrl_list);