From patchwork Fri Feb 17 09:55:23 2017 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Ulf Hansson X-Patchwork-Id: 9579367 X-Patchwork-Delegate: rjw@sisk.pl Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork.web.codeaurora.org (Postfix) with ESMTP id A453F600F6 for ; Fri, 17 Feb 2017 09:55:38 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 9B66028551 for ; Fri, 17 Feb 2017 09:55:38 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 90180286A2; Fri, 17 Feb 2017 09:55:38 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-6.5 required=2.0 tests=BAYES_00,DKIM_SIGNED, DKIM_VALID, DKIM_VALID_AU, RCVD_IN_DNSWL_HI, RCVD_IN_SORBS_SPAM autolearn=ham version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 09B3E28551 for ; Fri, 17 Feb 2017 09:55:38 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S933846AbdBQJzg (ORCPT ); Fri, 17 Feb 2017 04:55:36 -0500 Received: from mail-lf0-f41.google.com ([209.85.215.41]:35295 "EHLO mail-lf0-f41.google.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S933961AbdBQJzd (ORCPT ); Fri, 17 Feb 2017 04:55:33 -0500 Received: by mail-lf0-f41.google.com with SMTP id z127so20155491lfa.2 for ; Fri, 17 Feb 2017 01:55:32 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=linaro.org; s=google; h=from:to:cc:subject:date:message-id:in-reply-to:references; bh=6RUmNvLGKADJ18DWAOm4UuDsfpio7yRChXph+k/cSCs=; b=gGSK6JQ/345OI7oogG/l8eWbGGmzZDICThRVP5dqCTFWLzGLim/S0qxbMAWkyknkMc pYXee+FyUo52XnkfCPxm3AiJKjQvoYUANX8nuV3J7kyY2r4c89h3UDt8OAy4qpJPNTac q9aZrQxj/0EUBLliekPBsVQNTKXzn0IpOhFDA= X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:cc:subject:date:message-id:in-reply-to :references; bh=6RUmNvLGKADJ18DWAOm4UuDsfpio7yRChXph+k/cSCs=; b=q7Dke7jzkgVV0ULarv7U1vGIO99bmi8C2vB6FwRUqLrpTqJeug+Rkf6/TPdMDpJFrH m60s0ZR4gKAyZpMV9oIfmGO/tjGv/AAvLfTU7D3jIJDy4G6SxkgxB+ApvyhLgWZK5D16 s/ZZGiG6WIlANWQ8GdMfCC3d7YPGfikJvgVp4tezj/NkYkB3+JvE1Gz+dI/SeH9CsSBO mrdf6YMU2Xr1Ica5r+gKgNtZMVlbb2QMmsOxW6xUU9MLj7OtqDSGMZ0/YxWM/sWv6hsm x+VH9fLdPvvnY8FL8Q2BCjbLTcAeSFZCHum/OhfYnNn6AgcDMMgaz/BZanBSMkTr36FW slHg== X-Gm-Message-State: AMke39lLH7SNrPxOkqgh0Z6ydGkfJtUbFMk9ofGV7gTWGVxW3P0OXeiAQPTNvazBhsdJuGCx X-Received: by 10.25.29.195 with SMTP id d186mr2054046lfd.72.1487325331243; Fri, 17 Feb 2017 01:55:31 -0800 (PST) Received: from localhost.localdomain (h-155-4-221-67.na.cust.bahnhof.se. [155.4.221.67]) by smtp.gmail.com with ESMTPSA id f133sm2372773lfg.32.2017.02.17.01.55.30 (version=TLS1_2 cipher=ECDHE-RSA-AES128-SHA bits=128/128); Fri, 17 Feb 2017 01:55:30 -0800 (PST) From: Ulf Hansson To: "Rafael J. Wysocki" , Ulf Hansson , linux-pm@vger.kernel.org Cc: Len Brown , Pavel Machek , Kevin Hilman , Geert Uytterhoeven , Lina Iyer , Jon Hunter , Marek Szyprowski Subject: [PATCH 1/3] PM / Domains: Move genpd_power_off() above genpd_power_on() Date: Fri, 17 Feb 2017 10:55:23 +0100 Message-Id: <1487325325-18212-2-git-send-email-ulf.hansson@linaro.org> X-Mailer: git-send-email 1.9.1 In-Reply-To: <1487325325-18212-1-git-send-email-ulf.hansson@linaro.org> References: <1487325325-18212-1-git-send-email-ulf.hansson@linaro.org> Sender: linux-pm-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-pm@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP Following changes in genpd_power_on() makes it invoke genpd_power_off(). To enable these changes and avoiding to declare genpd_power_off(), let's move its implementation above genpd_power_on(). In this way, following changes should become easier to review. Signed-off-by: Ulf Hansson --- drivers/base/power/domain.c | 162 ++++++++++++++++++++++---------------------- 1 file changed, 81 insertions(+), 81 deletions(-) diff --git a/drivers/base/power/domain.c b/drivers/base/power/domain.c index 3a75fb1..3dc44f2 100644 --- a/drivers/base/power/domain.c +++ b/drivers/base/power/domain.c @@ -274,6 +274,87 @@ static void genpd_queue_power_off_work(struct generic_pm_domain *genpd) } /** + * genpd_power_off - Remove power from a given PM domain. + * @genpd: PM domain to power down. + * @is_async: PM domain is powered down from a scheduled work + * + * If all of the @genpd's devices have been suspended and all of its subdomains + * have been powered down, remove power from @genpd. + */ +static int genpd_power_off(struct generic_pm_domain *genpd, bool is_async) +{ + struct pm_domain_data *pdd; + struct gpd_link *link; + unsigned int not_suspended = 0; + + /* + * Do not try to power off the domain in the following situations: + * (1) The domain is already in the "power off" state. + * (2) System suspend is in progress. + */ + if (genpd->status == GPD_STATE_POWER_OFF + || genpd->prepared_count > 0) + return 0; + + if (atomic_read(&genpd->sd_count) > 0) + return -EBUSY; + + list_for_each_entry(pdd, &genpd->dev_list, list_node) { + enum pm_qos_flags_status stat; + + stat = dev_pm_qos_flags(pdd->dev, + PM_QOS_FLAG_NO_POWER_OFF + | PM_QOS_FLAG_REMOTE_WAKEUP); + if (stat > PM_QOS_FLAGS_NONE) + return -EBUSY; + + /* + * Do not allow PM domain to be powered off, when an IRQ safe + * device is part of a non-IRQ safe domain. + */ + if (!pm_runtime_suspended(pdd->dev) || + irq_safe_dev_in_no_sleep_domain(pdd->dev, genpd)) + not_suspended++; + } + + if (not_suspended > 1 || (not_suspended == 1 && is_async)) + return -EBUSY; + + if (genpd->gov && genpd->gov->power_down_ok) { + if (!genpd->gov->power_down_ok(&genpd->domain)) + return -EAGAIN; + } + + if (genpd->power_off) { + int ret; + + if (atomic_read(&genpd->sd_count) > 0) + return -EBUSY; + + /* + * If sd_count > 0 at this point, one of the subdomains hasn't + * managed to call genpd_power_on() for the master yet after + * incrementing it. In that case genpd_power_on() will wait + * for us to drop the lock, so we can call .power_off() and let + * the genpd_power_on() restore power for us (this shouldn't + * happen very often). + */ + ret = _genpd_power_off(genpd, true); + if (ret) + return ret; + } + + genpd->status = GPD_STATE_POWER_OFF; + + list_for_each_entry(link, &genpd->slave_links, slave_node) { + genpd_sd_counter_dec(link->master); + genpd_queue_power_off_work(link->master); + } + + return 0; +} + +/** * genpd_power_on - Restore power to a given PM domain and its masters. * @genpd: PM domain to power up. * @depth: nesting count for lockdep. @@ -368,87 +449,6 @@ static int genpd_dev_pm_qos_notifier(struct notifier_block *nb, } /** - * genpd_power_off - Remove power from a given PM domain. - * @genpd: PM domain to power down. - * @is_async: PM domain is powered down from a scheduled work - * - * If all of the @genpd's devices have been suspended and all of its subdomains - * have been powered down, remove power from @genpd. - */ -static int genpd_power_off(struct generic_pm_domain *genpd, bool is_async) -{ - struct pm_domain_data *pdd; - struct gpd_link *link; - unsigned int not_suspended = 0; - - /* - * Do not try to power off the domain in the following situations: - * (1) The domain is already in the "power off" state. - * (2) System suspend is in progress. - */ - if (genpd->status == GPD_STATE_POWER_OFF - || genpd->prepared_count > 0) - return 0; - - if (atomic_read(&genpd->sd_count) > 0) - return -EBUSY; - - list_for_each_entry(pdd, &genpd->dev_list, list_node) { - enum pm_qos_flags_status stat; - - stat = dev_pm_qos_flags(pdd->dev, - PM_QOS_FLAG_NO_POWER_OFF - | PM_QOS_FLAG_REMOTE_WAKEUP); - if (stat > PM_QOS_FLAGS_NONE) - return -EBUSY; - - /* - * Do not allow PM domain to be powered off, when an IRQ safe - * device is part of a non-IRQ safe domain. - */ - if (!pm_runtime_suspended(pdd->dev) || - irq_safe_dev_in_no_sleep_domain(pdd->dev, genpd)) - not_suspended++; - } - - if (not_suspended > 1 || (not_suspended == 1 && is_async)) - return -EBUSY; - - if (genpd->gov && genpd->gov->power_down_ok) { - if (!genpd->gov->power_down_ok(&genpd->domain)) - return -EAGAIN; - } - - if (genpd->power_off) { - int ret; - - if (atomic_read(&genpd->sd_count) > 0) - return -EBUSY; - - /* - * If sd_count > 0 at this point, one of the subdomains hasn't - * managed to call genpd_power_on() for the master yet after - * incrementing it. In that case genpd_power_on() will wait - * for us to drop the lock, so we can call .power_off() and let - * the genpd_power_on() restore power for us (this shouldn't - * happen very often). - */ - ret = _genpd_power_off(genpd, true); - if (ret) - return ret; - } - - genpd->status = GPD_STATE_POWER_OFF; - - list_for_each_entry(link, &genpd->slave_links, slave_node) { - genpd_sd_counter_dec(link->master); - genpd_queue_power_off_work(link->master); - } - - return 0; -} - -/** * genpd_power_off_work_fn - Power off PM domain whose subdomain count is 0. * @work: Work structure used for scheduling the execution of this function. */