Skip to content

feat(libSceAgc): implement the marker span builders - #971

Closed
hugodearaujo wants to merge 1 commit into
boykopovar:mainfrom
hugodearaujo:feat/agc-marker-span
Closed

hugodearaujo wants to merge 1 commit into
boykopovar:mainfrom
hugodearaujo:feat/agc-marker-span

Conversation

@hugodearaujo

Copy link
Copy Markdown
Contributor

What

sceAgcDcbPushMarkerSpan, sceAgcDcbSetMarkerSpan, sceAgcAcbPushMarkerSpan and sceAgcAcbSetMarkerSpan threw. They now write the same packets as the existing push and set markers, but take the text as (text, length) instead of a NUL-terminated string:

  • Push: one custom NOP push packet with the length bytes, NUL-terminated and zero-padded to a dword.
  • Set: that push packet followed by a pop, returning the push packet, as sceAgcDcbSetMarker does.
  • Color: not encoded, as in the other markers.

Agc::Marker::Push now calls a new Agc::Marker::PushSpan with strlen, so its packets are unchanged.

Invalid input throws and leaves the buffer untouched: a null buffer, null text with a non-zero length, or a span over 0xfffc bytes (the existing 0x4000-dword payload limit).

The signature (buffer, text, length, color) comes from the clean-room OpenAGC, the only reference that has these functions. OpenAGC's packet layout differs from the one AnyPS5 uses for markers: it writes the color as the first payload dword and no terminator. I kept AnyPS5's layout so all markers stay consistent. Both points are under "Unknown function info" in TechnicalDebt.

Tested

Linux (Arch, GCC), Release with BUILD_TESTING=ON, on current main.

agc_command_tests only runs its defaults mode under ctest, and its full mode already fails on main ("expected an exception"). The new cases therefore go in a separate agc_marker_span_tests, built from sources like agc_cond_exec_patch_tests. For the DCB and ACB variants it checks:

  • a 5-byte span of a longer string is cut and terminated;
  • the span packet is identical to sceAgcDcbPushMarker with the same text;
  • an 8-byte span gets its own terminator dword;
  • an empty span with null text works;
  • 0xfffc bytes fit exactly and 0x10000 is rejected;
  • Set is followed by a pop and returns the push packet;
  • invalid input throws without moving the cursor.

Six mutations each make the test fail: the whole string copied instead of the span, the null check removed, the length limit removed, the pop dropped from DCB Set, the pop dropped from ACB Set, and ACB Push ignoring the length.

Full ctest: 360/360 passed. A simulated merge with every open PR shows no conflict caused by this branch. Not tested with a title.

tools/progress.py --compare against main: System libraries 87.14% (+0.14%, +4 implemented functions).

Checklist

  • Based on current main; no other open PR implements the same functions
  • One topic per PR; follow-ups go in a new PR
  • No comments in code except technical debt
  • Unimplemented paths throw (NotImplemented_nid_no_patch); silent stubs are listed in TechnicalDebt
  • No notes, investigation .md files or images added to the repository (attach them to this PR)
  • New third-party code is a submodule built from source
  • Generic behaviour, not specific to one title
  • Depends on: none
  • AI-assisted: yes

🤖 Generated with Claude Code

sceAgcDcbPushMarkerSpan, sceAgcDcbSetMarkerSpan, sceAgcAcbPushMarkerSpan
and sceAgcAcbSetMarkerSpan write the same packets as the push and set
markers, with the text taken from an explicit length instead of a
NUL-terminated string.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
@hugodearaujo

Copy link
Copy Markdown
Contributor Author

Usage by titles: PS5PCEM agc_table.zig, "generated from the identifiers a shipped title imports", binds all four (sceAgcDcbPushMarkerSpan, sceAgcDcbSetMarkerSpan, sceAgcAcbPushMarkerSpan, sceAgcAcbSetMarkerSpan), but it does not name the title. I have no title ID beyond that.

@oneandonlydean

Copy link
Copy Markdown
Collaborator

Thanks for the clear write-up, and for recording the OpenAGC layout difference in TechnicalDebt.

Which title calls the marker span builders? The description says it wasn't tested with a title, and none of the four is imported by the titles we test with. If you know of a caller (an executable or engine module that imports one of these NIDs), please name it, since that's the main reason to replace a throw with a guessed packet layout.

Separately, the description says agc_command_tests in its full mode already fails on main ("expected an exception"). Could you open an issue with the failing case? That deserves a look of its own.

@oneandonlydean

Copy link
Copy Markdown
Collaborator

Thanks, and sorry: I asked before I'd seen your note. The PS5PCEM table doesn't name the title, so this one is weaker than #975: today a title that calls a marker span builder stops with a clear message. If you come across the title (or an engine module that imports one of the four NIDs), please add it here.

The agc_command_tests full-mode failure on main is still worth an issue of its own, whatever happens to this PR.

@github-actions

github-actions Bot commented Oct 6, 2026

Copy link
Copy Markdown

Progress report (e323c1f → 3e9f71c)

📈 System libraries: 86.89% (+0.14%, +4 implemented functions)

✅ 4 implemented
Library Name
libSceAgc sceAgcAcbPushMarkerSpan
libSceAgc sceAgcAcbSetMarkerSpan
libSceAgc sceAgcDcbPushMarkerSpan
libSceAgc sceAgcDcbSetMarkerSpan

@hugodearaujo

Copy link
Copy Markdown
Contributor Author

More on callers. I found two observations of real executables importing them, but neither names the title:

  • ShadPS5 reloc_summary.txt is the GOT of a PS5 main executable as its loader resolved it. It has all four: BYcSvEsINWU (sceAgcDcbSetMarkerSpan), 8Kly1JrJUlw (sceAgcAcbPushMarkerSpan), N7M3+N-sBCw (sceAgcDcbPushMarkerSpan) and pxx-GoOSdw4 (sceAgcAcbSetMarkerSpan).
  • The PS5PCEM entries come from e04956bf8d, which adds them so that "both graphics libraries now resolve completely for the title under test".

REmu also builds them, and keeps its payload compatible with the markers that take a NUL-terminated string, as this PR does.

So at least one shipped executable imports each of the four NIDs, but I still can't give a title ID. I'll leave it here unless I find one.

@github-actions

github-actions Bot commented Oct 7, 2026 •

Copy link
Copy Markdown

Other open pull requests touch the same code. Merging one will break the other, or both implement the same thing. If this one builds on them, list them in Depends on.

Pull request Conflicting files (lines on main) Same exports Same new files
#1060 core/libs/prx/libSceAgc/Unimplemented.cpp L33-47
#1215 docs/dev/TechnicalDebt.md L83-84

@hugodearaujo

Copy link
Copy Markdown
Contributor Author

I checked a dump of Propagation: Paradise Hotel (PPSA15878), the title the PS5PCEM table seemed to point to. It doesn't support this PR:

  • It imports the functions. eboot.bin imports all four marker span NIDs, and its bundled libSceJobManager.prx imports the two ACB ones.
  • It never calls them. Each import is reached only through a one-instruction jmp thunk, and none of the four thunks is called or referenced anywhere: no call/jmp, no RIP-relative reference, no pointer. The same check finds 5 call sites for the sceAgcDcbPushMarker thunk in the executable and 3 for sceAgcAcbPushMarker in libSceJobManager.prx. The span variants are linked in from the SDK but unused.
  • It doesn't start on main. It fails before running: error while loading shared libraries: libSceHmd2.prx.

So this title would never stop at a marker span function, and the PS5PCEM table only shows imports. I have no title that calls them. Feel free to close this. I'll reopen it with the title ID and the log line if I find one that stops here.

@oneandonlydean

Copy link
Copy Markdown
Collaborator

Closing as agreed: PPSA15878 imports the four span builders but never calls them, and no other title is known to. If you find one that stops at one of them on main, comment here with the title ID and the log line.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants