Page Menu
Home
FreeBSD
Search
Configure Global Search
Log In
Files
F167047347
D28050.id82086.diff
No One
Temporary
Actions
View File
Edit File
Delete File
View Transforms
Subscribe
Mute Notifications
Flag For Later
Award Token
Size
3 KB
Referenced Files
None
Subscribers
None
D28050.id82086.diff
View Options
diff --git a/sys/kern/imgact_elf.c b/sys/kern/imgact_elf.c
--- a/sys/kern/imgact_elf.c
+++ b/sys/kern/imgact_elf.c
@@ -190,6 +190,11 @@
CTLFLAG_RWTUN, &__elfN(sigfastblock), 0,
"enable sigfastblock for new processes");
+static bool __elfN(allow_wx) = true;
+SYSCTL_BOOL(__CONCAT(_kern_elf, __ELF_WORD_SIZE), OID_AUTO, allow_wx,
+ CTLFLAG_RWTUN, &__elfN(allow_wx), 0,
+ "Allow pages to be mapped simultaneously writable and executable");
+
static Elf_Brandinfo *elf_brand_list[MAX_BRANDS];
#define aligned(a, t) (rounddown2((u_long)(a), sizeof(t)) == (u_long)(a))
@@ -1237,6 +1242,9 @@
imgp->map_flags |= MAP_ASLR_IGNSTART;
}
+ if (!__elfN(allow_wx) && (fctl0 & NT_FREEBSD_FCTL_WXNEEDED) == 0)
+ imgp->map_flags |= MAP_WXORX;
+
error = exec_new_vmspace(imgp, sv);
vmspace = imgp->proc->p_vmspace;
map = &vmspace->vm_map;
diff --git a/sys/kern/kern_exec.c b/sys/kern/kern_exec.c
--- a/sys/kern/kern_exec.c
+++ b/sys/kern/kern_exec.c
@@ -1043,6 +1043,7 @@
struct rlimit rlim_stack;
vm_offset_t sv_minuser, stack_addr;
vm_map_t map;
+ vm_prot_t stack_prot;
u_long ssiz;
imgp->vmspace_destroyed = 1;
@@ -1074,12 +1075,12 @@
pmap_remove_pages(vmspace_pmap(vmspace));
vm_map_remove(map, vm_map_min(map), vm_map_max(map));
/*
- * An exec terminates mlockall(MCL_FUTURE), ASLR state
- * must be re-evaluated.
+ * An exec terminates mlockall(MCL_FUTURE).
+ * ASLR and W^X states must be re-evaluated.
*/
vm_map_lock(map);
vm_map_modflags(map, 0, MAP_WIREFUTURE | MAP_ASLR |
- MAP_ASLR_IGNSTART);
+ MAP_ASLR_IGNSTART | MAP_WXORX);
vm_map_unlock(map);
} else {
error = vmspace_exec(p, sv_minuser, sv->sv_maxuser);
@@ -1126,11 +1127,16 @@
if (ssiz < imgp->eff_stack_sz)
imgp->eff_stack_sz = ssiz;
stack_addr = sv->sv_usrstack - ssiz;
- error = vm_map_stack(map, stack_addr, (vm_size_t)ssiz,
- obj != NULL && imgp->stack_prot != 0 ? imgp->stack_prot :
- sv->sv_stackprot, VM_PROT_ALL, MAP_STACK_GROWS_DOWN);
- if (error != KERN_SUCCESS)
+ stack_prot = obj != NULL && imgp->stack_prot != 0 ?
+ imgp->stack_prot :sv->sv_stackprot;
+ error = vm_map_stack(map, stack_addr, (vm_size_t)ssiz, stack_prot,
+ VM_PROT_ALL, MAP_STACK_GROWS_DOWN);
+ if (error != KERN_SUCCESS) {
+ uprintf("exec_new_vmspace: mapping stack size %#jx prot %#x "
+ "failed mach error %d errno %d\n", (uintmax_t)ssiz,
+ stack_prot, error, vm_mmap_to_errno(error));
return (vm_mmap_to_errno(error));
+ }
/*
* vm_ssize and vm_maxsaddr are somewhat antiquated concepts, but they
diff --git a/sys/vm/vm_map.h b/sys/vm/vm_map.h
--- a/sys/vm/vm_map.h
+++ b/sys/vm/vm_map.h
@@ -228,6 +228,7 @@
#define MAP_ASLR 0x08 /* enabled ASLR */
#define MAP_ASLR_IGNSTART 0x10
#define MAP_REPLENISH 0x20
+#define MAP_WXORX 0x40 /* enforce W^X */
#ifdef _KERNEL
#if defined(KLD_MODULE) && !defined(KLD_TIED)
diff --git a/sys/vm/vm_map.c b/sys/vm/vm_map.c
--- a/sys/vm/vm_map.c
+++ b/sys/vm/vm_map.c
@@ -1671,6 +1671,10 @@
if (start == end || !vm_map_range_valid(map, start, end))
return (KERN_INVALID_ADDRESS);
+ if ((map->flags & MAP_WXORX) != 0 && (prot & (VM_PROT_WRITE |
+ VM_PROT_EXECUTE)) == (VM_PROT_WRITE | VM_PROT_EXECUTE))
+ return (KERN_PROTECTION_FAILURE);
+
/*
* Find the entry prior to the proposed starting address; if it's part
* of an existing entry, this range is bogus.
@@ -2751,6 +2755,13 @@
in_tran = NULL;
vm_map_lock(map);
+ if ((map->flags & MAP_WXORX) != 0 && (new_prot &
+ (VM_PROT_WRITE | VM_PROT_EXECUTE)) == (VM_PROT_WRITE |
+ VM_PROT_EXECUTE)) {
+ vm_map_unlock(map);
+ return (KERN_PROTECTION_FAILURE);
+ }
+
/*
* Ensure that we are not concurrently wiring pages. vm_map_wire() may
* need to fault pages into the map and will drop the map lock while
File Metadata
Details
Attached
Mime Type
text/plain
Expires
Wed, Aug 19, 7:29 PM (6 h, 10 m)
Storage Engine
blob
Storage Format
Raw Data
Storage Handle
36951729
Default Alt Text
D28050.id82086.diff (3 KB)
Attached To
Mode
D28050: Implement enforcing write XOR execute mapping policy.
Attached
Detach File
Event Timeline
Log In to Comment