From patchwork Sat Dec 15 00:25:58 2012 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Rafael Wysocki X-Patchwork-Id: 1882021 Return-Path: X-Original-To: patchwork-linux-pm@patchwork.kernel.org Delivered-To: patchwork-process-083081@patchwork1.kernel.org Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by patchwork1.kernel.org (Postfix) with ESMTP id 0541340079 for ; Sat, 15 Dec 2012 00:20:54 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1756848Ab2LOAUx (ORCPT ); Fri, 14 Dec 2012 19:20:53 -0500 Received: from hydra.sisk.pl ([212.160.235.94]:34264 "EHLO hydra.sisk.pl" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1756797Ab2LOAUw (ORCPT ); Fri, 14 Dec 2012 19:20:52 -0500 Received: from vostro.rjw.lan (afbf32.neoplus.adsl.tpnet.pl [95.49.31.32]) by hydra.sisk.pl (Postfix) with ESMTPSA id 3E7CEE3FE8; Sat, 15 Dec 2012 01:22:16 +0100 (CET) From: "Rafael J. Wysocki" To: Linux PM list Cc: LKML , Jan-Matthias Braun , Jiri Kosina , Alan Stern Subject: [Resend][PATCH] PM: Move disabling/enabling runtime PM to late suspend/early resume Date: Sat, 15 Dec 2012 01:25:58 +0100 Message-ID: <3307221.dy6xvn45xe@vostro.rjw.lan> User-Agent: KMail/4.9.3 (Linux/3.7.0; KDE/4.9.3; x86_64; ; ) In-Reply-To: <1988667.JSHu2WyJuF@vostro.rjw.lan> References: <1988667.JSHu2WyJuF@vostro.rjw.lan> MIME-Version: 1.0 Sender: linux-pm-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-pm@vger.kernel.org From: Rafael J. Wysocki Currently, the PM core disables runtime PM for all devices right after executing subsystem/driver .suspend() callbacks for them and re-enables it right before executing subsystem/driver .resume() callbacks for them. This may lead to problems when there are two devices such that the .suspend() callback executed for one of them depends on runtime PM working for the other. In that case, if runtime PM has already been disabled for the second device, the first one's .suspend() won't work correctly (and analogously for resume). To make those issues go away, make the PM core disable runtime PM for devices right before executing subsystem/driver .suspend_late() callbacks for them and enable runtime PM for them right after executing subsystem/driver .resume_early() callbacks for them. This way the potential conflitcs between .suspend_late()/.resume_early() and their runtime PM counterparts are still prevented from happening, but the subtle ordering issues related to disabling/enabling runtime PM for devices during system suspend/resume are much easier to avoid. Reported-and-tested-by: Jan-Matthias Braun Signed-off-by: Rafael J. Wysocki Reviewed-by: Ulf Hansson Reviewed-by: Kevin Hilman --- Documentation/power/runtime_pm.txt | 9 +++++---- drivers/base/power/main.c | 9 ++++----- 2 files changed, 9 insertions(+), 9 deletions(-) -- To unsubscribe from this list: send the line "unsubscribe linux-pm" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html Index: linux/drivers/base/power/main.c =================================================================== --- linux.orig/drivers/base/power/main.c +++ linux/drivers/base/power/main.c @@ -513,6 +513,8 @@ static int device_resume_early(struct de Out: TRACE_RESUME(error); + + pm_runtime_enable(dev); return error; } @@ -589,8 +591,6 @@ static int device_resume(struct device * if (!dev->power.is_suspended) goto Unlock; - pm_runtime_enable(dev); - if (dev->pm_domain) { info = "power domain "; callback = pm_op(&dev->pm_domain->ops, state); @@ -930,6 +930,8 @@ static int device_suspend_late(struct de pm_callback_t callback = NULL; char *info = NULL; + __pm_runtime_disable(dev, false); + if (dev->power.syscore) return 0; @@ -1133,11 +1135,8 @@ static int __device_suspend(struct devic Complete: complete_all(&dev->power.completion); - if (error) async_error = error; - else if (dev->power.is_suspended) - __pm_runtime_disable(dev, false); return error; } Index: linux/Documentation/power/runtime_pm.txt =================================================================== --- linux.orig/Documentation/power/runtime_pm.txt +++ linux/Documentation/power/runtime_pm.txt @@ -642,12 +642,13 @@ out the following operations: * During system suspend it calls pm_runtime_get_noresume() and pm_runtime_barrier() for every device right before executing the subsystem-level .suspend() callback for it. In addition to that it calls - pm_runtime_disable() for every device right after executing the - subsystem-level .suspend() callback for it. + __pm_runtime_disable() with 'false' as the second argument for every device + right before executing the subsystem-level .suspend_late() callback for it. * During system resume it calls pm_runtime_enable() and pm_runtime_put_sync() - for every device right before and right after executing the subsystem-level - .resume() callback for it, respectively. + for every device right after executing the subsystem-level .resume_early() + callback and right after executing the subsystem-level .resume() callback + for it, respectively. 7. Generic subsystem callbacks