Re: [PATCH 2/5] mm: expose arch_mmap_rnd when available
On Mon, Mar 02, 2015 at 04:19:45PM -0800, Kees Cook wrote: > diff --git a/arch/arm/Kconfig b/arch/arm/Kconfig > index 9f1f09a2bc9b..248d99cabaa8 100644 > --- a/arch/arm/Kconfig > +++ b/arch/arm/Kconfig > @@ -3,6 +3,7 @@ config ARM > default y > select ARCH_BINFMT_ELF_RANDOMIZE_PIE > select ARCH_HAS_ATOMIC64_DEC_IF_POSITIVE > + select ARCH_HAS_ELF_RANDOMIZE > select ARCH_HAS_TICK_BROADCAST if GENERIC_CLOCKEVENTS_BROADCAST > select ARCH_HAVE_CUSTOM_GPIO_H > select ARCH_HAS_GCOV_PROFILE_ALL > diff --git a/arch/arm/mm/mmap.c b/arch/arm/mm/mmap.c > index 0f8bc158f2c6..3c1fedb034bb 100644 > --- a/arch/arm/mm/mmap.c > +++ b/arch/arm/mm/mmap.c > @@ -169,7 +169,7 @@ arch_get_unmapped_area_topdown(struct file *filp, const > unsigned long addr0, > return addr; > } > > -static unsigned long mmap_rnd(void) > +unsigned long arch_mmap_rnd(void) > { > unsigned long rnd = 0UL; > > @@ -183,7 +183,7 @@ static unsigned long mmap_rnd(void) > > void arch_pick_mmap_layout(struct mm_struct *mm) > { > - unsigned long random_factor = mmap_rnd(); > + unsigned long random_factor = arch_mmap_rnd(); > > if (mmap_is_legacy()) { > mm->mmap_base = TASK_UNMAPPED_BASE + random_factor; For the above, Acked-by: Russell King -- FTTC broadband for 0.8mile line: currently at 10.5Mbps down 400kbps up according to speedtest.net. ___ Linuxppc-dev mailing list Linuxppc-dev@lists.ozlabs.org https://lists.ozlabs.org/listinfo/linuxppc-dev
[PATCH 2/5] mm: expose arch_mmap_rnd when available
When an architecture fully supports randomizing the ELF load location, a per-arch mmap_rnd() function is used to finding a randomized mmap base. In preparation for randomizing the location of ET_DYN binaries separately from mmap, this renames and exports these functions as arch_mmap_rnd(). Additionally introduces CONFIG_ARCH_HAS_ELF_RANDOMIZE for describing this feature on architectures that support it (which is a superset of ARCH_BINFMT_ELF_RANDOMIZE_PIE, since s390 already does this witout the ARCH_BINFMT_ELF_RANDOMIZE_PIE logic). Signed-off-by: Kees Cook --- arch/Kconfig | 7 +++ arch/arm/Kconfig | 1 + arch/arm/mm/mmap.c| 4 ++-- arch/arm64/Kconfig| 1 + arch/arm64/mm/mmap.c | 4 ++-- arch/mips/Kconfig | 1 + arch/mips/mm/mmap.c | 9 ++--- arch/powerpc/Kconfig | 1 + arch/powerpc/mm/mmap.c| 4 ++-- arch/s390/Kconfig | 1 + arch/s390/mm/mmap.c | 8 arch/x86/Kconfig | 1 + arch/x86/mm/mmap.c| 6 +++--- fs/binfmt_elf.c | 1 + include/linux/elf-randomize.h | 10 ++ 15 files changed, 43 insertions(+), 16 deletions(-) create mode 100644 include/linux/elf-randomize.h diff --git a/arch/Kconfig b/arch/Kconfig index 05d7a8a458d5..e315cc79ebe7 100644 --- a/arch/Kconfig +++ b/arch/Kconfig @@ -484,6 +484,13 @@ config HAVE_IRQ_EXIT_ON_IRQ_STACK This spares a stack switch and improves cache usage on softirq processing. +config ARCH_HAS_ELF_RANDOMIZE + bool + help + An architecture supports choosing randomized locations for + stack, mmap, brk, and ET_DYN. Defined functions: + - arch_mmap_rnd(), must respect (current->flags & PF_RANDOMIZE) + # # ABI hall of shame # diff --git a/arch/arm/Kconfig b/arch/arm/Kconfig index 9f1f09a2bc9b..248d99cabaa8 100644 --- a/arch/arm/Kconfig +++ b/arch/arm/Kconfig @@ -3,6 +3,7 @@ config ARM default y select ARCH_BINFMT_ELF_RANDOMIZE_PIE select ARCH_HAS_ATOMIC64_DEC_IF_POSITIVE + select ARCH_HAS_ELF_RANDOMIZE select ARCH_HAS_TICK_BROADCAST if GENERIC_CLOCKEVENTS_BROADCAST select ARCH_HAVE_CUSTOM_GPIO_H select ARCH_HAS_GCOV_PROFILE_ALL diff --git a/arch/arm/mm/mmap.c b/arch/arm/mm/mmap.c index 0f8bc158f2c6..3c1fedb034bb 100644 --- a/arch/arm/mm/mmap.c +++ b/arch/arm/mm/mmap.c @@ -169,7 +169,7 @@ arch_get_unmapped_area_topdown(struct file *filp, const unsigned long addr0, return addr; } -static unsigned long mmap_rnd(void) +unsigned long arch_mmap_rnd(void) { unsigned long rnd = 0UL; @@ -183,7 +183,7 @@ static unsigned long mmap_rnd(void) void arch_pick_mmap_layout(struct mm_struct *mm) { - unsigned long random_factor = mmap_rnd(); + unsigned long random_factor = arch_mmap_rnd(); if (mmap_is_legacy()) { mm->mmap_base = TASK_UNMAPPED_BASE + random_factor; diff --git a/arch/arm64/Kconfig b/arch/arm64/Kconfig index 1b8e97331ffb..5f469095e0e2 100644 --- a/arch/arm64/Kconfig +++ b/arch/arm64/Kconfig @@ -2,6 +2,7 @@ config ARM64 def_bool y select ARCH_BINFMT_ELF_RANDOMIZE_PIE select ARCH_HAS_ATOMIC64_DEC_IF_POSITIVE + select ARCH_HAS_ELF_RANDOMIZE select ARCH_HAS_GCOV_PROFILE_ALL select ARCH_HAS_SG_CHAIN select ARCH_HAS_TICK_BROADCAST if GENERIC_CLOCKEVENTS_BROADCAST diff --git a/arch/arm64/mm/mmap.c b/arch/arm64/mm/mmap.c index 54922d1275b8..b7117cb4bc07 100644 --- a/arch/arm64/mm/mmap.c +++ b/arch/arm64/mm/mmap.c @@ -47,7 +47,7 @@ static int mmap_is_legacy(void) return sysctl_legacy_va_layout; } -static unsigned long mmap_rnd(void) +unsigned long arch_mmap_rnd(void) { unsigned long rnd = 0; @@ -66,7 +66,7 @@ static unsigned long mmap_base(void) else if (gap > MAX_GAP) gap = MAX_GAP; - return PAGE_ALIGN(STACK_TOP - gap - mmap_rnd()); + return PAGE_ALIGN(STACK_TOP - gap - arch_mmap_rnd()); } /* diff --git a/arch/mips/Kconfig b/arch/mips/Kconfig index c7a16904cd03..72ce5cece768 100644 --- a/arch/mips/Kconfig +++ b/arch/mips/Kconfig @@ -24,6 +24,7 @@ config MIPS select HAVE_DEBUG_KMEMLEAK select HAVE_SYSCALL_TRACEPOINTS select ARCH_BINFMT_ELF_RANDOMIZE_PIE + select ARCH_HAS_ELF_RANDOMIZE select HAVE_ARCH_TRANSPARENT_HUGEPAGE if CPU_SUPPORTS_HUGEPAGES && 64BIT select RTC_LIB if !MACH_LOONGSON select GENERIC_ATOMIC64 if !64BIT diff --git a/arch/mips/mm/mmap.c b/arch/mips/mm/mmap.c index f1baadd56e82..d32490d99671 100644 --- a/arch/mips/mm/mmap.c +++ b/arch/mips/mm/mmap.c @@ -164,9 +164,12 @@ void arch_pick_mmap_layout(struct mm_struct *mm) } } -static inline unsigned long brk_rnd(void) +unsigned long arch_mmap_rnd(void) { - unsigned long rnd = get_random_int(); + unsigned long rnd = 0; + + if (current->flags & PF_RANDOMI
[PATCH 2/5] mm: expose arch_mmap_rnd when available
When an architecture fully supports randomizing the ELF load location, the arch_mmap_rnd() function becomes available. Rename and expose these functions where they exist. Introduces CONFIG_ARCH_HAS_ELF_RANDOMIZE. Signed-off-by: Kees Cook --- arch/Kconfig | 7 +++ arch/arm/Kconfig | 1 + arch/arm/mm/mmap.c| 4 ++-- arch/arm64/Kconfig| 1 + arch/arm64/mm/mmap.c | 4 ++-- arch/mips/Kconfig | 1 + arch/mips/mm/mmap.c | 9 ++--- arch/powerpc/Kconfig | 1 + arch/powerpc/mm/mmap.c| 4 ++-- arch/s390/Kconfig | 1 + arch/s390/mm/mmap.c | 8 arch/x86/Kconfig | 1 + arch/x86/mm/mmap.c| 6 +++--- fs/binfmt_elf.c | 1 + include/linux/elf-randomize.h | 10 ++ 15 files changed, 43 insertions(+), 16 deletions(-) create mode 100644 include/linux/elf-randomize.h diff --git a/arch/Kconfig b/arch/Kconfig index 05d7a8a458d5..e315cc79ebe7 100644 --- a/arch/Kconfig +++ b/arch/Kconfig @@ -484,6 +484,13 @@ config HAVE_IRQ_EXIT_ON_IRQ_STACK This spares a stack switch and improves cache usage on softirq processing. +config ARCH_HAS_ELF_RANDOMIZE + bool + help + An architecture supports choosing randomized locations for + stack, mmap, brk, and ET_DYN. Defined functions: + - arch_mmap_rnd(), must respect (current->flags & PF_RANDOMIZE) + # # ABI hall of shame # diff --git a/arch/arm/Kconfig b/arch/arm/Kconfig index 9f1f09a2bc9b..248d99cabaa8 100644 --- a/arch/arm/Kconfig +++ b/arch/arm/Kconfig @@ -3,6 +3,7 @@ config ARM default y select ARCH_BINFMT_ELF_RANDOMIZE_PIE select ARCH_HAS_ATOMIC64_DEC_IF_POSITIVE + select ARCH_HAS_ELF_RANDOMIZE select ARCH_HAS_TICK_BROADCAST if GENERIC_CLOCKEVENTS_BROADCAST select ARCH_HAVE_CUSTOM_GPIO_H select ARCH_HAS_GCOV_PROFILE_ALL diff --git a/arch/arm/mm/mmap.c b/arch/arm/mm/mmap.c index 0f8bc158f2c6..3c1fedb034bb 100644 --- a/arch/arm/mm/mmap.c +++ b/arch/arm/mm/mmap.c @@ -169,7 +169,7 @@ arch_get_unmapped_area_topdown(struct file *filp, const unsigned long addr0, return addr; } -static unsigned long mmap_rnd(void) +unsigned long arch_mmap_rnd(void) { unsigned long rnd = 0UL; @@ -183,7 +183,7 @@ static unsigned long mmap_rnd(void) void arch_pick_mmap_layout(struct mm_struct *mm) { - unsigned long random_factor = mmap_rnd(); + unsigned long random_factor = arch_mmap_rnd(); if (mmap_is_legacy()) { mm->mmap_base = TASK_UNMAPPED_BASE + random_factor; diff --git a/arch/arm64/Kconfig b/arch/arm64/Kconfig index 1b8e97331ffb..5f469095e0e2 100644 --- a/arch/arm64/Kconfig +++ b/arch/arm64/Kconfig @@ -2,6 +2,7 @@ config ARM64 def_bool y select ARCH_BINFMT_ELF_RANDOMIZE_PIE select ARCH_HAS_ATOMIC64_DEC_IF_POSITIVE + select ARCH_HAS_ELF_RANDOMIZE select ARCH_HAS_GCOV_PROFILE_ALL select ARCH_HAS_SG_CHAIN select ARCH_HAS_TICK_BROADCAST if GENERIC_CLOCKEVENTS_BROADCAST diff --git a/arch/arm64/mm/mmap.c b/arch/arm64/mm/mmap.c index 54922d1275b8..b7117cb4bc07 100644 --- a/arch/arm64/mm/mmap.c +++ b/arch/arm64/mm/mmap.c @@ -47,7 +47,7 @@ static int mmap_is_legacy(void) return sysctl_legacy_va_layout; } -static unsigned long mmap_rnd(void) +unsigned long arch_mmap_rnd(void) { unsigned long rnd = 0; @@ -66,7 +66,7 @@ static unsigned long mmap_base(void) else if (gap > MAX_GAP) gap = MAX_GAP; - return PAGE_ALIGN(STACK_TOP - gap - mmap_rnd()); + return PAGE_ALIGN(STACK_TOP - gap - arch_mmap_rnd()); } /* diff --git a/arch/mips/Kconfig b/arch/mips/Kconfig index c7a16904cd03..72ce5cece768 100644 --- a/arch/mips/Kconfig +++ b/arch/mips/Kconfig @@ -24,6 +24,7 @@ config MIPS select HAVE_DEBUG_KMEMLEAK select HAVE_SYSCALL_TRACEPOINTS select ARCH_BINFMT_ELF_RANDOMIZE_PIE + select ARCH_HAS_ELF_RANDOMIZE select HAVE_ARCH_TRANSPARENT_HUGEPAGE if CPU_SUPPORTS_HUGEPAGES && 64BIT select RTC_LIB if !MACH_LOONGSON select GENERIC_ATOMIC64 if !64BIT diff --git a/arch/mips/mm/mmap.c b/arch/mips/mm/mmap.c index f1baadd56e82..d32490d99671 100644 --- a/arch/mips/mm/mmap.c +++ b/arch/mips/mm/mmap.c @@ -164,9 +164,12 @@ void arch_pick_mmap_layout(struct mm_struct *mm) } } -static inline unsigned long brk_rnd(void) +unsigned long arch_mmap_rnd(void) { - unsigned long rnd = get_random_int(); + unsigned long rnd = 0; + + if (current->flags & PF_RANDOMIZE) + rnd = get_random_int(); rnd = rnd << PAGE_SHIFT; /* 8MB for 32bit, 256MB for 64bit */ @@ -183,7 +186,7 @@ unsigned long arch_randomize_brk(struct mm_struct *mm) unsigned long base = mm->brk; unsigned long ret; - ret = PAGE_ALIGN(base + brk_rnd()); + ret = PA