mirror of
https://github.com/shadps4-emu/shadPS4.git
synced 2025-07-22 18:15:14 +00:00
shader_recompiler: Separate vertex inputs from LS stage, cleanup tess
This commit is contained in:
parent
b16b9a1544
commit
dde954a3cb
@ -52,7 +52,7 @@ Id VsOutputAttrPointer(EmitContext& ctx, VsOutput output) {
|
||||
Id OutputAttrPointer(EmitContext& ctx, IR::Attribute attr, u32 element) {
|
||||
if (IR::IsParam(attr)) {
|
||||
const u32 attr_index{u32(attr) - u32(IR::Attribute::Param0)};
|
||||
if (ctx.stage == Stage::Local && ctx.runtime_info.ls_info.links_with_tcs) {
|
||||
if (ctx.stage == Stage::Local) {
|
||||
const auto component_ptr = ctx.TypePointer(spv::StorageClass::Output, ctx.F32[1]);
|
||||
return ctx.OpAccessChain(component_ptr, ctx.output_attr_array, ctx.ConstU32(attr_index),
|
||||
ctx.ConstU32(element));
|
||||
@ -94,13 +94,9 @@ Id OutputAttrPointer(EmitContext& ctx, IR::Attribute attr, u32 element) {
|
||||
|
||||
std::pair<Id, bool> OutputAttrComponentType(EmitContext& ctx, IR::Attribute attr) {
|
||||
if (IR::IsParam(attr)) {
|
||||
if (ctx.stage == Stage::Local && ctx.runtime_info.ls_info.links_with_tcs) {
|
||||
return {ctx.F32[1], false};
|
||||
} else {
|
||||
const u32 index{u32(attr) - u32(IR::Attribute::Param0)};
|
||||
const auto& info{ctx.output_params.at(index)};
|
||||
return {info.component_type, info.is_integer};
|
||||
}
|
||||
const u32 index{u32(attr) - u32(IR::Attribute::Param0)};
|
||||
const auto& info{ctx.output_params.at(index)};
|
||||
return {info.component_type, info.is_integer};
|
||||
}
|
||||
if (IR::IsMrt(attr)) {
|
||||
const u32 index{u32(attr) - u32(IR::Attribute::RenderTarget0)};
|
||||
|
@ -551,7 +551,7 @@ void EmitContext::DefineOutputs() {
|
||||
cull_distances =
|
||||
DefineVariable(type, spv::BuiltIn::CullDistance, spv::StorageClass::Output);
|
||||
}
|
||||
if (stage == Shader::Stage::Local && runtime_info.ls_info.links_with_tcs) {
|
||||
if (stage == Stage::Local) {
|
||||
const u32 num_attrs = Common::AlignUp(runtime_info.ls_info.ls_stride, 16) >> 4;
|
||||
if (num_attrs > 0) {
|
||||
const Id type{TypeArray(F32[4], ConstU32(num_attrs))};
|
||||
@ -737,19 +737,19 @@ EmitContext::BufferSpv EmitContext::DefineBuffer(bool is_storage, bool is_writte
|
||||
Decorate(id, spv::Decoration::NonWritable);
|
||||
}
|
||||
switch (buffer_type) {
|
||||
case Shader::BufferType::GdsBuffer:
|
||||
case BufferType::GdsBuffer:
|
||||
Name(id, "gds_buffer");
|
||||
break;
|
||||
case Shader::BufferType::Flatbuf:
|
||||
case BufferType::Flatbuf:
|
||||
Name(id, "srt_flatbuf");
|
||||
break;
|
||||
case Shader::BufferType::BdaPagetable:
|
||||
case BufferType::BdaPagetable:
|
||||
Name(id, "bda_pagetable");
|
||||
break;
|
||||
case Shader::BufferType::FaultBuffer:
|
||||
case BufferType::FaultBuffer:
|
||||
Name(id, "fault_buffer");
|
||||
break;
|
||||
case Shader::BufferType::SharedMemory:
|
||||
case BufferType::SharedMemory:
|
||||
Name(id, "ssbo_shmem");
|
||||
break;
|
||||
default:
|
||||
|
@ -90,27 +90,40 @@ void Translator::EmitPrologue(IR::Block* first_block) {
|
||||
case LogicalStage::Vertex:
|
||||
// v0: vertex ID, always present
|
||||
ir.SetVectorReg(dst_vreg++, ir.GetAttributeU32(IR::Attribute::VertexId));
|
||||
// v1: instance ID, step rate 0
|
||||
if (runtime_info.num_input_vgprs > 0) {
|
||||
if (runtime_info.vs_info.step_rate_0 != 0) {
|
||||
ir.SetVectorReg(dst_vreg++, ir.IDiv(ir.GetAttributeU32(IR::Attribute::InstanceId),
|
||||
ir.Imm32(runtime_info.vs_info.step_rate_0)));
|
||||
} else {
|
||||
if (info.stage == Stage::Local) {
|
||||
// v1: rel patch ID
|
||||
if (runtime_info.num_input_vgprs > 0) {
|
||||
ir.SetVectorReg(dst_vreg++, ir.Imm32(0));
|
||||
}
|
||||
}
|
||||
// v2: instance ID, step rate 1
|
||||
if (runtime_info.num_input_vgprs > 1) {
|
||||
if (runtime_info.vs_info.step_rate_1 != 0) {
|
||||
ir.SetVectorReg(dst_vreg++, ir.IDiv(ir.GetAttributeU32(IR::Attribute::InstanceId),
|
||||
ir.Imm32(runtime_info.vs_info.step_rate_1)));
|
||||
} else {
|
||||
ir.SetVectorReg(dst_vreg++, ir.Imm32(0));
|
||||
// v2: instance ID
|
||||
if (runtime_info.num_input_vgprs > 1) {
|
||||
ir.SetVectorReg(dst_vreg++, ir.GetAttributeU32(IR::Attribute::InstanceId));
|
||||
}
|
||||
} else {
|
||||
// v1: instance ID, step rate 0
|
||||
if (runtime_info.num_input_vgprs > 0) {
|
||||
if (runtime_info.vs_info.step_rate_0 != 0) {
|
||||
ir.SetVectorReg(dst_vreg++,
|
||||
ir.IDiv(ir.GetAttributeU32(IR::Attribute::InstanceId),
|
||||
ir.Imm32(runtime_info.vs_info.step_rate_0)));
|
||||
} else {
|
||||
ir.SetVectorReg(dst_vreg++, ir.Imm32(0));
|
||||
}
|
||||
}
|
||||
// v2: instance ID, step rate 1
|
||||
if (runtime_info.num_input_vgprs > 1) {
|
||||
if (runtime_info.vs_info.step_rate_1 != 0) {
|
||||
ir.SetVectorReg(dst_vreg++,
|
||||
ir.IDiv(ir.GetAttributeU32(IR::Attribute::InstanceId),
|
||||
ir.Imm32(runtime_info.vs_info.step_rate_1)));
|
||||
} else {
|
||||
ir.SetVectorReg(dst_vreg++, ir.Imm32(0));
|
||||
}
|
||||
}
|
||||
// v3: instance ID, plain
|
||||
if (runtime_info.num_input_vgprs > 2) {
|
||||
ir.SetVectorReg(dst_vreg++, ir.GetAttributeU32(IR::Attribute::InstanceId));
|
||||
}
|
||||
}
|
||||
// v3: instance ID, plain
|
||||
if (runtime_info.num_input_vgprs > 2) {
|
||||
ir.SetVectorReg(dst_vreg++, ir.GetAttributeU32(IR::Attribute::InstanceId));
|
||||
}
|
||||
break;
|
||||
case LogicalStage::Fragment:
|
||||
|
@ -33,12 +33,9 @@ void RingAccessElimination(const IR::Program& program, const RuntimeInfo& runtim
|
||||
bool is_composite = opcode == IR::Opcode::WriteSharedU64;
|
||||
u32 num_components = opcode == IR::Opcode::WriteSharedU32 ? 1 : 2;
|
||||
|
||||
u32 offset = 0;
|
||||
const auto* addr = inst.Arg(0).InstRecursive();
|
||||
if (addr->GetOpcode() == IR::Opcode::IAdd32) {
|
||||
ASSERT(addr->Arg(1).IsImmediate());
|
||||
offset = addr->Arg(1).U32();
|
||||
}
|
||||
ASSERT(inst.Arg(0).IsImmediate());
|
||||
|
||||
u32 offset = inst.Arg(0).U32();
|
||||
IR::Value data = is_composite ? ir.UnpackUint2x32(IR::U64{inst.Arg(1).Resolve()})
|
||||
: inst.Arg(1).Resolve();
|
||||
for (s32 i = 0; i < num_components; i++) {
|
||||
|
@ -42,7 +42,6 @@ constexpr u32 MaxStageTypes = static_cast<u32>(LogicalStage::NumLogicalStages);
|
||||
|
||||
struct LocalRuntimeInfo {
|
||||
u32 ls_stride;
|
||||
bool links_with_tcs;
|
||||
|
||||
auto operator<=>(const LocalRuntimeInfo&) const noexcept = default;
|
||||
};
|
||||
|
@ -94,15 +94,10 @@ const Shader::RuntimeInfo& PipelineCache::BuildRuntimeInfo(Stage stage, LogicalS
|
||||
switch (stage) {
|
||||
case Stage::Local: {
|
||||
BuildCommon(regs.ls_program);
|
||||
if (regs.stage_enable.IsStageEnabled(static_cast<u32>(Stage::Hull))) {
|
||||
info.ls_info.links_with_tcs = true;
|
||||
Shader::TessellationDataConstantBuffer tess_constants;
|
||||
const auto* pgm = regs.ProgramForStage(static_cast<u32>(Stage::Hull));
|
||||
const auto params = Liverpool::GetParams(*pgm);
|
||||
const auto& hull_info = program_cache.at(params.hash)->info;
|
||||
hull_info.ReadTessConstantBuffer(tess_constants);
|
||||
info.ls_info.ls_stride = tess_constants.ls_stride;
|
||||
}
|
||||
Shader::TessellationDataConstantBuffer tess_constants;
|
||||
const auto* hull_info = infos[u32(Shader::LogicalStage::TessellationControl)];
|
||||
hull_info->ReadTessConstantBuffer(tess_constants);
|
||||
info.ls_info.ls_stride = tess_constants.ls_stride;
|
||||
break;
|
||||
}
|
||||
case Stage::Hull: {
|
||||
|
Loading…
Reference in New Issue
Block a user