diff options
author | Aneesh Kumar K.V <aneesh.kumar@linux.vnet.ibm.com> | 2016-04-29 16:25:34 +0300 |
---|---|---|
committer | Michael Ellerman <mpe@ellerman.id.au> | 2016-05-01 11:32:26 +0300 |
commit | ac29c64089b74d107edb90879e63a2f7a03cd66b (patch) | |
tree | 3143933d055f49376ec549cc3ffe76a224b23288 /arch/powerpc/include/asm/book3s/64/pgtable.h | |
parent | e7bfc462d32fc417d3fea8ad07b62b59f000e925 (diff) | |
download | linux-ac29c64089b74d107edb90879e63a2f7a03cd66b.tar.xz |
powerpc/mm: Replace _PAGE_USER with _PAGE_PRIVILEGED
_PAGE_PRIVILEGED means the page can be accessed only by the kernel. This
is done to keep pte bits similar to PowerISA 3.0 Radix PTE format. User
pages are now marked by clearing _PAGE_PRIVILEGED bit.
Previously we allowed the kernel to have a privileged page in the lower
address range (USER_REGION). With this patch such access is denied.
We also prevent a kernel access to a non-privileged page in higher
address range (ie, REGION_ID != 0).
Both the above access scenarios should never happen.
Cc: Arnd Bergmann <arnd@arndb.de>
Cc: Jeremy Kerr <jk@ozlabs.org>
Cc: Frederic Barrat <fbarrat@linux.vnet.ibm.com>
Acked-by: Ian Munsie <imunsie@au1.ibm.com>
Signed-off-by: Aneesh Kumar K.V <aneesh.kumar@linux.vnet.ibm.com>
Signed-off-by: Michael Ellerman <mpe@ellerman.id.au>
Diffstat (limited to 'arch/powerpc/include/asm/book3s/64/pgtable.h')
-rw-r--r-- | arch/powerpc/include/asm/book3s/64/pgtable.h | 18 |
1 files changed, 17 insertions, 1 deletions
diff --git a/arch/powerpc/include/asm/book3s/64/pgtable.h b/arch/powerpc/include/asm/book3s/64/pgtable.h index 60e84260a07d..b609729e0d76 100644 --- a/arch/powerpc/include/asm/book3s/64/pgtable.h +++ b/arch/powerpc/include/asm/book3s/64/pgtable.h @@ -187,7 +187,7 @@ extern struct page *pgd_page(pgd_t pgd); static inline bool pte_user(pte_t pte) { - return !!(pte_val(pte) & _PAGE_USER); + return !(pte_val(pte) & _PAGE_PRIVILEGED); } #ifdef CONFIG_MEM_SOFT_DIRTY @@ -211,6 +211,22 @@ static inline pte_t pte_swp_clear_soft_dirty(pte_t pte) } #endif /* CONFIG_HAVE_ARCH_SOFT_DIRTY */ +static inline bool check_pte_access(unsigned long access, unsigned long ptev) +{ + /* + * This check for _PAGE_RWX and _PAGE_PRESENT bits + */ + if (access & ~ptev) + return false; + /* + * This check for access to privilege space + */ + if ((access & _PAGE_PRIVILEGED) != (ptev & _PAGE_PRIVILEGED)) + return false; + + return true; +} + void pgtable_cache_add(unsigned shift, void (*ctor)(void *)); void pgtable_cache_init(void); |