Repository navigation
fix(linux): enter the guest entry on a main stack at the console's address - #7532
hugodearaujo wants to merge 1 commit into
Conversation
|
Some comparisons could not be completed because a pull request conflicts with the base branch. Review these shared files manually before concluding that there is no overlap.
|
|
Thanks, the design looks right, and the stub, the 16-byte alignment and the bounds query all check out. One small safety change before merge: On order: as discussed on #7594, this lands first and #7594 rebases with its MXCSR set before |
|
I reproduced Dean's collision concern and tested the requested exclusive call locally on exact head With soft
The local production change is only: DoMapAnon(&mapping, bytes, 3, GUEST_MAP_FIXED, PS5_PAGE_SIZE, true)Both refused cases report Boundary/guard checks, on both the submitted head and the local proposal: an extension of
All 14 processes pass. Every reported upper bound is
I restored the submitted source; the worktree is clean. The exclusive call above is a tested local proposal, not a pushed change. Generated-input/runtime-helper checks only: no Mirage/title, Windows, ASan-offset or full-suite result. |
What
On Linux the relinked executable entered the title's entry point on the host process stack, near the top of the address space (
0x7ffc...). On the console a process's main thread stack sits inside the user area: a payload on a PS5 (FW 13.60) reports its main thread stack at0x7eedfc000-0x7eeffc000throughpthread_attr_get_np, right above a worker thread's stack at0x7eede8000-0x7eedf8000.When the executable loads
libkernel.prx, its Linux entry stub now callsEnterGuestMainStack_nid_no_patch(libkernel) through aGLOB_DATslot, with the initial stack pointer and the entry point.0x7eeffc000, moved by the arena's offset in ASan builds). Below it is a 16 KiB guard. Its size is the host'sRLIMIT_STACK(8 MiB when unlimited, at most 1 GiB).sceKernelIsStackand the main thread's attributes report that range.libkernel.prxkeeps the stub as it was.#3965 does the same on Windows, with a helper in libc that is built only there.
Title
Assassin's Creed Mirage (PPSA13960, 01.007.000) first stops on
mainat a kevent read event, which #6343 implements. With #6343 applied, it stops with SIGSEGV on the main thread 6 s after start, with nothing in the log.pointer >> 28(eboot0x570b9c1-0x570b9ec).0x7fffffff42c8gives index0x7ffff, so the lookup reads past the table and dereferences what it finds there (0x8232f00).0x7eeffc000, which gives index0x7e.With this PR and #6343 it passes that point and goes through its start-up screens (photosensitivity warning, Ubisoft logo, intro video, disclaimer, autosave notice; screenshots from two runs) to the next unimplemented path:
Tested
PS5 (FW 13.60): a payload prints the address of a local in
main, itspthread_attr_get_npstack range, a worker thread's range, and amallocand anmmapaddress:The runs below are on
main0d078f75d. Each title was relinked twice from the same ELF with the same options, with this PR's relinker: for A it is built with thelibkernel.prxcheck forced off, so the stub ismain's. Both runs of a title use this PR's runtime libraries.Assassin's Creed Mirage, with feat(libkernel): accept a kevent read event on descriptor 0 #6343's
Kqueue.cppchange in libkernel:main.Titles that already ran on
main:CONTROL Resonant's first A run went before B and showed its photosensitivity warning after the script's first press, so it ended one screen behind the script; the A row is a second A run made after B.
guest_main_stack(new, Linux) enters a test entry through the helper and checks:sceKernelIsStackreports a range ending at0x7eeffc000that holds the entry's locals;With
HostStackLimitsas onmainit fails atGuestMainStack.cpp:68.linux_main_stack_entry(new) relinks an executable that loadslibkernel.prxand one that does not, and checks the stub and the imports of both.libkernel.prxwhose helper calls the entry point. The entry exits with itsargcplus 41.libkernel.prxcheck forced off it fails.entry_stubchecks both stubs.Linux (Arch, kernel 7.2.9, GCC 16.2.1, Release, AMD Radeon RX 9070 XT with RADV, Mesa 26.2.4): full CTest with
-j8, 1439 of 1440 pass.agc_driver_tessellationsegfaults the same way without this PR.Windows Server 2025 VM, WinLibs GCC 15.2, Release,
BUILD_TESTING=ON, no GPU: full CTest, 1478 of 1479 pass (agc_driver_gated_dispatch_capture_short_timeoutis skipped there).guest_positioned_closefailed: it fails intermittently onmaintoo, 5 of 30 runs ofmain0d078f75don the same VM. Windows does not use this stub.tools/check_conventions.pypasses.tools/pr_overlap.pylists feat(relinker): support --trace-imports for Linux output #7417:TraceImport_nid_no_patchto the Linux output the same way (an undefined symbol with aGLOB_DATslot) and puts a prologue before the entry stub, so the two change neighbouring lines ofLinuxElfPatcher::Patch. With both symbols and both relocations kept and its prologue falling through to this stub, the merge builds and all 199 relinker tests pass,linux_main_stack_entryandlinux_trace_importsincluded.HostStackLimits: it caches the host stack range the function reads. The guest main stack check runs before that, so the two combine, andgit merge-treemerges them without conflicts.Checklist
main; no other open PR implements the same functionsNotImplemented_nid_no_patch); silent stubs are listed under Silent stubs in their library's technical debt file.mdfiles or images added to the repository (attach them to this PR)🤖 Generated with Claude Code