diff options
author | Sergey Bugaev <bugaevc@gmail.com> | 2024-04-05 18:18:48 +0300 |
---|---|---|
committer | Samuel Thibault <samuel.thibault@ens-lyon.org> | 2024-04-05 17:43:14 +0200 |
commit | 7b87e10b89a190bca0d9e6c5e183984411840dc3 (patch) | |
tree | 35bc4fdf954d040e7bbe7ae77e56fe44017957f9 /vm/vm_init.c | |
parent | df19628b2b6665468e698e290dfd1568720ba042 (diff) | |
download | gnumach-7b87e10b89a190bca0d9e6c5e183984411840dc3.tar.gz gnumach-7b87e10b89a190bca0d9e6c5e183984411840dc3.tar.bz2 gnumach-7b87e10b89a190bca0d9e6c5e183984411840dc3.zip |
vm: Fix use-after-free in vm_map_pageable_scan()
When operating on the kernel map, vm_map_pageable_scan() does what
the code itself describes as "HACK HACK HACK HACK": it unlocks the map,
and calls vm_fault_wire() with the map unlocked. This hack is required
to avoid a deadlock in case vm_fault or one of its callees (perhaps, a
pager) needs to allocate memory in the kernel map. The hack relies on
other kernel code being "well-behaved", in particular on that nothing
will do any serious changes to this region of memory while the map is
unlocked, since this region of memory is "owned" by the caller.
This reasoning doesn't apply to the validity of the 'end' entry (the
first entry after the region to be wired), since it's not a part of the
region, and is "owned" by someone else. Once the map is unlocked, the
'end' entry could get deallocated. Alternatively, a different entry
could get inserted after the VM region in front of 'end', which would
break the 'for (entry = start; entry != end; entry = entry->vme_next)'
loop condition.
This was not an issue in the original Mach 3 kernel, since it used an
address range check for the loop condition, but got broken in commit
023401c5b97023670a44059a60eb2a3a11c8a929 "VM: rework map entry wiring".
Fix this by switching the iteration back to use an address check.
This partly fixes a deadlock with concurrent mach_port_names() calls on
SMP, which was
Reported-by: Damien Zammit <damien@zamaudio.com>
Message-ID: <20240405151850.41633-1-bugaevc@gmail.com>
Diffstat (limited to 'vm/vm_init.c')
0 files changed, 0 insertions, 0 deletions