3cd12006bb
Signed-off-by: Dean Troyer <dtroyer@gmail.com>
93 lines
3.6 KiB
Diff
93 lines
3.6 KiB
Diff
From 44285722649a364928853647fad5ad2d9be3b488 Mon Sep 17 00:00:00 2001
|
|
Message-Id: <44285722649a364928853647fad5ad2d9be3b488.1507237259.git.Jim.Somerville@windriver.com>
|
|
In-Reply-To: <2a9fb6a58e40e8604d97223603111e869bb774b1.1507237258.git.Jim.Somerville@windriver.com>
|
|
References: <2a9fb6a58e40e8604d97223603111e869bb774b1.1507237258.git.Jim.Somerville@windriver.com>
|
|
From: "Rafael J. Wysocki" <rafael.j.wysocki@intel.com>
|
|
Date: Fri, 24 Feb 2017 13:25:14 +0100
|
|
Subject: [PATCH 22/24] cpuidle: menu: Avoid taking spinlock for accessing QoS
|
|
values
|
|
|
|
[commit 6dbf5cea05a7098a69f294c96b6d76f08562cae5 from linux-stable ]
|
|
|
|
After commit 9908859acaa9 (cpuidle/menu: add per CPU PM QoS resume
|
|
latency consideration) the cpuidle menu governor calls
|
|
dev_pm_qos_read_value() on CPU devices to read the current resume latency QoS
|
|
constraint values for them. That function takes a spinlock to prevent the
|
|
device's power.qos pointer from becoming NULL during the access which is a
|
|
problem for the RT patchset where spinlocks are converted into mutexes and
|
|
the idle loop stops working.
|
|
|
|
However, it is not even necessary for the menu governor to take
|
|
that spinlock, because the power.qos pointer accessed under it
|
|
cannot be modified during the access anyway.
|
|
|
|
For this reason, introduce a "raw" routine for accessing device
|
|
QoS resume latency constraints without locking and use it in the
|
|
menu governor.
|
|
|
|
Fixes: 9908859acaa9 (cpuidle/menu: add per CPU PM QoS resume latency consideration)
|
|
Acked-by: Alex Shi <alex.shi@linaro.org>
|
|
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
|
|
Signed-off-by: Alex Kozyrev <alex.kozyrev@windriver.com>
|
|
Signed-off-by: Jim Somerville <Jim.Somerville@windriver.com>
|
|
---
|
|
drivers/base/power/qos.c | 3 +--
|
|
drivers/cpuidle/governors/menu.c | 2 +-
|
|
include/linux/pm_qos.h | 6 ++++++
|
|
3 files changed, 8 insertions(+), 3 deletions(-)
|
|
|
|
diff --git a/drivers/base/power/qos.c b/drivers/base/power/qos.c
|
|
index 2f8ac59..08a4cec 100644
|
|
--- a/drivers/base/power/qos.c
|
|
+++ b/drivers/base/power/qos.c
|
|
@@ -104,8 +104,7 @@ EXPORT_SYMBOL_GPL(dev_pm_qos_flags);
|
|
*/
|
|
s32 __dev_pm_qos_read_value(struct device *dev)
|
|
{
|
|
- return IS_ERR_OR_NULL(dev->power.qos) ?
|
|
- 0 : pm_qos_read_value(&dev->power.qos->latency);
|
|
+ return dev_pm_qos_raw_read_value(dev);
|
|
}
|
|
|
|
/**
|
|
diff --git a/drivers/cpuidle/governors/menu.c b/drivers/cpuidle/governors/menu.c
|
|
index fe2dcb8..f9861fd 100644
|
|
--- a/drivers/cpuidle/governors/menu.c
|
|
+++ b/drivers/cpuidle/governors/menu.c
|
|
@@ -265,7 +265,7 @@ static int menu_select(struct cpuidle_driver *drv, struct cpuidle_device *dev)
|
|
int i;
|
|
int multiplier;
|
|
struct timespec t;
|
|
- int resume_latency = dev_pm_qos_read_value(device);
|
|
+ int resume_latency = dev_pm_qos_raw_read_value(device);
|
|
|
|
if (data->needs_update) {
|
|
menu_update(drv, dev);
|
|
diff --git a/include/linux/pm_qos.h b/include/linux/pm_qos.h
|
|
index 5281e7f..1d8b629 100644
|
|
--- a/include/linux/pm_qos.h
|
|
+++ b/include/linux/pm_qos.h
|
|
@@ -217,6 +217,11 @@ static inline s32 dev_pm_qos_requested_flags(struct device *dev)
|
|
{
|
|
return dev->power.qos->flags_req->data.flr.flags;
|
|
}
|
|
+static inline s32 dev_pm_qos_raw_read_value(struct device *dev)
|
|
+{
|
|
+ return IS_ERR_OR_NULL(dev->power.qos) ?
|
|
+ 0 : pm_qos_read_value(&dev->power.qos->latency);
|
|
+}
|
|
#else
|
|
static inline int dev_pm_qos_expose_latency_limit(struct device *dev, s32 value)
|
|
{ return 0; }
|
|
@@ -236,6 +241,7 @@ static inline void dev_pm_qos_hide_latency_tolerance(struct device *dev) {}
|
|
|
|
static inline s32 dev_pm_qos_requested_latency(struct device *dev) { return 0; }
|
|
static inline s32 dev_pm_qos_requested_flags(struct device *dev) { return 0; }
|
|
+static inline s32 dev_pm_qos_raw_read_value(struct device *dev) { return 0; }
|
|
#endif
|
|
|
|
#endif
|
|
--
|
|
1.8.3.1
|
|
|