diff options
Diffstat (limited to 'include/linux/rmap.h')
-rw-r--r-- | include/linux/rmap.h | 45 |
1 files changed, 10 insertions, 35 deletions
diff --git a/include/linux/rmap.h b/include/linux/rmap.h index e9fd04ca1e51..830e65dc01ee 100644 --- a/include/linux/rmap.h +++ b/include/linux/rmap.h | |||
@@ -27,18 +27,15 @@ | |||
27 | struct anon_vma { | 27 | struct anon_vma { |
28 | struct anon_vma *root; /* Root of this anon_vma tree */ | 28 | struct anon_vma *root; /* Root of this anon_vma tree */ |
29 | spinlock_t lock; /* Serialize access to vma list */ | 29 | spinlock_t lock; /* Serialize access to vma list */ |
30 | #if defined(CONFIG_KSM) || defined(CONFIG_MIGRATION) | ||
31 | |||
32 | /* | 30 | /* |
33 | * The external_refcount is taken by either KSM or page migration | 31 | * The refcount is taken on an anon_vma when there is no |
34 | * to take a reference to an anon_vma when there is no | ||
35 | * guarantee that the vma of page tables will exist for | 32 | * guarantee that the vma of page tables will exist for |
36 | * the duration of the operation. A caller that takes | 33 | * the duration of the operation. A caller that takes |
37 | * the reference is responsible for clearing up the | 34 | * the reference is responsible for clearing up the |
38 | * anon_vma if they are the last user on release | 35 | * anon_vma if they are the last user on release |
39 | */ | 36 | */ |
40 | atomic_t external_refcount; | 37 | atomic_t refcount; |
41 | #endif | 38 | |
42 | /* | 39 | /* |
43 | * NOTE: the LSB of the head.next is set by | 40 | * NOTE: the LSB of the head.next is set by |
44 | * mm_take_all_locks() _after_ taking the above lock. So the | 41 | * mm_take_all_locks() _after_ taking the above lock. So the |
@@ -71,42 +68,19 @@ struct anon_vma_chain { | |||
71 | }; | 68 | }; |
72 | 69 | ||
73 | #ifdef CONFIG_MMU | 70 | #ifdef CONFIG_MMU |
74 | #if defined(CONFIG_KSM) || defined(CONFIG_MIGRATION) | ||
75 | static inline void anonvma_external_refcount_init(struct anon_vma *anon_vma) | ||
76 | { | ||
77 | atomic_set(&anon_vma->external_refcount, 0); | ||
78 | } | ||
79 | |||
80 | static inline int anonvma_external_refcount(struct anon_vma *anon_vma) | ||
81 | { | ||
82 | return atomic_read(&anon_vma->external_refcount); | ||
83 | } | ||
84 | |||
85 | static inline void get_anon_vma(struct anon_vma *anon_vma) | 71 | static inline void get_anon_vma(struct anon_vma *anon_vma) |
86 | { | 72 | { |
87 | atomic_inc(&anon_vma->external_refcount); | 73 | atomic_inc(&anon_vma->refcount); |
88 | } | 74 | } |
89 | 75 | ||
90 | void drop_anon_vma(struct anon_vma *); | 76 | void __put_anon_vma(struct anon_vma *anon_vma); |
91 | #else | ||
92 | static inline void anonvma_external_refcount_init(struct anon_vma *anon_vma) | ||
93 | { | ||
94 | } | ||
95 | 77 | ||
96 | static inline int anonvma_external_refcount(struct anon_vma *anon_vma) | 78 | static inline void put_anon_vma(struct anon_vma *anon_vma) |
97 | { | ||
98 | return 0; | ||
99 | } | ||
100 | |||
101 | static inline void get_anon_vma(struct anon_vma *anon_vma) | ||
102 | { | 79 | { |
80 | if (atomic_dec_and_test(&anon_vma->refcount)) | ||
81 | __put_anon_vma(anon_vma); | ||
103 | } | 82 | } |
104 | 83 | ||
105 | static inline void drop_anon_vma(struct anon_vma *anon_vma) | ||
106 | { | ||
107 | } | ||
108 | #endif /* CONFIG_KSM */ | ||
109 | |||
110 | static inline struct anon_vma *page_anon_vma(struct page *page) | 84 | static inline struct anon_vma *page_anon_vma(struct page *page) |
111 | { | 85 | { |
112 | if (((unsigned long)page->mapping & PAGE_MAPPING_FLAGS) != | 86 | if (((unsigned long)page->mapping & PAGE_MAPPING_FLAGS) != |
@@ -148,7 +122,6 @@ void unlink_anon_vmas(struct vm_area_struct *); | |||
148 | int anon_vma_clone(struct vm_area_struct *, struct vm_area_struct *); | 122 | int anon_vma_clone(struct vm_area_struct *, struct vm_area_struct *); |
149 | int anon_vma_fork(struct vm_area_struct *, struct vm_area_struct *); | 123 | int anon_vma_fork(struct vm_area_struct *, struct vm_area_struct *); |
150 | void __anon_vma_link(struct vm_area_struct *); | 124 | void __anon_vma_link(struct vm_area_struct *); |
151 | void anon_vma_free(struct anon_vma *); | ||
152 | 125 | ||
153 | static inline void anon_vma_merge(struct vm_area_struct *vma, | 126 | static inline void anon_vma_merge(struct vm_area_struct *vma, |
154 | struct vm_area_struct *next) | 127 | struct vm_area_struct *next) |
@@ -157,6 +130,8 @@ static inline void anon_vma_merge(struct vm_area_struct *vma, | |||
157 | unlink_anon_vmas(next); | 130 | unlink_anon_vmas(next); |
158 | } | 131 | } |
159 | 132 | ||
133 | struct anon_vma *page_get_anon_vma(struct page *page); | ||
134 | |||
160 | /* | 135 | /* |
161 | * rmap interfaces called when adding or removing pte of page | 136 | * rmap interfaces called when adding or removing pte of page |
162 | */ | 137 | */ |