Repository navigation
Conversation
…'s timestamp, outside the decoder lock One frame at a time (max_frame_delay 1, 2 threads) took 9-20 ms a packet of Ocarina of Time's 1080p60 title movie on an M1 Max, single packets up to 134 ms; more threads on one frame did not help. 8 threads and 8 frames in flight: at most 26 ms. A picture then comes some packets after its own: mav1_decode_ts carries the packet's timestamp through dav1d (Dav1dData.m), the wrapper queues pictures (mav1_next) and gives the frames still decoding at the end of the stream (mav1_drain), asking dav1d once per input, since a second ask drains. cv_dec_submit decodes AV1 under a decode lock of its own, so Release and Acquire do not wait on dav1d; a packet may add up to CV_BURST pictures past CV_HOLD, where packets are still refused. t_codec_video: a lone frame's picture comes at the end of the stream; 20 packets give 20 pictures in order with their timestamps. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
… late pictures instead of playing the movie slowly Ocarina of Time's player shows one picture a frame and sends packets until refused; its movies are 60 fps. At 28 frames a second (an M1 Max's GPU under the title's NDVE filter) the title movie ran at 0.44x, its sound ahead. The decoder now gives pictures by their timestamps against the host clock: of the waiting pictures, the newest that is due, the late ones before it dropped, a picture late once the next is 50 ms overdue. A stall over a second or a timestamp going back starts the clock again; Reset too. AV1 only; DM_CV_LATE=0 turns it off. t_codec_video checks the rules on a clock it sets. Movie time against host time: 66.03 s in 66.05 s. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
…lel and pictures follow the movie's clock
…switch table The watch job reads "skip" lines from .github/upstream-watch.tsv (number and reason) and lists those pull requests as left out instead of counting them. Three are: seedds#1311 (Ocarina's play reports already complete offline, from seedds#1299; this is a whole prepo:u service on new CMIF not taken upstream yet), seedds#1357 (NXForge compiles again with a deeper bracket limit only when Metal asks, so the shader chain stays the same) and seedds#1365 (upstream's agent charter, docs only). docs/env_switches.tsv gets DM_CV_LATE, which seedds#1379 reads: env_switches.py --check failed on this branch since that merge. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_016qteK29T18U8p1c9LsVY8g
|
Tested on a MacBook Pro 14" (M2 Pro, no hardware AV1, 32 GB), macOS 27.2: Before: the title movie ran at 22 fps (GPU 36 ms a frame), a scene's sound played before its picture, and when the picture reached the scene its sound had already ended (silence). With this PR the log shows |
… the clock again, and the clock is the guest's A picture over a second late started the movie clock again. That suits a pause, but on a stall in the host (a pipeline built on first use, a long GPU wait) the game's sound goes on, and the picture then stayed that far behind the narration until the next stream (reported on an M2 Pro). Now the clock starts again only when the game held the movie: it presented 6 frames or more without taking a picture (a pause menu, a load screen), or its window lost the focus meanwhile. Otherwise the late pictures are skipped until the movie is back on its clock. The clock is guest_ns, which does not run while the Mac sleeps, an iPhone app is in the background or DM_DETCLOCK steps it. The log says when the clock starts again and why, and when a stall is caught up. t_codec_video adds a pause, a stall and a focus change. DM_CV_LATE gets its row in docs/env_switches.tsv (test_env_switches listed it as a switch without a meaning), and docs/reference/movies.md an entry. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_017WLejRwCykjPcsPU4Hdenf
|
Thanks for testing on the M2 Pro. The slip matches a rule in the first version: a picture over a second late restarted the clock. That was meant for a pause, but on a stall in the host (a pipeline built on first use, a long GPU wait) the narration goes on, so the picture stayed behind until the next stream started. The PR now restarts the clock only when the game held the movie (it presented frames without taking a picture, or the window lost the focus), and otherwise skips the late pictures to catch up. Reproduced here by stopping Also, your build has #1331: with Drafted with Claude; reviewed by me. |
…ll in the host is caught up instead of starting the clock again, and the clock is the guest's Resolved: cv_dec keeps NXForge's refused count beside seedds#1379's catch-up fields; docs/env_switches.tsv keeps DM_CURSOR_HIDE and takes seedds#1379's DM_CV_LATE line. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_016qteK29T18U8p1c9LsVY8g
) replaces the pull request heads Upstream landed Ocarina of Time in main (chain adec7d81d970: "holds 60 fps in Kokiri Forest, 4 GB less") and closed the pull requests it folded in, with reworded and partly different code. Mixing a pull request head with its landed version hunk by hunk silently broke things (two GlobalToStorage tables, a duplicate AF2ip, two mtk_pso definitions), so the rule here is one version per feature: - Pull requests upstream closed (seedds#1299, seedds#1300, seedds#1312, seedds#1343, seedds#1345, seedds#1353, seedds#1354, seedds#1359, seedds#1360, seedds#1373, seedds#1428, seedds#1430, seedds#1434): their hunks are taken out of our side before the three-way merge, so upstream's landed version stands alone. Gone with them: bindless pool table patching (reg_bump), the ghost table's per-submission hold, the growing raw pool table and its write-log sizing, seedds#1428's pool_buf spares (upstream's pool_table_take is the same idea), the ixc-based indirect mesh draw (upstream uses mdx), and their tests (t_pool_table, t_mesh_indirect, t_gmem_raw, finalized_bindless_pool, test_bnsh_nvn2, test_ndve). - Open pull requests that upstream's landing supersedes: seedds#1394 (upstream's mtl_pool_addressed) and seedds#1393 pool_skip_retired (upstream's budgeted pool walk; the profile does not use it) are dropped with their tests and docs. seedds#1368's mesh pipeline prewarm is dropped too: upstream kept the background build in nvn_geometry.inc, and the prewarm's mtk_build / mtk_claim / g_warm_mps went with it. - Kept, as upstream does not have them: NXForge's own features (GPU watchdog, present filters and anti-aliasing, aniso floor, quick settings, pipeline archive compaction, upload breakdown, memory report lines) and the still open pull requests seedds#1304, seedds#1305, seedds#1308, seedds#1320, seedds#1331, seedds#1332, seedds#1355, seedds#1356, seedds#1369, seedds#1376, seedds#1377, seedds#1379, seedds#1382, seedds#1390, seedds#1391, seedds#1392, seedds#1414, seedds#1420, seedds#1436, seedds#1439, seedds#1446, seedds#1453. - Combined where both sides changed the same lines: GW_N 1 << 16 with seedds#1320's wide-write intervals (GW_PAGES = SBW_WPAGES, 128 slots), the CPU upload log with upstream's linear upload route, arch_open_end before the compaction limit, cbn_prog in geo_gs_one (seedds#1382). - Translator: upstream's sources and binaries, plus seedds#1414's InstEmitAmpereMem diff and the LDSM SubgroupBarrier in InstEmitAmpereTensor.cs. The binaries and dmsh_chain.lock are upstream's until the Mac rebuilds them (dotnet publish, tool_lock --update-lock, dmsh_chain --header); dmsh_chain.h is regenerated for now. - RED_ONCE keys: upstream took 153 and 154, so the present anti-aliasing lines move to 156 and 157 and seedds#1420's packaged-entry line to 158 (array 159). - Host: hle_net.c and t_net_eventfd.c are upstream's (its eventfd poll waits out the whole timeout, which our 5d7920c fixed another way). - Kept ours: dm/tools/romfs_image.py and its test, so the 26 GB RomFS image is not packed again. dm/tools tests on Linux: same failures as on 875449e (Linux-only quirks), plus test_nlg4 and test_dmsh_pool_arrays, which fail on upstream main too. Not yet built on the Mac. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_016qteK29T18U8p1c9LsVY8g
|
Tested #1377 and #1379 on an M2 Pro (MacBook Pro, 19-core GPU, 32 GB, macOS 27.2, no hardware AV1) with #1331's direct mode on ( Build: main
Control: the baseline reaches the same loop end, the game's fade to black, at 120.4 s, against 97.8 s with #1377 and 97.6 s with #1379, so the same 5,947 pictures take 1.23× as long (0.81×). The fade, about 5.6 s, is there in all three. A second #1377 run gave 0.1% again. So with the direct mode the game does present at 60, but without #1377 its player takes a new picture on only about 4 frames in 5. The decoder itself keeps up: dav1d with the host's settings (2 threads, frame delay 1) decodes this movie at 133 fps on this Mac, and the queue is full ( The 5.5 s with an unchanged patch at 97.8 s in the #1377 runs is the game's fade to black between two loops (luminance 1.2 → 0.15 → 0 → back up), not a stall. |
…han its movie skips late pictures instead of playing the movie slowly Upstream pull requests applied in this commit (their authors' work, brought onto this tree with a three-way merge; the description is in each PR): - seedds#1379 by MetaIX (open): AV1 pictures by the movie's clock: a game slower than its movie skips late pictures instead of playing the movie slowly
Stacked on #1377: this branch includes its commit. Only the last commit (
AV1 pictures by the movie's clock…) is this PR's; I'll rebase once #1377 is in.What and why
Symptom: Ocarina of Time's player (
0400486024DEC000v131072, profile in #1299) shows one picture per game frame and sends packets until the decoder refuses them. All 26 of its movies are 60 fps. On a Mac that renders the title below 60 fps, the movie plays slowly and out of step with its sound: at 28 frames a second (an M1 Max, under the title's NDVE filter) it ran at 0.44×.Change: the decoder hands out pictures by the movie's clock, as a video player does.
guest_ns, which does not run while the Mac sleeps, an iPhone app is in the background orDM_DETCLOCKsteps it).Resetrestarts it too. So does a picture over a second late when the game held the movie: it presented 6 or more frames without taking a picture (a pause menu, a load screen), or its window lost the focus.DM_CV_LATE=0turns it off.Checked
make -C dm/host/tests GAME=0100000000010000 runpasses.t_codec_videochecks the rules on a clock it sets:dmhoststopped with SIGSTOP during the title movie, NDVE on, 28 fps): afterwards the picture is 0.06 s off the movie's clock, as before the stall. The first version of this PR restarted the clock there and stayed 1.72 s behind for the rest of the movie: the slip reported on an M2 Pro below.Docs
docs/reference/movies.mdentry, andpython3 dm/tools/docs_symptoms.pywas run (the symptom index)DM_CV_LATEis indocs/env_switches.tsv(test_env_switchespasses on this branch)🤖 Generated with Claude Code