aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorFrederic Weisbecker <fweisbec@gmail.com>2014-11-28 13:23:34 -0500
committerMartin Schwidefsky <schwidefsky@de.ibm.com>2014-12-08 03:42:32 -0500
commit1ce2180498fd40ed3f6485fc5daadf4b711f305f (patch)
tree5766a052dba787bb3de5e0af8e9fba0c8f1e52e1
parent200e7c0ffb1b174a4aeaa05f7f43a91ac0fddde3 (diff)
s390/idle: convert open coded idle time seqcount
s390 uses open coded seqcount to synchronize idle time accounting. Lets consolidate it with the standard API. Cc: Benjamin Herrenschmidt <benh@kernel.crashing.org> Cc: Heiko Carstens <heiko.carstens@de.ibm.com> Cc: Ingo Molnar <mingo@kernel.org> Cc: Martin Schwidefsky <schwidefsky@de.ibm.com> Cc: Oleg Nesterov <oleg@redhat.com> Cc: Paul Mackerras <paulus@samba.org> Cc: Peter Zijlstra <peterz@infradead.org> Cc: Rik van Riel <riel@redhat.com> Cc: Thomas Gleixner <tglx@linutronix.de> Cc: Tony Luck <tony.luck@intel.com> Cc: Wu Fengguang <fengguang.wu@intel.com> Signed-off-by: Frederic Weisbecker <fweisbec@gmail.com> Signed-off-by: Heiko Carstens <heiko.carstens@de.ibm.com> Signed-off-by: Martin Schwidefsky <schwidefsky@de.ibm.com>
-rw-r--r--arch/s390/include/asm/idle.h3
-rw-r--r--arch/s390/kernel/idle.c24
2 files changed, 13 insertions, 14 deletions
diff --git a/arch/s390/include/asm/idle.h b/arch/s390/include/asm/idle.h
index 6af037f574b8..113cd963dbbe 100644
--- a/arch/s390/include/asm/idle.h
+++ b/arch/s390/include/asm/idle.h
@@ -9,9 +9,10 @@
9 9
10#include <linux/types.h> 10#include <linux/types.h>
11#include <linux/device.h> 11#include <linux/device.h>
12#include <linux/seqlock.h>
12 13
13struct s390_idle_data { 14struct s390_idle_data {
14 unsigned int sequence; 15 seqcount_t seqcount;
15 unsigned long long idle_count; 16 unsigned long long idle_count;
16 unsigned long long idle_time; 17 unsigned long long idle_time;
17 unsigned long long clock_idle_enter; 18 unsigned long long clock_idle_enter;
diff --git a/arch/s390/kernel/idle.c b/arch/s390/kernel/idle.c
index 8814dd9cf644..7a55c29b0b33 100644
--- a/arch/s390/kernel/idle.c
+++ b/arch/s390/kernel/idle.c
@@ -38,15 +38,13 @@ void enabled_wait(void)
38 trace_hardirqs_off(); 38 trace_hardirqs_off();
39 39
40 /* Account time spent with enabled wait psw loaded as idle time. */ 40 /* Account time spent with enabled wait psw loaded as idle time. */
41 idle->sequence++; 41 write_seqcount_begin(&idle->seqcount);
42 smp_wmb();
43 idle_time = idle->clock_idle_exit - idle->clock_idle_enter; 42 idle_time = idle->clock_idle_exit - idle->clock_idle_enter;
44 idle->clock_idle_enter = idle->clock_idle_exit = 0ULL; 43 idle->clock_idle_enter = idle->clock_idle_exit = 0ULL;
45 idle->idle_time += idle_time; 44 idle->idle_time += idle_time;
46 idle->idle_count++; 45 idle->idle_count++;
47 account_idle_time(idle_time); 46 account_idle_time(idle_time);
48 smp_wmb(); 47 write_seqcount_end(&idle->seqcount);
49 idle->sequence++;
50} 48}
51NOKPROBE_SYMBOL(enabled_wait); 49NOKPROBE_SYMBOL(enabled_wait);
52 50
@@ -55,14 +53,14 @@ static ssize_t show_idle_count(struct device *dev,
55{ 53{
56 struct s390_idle_data *idle = &per_cpu(s390_idle, dev->id); 54 struct s390_idle_data *idle = &per_cpu(s390_idle, dev->id);
57 unsigned long long idle_count; 55 unsigned long long idle_count;
58 unsigned int sequence; 56 unsigned int seq;
59 57
60 do { 58 do {
61 sequence = ACCESS_ONCE(idle->sequence); 59 seq = read_seqcount_begin(&idle->seqcount);
62 idle_count = ACCESS_ONCE(idle->idle_count); 60 idle_count = ACCESS_ONCE(idle->idle_count);
63 if (ACCESS_ONCE(idle->clock_idle_enter)) 61 if (ACCESS_ONCE(idle->clock_idle_enter))
64 idle_count++; 62 idle_count++;
65 } while ((sequence & 1) || (ACCESS_ONCE(idle->sequence) != sequence)); 63 } while (read_seqcount_retry(&idle->seqcount, seq));
66 return sprintf(buf, "%llu\n", idle_count); 64 return sprintf(buf, "%llu\n", idle_count);
67} 65}
68DEVICE_ATTR(idle_count, 0444, show_idle_count, NULL); 66DEVICE_ATTR(idle_count, 0444, show_idle_count, NULL);
@@ -72,15 +70,15 @@ static ssize_t show_idle_time(struct device *dev,
72{ 70{
73 struct s390_idle_data *idle = &per_cpu(s390_idle, dev->id); 71 struct s390_idle_data *idle = &per_cpu(s390_idle, dev->id);
74 unsigned long long now, idle_time, idle_enter, idle_exit; 72 unsigned long long now, idle_time, idle_enter, idle_exit;
75 unsigned int sequence; 73 unsigned int seq;
76 74
77 do { 75 do {
78 now = get_tod_clock(); 76 now = get_tod_clock();
79 sequence = ACCESS_ONCE(idle->sequence); 77 seq = read_seqcount_begin(&idle->seqcount);
80 idle_time = ACCESS_ONCE(idle->idle_time); 78 idle_time = ACCESS_ONCE(idle->idle_time);
81 idle_enter = ACCESS_ONCE(idle->clock_idle_enter); 79 idle_enter = ACCESS_ONCE(idle->clock_idle_enter);
82 idle_exit = ACCESS_ONCE(idle->clock_idle_exit); 80 idle_exit = ACCESS_ONCE(idle->clock_idle_exit);
83 } while ((sequence & 1) || (ACCESS_ONCE(idle->sequence) != sequence)); 81 } while (read_seqcount_retry(&idle->seqcount, seq));
84 idle_time += idle_enter ? ((idle_exit ? : now) - idle_enter) : 0; 82 idle_time += idle_enter ? ((idle_exit ? : now) - idle_enter) : 0;
85 return sprintf(buf, "%llu\n", idle_time >> 12); 83 return sprintf(buf, "%llu\n", idle_time >> 12);
86} 84}
@@ -90,14 +88,14 @@ cputime64_t arch_cpu_idle_time(int cpu)
90{ 88{
91 struct s390_idle_data *idle = &per_cpu(s390_idle, cpu); 89 struct s390_idle_data *idle = &per_cpu(s390_idle, cpu);
92 unsigned long long now, idle_enter, idle_exit; 90 unsigned long long now, idle_enter, idle_exit;
93 unsigned int sequence; 91 unsigned int seq;
94 92
95 do { 93 do {
96 now = get_tod_clock(); 94 now = get_tod_clock();
97 sequence = ACCESS_ONCE(idle->sequence); 95 seq = read_seqcount_begin(&idle->seqcount);
98 idle_enter = ACCESS_ONCE(idle->clock_idle_enter); 96 idle_enter = ACCESS_ONCE(idle->clock_idle_enter);
99 idle_exit = ACCESS_ONCE(idle->clock_idle_exit); 97 idle_exit = ACCESS_ONCE(idle->clock_idle_exit);
100 } while ((sequence & 1) || (ACCESS_ONCE(idle->sequence) != sequence)); 98 } while (read_seqcount_retry(&idle->seqcount, seq));
101 return idle_enter ? ((idle_exit ?: now) - idle_enter) : 0; 99 return idle_enter ? ((idle_exit ?: now) - idle_enter) : 0;
102} 100}
103 101