aboutsummaryrefslogtreecommitdiffstats
path: root/include
diff options
context:
space:
mode:
authorChristoph Lameter <clameter@sgi.com>2007-02-10 04:43:01 -0500
committerLinus Torvalds <torvalds@woody.linux-foundation.org>2007-02-11 13:51:17 -0500
commitc878538598d1e7ab41ecc0de8894e34e2fdef630 (patch)
treed22e73fddef75521e287c3e7754a1d3224c348d9 /include
parentc3704ceb4ad055b489b143f4e37c57d128908012 (diff)
[PATCH] Use ZVC for inactive and active counts
The determination of the dirty ratio to determine writeback behavior is currently based on the number of total pages on the system. However, not all pages in the system may be dirtied. Thus the ratio is always too low and can never reach 100%. The ratio may be particularly skewed if large hugepage allocations, slab allocations or device driver buffers make large sections of memory not available anymore. In that case we may get into a situation in which f.e. the background writeback ratio of 40% cannot be reached anymore which leads to undesired writeback behavior. This patchset fixes that issue by determining the ratio based on the actual pages that may potentially be dirty. These are the pages on the active and the inactive list plus free pages. The problem with those counts has so far been that it is expensive to calculate these because counts from multiple nodes and multiple zones will have to be summed up. This patchset makes these counters ZVC counters. This means that a current sum per zone, per node and for the whole system is always available via global variables and not expensive anymore to calculate. The patchset results in some other good side effects: - Removal of the various functions that sum up free, active and inactive page counts - Cleanup of the functions that display information via the proc filesystem. This patch: The use of a ZVC for nr_inactive and nr_active allows a simplification of some counter operations. More ZVC functionality is used for sums etc in the following patches. [akpm@osdl.org: UP build fix] Signed-off-by: Christoph Lameter <clameter@sgi.com> Signed-off-by: Andrew Morton <akpm@linux-foundation.org> Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
Diffstat (limited to 'include')
-rw-r--r--include/linux/mm_inline.h13
-rw-r--r--include/linux/mmzone.h4
-rw-r--r--include/linux/vmstat.h9
3 files changed, 17 insertions, 9 deletions
diff --git a/include/linux/mm_inline.h b/include/linux/mm_inline.h
index 3b6723dfaff3..895bc4e93039 100644
--- a/include/linux/mm_inline.h
+++ b/include/linux/mm_inline.h
@@ -1,30 +1,29 @@
1
2static inline void 1static inline void
3add_page_to_active_list(struct zone *zone, struct page *page) 2add_page_to_active_list(struct zone *zone, struct page *page)
4{ 3{
5 list_add(&page->lru, &zone->active_list); 4 list_add(&page->lru, &zone->active_list);
6 zone->nr_active++; 5 __inc_zone_state(zone, NR_ACTIVE);
7} 6}
8 7
9static inline void 8static inline void
10add_page_to_inactive_list(struct zone *zone, struct page *page) 9add_page_to_inactive_list(struct zone *zone, struct page *page)
11{ 10{
12 list_add(&page->lru, &zone->inactive_list); 11 list_add(&page->lru, &zone->inactive_list);
13 zone->nr_inactive++; 12 __inc_zone_state(zone, NR_INACTIVE);
14} 13}
15 14
16static inline void 15static inline void
17del_page_from_active_list(struct zone *zone, struct page *page) 16del_page_from_active_list(struct zone *zone, struct page *page)
18{ 17{
19 list_del(&page->lru); 18 list_del(&page->lru);
20 zone->nr_active--; 19 __dec_zone_state(zone, NR_ACTIVE);
21} 20}
22 21
23static inline void 22static inline void
24del_page_from_inactive_list(struct zone *zone, struct page *page) 23del_page_from_inactive_list(struct zone *zone, struct page *page)
25{ 24{
26 list_del(&page->lru); 25 list_del(&page->lru);
27 zone->nr_inactive--; 26 __dec_zone_state(zone, NR_INACTIVE);
28} 27}
29 28
30static inline void 29static inline void
@@ -33,9 +32,9 @@ del_page_from_lru(struct zone *zone, struct page *page)
33 list_del(&page->lru); 32 list_del(&page->lru);
34 if (PageActive(page)) { 33 if (PageActive(page)) {
35 __ClearPageActive(page); 34 __ClearPageActive(page);
36 zone->nr_active--; 35 __dec_zone_state(zone, NR_ACTIVE);
37 } else { 36 } else {
38 zone->nr_inactive--; 37 __dec_zone_state(zone, NR_INACTIVE);
39 } 38 }
40} 39}
41 40
diff --git a/include/linux/mmzone.h b/include/linux/mmzone.h
index b262f47961fb..9137d1b9735c 100644
--- a/include/linux/mmzone.h
+++ b/include/linux/mmzone.h
@@ -47,6 +47,8 @@ struct zone_padding {
47#endif 47#endif
48 48
49enum zone_stat_item { 49enum zone_stat_item {
50 NR_INACTIVE,
51 NR_ACTIVE,
50 NR_ANON_PAGES, /* Mapped anonymous pages */ 52 NR_ANON_PAGES, /* Mapped anonymous pages */
51 NR_FILE_MAPPED, /* pagecache pages mapped into pagetables. 53 NR_FILE_MAPPED, /* pagecache pages mapped into pagetables.
52 only modified from process context */ 54 only modified from process context */
@@ -197,8 +199,6 @@ struct zone {
197 struct list_head inactive_list; 199 struct list_head inactive_list;
198 unsigned long nr_scan_active; 200 unsigned long nr_scan_active;
199 unsigned long nr_scan_inactive; 201 unsigned long nr_scan_inactive;
200 unsigned long nr_active;
201 unsigned long nr_inactive;
202 unsigned long pages_scanned; /* since last reclaim */ 202 unsigned long pages_scanned; /* since last reclaim */
203 int all_unreclaimable; /* All pages pinned */ 203 int all_unreclaimable; /* All pages pinned */
204 204
diff --git a/include/linux/vmstat.h b/include/linux/vmstat.h
index 5e9803ed17fc..c8d55bcc09b9 100644
--- a/include/linux/vmstat.h
+++ b/include/linux/vmstat.h
@@ -186,6 +186,9 @@ void inc_zone_page_state(struct page *, enum zone_stat_item);
186void dec_zone_page_state(struct page *, enum zone_stat_item); 186void dec_zone_page_state(struct page *, enum zone_stat_item);
187 187
188extern void inc_zone_state(struct zone *, enum zone_stat_item); 188extern void inc_zone_state(struct zone *, enum zone_stat_item);
189extern void __inc_zone_state(struct zone *, enum zone_stat_item);
190extern void dec_zone_state(struct zone *, enum zone_stat_item);
191extern void __dec_zone_state(struct zone *, enum zone_stat_item);
189 192
190void refresh_cpu_vm_stats(int); 193void refresh_cpu_vm_stats(int);
191void refresh_vm_stats(void); 194void refresh_vm_stats(void);
@@ -214,6 +217,12 @@ static inline void __inc_zone_page_state(struct page *page,
214 __inc_zone_state(page_zone(page), item); 217 __inc_zone_state(page_zone(page), item);
215} 218}
216 219
220static inline void __dec_zone_state(struct zone *zone, enum zone_stat_item item)
221{
222 atomic_long_dec(&zone->vm_stat[item]);
223 atomic_long_dec(&vm_stat[item]);
224}
225
217static inline void __dec_zone_page_state(struct page *page, 226static inline void __dec_zone_page_state(struct page *page,
218 enum zone_stat_item item) 227 enum zone_stat_item item)
219{ 228{