From patchwork Sat Jul 20 06:16:42 2019 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Saravana Kannan X-Patchwork-Id: 1134353 Return-Path: X-Original-To: incoming-dt@patchwork.ozlabs.org Delivered-To: patchwork-incoming-dt@bilbo.ozlabs.org Authentication-Results: ozlabs.org; spf=none (mailfrom) smtp.mailfrom=vger.kernel.org (client-ip=209.132.180.67; helo=vger.kernel.org; envelope-from=devicetree-owner@vger.kernel.org; receiver=) Authentication-Results: ozlabs.org; dmarc=pass (p=reject dis=none) header.from=google.com Authentication-Results: ozlabs.org; dkim=pass (2048-bit key; unprotected) header.d=google.com header.i=@google.com header.b="jhWeaEAs"; dkim-atps=neutral Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by ozlabs.org (Postfix) with ESMTP id 45rHj35RSxz9sNf for ; Sat, 20 Jul 2019 16:17:27 +1000 (AEST) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1726346AbfGTGRG (ORCPT ); Sat, 20 Jul 2019 02:17:06 -0400 Received: from mail-qt1-f201.google.com ([209.85.160.201]:40214 "EHLO mail-qt1-f201.google.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1726333AbfGTGRF (ORCPT ); Sat, 20 Jul 2019 02:17:05 -0400 Received: by mail-qt1-f201.google.com with SMTP id e32so29753423qtc.7 for ; Fri, 19 Jul 2019 23:17:05 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=20161025; h=date:in-reply-to:message-id:mime-version:references:subject:from:to :cc; bh=Og1mQTkoBXXuVmW9REcEW86ek8LbY7FIolyGM3Z5bgQ=; b=jhWeaEAsKTy4JC/sfjf9cTu2h5M+N+o9Q4FfTdmeNdB7KuyHSjFIuO1dItmHeV5mvp Xn7+Bzn7LSPL2qVoBHW5cvdvwtH7FB60bcwoxFwaSZ+Ff/dSrExgxbdDRtix7xqa9cBt eBd1jcRu9t185Cb80k09pATa5RJ3KFaCRZCAXasQKW5yIWpMEaZt7HFhqrEe6amTvTrI wmApWHPoqbAeDchGdb3VC9GhRpuAmznNP4ps5x1OQfXuWZ9pZhLWMyFfysGz4SfoSPmw nq5LlyjXY89bjX8kaH7NC8BRyGfKEu474thyR4ijoNVyysktQHIYToQoFLPKw5FXK+0I wYLg== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:date:in-reply-to:message-id:mime-version :references:subject:from:to:cc; bh=Og1mQTkoBXXuVmW9REcEW86ek8LbY7FIolyGM3Z5bgQ=; b=uWyblP5c0O0ObWMt98oDwZ5NKwjRus6GxbbPOtaCQ0i9P9Ay6/use1O12liXr47/RS ZhOoJdLWHRuDww0R5UWbEuyGWHxaUIt9dDtWFa+y6cA6VsEp9iM7LjPiS9yGUybxgLXI 2qnPufttG2Oz4R5wC2bueoAAU3SlETwdqKG+/grkV357L74Mw8iiE66zS5g8Yswurhnk p7ZCFf13aSsgDjCEovrVdxmKXK5ydNkRK/2VwlWrYbYjnboWmemGyXTAuWEbwKTDyNAQ yfJ0CER9D270tED2RkRe54IsPHgGvBIn524emGyIhr0P8ePRB0OWPZPJars2rWBBEPPO wFLg== X-Gm-Message-State: APjAAAWAb5G+Q+c4JdgxIA6Dwlir7Cun2GgPudfE0cDOr+E99rYrzi80 LrbAE1VeMG2rd3LmcOGzRpOy1uqyJDLRWQg= X-Google-Smtp-Source: APXvYqz0mSnepFmFR82ABoetJqAuNQphWIzPe508tQEck+N6DfNGK0n2KiJkoQN9nf5Ic3tzE07AK6NnVWfBlCE= X-Received: by 2002:ac8:333d:: with SMTP id t58mr41352177qta.167.1563603424389; Fri, 19 Jul 2019 23:17:04 -0700 (PDT) Date: Fri, 19 Jul 2019 23:16:42 -0700 In-Reply-To: <20190720061647.234852-1-saravanak@google.com> Message-Id: <20190720061647.234852-4-saravanak@google.com> Mime-Version: 1.0 References: <20190720061647.234852-1-saravanak@google.com> X-Mailer: git-send-email 2.22.0.657.g960e92d24f-goog Subject: [PATCH v6 3/7] of/platform: Add functional dependency link from DT bindings From: Saravana Kannan To: Rob Herring , Mark Rutland , Greg Kroah-Hartman , "Rafael J. Wysocki" , Frank Rowand , Jonathan Corbet Cc: Saravana Kannan , devicetree@vger.kernel.org, linux-kernel@vger.kernel.org, David Collins , kernel-team@android.com, linux-doc@vger.kernel.org Sender: devicetree-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: devicetree@vger.kernel.org Add device-links after the devices are created (but before they are probed) by looking at common DT bindings like clocks and interconnects. Automatically adding device-links for functional dependencies at the framework level provides the following benefits: - Optimizes device probe order and avoids the useless work of attempting probes of devices that will not probe successfully (because their suppliers aren't present or haven't probed yet). For example, in a commonly available mobile SoC, registering just one consumer device's driver at an initcall level earlier than the supplier device's driver causes 11 failed probe attempts before the consumer device probes successfully. This was with a kernel with all the drivers statically compiled in. This problem gets a lot worse if all the drivers are loaded as modules without direct symbol dependencies. - Supplier devices like clock providers, interconnect providers, etc need to keep the resources they provide active and at a particular state(s) during boot up even if their current set of consumers don't request the resource to be active. This is because the rest of the consumers might not have probed yet and turning off the resource before all the consumers have probed could lead to a hang or undesired user experience. Some frameworks (Eg: regulator) handle this today by turning off "unused" resources at late_initcall_sync and hoping all the devices have probed by then. This is not a valid assumption for systems with loadable modules. Other frameworks (Eg: clock) just don't handle this due to the lack of a clear signal for when they can turn off resources. This leads to downstream hacks to handle cases like this that can easily be solved in the upstream kernel. By linking devices before they are probed, we give suppliers a clear count of the number of dependent consumers. Once all of the consumers are active, the suppliers can turn off the unused resources without making assumptions about the number of consumers. By default we just add device-links to track "driver presence" (probe succeeded) of the supplier device. If any other functionality provided by device-links are needed, it is left to the consumer/supplier devices to change the link when they probe. Signed-off-by: Saravana Kannan --- .../admin-guide/kernel-parameters.txt | 5 + drivers/of/platform.c | 158 ++++++++++++++++++ 2 files changed, 163 insertions(+) diff --git a/Documentation/admin-guide/kernel-parameters.txt b/Documentation/admin-guide/kernel-parameters.txt index 138f6664b2e2..109b4310844f 100644 --- a/Documentation/admin-guide/kernel-parameters.txt +++ b/Documentation/admin-guide/kernel-parameters.txt @@ -3141,6 +3141,11 @@ This can be set from sysctl after boot. See Documentation/sysctl/vm.txt for details. + of_devlink [KNL] Make device links from common DT bindings. Useful + for optimizing probe order and making sure resources + aren't turned off before the consumer devices have + probed. + ohci1394_dma=early [HW] enable debugging via the ohci1394 driver. See Documentation/debugging-via-ohci1394.txt for more info. diff --git a/drivers/of/platform.c b/drivers/of/platform.c index 04ad312fd85b..88a2086e26fa 100644 --- a/drivers/of/platform.c +++ b/drivers/of/platform.c @@ -509,6 +509,163 @@ int of_platform_default_populate(struct device_node *root, } EXPORT_SYMBOL_GPL(of_platform_default_populate); +bool of_link_is_valid(struct device_node *con, struct device_node *sup) +{ + of_node_get(sup); + /* + * Don't allow linking a device node as a consumer of one of its + * descendant nodes. By definition, a child node can't be a functional + * dependency for the parent node. + */ + while (sup) { + if (sup == con) { + of_node_put(sup); + return false; + } + sup = of_get_next_parent(sup); + } + return true; +} + +static int of_link_to_phandle(struct device *dev, struct device_node *sup_np) +{ + struct platform_device *sup_dev; + u32 dl_flags = DL_FLAG_AUTOPROBE_CONSUMER; + int ret = 0; + + /* + * Since we are trying to create device links, we need to find + * the actual device node that owns this supplier phandle. + * Often times it's the same node, but sometimes it can be one + * of the parents. So walk up the parent till you find a + * device. + */ + while (sup_np && !of_find_property(sup_np, "compatible", NULL)) + sup_np = of_get_next_parent(sup_np); + if (!sup_np) + return 0; + + if (!of_link_is_valid(dev->of_node, sup_np)) { + of_node_put(sup_np); + return 0; + } + sup_dev = of_find_device_by_node(sup_np); + of_node_put(sup_np); + if (!sup_dev) + return -ENODEV; + if (!device_link_add(dev, &sup_dev->dev, dl_flags)) + ret = -ENODEV; + put_device(&sup_dev->dev); + return ret; +} + +static struct device_node *parse_prop_cells(struct device_node *np, + const char *prop, int i, + const char *binding, + const char *cell) +{ + struct of_phandle_args sup_args; + + if (!i && strcmp(prop, binding)) + return NULL; + + if (of_parse_phandle_with_args(np, binding, cell, i, &sup_args)) + return NULL; + + return sup_args.np; +} + +static struct device_node *parse_clocks(struct device_node *np, + const char *prop, int i) +{ + return parse_prop_cells(np, prop, i, "clocks", "#clock-cells"); +} + +static struct device_node *parse_interconnects(struct device_node *np, + const char *prop, int i) +{ + return parse_prop_cells(np, prop, i, "interconnects", + "#interconnect-cells"); +} + +static int strcmp_suffix(const char *str, const char *suffix) +{ + unsigned int len, suffix_len; + + len = strlen(str); + suffix_len = strlen(suffix); + if (len <= suffix_len) + return -1; + return strcmp(str + len - suffix_len, suffix); +} + +static struct device_node *parse_regulators(struct device_node *np, + const char *prop, int i) +{ + if (i || strcmp_suffix(prop, "-supply")) + return NULL; + + return of_parse_phandle(np, prop, 0); +} + +/** + * struct supplier_bindings - Information for parsing supplier DT binding + * + * @parse_prop: If the function cannot parse the property, return NULL. + * Otherwise, return the phandle listed in the property + * that corresponds to index i. + */ +struct supplier_bindings { + struct device_node *(*parse_prop)(struct device_node *np, + const char *name, int i); +}; + +struct supplier_bindings bindings[] = { + { .parse_prop = parse_clocks, }, + { .parse_prop = parse_interconnects, }, + { .parse_prop = parse_regulators, }, + { }, +}; + +static bool of_link_property(struct device *dev, struct device_node *con_np, + const char *prop) +{ + struct device_node *phandle; + struct supplier_bindings *s = bindings; + unsigned int i = 0; + bool done = true; + + while (!i && s->parse_prop) { + while ((phandle = s->parse_prop(con_np, prop, i))) { + i++; + if (of_link_to_phandle(dev, phandle)) + done = false; + } + s++; + } + return done ? 0 : -ENODEV; +} + +static bool of_devlink; +core_param(of_devlink, of_devlink, bool, 0); + +static int of_link_to_suppliers(struct device *dev) +{ + struct property *p; + bool done = true; + + if (!of_devlink) + return 0; + if (unlikely(!dev->of_node)) + return 0; + + for_each_property_of_node(dev->of_node, p) + if (of_link_property(dev, dev->of_node, p->name)) + done = false; + + return done ? 0 : -ENODEV; +} + #ifndef CONFIG_PPC static const struct of_device_id reserved_mem_matches[] = { { .compatible = "qcom,rmtfs-mem" }, @@ -524,6 +681,7 @@ static int __init of_platform_default_populate_init(void) if (!of_have_populated_dt()) return -ENODEV; + platform_bus_type.add_links = of_link_to_suppliers; /* * Handle certain compatibles explicitly, since we don't want to create * platform_devices for every node in /reserved-memory with a From patchwork Sat Jul 20 06:16:44 2019 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Saravana Kannan X-Patchwork-Id: 1134352 Return-Path: X-Original-To: incoming-dt@patchwork.ozlabs.org Delivered-To: patchwork-incoming-dt@bilbo.ozlabs.org Authentication-Results: ozlabs.org; spf=none (mailfrom) smtp.mailfrom=vger.kernel.org (client-ip=209.132.180.67; helo=vger.kernel.org; envelope-from=devicetree-owner@vger.kernel.org; receiver=) Authentication-Results: ozlabs.org; dmarc=pass (p=reject dis=none) header.from=google.com Authentication-Results: ozlabs.org; dkim=pass (2048-bit key; unprotected) header.d=google.com header.i=@google.com header.b="ZcIRGpRC"; dkim-atps=neutral Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by ozlabs.org (Postfix) with ESMTP id 45rHj23WDyz9sNf for ; Sat, 20 Jul 2019 16:17:26 +1000 (AEST) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1726399AbfGTGRM (ORCPT ); Sat, 20 Jul 2019 02:17:12 -0400 Received: from mail-pf1-f202.google.com ([209.85.210.202]:34825 "EHLO mail-pf1-f202.google.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1726393AbfGTGRL (ORCPT ); Sat, 20 Jul 2019 02:17:11 -0400 Received: by mail-pf1-f202.google.com with SMTP id r142so19965893pfc.2 for ; Fri, 19 Jul 2019 23:17:11 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=20161025; h=date:in-reply-to:message-id:mime-version:references:subject:from:to :cc; bh=MUMtT5fNTfc8RU/9CTuiAA1krAnocmy3WUu1kHP2UCU=; b=ZcIRGpRC6ImMsB6lcmhdeaG93F5yso9QsFv9UIzd6S5yw7j2RNg1NtSCBlBy+f4ZAY 6P56F61pR2uLx+g/zNIHkg0JMQe7cIRSmmy4NlCWha09GyVjqC7qfmsGDfQEQxk3AGrP iITpXE9OIe8zumu3B9dSA5PAe+icAYbflENH/oV2phFwkKcYlL9ZClqStukx79N9bG4G mUBTuhquOiEyDSd2g5IlFbuOUWnNu74J3I4FNIYLLE58b54ephRO1JKPUKbApN3lWIe6 1KxQcmRIOOI7Q8+50cLSr0K2fNg3NVl2p56m6tBhN1kAp9Q7+9lTvfpFGSSTcTDSNsFT Uz/g== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:date:in-reply-to:message-id:mime-version :references:subject:from:to:cc; bh=MUMtT5fNTfc8RU/9CTuiAA1krAnocmy3WUu1kHP2UCU=; b=jZJHfmdrO9WPYFW17axhTmX0AKIClLUqZ8BVskzQj6R72sdLGZ6ParVHMply6xI4O9 6Ft/V+7GXptS5+aNdStbFz3y4X8GcrQAYaJz+zqrQxfBpzl74zj9U3mBIPJOJEY8eh96 IE1L7jvnWXtVmVrgNpMZVqQe/BYdAmA3FPRQk0/McgjNGHu60pg1lLqTBxwtPJ2F36LC 7Nqu9GQPMjS6xcx3SXF6XegXdHbI2PRiSjFCXSGqSXn36Lepp1AXCYf//1wRKqg6Hq6Z pjBa8o0jnYJZ/28Ec94DL4A1DhuR94IFlWhoGj+6FPfLcboKxFaT4tkqDBxRg+yYixby S82A== X-Gm-Message-State: APjAAAX+DX7zRc/92RzhEvdKpVHVO7+4aXXo8eN6Ryo3t5dBUntAjv/r +Bk2Obu59pymeEKmNK8idPgbNH6tNLBhd3o= X-Google-Smtp-Source: APXvYqxKQVDMn5SLR1DIDSF3SNu3xYVoESeaCay+MnIMKEFONMVfjtcEKZrqhK6l1f0tlgMzemu+Qsq2kckBBMs= X-Received: by 2002:a65:6406:: with SMTP id a6mr22156058pgv.393.1563603430627; Fri, 19 Jul 2019 23:17:10 -0700 (PDT) Date: Fri, 19 Jul 2019 23:16:44 -0700 In-Reply-To: <20190720061647.234852-1-saravanak@google.com> Message-Id: <20190720061647.234852-6-saravanak@google.com> Mime-Version: 1.0 References: <20190720061647.234852-1-saravanak@google.com> X-Mailer: git-send-email 2.22.0.657.g960e92d24f-goog Subject: [PATCH v6 5/7] of/platform: Pause/resume sync state during init and of_platform_populate() From: Saravana Kannan To: Rob Herring , Mark Rutland , Greg Kroah-Hartman , "Rafael J. Wysocki" , Frank Rowand Cc: Saravana Kannan , devicetree@vger.kernel.org, linux-kernel@vger.kernel.org, David Collins , kernel-team@android.com Sender: devicetree-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: devicetree@vger.kernel.org When all the top level devices are populated from DT during kernel init, the supplier devices could be added and probed before the consumer devices are added and linked to the suppliers. To avoid the sync_state() callback from being called prematurely, pause the sync_state() callbacks before populating the devices and resume them at late_initcall_sync(). Similarly, when children devices are populated after kernel init using of_platform_populate(), there could be supplier-consumer dependencies between the children devices that are populated. To avoid the same problem with sync_state() being called prematurely, pause and resume sync_state() callbacks across of_platform_populate(). Signed-off-by: Saravana Kannan --- drivers/of/platform.c | 11 +++++++++++ 1 file changed, 11 insertions(+) diff --git a/drivers/of/platform.c b/drivers/of/platform.c index 88a2086e26fa..d0c2f6443247 100644 --- a/drivers/of/platform.c +++ b/drivers/of/platform.c @@ -486,6 +486,7 @@ int of_platform_populate(struct device_node *root, pr_debug("%s()\n", __func__); pr_debug(" starting at: %pOF\n", root); + device_links_supplier_sync_state_pause(); for_each_child_of_node(root, child) { rc = of_platform_bus_create(child, matches, lookup, parent, true); if (rc) { @@ -493,6 +494,8 @@ int of_platform_populate(struct device_node *root, break; } } + device_links_supplier_sync_state_resume(); + of_node_set_flag(root, OF_POPULATED_BUS); of_node_put(root); @@ -682,6 +685,7 @@ static int __init of_platform_default_populate_init(void) return -ENODEV; platform_bus_type.add_links = of_link_to_suppliers; + device_links_supplier_sync_state_pause(); /* * Handle certain compatibles explicitly, since we don't want to create * platform_devices for every node in /reserved-memory with a @@ -702,6 +706,13 @@ static int __init of_platform_default_populate_init(void) return 0; } arch_initcall_sync(of_platform_default_populate_init); + +static int __init of_platform_sync_state_init(void) +{ + device_links_supplier_sync_state_resume(); + return 0; +} +late_initcall_sync(of_platform_sync_state_init); #endif int of_platform_device_destroy(struct device *dev, void *data) From patchwork Sat Jul 20 06:16:45 2019 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Saravana Kannan X-Patchwork-Id: 1134350 Return-Path: X-Original-To: incoming-dt@patchwork.ozlabs.org Delivered-To: patchwork-incoming-dt@bilbo.ozlabs.org Authentication-Results: ozlabs.org; spf=none (mailfrom) smtp.mailfrom=vger.kernel.org (client-ip=209.132.180.67; helo=vger.kernel.org; envelope-from=devicetree-owner@vger.kernel.org; receiver=) Authentication-Results: ozlabs.org; dmarc=pass (p=reject dis=none) header.from=google.com Authentication-Results: ozlabs.org; dkim=pass (2048-bit key; unprotected) header.d=google.com header.i=@google.com header.b="JjeSiWUW"; dkim-atps=neutral Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by ozlabs.org (Postfix) with ESMTP id 45rHht3c9pz9sND for ; Sat, 20 Jul 2019 16:17:18 +1000 (AEST) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1726429AbfGTGRP (ORCPT ); Sat, 20 Jul 2019 02:17:15 -0400 Received: from mail-qk1-f201.google.com ([209.85.222.201]:47850 "EHLO mail-qk1-f201.google.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1726425AbfGTGRO (ORCPT ); Sat, 20 Jul 2019 02:17:14 -0400 Received: by mail-qk1-f201.google.com with SMTP id x17so28309125qkf.14 for ; Fri, 19 Jul 2019 23:17:14 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=20161025; h=date:in-reply-to:message-id:mime-version:references:subject:from:to :cc; bh=czN7OgNyihOa9VdIP6ZEMSedIRrbUsmUmhpHuJJjXTo=; b=JjeSiWUWj0/rue13YU+ELAHX6hLfpI4PJnFZ3Q3aZh5PTfek/rlsbRkh9vntEdz3pc RVJXwy8Z/Eq5iaSAz00CO7t/AzU/8PBLyovCjFnjha9Q3UbeEUv8jNIVllc5UZDvQbu6 iz5YOIH9wo86uj6dUCcIKZv9wTyW4SpxKEYiPy34pOz7dy3/Aax9RQLXEFYjhITigF2y eVurdpmIiZe3KXQMcoyvXqVq8XJ9iVAm7XR4T+aZ1r/sN4eIAhud6GkZvhQFh7732JAZ DKrXi6HKEMhxT1OhGFzJq1scn0ol5E0tdLDkd88gWhZ9U0UH1LCxNybbbYW0T3oWHtCq MTJQ== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:date:in-reply-to:message-id:mime-version :references:subject:from:to:cc; bh=czN7OgNyihOa9VdIP6ZEMSedIRrbUsmUmhpHuJJjXTo=; b=DMaJT/PUbi6s3yF79+GmIpX63l6tvY4dYX8tkOsXq27302yhUDmMj551fJJSHpY4Dg iCn4UCXzSdE3DJ76E2/c0t05SnRu1lcBPY3wjWPZO+aUtlxsSBUBah5ZWdoitOQkjs3i Frh4Umibzo/+w8QujxtJM6CUZM6HCpKSAsGGAAaG9yf5Jgja1EUHovsec2ULCOEsaw2o xfTfn67XkD6nvOiJdSLJ1whCOT9pjUYx55b+m/5w8AkRR1oM7OuFFEXF8fcoXObso7Vy 5NR1sETxLwb4HHitLZOYmytMGYa8tKC2Wuur3/1bMLqtELh69hQgHeU99KwiJFnPTwHZ NgTQ== X-Gm-Message-State: APjAAAX83RjvdZbC8Kjc0mCgWq6nfTH9b38AzfTyikYqsU97Fhd6xJej dtZmWVm0rG/CwweQ908leJ8cOnFVq9iMqKo= X-Google-Smtp-Source: APXvYqygd13xcNmYEyZjLdS4UFApbnJ8wQTgyJWml2t3cpy9zX8fatUprOcbabMm7FZ5uWgUmhb8yrS73/j7zmE= X-Received: by 2002:a37:7ec1:: with SMTP id z184mr38505880qkc.491.1563603433832; Fri, 19 Jul 2019 23:17:13 -0700 (PDT) Date: Fri, 19 Jul 2019 23:16:45 -0700 In-Reply-To: <20190720061647.234852-1-saravanak@google.com> Message-Id: <20190720061647.234852-7-saravanak@google.com> Mime-Version: 1.0 References: <20190720061647.234852-1-saravanak@google.com> X-Mailer: git-send-email 2.22.0.657.g960e92d24f-goog Subject: [PATCH v6 6/7] of/platform: Create device links for all child-supplier depencencies From: Saravana Kannan To: Rob Herring , Mark Rutland , Greg Kroah-Hartman , "Rafael J. Wysocki" , Frank Rowand Cc: Saravana Kannan , devicetree@vger.kernel.org, linux-kernel@vger.kernel.org, David Collins , kernel-team@android.com Sender: devicetree-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: devicetree@vger.kernel.org A parent device can have child devices that it adds when it probes. But this probing of the parent device can happen way after kernel init is done -- for example, when the parent device's driver is loaded as a module. In such cases, if the child devices depend on a supplier in the system, we need to make sure the supplier gets the sync_state() callback only after these child devices are added and probed. To achieve this, when creating device links for a device by looking at its DT node, don't just look at DT references at the top node level. Look at DT references in all the descendant nodes too and create device links from the ancestor device to all these supplier devices. This way, when the parent device probes and adds child devices, the child devices can then create their own device links to the suppliers and further delay the supplier's sync_state() callback to after the child devices are probed. Example: In this illustration, -> denotes DT references and indentation represents child status. Device node A Device node B -> D Device node C -> B, D Device node D Assume all these devices have their drivers loaded as modules. Without this patch, this is the sequence of events: 1. D is added. 2. A is added. 3. Device D probes. 4. Device D gets its sync_state() callback. 5. Device B and C might malfunction because their resources got altered/turned off before they can make active requests for them. With this patch, this is the sequence of events: 1. D is added. 2. A is added and creates device links to D. 3. Device link from A to B is not added because A is a parent of B. 4. Device D probes. 5. Device D does not get it's sync_state() callback because consumer A hasn't probed yet. 5. Device A probes. 5. a. Devices B and C are added. 5. b. Device links from B and C to D are added. 5. c. Device A's probe completes. 6. Device D does not get it's sync_state() callback because consumer A has probed but consumers B and C haven't probed yet. 7. Device B and C probe. 8. Device D gets it's sync_state() callback because all its consumers have probed. 9. None of the devices malfunction. Signed-off-by: Saravana Kannan --- drivers/of/platform.c | 27 +++++++++++++++++++-------- 1 file changed, 19 insertions(+), 8 deletions(-) diff --git a/drivers/of/platform.c b/drivers/of/platform.c index d0c2f6443247..c1a116f7a087 100644 --- a/drivers/of/platform.c +++ b/drivers/of/platform.c @@ -649,24 +649,35 @@ static bool of_link_property(struct device *dev, struct device_node *con_np, return done ? 0 : -ENODEV; } +static int __of_link_to_suppliers(struct device *dev, + struct device_node *con_np) +{ + struct device_node *child; + struct property *p; + bool done = true; + + for_each_property_of_node(con_np, p) + if (of_link_property(dev, con_np, p->name)) + done = false; + + for_each_child_of_node(con_np, child) + if (__of_link_to_suppliers(dev, child)) + done = false; + + return done ? 0 : -ENODEV; +} + static bool of_devlink; core_param(of_devlink, of_devlink, bool, 0); static int of_link_to_suppliers(struct device *dev) { - struct property *p; - bool done = true; - if (!of_devlink) return 0; if (unlikely(!dev->of_node)) return 0; - for_each_property_of_node(dev->of_node, p) - if (of_link_property(dev, dev->of_node, p->name)) - done = false; - - return done ? 0 : -ENODEV; + return __of_link_to_suppliers(dev, dev->of_node); } #ifndef CONFIG_PPC From patchwork Sat Jul 20 06:16:46 2019 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Saravana Kannan X-Patchwork-Id: 1134351 Return-Path: X-Original-To: incoming-dt@patchwork.ozlabs.org Delivered-To: patchwork-incoming-dt@bilbo.ozlabs.org Authentication-Results: ozlabs.org; spf=none (mailfrom) smtp.mailfrom=vger.kernel.org (client-ip=209.132.180.67; helo=vger.kernel.org; envelope-from=devicetree-owner@vger.kernel.org; receiver=) Authentication-Results: ozlabs.org; dmarc=pass (p=reject dis=none) header.from=google.com Authentication-Results: ozlabs.org; dkim=pass (2048-bit key; unprotected) header.d=google.com header.i=@google.com header.b="UOqEDx5B"; dkim-atps=neutral Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by ozlabs.org (Postfix) with ESMTP id 45rHj12HXCz9sNT for ; Sat, 20 Jul 2019 16:17:25 +1000 (AEST) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1726455AbfGTGRU (ORCPT ); Sat, 20 Jul 2019 02:17:20 -0400 Received: from mail-pl1-f201.google.com ([209.85.214.201]:43299 "EHLO mail-pl1-f201.google.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1726436AbfGTGRR (ORCPT ); Sat, 20 Jul 2019 02:17:17 -0400 Received: by mail-pl1-f201.google.com with SMTP id t2so16954849plo.10 for ; Fri, 19 Jul 2019 23:17:17 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=20161025; h=date:in-reply-to:message-id:mime-version:references:subject:from:to :cc; bh=XHZhcOCJhaOJlDHmwmoOr4DNUGpZjh/DgPbCgvVVpt0=; b=UOqEDx5Bi4XIR97mxVHJYqDas/gsviEa+U5OwWS5eTKp23OgwAL8BATExEQrvB5K3e Ac5paop5IS6XUhdjTZWHgpDoDoOWqQi2476Ysg+MGrfgVAzjXMld8YKcJJHViAa1SGdX hUkYrdANakYTdX/zk5IO2S3mEAx8rXP3gNNE7HZjzxm4i2cCs2y3EQN9EWVdMCNnEBFz TpU/TMt9MQC+Ptilkiks31OWbz2LLdF0QU4/jbIyoYugEgz7isdRkNSSt9l9uvzBHksG rTwMTpV8jj00BNiu3t7MVWhQkTM61rPqYZoKZ3V1kwSsCQRysU/IpzFXBOUyyoWjFjvT HH2Q== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:date:in-reply-to:message-id:mime-version :references:subject:from:to:cc; bh=XHZhcOCJhaOJlDHmwmoOr4DNUGpZjh/DgPbCgvVVpt0=; b=NeTnDj5uZIS8r9TCP6J3cEptPxkIGSWeofxWJ+He+h4GLDg4W2C7iyC6KFJ+B5A8tT skY5BjtDzRitunNmC8a1JizjdJ2rzdddJ6BH539Ql2AdHu9g1Glmwxln+hFNfHKBs/Xs zJ5BxazWBoHzkfBftlPvuuE+ZI+VMujBxEvzQgGln2xpbcPYunnWXp8OEP8IJi60lIVU t28lFLemFTvjafD4pZ9uXy+hWwGarKiCfLEovG+4wt4baqo+TTgwa5Tb0MEtJhY/Rtze kuMShQRhqPXdOpOqenxWQfKdS0EPf5nvkqMBLzPj9qtjgF+iRhxY+0sfE9DG1joEEL3X Ao/A== X-Gm-Message-State: APjAAAXPpY7hrfzx7LGllqpOrLy4CGWc1BGFb9e/Qc7dJTaU9NbY/rXt rwn61TvrgWFD0Ag8C3ARMLAQGZK3/bw2Fc8= X-Google-Smtp-Source: APXvYqzAzcE5vBjP6RCbXmbEeN0ZSnHHEiMT4lXXkWB1Ez6n0o/JsYvE1WUbpT4tc6ua9le+jI6/+snaGAzggFc= X-Received: by 2002:a63:1950:: with SMTP id 16mr58157917pgz.312.1563603436732; Fri, 19 Jul 2019 23:17:16 -0700 (PDT) Date: Fri, 19 Jul 2019 23:16:46 -0700 In-Reply-To: <20190720061647.234852-1-saravanak@google.com> Message-Id: <20190720061647.234852-8-saravanak@google.com> Mime-Version: 1.0 References: <20190720061647.234852-1-saravanak@google.com> X-Mailer: git-send-email 2.22.0.657.g960e92d24f-goog Subject: [PATCH v6 7/7] of/platform: Don't create device links for default busses From: Saravana Kannan To: Rob Herring , Mark Rutland , Greg Kroah-Hartman , "Rafael J. Wysocki" , Frank Rowand Cc: Saravana Kannan , devicetree@vger.kernel.org, linux-kernel@vger.kernel.org, David Collins , kernel-team@android.com Sender: devicetree-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: devicetree@vger.kernel.org Default busses also have devices created for them. But there's no point in creating device links for them. It's especially wasteful as it'll cause the traversal of the entire device tree and also spend a lot of time checking and figuring out that creating those links isn't allowed. So check for default busses and skip trying to create device links for them. Signed-off-by: Saravana Kannan --- drivers/of/platform.c | 2 ++ 1 file changed, 2 insertions(+) diff --git a/drivers/of/platform.c b/drivers/of/platform.c index c1a116f7a087..8bf975ee2ff7 100644 --- a/drivers/of/platform.c +++ b/drivers/of/platform.c @@ -676,6 +676,8 @@ static int of_link_to_suppliers(struct device *dev) return 0; if (unlikely(!dev->of_node)) return 0; + if (of_match_node(of_default_bus_match_table, dev->of_node)) + return 0; return __of_link_to_suppliers(dev, dev->of_node); }