Files
KytyPS5/src/graphics/shader/recompiler/decompiler/ShaderDecoder.h
T

683 lines
12 KiB
C++

#ifndef EMULATOR_INCLUDE_EMULATOR_GRAPHICS_SHADER_RECOMPILER_SHADERDECODER_H_
#define EMULATOR_INCLUDE_EMULATOR_GRAPHICS_SHADER_RECOMPILER_SHADERDECODER_H_
#include "common/common.h"
#include "common/stringUtils.h"
#include <span>
#include <vector>
namespace Libs::Graphics::ShaderRecompiler::Decoder {
enum class Family {
Unknown,
SOP1,
SOP2,
SOPK,
SOPC,
SOPP,
VOP1,
VOP2,
VOP3,
VOP3P,
VOPC,
VINTRP,
SMEM,
MUBUF,
MTBUF,
FLAT,
DS,
MIMG,
EXP
};
enum class Opcode {
Unknown,
Unsupported,
SMovB32,
SMovB64,
SMovkI32,
SAbsI32,
SBrevB32,
SBcnt1I32B32,
SBcnt1I32B64,
SFf1I32B32,
SFlbitI32B64,
SBitreplicateB64B32,
SGetpcB64,
SSetpcB64,
SAndSaveexecB32,
SAndn1SaveexecB32,
SAndSaveexecB64,
SOrn2SaveexecB64,
SAndn1SaveexecB64,
SNotB32,
SNotB64,
SWqmB64,
SAddU32,
SAddcU32,
SSubbU32,
SSubU32,
SAddI32,
SSubI32,
SBitcmp0B32,
SBitcmp1B32,
SBitset0B32,
SBitset1B32,
SMinI32,
SMaxI32,
SMinU32,
SMaxU32,
SAndB32,
SAndB64,
SAndn2B32,
SAndn2B64,
SOrB32,
SOrB64,
SOrn2B32,
SOrn2B64,
SXorB32,
SXorB64,
SNandB32,
SNandB64,
SNorB32,
SNorB64,
SXnorB32,
SXnorB64,
SLshlB32,
SLshlB64,
SLshl1AddU32,
SLshl2AddU32,
SLshl3AddU32,
SLshl4AddU32,
SLshrB32,
SLshrB64,
SAshrI32,
SMulI32,
SMulHiU32,
SMulkI32,
SBfeU32,
SBfeU64,
SBfmB32,
SBfmB64,
SCselectB32,
SCselectB64,
SPackLlB32B16,
SPackLhB32B16,
SPackHhB32B16,
SCmpEqI32,
SCmpLgI32,
SCmpGtI32,
SCmpGeI32,
SCmpLtI32,
SCmpLeI32,
SCmpEqU32,
SCmpLgU32,
SCmpGtU32,
SCmpGeU32,
SCmpLtU32,
SCmpLeU32,
SCmpLgU64,
VNop,
VMovB32,
VMovreldB32,
VMovrelsB32,
VReadfirstlaneB32,
VReadlaneB32,
VWritelaneB32,
VPermlane16B32,
VPermlanex16B32,
VCubeidF32,
VCubescF32,
VCubetcF32,
VCubemaF32,
VCndmaskB32,
VDot2cF32F16,
VCvtF32I32,
VCvtF32U32,
VCvtU32F32,
VCvtI32F32,
VCvtF16F32,
VCvtF32F16,
VCvtF16U16,
VCvtU16F16,
VCvtF16I16,
VCvtI16F16,
VCvtRpiI32F32,
VCvtFlrI32F32,
VCvtOffF32I4,
VCvtF32Ubyte0,
VCvtF32Ubyte1,
VCvtF32Ubyte2,
VCvtF32Ubyte3,
VRcpF32,
VFractF32,
VTruncF32,
VCeilF32,
VRndneF32,
VFloorF32,
VExpF32,
VLogF32,
VRsqF32,
VSqrtF32,
VRcpF16,
VSqrtF16,
VRsqF16,
VLogF16,
VExpF16,
VFloorF16,
VCeilF16,
VTruncF16,
VRndneF16,
VSinF32,
VCosF32,
VNotB32,
VBfrevB32,
VFfbhU32,
VFfblB32,
VAddF32,
VSubF32,
VSubrevF32,
VMulF32,
VMacF32,
VMadmkF32,
VMadakF32,
VMinF32,
VMaxF32,
VAddF16,
VSubF16,
VSubrevF16,
VMulF16,
VFmacF16,
VFmamkF16,
VFmaakF16,
VMinI32,
VMaxI32,
VMulI32I24,
VMulU32U24,
VMulLoU32,
VMulHiU32,
VMulLoI32,
VMulHiI32,
VCvtPkrtzF16F32,
VCvtPkU8F32,
VMadF32,
VMadI32I24,
VMadU32U24,
VMadU64U32,
VFmaF32,
VFmaF16,
VPackB32F16,
VBfeU32,
VBfeI32,
VBfiB32,
VAlignbitB32,
VMin3F32,
VMin3I32,
VMin3U32,
VMin3F16,
VMax3F32,
VMax3I32,
VMax3U32,
VMax3F16,
VMed3F32,
VMed3I32,
VMed3U32,
VMed3F16,
VSadU32,
VAdd3U32,
VLshlAddU32,
VAddLshlU32,
VXadU32,
VLshlOrB32,
VAndOrB32,
VOr3B32,
VXor3B32,
VAddI32,
VSubI32,
VSubrevI32,
VBfmB32,
VLdexpF32,
VCvtPknormI16F32,
VCvtPknormU16F32,
VCvtPkU16U32,
VPkMadI16,
VPkMulLoU16,
VPkAddI16,
VPkSubI16,
VPkLshlrevB16,
VPkLshrrevB16,
VPkAshrrevI16,
VPkMaxI16,
VPkMinI16,
VPkMadU16,
VPkAddF16,
VPkMulF16,
VPkMinF16,
VPkMaxF16,
VPkFmaF16,
VPkFmacF16,
VPkAddU16,
VPkSubU16,
VPkMaxU16,
VPkMinU16,
VMadMixloF16,
VMadMixhiF16,
VAddNcU32,
VAddcU32,
VSubNcU32,
VSubrevNcU32,
VAddNcU16,
VSubNcU16,
VMaxU16,
VMaxI16,
VMinU16,
VMinI16,
VAddNcI16,
VSubNcI16,
VAndB32,
VOrB32,
VXorB32,
VXnorB32,
VLshlB32,
VLshlrevB32,
VLshrB32,
VLshrrevB32,
VAshrI32,
VAshrrevI32,
VLshlrevB16,
VLshrrevB16,
VAshrrevI16,
VBcntU32B32,
VMbcntLoU32B32,
VMbcntHiU32B32,
VMinU32,
VMaxU32,
VMaxF16,
VMinF16,
VCmpFF32,
VCmpLtF32,
VCmpEqF32,
VCmpLeF32,
VCmpGtF32,
VCmpLgF32,
VCmpGeF32,
VCmpOF32,
VCmpUF32,
VCmpNgeF32,
VCmpNlgF32,
VCmpNgtF32,
VCmpNleF32,
VCmpNeqF32,
VCmpNltF32,
VCmpTruF32,
VCmpxLtF32,
VCmpxEqF32,
VCmpxLeF32,
VCmpxGtF32,
VCmpxLgF32,
VCmpxGeF32,
VCmpxNgeF32,
VCmpxNlgF32,
VCmpxNgtF32,
VCmpxNleF32,
VCmpxNeqF32,
VCmpxNltF32,
VCmpFI32,
VCmpLtI32,
VCmpEqI32,
VCmpLeI32,
VCmpGtI32,
VCmpNeI32,
VCmpGeI32,
VCmpTI32,
VCmpClassF32,
VCmpLtI16,
VCmpEqI16,
VCmpLeI16,
VCmpGtI16,
VCmpNeI16,
VCmpGeI16,
VCmpLtF16,
VCmpEqF16,
VCmpLeF16,
VCmpGtF16,
VCmpLgF16,
VCmpGeF16,
VCmpNeqF16,
VCmpxLtF16,
VCmpxEqF16,
VCmpxLeF16,
VCmpxGtF16,
VCmpxGeF16,
VCmpxNeqF16,
VCmpxNltF16,
VCmpxLtI32,
VCmpxEqI32,
VCmpxLeI32,
VCmpxGtI32,
VCmpxNeI32,
VCmpxGeI32,
VCmpLtU16,
VCmpEqU16,
VCmpLeU16,
VCmpGtU16,
VCmpNeU16,
VCmpGeU16,
VCmpFU32,
VCmpLtU32,
VCmpEqU32,
VCmpLeU32,
VCmpGtU32,
VCmpNeU32,
VCmpGeU32,
VCmpTU32,
VCmpNeU64,
VCmpxLtU32,
VCmpxEqU32,
VCmpxLeU32,
VCmpxGtU32,
VCmpxNeU32,
VCmpxGeU32,
SLoadDword,
SLoadDwordx2,
SLoadDwordx4,
SLoadDwordx8,
SLoadDwordx16,
SBufferLoadDword,
SBufferLoadDwordx2,
SBufferLoadDwordx4,
SBufferLoadDwordx8,
SBufferLoadDwordx16,
BufferLoadFormatX,
BufferLoadFormatXy,
BufferLoadFormatXyz,
BufferLoadFormatXyzw,
BufferStoreFormatX,
BufferStoreFormatXy,
BufferStoreFormatXyz,
BufferStoreFormatXyzw,
BufferLoadUbyte,
BufferLoadSbyte,
BufferLoadUshort,
BufferLoadSshort,
BufferLoadDword,
BufferLoadDwordx2,
BufferLoadDwordx3,
BufferLoadDwordx4,
BufferStoreByte,
BufferStoreShort,
BufferStoreDword,
BufferStoreDwordx2,
BufferStoreDwordx3,
BufferStoreDwordx4,
TBufferLoadFormatX,
TBufferLoadFormatXy,
TBufferLoadFormatXyz,
TBufferLoadFormatXyzw,
TBufferStoreFormatX,
TBufferStoreFormatXy,
TBufferStoreFormatXyz,
TBufferStoreFormatXyzw,
BufferAtomicSwap,
BufferAtomicAdd,
BufferAtomicSub,
BufferAtomicSMin,
BufferAtomicUMin,
BufferAtomicSMax,
BufferAtomicUMax,
BufferAtomicAnd,
BufferAtomicOr,
BufferAtomicXor,
FlatLoadUbyte,
FlatLoadSbyte,
FlatLoadUshort,
FlatLoadSshort,
FlatLoadDword,
FlatLoadDwordx2,
FlatLoadDwordx3,
FlatLoadDwordx4,
FlatStoreByte,
FlatStoreShort,
FlatStoreDword,
FlatStoreDwordx2,
FlatStoreDwordx3,
FlatStoreDwordx4,
DsAddU32,
DsAddRtnU32,
DsSubU32,
DsSubRtnU32,
DsMinI32,
DsMinRtnI32,
DsMaxI32,
DsMaxRtnI32,
DsMinU32,
DsMinRtnU32,
DsMaxU32,
DsMaxRtnU32,
DsAndB32,
DsAndRtnB32,
DsOrB32,
DsOrRtnB32,
DsXorB32,
DsXorRtnB32,
DsWrxchgRtnB32,
DsMinF32,
DsMaxF32,
DsSwizzleB32,
DsConsume,
DsAppend,
DsReadSbyte,
DsReadUbyte,
DsReadSshort,
DsReadUshort,
DsRead2B32,
DsReadB32,
DsReadB64,
DsRead2B64,
DsRead2St64B64,
DsReadB96,
DsReadB128,
DsWriteByte,
DsWriteShort,
DsWrite2B32,
DsWrite2St64B32,
DsWrite2B64,
DsWrite2St64B64,
DsWriteB32,
DsWriteB64,
DsWriteB96,
DsWriteB128,
DsWriteAddtidB32,
DsReadAddtidB32,
ImageGetResinfo,
ImageGetLod,
ImageLoad,
ImageLoadMip,
ImageStore,
ImageStoreMip,
ImageAtomicAdd,
ImageAtomicUMin,
ImageAtomicUMax,
ImageAtomicAnd,
ImageAtomicOr,
ImageAtomicXor,
ImageSample,
ImageGather4Lz,
ImageGather4C,
ImageGather4CLz,
ImageGather4LzO,
ImageGather4CO,
ImageGather4CLzO,
ImageGather4H,
VInterpP1F32,
VInterpP2F32,
VInterpMovF32,
SNop,
SWaitcnt,
SBarrier,
SBranch,
SCbranchScc0,
SCbranchScc1,
SCbranchVccz,
SCbranchVccnz,
SCbranchExecz,
SCbranchExecnz,
SSendmsg,
SSetregB32,
SSleep,
STtraceData,
SInstPrefetch,
SEndpgm,
Exp
};
enum class OperandKind {
Unknown,
LiteralConstant,
IntegerInlineConstant,
FloatInlineConstant,
Sgpr,
VccLo,
VccHi,
VccZ,
ExecLo,
ExecHi,
ExecZ,
Scc,
M0,
PopsExitingWaveId,
Null,
Vgpr,
};
enum ImageSampleFlag : uint32_t {
ImageSampleFlagLod = 1u << 0u,
ImageSampleFlagBias = 1u << 1u,
ImageSampleFlagDerivative = 1u << 2u,
ImageSampleFlagCompare = 1u << 3u,
ImageSampleFlagOffset = 1u << 4u,
ImageSampleFlagLevelZero = 1u << 5u,
ImageSampleFlagLodClamp = 1u << 6u,
ImageSampleFlagA16 = 1u << 7u,
ImageSampleFlagCd = 1u << 8u,
ImageSampleFlagGatherHorizontal = 1u << 9u,
};
enum class ImageDimension : uint32_t {
Unknown,
Dim1D,
Dim1DArray,
Dim2D,
Dim3D,
Dim2DArray,
Dim2DMsaa,
Dim2DMsaaArray,
};
constexpr uint32_t MaxInstructionRawWords = 5u;
constexpr uint32_t MaxImageNsaAddressComponents = 12u;
struct Operand {
OperandKind kind = OperandKind::Unknown;
uint32_t value = 0;
int32_t signed_val = 0;
float float_val = 0.0f;
uint32_t reg = 0;
uint32_t sdwa_sel = 6;
uint32_t sdwa_dst_unused = 0;
uint32_t omod = 0;
uint32_t dpp_ctrl = 0;
uint32_t dpp_row_mask = 0xf;
uint32_t dpp_bank_mask = 0xf;
bool sdwa_sext = false;
bool dpp_fetch_inactive = false;
bool dpp_bound_ctrl = false;
bool op_sel = false;
bool op_sel_hi = false;
bool negate = false;
bool negate_hi = false;
bool absolute = false;
bool clamp = false;
bool dpp = false;
};
struct Instruction {
uint32_t pc = 0;
uint32_t word = 0;
uint32_t word_count = 1;
uint32_t raw[MaxInstructionRawWords] = {};
uint32_t raw_count = 1;
Family family = Family::Unknown;
uint32_t opcode_id = 0;
Opcode opcode = Opcode::Unknown;
Operand dst;
Operand dst2;
Operand src0;
Operand src1;
Operand src2;
Operand src3;
uint32_t src_count = 0;
uint32_t offset = 0;
uint32_t secondary_offset = 0;
uint32_t dmask = 0;
uint32_t data_dwords = 1;
uint32_t data_bits = 32;
uint32_t data_format = 0;
uint32_t number_format = 0;
uint32_t image_sample_flags = 0;
ImageDimension image_dimension = ImageDimension::Unknown;
uint32_t image_address_components = 0;
uint32_t image_nsa_dwords = 0;
uint32_t image_nsa_addr[MaxImageNsaAddressComponents] = {};
uint32_t memory_segment = 0;
bool data_signed = false;
bool typed = false;
bool formatted = false;
bool gds = false;
bool glc = false;
bool slc = false;
bool idxen = false;
bool offen = false;
int32_t branch_offset = 0;
uint32_t branch_target = 0;
struct {
uint32_t target = 0;
uint32_t en = 0;
bool done = false;
bool compr = false;
bool vm = false;
} exp;
std::string unsupported_reason;
};
struct Program {
std::span<const uint32_t> code;
std::vector<Instruction> instructions;
};
bool DecodeProgram(std::span<const uint32_t> code, Program& program, std::string* error);
bool DecodeScalarSource(uint32_t code, uint32_t pc, Operand& operand, std::string* error);
bool DecodeScalarDestination(uint32_t code, uint32_t pc, Operand& operand, std::string* error);
bool DecodeVectorGpr(uint32_t reg, Operand& operand, std::string* error);
bool ReadLiteralOperands(std::span<const uint32_t> code, uint32_t word_index, Instruction& inst,
std::string* error);
void SetRawWords(Instruction& inst, std::span<const uint32_t> code, uint32_t word_index,
uint32_t word_count);
void SetUnsupported(Instruction& inst, Family family, uint32_t opcode_id, const char* reason);
std::string FamilyToString(Family family);
std::string OpcodeToString(Opcode opcode);
std::string OperandToString(const Operand& operand);
const char* ImageDimensionToString(ImageDimension dimension);
std::string InstructionToString(const Instruction& inst);
std::string ProgramToString(const Program& program);
} // namespace Libs::Graphics::ShaderRecompiler::Decoder
#endif /* EMULATOR_INCLUDE_EMULATOR_GRAPHICS_SHADER_RECOMPILER_SHADERDECODER_H_ */