[GPU] Move all xenos.h to gpu::xenos, disambiguate Dimension/TextureDimension

This commit is contained in:
Triang3l
2020-07-11 15:54:22 +03:00
parent 39490f3c3a
commit 4bb0ca0e09
61 changed files with 1411 additions and 1365 deletions

View File

@@ -173,16 +173,16 @@ void PrimitiveConverter::BeginFrame() {
memory_regions_used_ = 0;
}
PrimitiveType PrimitiveConverter::GetReplacementPrimitiveType(
PrimitiveType type) {
xenos::PrimitiveType PrimitiveConverter::GetReplacementPrimitiveType(
xenos::PrimitiveType type) {
switch (type) {
case PrimitiveType::kTriangleFan:
return PrimitiveType::kTriangleList;
case PrimitiveType::kLineLoop:
return PrimitiveType::kLineStrip;
case PrimitiveType::kQuadList:
case xenos::PrimitiveType::kTriangleFan:
return xenos::PrimitiveType::kTriangleList;
case xenos::PrimitiveType::kLineLoop:
return xenos::PrimitiveType::kLineStrip;
case xenos::PrimitiveType::kQuadList:
if (cvars::d3d12_convert_quads_to_triangles) {
return PrimitiveType::kTriangleList;
return xenos::PrimitiveType::kTriangleList;
}
break;
default:
@@ -192,10 +192,10 @@ PrimitiveType PrimitiveConverter::GetReplacementPrimitiveType(
}
PrimitiveConverter::ConversionResult PrimitiveConverter::ConvertPrimitives(
PrimitiveType source_type, uint32_t address, uint32_t index_count,
IndexFormat index_format, Endian index_endianness,
xenos::PrimitiveType source_type, uint32_t address, uint32_t index_count,
xenos::IndexFormat index_format, xenos::Endian index_endianness,
D3D12_GPU_VIRTUAL_ADDRESS& gpu_address_out, uint32_t& index_count_out) {
bool index_32bit = index_format == IndexFormat::kInt32;
bool index_32bit = index_format == xenos::IndexFormat::kInt32;
auto& regs = *register_file_;
bool reset = regs.Get<reg::PA_SU_SC_MODE_CNTL>().multi_prim_ib_ena;
// Swap the reset index because we will be comparing unswapped values to it.
@@ -207,22 +207,22 @@ PrimitiveConverter::ConversionResult PrimitiveConverter::ConvertPrimitives(
uint32_t reset_index_host = index_32bit ? 0xFFFFFFFFu : 0xFFFFu;
// Degenerate line loops are just lines.
if (source_type == PrimitiveType::kLineLoop && index_count <= 2) {
source_type = PrimitiveType::kLineStrip;
if (source_type == xenos::PrimitiveType::kLineLoop && index_count <= 2) {
source_type = xenos::PrimitiveType::kLineStrip;
}
// Check if need to convert at all.
if (source_type == PrimitiveType::kTriangleStrip ||
source_type == PrimitiveType::kLineStrip) {
if (source_type == xenos::PrimitiveType::kTriangleStrip ||
source_type == xenos::PrimitiveType::kLineStrip) {
if (!reset || reset_index == reset_index_host) {
return ConversionResult::kConversionNotNeeded;
}
} else if (source_type == PrimitiveType::kQuadList) {
} else if (source_type == xenos::PrimitiveType::kQuadList) {
if (!cvars::d3d12_convert_quads_to_triangles) {
return ConversionResult::kConversionNotNeeded;
}
} else if (source_type != PrimitiveType::kTriangleFan &&
source_type != PrimitiveType::kLineLoop) {
} else if (source_type != xenos::PrimitiveType::kTriangleFan &&
source_type != xenos::PrimitiveType::kLineLoop) {
return ConversionResult::kConversionNotNeeded;
}
@@ -232,10 +232,10 @@ PrimitiveConverter::ConversionResult PrimitiveConverter::ConvertPrimitives(
// Exit early for clearly empty draws, without even reading the memory.
uint32_t index_count_min;
if (source_type == PrimitiveType::kLineStrip ||
source_type == PrimitiveType::kLineLoop) {
if (source_type == xenos::PrimitiveType::kLineStrip ||
source_type == xenos::PrimitiveType::kLineLoop) {
index_count_min = 2;
} else if (source_type == PrimitiveType::kQuadList) {
} else if (source_type == xenos::PrimitiveType::kQuadList) {
index_count_min = 4;
} else {
index_count_min = 3;
@@ -308,15 +308,16 @@ PrimitiveConverter::ConversionResult PrimitiveConverter::ConvertPrimitives(
// Optimization specific to primitive types - if reset index not found in the
// source index buffer, can set this to false and use a faster way of copying.
bool reset_actually_used = reset;
if (source_type == PrimitiveType::kTriangleFan) {
if (source_type == xenos::PrimitiveType::kTriangleFan) {
// Triangle fans are not supported by Direct3D 12 at all.
conversion_needed = true;
trace_writer_->WriteMemoryRead(address, index_buffer_size);
if (reset) {
uint32_t current_fan_index_count = 0;
for (uint32_t i = 0; i < index_count; ++i) {
uint32_t index =
index_format == IndexFormat::kInt32 ? source_32[i] : source_16[i];
uint32_t index = index_format == xenos::IndexFormat::kInt32
? source_32[i]
: source_16[i];
if (index == reset_index) {
current_fan_index_count = 0;
continue;
@@ -328,8 +329,8 @@ PrimitiveConverter::ConversionResult PrimitiveConverter::ConvertPrimitives(
} else {
converted_index_count = 3 * (index_count - 2);
}
} else if (source_type == PrimitiveType::kTriangleStrip ||
source_type == PrimitiveType::kLineStrip) {
} else if (source_type == xenos::PrimitiveType::kTriangleStrip ||
source_type == xenos::PrimitiveType::kLineStrip) {
converted_index_count = index_count;
// Check if the restart index is used at all in this buffer because reading
// vertices from a default heap is faster than from an upload heap.
@@ -348,7 +349,7 @@ PrimitiveConverter::ConversionResult PrimitiveConverter::ConvertPrimitives(
check_source = source;
uint32_t check_indices_remaining = index_count;
alignas(16) uint64_t check_result[2];
if (index_format == IndexFormat::kInt32) {
if (index_format == xenos::IndexFormat::kInt32) {
while (check_indices_remaining != 0 && (check_source_uintptr & 15)) {
--check_indices_remaining;
if (*(check_source_32++) == reset_index) {
@@ -402,7 +403,7 @@ PrimitiveConverter::ConversionResult PrimitiveConverter::ConvertPrimitives(
}
}
#else
if (index_format == IndexFormat::kInt32) {
if (index_format == xenos::IndexFormat::kInt32) {
for (uint32_t i = 0; i < index_count; ++i) {
if (source_32[i] == reset_index) {
conversion_needed = true;
@@ -418,15 +419,16 @@ PrimitiveConverter::ConversionResult PrimitiveConverter::ConvertPrimitives(
}
}
#endif // XE_ARCH_AMD64
} else if (source_type == PrimitiveType::kLineLoop) {
} else if (source_type == xenos::PrimitiveType::kLineLoop) {
conversion_needed = true;
trace_writer_->WriteMemoryRead(address, index_buffer_size);
if (reset) {
reset_actually_used = false;
uint32_t current_strip_index_count = 0;
for (uint32_t i = 0; i < index_count; ++i) {
uint32_t index =
index_format == IndexFormat::kInt32 ? source_32[i] : source_16[i];
uint32_t index = index_format == xenos::IndexFormat::kInt32
? source_32[i]
: source_16[i];
if (index == reset_index) {
reset_actually_used = true;
// Loop strips with more than 2 vertices.
@@ -444,7 +446,7 @@ PrimitiveConverter::ConversionResult PrimitiveConverter::ConvertPrimitives(
} else {
converted_index_count = index_count + 1;
}
} else if (source_type == PrimitiveType::kQuadList) {
} else if (source_type == xenos::PrimitiveType::kQuadList) {
conversion_needed = true;
trace_writer_->WriteMemoryRead(address, index_buffer_size);
converted_index_count = (index_count >> 2) * 6;
@@ -471,13 +473,13 @@ PrimitiveConverter::ConversionResult PrimitiveConverter::ConvertPrimitives(
return ConversionResult::kFailed;
}
if (source_type == PrimitiveType::kTriangleFan) {
if (source_type == xenos::PrimitiveType::kTriangleFan) {
// https://docs.microsoft.com/en-us/windows/desktop/direct3d9/triangle-fans
// Ordered as (v1, v2, v0), (v2, v3, v0).
if (reset) {
uint32_t current_fan_index_count = 0;
uint32_t current_fan_first_index = 0;
if (index_format == IndexFormat::kInt32) {
if (index_format == xenos::IndexFormat::kInt32) {
uint32_t* target_32 = reinterpret_cast<uint32_t*>(target);
for (uint32_t i = 0; i < index_count; ++i) {
uint32_t index = source_32[i];
@@ -513,7 +515,7 @@ PrimitiveConverter::ConversionResult PrimitiveConverter::ConvertPrimitives(
}
}
} else {
if (index_format == IndexFormat::kInt32) {
if (index_format == xenos::IndexFormat::kInt32) {
uint32_t* target_32 = reinterpret_cast<uint32_t*>(target);
for (uint32_t i = 2; i < index_count; ++i) {
*(target_32++) = source_32[i - 1];
@@ -529,8 +531,8 @@ PrimitiveConverter::ConversionResult PrimitiveConverter::ConvertPrimitives(
}
}
}
} else if (source_type == PrimitiveType::kTriangleStrip ||
source_type == PrimitiveType::kLineStrip) {
} else if (source_type == xenos::PrimitiveType::kTriangleStrip ||
source_type == xenos::PrimitiveType::kLineStrip) {
#if XE_ARCH_AMD64
// Replace the reset index with the maximum representable value - vector OR
// gives 0 or 0xFFFF/0xFFFFFFFF, which is exactly what is needed.
@@ -549,7 +551,7 @@ PrimitiveConverter::ConversionResult PrimitiveConverter::ConvertPrimitives(
target_aligned_uintptr =
reinterpret_cast<uintptr_t>(target) & ~(uintptr_t(15));
uint32_t vector_count = (address_last >> 4) - (address >> 4) + 1;
if (index_format == IndexFormat::kInt32) {
if (index_format == xenos::IndexFormat::kInt32) {
__m128i reset_index_vector = _mm_set1_epi32(reset_index);
for (uint32_t i = 0; i < vector_count; ++i) {
__m128i indices_vector = _mm_load_si128(source_aligned_128++);
@@ -569,7 +571,7 @@ PrimitiveConverter::ConversionResult PrimitiveConverter::ConvertPrimitives(
}
}
#else
if (index_format == IndexFormat::kInt32) {
if (index_format == xenos::IndexFormat::kInt32) {
for (uint32_t i = 0; i < index_count; ++i) {
uint32_t index = source_32[i];
reinterpret_cast<uint32_t*>(target)[i] =
@@ -583,11 +585,11 @@ PrimitiveConverter::ConversionResult PrimitiveConverter::ConvertPrimitives(
}
}
#endif // XE_ARCH_AMD64
} else if (source_type == PrimitiveType::kLineLoop) {
} else if (source_type == xenos::PrimitiveType::kLineLoop) {
if (reset_actually_used) {
uint32_t current_strip_index_count = 0;
uint32_t current_strip_first_index = 0;
if (index_format == IndexFormat::kInt32) {
if (index_format == xenos::IndexFormat::kInt32) {
uint32_t* target_32 = reinterpret_cast<uint32_t*>(target);
for (uint32_t i = 0; i < index_count; ++i) {
uint32_t index = source_32[i];
@@ -635,16 +637,16 @@ PrimitiveConverter::ConversionResult PrimitiveConverter::ConvertPrimitives(
} else {
std::memcpy(target, source, index_count * index_size);
if (converted_index_count > index_count) {
if (index_format == IndexFormat::kInt32) {
if (index_format == xenos::IndexFormat::kInt32) {
reinterpret_cast<uint32_t*>(target)[index_count] = source_32[0];
} else {
reinterpret_cast<uint16_t*>(target)[index_count] = source_16[0];
}
}
}
} else if (source_type == PrimitiveType::kQuadList) {
} else if (source_type == xenos::PrimitiveType::kQuadList) {
uint32_t quad_count = index_count >> 4;
if (index_format == IndexFormat::kInt32) {
if (index_format == xenos::IndexFormat::kInt32) {
uint32_t* target_32 = reinterpret_cast<uint32_t*>(target);
for (uint32_t i = 0; i < quad_count; ++i) {
uint32_t quad_index = i << 2;
@@ -680,13 +682,14 @@ PrimitiveConverter::ConversionResult PrimitiveConverter::ConvertPrimitives(
}
void* PrimitiveConverter::AllocateIndices(
IndexFormat format, uint32_t count, uint32_t simd_offset,
xenos::IndexFormat format, uint32_t count, uint32_t simd_offset,
D3D12_GPU_VIRTUAL_ADDRESS& gpu_address_out) {
if (count == 0) {
return nullptr;
}
uint32_t size = count * (format == IndexFormat::kInt32 ? sizeof(uint32_t)
: sizeof(uint16_t));
uint32_t size =
count * (format == xenos::IndexFormat::kInt32 ? sizeof(uint32_t)
: sizeof(uint16_t));
// 16-align all index data because SIMD is used to replace the reset index
// (without that, 4-alignment would be required anyway to mix 16-bit and
// 32-bit indices in one buffer page).
@@ -703,7 +706,7 @@ void* PrimitiveConverter::AllocateIndices(
nullptr, nullptr, &gpu_address);
if (mapping == nullptr) {
XELOGE("Failed to allocate space for {} converted {}-bit vertex indices",
count, format == IndexFormat::kInt32 ? 32 : 16);
count, format == xenos::IndexFormat::kInt32 ? 32 : 16);
return nullptr;
}
gpu_address_out = gpu_address + simd_offset;
@@ -732,18 +735,18 @@ PrimitiveConverter::MemoryInvalidationCallbackThunk(
}
D3D12_GPU_VIRTUAL_ADDRESS PrimitiveConverter::GetStaticIndexBuffer(
PrimitiveType source_type, uint32_t index_count,
xenos::PrimitiveType source_type, uint32_t index_count,
uint32_t& index_count_out) const {
if (index_count > kMaxNonIndexedVertices) {
assert_always();
return D3D12_GPU_VIRTUAL_ADDRESS(0);
}
if (source_type == PrimitiveType::kTriangleFan) {
if (source_type == xenos::PrimitiveType::kTriangleFan) {
index_count_out = (std::max(index_count, uint32_t(2)) - 2) * 3;
return static_ib_gpu_address_ +
kStaticIBTriangleFanOffset * sizeof(uint16_t);
}
if (source_type == PrimitiveType::kQuadList &&
if (source_type == xenos::PrimitiveType::kQuadList &&
cvars::d3d12_convert_quads_to_triangles) {
index_count_out = (index_count >> 2) * 6;
return static_ib_gpu_address_ + kStaticIBQuadOffset * sizeof(uint16_t);