aboutsummaryrefslogtreecommitdiffstats
path: root/mm/vmstat.c
diff options
context:
space:
mode:
authorChristoph Lameter <cl@linux.com>2010-12-06 12:16:20 -0500
committerTejun Heo <tj@kernel.org>2010-12-17 09:07:18 -0500
commit12938a9220a38d555e38dc9b40021e664b99a1f1 (patch)
tree978c0199dcd22faf92250fcfd5bfa2aac1100baa /mm/vmstat.c
parent819a72af8d6653daa48334f24ce0a935ccdd33c7 (diff)
vmstat: Optimize zone counter modifications through the use of this cpu operations
this cpu operations can be used to slightly optimize the function. The changes will avoid some address calculations and replace them with the use of the percpu segment register. If one would have this_cpu_inc_return and this_cpu_dec_return then it would be possible to optimize inc_zone_page_state and dec_zone_page_state even more. V1->V2: - Fix __dec_zone_state overflow handling - Use s8 variables for temporary storage. V2->V3: - Put __percpu annotations in correct places. Reviewed-by: Pekka Enberg <penberg@kernel.org> Acked-by: H. Peter Anvin <hpa@zytor.com> Signed-off-by: Christoph Lameter <cl@linux.com> Signed-off-by: Tejun Heo <tj@kernel.org>
Diffstat (limited to 'mm/vmstat.c')
-rw-r--r--mm/vmstat.c48
1 files changed, 28 insertions, 20 deletions
diff --git a/mm/vmstat.c b/mm/vmstat.c
index 8f62f17ee1c7..3ad909d9600f 100644
--- a/mm/vmstat.c
+++ b/mm/vmstat.c
@@ -167,18 +167,20 @@ static void refresh_zone_stat_thresholds(void)
167void __mod_zone_page_state(struct zone *zone, enum zone_stat_item item, 167void __mod_zone_page_state(struct zone *zone, enum zone_stat_item item,
168 int delta) 168 int delta)
169{ 169{
170 struct per_cpu_pageset *pcp = this_cpu_ptr(zone->pageset); 170 struct per_cpu_pageset __percpu *pcp = zone->pageset;
171 171 s8 __percpu *p = pcp->vm_stat_diff + item;
172 s8 *p = pcp->vm_stat_diff + item;
173 long x; 172 long x;
173 long t;
174
175 x = delta + __this_cpu_read(*p);
174 176
175 x = delta + *p; 177 t = __this_cpu_read(pcp->stat_threshold);
176 178
177 if (unlikely(x > pcp->stat_threshold || x < -pcp->stat_threshold)) { 179 if (unlikely(x > t || x < -t)) {
178 zone_page_state_add(x, zone, item); 180 zone_page_state_add(x, zone, item);
179 x = 0; 181 x = 0;
180 } 182 }
181 *p = x; 183 __this_cpu_write(*p, x);
182} 184}
183EXPORT_SYMBOL(__mod_zone_page_state); 185EXPORT_SYMBOL(__mod_zone_page_state);
184 186
@@ -221,16 +223,19 @@ EXPORT_SYMBOL(mod_zone_page_state);
221 */ 223 */
222void __inc_zone_state(struct zone *zone, enum zone_stat_item item) 224void __inc_zone_state(struct zone *zone, enum zone_stat_item item)
223{ 225{
224 struct per_cpu_pageset *pcp = this_cpu_ptr(zone->pageset); 226 struct per_cpu_pageset __percpu *pcp = zone->pageset;
225 s8 *p = pcp->vm_stat_diff + item; 227 s8 __percpu *p = pcp->vm_stat_diff + item;
228 s8 v, t;
226 229
227 (*p)++; 230 __this_cpu_inc(*p);
228 231
229 if (unlikely(*p > pcp->stat_threshold)) { 232 v = __this_cpu_read(*p);
230 int overstep = pcp->stat_threshold / 2; 233 t = __this_cpu_read(pcp->stat_threshold);
234 if (unlikely(v > t)) {
235 s8 overstep = t >> 1;
231 236
232 zone_page_state_add(*p + overstep, zone, item); 237 zone_page_state_add(v + overstep, zone, item);
233 *p = -overstep; 238 __this_cpu_write(*p, -overstep);
234 } 239 }
235} 240}
236 241
@@ -242,16 +247,19 @@ EXPORT_SYMBOL(__inc_zone_page_state);
242 247
243void __dec_zone_state(struct zone *zone, enum zone_stat_item item) 248void __dec_zone_state(struct zone *zone, enum zone_stat_item item)
244{ 249{
245 struct per_cpu_pageset *pcp = this_cpu_ptr(zone->pageset); 250 struct per_cpu_pageset __percpu *pcp = zone->pageset;
246 s8 *p = pcp->vm_stat_diff + item; 251 s8 __percpu *p = pcp->vm_stat_diff + item;
252 s8 v, t;
247 253
248 (*p)--; 254 __this_cpu_dec(*p);
249 255
250 if (unlikely(*p < - pcp->stat_threshold)) { 256 v = __this_cpu_read(*p);
251 int overstep = pcp->stat_threshold / 2; 257 t = __this_cpu_read(pcp->stat_threshold);
258 if (unlikely(v < - t)) {
259 s8 overstep = t >> 1;
252 260
253 zone_page_state_add(*p - overstep, zone, item); 261 zone_page_state_add(v - overstep, zone, item);
254 *p = overstep; 262 __this_cpu_write(*p, overstep);
255 } 263 }
256} 264}
257 265