1 #ifndef __LUNAIX_ARCH_PAGETABLE_H
2 #define __LUNAIX_ARCH_PAGETABLE_H
4 #include <lunaix/types.h>
5 #include <lunaix/compiler.h>
7 /* ******** Page Table Manipulation ******** */
9 #ifdef CONFIG_ARCH_X86_64
19 /* General mask to get page offset of a LnT huge page */
21 #define L0T_MASK ( L0T_SIZE - 1 )
22 #define L1T_MASK ( L1T_SIZE - 1 )
23 #define L2T_MASK ( L2T_SIZE - 1 )
24 #define L3T_MASK ( L3T_SIZE - 1 )
25 #define LFT_MASK ( LFT_SIZE - 1 )
27 /* Masks to get index of a LnTE */
29 #define L0T_INDEX_MASK ( VMS_MASK ^ L0T_MASK )
30 #define L1T_INDEX_MASK ( L0T_MASK ^ L1T_MASK )
31 #define L2T_INDEX_MASK ( L1T_MASK ^ L2T_MASK )
32 #define L3T_INDEX_MASK ( L2T_MASK ^ L3T_MASK )
33 #define LFT_INDEX_MASK ( L3T_MASK ^ LFT_MASK )
35 #define PAGE_SHIFT _PAGE_BASE_SHIFT
36 #define PAGE_SIZE _PAGE_BASE_SIZE
37 #define PAGE_MASK _PAGE_BASE_MASK
39 #define LEVEL_SHIFT _PAGE_LEVEL_SHIFT
40 #define LEVEL_SIZE _PAGE_LEVEL_SIZE
41 #define LEVEL_MASK _PAGE_LEVEL_MASK
44 #define MAX_PTEN _PAGE_LEVEL_SIZE
46 // max translation level supported
47 #define MAX_LEVEL _PTW_LEVEL
50 typedef struct __pte pte_t;
54 #define _PTE_PROT_MASK ( _PTE_W | _PTE_U | _PTE_X )
56 #define KERNEL_PAGE ( _PTE_P )
57 #define KERNEL_EXEC ( KERNEL_PAGE | _PTE_X )
58 #define KERNEL_DATA ( KERNEL_PAGE | _PTE_W | _PTE_NX )
59 #define KERNEL_RDONLY ( KERNEL_PAGE | _PTE_NX )
60 #define KERNEL_ROEXEC ( KERNEL_PAGE | _PTE_X )
62 #define USER_PAGE ( _PTE_P | _PTE_U )
63 #define USER_EXEC ( USER_PAGE | _PTE_X )
64 #define USER_DATA ( USER_PAGE | _PTE_W | _PTE_NX )
65 #define USER_RDONLY ( USER_PAGE | _PTE_NX )
66 #define USER_ROEXEC ( USER_PAGE | _PTE_X )
68 #define SELF_MAP ( KERNEL_DATA | _PTE_WT | _PTE_CD )
70 #define __mkpte_from(pte_val) ((pte_t){ .val = (pte_val) })
72 #define null_pte ( __mkpte_from(0) )
73 #define guard_pte ( __mkpte_from(__MEMGUARD) )
74 #define pte_val(pte) ( pte.val )
78 pte_isguardian(pte_t pte)
80 return pte.val == __MEMGUARD;
84 mkpte_prot(pte_attr_t prot)
86 pte_attr_t attrs = (prot & _PTE_PROT_MASK) | _PTE_P;
87 return __mkpte_from(attrs);
91 mkpte(ptr_t paddr, pte_attr_t prot)
93 pte_attr_t attrs = (prot & _PTE_PROT_MASK) | _PTE_P;
94 return __mkpte_from((paddr & ~_PAGE_BASE_MASK) | attrs);
98 mkpte_root(ptr_t paddr, pte_attr_t prot)
100 pte_attr_t attrs = (prot & _PTE_PROT_MASK) | _PTE_P;
101 return __mkpte_from((paddr & ~_PAGE_BASE_MASK) | attrs);
105 mkpte_raw(unsigned long pte_val)
107 return __mkpte_from(pte_val);
111 pte_setpaddr(pte_t pte, ptr_t paddr)
113 return __mkpte_from((pte.val & _PAGE_BASE_MASK) | (paddr & ~_PAGE_BASE_MASK));
117 pte_setppfn(pte_t pte, pfn_t ppfn)
119 return __mkpte_from((pte.val & _PAGE_BASE_MASK) | (ppfn * PAGE_SIZE));
125 return __paddr(pte.val) & ~_PAGE_BASE_MASK;
131 return __paddr(pte.val) >> _PAGE_BASE_SHIFT;
135 pte_setprot(pte_t pte, ptr_t prot)
137 return __mkpte_from((pte.val & ~_PTE_PROT_MASK) | (prot & _PTE_PROT_MASK));
140 static inline pte_attr_t
143 return (pte.val & _PTE_PROT_MASK);
147 pte_isnull(pte_t pte)
153 pte_mkhuge(pte_t pte)
155 return __mkpte_from(pte.val | _PTE_PS);
159 pte_mkvolatile(pte_t pte)
161 return __mkpte_from(pte.val | _PTE_WT | _PTE_CD);
165 pte_mkroot(pte_t pte)
167 return __mkpte_from(pte.val & ~_PTE_PS);
171 pte_usepat(pte_t pte)
173 return __mkpte_from(pte.val | _PTE_PAT);
179 return !!(pte.val & _PTE_PS);
183 pte_mkloaded(pte_t pte)
185 return __mkpte_from(pte.val | _PTE_P);
189 pte_mkunloaded(pte_t pte)
191 return __mkpte_from(pte.val & ~_PTE_P);
195 pte_isloaded(pte_t pte)
197 return !!(pte.val & _PTE_P);
201 pte_mkwprotect(pte_t pte)
203 return __mkpte_from(pte.val & ~_PTE_W);
207 pte_mkwritable(pte_t pte)
209 return __mkpte_from(pte.val | _PTE_W);
213 pte_iswprotect(pte_t pte)
215 return !(pte.val & _PTE_W);
219 pte_mkuser(pte_t pte)
221 return __mkpte_from(pte.val | _PTE_U);
225 pte_mkkernel(pte_t pte)
227 return __mkpte_from(pte.val & ~_PTE_U);
231 pte_allow_user(pte_t pte)
233 return !!(pte.val & _PTE_U);
237 pte_mkexec(pte_t pte)
239 return __mkpte_from(pte.val & ~_PTE_NX);
243 pte_mknonexec(pte_t pte)
245 return __mkpte_from(pte.val | _PTE_NX);
249 pte_isexec(pte_t pte)
251 return !(pte.val & _PTE_NX);
255 pte_mkuntouch(pte_t pte)
257 return __mkpte_from(pte.val & ~_PTE_A);
261 pte_istouched(pte_t pte)
263 return !!(pte.val & _PTE_A);
267 pte_mkclean(pte_t pte)
269 return __mkpte_from(pte.val & ~_PTE_D);
275 return !!(pte.val & _PTE_D);
279 set_pte(pte_t* ptep, pte_t pte)
285 pte_at(pte_t* ptep) {
290 #endif /* __LUNAIX_ARCH_PAGETABLE_H */