Provide 8 more bits of stack randomization, from the PaX author.

While here, don't make too much use of one random value, and call
arc4random() directly. Allows for the removal of 'ep_random' from the
exec_package.

Prompted by and okay christos@.
This commit is contained in:
elad 2007-12-28 17:14:50 +00:00
parent ca5bc82dc2
commit 0f25f24ed8
4 changed files with 19 additions and 17 deletions

View File

@ -1,4 +1,4 @@
/* $NetBSD: exec_elf32.c,v 1.129 2007/12/27 15:21:52 elad Exp $ */ /* $NetBSD: exec_elf32.c,v 1.130 2007/12/28 17:14:50 elad Exp $ */
/*- /*-
* Copyright (c) 1994, 2000, 2005 The NetBSD Foundation, Inc. * Copyright (c) 1994, 2000, 2005 The NetBSD Foundation, Inc.
@ -64,7 +64,7 @@
*/ */
#include <sys/cdefs.h> #include <sys/cdefs.h>
__KERNEL_RCSID(1, "$NetBSD: exec_elf32.c,v 1.129 2007/12/27 15:21:52 elad Exp $"); __KERNEL_RCSID(1, "$NetBSD: exec_elf32.c,v 1.130 2007/12/28 17:14:50 elad Exp $");
/* If not included by exec_elf64.c, ELFSIZE won't be defined. */ /* If not included by exec_elf64.c, ELFSIZE won't be defined. */
#ifndef ELFSIZE #ifndef ELFSIZE
@ -130,6 +130,7 @@ pax_aslr_elf(struct lwp *l, struct exec_package *epp, Elf_Ehdr *eh,
Elf_Phdr *ph) Elf_Phdr *ph)
{ {
size_t pax_align = 0, pax_offset, i; size_t pax_align = 0, pax_offset, i;
uint32_t r;
if (!pax_aslr_active(l)) if (!pax_aslr_active(l))
return; return;
@ -144,14 +145,16 @@ pax_aslr_elf(struct lwp *l, struct exec_package *epp, Elf_Ehdr *eh,
break; break;
} }
r = arc4random();
if (pax_align == 0) if (pax_align == 0)
pax_align = PGSHIFT; pax_align = PGSHIFT;
#ifdef DEBUG_ASLR #ifdef DEBUG_ASLR
uprintf("r=0x%x a=0x%x p=0x%x Delta=0x%lx\n", epp->ep_random, uprintf("r=0x%x a=0x%x p=0x%x Delta=0x%lx\n", r,
ilog2(pax_align), PGSHIFT, PAX_ASLR_DELTA(epp->ep_random, ilog2(pax_align), PGSHIFT, PAX_ASLR_DELTA(r,
ilog2(pax_align), PAX_ASLR_DELTA_EXEC_LEN)); ilog2(pax_align), PAX_ASLR_DELTA_EXEC_LEN));
#endif #endif
pax_offset = ELF_TRUNC(PAX_ASLR_DELTA(epp->ep_random, pax_offset = ELF_TRUNC(PAX_ASLR_DELTA(r,
ilog2(pax_align), PAX_ASLR_DELTA_EXEC_LEN), pax_align); ilog2(pax_align), PAX_ASLR_DELTA_EXEC_LEN), pax_align);
for (i = 0; i < eh->e_phnum; i++) for (i = 0; i < eh->e_phnum; i++)

View File

@ -1,4 +1,4 @@
/* $NetBSD: kern_exec.c,v 1.261 2007/12/26 22:49:19 xtraeme Exp $ */ /* $NetBSD: kern_exec.c,v 1.262 2007/12/28 17:14:50 elad Exp $ */
/*- /*-
* Copyright (C) 1993, 1994, 1996 Christopher G. Demetriou * Copyright (C) 1993, 1994, 1996 Christopher G. Demetriou
@ -33,7 +33,7 @@
*/ */
#include <sys/cdefs.h> #include <sys/cdefs.h>
__KERNEL_RCSID(0, "$NetBSD: kern_exec.c,v 1.261 2007/12/26 22:49:19 xtraeme Exp $"); __KERNEL_RCSID(0, "$NetBSD: kern_exec.c,v 1.262 2007/12/28 17:14:50 elad Exp $");
#include "opt_ktrace.h" #include "opt_ktrace.h"
#include "opt_syscall_debug.h" #include "opt_syscall_debug.h"
@ -297,11 +297,6 @@ check_exec(struct lwp *l, struct exec_package *epp)
goto bad2; goto bad2;
epp->ep_hdrvalid = epp->ep_hdrlen - resid; epp->ep_hdrvalid = epp->ep_hdrlen - resid;
#ifdef PAX_ASLR
/* Generate random seed to be used. */
epp->ep_random = arc4random();
#endif /* PAX_ASLR */
/* /*
* Set up default address space limits. Can be overridden * Set up default address space limits. Can be overridden
* by individual exec packages. * by individual exec packages.
@ -610,6 +605,11 @@ execve1(struct lwp *l, const char *path, char * const *args,
szsigcode + sizeof(struct ps_strings) + STACK_PTHREADSPACE) szsigcode + sizeof(struct ps_strings) + STACK_PTHREADSPACE)
- argp; - argp;
#ifdef PAX_ASLR
if (pax_aslr_active(l))
len += (arc4random() % PAGE_SIZE);
#endif /* PAX_ASLR */
#ifdef STACKLALIGN /* arm, etc. */ #ifdef STACKLALIGN /* arm, etc. */
len = STACKALIGN(len); /* make the stack "safely" aligned */ len = STACKALIGN(len); /* make the stack "safely" aligned */
#else #else

View File

@ -1,4 +1,4 @@
/* $NetBSD: kern_pax.c,v 1.19 2007/12/27 15:21:53 elad Exp $ */ /* $NetBSD: kern_pax.c,v 1.20 2007/12/28 17:14:51 elad Exp $ */
/*- /*-
* Copyright (c) 2006 Elad Efrat <elad@NetBSD.org> * Copyright (c) 2006 Elad Efrat <elad@NetBSD.org>
@ -28,7 +28,7 @@
*/ */
#include <sys/cdefs.h> #include <sys/cdefs.h>
__KERNEL_RCSID(0, "$NetBSD: kern_pax.c,v 1.19 2007/12/27 15:21:53 elad Exp $"); __KERNEL_RCSID(0, "$NetBSD: kern_pax.c,v 1.20 2007/12/28 17:14:51 elad Exp $");
#include "opt_pax.h" #include "opt_pax.h"
@ -394,7 +394,7 @@ void
pax_aslr_stack(struct lwp *l, struct exec_package *epp, u_long *max_stack_size) pax_aslr_stack(struct lwp *l, struct exec_package *epp, u_long *max_stack_size)
{ {
if (pax_aslr_active(l)) { if (pax_aslr_active(l)) {
u_long d = PAX_ASLR_DELTA(epp->ep_random, u_long d = PAX_ASLR_DELTA(arc4random(),
PAX_ASLR_DELTA_STACK_LSB, PAX_ASLR_DELTA_STACK_LSB,
PAX_ASLR_DELTA_STACK_LEN); PAX_ASLR_DELTA_STACK_LEN);
#ifdef DEBUG_ASLR #ifdef DEBUG_ASLR

View File

@ -1,4 +1,4 @@
/* $NetBSD: exec.h,v 1.119 2007/12/26 22:11:52 christos Exp $ */ /* $NetBSD: exec.h,v 1.120 2007/12/28 17:14:50 elad Exp $ */
/*- /*-
* Copyright (c) 1992, 1993 * Copyright (c) 1992, 1993
@ -203,7 +203,6 @@ struct exec_package {
struct vnode *ep_interp; /* vnode of (elf) interpeter */ struct vnode *ep_interp; /* vnode of (elf) interpeter */
uint32_t ep_pax_flags; /* pax flags */ uint32_t ep_pax_flags; /* pax flags */
char *ep_path; /* absolute path of executable */ char *ep_path; /* absolute path of executable */
uint32_t ep_random; /* random seed for PaX ASLR */
}; };
#define EXEC_INDIR 0x0001 /* script handling already done */ #define EXEC_INDIR 0x0001 /* script handling already done */
#define EXEC_HASFD 0x0002 /* holding a shell script */ #define EXEC_HASFD 0x0002 /* holding a shell script */