0001
0002 #ifndef __ASM_GENERIC_PGALLOC_H
0003 #define __ASM_GENERIC_PGALLOC_H
0004
0005 #ifdef CONFIG_MMU
0006
0007 #define GFP_PGTABLE_KERNEL (GFP_KERNEL | __GFP_ZERO)
0008 #define GFP_PGTABLE_USER (GFP_PGTABLE_KERNEL | __GFP_ACCOUNT)
0009
0010
0011
0012
0013
0014
0015
0016
0017
0018
0019 static inline pte_t *__pte_alloc_one_kernel(struct mm_struct *mm)
0020 {
0021 return (pte_t *)__get_free_page(GFP_PGTABLE_KERNEL);
0022 }
0023
0024 #ifndef __HAVE_ARCH_PTE_ALLOC_ONE_KERNEL
0025
0026
0027
0028
0029
0030
0031 static inline pte_t *pte_alloc_one_kernel(struct mm_struct *mm)
0032 {
0033 return __pte_alloc_one_kernel(mm);
0034 }
0035 #endif
0036
0037
0038
0039
0040
0041
0042 static inline void pte_free_kernel(struct mm_struct *mm, pte_t *pte)
0043 {
0044 free_page((unsigned long)pte);
0045 }
0046
0047
0048
0049
0050
0051
0052
0053
0054
0055
0056
0057
0058
0059 static inline pgtable_t __pte_alloc_one(struct mm_struct *mm, gfp_t gfp)
0060 {
0061 struct page *pte;
0062
0063 pte = alloc_page(gfp);
0064 if (!pte)
0065 return NULL;
0066 if (!pgtable_pte_page_ctor(pte)) {
0067 __free_page(pte);
0068 return NULL;
0069 }
0070
0071 return pte;
0072 }
0073
0074 #ifndef __HAVE_ARCH_PTE_ALLOC_ONE
0075
0076
0077
0078
0079
0080
0081
0082
0083 static inline pgtable_t pte_alloc_one(struct mm_struct *mm)
0084 {
0085 return __pte_alloc_one(mm, GFP_PGTABLE_USER);
0086 }
0087 #endif
0088
0089
0090
0091
0092
0093
0094
0095
0096
0097
0098
0099 static inline void pte_free(struct mm_struct *mm, struct page *pte_page)
0100 {
0101 pgtable_pte_page_dtor(pte_page);
0102 __free_page(pte_page);
0103 }
0104
0105
0106 #if CONFIG_PGTABLE_LEVELS > 2
0107
0108 #ifndef __HAVE_ARCH_PMD_ALLOC_ONE
0109
0110
0111
0112
0113
0114
0115
0116
0117
0118
0119 static inline pmd_t *pmd_alloc_one(struct mm_struct *mm, unsigned long addr)
0120 {
0121 struct page *page;
0122 gfp_t gfp = GFP_PGTABLE_USER;
0123
0124 if (mm == &init_mm)
0125 gfp = GFP_PGTABLE_KERNEL;
0126 page = alloc_pages(gfp, 0);
0127 if (!page)
0128 return NULL;
0129 if (!pgtable_pmd_page_ctor(page)) {
0130 __free_pages(page, 0);
0131 return NULL;
0132 }
0133 return (pmd_t *)page_address(page);
0134 }
0135 #endif
0136
0137 #ifndef __HAVE_ARCH_PMD_FREE
0138 static inline void pmd_free(struct mm_struct *mm, pmd_t *pmd)
0139 {
0140 BUG_ON((unsigned long)pmd & (PAGE_SIZE-1));
0141 pgtable_pmd_page_dtor(virt_to_page(pmd));
0142 free_page((unsigned long)pmd);
0143 }
0144 #endif
0145
0146 #endif
0147
0148 #if CONFIG_PGTABLE_LEVELS > 3
0149
0150 static inline pud_t *__pud_alloc_one(struct mm_struct *mm, unsigned long addr)
0151 {
0152 gfp_t gfp = GFP_PGTABLE_USER;
0153
0154 if (mm == &init_mm)
0155 gfp = GFP_PGTABLE_KERNEL;
0156 return (pud_t *)get_zeroed_page(gfp);
0157 }
0158
0159 #ifndef __HAVE_ARCH_PUD_ALLOC_ONE
0160
0161
0162
0163
0164
0165
0166
0167
0168
0169 static inline pud_t *pud_alloc_one(struct mm_struct *mm, unsigned long addr)
0170 {
0171 return __pud_alloc_one(mm, addr);
0172 }
0173 #endif
0174
0175 static inline void __pud_free(struct mm_struct *mm, pud_t *pud)
0176 {
0177 BUG_ON((unsigned long)pud & (PAGE_SIZE-1));
0178 free_page((unsigned long)pud);
0179 }
0180
0181 #ifndef __HAVE_ARCH_PUD_FREE
0182 static inline void pud_free(struct mm_struct *mm, pud_t *pud)
0183 {
0184 __pud_free(mm, pud);
0185 }
0186 #endif
0187
0188 #endif
0189
0190 #ifndef __HAVE_ARCH_PGD_FREE
0191 static inline void pgd_free(struct mm_struct *mm, pgd_t *pgd)
0192 {
0193 free_page((unsigned long)pgd);
0194 }
0195 #endif
0196
0197 #endif
0198
0199 #endif