[D3D12] DXBC RDEF types
This commit is contained in:
parent
443e371a94
commit
6d783fd3bf
|
@ -28,6 +28,8 @@ void DxbcShaderTranslator::Reset() {
|
||||||
ShaderTranslator::Reset();
|
ShaderTranslator::Reset();
|
||||||
|
|
||||||
shader_code_.clear();
|
shader_code_.clear();
|
||||||
|
|
||||||
|
rdef_constants_used_ = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
std::vector<uint8_t> DxbcShaderTranslator::CompleteTranslation() {
|
std::vector<uint8_t> DxbcShaderTranslator::CompleteTranslation() {
|
||||||
|
@ -89,20 +91,43 @@ uint32_t DxbcShaderTranslator::AppendString(std::vector<uint32_t>& dest,
|
||||||
return uint32_t(size_aligned);
|
return uint32_t(size_aligned);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const DxbcShaderTranslator::RdefStructMember
|
||||||
|
DxbcShaderTranslator::rdef_float_constant_page_member_ = {
|
||||||
|
"c", RdefTypeIndex::kFloat4Array32, 0};
|
||||||
|
|
||||||
|
const DxbcShaderTranslator::RdefType DxbcShaderTranslator::rdef_types_[size_t(
|
||||||
|
DxbcShaderTranslator::RdefTypeIndex::kCount)] = {
|
||||||
|
{"float", 0, 3, 1, 1, 0, 0, RdefTypeIndex::kUnknown, nullptr},
|
||||||
|
{"float2", 1, 3, 1, 2, 0, 0, RdefTypeIndex::kUnknown, nullptr},
|
||||||
|
{"float3", 1, 3, 1, 3, 0, 0, RdefTypeIndex::kUnknown, nullptr},
|
||||||
|
{"float4", 1, 3, 1, 4, 0, 0, RdefTypeIndex::kUnknown, nullptr},
|
||||||
|
{"int", 0, 2, 1, 1, 0, 0, RdefTypeIndex::kUnknown, nullptr},
|
||||||
|
{"uint", 0, 19, 1, 1, 0, 0, RdefTypeIndex::kUnknown, nullptr},
|
||||||
|
{"uint4", 1, 19, 1, 4, 0, 0, RdefTypeIndex::kUnknown, nullptr},
|
||||||
|
{nullptr, 1, 3, 1, 4, 20, 0, RdefTypeIndex::kFloat4, nullptr},
|
||||||
|
{nullptr, 1, 19, 1, 4, 8, 0, RdefTypeIndex::kUint4, nullptr},
|
||||||
|
{nullptr, 1, 19, 1, 4, 32, 0, RdefTypeIndex::kUint4, nullptr},
|
||||||
|
{nullptr, 1, 19, 1, 4, 48, 0, RdefTypeIndex::kUint4, nullptr},
|
||||||
|
{"XeFloatConstantPage", 5, 0, 1, 128, 1, 1, RdefTypeIndex::kUnknown,
|
||||||
|
&rdef_float_constant_page_member_},
|
||||||
|
};
|
||||||
|
|
||||||
void DxbcShaderTranslator::WriteResourceDefinitions() {
|
void DxbcShaderTranslator::WriteResourceDefinitions() {
|
||||||
uint32_t chunk_position_dwords = uint32_t(shader_object_.size());
|
uint32_t chunk_position_dwords = uint32_t(shader_object_.size());
|
||||||
|
uint32_t new_offset;
|
||||||
|
|
||||||
// Write the header.
|
// TODO(Triang3l): Include shared memory, textures, samplers.
|
||||||
|
uint32_t binding_count = uint32_t(RdefConstantBufferIndex::kCount);
|
||||||
|
|
||||||
|
// ***************************************************************************
|
||||||
|
// Header
|
||||||
|
// ***************************************************************************
|
||||||
// Constant buffer count.
|
// Constant buffer count.
|
||||||
// b0 - Xenia system constants.
|
shader_object_.push_back(uint32_t(RdefConstantBufferIndex::kCount));
|
||||||
// b1 - bool and loop constants.
|
|
||||||
// b2 - fetch constants.
|
|
||||||
// b3-b10 - float constants.
|
|
||||||
shader_object_.push_back(4);
|
|
||||||
// Constant buffer offset (set later).
|
// Constant buffer offset (set later).
|
||||||
shader_object_.push_back(0);
|
shader_object_.push_back(0);
|
||||||
// TODO(Triang3l): Bound resource count (CBV + other views) (set later).
|
// Bound resource count (CBV, SRV, UAV, samplers).
|
||||||
shader_object_.push_back(4);
|
shader_object_.push_back(binding_count);
|
||||||
// TODO(Triang3l): Bound resource buffer offset (set later).
|
// TODO(Triang3l): Bound resource buffer offset (set later).
|
||||||
shader_object_.push_back(0);
|
shader_object_.push_back(0);
|
||||||
if (is_vertex_shader()) {
|
if (is_vertex_shader()) {
|
||||||
|
@ -131,10 +156,72 @@ void DxbcShaderTranslator::WriteResourceDefinitions() {
|
||||||
// Generator name.
|
// Generator name.
|
||||||
AppendString(shader_object_, "Xenia");
|
AppendString(shader_object_, "Xenia");
|
||||||
|
|
||||||
// Constant buffers.
|
// ***************************************************************************
|
||||||
uint32_t cbuffer_position_dwords = uint32_t(shader_object_.size());
|
// Constant types
|
||||||
shader_object_[chunk_position_dwords + 1] =
|
// ***************************************************************************
|
||||||
cbuffer_position_dwords * sizeof(uint32_t);
|
// Type names.
|
||||||
|
new_offset = (uint32_t(shader_object_.size()) - chunk_position_dwords) *
|
||||||
|
sizeof(uint32_t);
|
||||||
|
uint32_t type_name_offsets[size_t(RdefTypeIndex::kCount)];
|
||||||
|
for (uint32_t i = 0; i < uint32_t(RdefTypeIndex::kCount); ++i) {
|
||||||
|
const RdefType& type = rdef_types_[i];
|
||||||
|
if (type.name == nullptr) {
|
||||||
|
// Array - use the name of the element type.
|
||||||
|
type_name_offsets[i] =
|
||||||
|
type_name_offsets[uint32_t(type.array_element_type)];
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
type_name_offsets[i] = new_offset;
|
||||||
|
new_offset += AppendString(shader_object_, type.name);
|
||||||
|
}
|
||||||
|
// Types.
|
||||||
|
uint32_t types_position_dwords = uint32_t(shader_object_.size());
|
||||||
|
const uint32_t type_size_dwords = 9;
|
||||||
|
uint32_t types_offset =
|
||||||
|
(types_position_dwords - chunk_position_dwords) * sizeof(uint32_t);
|
||||||
|
const uint32_t type_size = type_size_dwords * sizeof(uint32_t);
|
||||||
|
for (uint32_t i = 0; i < uint32_t(RdefTypeIndex::kCount); ++i) {
|
||||||
|
const RdefType& type = rdef_types_[i];
|
||||||
|
shader_object_.push_back(type.type_class | (type.type << 16));
|
||||||
|
shader_object_.push_back(type.row_count | (type.column_count << 16));
|
||||||
|
shader_object_.push_back(type.element_count |
|
||||||
|
(type.struct_member_count << 16));
|
||||||
|
// Struct member offset (set later).
|
||||||
|
shader_object_.push_back(0);
|
||||||
|
// Unknown.
|
||||||
|
shader_object_.push_back(0);
|
||||||
|
shader_object_.push_back(0);
|
||||||
|
shader_object_.push_back(0);
|
||||||
|
shader_object_.push_back(0);
|
||||||
|
shader_object_.push_back(type_name_offsets[i]);
|
||||||
|
}
|
||||||
|
// Struct members.
|
||||||
|
for (uint32_t i = 0; i < uint32_t(RdefTypeIndex::kCount); ++i) {
|
||||||
|
const RdefType& type = rdef_types_[i];
|
||||||
|
const RdefStructMember* struct_members = type.struct_members;
|
||||||
|
if (struct_members == nullptr) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
uint32_t struct_member_position_dwords = uint32_t(shader_object_.size());
|
||||||
|
shader_object_[types_position_dwords + i * type_size_dwords + 3] =
|
||||||
|
(struct_member_position_dwords - chunk_position_dwords) *
|
||||||
|
sizeof(uint32_t);
|
||||||
|
uint32_t struct_member_count = type.struct_member_count;
|
||||||
|
// Reserve space for names and write types and offsets.
|
||||||
|
for (uint32_t j = 0; j < struct_member_count; ++j) {
|
||||||
|
shader_object_.push_back(0);
|
||||||
|
shader_object_.push_back(types_offset +
|
||||||
|
uint32_t(struct_members[j].type) * type_size);
|
||||||
|
shader_object_.push_back(struct_members[j].offset);
|
||||||
|
}
|
||||||
|
// Write member names.
|
||||||
|
new_offset = (uint32_t(shader_object_.size()) - chunk_position_dwords) *
|
||||||
|
sizeof(uint32_t);
|
||||||
|
for (uint32_t j = 0; j < struct_member_count; ++j) {
|
||||||
|
shader_object_[struct_member_position_dwords + j * 3] = new_offset;
|
||||||
|
new_offset += AppendString(shader_object_, struct_members[j].name);
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
} // namespace gpu
|
} // namespace gpu
|
||||||
|
|
|
@ -23,6 +23,37 @@ class DxbcShaderTranslator : public ShaderTranslator {
|
||||||
DxbcShaderTranslator();
|
DxbcShaderTranslator();
|
||||||
~DxbcShaderTranslator() override;
|
~DxbcShaderTranslator() override;
|
||||||
|
|
||||||
|
struct SystemConstants {
|
||||||
|
// vec4 0
|
||||||
|
float mul_rcp_w[3];
|
||||||
|
uint32_t vertex_base_index;
|
||||||
|
|
||||||
|
// vec4 1
|
||||||
|
float ndc_scale[3];
|
||||||
|
uint32_t vertex_index_endian;
|
||||||
|
|
||||||
|
// vec4 2
|
||||||
|
float ndc_offset[3];
|
||||||
|
float pixel_half_pixel_offset;
|
||||||
|
|
||||||
|
// vec4 3
|
||||||
|
float point_size[2];
|
||||||
|
float ssaa_inv_scale[2];
|
||||||
|
|
||||||
|
// vec3 4
|
||||||
|
uint32_t pixel_pos_reg;
|
||||||
|
// 0 - disabled, 1 - passes if in range, -1 - fails if in range.
|
||||||
|
int32_t alpha_test;
|
||||||
|
// The range is floats as uints so it's easier to pass infinity.
|
||||||
|
uint32_t alpha_test_range[2];
|
||||||
|
|
||||||
|
// vec4 5
|
||||||
|
float color_exp_bias[4];
|
||||||
|
|
||||||
|
// vec4 6
|
||||||
|
uint32_t color_output_map[4];
|
||||||
|
};
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
void Reset() override;
|
void Reset() override;
|
||||||
|
|
||||||
|
@ -39,6 +70,112 @@ class DxbcShaderTranslator : public ShaderTranslator {
|
||||||
// Complete shader object, with all the needed chunks and dcl_ instructions -
|
// Complete shader object, with all the needed chunks and dcl_ instructions -
|
||||||
// generated in the end of translation.
|
// generated in the end of translation.
|
||||||
std::vector<uint32_t> shader_object_;
|
std::vector<uint32_t> shader_object_;
|
||||||
|
|
||||||
|
// Data types used in constants buffers. Listed in dependency order.
|
||||||
|
enum class RdefTypeIndex {
|
||||||
|
kFloat,
|
||||||
|
kFloat2,
|
||||||
|
kFloat3,
|
||||||
|
kFloat4,
|
||||||
|
kInt,
|
||||||
|
kUint,
|
||||||
|
kUint4,
|
||||||
|
// Float constants in one page.
|
||||||
|
kFloat4Array32,
|
||||||
|
// Bool constants.
|
||||||
|
kUint4Array8,
|
||||||
|
// Loop constants.
|
||||||
|
kUint4Array32,
|
||||||
|
// Fetch constants.
|
||||||
|
kUint4Array48,
|
||||||
|
kFloatConstantPageStruct,
|
||||||
|
|
||||||
|
kCount,
|
||||||
|
kUnknown = kCount
|
||||||
|
};
|
||||||
|
|
||||||
|
struct RdefStructMember {
|
||||||
|
const char* name;
|
||||||
|
RdefTypeIndex type;
|
||||||
|
uint32_t offset;
|
||||||
|
};
|
||||||
|
static const RdefStructMember rdef_float_constant_page_member_;
|
||||||
|
|
||||||
|
struct RdefType {
|
||||||
|
// Name ignored for arrays.
|
||||||
|
const char* name;
|
||||||
|
// D3D10_SHADER_VARIABLE_CLASS.
|
||||||
|
uint32_t type_class;
|
||||||
|
// D3D10_SHADER_VARIABLE_TYPE.
|
||||||
|
uint32_t type;
|
||||||
|
uint32_t row_count;
|
||||||
|
uint32_t column_count;
|
||||||
|
// 0 for primitive types, 1 for structures, array size for arrays.
|
||||||
|
uint32_t element_count;
|
||||||
|
uint32_t struct_member_count;
|
||||||
|
RdefTypeIndex array_element_type;
|
||||||
|
const RdefStructMember* struct_members;
|
||||||
|
};
|
||||||
|
static const RdefType rdef_types_[size_t(RdefTypeIndex::kCount)];
|
||||||
|
|
||||||
|
enum class RdefConstantIndex {
|
||||||
|
kSystemConstantFirst,
|
||||||
|
kSysMulRcpW = kSystemConstantFirst,
|
||||||
|
kSysVertexBaseIndex,
|
||||||
|
kSysNDCScale,
|
||||||
|
kSysVertexIndexEndian,
|
||||||
|
kSysNDCOffset,
|
||||||
|
kSysPixelHalfPixelOffset,
|
||||||
|
kSysPointSize,
|
||||||
|
kSysSSAAInvScale,
|
||||||
|
kSysPixelPosReg,
|
||||||
|
kSysAlphaTest,
|
||||||
|
kSysAlphaTestRange,
|
||||||
|
kSysColorExpBias,
|
||||||
|
kSysColorOutputMap,
|
||||||
|
kSystemConstantLast = kSysColorOutputMap,
|
||||||
|
|
||||||
|
kBoolConstants,
|
||||||
|
kLoopConstants,
|
||||||
|
|
||||||
|
kFetchConstants,
|
||||||
|
|
||||||
|
kFloatConstants,
|
||||||
|
|
||||||
|
kCount,
|
||||||
|
kSystemConstantCount = kSystemConstantLast - kSystemConstantFirst + 1,
|
||||||
|
};
|
||||||
|
struct RdefConstant {
|
||||||
|
const char* name;
|
||||||
|
RdefTypeIndex type;
|
||||||
|
uint32_t offset;
|
||||||
|
uint32_t size;
|
||||||
|
};
|
||||||
|
static const RdefConstant rdef_constants_[size_t(RdefConstantIndex::kCount)];
|
||||||
|
static_assert(uint32_t(RdefConstantIndex::kCount) <= 64,
|
||||||
|
"Too many constants in all constant buffers - can't use a 64 "
|
||||||
|
"bit vector to store which constants are used");
|
||||||
|
uint64_t rdef_constants_used_;
|
||||||
|
|
||||||
|
enum class RdefConstantBufferIndex {
|
||||||
|
kSystemConstants,
|
||||||
|
kBoolLoopConstants,
|
||||||
|
kFetchConstants,
|
||||||
|
kFloatConstants,
|
||||||
|
|
||||||
|
kCount
|
||||||
|
};
|
||||||
|
struct RdefConstantBuffer {
|
||||||
|
const char* name;
|
||||||
|
RdefConstantIndex first_constant;
|
||||||
|
uint32_t constant_count;
|
||||||
|
uint32_t size;
|
||||||
|
uint32_t register_index;
|
||||||
|
uint32_t binding_count;
|
||||||
|
bool dynamic_indexed;
|
||||||
|
};
|
||||||
|
static const RdefConstantBuffer
|
||||||
|
rdef_constant_buffers[size_t(RdefConstantBufferIndex::kCount)];
|
||||||
};
|
};
|
||||||
|
|
||||||
} // namespace gpu
|
} // namespace gpu
|
||||||
|
|
Loading…
Reference in New Issue