shader: treat call-target registers with several reaching definitions as GPU-selected

This commit is contained in:
nmzik committed 2026-10-31 04:07:35 +01:00
1 parent ee034be4b2
commit abd77f574c
4 files changed
+24 -10

No files matched your search

@@ -1720,9 +1720,9 @@ bool MayWriteScalarRegister(const Decoder::Instruction& inst, uint32_t code, uin
return InstructionWritesScalarCode(inst, code);
}
uint32_t FindScalarDefinition(const Decoder::Program& program, const Graph& graph,
uint32_t before, uint32_t code, uint32_t wave_size,
std::vector<uint32_t>& crossed_calls) {
std::optional<uint32_t> FindScalarDefinition(const Decoder::Program& program, const Graph& graph,
uint32_t before, uint32_t code, uint32_t wave_size,
std::vector<uint32_t>& crossed_calls) {
EXIT_IF(before >= program.instructions.size());
const auto found = std::ranges::find_if(graph.blocks, [before](const auto& block) {
return block.inst_begin <= before && before < block.inst_end;
@@ -1748,7 +1748,7 @@ uint32_t FindScalarDefinition(const Decoder::Program& program, const Graph& grap
if (MayWriteScalarRegister(inst, code, wave_size)) { index = i; break; }
}
if (index != UINT32_MAX || block->id == graph.entry_block) {
EXIT_IF(definition && *definition != index);
if (definition && *definition != index) return std::nullopt;
definition = index;
continue;
}
@@ -1758,7 +1758,7 @@ uint32_t FindScalarDefinition(const Decoder::Program& program, const Graph& grap
}
}
EXIT_IF(!definition);
return *definition;
return definition;
}
std::string BranchConditionToString(BranchCondition condition) {
@@ -5,6 +5,7 @@
#include "common/stringUtils.h"
#include "graphics/shader/recompiler/frontend/decode/ShaderDecoder.h"
#include <optional>
#include <vector>
namespace Libs::Graphics::ShaderRecompiler::CFG {
@@ -114,9 +115,11 @@ struct Graph {
Graph BuildGraph(const Decoder::Program& program);
bool MayWriteScalarRegister(const Decoder::Instruction& inst, uint32_t code, uint32_t wave_size);
uint32_t FindScalarDefinition(const Decoder::Program& program, const Graph& graph,
uint32_t before, uint32_t code, uint32_t wave_size,
std::vector<uint32_t>& crossed_calls);
// Returns the one instruction defining `code` that reaches `before` (UINT32_MAX: the entry value),
// or nullopt if several do.
std::optional<uint32_t> FindScalarDefinition(const Decoder::Program& program, const Graph& graph,
uint32_t before, uint32_t code, uint32_t wave_size,
std::vector<uint32_t>& crossed_calls);
// Returns structured control flow or failure diagnostics without changing the native graph.
// On failure, failure_block is an original block ID or UINT32_MAX.
Graph Structurize(const Graph& graph);