From: Russell Currey <rus...@russell.cc> To enable strict module RWX on powerpc, set:
CONFIG_STRICT_MODULE_RWX=y You should also have CONFIG_STRICT_KERNEL_RWX=y set to have any real security benefit. ARCH_HAS_STRICT_MODULE_RWX is set to require ARCH_HAS_STRICT_KERNEL_RWX. This is due to a quirk in arch/Kconfig and arch/powerpc/Kconfig that makes STRICT_MODULE_RWX *on by default* in configurations where STRICT_KERNEL_RWX is *unavailable*. Since this doesn't make much sense, and module RWX without kernel RWX doesn't make much sense, having the same dependencies as kernel RWX works around this problem. With STRICT_MODULE_RWX, now make module_alloc() allocate pages with KERNEL_PAGE protection rather than KERNEL_PAGE_EXEC. Book32s/32 processors with a hash mmu (i.e. 604 core) can not set memory protection on a page by page basis so do not enable. Signed-off-by: Russell Currey <rus...@russell.cc> [jpn: - predicate on !PPC_BOOK3S_604 - make module_alloc() use PAGE_KERNEL protection] Signed-off-by: Jordan Niethe <jniet...@gmail.com> --- v10: - Predicate on !PPC_BOOK3S_604 - Make module_alloc() use PAGE_KERNEL protection v11: - Neaten up --- arch/powerpc/Kconfig | 1 + arch/powerpc/kernel/module.c | 9 ++++++--- 2 files changed, 7 insertions(+), 3 deletions(-) diff --git a/arch/powerpc/Kconfig b/arch/powerpc/Kconfig index 94c34932a74b..9e264309fd99 100644 --- a/arch/powerpc/Kconfig +++ b/arch/powerpc/Kconfig @@ -140,6 +140,7 @@ config PPC select ARCH_HAS_SCALED_CPUTIME if VIRT_CPU_ACCOUNTING_NATIVE && PPC_BOOK3S_64 select ARCH_HAS_SET_MEMORY select ARCH_HAS_STRICT_KERNEL_RWX if ((PPC_BOOK3S_64 || PPC32) && !HIBERNATION) + select ARCH_HAS_STRICT_MODULE_RWX if ARCH_HAS_STRICT_KERNEL_RWX && !PPC_BOOK3S_604 select ARCH_HAS_TICK_BROADCAST if GENERIC_CLOCKEVENTS_BROADCAST select ARCH_HAS_UACCESS_FLUSHCACHE select ARCH_HAS_COPY_MC if PPC64 diff --git a/arch/powerpc/kernel/module.c b/arch/powerpc/kernel/module.c index c60c7457ff47..9eabaf1fadbe 100644 --- a/arch/powerpc/kernel/module.c +++ b/arch/powerpc/kernel/module.c @@ -92,9 +92,12 @@ int module_finalize(const Elf_Ehdr *hdr, static __always_inline void * __module_alloc(unsigned long size, unsigned long start, unsigned long end) { - return __vmalloc_node_range(size, 1, start, end, GFP_KERNEL, - PAGE_KERNEL_EXEC, VM_FLUSH_RESET_PERMS, NUMA_NO_NODE, - __builtin_return_address(0)); + pgprot_t prot = IS_ENABLED(CONFIG_STRICT_MODULE_RWX) ? PAGE_KERNEL : + PAGE_KERNEL_EXEC; + + return __vmalloc_node_range(size, 1, MODULES_VADDR, MODULES_END, + GFP_KERNEL, prot, VM_FLUSH_RESET_PERMS, + NUMA_NO_NODE, __builtin_return_address(0)); } void *module_alloc(unsigned long size) -- 2.25.1