1
0
mirror of https://github.com/RPCS3/rpcs3.git synced 2024-11-22 18:53:28 +01:00

gl/vk: Vertex attribute uploading and texture swizzle fixes (#2174)

* gl/vk: Properly upload vertex attributes

* vk: Fix cmp type

* vk: Remap all texture formats
This commit is contained in:
kd-11 2016-09-29 10:16:00 +03:00 committed by raven02
parent 5430e1d310
commit 1c9718389f
3 changed files with 48 additions and 42 deletions

View File

@ -171,7 +171,8 @@ namespace
{
u32 min_index, max_index, vertex_draw_count = initial_vertex_count;
vertex_draw_count = (u32)get_index_count(draw_mode, ::narrow<int>(vertex_draw_count));
if (!gl::is_primitive_native(draw_mode))
vertex_draw_count = (u32)get_index_count(draw_mode, ::narrow<int>(vertex_draw_count));
u32 type_size = ::narrow<u32>(get_index_type_size(type));
u32 block_sz = vertex_draw_count * type_size;
@ -179,7 +180,7 @@ namespace
gsl::span<gsl::byte> dst{ reinterpret_cast<gsl::byte*>(ptr), ::narrow<u32>(block_sz) };
std::tie(min_index, max_index) = write_index_array_data_to_buffer(dst, raw_index_buffer,
type, draw_mode, rsx::method_registers.restart_index_enabled(), rsx::method_registers.restart_index(), first_count_commands,
[](auto prim) { return !is_primitive_native(prim); });
[](auto prim) { return !gl::is_primitive_native(prim); });
return std::make_tuple(min_index, max_index, vertex_draw_count);
}
@ -355,25 +356,26 @@ namespace
rsx::index_array_type type = rsx::method_registers.index_type();
u32 type_size = ::narrow<u32>(get_index_type_size(type));
u32 index_count = get_index_count(rsx::method_registers.current_draw_clause.primitive,
rsx::method_registers.current_draw_clause.get_elements_count());
u32 vertex_count = rsx::method_registers.current_draw_clause.get_elements_count();
u32 index_count = vertex_count;
if (!gl::is_primitive_native(rsx::method_registers.current_draw_clause.primitive))
index_count = (u32)get_index_count(rsx::method_registers.current_draw_clause.primitive, vertex_count);
u32 max_size = index_count * type_size;
auto mapping = m_index_ring_buffer.alloc_and_map(max_size);
void* ptr = mapping.first;
u32 offset_in_index_buffer = mapping.second;
u32 expanded_index_count;
std::tie(min_index, max_index, expanded_index_count) = upload_index_buffer(
std::tie(min_index, max_index, index_count) = upload_index_buffer(
command.raw_index_buffer, ptr, type, rsx::method_registers.current_draw_clause.primitive,
rsx::method_registers.current_draw_clause.first_count_commands, index_count);
min_index = 0; // we must keep index to vertex mapping
rsx::method_registers.current_draw_clause.first_count_commands, vertex_count);
m_index_ring_buffer.unmap();
upload_vertex_buffers(0, max_index, max_vertex_attrib_size, texture_index_offset);
upload_vertex_buffers(min_index, max_index, max_vertex_attrib_size, texture_index_offset);
return std::make_tuple(
expanded_index_count, std::make_tuple(get_index_type(type), offset_in_index_buffer));
return std::make_tuple(index_count, std::make_tuple(get_index_type(type), offset_in_index_buffer));
}
std::tuple<u32, std::optional<std::tuple<GLenum, u32>>> operator()(

View File

@ -116,6 +116,9 @@ VkComponentMapping get_component_mapping(u32 format, u8 swizzle_mask)
const u8 remap_g = (swizzle_mask >> 4) & 0x3;
const u8 remap_b = (swizzle_mask >> 6) & 0x3;
//Component map in ARGB format
std::array<VkComponentSwizzle, 4> mapping = {};
switch (format)
{
case CELL_GCM_TEXTURE_A1R5G5B5:
@ -131,57 +134,50 @@ VkComponentMapping get_component_mapping(u32 format, u8 swizzle_mask)
case CELL_GCM_TEXTURE_COMPRESSED_DXT45:
case CELL_GCM_TEXTURE_COMPRESSED_B8R8_G8R8:
case CELL_GCM_TEXTURE_COMPRESSED_R8B8_R8G8:
return { VK_COMPONENT_SWIZZLE_R, VK_COMPONENT_SWIZZLE_G, VK_COMPONENT_SWIZZLE_B, VK_COMPONENT_SWIZZLE_A };
mapping = { VK_COMPONENT_SWIZZLE_A, VK_COMPONENT_SWIZZLE_R, VK_COMPONENT_SWIZZLE_G, VK_COMPONENT_SWIZZLE_B }; break;
case CELL_GCM_TEXTURE_B8:
return { VK_COMPONENT_SWIZZLE_R, VK_COMPONENT_SWIZZLE_R, VK_COMPONENT_SWIZZLE_R, VK_COMPONENT_SWIZZLE_R };
mapping = { VK_COMPONENT_SWIZZLE_R, VK_COMPONENT_SWIZZLE_R, VK_COMPONENT_SWIZZLE_R, VK_COMPONENT_SWIZZLE_R }; break;
case CELL_GCM_TEXTURE_G8B8:
{
VkComponentSwizzle map_table[] = { VK_COMPONENT_SWIZZLE_G, VK_COMPONENT_SWIZZLE_R, VK_COMPONENT_SWIZZLE_G, VK_COMPONENT_SWIZZLE_R };
return{ map_table[remap_r], map_table[remap_g], map_table[remap_b], map_table[remap_a] };
}
mapping = { VK_COMPONENT_SWIZZLE_R, VK_COMPONENT_SWIZZLE_G, VK_COMPONENT_SWIZZLE_R, VK_COMPONENT_SWIZZLE_G }; break;
case CELL_GCM_TEXTURE_X16:
case CELL_GCM_TEXTURE_X32_FLOAT:
return { VK_COMPONENT_SWIZZLE_R, VK_COMPONENT_SWIZZLE_R, VK_COMPONENT_SWIZZLE_R, VK_COMPONENT_SWIZZLE_R };
mapping = { VK_COMPONENT_SWIZZLE_R, VK_COMPONENT_SWIZZLE_R, VK_COMPONENT_SWIZZLE_R, VK_COMPONENT_SWIZZLE_R }; break;
case CELL_GCM_TEXTURE_Y16_X16:
return { VK_COMPONENT_SWIZZLE_G, VK_COMPONENT_SWIZZLE_R, VK_COMPONENT_SWIZZLE_G, VK_COMPONENT_SWIZZLE_R };
case CELL_GCM_TEXTURE_Y16_X16_FLOAT:
return { VK_COMPONENT_SWIZZLE_R, VK_COMPONENT_SWIZZLE_G, VK_COMPONENT_SWIZZLE_R, VK_COMPONENT_SWIZZLE_G };
mapping = { VK_COMPONENT_SWIZZLE_R, VK_COMPONENT_SWIZZLE_G, VK_COMPONENT_SWIZZLE_R, VK_COMPONENT_SWIZZLE_G }; break;
case CELL_GCM_TEXTURE_W16_Z16_Y16_X16_FLOAT:
case CELL_GCM_TEXTURE_W32_Z32_Y32_X32_FLOAT:
return { VK_COMPONENT_SWIZZLE_A, VK_COMPONENT_SWIZZLE_B, VK_COMPONENT_SWIZZLE_G, VK_COMPONENT_SWIZZLE_R };
mapping = { VK_COMPONENT_SWIZZLE_R, VK_COMPONENT_SWIZZLE_A, VK_COMPONENT_SWIZZLE_B, VK_COMPONENT_SWIZZLE_G }; break;
case CELL_GCM_TEXTURE_A4R4G4B4:
{
VkComponentSwizzle map_table[] = { VK_COMPONENT_SWIZZLE_R, VK_COMPONENT_SWIZZLE_G, VK_COMPONENT_SWIZZLE_B, VK_COMPONENT_SWIZZLE_A };
return { map_table[remap_r], map_table[remap_g], map_table[remap_b], map_table[remap_a] };
}
mapping = { VK_COMPONENT_SWIZZLE_R, VK_COMPONENT_SWIZZLE_G, VK_COMPONENT_SWIZZLE_B, VK_COMPONENT_SWIZZLE_A }; break;
case CELL_GCM_TEXTURE_D8R8G8B8:
case CELL_GCM_TEXTURE_D1R5G5B5:
return { VK_COMPONENT_SWIZZLE_R, VK_COMPONENT_SWIZZLE_G, VK_COMPONENT_SWIZZLE_B, VK_COMPONENT_SWIZZLE_ONE };
mapping = { VK_COMPONENT_SWIZZLE_ONE, VK_COMPONENT_SWIZZLE_R, VK_COMPONENT_SWIZZLE_G, VK_COMPONENT_SWIZZLE_B }; break;
case CELL_GCM_TEXTURE_COMPRESSED_HILO8:
case CELL_GCM_TEXTURE_COMPRESSED_HILO_S8:
return { VK_COMPONENT_SWIZZLE_G, VK_COMPONENT_SWIZZLE_R, VK_COMPONENT_SWIZZLE_G, VK_COMPONENT_SWIZZLE_R };
mapping = { VK_COMPONENT_SWIZZLE_G, VK_COMPONENT_SWIZZLE_R, VK_COMPONENT_SWIZZLE_G, VK_COMPONENT_SWIZZLE_R }; break;
case ~(CELL_GCM_TEXTURE_LN | CELL_GCM_TEXTURE_UN) & CELL_GCM_TEXTURE_COMPRESSED_B8R8_G8R8:
case ~(CELL_GCM_TEXTURE_LN | CELL_GCM_TEXTURE_UN) & CELL_GCM_TEXTURE_COMPRESSED_R8B8_R8G8:
return { VK_COMPONENT_SWIZZLE_G, VK_COMPONENT_SWIZZLE_B, VK_COMPONENT_SWIZZLE_R, VK_COMPONENT_SWIZZLE_ZERO };
mapping = { VK_COMPONENT_SWIZZLE_ZERO, VK_COMPONENT_SWIZZLE_G, VK_COMPONENT_SWIZZLE_B, VK_COMPONENT_SWIZZLE_R }; break;
case CELL_GCM_TEXTURE_A8R8G8B8:
{
VkComponentSwizzle map_table[] = { VK_COMPONENT_SWIZZLE_B, VK_COMPONENT_SWIZZLE_G, VK_COMPONENT_SWIZZLE_R, VK_COMPONENT_SWIZZLE_A };
return { map_table[remap_r], map_table[remap_g], map_table[remap_b], map_table[remap_a] };
mapping = { VK_COMPONENT_SWIZZLE_B, VK_COMPONENT_SWIZZLE_G, VK_COMPONENT_SWIZZLE_R, VK_COMPONENT_SWIZZLE_A }; break;
default:
fmt::throw_exception("Invalid or unsupported component mapping for texture format (0x%x)" HERE, format);
}
}
fmt::throw_exception("Invalid or unsupported component mapping for texture format (0x%x)" HERE, format);
return {mapping[remap_r], mapping[remap_g], mapping[remap_b], mapping[remap_a]};
}
}

View File

@ -41,10 +41,10 @@ namespace vk
* Set up buffer fetches to only work on 4-component access. This is hardware dependant so we use 4-component access to avoid branching based on IHV implementation
* AMD GCN 1.0 for example does not support RGB32 formats for texel buffers
*/
const VkFormat vec1_types[] = { VK_FORMAT_R16_UNORM, VK_FORMAT_R32_SFLOAT, VK_FORMAT_R16_SFLOAT, VK_FORMAT_R8_UNORM, VK_FORMAT_R16_SINT, VK_FORMAT_R16_SFLOAT, VK_FORMAT_R8_UINT };
const VkFormat vec2_types[] = { VK_FORMAT_R16G16_UNORM, VK_FORMAT_R32G32_SFLOAT, VK_FORMAT_R16G16_SFLOAT, VK_FORMAT_R8G8_UNORM, VK_FORMAT_R16G16_SINT, VK_FORMAT_R16G16_SFLOAT, VK_FORMAT_R8G8_UINT };
const VkFormat vec3_types[] = { VK_FORMAT_R16G16B16A16_UNORM, VK_FORMAT_R32G32B32A32_SFLOAT, VK_FORMAT_R16G16B16A16_SFLOAT, VK_FORMAT_R8G8B8A8_UNORM, VK_FORMAT_R16G16B16A16_SINT, VK_FORMAT_R16G16B16A16_SFLOAT, VK_FORMAT_R8G8B8A8_UINT }; //VEC3 COMPONENTS NOT SUPPORTED!
const VkFormat vec4_types[] = { VK_FORMAT_R16G16B16A16_UNORM, VK_FORMAT_R32G32B32A32_SFLOAT, VK_FORMAT_R16G16B16A16_SFLOAT, VK_FORMAT_R8G8B8A8_UNORM, VK_FORMAT_R16G16B16A16_SINT, VK_FORMAT_R16G16B16A16_SFLOAT, VK_FORMAT_R8G8B8A8_UINT };
const VkFormat vec1_types[] = { VK_FORMAT_R16_UNORM, VK_FORMAT_R32_SFLOAT, VK_FORMAT_R16_SFLOAT, VK_FORMAT_R8_UNORM, VK_FORMAT_R16_SINT, VK_FORMAT_R16_UNORM, VK_FORMAT_R8_UINT };
const VkFormat vec2_types[] = { VK_FORMAT_R16G16_UNORM, VK_FORMAT_R32G32_SFLOAT, VK_FORMAT_R16G16_SFLOAT, VK_FORMAT_R8G8_UNORM, VK_FORMAT_R16G16_SINT, VK_FORMAT_R16G16_UNORM, VK_FORMAT_R8G8_UINT };
const VkFormat vec3_types[] = { VK_FORMAT_R16G16B16A16_UNORM, VK_FORMAT_R32G32B32A32_SFLOAT, VK_FORMAT_R16G16B16A16_SFLOAT, VK_FORMAT_R8G8B8A8_UNORM, VK_FORMAT_R16G16B16A16_SINT, VK_FORMAT_R16G16B16A16_UNORM, VK_FORMAT_R8G8B8A8_UINT }; //VEC3 COMPONENTS NOT SUPPORTED!
const VkFormat vec4_types[] = { VK_FORMAT_R16G16B16A16_UNORM, VK_FORMAT_R32G32B32A32_SFLOAT, VK_FORMAT_R16G16B16A16_SFLOAT, VK_FORMAT_R8G8B8A8_UNORM, VK_FORMAT_R16G16B16A16_SINT, VK_FORMAT_R16G16B16A16_UNORM, VK_FORMAT_R8G8B8A8_UINT };
const VkFormat* vec_selectors[] = { 0, vec1_types, vec2_types, vec3_types, vec4_types };
@ -85,6 +85,13 @@ namespace vk
}
}
bool is_primitive_native(rsx::primitive_type& mode)
{
bool result;
get_appropriate_topology(mode, result);
return !result;
}
template <typename T, u32 padding>
void copy_inlined_data_to_buffer(void *src_data, void *dst_data, u32 vertex_count, rsx::vertex_base_type type, u8 src_channels, u8 dst_channels, u16 element_size, u16 stride)
{
@ -393,8 +400,9 @@ namespace
rsx::index_array_type index_type = rsx::method_registers.index_type();
u32 type_size = gsl::narrow<u32>(get_index_type_size(index_type));
u32 index_count = get_index_count(rsx::method_registers.current_draw_clause.primitive,
rsx::method_registers.current_draw_clause.get_elements_count());
u32 index_count = rsx::method_registers.current_draw_clause.get_elements_count();
if (primitives_emulated)
index_count = get_index_count(rsx::method_registers.current_draw_clause.primitive, index_count);
u32 upload_size = index_count * type_size;
VkDeviceSize offset_in_index_buffer = m_index_buffer_ring_info.alloc<256>(upload_size);
@ -410,7 +418,7 @@ namespace
rsx::method_registers.current_draw_clause.primitive,
rsx::method_registers.restart_index_enabled(),
rsx::method_registers.restart_index(), command.ranges_to_fetch_in_index_buffer,
[](auto prim) { return !is_primitive_native(prim); });
[](auto prim) { return !vk::is_primitive_native(prim); });
m_index_buffer_ring_info.unmap();