kern/181497: ASLR Feature Request - patch included

Oliver Pinter oliver.pntr at gmail.com
Sat Aug 24 21:40:16 UTC 2013


performance test on HEAD from Juni + ASLR patches:
http://centaur.sch.bme.hu/~oliverp/hunger/new/

On 8/24/13, Steven Lee <steven at roothosts.com> wrote:
> The following reply was made to PR kern/181497; it has been noted by GNATS.
>
> From: Steven Lee <steven at roothosts.com>
> To: Oliver Pinter <oliver.pntr at gmail.com>,
>  freebsd-gnats-submit at freebsd.org
> Cc:
> Subject: Re: kern/181497: ASLR Feature Request - patch included
> Date: Sat, 24 Aug 2013 14:49:03 -0600
>
>  Wow... very nice. :)
>
>  On 13-08-24 07:48 AM, Oliver Pinter wrote:
>  > new version of the patchset:
>  >
> https://github.com/opntr/freebsd-patches-2013-tavasz/tree/master/r249952+ASLR
>  >
>  > On 8/24/13, Steven Lee <steven at roothosts.com> wrote:
>  >>
>  >>> Number:         181497
>  >>> Category:       kern
>  >>> Synopsis:       ASLR Feature Request - patch included
>  >>> Confidential:   no
>  >>> Severity:       non-critical
>  >>> Priority:       low
>  >>> Responsible:    freebsd-bugs
>  >>> State:          open
>  >>> Quarter:
>  >>> Keywords:
>  >>> Date-Required:
>  >>> Class:          change-request
>  >>> Submitter-Id:   current-users
>  >>> Arrival-Date:   Sat Aug 24 02:20:00 UTC 2013
>  >>> Closed-Date:
>  >>> Last-Modified:
>  >>> Originator:     Steven Lee
>  >>> Release:        releng/9.2
>  >>> Organization:
>  >> Root Hosts
>  >>> Environment:
>  >> N/A
>  >>> Description:
>  >> Most modern operating systems have ASLR to help mitigate yet-unknown
>  >> vulnerabilities.
>  >>
>  >> It would be very nice if FreeBSD shipped with ASLR features in the
> kernel
>  >> (default off), that could be easily switched on with a sysctl variable.
>  >>
>  >> I understand that in some production environments ASLR may make a
> system
>  >> slower through memory fragmentation, but at least give people the option
> to
>  >> turn ASLR on for those who actually want it. :)
>  >>
>  >>> How-To-Repeat:
>  >> N/A
>  >>> Fix:
>  >> This patch has been circulating the internet since FreeBSD 7.0-RELEASE
> at
>  >> least. It looks like parts of it are from OpenBSD? (I could be wrong.)
> I've
>  >> used it in production for many many years and it works like a champ.
>  >>
>  >> The patch will just need the sysctl defaults inverted and the variable
> names
>  >> possibly renamed for clarity.
>  >>
>  >>
>  >> Patch attached with submission follows:
>  >>
>  >> commit 779a962519e7ead63dda24348b98f6cde8156752
>  >> Author: Oliver Pinter <opn at opn.(none)>
>  >> Date:   Tue Oct 4 00:24:01 2011 +0200
>  >>
>  >>     forwardport mmap-randomization patch from 7-STABLE-op
>  >>
>  >>     Signed-off-by: Oliver Pinter <oliver.pntr at gmail.com>
>  >>
>  >> diff --git a/sys/kern/kern_exec.c b/sys/kern/kern_exec.c
>  >> index fe01142..dc66db6 100644
>  >> --- a/sys/kern/kern_exec.c
>  >> +++ b/sys/kern/kern_exec.c
>  >> @@ -106,6 +106,7 @@ MALLOC_DEFINE(M_PARGS, "proc-args", "Process
>  >> arguments");
>  >>  static int sysctl_kern_ps_strings(SYSCTL_HANDLER_ARGS);
>  >>  static int sysctl_kern_usrstack(SYSCTL_HANDLER_ARGS);
>  >>  static int sysctl_kern_stackprot(SYSCTL_HANDLER_ARGS);
>  >> +static int sysctl_kern_stackgap_random(SYSCTL_HANDLER_ARGS);
>  >>  static int do_execve(struct thread *td, struct image_args *args,
>  >>      struct mac *mac_p);
>  >>
>  >> @@ -120,6 +121,9 @@ SYSCTL_PROC(_kern, KERN_USRSTACK, usrstack,
>  >> CTLTYPE_ULONG|CTLFLAG_RD|
>  >>  SYSCTL_PROC(_kern, OID_AUTO, stackprot, CTLTYPE_INT|CTLFLAG_RD,
>  >>      NULL, 0, sysctl_kern_stackprot, "I", "");
>  >>
>  >> +SYSCTL_PROC(_kern, OID_AUTO, stackgap_random, CTLTYPE_INT|CTLFLAG_RW,
>  >> +    NULL, 0, sysctl_kern_stackgap_random, "I", "stackgap maximum
> offset");
>  >> +
>  >>  u_long ps_arg_cache_limit = PAGE_SIZE / 16;
>  >>  SYSCTL_ULONG(_kern, OID_AUTO, ps_arg_cache_limit, CTLFLAG_RW,
>  >>      &ps_arg_cache_limit, 0, "");
>  >> @@ -177,6 +181,30 @@ sysctl_kern_stackprot(SYSCTL_HANDLER_ARGS)
>  >>  	    sizeof(p->p_sysent->sv_stackprot)));
>  >>  }
>  >>
>  >> +static int	stackgap_random = 64 * 1024;
>  >> +
>  >> +static int
>  >> +sysctl_kern_stackgap_random(SYSCTL_HANDLER_ARGS)
>  >> +{
>  >> +	int	err;
>  >> +	int	val;
>  >> +
>  >> +	val=stackgap_random;
>  >> +	err=sysctl_handle_int(oidp, &val, sizeof(int), req);
>  >> +	if (err || !req->newptr) {
>  >> +		return (err);
>  >> +	}
>  >> +
>  >> +	if ((val<ALIGNBYTES && (val!=0))
>  >> +	    || !powerof2(val) || val>64*1024*1024) {
>  >> +		return (EINVAL);
>  >> +	}
>  >> +
>  >> +	stackgap_random=val;
>  >> +
>  >> +	return (0);
>  >> +}
>  >> +
>  >>  /*
>  >>   * Each of the items is a pointer to a `const struct execsw', hence
> the
>  >>   * double pointer here.
>  >> @@ -1248,6 +1276,7 @@ exec_copyout_strings(imgp)
>  >>  	size_t execpath_len;
>  >>  	int szsigcode, szps;
>  >>  	char canary[sizeof(long) * 8];
>  >> +	int sgap;
>  >>
>  >>  	szps = sizeof(pagesizes[0]) * MAXPAGESIZES;
>  >>  	/*
>  >> @@ -1265,7 +1294,11 @@ exec_copyout_strings(imgp)
>  >>  		if (p->p_sysent->sv_szsigcode != NULL)
>  >>  			szsigcode = *(p->p_sysent->sv_szsigcode);
>  >>  	}
>  >> -	destp =	(caddr_t)arginfo - szsigcode - SPARE_USRSPACE -
>  >> +	sgap=0;
>  >> +	if (stackgap_random!=0) {
>  >> +		sgap=ALIGN(arc4random()&(stackgap_random-1));
>  >> +	}
>  >> +	destp =	(caddr_t)arginfo - szsigcode - SPARE_USRSPACE - sgap -
>  >>  	    roundup(execpath_len, sizeof(char *)) -
>  >>  	    roundup(sizeof(canary), sizeof(char *)) -
>  >>  	    roundup(szps, sizeof(char *)) -
>  >> diff --git a/sys/vm/vm_mmap.c b/sys/vm/vm_mmap.c
>  >> index e85b681..991a37d 100644
>  >> --- a/sys/vm/vm_mmap.c
>  >> +++ b/sys/vm/vm_mmap.c
>  >> @@ -68,6 +68,7 @@ __FBSDID("$FreeBSD$");
>  >>  #include <sys/stat.h>
>  >>  #include <sys/sysent.h>
>  >>  #include <sys/vmmeter.h>
>  >> +#include <sys/sysctl.h>
>  >>
>  >>  #include <security/mac/mac_framework.h>
>  >>
>  >> @@ -99,6 +100,10 @@ static int vm_mmap_cdev(struct thread *, vm_size_t,
>  >> vm_prot_t, vm_prot_t *,
>  >>  static int vm_mmap_shm(struct thread *, vm_size_t, vm_prot_t, vm_prot_t
> *,
>  >>      int *, struct shmfd *, vm_ooffset_t, vm_object_t *);
>  >>
>  >> +static int mmap_random=1;
>  >> +SYSCTL_INT(_vm, OID_AUTO, mmap_random, CTLFLAG_RW, &mmap_random, 0,
>  >> +		"random mmap offset");
>  >> +
>  >>  /*
>  >>   * MPSAFE
>  >>   */
>  >> @@ -256,7 +261,8 @@ sys_mmap(td, uap)
>  >>  		/*
>  >>  		 * XXX for non-fixed mappings where no hint is provided or
>  >>  		 * the hint would fall in the potential heap space,
>  >> -		 * place it after the end of the largest possible heap.
>  >> +		 * place it after the end of the largest possible heap,
>  >> +		 * plus a random offset, if mmap_random is set.
>  >>  		 *
>  >>  		 * There should really be a pmap call to determine a reasonable
>  >>  		 * location.
>  >> @@ -265,9 +271,13 @@ sys_mmap(td, uap)
>  >>  		if (addr == 0 ||
>  >>  		    (addr >= round_page((vm_offset_t)vms->vm_taddr) &&
>  >>  		    addr < round_page((vm_offset_t)vms->vm_daddr +
>  >> -		    lim_max(td->td_proc, RLIMIT_DATA))))
>  >> +		    lim_max(td->td_proc, RLIMIT_DATA)))) {
>  >>  			addr = round_page((vm_offset_t)vms->vm_daddr +
>  >>  			    lim_max(td->td_proc, RLIMIT_DATA));
>  >> +			if (mmap_random) {
>  >> +				addr+=arc4random()&(256*1024*1024-1);
>  >> +			}
>  >> +		}
>  >>  		PROC_UNLOCK(td->td_proc);
>  >>  	}
>  >>  	if (flags & MAP_ANON) {
>  >>
>  >>> Release-Note:
>  >>> Audit-Trail:
>  >>> Unformatted:
>  >> _______________________________________________
>  >> freebsd-bugs at freebsd.org mailing list
>  >> http://lists.freebsd.org/mailman/listinfo/freebsd-bugs
>  >> To unsubscribe, send any mail to "freebsd-bugs-unsubscribe at freebsd.org"
>  >>
>
>  --
>  Regards,
>  Steven Lee
>
> _______________________________________________
> freebsd-bugs at freebsd.org mailing list
> http://lists.freebsd.org/mailman/listinfo/freebsd-bugs
> To unsubscribe, send any mail to "freebsd-bugs-unsubscribe at freebsd.org"
>


More information about the freebsd-bugs mailing list