Its section moves from after HDR output to before Windows crash diagnostics, next to the other switches for looking into a run. Other open changes add their own sections right after HDR output.
A -U0 hunk for an insertion before line 1 starts at line 0, so two PRs
inserting at the top of one file produced a link to the nonexistent
line L0. hunks now clamps the start to line 1 and derives the end from
the clamped start. A test covers the clash range and the rendered link.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
Claude-Session: https://claude.ai/code/session_012zyXkUzTZGh3nBwNMtrLaW
A push to main ran every job: relinker on three hosts, register context
on four and write watch on two, next to the full Linux and Windows
builds. The eligibility gate now reads the files of the push (compare
before...after) and applies the same path rules as pull requests; when
it cannot (a first push, 300 or more files, an API error) every job runs
as before.
Whenever the full builds run (push and manual builds), the Linux and
Windows relinker jobs repeat tests the full builds already run: the
relinker-only ctest lists (150 and 145 tests) are subsets of the full
Linux and Windows ones (1052 and 1069) in run 38397922579. The relinker
matrix now keeps only macOS then; automatic pull request builds, which
have no full build, still run all three.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
A write-back stored on the GPU over memory outside the write watch left its
units without saved guest bytes (only the CPU path saved them), so the next
store of results landing there threw (#5711), and every refresh re-uploaded
the image. The stored ranges are now copied from the retile scratch into a
host-visible buffer behind the store and become the saved bytes when the
batch completes; a store or refresh that needs them first syncs that batch.
Units without a write generation pending when their range leaves the watch
save their bytes there too.
The second-store fixture waits for the GPU before its surface is freed on
every return, as #5790 does for the other cases.
`return ::Fail();` and `else ::Fail();` call the global wrapper, but
QUALIFIED took the keyword for a qualifier name and counted the export
as done. The name before `::` must now be an identifier that is not a
keyword, or a template's closing `>`.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
Claude-Session: https://claude.ai/code/session_012zyXkUzTZGh3nBwNMtrLaW
A sampled depth texture whose layers are all backed by host depth surfaces is
gathered host-to-host, plane by plane. The gather located the surface for
layer n at base.address + n * DepthSliceBytes(extent), the host depth slice
stride, and required the guest descriptor's sliceLinearBytes to equal that
stride.
Bendy and the Ink Machine (PPSA27616) samples a 64x64 F32 cube over six D32
depth surfaces. The descriptor's per-layer footprint is the tiled depth slice,
but its linear footprint is smaller, so the check refused a valid resource and
the game aborted as soon as it sampled the cube.
Locate each layer at base.address + geometry.GuestLayerOffset(layer) instead.
That is the address the descriptor itself uses, and the one the guest-memory
fallback already used, so both ways of finding a layer agree by construction.
Keep the geometry check for the mixed case, where a layer has no host surface
and is filled from guest memory, because that path lays its layers out at
sliceLinearBytes.
The storage-image path still refuses a layer pitch that is not the depth slice
size; that is unchanged and out of scope.
With libSceNet sockets on ordinary descriptor numbers (#4391), poll on a
libSceNet socket threw "neither a socket nor a pipe": poll only knew
libkernel sockets and pipes, while select already asks libSceNet through
its poller. libSceNet now lends libkernel the host socket behind a
descriptor, together with an owner that keeps it open, so poll puts it in
the same WSAPoll or poll call as libkernel sockets. ProsperoLight
(PPSA99002) stopped here on Linux and now reaches its PC list.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
Claude-Session: https://claude.ai/code/session_01EvDbpwUPTa78oCAJqe7m9K
v_cubeid_f32, v_cubesc_f32, v_cubetc_f32 and v_cubema_f32 refused any
output modifier with "VOP3 source modifiers are not implemented";
PPSA11386 stops there on v_cubeid_f32 v, v, -v, -v div:2.
On RDNA2 (gfx1036), over 2048 inputs in every combination of IEEE mode,
the four f32 denormal values and f16/f64 denormals flushed or kept, with
round to nearest even, the four instructions apply mul:2, mul:4 and
div:2 whenever IEEE mode is off, also with f32 output denormals kept,
where v_mul_f32_e64 in the same kernels ignores them, and ignore them
with IEEE mode on. Where applied, the result is the existing bit-level
f32 output modifier result, and clamp is applied after it.
The decoder accepts the modifier on the four instructions. floatCube
applies the shared f32 scaling, now scaleF32Result, in those modes and
writes with the modifier cleared, so clamp is still applied after it.
With IEEE mode on the signaling NaN quieting applies and the modifier is
ignored; with it off the quieting does nothing and the modifier is
applied. agc_driver_vop3_cube_clamp checks each instruction with each
modifier against tables captured on gfx1036.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
Claude-Session: https://claude.ai/code/session_01Fnrk5Dazjb2tLooVSpdRQq
OpenOrbis modules keep read-only data after their code, as executables
do. The syscall scan of sce_module modules decoded it, and the module of
the OpenOrbis library sample (libExample.prx) failed with "Forbidden
syscall instruction". For modules with a PT_SCE_DYNLIBDATA segment, the
scan now stops at the end of the PLT after the last unwind function,
found by FindSceCodeEnd as for executables.
The same modules begin their executable segment with the
/libexec/ld-elf.so.1 string but have no PT_INTERP header, so code
analysis decoded the string and failed with "Unsupported Windows guest
TLS instruction (bytes: 64 2d 65 6c 66 2e)", which is the text "d-elf.".
When no PT_INTERP header covers the start of a PS4 code segment, code
analysis now starts after that exact string.
OpenOrbis programs and modules import these PS4 libkernel names (the
graphics, library and networking samples). The underscore names
forward to readv, writev, fcntl and fstat, as _ioctl already does;
_fcntl passes its argument on as a full 64-bit value, so the record
lock commands keep their whole pointer. __sys_socketex creates a
socket like socket(); its name argument is ignored, as sceNetSocket
does.
Add the PS4 functions sceVideoOutSetBufferAttribute and
sceVideoOutRegisterBuffers on top of the existing registration. The PS4
call uses the first free attribute set and returns its index. It
accepts linear A8R8G8B8_SRGB and A8B8G8R8_SRGB buffers, which map to the
PS5 B8G8R8A8 and R8G8B8A8 formats. It throws for tiled buffers, whose
PS4 layout differs from the PS5 one. Linear PS4 buffers may be 4 KiB
aligned: the OpenOrbis graphics sample places its second 1920x1080
buffer 8,294,400 bytes after the first. PS5 buffers keep the 64 KiB
rule. A handle with PS4 buffers writes the PS4 flip status (64 bytes)
and vblank status (32 bytes). Writing the 128-byte PS5 flip status into
the sample's stack structure overwrote its saved frame pointer.
DepthSurfaceStoreBack walked the surfaces oldest first and let the first
one whose plane the storage image covers take the copy. A depth plane
bound with several stencil planes has one surface per pairing, so the
copy could land in an older pairing while DepthSurfaceStorage,
DepthSurfaceTexture and DepthSurfaceAt read the newest one, and a store
back through a replaced view was accepted by an older pairing instead of
throwing.
The surface's own view and the replaced views are now checked on every
surface first; only then does the newest surface covering the plane take
the copy, the order DepthSurfaceStorage resolves a plane in. Reported
with the repro and the fix by nikowolf123; the repro is the new
RunPairings test.
AI-assisted: yes
DepthSurfaceStoreBack took only the storage image a depth surface had
handed out for its plane. A storage image over the same plane that the
surface did not hand out (one cached before the surface existed, kept by
a dispatch whose resources revalidate from their records) was written
and never reached the depth image: later depth tests and plane reads
used the surface's old contents.
A written storage image that covers a depth surface's depth or stencil
plane exactly (the plane's address and extent, level 0, one 2D layer,
the plane's 32-bit float, 16-bit unorm or 8-bit uint format) is now
copied into that plane when it is stored back, as the surface's own view
is. A view the surface's own view replaced still throws.
Uncharted: Legacy of Thieves Collection (PPSA05684) writes a 640x360
downsampled depth with a compute shader and then tests its mist
particles against it as a depth target; the depth target stayed at its
clear and the mist drew over foreground geometry.
A slice of a depth array target (DB_DEPTH_VIEW SLICE_START) offset its
depth and stencil addresses but kept the array's DB_HTILE_DATA_BASE as
its HTILE. Every slice then shared slice 0's metadata: a fast clear of
slice 0's HTILE cleared every slice, and a clear of any other slice's
HTILE matched none.
A slice's HTILE now starts at the base plus the slice times one slice's
pipe-aligned metadata, as addrlib addresses it (sliceSize * slice in
Gfx10Lib::HwlComputeHtileAddrFromCoord; HtileMetadataBytes is that slice
size). The recognized HTILE clear kernel now reports the bytes it
clears, 16 per thread (global_store_dwordx4 at the thread index << 4),
and a surface takes the clear when that range covers its HTILE, as a
DMA_DATA fill does; a clear over a whole array still clears every slice.
Uncharted: Legacy of Thieves Collection (PPSA05684) renders its sun
shadow cascades into the four slices of a 2048x2048 D16 array; each
slice's HTILE lies 256 KiB after the previous one.
An s_swappc_b64 whose target is not resolved compiles to a faulting call
only at the fallback the table-call linker emits; the linker lists those
calls in the request (GuestContext::linkedCallFallbacks), and every other
computed call is refused at compile time again, as on main. The new
agc_driver_compute_table_calls test runs a linked two-record table on
Vulkan in wave32 and wave64, with SCC 0 and 1 reaching the callee, and a
record past the table reporting the UnlinkedCall fault.
Co-Authored-By: Claude Opus 5.5 (1M context) <[email protected]>
An s_swappc_b64 whose target pair comes from an s_buffer_load of a buffer
whose descriptor is loaded from user data now calls the targets that buffer
holds: at dispatch the driver reads the buffer, links one copy of each
distinct callee after the caller and rewrites the call into a compare chain
that s_call_b64s the matching copy. A target that matches no copy, and any
other computed call, records an UnlinkedCall fault that the driver reports,
instead of failing the shader at compile time.
Co-Authored-By: Claude Opus 5.5 (1M context) <[email protected]>
Decode and Flush let FFmpeg crop every picture to its display size, so a
1080p H.264 stream came out as 1920x1080 with the chroma after 1080 luma
rows. The console reports and writes the coded picture: EVO-PLAYER-PS5's
hardware run of a 1080p H.264 IDR returned 1920x1088 with pitch 2048 and
the chroma after the 1088 luma rows, and ProsperoLight rejects a 1080p
H.264 or HEVC picture whose height is not 1088. FFmpeg's cropping is now
off, so the frame size, the chroma offset and the sizes in the AVC
picture info are those of the coded picture. The pitch is unchanged, and
the frame size QueryDecoderMemoryInfo reports, which aligns the maximum
height to 32 rows, still holds a picture coded within the maximum and the
macroblock-padded H.264 picture of a maximum given as the display size.
libSceVdecsw derived its crop offsets from the difference between that
size and the macroblock grid, which is now zero. It takes the crop FFmpeg
exports for the picture from libSceVideodec2 instead.
The H.264 fixture is coded at 64x48 with frame_crop_bottom_offset 4: its
pictures are checked at 64x48 and the crop through Vdecsw. The HEVC and
VP9 fixtures are coded at 64x40 and keep their hashes. The new hashes come
from FFmpeg 8.1 decoding with apply_cropping 0, hashed as the tests do;
the same method reproduces every previous H.264, HEVC and VP9 hash.
Co-Authored-By: Claude Opus 5.5 (1M context) <[email protected]>