shader: support DS_WRITE_B8_D16_HI (#794)

Decode GFX10 DS opcode 0xa0 as DS_WRITE_B8_D16_HI (next to
DS_WRITE_B16_D16_HI at 0xa1) and lower it through the existing 8-bit
shared-memory write. The stored byte is bits 23:16 of the data VGPR,
selected with SDWA BYTE_2 on src1.

Add captured-instruction decode coverage (from GTA V, PPSA04264) and a
runtime regression that writes one byte of a distinctive source value
into a pre-filled LDS dword.
This commit is contained in:
Deniz ŞAHİN
2026-09-23 23:44:39 +03:00
committed by GitHub
parent 569ec04d1a
commit fc86509aac
6 changed files with 60 additions and 1 deletions
+34
View File
@@ -16416,6 +16416,7 @@ CoverageClass ClassifyOpcode(ShaderOpcode opcode,
case Opcode::DS_READ_B128:
case Opcode::DS_WRITE_B8:
case Opcode::DS_WRITE_B16:
case Opcode::DS_WRITE_B8_D16_HI:
case Opcode::DS_WRITE_B16_D16_HI:
case Opcode::DS_WRITE2_B32:
case Opcode::DS_WRITE2ST64_B32:
@@ -24688,6 +24689,38 @@ TestCase DsWriteB16D16HiCapturedUsesHighHalf() {
return test;
}
TestCase DsWriteB8D16HiWritesByteTwo() {
using O = ShaderOpcode;
std::vector<u32> code;
AppendVMovU32(&code, 1, 0);
AppendVMovLiteral(&code, 3, 0xdeadbeefu);
code.push_back(EncodeDs0(0x0d));
code.push_back(EncodeDs1(0, 3, 1)); // ds_write_b32 v1, v3
// Every byte of the source differs, so selecting any byte but 23:16 fails.
AppendVMovU32(&code, 20, 1);
AppendVMovLiteral(&code, 2, 0x11a22233u);
AppendVMovLiteral(&code, 0, 0x87654321u);
code.push_back(EncodeDs0(0xa0));
code.push_back(EncodeDs1(0, 2, 20)); // ds_write_b8_d16_hi v20, v2
code.push_back(EncodeDs0(0x36));
code.push_back(EncodeDs1(4, 0, 1)); // ds_read_b32 v4, v1
AppendStoreVgpr(&code, 4, 0);
AppendStoreVgpr(&code, 0, 1);
AppendEnd(&code);
TestCase test{"DsWriteB8D16HiWritesByteTwo",
code,
std::vector<u32>(2, 0),
{0xdeada2efu, 0x87654321u},
{O::V_MOV_B32, O::DS_WRITE_B32, O::DS_WRITE_B8_D16_HI,
O::DS_READ_B32, O::BUFFER_STORE_DWORD, O::S_ENDPGM}};
test.decoded_counts = {{"DS_WRITE_B8_D16_HI", 1}};
return test;
}
TestCase DsReadU16D16HiCapturedPreservesLowHalf() {
using O = ShaderOpcode;
@@ -28177,6 +28210,7 @@ std::vector<TestCase> MakeCases() {
AddCase(ScratchIsPrivatePerInvocation);
AddCase(DsReadWriteVariants);
AddCase(DsWriteB16D16HiCapturedUsesHighHalf);
AddCase(DsWriteB8D16HiWritesByteTwo);
AddCase(DsReadU16D16CapturedPreservesHighHalf);
AddCase(DsReadU16D16HiCapturedPreservesLowHalf);
AddCase(DsAppendConsumeUsesEncodedLdsSelector);