From patchwork Sun Nov 28 05:53:15 2010 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: "Gao, Yunpeng" X-Patchwork-Id: 361802 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by demeter1.kernel.org (8.14.4/8.14.3) with ESMTP id oAS6KFPl013466 for ; Sun, 28 Nov 2010 06:20:15 GMT Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1751413Ab0K1GUM (ORCPT ); Sun, 28 Nov 2010 01:20:12 -0500 Received: from mga02.intel.com ([134.134.136.20]:64660 "EHLO mga02.intel.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1751366Ab0K1GUM (ORCPT ); Sun, 28 Nov 2010 01:20:12 -0500 Received: from orsmga001.jf.intel.com ([10.7.209.18]) by orsmga101.jf.intel.com with ESMTP; 27 Nov 2010 22:20:11 -0800 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="4.59,269,1288594800"; d="scan'208,223";a="681636686" Received: from unknown (HELO intel.com) ([172.16.118.85]) by orsmga001.jf.intel.com with ESMTP; 27 Nov 2010 22:19:47 -0800 Date: Sun, 28 Nov 2010 13:53:15 +0800 From: Yunpeng Gao To: linux-mmc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Subject: [PATCH v1 3/3]mmc: changes to enable runtime PM of mmc core layer Message-ID: <20101128055315.GD3318@intel.com> MIME-Version: 1.0 Content-Disposition: inline User-Agent: Mutt/1.5.17 (2007-11-01) Sender: linux-mmc-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-mmc@vger.kernel.org X-Greylist: IP, sender and recipient auto-whitelisted, not delayed by milter-greylist-4.2.3 (demeter1.kernel.org [140.211.167.41]); Sun, 28 Nov 2010 06:20:16 +0000 (UTC) diff --git a/drivers/mmc/core/bus.c b/drivers/mmc/core/bus.c index af8dc6a..96b6cff 100644 --- a/drivers/mmc/core/bus.c +++ b/drivers/mmc/core/bus.c @@ -160,7 +160,7 @@ static int mmc_runtime_resume(struct device *dev) static int mmc_runtime_idle(struct device *dev) { - return pm_runtime_suspend(dev); + return pm_schedule_suspend(dev, 100); } static const struct dev_pm_ops mmc_bus_pm_ops = { diff --git a/drivers/mmc/core/core.c b/drivers/mmc/core/core.c index 6286898..2905dac 100644 --- a/drivers/mmc/core/core.c +++ b/drivers/mmc/core/core.c @@ -22,6 +22,7 @@ #include #include #include +#include #include #include @@ -1503,6 +1504,7 @@ void mmc_rescan(struct work_struct *work) spin_unlock_irqrestore(&host->lock, flags); + pm_runtime_get_sync(host->parent); mmc_bus_get(host); @@ -1598,6 +1600,8 @@ out_fail: mmc_power_off(host); } out: + pm_runtime_put_sync(host->parent); + if (host->caps & MMC_CAP_NEEDS_POLL) mmc_schedule_delayed_work(&host->detect, HZ); } diff --git a/drivers/mmc/core/host.c b/drivers/mmc/core/host.c index 92e3370..8268b8e 100644 --- a/drivers/mmc/core/host.c +++ b/drivers/mmc/core/host.c @@ -19,6 +19,7 @@ #include #include #include +#include #include #include @@ -28,6 +29,33 @@ #define cls_dev_to_mmc_host(d) container_of(d, struct mmc_host, class_dev) +#ifdef CONFIG_PM_RUNTIME +static int mmc_host_runtime_suspend(struct device *dev) +{ + return 0; +} + +static int mmc_host_runtime_resume(struct device *dev) +{ + return 0; +} + +static int mmc_host_runtime_idle(struct device *dev) +{ + return pm_runtime_suspend(dev); +} +#else +#define mmc_host_runtime_suspend NULL +#define mmc_host_runtime_resume NULL +#define mmc_host_runtime_idle NULL +#endif + +const static struct dev_pm_ops host_pm = { + .runtime_suspend = mmc_host_runtime_suspend, + .runtime_resume = mmc_host_runtime_resume, + .runtime_idle = mmc_host_runtime_idle, +}; + static void mmc_host_classdev_release(struct device *dev) { struct mmc_host *host = cls_dev_to_mmc_host(dev); @@ -37,6 +65,7 @@ static void mmc_host_classdev_release(struct device *dev) static struct class mmc_host_class = { .name = "mmc_host", .dev_release = mmc_host_classdev_release, + .pm = &host_pm, }; int mmc_register_host_class(void) @@ -333,6 +362,12 @@ int mmc_add_host(struct mmc_host *host) if (err) return err; + /* Enable runtime PM */ + pm_runtime_get_noresume(&host->class_dev); + pm_runtime_set_active(&host->class_dev); + pm_runtime_enable(&host->class_dev); + pm_runtime_put_sync(&host->class_dev); + #ifdef CONFIG_DEBUG_FS mmc_add_host_debugfs(host); #endif