mirror of
https://github.com/par274/sharpemu.git
synced 2026-07-16 03:00:57 +00:00
Fix macOS exact-address mmap falling back to MAP_FIXED (#214)
The PS5 image loader requires guest images to land at fixed virtual addresses (e.g. the 32 GiB main image base). On macOS the exact-address mmap path only ever passed that address as a hint, never MAP_FIXED, to avoid clobbering untracked host mappings (dyld, JIT heap, Rosetta). On Apple Silicon under Rosetta 2 the kernel does not reliably honor that hint, so the allocation failed deterministically before a single guest instruction ran (reported in #194). Retry with true MAP_FIXED as a fallback only when the hint-only attempt doesn't land at the requested address, so the safer hint path is still tried first.
This commit is contained in:
@@ -271,6 +271,26 @@ internal sealed unsafe class PosixHostMemory : IHostMemory
|
|||||||
|
|
||||||
var exactFlags = OperatingSystem.IsMacOS() ? flags : flags | MAP_FIXED_NOREPLACE;
|
var exactFlags = OperatingSystem.IsMacOS() ? flags : flags | MAP_FIXED_NOREPLACE;
|
||||||
result = mmap((nint)address, (nuint)alignedSize, posixProtect, exactFlags, -1, 0);
|
result = mmap((nint)address, (nuint)alignedSize, posixProtect, exactFlags, -1, 0);
|
||||||
|
if (result != MAP_FAILED && (ulong)result != (ulong)address)
|
||||||
|
{
|
||||||
|
munmap(result, (nuint)alignedSize);
|
||||||
|
result = MAP_FAILED;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (result == MAP_FAILED && OperatingSystem.IsMacOS())
|
||||||
|
{
|
||||||
|
// The hint-only attempt above didn't land at the requested
|
||||||
|
// address. This is routinely the case for the PS5's fixed
|
||||||
|
// 32 GiB image base under Rosetta 2 on Apple Silicon, where
|
||||||
|
// the kernel never honors that hint. Retry with true
|
||||||
|
// MAP_FIXED: this can clobber an untracked host mapping
|
||||||
|
// (dyld, the runtime's JIT heap, Rosetta) if one already
|
||||||
|
// sits exactly there, but without it guest images that
|
||||||
|
// require this base never load at all on macOS.
|
||||||
|
Trace($"exact mmap hint failed, retrying with MAP_FIXED: addr=0x{(ulong)address:X16}");
|
||||||
|
result = mmap((nint)address, (nuint)alignedSize, posixProtect, flags | MAP_FIXED, -1, 0);
|
||||||
|
}
|
||||||
|
|
||||||
if (result == MAP_FAILED || (ulong)result != (ulong)address)
|
if (result == MAP_FAILED || (ulong)result != (ulong)address)
|
||||||
{
|
{
|
||||||
Trace($"exact mmap failed: addr=0x{(ulong)address:X16} got=0x{(ulong)result:X16} size=0x{alignedSize:X} errno={Marshal.GetLastPInvokeError()}");
|
Trace($"exact mmap failed: addr=0x{(ulong)address:X16} got=0x{(ulong)result:X16} size=0x{alignedSize:X} errno={Marshal.GetLastPInvokeError()}");
|
||||||
|
|||||||
Reference in New Issue
Block a user