mirror of
https://github.com/RPCS3/rpcs3.git
synced 2024-11-22 18:53:28 +01:00
OpenGL renderer: improved vertex attributes setup
Minor fixes
This commit is contained in:
parent
d22ac91ee1
commit
f30d71da6c
@ -310,16 +310,20 @@ void GLGSRender::end()
|
||||
int texture_index = 0;
|
||||
for (int i = 0; i < rsx::limits::textures_count; ++i)
|
||||
{
|
||||
if (!textures[i].enabled())
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
int location;
|
||||
if (m_program->uniforms.has_location("texture" + std::to_string(i), &location))
|
||||
{
|
||||
__glcheck glProgramUniform1i(m_program->id(), location, texture_index);
|
||||
__glcheck m_gl_textures[i].init(texture_index, textures[i]);
|
||||
if (!textures[i].enabled())
|
||||
{
|
||||
glActiveTexture(GL_TEXTURE0 + i);
|
||||
glBindTexture(GL_TEXTURE_2D, 0);
|
||||
glProgramUniform1i(m_program->id(), location, i);
|
||||
|
||||
continue;
|
||||
}
|
||||
|
||||
__glcheck glProgramUniform1i(m_program->id(), location, i);
|
||||
__glcheck m_gl_textures[i].init(i, textures[i]);
|
||||
|
||||
texture_index++;
|
||||
|
||||
@ -327,7 +331,11 @@ void GLGSRender::end()
|
||||
{
|
||||
if (textures[i].format() & CELL_GCM_TEXTURE_UN)
|
||||
{
|
||||
//glProgramUniform4f(m_program->id(), location, textures[i].width(), textures[i].height(), textures[i].depth(), 1.0f);
|
||||
u32 width = std::max<u32>(textures[i].width(), 1);
|
||||
u32 height = std::max<u32>(textures[i].height(), 1);
|
||||
u32 depth = std::max<u32>(textures[i].depth(), 1);
|
||||
|
||||
glProgramUniform4f(m_program->id(), location, 1.f / width, 1.f / height, 1.f / depth, 1.0f);
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -349,8 +357,6 @@ void GLGSRender::end()
|
||||
*/
|
||||
}
|
||||
|
||||
__glcheck 0;
|
||||
|
||||
u32 offset_in_index_buffer = set_vertex_buffer();
|
||||
m_vao.bind();
|
||||
|
||||
@ -430,8 +436,6 @@ void GLGSRender::set_viewport()
|
||||
}
|
||||
|
||||
glEnable(GL_SCISSOR_TEST);
|
||||
|
||||
__glcheck 0;
|
||||
}
|
||||
|
||||
void GLGSRender::on_init_thread()
|
||||
@ -685,8 +689,6 @@ bool GLGSRender::load_program()
|
||||
auto mapping = m_uniform_ring_buffer.alloc_from_reserve(fragment_constants_size, m_uniform_buffer_offset_align);
|
||||
fragment_constants_offset = mapping.second;
|
||||
|
||||
u32 buffer_offset = 0;
|
||||
|
||||
static const __m128i mask = _mm_set_epi8(
|
||||
0xE, 0xF, 0xC, 0xD,
|
||||
0xA, 0xB, 0x8, 0x9,
|
||||
@ -695,20 +697,23 @@ bool GLGSRender::load_program()
|
||||
|
||||
auto ucode = (const rsx::fragment_program::ucode_instr *)info.fragment_shader.decompiled->raw->ucode_ptr;
|
||||
|
||||
auto dst = (const rsx::fragment_program::ucode_instr *)mapping.first;
|
||||
|
||||
for (const auto& constant : info.fragment_shader.decompiled->constants)
|
||||
{
|
||||
const void *data = ucode + u32(constant.id / sizeof(rsx::fragment_program::ucode_instr));
|
||||
const __m128i &vector = _mm_loadu_si128((const __m128i*)data);
|
||||
const __m128i &shuffled_vector = _mm_shuffle_epi8(vector, mask);
|
||||
_mm_stream_si128((__m128i*)((char*)mapping.first + buffer_offset), shuffled_vector);
|
||||
const void *src = ucode + u32(constant.id / sizeof(*ucode));
|
||||
|
||||
//float x = ((float*)((char*)mapping.first + buffer_offset))[0];
|
||||
//float y = ((float*)((char*)mapping.first + buffer_offset))[1];
|
||||
//float z = ((float*)((char*)mapping.first + buffer_offset))[2];
|
||||
//float w = ((float*)((char*)mapping.first + buffer_offset))[3];
|
||||
const __m128i &vector = _mm_loadu_si128((const __m128i*)src);
|
||||
const __m128i &shuffled_vector = _mm_shuffle_epi8(vector, mask);
|
||||
_mm_stream_si128((__m128i*)dst, shuffled_vector);
|
||||
|
||||
float x = ((float*)dst)[0];
|
||||
float y = ((float*)dst)[1];
|
||||
float z = ((float*)dst)[2];
|
||||
float w = ((float*)dst)[3];
|
||||
|
||||
//LOG_WARNING(RSX, "fc%u = {%g, %g, %g, %g}", constant.id, x, y, z, w);
|
||||
buffer_offset += 4 * sizeof(f32);
|
||||
++dst;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -259,17 +259,65 @@ rsx::complete_shader glsl_complete_shader(const rsx::decompiled_shader &shader,
|
||||
" gl_Position.w = o0.w;\n";
|
||||
}
|
||||
|
||||
for (std::size_t index = 0; index < 16; ++index)
|
||||
{
|
||||
if (shader.input_attributes & (1 << index))
|
||||
{
|
||||
// result.code += "in vec4 " + rsx::vertex_program::input_attrib_names[index] + ";\n";
|
||||
std::string code_end;
|
||||
|
||||
// TODO: use actual information about vertex inputs
|
||||
result.code += "layout(location=" + std::to_string(location++) + ") uniform samplerBuffer " + rsx::vertex_program::input_attrib_names[index] + "_buffer" + ";\n";
|
||||
result.code += "vec4 " + rsx::vertex_program::input_attrib_names[index]
|
||||
+ " = texelFetch(" + rsx::vertex_program::input_attrib_names[index] + "_buffer, gl_VertexID).rgba;\n";
|
||||
for (std::size_t index = 0; index < 16; ++index)
|
||||
{
|
||||
if (shader.input_attributes & (1 << index))
|
||||
{
|
||||
// result.code += "in vec4 " + rsx::vertex_program::input_attrib_names[index] + ";\n";
|
||||
|
||||
// TODO: use actual information about vertex inputs
|
||||
const std::string &attrib_name = rsx::vertex_program::input_attrib_names[index];
|
||||
|
||||
result.code += "uniform ";
|
||||
|
||||
if (state.is_int & (1 << index))
|
||||
{
|
||||
result.code += "isamplerBuffer ";
|
||||
code_end += "ivec4 ";
|
||||
}
|
||||
else
|
||||
{
|
||||
result.code += "samplerBuffer ";
|
||||
code_end += "vec4 ";
|
||||
}
|
||||
|
||||
result.code += attrib_name + "_buffer" + ";\n";
|
||||
|
||||
code_end += attrib_name + ";\n";
|
||||
|
||||
std::string vertex_id;
|
||||
|
||||
if (state.is_array & (1 << index))
|
||||
{
|
||||
vertex_id = "gl_VertexID";
|
||||
|
||||
if (state.frequency[index] > 1)
|
||||
{
|
||||
if (state.divider_op & (1 << index))
|
||||
{
|
||||
vertex_id += " % ";
|
||||
}
|
||||
else
|
||||
{
|
||||
vertex_id += " / ";
|
||||
}
|
||||
|
||||
vertex_id += std::to_string(state.frequency[index]);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
vertex_id = "0";
|
||||
}
|
||||
|
||||
prepare += '\t' + attrib_name + " = texelFetch(" + attrib_name + "_buffer, " + vertex_id + ");\n";
|
||||
}
|
||||
}
|
||||
|
||||
result.code += code_end;
|
||||
}
|
||||
|
||||
{
|
||||
|
@ -160,17 +160,9 @@ u32 GLGSRender::set_vertex_buffer()
|
||||
//initialize vertex attributes
|
||||
//merge all vertex arrays
|
||||
|
||||
std::chrono::time_point<std::chrono::system_clock> then = std::chrono::system_clock::now();
|
||||
static const u32 texture_index_offset = rsx::limits::textures_count + rsx::limits::vertex_textures_count;
|
||||
|
||||
const std::string reg_table[] =
|
||||
{
|
||||
"in_pos", "in_weight", "in_normal",
|
||||
"in_diff_color", "in_spec_color",
|
||||
"in_fog",
|
||||
"in_point_size", "in_7",
|
||||
"in_tc0", "in_tc1", "in_tc2", "in_tc3",
|
||||
"in_tc4", "in_tc5", "in_tc6", "in_tc7"
|
||||
};
|
||||
std::chrono::time_point<std::chrono::system_clock> then = std::chrono::system_clock::now();
|
||||
|
||||
u32 input_mask = rsx::method_registers[NV4097_SET_VERTEX_ATTRIB_INPUT_MASK];
|
||||
u32 min_index = 0, max_index = 0;
|
||||
@ -185,7 +177,9 @@ u32 GLGSRender::set_vertex_buffer()
|
||||
for (u8 index = 0; index < rsx::limits::vertex_count; ++index)
|
||||
{
|
||||
if (vertex_arrays_info[index].size == 0)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
max_vertex_attrib_size += 16;
|
||||
}
|
||||
@ -240,9 +234,9 @@ u32 GLGSRender::set_vertex_buffer()
|
||||
|
||||
if (!vertex_info.size) // disabled, bind a null sampler
|
||||
{
|
||||
glActiveTexture(GL_TEXTURE0 + index + rsx::limits::textures_count);
|
||||
glActiveTexture(GL_TEXTURE0 + index + texture_index_offset);
|
||||
glBindTexture(GL_TEXTURE_BUFFER, 0);
|
||||
glProgramUniform1i(m_program->id(), location, index + rsx::limits::textures_count);
|
||||
glProgramUniform1i(m_program->id(), location, index + texture_index_offset);
|
||||
continue;
|
||||
}
|
||||
|
||||
@ -279,7 +273,7 @@ u32 GLGSRender::set_vertex_buffer()
|
||||
texture.copy_from(m_attrib_ring_buffer, gl_type, mapping.second, data_size);
|
||||
|
||||
//Link texture to uniform
|
||||
m_program->uniforms.texture(location, index + rsx::limits::textures_count, texture);
|
||||
m_program->uniforms.texture(location, index + texture_index_offset, texture);
|
||||
if (!is_primitive_native(draw_mode))
|
||||
{
|
||||
std::tie(vertex_draw_count, offset_in_index_buffer) = get_index_array_for_emulated_non_indexed_draw({ { 0, vertex_draw_count } }, draw_mode, m_index_ring_buffer);
|
||||
@ -309,9 +303,9 @@ u32 GLGSRender::set_vertex_buffer()
|
||||
bool enabled = !!(input_mask & (1 << index));
|
||||
if (!enabled)
|
||||
{
|
||||
glActiveTexture(GL_TEXTURE0 + index + rsx::limits::textures_count);
|
||||
glActiveTexture(GL_TEXTURE0 + index + texture_index_offset);
|
||||
glBindTexture(GL_TEXTURE_BUFFER, 0);
|
||||
glProgramUniform1i(m_program->id(), location, index + rsx::limits::textures_count);
|
||||
glProgramUniform1i(m_program->id(), location, index + texture_index_offset);
|
||||
continue;
|
||||
}
|
||||
|
||||
@ -367,7 +361,7 @@ u32 GLGSRender::set_vertex_buffer()
|
||||
texture.copy_from(m_attrib_ring_buffer, gl_type, buffer_offset, data_size);
|
||||
|
||||
//Link texture to uniform
|
||||
m_program->uniforms.texture(location, index + rsx::limits::textures_count, texture);
|
||||
m_program->uniforms.texture(location, index + texture_index_offset, texture);
|
||||
}
|
||||
else if (register_vertex_info[index].size > 0)
|
||||
{
|
||||
@ -392,7 +386,7 @@ u32 GLGSRender::set_vertex_buffer()
|
||||
texture.copy_from(m_attrib_ring_buffer, gl_type, mapping.second, data_size);
|
||||
|
||||
//Link texture to uniform
|
||||
m_program->uniforms.texture(location, index + rsx::limits::textures_count, texture);
|
||||
m_program->uniforms.texture(location, index + texture_index_offset, texture);
|
||||
break;
|
||||
}
|
||||
default:
|
||||
@ -402,9 +396,9 @@ u32 GLGSRender::set_vertex_buffer()
|
||||
}
|
||||
else
|
||||
{
|
||||
glActiveTexture(GL_TEXTURE0 + index + rsx::limits::textures_count);
|
||||
glActiveTexture(GL_TEXTURE0 + index + texture_index_offset);
|
||||
glBindTexture(GL_TEXTURE_BUFFER, 0);
|
||||
glProgramUniform1i(m_program->id(), location, index + rsx::limits::textures_count);
|
||||
glProgramUniform1i(m_program->id(), location, index + texture_index_offset);
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
@ -72,6 +72,8 @@ namespace rsx
|
||||
case rsx::texture_dimension::dimension1d: return rsx::texture_dimension_extended::texture_dimension_1d;
|
||||
case rsx::texture_dimension::dimension3d: return rsx::texture_dimension_extended::texture_dimension_2d;
|
||||
case rsx::texture_dimension::dimension2d: return cubemap() ? rsx::texture_dimension_extended::texture_dimension_cubemap : rsx::texture_dimension_extended::texture_dimension_2d;
|
||||
|
||||
default: ASSUME(0);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -751,8 +751,39 @@ namespace rsx
|
||||
|
||||
u32 fp_info = rsx::method_registers[NV4097_SET_SHADER_PROGRAM];
|
||||
|
||||
result.state.input_attributes = rsx::method_registers[NV4097_SET_VERTEX_ATTRIB_INPUT_MASK];
|
||||
result.state.output_attributes = rsx::method_registers[NV4097_SET_VERTEX_ATTRIB_OUTPUT_MASK];
|
||||
result.state.ctrl = rsx::method_registers[NV4097_SET_SHADER_CONTROL];
|
||||
result.state.divider_op = rsx::method_registers[NV4097_SET_FREQUENCY_DIVIDER_OPERATION];
|
||||
|
||||
result.state.is_array = 0;
|
||||
result.state.is_int = 0;
|
||||
|
||||
for (u8 index = 0; index < rsx::limits::vertex_count; ++index)
|
||||
{
|
||||
bool is_int = false;
|
||||
|
||||
if (vertex_arrays_info[index].size > 0)
|
||||
{
|
||||
result.state.is_array |= 1 << index;
|
||||
is_int = is_int_type(vertex_arrays_info[index].type);
|
||||
result.state.frequency[index] = vertex_arrays_info[index].frequency;
|
||||
}
|
||||
else if (register_vertex_info[index].size > 0)
|
||||
{
|
||||
is_int = is_int_type(register_vertex_info[index].type);
|
||||
result.state.frequency[index] = register_vertex_info[index].frequency;
|
||||
}
|
||||
else
|
||||
{
|
||||
result.state.frequency[index] = 0;
|
||||
}
|
||||
|
||||
if (is_int)
|
||||
{
|
||||
result.state.is_int |= 1 << index;
|
||||
}
|
||||
}
|
||||
|
||||
result.vertex_shader.ucode_ptr = transform_program;
|
||||
result.vertex_shader.offset = rsx::method_registers[NV4097_SET_TRANSFORM_PROGRAM_START];
|
||||
|
@ -1 +1 @@
|
||||
Subproject commit e4d938c76850549acd837326e2fe0890d5b4be03
|
||||
Subproject commit e1bd56e959e4eaae181c7c19b94fe2fb1ec00c08
|
Loading…
Reference in New Issue
Block a user