diff options
Diffstat (limited to 'arch/powerpc/include/asm/hugetlb.h')
-rw-r--r-- | arch/powerpc/include/asm/hugetlb.h | 63 |
1 files changed, 61 insertions, 2 deletions
diff --git a/arch/powerpc/include/asm/hugetlb.h b/arch/powerpc/include/asm/hugetlb.h index 5856a66ab404..86004930a78e 100644 --- a/arch/powerpc/include/asm/hugetlb.h +++ b/arch/powerpc/include/asm/hugetlb.h | |||
@@ -1,15 +1,60 @@ | |||
1 | #ifndef _ASM_POWERPC_HUGETLB_H | 1 | #ifndef _ASM_POWERPC_HUGETLB_H |
2 | #define _ASM_POWERPC_HUGETLB_H | 2 | #define _ASM_POWERPC_HUGETLB_H |
3 | 3 | ||
4 | #ifdef CONFIG_HUGETLB_PAGE | ||
4 | #include <asm/page.h> | 5 | #include <asm/page.h> |
5 | 6 | ||
7 | extern struct kmem_cache *hugepte_cache; | ||
8 | extern void __init reserve_hugetlb_gpages(void); | ||
9 | |||
10 | static inline pte_t *hugepd_page(hugepd_t hpd) | ||
11 | { | ||
12 | BUG_ON(!hugepd_ok(hpd)); | ||
13 | return (pte_t *)((hpd.pd & ~HUGEPD_SHIFT_MASK) | PD_HUGE); | ||
14 | } | ||
15 | |||
16 | static inline unsigned int hugepd_shift(hugepd_t hpd) | ||
17 | { | ||
18 | return hpd.pd & HUGEPD_SHIFT_MASK; | ||
19 | } | ||
20 | |||
21 | static inline pte_t *hugepte_offset(hugepd_t *hpdp, unsigned long addr, | ||
22 | unsigned pdshift) | ||
23 | { | ||
24 | /* | ||
25 | * On 32-bit, we have multiple higher-level table entries that point to | ||
26 | * the same hugepte. Just use the first one since they're all | ||
27 | * identical. So for that case, idx=0. | ||
28 | */ | ||
29 | unsigned long idx = 0; | ||
30 | |||
31 | pte_t *dir = hugepd_page(*hpdp); | ||
32 | #ifdef CONFIG_PPC64 | ||
33 | idx = (addr & ((1UL << pdshift) - 1)) >> hugepd_shift(*hpdp); | ||
34 | #endif | ||
35 | |||
36 | return dir + idx; | ||
37 | } | ||
38 | |||
6 | pte_t *huge_pte_offset_and_shift(struct mm_struct *mm, | 39 | pte_t *huge_pte_offset_and_shift(struct mm_struct *mm, |
7 | unsigned long addr, unsigned *shift); | 40 | unsigned long addr, unsigned *shift); |
8 | 41 | ||
9 | void flush_dcache_icache_hugepage(struct page *page); | 42 | void flush_dcache_icache_hugepage(struct page *page); |
10 | 43 | ||
44 | #if defined(CONFIG_PPC_MM_SLICES) || defined(CONFIG_PPC_SUBPAGE_PROT) | ||
11 | int is_hugepage_only_range(struct mm_struct *mm, unsigned long addr, | 45 | int is_hugepage_only_range(struct mm_struct *mm, unsigned long addr, |
12 | unsigned long len); | 46 | unsigned long len); |
47 | #else | ||
48 | static inline int is_hugepage_only_range(struct mm_struct *mm, | ||
49 | unsigned long addr, | ||
50 | unsigned long len) | ||
51 | { | ||
52 | return 0; | ||
53 | } | ||
54 | #endif | ||
55 | |||
56 | void book3e_hugetlb_preload(struct mm_struct *mm, unsigned long ea, pte_t pte); | ||
57 | void flush_hugetlb_page(struct vm_area_struct *vma, unsigned long vmaddr); | ||
13 | 58 | ||
14 | void hugetlb_free_pgd_range(struct mmu_gather *tlb, unsigned long addr, | 59 | void hugetlb_free_pgd_range(struct mmu_gather *tlb, unsigned long addr, |
15 | unsigned long end, unsigned long floor, | 60 | unsigned long end, unsigned long floor, |
@@ -50,8 +95,11 @@ static inline void set_huge_pte_at(struct mm_struct *mm, unsigned long addr, | |||
50 | static inline pte_t huge_ptep_get_and_clear(struct mm_struct *mm, | 95 | static inline pte_t huge_ptep_get_and_clear(struct mm_struct *mm, |
51 | unsigned long addr, pte_t *ptep) | 96 | unsigned long addr, pte_t *ptep) |
52 | { | 97 | { |
53 | unsigned long old = pte_update(mm, addr, ptep, ~0UL, 1); | 98 | #ifdef CONFIG_PPC64 |
54 | return __pte(old); | 99 | return __pte(pte_update(mm, addr, ptep, ~0UL, 1)); |
100 | #else | ||
101 | return __pte(pte_update(ptep, ~0UL, 0)); | ||
102 | #endif | ||
55 | } | 103 | } |
56 | 104 | ||
57 | static inline void huge_ptep_clear_flush(struct vm_area_struct *vma, | 105 | static inline void huge_ptep_clear_flush(struct vm_area_struct *vma, |
@@ -93,4 +141,15 @@ static inline void arch_release_hugepage(struct page *page) | |||
93 | { | 141 | { |
94 | } | 142 | } |
95 | 143 | ||
144 | #else /* ! CONFIG_HUGETLB_PAGE */ | ||
145 | static inline void reserve_hugetlb_gpages(void) | ||
146 | { | ||
147 | pr_err("Cannot reserve gpages without hugetlb enabled\n"); | ||
148 | } | ||
149 | static inline void flush_hugetlb_page(struct vm_area_struct *vma, | ||
150 | unsigned long vmaddr) | ||
151 | { | ||
152 | } | ||
153 | #endif | ||
154 | |||
96 | #endif /* _ASM_POWERPC_HUGETLB_H */ | 155 | #endif /* _ASM_POWERPC_HUGETLB_H */ |