Commit Graph

221 Commits

Author SHA1 Message Date
Scott Schuster 0a1b31f5c4 test(agc): cover NGG vertex programs routed to the mesh path
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-11 07:56:37 +02:00
Scott Schuster dddd9f29c2 test(agc): cover raw program snapshots and headerless vertex decode
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-10 18:59:28 -05:00
Chad b89b7f953c fix(agc): expand comp-to-single DCC keys in a DCC decompress pass
Key 0x10 (GFX9_DCC_CLEAR_SINGLE in Mesa) marks a 256-byte block whose texels all equal its first texel. A CB DCC decompress pass over uniform comp-to-single keys now writes that texel over its block and stores uncompressed keys; a fast-clear eliminate over them throws.
2026-10-11 01:38:27 +02:00
XairRrR 048c9ff013 feat(agc-driver): render to COLOR_8_8 targets with SWAP_ALT
CB_COLOR_INFO COMP_SWAP 1 (SWAP_ALT) on a two-channel format stores the
x and w exports in its two channels (Mesa si_translate_colorswap,
"X__Y"). COLOR_8_8 UNORM and SNORM targets with it bind as R8G8 with
export mapping 0xec; blending into them still throws, since Vulkan
would apply alpha factors to the wrong channel.

Uncharted: Legacy of Thieves Collection (PPSA05684) stopped in its
first level with "unsupported color format 3 number type 0 component
swap 1".
2026-10-10 19:59:14 +02:00
Dean db343a934c
Merge pull request #2656 from oneandonlydean/up2/buffer-slabs
perf(agc): sub-allocate small host buffers from shared memory blocks
2026-10-11 02:59:36 +13:00
Dean 808d8dc43a
Merge pull request #2691 from oneandonlydean/up2/parallel-snapshot-compare
perf(agc): compare large stale draw snapshots on helper threads
2026-10-11 02:35:16 +13:00
Dean Galvin db2cd3559e perf(agc): compare large stale draw snapshots on helper threads
A stale storage snapshot is revalidated by comparing every tracker block
stamped since it was taken. A title that binds buffers a dispatch writes
in place every frame (the whole declared range stamped, few pages really
changed) makes the graphics worker compare gigabytes per second.

Compares of 1 MiB or more are now split by block across a small pool of
helper threads (hardware threads / 8, from 1 to 4). The compare is memory
bound, so the worker's share roughly halves rather than dividing by the
thread count. A caller that finds the pool busy compares on its own
thread. Results and the patch-in-place rules are unchanged.

agc_driver_graphics_tests parallelCompareTests: per-span results on the
pool and serial paths, and two threads comparing at once.
2026-10-10 23:55:38 +13:00
Adrià Franch 8c802e5eb1 perf(agc): give each graphics stage a fixed push constant slot with pipeline libraries
Co-Authored-By: Claude <noreply@anthropic.com>
2026-10-10 12:19:31 +02:00
Dean Galvin 765619a00b perf(agc): sub-allocate small host buffers from shared memory blocks
Every small host buffer (size classes below 1 MiB: draw and dispatch data,
copied regions, snapshots) had a VkDeviceMemory of its own. When the pool
missed, the worker paid a vkAllocateMemory and vkMapMemory, and the release
thread a vkUnmapMemory and vkFreeMemory, for each one. The frees also stall
the worker's vkQueueSubmit in the driver.

A host-visible buffer of a size class now gets its own VkBuffer bound into a
slot of a shared block (2 MiB, or 8 slots for the large classes) per memory
type, size class and device-address use, mapped once. Releasing it destroys
only the VkBuffer and returns the slot; a block is freed when it empties and
its slab already keeps an empty one. A slot is used only when the buffer's
alignment and the non-coherent atom divide its size class, so the slot
offset is valid for the bind and Invalidate covers exactly the slot. The
pool still retains released buffers by class as before; only what backs
them changed.
2026-10-10 23:05:21 +13:00
Adrià aad13ac11b
Merge pull request #1147 from alfalfa-star/perf/agc-staging-pool-heap-budget
perf(agc): size the device staging pool from the device-local heap
2026-10-10 11:28:29 +02:00
Adrià 2f3b5046e5
Merge pull request #1492 from Celegans12/feat/agc-dual-source-blending
feat(agc): implement dual-source blending from the MRT1 export
2026-10-10 11:01:16 +02:00
Adrià a56b44a13c
Merge pull request #1735 from TheAggie/feat/agc-color-target-4kb-xor
feat(agc): render into XOR-swizzled color targets with a pipe/bank XOR, and into SW_4KB_S_X/D_X
2026-10-10 10:49:43 +02:00
Adrià 1de7e438fa
Merge pull request #2626 from oneandonlydean/fix/carry-2578
fix(agc): render into one slice of a 2D array color target
2026-10-10 10:48:29 +02:00
Celegans12 b8cc4adb3b feat(agc): implement dual-source blending from the MRT1 export
CB_BLENDn_CONTROL factors 15-18 (BLEND_SRC1_COLOR, BLEND_INV_SRC1_COLOR,
BLEND_SRC1_ALPHA, BLEND_INV_SRC1_ALPHA) threw "unsupported blend
factor". They blend MRT0 with the pixel shader's MRT1 export as the
second source, as RADV and radeonsi program it.

DecodeState maps them to the VK_BLEND_FACTOR_SRC1_* factors and accepts
them only with pixel exports to slots 0 and 1, color writes to slot 0
alone, an MRT1 export with MRT0's export format and shader mask, an
ADD, SUBTRACT or REVERSE_SUBTRACT operation and an identity component
order. The blend is draw state, so the specialized module of the
registered pixel shader moves its MRT1 output to location 0 index 1,
which ValidateShaders requires; pipelines need dualSrcBlend, now enabled
when present. The request field dualSourceBlend is in the module key,
the result memo, the draw key and the serialized request (version 15).
2026-10-10 10:29:00 +02:00
AlxcBTW ce8bee6980 fix(agc): render into one slice of a 2D array color target
DecodeColorTileMode rejected 2D color targets with a nonzero MIP0_DEPTH, so
an array target could only be rendered into through a view of a surface that
declares one slice. radeonsi sets CB_COLOR_ATTRIB3.MIP0_DEPTH to the last layer
of an array target (si_state.c, ac_descriptors.c), and Mesa-built homebrew
emits such targets. The view's slice already moves the target by one slice
size; it is now also checked against MIP0_DEPTH.
2026-10-10 21:20:29 +13:00
alfalfa-star 3bb4494ea7 perf(agc): size the device staging pool from the device-local heap
The buffer pool's device tier (detiler scratch buffers and the staging
shadows of written guest buffers) retained at most 512 MiB by default.
A title whose working set of these buffers is larger allocates and
frees device memory continually: PPSA14632 (LEGO Horizon Adventures)
had 70761 misses and 69828 evictions per 10 s with 485 of 512 MiB
retained, each a vkAllocateMemory or vkFreeMemory.

The default budget is now an eighth of the largest device-local heap,
and at least the old 512 MiB, so a 16 GiB card retains up to 2 GiB and
an 8 GiB card 1 GiB. APS5_STAGING_POOL_MIB still sets it.

Only the constructor knows the device, so only the budget comes from the
heap. Whether the tier is in use at all (APS5_STAGING_POOL_MIB unset or
not 0) stays a static check, DeviceTierEnabled, which Capacity, Usage and
tierFor share, so the size classes and the tier stay consistent.

On PPSA14632 with 2 GiB the device tier has 1312 misses and 99
evictions per 10 s (1628 MiB retained), and presents rise from about 34
to about 39 per 10 s.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-10 10:19:34 +02:00
Scott Schuster c160d31649 feat(agc): accept the LINE_STIPPLE_TEX and POS_FIXED_PT pixel inputs
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-10 10:18:16 +02:00
danzaio 5e3268969b fix(agc): zero-fill a vertex fetch past the record count
A strided vertex fetch whose index is at or past the descriptor's num_records threw and aborted the title. PPSA01325 draws its fullscreen composite as a 4-vertex strip over a 3-record buffer, so the fourth vertex past the records stopped presentation.

Hardware returns (0, 0, 0, 0) for such a fetch with OOB_SELECT 0 and 1, measured on RDNA2 gfx1036 with tools/hw-oracle in #2241. VertexBufferReadSize now spans the whole fetch, and the staging copy reads the record bytes then zero-fills from num_records * stride onward. Each such fetch gets its own copy, outside the shared copies of its sibling attributes, the host-import in-place path and the draw-snapshot cache. OOB_SELECT 2 and 3 keep throwing past num_records, since each needs its own rule. Recorded in docs/dev/TechnicalDebt.md.
2026-10-10 20:58:25 +13:00
Adrià 51b8cef4f9
Merge pull request #1969 from lubaxe/fix/agc-null-vertex-buffer-descriptor
fix(agc): read zero for vertex attributes behind a null V#
2026-10-10 09:28:06 +02:00
Adrià d99babe24c
Merge pull request #1607 from saarthakpant/fix/agc-per-stage-color-attachments
fix(agc): count a pixel stage's colour attachments against maxPerStageResources
2026-10-10 09:25:20 +02:00
Adrià b23bd7323f
Merge pull request #1831 from yabanana/fix/macos-descriptor-array-ranges
fix(agc): preserve descriptor array ranges in draw snapshots
2026-10-10 09:22:08 +02:00
Adrià eba8525acb
Merge pull request #1924 from fisherjoey/fix/depth-bias-per-face
fix(agc): draw each face with its own depth bias
2026-10-10 09:19:03 +02:00
Sasha Papo e6e0b69101 fix(agc): read zero for vertex attributes behind a null V#
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-10 09:17:49 +02:00
Adrià a86ffd3368
Merge pull request #1995 from lubaxe/feat/agc-store-pending-at-flip
feat(agc): store pending storage-image results at each flip with APS5_STORE_AT_FLIP
2026-10-10 09:12:46 +02:00
Daniele Giovane 1730b29c4a fix(agc): preserve descriptor array ranges in draw snapshots 2026-10-10 09:07:26 +02:00
Joey Fisher e0084a56b0 fix(agc): draw each face with its own depth bias
A draw that rasterizes both faces with different front and back depth
bias was rejected, since Vulkan has one depth bias per draw and the
cull mode is pipeline state. Such a draw is now recorded twice in the
same pass: front faces with the back faces culled and the front bias,
then back faces with the front faces culled and the back bias. A face
whose offset is disabled gets no bias.
2026-10-10 09:04:37 +02:00
Adrià 3a1c79f387
Merge pull request #2219 from XairRrR/feat/agc-depth-clear-draws
feat(agc-driver): draw DB_RENDER_CONTROL depth clears
2026-10-10 08:59:33 +02:00
Sasha Papo 3221ae8acd fix(agc): accept only 1 for APS5_STORE_AT_FLIP and test the switch instead of FlushAllPending
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-10 08:56:11 +02:00
seven 5b9fdd111a fix(agc): count a pixel stage's colour attachments against maxPerStageResources
Vulkan counts the framebuffer colour attachments against maxPerStageResources
for the fragment stage. The draw's attachment count now seeds the fragment
stage's resource total in ShaderResources, so a pixel shader whose buffers and
images fit the limit but whose pipeline exceeds it throws instead of creating
an invalid pipeline. The draw resource cache key carries the attachment count,
so a cached build is never reused by a draw with more attachments.
2026-10-10 12:07:56 +05:30
Scott Schuster ee95202948 fix(agc): apply RADV's HTILE depth fast clears to the host depth surface
RADV clears depth by rewriting HTILE with its clear_htile_mask kernel
(ZMASK to 0) instead of writing depth memory. Recognize that kernel and
clear the matching host depth surface to DB_DEPTH_CLEAR when it is next
bound; the depth target now records its HTILE address.

AI-assisted (Claude Code).

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-10 08:36:58 +02:00
XairRrR 295223f3eb feat(agc-driver): draw DB_RENDER_CONTROL depth clears
DEPTH_CLEAR_ENABLE (DB_RENDER_CONTROL bit 0, Mesa sid.h) makes the DB
write DB_DEPTH_CLEAR wherever the draw covers. Such a draw is now
rasterized as submitted with an always-passing depth write, no depth
bounds, no depth bias and the viewport depth range pinned to the clear
value, so it touches exactly the pixels the title's geometry covers.
Clearing a read-only or absent depth plane throws, at decode and in the
draw precheck. Depth and stencil clears combine; copy, resummarize and
decompress draws still throw.

Uncharted: Legacy of Thieves Collection (PPSA05684) clears with draws
that set DB_RENDER_CONTROL to 0x3 and stopped with "depth/stencil
clear, copy, resummarize or decompress draws (DB_RENDER_CONTROL) is
unsupported (register 0x0 = 0x00000003)".
2026-10-10 08:33:04 +02:00
jweidenh 3671668472 test(agc): supply pixel registers for provoking vertex precheck 2026-10-10 08:26:14 +02:00
jweidenh 3a8cf3a38b feat(agc): support last provoking vertex for native primitives 2026-10-10 08:26:14 +02:00
Adrià 530b6a4270
Merge pull request #2226 from EdouardSence/fix/agc-conservative-uncertainty-disabled
fix(agc): accept disabled conservative rasterization with uncertainty-region bits
2026-10-10 08:20:08 +02:00
Adrià 394b6d049c
Merge pull request #2253 from Raghav314/perf/agc-draw-inputs-in-place
perf(agc): read draw vertex and index buffers in place from host imports
2026-10-10 08:19:00 +02:00
Scott Schuster 982849c8ac feat(agc): render into SW_4KB_S_X and SW_4KB_D_X color targets
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-10 01:18:15 -05:00
Scott Schuster bbf9360305 feat(agc): render into SW_64KB_R_X color targets whose base carries a pipe/bank XOR
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-10 01:18:14 -05:00
Adrià e53e26a209
Merge pull request #2378 from krishnaraya4/fix/agc-vertex-10-10-10-2-int-class
fix(shader): give 10_10_10_2 integer vertex inputs an integer type
2026-10-10 08:16:57 +02:00
Adrià 3064754c6a
Merge pull request #1547 from russhil/feat/shader-barycentric-emulation
feat(shader): emulate fragment barycentrics with a generated geometry stage
2026-10-10 08:15:00 +02:00
Adrià feea78cdd2
Merge pull request #2198 from XairRrR/fix/rect-list-fault-binding
fix(recompiler): bind the rect-list fault buffer in the tessellation control group
2026-10-10 08:14:27 +02:00
Adrià 9b67cbbd0a
Merge pull request #2022 from NahuelGenchi/fix/agc-unwritten-pixel-program
fix(agc): read an unwritten pixel program address as unset
2026-10-10 08:08:04 +02:00
Adrià 6f51afaa7e
Merge pull request #1736 from TheAggie/feat/agc-color-8888-uint
feat(agc): accept 8_8_8_8 UINT color targets
2026-10-10 07:59:59 +02:00
Adrià 29b4429870
Merge pull request #1485 from Celegans12/feat/agc-10-11-11-unorm-color-targets
feat(agc): implement 10_11_11 unorm color targets through 32-bit uint attachments
2026-10-10 07:58:55 +02:00
Dean Galvin 9c3a35b867 fix(agc): apply CMASK fast clears per tile
A CMASK that was neither all fast-cleared nor all expanded threw, so a
title that fast clears a target and then draws over part of it before the
eliminate could not run past it.

The CMASK is now decoded tile by tile: one nibble per 8x8 tile in
1024x512 metablocks of 4 KiB, addressed with the pipe-aligned
SW_64KB_Z_X CMASK equation for 16 pipes (addrlib
GFX10_CMASK_SW_PATTERN, Gfx10Lib::HwlComputeCmaskAddrFromCoord). Code 0
stores CB_COLOR_CLEAR_WORD into the tile's texels, 0xF keeps them; any
other code, a cleared tile of a DCC target and any other CMASK swizzle
mode throw. Edge tiles are included and the CMASK is then stored as
expanded.

For a resident target whose CMASK is host-imported the clear is a
compute pass recorded in stream order: it reads the nibbles from the
import, stores the clear into the cleared tiles through a UINT view of
the image and fills the CMASK expanded, so nothing waits for pending GPU
writes of the CMASK. Invalid codes it reads set a bit that the next
materialization throws on. Otherwise the CPU reads the CMASK and stores
the cleared tiles into guest memory, or fills the resident image when
every tile is cleared. A CMASK nothing has stored over since it was
expanded is skipped.

The decode requires CB_COLOR_ATTRIB3 FMASK_SW_MODE SW_64KB_Z_X with
CMASK_PIPE_ALIGNED, a 4 KiB aligned writable CMASK and texels of at most
64 bits, and CMASK_BASE_EXT is part of the draw key.

Tests: CMASK sizes and nibble addresses against addrlib; decode
rejections and draw key coverage; CPU eliminate of full, partial,
out-of-range-nibble and DCC decompress cases and invalid codes. The new
agc_driver_cmask_fast_clear GPU test draws over fast-cleared and partly
fast-cleared linear and SW_64KB_R_X targets, eliminates partial, edge
and checkerboard CMASKs through the compute pass and checks that an
invalid code it reads throws.
2026-10-10 18:20:06 +13:00
raghav314 c903d1adf9 perf(agc): read draw vertex and index buffers in place from host imports
Every draw copied its index range and its vertex ranges out of guest
memory into new host buffers (CopyDrawInput) before the GPU could read
them. A range that lies in a host import is now bound from the import
itself, at its offset in it, the way the console's input assembler reads
guest memory directly.

A range is bound in place only when the batch has no write over it that
could still land (a recorded or in-flight GPU write after the pending
results are flushed, a completion label, a queued label store, a copied
buffer a dispatch or draw writes back) and its offset in the import is a
multiple of what the reader needs: the index size, or the strictest
format alignment of the vertex attributes that share the range
(VertexCopyPlan::alignments; a copy starts its range at offset 0, so
only an in-place range can be misaligned). Otherwise it is copied as
before. The read is noted on the batch (Recorder::ReadKind::DrawInput),
so a CPU store into the range waits for the draw like the other in-place
readers, and the barrier validation sees it. Imports gain vertex and
index buffer usage.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-10 10:22:58 +05:30
Dean 5e5c72ee33
Merge pull request #2197 from XairRrR/fix/agc-collapsed-viewport
fix(agc-driver): rasterize nothing through a zero-scale viewport
2026-10-10 17:45:01 +13:00
Dean 6377727dd9
Merge pull request #2179 from oneandonlydean/up639/depth-bounds-absent-planes
fix(agc): pass the depth bounds test when both depth planes are absent
2026-10-10 17:44:53 +13:00
Dean ea8f654350
Merge pull request #2178 from oneandonlydean/up639/resummarize-blits
fix(agc): draw nothing for resummarize draws without depth or color work
2026-10-10 17:44:46 +13:00
Dean 7538f22fde
Merge pull request #2128 from MathiasDevelopes/fix/agc-spi-ps-input-cntl-clear-state
fix(libSceAgcDriver): SPI_PS_INPUT_CNTL registers start at their clear-state value
2026-10-10 17:44:08 +13:00
Dean d3c507052a
Merge pull request #2095 from Raghav314/fix/agc-1d-color-targets
fix(agc): render into 1D color targets as one-row 2D targets
2026-10-10 17:44:00 +13:00