diff options
author | James Morse <james.morse@arm.com> | 2019-01-15 18:49:17 +0000 |
---|---|---|
committer | Will Deacon <will.deacon@arm.com> | 2019-01-16 11:55:11 +0000 |
commit | 2f97967503df8e45bc256a348b6f050abd2a38ed (patch) | |
tree | a944534da02dde3be903dd460668e2667bcd07ca | |
parent | 1c7fc5cbc33980acd13d668f1c8f0313d6ae9fd8 (diff) |
arm64: kpti: Update arm64_kernel_use_ng_mappings() when forced on
Since commit b89d82ef01b3 ("arm64: kpti: Avoid rewriting early page
tables when KASLR is enabled"), a kernel built with CONFIG_RANDOMIZE_BASE
can decide early whether to use non-global mappings by checking the
kaslr_offset().
A kernel built without CONFIG_RANDOMIZE_BASE, instead checks the
cpufeature static-key.
This leaves a gap where CONFIG_RANDOMIZE_BASE was enabled, no
kaslr seed was provided, but kpti was forced on using the cmdline
option.
When the decision is made late, kpti_install_ng_mappings() will re-write
the page tables, but arm64_kernel_use_ng_mappings()'s value does not
change as it only tests the cpufeature static-key if
CONFIG_RANDOMIZE_BASE is disabled.
This function influences PROT_DEFAULT via PTE_MAYBE_NG, and causes
pgattr_change_is_safe() to catch nG->G transitions when the unchanged
PROT_DEFAULT is used as part of PAGE_KERNEL_RO:
[ 1.942255] alternatives: patching kernel code
[ 1.998288] ------------[ cut here ]------------
[ 2.000693] kernel BUG at arch/arm64/mm/mmu.c:165!
[ 2.019215] Internal error: Oops - BUG: 0 [#1] PREEMPT SMP
[ 2.020257] Modules linked in:
[ 2.020807] CPU: 0 PID: 1 Comm: swapper/0 Not tainted 5.0.0-rc2 #51
[ 2.021917] Hardware name: linux,dummy-virt (DT)
[ 2.022790] pstate: 40000005 (nZcv daif -PAN -UAO)
[ 2.023742] pc : __create_pgd_mapping+0x508/0x6d0
[ 2.024671] lr : __create_pgd_mapping+0x500/0x6d0
[ 2.058059] Process swapper/0 (pid: 1, stack limit = 0x(____ptrval____))
[ 2.059369] Call trace:
[ 2.059845] __create_pgd_mapping+0x508/0x6d0
[ 2.060684] update_mapping_prot+0x48/0xd0
[ 2.061477] mark_linear_text_alias_ro+0xdc/0xe4
[ 2.070502] smp_cpus_done+0x90/0x98
[ 2.071216] smp_init+0x100/0x114
[ 2.071878] kernel_init_freeable+0xd4/0x220
[ 2.072750] kernel_init+0x10/0x100
[ 2.073455] ret_from_fork+0x10/0x18
[ 2.075414] ---[ end trace 3572f3a7782292de ]---
[ 2.076389] Kernel panic - not syncing: Attempted to kill init! exitcode=0x0000000b
If arm64_kernel_unmapped_at_el0() is true, arm64_kernel_use_ng_mappings()
should also be true.
Signed-off-by: James Morse <james.morse@arm.com>
CC: Ard Biesheuvel <ard.biesheuvel@linaro.org>
CC: John Garry <john.garry@huawei.com>
CC: Will Deacon <will.deacon@arm.com>
Signed-off-by: Will Deacon <will.deacon@arm.com>
-rw-r--r-- | arch/arm64/include/asm/mmu.h | 5 |
1 files changed, 4 insertions, 1 deletions
diff --git a/arch/arm64/include/asm/mmu.h b/arch/arm64/include/asm/mmu.h index ac352accb3d9..3e8063f4f9d3 100644 --- a/arch/arm64/include/asm/mmu.h +++ b/arch/arm64/include/asm/mmu.h @@ -60,8 +60,11 @@ static inline bool arm64_kernel_use_ng_mappings(void) * later determine that kpti is required, then * kpti_install_ng_mappings() will make them non-global. */ + if (arm64_kernel_unmapped_at_el0()) + return true; + if (!IS_ENABLED(CONFIG_RANDOMIZE_BASE)) - return arm64_kernel_unmapped_at_el0(); + return false; /* * KASLR is enabled so we're going to be enabling kpti on non-broken |