aboutsummaryrefslogtreecommitdiffstats
path: root/include/asm-x86/pgtable.h
diff options
context:
space:
mode:
Diffstat (limited to 'include/asm-x86/pgtable.h')
-rw-r--r--include/asm-x86/pgtable.h156
1 files changed, 120 insertions, 36 deletions
diff --git a/include/asm-x86/pgtable.h b/include/asm-x86/pgtable.h
index e814cfe96af2..2ce765070464 100644
--- a/include/asm-x86/pgtable.h
+++ b/include/asm-x86/pgtable.h
@@ -48,12 +48,15 @@
48#endif 48#endif
49 49
50/* If _PAGE_PRESENT is clear, we use these: */ 50/* If _PAGE_PRESENT is clear, we use these: */
51#define _PAGE_FILE _PAGE_DIRTY /* nonlinear file mapping, saved PTE; unset:swap */ 51#define _PAGE_FILE _PAGE_DIRTY /* nonlinear file mapping,
52 * saved PTE; unset:swap */
52#define _PAGE_PROTNONE _PAGE_PSE /* if the user mapped it with PROT_NONE; 53#define _PAGE_PROTNONE _PAGE_PSE /* if the user mapped it with PROT_NONE;
53 pte_present gives true */ 54 pte_present gives true */
54 55
55#define _PAGE_TABLE (_PAGE_PRESENT | _PAGE_RW | _PAGE_USER | _PAGE_ACCESSED | _PAGE_DIRTY) 56#define _PAGE_TABLE (_PAGE_PRESENT | _PAGE_RW | _PAGE_USER | \
56#define _KERNPG_TABLE (_PAGE_PRESENT | _PAGE_RW | _PAGE_ACCESSED | _PAGE_DIRTY) 57 _PAGE_ACCESSED | _PAGE_DIRTY)
58#define _KERNPG_TABLE (_PAGE_PRESENT | _PAGE_RW | _PAGE_ACCESSED | \
59 _PAGE_DIRTY)
57 60
58#define _PAGE_CHG_MASK (PTE_MASK | _PAGE_ACCESSED | _PAGE_DIRTY) 61#define _PAGE_CHG_MASK (PTE_MASK | _PAGE_ACCESSED | _PAGE_DIRTY)
59 62
@@ -64,14 +67,20 @@
64#define _PAGE_CACHE_UC (_PAGE_PCD | _PAGE_PWT) 67#define _PAGE_CACHE_UC (_PAGE_PCD | _PAGE_PWT)
65 68
66#define PAGE_NONE __pgprot(_PAGE_PROTNONE | _PAGE_ACCESSED) 69#define PAGE_NONE __pgprot(_PAGE_PROTNONE | _PAGE_ACCESSED)
67#define PAGE_SHARED __pgprot(_PAGE_PRESENT | _PAGE_RW | _PAGE_USER | _PAGE_ACCESSED | _PAGE_NX) 70#define PAGE_SHARED __pgprot(_PAGE_PRESENT | _PAGE_RW | _PAGE_USER | \
68 71 _PAGE_ACCESSED | _PAGE_NX)
69#define PAGE_SHARED_EXEC __pgprot(_PAGE_PRESENT | _PAGE_RW | _PAGE_USER | _PAGE_ACCESSED) 72
70#define PAGE_COPY_NOEXEC __pgprot(_PAGE_PRESENT | _PAGE_USER | _PAGE_ACCESSED | _PAGE_NX) 73#define PAGE_SHARED_EXEC __pgprot(_PAGE_PRESENT | _PAGE_RW | \
71#define PAGE_COPY_EXEC __pgprot(_PAGE_PRESENT | _PAGE_USER | _PAGE_ACCESSED) 74 _PAGE_USER | _PAGE_ACCESSED)
75#define PAGE_COPY_NOEXEC __pgprot(_PAGE_PRESENT | _PAGE_USER | \
76 _PAGE_ACCESSED | _PAGE_NX)
77#define PAGE_COPY_EXEC __pgprot(_PAGE_PRESENT | _PAGE_USER | \
78 _PAGE_ACCESSED)
72#define PAGE_COPY PAGE_COPY_NOEXEC 79#define PAGE_COPY PAGE_COPY_NOEXEC
73#define PAGE_READONLY __pgprot(_PAGE_PRESENT | _PAGE_USER | _PAGE_ACCESSED | _PAGE_NX) 80#define PAGE_READONLY __pgprot(_PAGE_PRESENT | _PAGE_USER | \
74#define PAGE_READONLY_EXEC __pgprot(_PAGE_PRESENT | _PAGE_USER | _PAGE_ACCESSED) 81 _PAGE_ACCESSED | _PAGE_NX)
82#define PAGE_READONLY_EXEC __pgprot(_PAGE_PRESENT | _PAGE_USER | \
83 _PAGE_ACCESSED)
75 84
76#ifdef CONFIG_X86_32 85#ifdef CONFIG_X86_32
77#define _PAGE_KERNEL_EXEC \ 86#define _PAGE_KERNEL_EXEC \
@@ -142,7 +151,7 @@ extern pteval_t __PAGE_KERNEL, __PAGE_KERNEL_EXEC;
142 * ZERO_PAGE is a global shared page that is always zero: used 151 * ZERO_PAGE is a global shared page that is always zero: used
143 * for zero-mapped memory areas etc.. 152 * for zero-mapped memory areas etc..
144 */ 153 */
145extern unsigned long empty_zero_page[PAGE_SIZE/sizeof(unsigned long)]; 154extern unsigned long empty_zero_page[PAGE_SIZE / sizeof(unsigned long)];
146#define ZERO_PAGE(vaddr) (virt_to_page(empty_zero_page)) 155#define ZERO_PAGE(vaddr) (virt_to_page(empty_zero_page))
147 156
148extern spinlock_t pgd_lock; 157extern spinlock_t pgd_lock;
@@ -152,30 +161,101 @@ extern struct list_head pgd_list;
152 * The following only work if pte_present() is true. 161 * The following only work if pte_present() is true.
153 * Undefined behaviour if not.. 162 * Undefined behaviour if not..
154 */ 163 */
155static inline int pte_dirty(pte_t pte) { return pte_val(pte) & _PAGE_DIRTY; } 164static inline int pte_dirty(pte_t pte)
156static inline int pte_young(pte_t pte) { return pte_val(pte) & _PAGE_ACCESSED; } 165{
157static inline int pte_write(pte_t pte) { return pte_val(pte) & _PAGE_RW; } 166 return pte_val(pte) & _PAGE_DIRTY;
158static inline int pte_file(pte_t pte) { return pte_val(pte) & _PAGE_FILE; } 167}
159static inline int pte_huge(pte_t pte) { return pte_val(pte) & _PAGE_PSE; } 168
160static inline int pte_global(pte_t pte) { return pte_val(pte) & _PAGE_GLOBAL; } 169static inline int pte_young(pte_t pte)
161static inline int pte_exec(pte_t pte) { return !(pte_val(pte) & _PAGE_NX); } 170{
162 171 return pte_val(pte) & _PAGE_ACCESSED;
163static inline int pmd_large(pmd_t pte) { 172}
164 return (pmd_val(pte) & (_PAGE_PSE|_PAGE_PRESENT)) == 173
165 (_PAGE_PSE|_PAGE_PRESENT); 174static inline int pte_write(pte_t pte)
175{
176 return pte_val(pte) & _PAGE_RW;
177}
178
179static inline int pte_file(pte_t pte)
180{
181 return pte_val(pte) & _PAGE_FILE;
182}
183
184static inline int pte_huge(pte_t pte)
185{
186 return pte_val(pte) & _PAGE_PSE;
166} 187}
167 188
168static inline pte_t pte_mkclean(pte_t pte) { return __pte(pte_val(pte) & ~(pteval_t)_PAGE_DIRTY); } 189static inline int pte_global(pte_t pte)
169static inline pte_t pte_mkold(pte_t pte) { return __pte(pte_val(pte) & ~(pteval_t)_PAGE_ACCESSED); } 190{
170static inline pte_t pte_wrprotect(pte_t pte) { return __pte(pte_val(pte) & ~(pteval_t)_PAGE_RW); } 191 return pte_val(pte) & _PAGE_GLOBAL;
171static inline pte_t pte_mkexec(pte_t pte) { return __pte(pte_val(pte) & ~(pteval_t)_PAGE_NX); } 192}
172static inline pte_t pte_mkdirty(pte_t pte) { return __pte(pte_val(pte) | _PAGE_DIRTY); } 193
173static inline pte_t pte_mkyoung(pte_t pte) { return __pte(pte_val(pte) | _PAGE_ACCESSED); } 194static inline int pte_exec(pte_t pte)
174static inline pte_t pte_mkwrite(pte_t pte) { return __pte(pte_val(pte) | _PAGE_RW); } 195{
175static inline pte_t pte_mkhuge(pte_t pte) { return __pte(pte_val(pte) | _PAGE_PSE); } 196 return !(pte_val(pte) & _PAGE_NX);
176static inline pte_t pte_clrhuge(pte_t pte) { return __pte(pte_val(pte) & ~(pteval_t)_PAGE_PSE); } 197}
177static inline pte_t pte_mkglobal(pte_t pte) { return __pte(pte_val(pte) | _PAGE_GLOBAL); } 198
178static inline pte_t pte_clrglobal(pte_t pte) { return __pte(pte_val(pte) & ~(pteval_t)_PAGE_GLOBAL); } 199static inline int pmd_large(pmd_t pte)
200{
201 return (pmd_val(pte) & (_PAGE_PSE | _PAGE_PRESENT)) ==
202 (_PAGE_PSE | _PAGE_PRESENT);
203}
204
205static inline pte_t pte_mkclean(pte_t pte)
206{
207 return __pte(pte_val(pte) & ~(pteval_t)_PAGE_DIRTY);
208}
209
210static inline pte_t pte_mkold(pte_t pte)
211{
212 return __pte(pte_val(pte) & ~(pteval_t)_PAGE_ACCESSED);
213}
214
215static inline pte_t pte_wrprotect(pte_t pte)
216{
217 return __pte(pte_val(pte) & ~(pteval_t)_PAGE_RW);
218}
219
220static inline pte_t pte_mkexec(pte_t pte)
221{
222 return __pte(pte_val(pte) & ~(pteval_t)_PAGE_NX);
223}
224
225static inline pte_t pte_mkdirty(pte_t pte)
226{
227 return __pte(pte_val(pte) | _PAGE_DIRTY);
228}
229
230static inline pte_t pte_mkyoung(pte_t pte)
231{
232 return __pte(pte_val(pte) | _PAGE_ACCESSED);
233}
234
235static inline pte_t pte_mkwrite(pte_t pte)
236{
237 return __pte(pte_val(pte) | _PAGE_RW);
238}
239
240static inline pte_t pte_mkhuge(pte_t pte)
241{
242 return __pte(pte_val(pte) | _PAGE_PSE);
243}
244
245static inline pte_t pte_clrhuge(pte_t pte)
246{
247 return __pte(pte_val(pte) & ~(pteval_t)_PAGE_PSE);
248}
249
250static inline pte_t pte_mkglobal(pte_t pte)
251{
252 return __pte(pte_val(pte) | _PAGE_GLOBAL);
253}
254
255static inline pte_t pte_clrglobal(pte_t pte)
256{
257 return __pte(pte_val(pte) & ~(pteval_t)_PAGE_GLOBAL);
258}
179 259
180extern pteval_t __supported_pte_mask; 260extern pteval_t __supported_pte_mask;
181 261
@@ -342,7 +422,8 @@ static inline void native_set_pte_at(struct mm_struct *mm, unsigned long addr,
342}) 422})
343 423
344#define __HAVE_ARCH_PTEP_GET_AND_CLEAR 424#define __HAVE_ARCH_PTEP_GET_AND_CLEAR
345static inline pte_t ptep_get_and_clear(struct mm_struct *mm, unsigned long addr, pte_t *ptep) 425static inline pte_t ptep_get_and_clear(struct mm_struct *mm, unsigned long addr,
426 pte_t *ptep)
346{ 427{
347 pte_t pte = native_ptep_get_and_clear(ptep); 428 pte_t pte = native_ptep_get_and_clear(ptep);
348 pte_update(mm, addr, ptep); 429 pte_update(mm, addr, ptep);
@@ -350,7 +431,9 @@ static inline pte_t ptep_get_and_clear(struct mm_struct *mm, unsigned long addr,
350} 431}
351 432
352#define __HAVE_ARCH_PTEP_GET_AND_CLEAR_FULL 433#define __HAVE_ARCH_PTEP_GET_AND_CLEAR_FULL
353static inline pte_t ptep_get_and_clear_full(struct mm_struct *mm, unsigned long addr, pte_t *ptep, int full) 434static inline pte_t ptep_get_and_clear_full(struct mm_struct *mm,
435 unsigned long addr, pte_t *ptep,
436 int full)
354{ 437{
355 pte_t pte; 438 pte_t pte;
356 if (full) { 439 if (full) {
@@ -366,7 +449,8 @@ static inline pte_t ptep_get_and_clear_full(struct mm_struct *mm, unsigned long
366} 449}
367 450
368#define __HAVE_ARCH_PTEP_SET_WRPROTECT 451#define __HAVE_ARCH_PTEP_SET_WRPROTECT
369static inline void ptep_set_wrprotect(struct mm_struct *mm, unsigned long addr, pte_t *ptep) 452static inline void ptep_set_wrprotect(struct mm_struct *mm,
453 unsigned long addr, pte_t *ptep)
370{ 454{
371 clear_bit(_PAGE_BIT_RW, (unsigned long *)&ptep->pte); 455 clear_bit(_PAGE_BIT_RW, (unsigned long *)&ptep->pte);
372 pte_update(mm, addr, ptep); 456 pte_update(mm, addr, ptep);