Module Name: src Committed By: christos Date: Wed May 25 17:25:32 UTC 2016
Modified Files: src/sys/kern: exec_elf.c kern_pax.c src/sys/sys: pax.h Log Message: randomize the location of the rtld. To generate a diff of this commit: cvs rdiff -u -r1.84 -r1.85 src/sys/kern/exec_elf.c cvs rdiff -u -r1.50 -r1.51 src/sys/kern/kern_pax.c cvs rdiff -u -r1.21 -r1.22 src/sys/sys/pax.h Please note that diffs are not public domain; they are subject to the copyright notices on the relevant files.
Modified files: Index: src/sys/kern/exec_elf.c diff -u src/sys/kern/exec_elf.c:1.84 src/sys/kern/exec_elf.c:1.85 --- src/sys/kern/exec_elf.c:1.84 Sun May 22 10:26:09 2016 +++ src/sys/kern/exec_elf.c Wed May 25 13:25:32 2016 @@ -1,4 +1,4 @@ -/* $NetBSD: exec_elf.c,v 1.84 2016/05/22 14:26:09 christos Exp $ */ +/* $NetBSD: exec_elf.c,v 1.85 2016/05/25 17:25:32 christos Exp $ */ /*- * Copyright (c) 1994, 2000, 2005, 2015 The NetBSD Foundation, Inc. @@ -57,7 +57,7 @@ */ #include <sys/cdefs.h> -__KERNEL_RCSID(1, "$NetBSD: exec_elf.c,v 1.84 2016/05/22 14:26:09 christos Exp $"); +__KERNEL_RCSID(1, "$NetBSD: exec_elf.c,v 1.85 2016/05/25 17:25:32 christos Exp $"); #ifdef _KERNEL_OPT #include "opt_pax.h" @@ -506,6 +506,8 @@ elf_load_interp(struct lwp *l, struct ex epp->ep_daddr, round_page(limit) - trunc_page(base_ph->p_vaddr), use_topdown); + addr += (Elf_Addr)pax_aslr_rtld_offset(epp, base_ph->p_align, + use_topdown); } else { addr = *last; /* may be ELF_LINK_ADDR */ } Index: src/sys/kern/kern_pax.c diff -u src/sys/kern/kern_pax.c:1.50 src/sys/kern/kern_pax.c:1.51 --- src/sys/kern/kern_pax.c:1.50 Tue May 24 13:30:01 2016 +++ src/sys/kern/kern_pax.c Wed May 25 13:25:32 2016 @@ -1,4 +1,4 @@ -/* $NetBSD: kern_pax.c,v 1.50 2016/05/24 17:30:01 martin Exp $ */ +/* $NetBSD: kern_pax.c,v 1.51 2016/05/25 17:25:32 christos Exp $ */ /* * Copyright (c) 2015 The NetBSD Foundation, Inc. @@ -57,7 +57,7 @@ */ #include <sys/cdefs.h> -__KERNEL_RCSID(0, "$NetBSD: kern_pax.c,v 1.50 2016/05/24 17:30:01 martin Exp $"); +__KERNEL_RCSID(0, "$NetBSD: kern_pax.c,v 1.51 2016/05/25 17:25:32 christos Exp $"); #include "opt_pax.h" @@ -143,7 +143,8 @@ uint32_t pax_aslr_rand; #define PAX_ASLR_STACK_GAP 0x02 #define PAX_ASLR_MMAP 0x04 #define PAX_ASLR_EXEC_OFFSET 0x08 -#define PAX_ASLR_FIXED 0x10 +#define PAX_ASLR_RTLD_OFFSET 0x10 +#define PAX_ASLR_FIXED 0x20 #endif static int pax_segvguard_enabled = 1; @@ -525,22 +526,13 @@ pax_aslr_mmap(struct lwp *l, vaddr_t *ad } } -#define PAX_TRUNC(a, b) ((a) & ~((b) - 1)) -vaddr_t -pax_aslr_exec_offset(struct exec_package *epp, vaddr_t align) +static vaddr_t +pax_aslr_offset(vaddr_t align) { size_t pax_align, l2, delta; uint32_t rand; vaddr_t offset; - if (!pax_aslr_epp_active(epp)) - goto out; - -#ifdef PAX_ASLR_DEBUG - if (pax_aslr_flags & PAX_ASLR_EXEC_OFFSET) - goto out; -#endif - pax_align = align == 0 ? PGSHIFT : align; l2 = ilog2(pax_align); @@ -549,16 +541,52 @@ pax_aslr_exec_offset(struct exec_package if (pax_aslr_flags & PAX_ASLR_FIXED) rand = pax_aslr_rand; #endif + +#define PAX_TRUNC(a, b) ((a) & ~((b) - 1)) + delta = PAX_ASLR_DELTA(rand, l2, PAX_ASLR_DELTA_EXEC_LEN); offset = PAX_TRUNC(delta, pax_align) + PAGE_SIZE; PAX_DPRINTF("rand=%#x l2=%#zx pax_align=%#zx delta=%#zx offset=%#jx", rand, l2, pax_align, delta, (uintmax_t)offset); + return offset; +} + +vaddr_t +pax_aslr_exec_offset(struct exec_package *epp, vaddr_t align) +{ + if (!pax_aslr_epp_active(epp)) + goto out; + +#ifdef PAX_ASLR_DEBUG + if (pax_aslr_flags & PAX_ASLR_EXEC_OFFSET) + goto out; +#endif + return pax_aslr_offset(align) + PAGE_SIZE; out: return MAX(align, PAGE_SIZE); } +voff_t +pax_aslr_rtld_offset(struct exec_package *epp, vaddr_t align, int use_topdown) +{ + voff_t offset; + + if (!pax_aslr_epp_active(epp)) + return 0; + +#ifdef PAX_ASLR_DEBUG + if (pax_aslr_flags & PAX_ASLR_RTLD_OFFSET) + return 0; +#endif + offset = pax_aslr_offset(align); + if (use_topdown) + offset = -offset; + + return offset; +} + void pax_aslr_stack(struct exec_package *epp, u_long *max_stack_size) { Index: src/sys/sys/pax.h diff -u src/sys/sys/pax.h:1.21 src/sys/sys/pax.h:1.22 --- src/sys/sys/pax.h:1.21 Sun May 22 10:26:10 2016 +++ src/sys/sys/pax.h Wed May 25 13:25:32 2016 @@ -1,4 +1,4 @@ -/* $NetBSD: pax.h,v 1.21 2016/05/22 14:26:10 christos Exp $ */ +/* $NetBSD: pax.h,v 1.22 2016/05/25 17:25:32 christos Exp $ */ /*- * Copyright (c) 2006 Elad Efrat <e...@netbsd.org> @@ -86,12 +86,14 @@ void pax_aslr_init_vm(struct lwp *, stru void pax_aslr_stack(struct exec_package *, u_long *); uint32_t pax_aslr_stack_gap(struct exec_package *); vaddr_t pax_aslr_exec_offset(struct exec_package *, vaddr_t); +voff_t pax_aslr_rtld_offset(struct exec_package *, vaddr_t, int); void pax_aslr_mmap(struct lwp *, vaddr_t *, vaddr_t, int); #else # define pax_aslr_init_vm(l, v, e) # define pax_aslr_stack(e, o) # define pax_aslr_stack_gap(e) 0 # define pax_aslr_exec_offset(e, a) MAX(a, PAGE_SIZE) +# define pax_aslr_rtld_offset(e, a, u) 0 # define pax_aslr_mmap(l, a, b, c) #endif