Repository navigation
Divinity: Original Sin II Definitive Edition (PPSA06866) #13726
XatiX
started this conversation in
Game bring-up
Replies: 0 comments
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Uh oh!
There was an error while loading. Please reload this page.
Uh oh!
There was an error while loading. Please reload this page.
Existing thread: searched this category for PPSA06866 on 2026-10-31; no thread exists.
Title: Divinity: Original Sin II Definitive Edition (PPSA06866, EUR)
Content version tested: 01.007.000
AnyPS5 commit: XatiX/AnyPS5
test/dos2-retestat2e499428ca. This is a test branch, not proposed for merging as it stands. It ismainf776fddcffplus:a90d0b73bb1d48b3aa38abefad201638c1448817987a821acc753642212d8ce0ef80d7357f0a324df3c2705cb83600280d308e9c33442f617f36cd373edfe41acc75364268139cbfacbb3d98869efb11c2675dbc8e544eb02c0c4f9efd2e499428ca#13734 is merged, so blocker 1 is gone from
main. From the order of the stops below,mainwithout these should stop at blocker 2. That was not rerun on thismain.System tested: Windows 11 Pro 10.0.26300, GCC 15.2.0 (WinLibs), RTX 5080 (NVIDIA 617.42), Ryzen 7 9800X3D, 32 GB RAM. Tested 2026-10-31.
Furthest point: In game (host imports on, default settings)
What is shown: in a manual session of 21 minutes on an earlier commit of this work, with no crash and a clean exit, a manual save was written and loaded back, and by the tester's report combat worked and audio appears to work. Saves list correctly with their name, time and version. Before that: boot, title screen, main menu, Campaign, difficulty, character creation, the origin story scene, the intro cinematic, the level load, then the opening in The Hold: Magister Siwan's dialogue, followed by free play with hotbar and minimap. On
456a530efb, before the speed commits, one scripted run of about 570 s and one manual session reached The Hold, with no crash or error in the log. An autosave completed in the manual session (SavetoRunningon client and server). Two scripted runs on the older base also reached The Hold, and three more reached character creation.On
2e499428ca, speed depends on the scene. On a later save in The Hold it runs at about 23 fps (224 to 229 presents per 10 s). The opening scene ran at about 49 fps on an earlier commit, and every speed row below up to the rebase is from that opening scene. The main menu last measured about 15.5 fps, on an earlier commit. These come from scripted runs that stand still with the cursor showing. Pad input works for Cross, Options and L3. In play the title reports lower figures in some screens, such as about 17 fps with the Load menu open.Not tested: everything past The Hold, and combat and audio beyond that one session. Stencil copy values are unverified: the scenes look right, but nothing reads them back and there is no test. Unit test coverage of the publication changes is incomplete, and this branch does not pass every depth publication case. Speed figures are from the run summaries, not
tools/trace_digest.pycomparisons.Current blocker
None stops the title in the tested range. Speed is the main problem now, and it is CPU-bound: on the later save the GPU takes about 16 ms per frame, while
Driver.Packettakes about 43 ms and the committer thread stays busy. See Speed below. Two picture faults remain, listed under Measured. Each stop below was only reached after the one before it was passed.sceHttp2SslEnableOptionon a context handlemainby #13734, confirmed on this titleDB_RENDER_CONTROL0x88 stencil copycannot distinguish an unwritten byte…nvoglv64.dll, about 30 to 33 sguest writes over native multisample depthandpublication captureStrong contenders
Open pull requests that bear on these blockers, checked on 2026-10-31. Findings are posted on each one.
sceHttp2failure withmain's copy (findings)native multisample depth sampled identity or format mismatch. The stencil copy pass itself is still an own commitNo open pull request found for blocker 2 (stencil copy) or blocker 7 (socket forwards). Merged #9515 fixed the same kind of gap for
getsockoptonsceNetSocketsockets, so blocker 7 could follow that pattern.Measured
id=1 kind=0 owner=0 transport=0. NosceHttp2failure with fix(libSceHttp2): accept SSL options on a context #13734.DB_RENDER_CONTROL0x88,DB_DEPTH_CONTROL0,DB_Z_INFO0xa0000187,DB_STENCIL_INFO0x20000181,CB_COLOR0_INFO0x00050c04,CB_TARGET_MASK0x2,CB_SHADER_MASK0x3,SPI_SHADER_COL_FORMAT0x2. The surface is 1920x2160 with 2 samples. Same value on PPSA05666 (feat(agc): run DB depth copies into a single-sample R32 float target #5499, Vr compatibity? #7649).ImportWindowstamps, which set the CPU flag but not the stored flag. Every imported page traced kept its bytes. Publication now checks stores only, through a newNoStoreSinceLastCollect.VK_LAYER_LUNARG_api_dump. On one command buffer:vkCmdBindPipeline,vkEndCommandBuffer,vkQueueSubmit,vkFreeCommandBuffers, thenvkCmdBindDescriptorSets,vkCmdPushConstants,vkCmdDispatchandvkCmdPipelineBarrier, which crashes.recordDispatchcaches the handle, thenShaderResources::BindcallsrequireGuestBuffers, which reaches the feat(agc): publish a written native multisample D32S8 surface to its guest planes on a guest read #13021 publication, and that flushes the recorder. The local fix runs the check before the handle is taken, inrecordDispatchand beforeStartDrawPass. The crash does not need feat(agc): sample the stencil plane of a native multisampled D32S8 target #9717: with feat(agc): sample the stencil plane of a native multisampled D32S8 target #9717 out, the stencil copy draw skipped and this fix removed, it recurred at the same address,nvoglv64.dll+0xe35467, about 31 s in. That build still helded82dbdccfand456a530efb. Not the cause, each tested: VRAM pressure (it crashed with 971 MiB in use), descriptor reuse and retired imports..pakfiles. The cause was in the game's own log:AbstractPeer::Init: Failed to bind socket to port in range 0 - 0, thenGameServer::Init: Initializing server failed, so the local server never started and the client waited forever. RakNet creates its socket withsceNetSocket, then callsbind,getsocknameandsendtofrom libkernel, which does not know that socket. The local fix is a table of forwards that libSceNet registers with libkernel forbind,getsockname,sendtoandrecvfrom.setsockoptstill refusesSO_LINGERand level 0 option 2, and the title carries on regardless.2e499428ca: every save stored noise as its PNG. The file was valid, and the bytes were BC1 blocks of a ground texture with the alpha byte forced to 255. The title renders the thumbnail by compute into a 768 KiB tiled 480x270 image at0x3a8780000, then reads it on the CPU after a label.StoreReadbackBeforeLabelstores only linear images and those up to 64 KiB, so the CPU read the old bytes at that address. Images up to 1 MiB not written in the last 8 flips are now stored too. Two saves produced correct pictures: one on this fix's final form, one on a wider test version. It was not repeated after the last rebase, and there is no automated test. The 1 MiB and 8 flip limits are chosen from this one case.Speed
The opening scene of The Hold, idle, on the Continue route, 10 s windows. Each row adds to the one before it, and the first one or two windows after loading are left out.
tools/trace_digest.pysummaries without samplers)main9fe758d752The same route on a later save in The Hold, which is the fairer figure for play:
mainf776fddcffThis is the bottleneck tracked in #7895: one draw committer. On the later save, with draw profiling on, about 2,070 draws per frame reach it at about 18 µs each, and it is idle about 7% of the time. In the opening scene the figures are about 672 draws at about 29 µs. The cost is spread thinly: recording about 24%, the write watch walk about 12%, key and lookup about 10%. The GPU alone takes about 16.2 ms, so 60 fps would leave no margin here even with the CPU cost removed.
Remaining committer cost in the opening scene, and why:
waitForFlipRoom, so the emulated GPU work sets the pace. About 672 draws per frame reach the committer, which stays nearly full. The frame takes about 19.7 ms and 60 fps needs 16.6 ms.0x376200000does not get a host import, so a 3,008 MiB heap mirror is checked by address-based builds (about 1,800 per second, about 41 per collect epoch). Each epoch walks the whole range throughGetWriteWatch: about 1,500 runs of 2 MiB at about 2 µs each, with no dirty pages seen. A standalone benchmark puts one call over 3 GiB at about 1.6 ms, and the reset flag adds nothing, so merging the runs would save about 1.4 ms at most. Moving this walk to the queue worker worked (AcquireRegisteredfell from 17% to 1.8% of the committer) but gained no fps, also with a pipeline depth of 128, so it was not kept. The committer went idle instead, probably because the walk follows a drain and leaves nothing queued to overlap with. The walk has to get shorter or rarer, not move.resolved.moved, read-only buffers at new addresses each frame, and only 0.1% would qualify. fix(agc): look up and attach draw recipes on the relocated donor entry #7369 cannot help this title, so it was not resolved or tested.CheckCurrentfrom 11.8% to 2.0% of the committer. It gained more than the wait's sampled cost, probably because the wait also split GPU work.0x383d00000as a written buffer, andstoreBackClearedHtilewaits for it. It always reads back uniform0xfffc000f, but it is a real GPU write, so the wait stays.Tested with no gain on this title: #13858, #9899, #9858, #9898, #12070, #10886. A larger
APS5_HOST_IMPORT_MIBmade it worse: with 13000,vkAllocateMemoryfailed at about 8.5 GiB of imports, the budget was lowered to that, fps fell to about 17 and loads stalled.Analysis (AI-generated, not measured)
0x88reads asSTENCIL_COPYplusCOPY_CENTROID, and the 1920x2160 2x target looks like checkerboard rendering. The local pass assumes the DB exports stencil on both of the first two channels. That has not been measured on a console.Next steps
readTarget,markLayersPending, perf(agc): build a pipelined draw's resource-cache key before it reaches the committer #10678 and merging the 2 MiB runs. They help, but they will not reach 60. Recipes that accept moved buffers look worth about 2 ms at most in the opening scene, an estimate from samples.How it was run
Dump content in
app0\, witheboot.binand the threesce_modulePRX unwrapped. Noto fonts inanyps5-fonts\. No PlayGo or other title-specific workarounds.APS5_LOG_TIMESTAMPS=1,APS5_TRACE_SUMMARY_EVERY=10,APS5_DUMP_FRAMES=400,APS5_DUMP_FRAMES_EVERY=40,APS5_PAD_INPUT_FILE=<path>. Input was scripted: Cross through the menus from 45 s, Cross at 150 s to close the tutorial popup, Options at 170 s, Cross at 190 s to confirm, then Cross every 12 s from 300 s in the longest runs. Each lasted 700 ms, because shorter presses can fall between frames at these rates. Shader caches were warm except for the first run of a build. Times are from launch.Creating
temp0/Logsbefore launch turns on the title's ownnetwork.logandgold.log, which show the client and server state machines. It is not needed to run the title.Host report (integration build)
This report is from an earlier build of this work on
maind30e04fb8a, so itscommit:line differs from the branch above. The system is the same.AI-assisted: yes
All reactions