mirror of
https://github.com/RPCS3/rpcs3.git
synced 2025-07-05 22:41:25 +12:00
rsx/gl: Minor cleanup and optimization
- Track register change status - Remove unused gl classes
This commit is contained in:
parent
8695f95267
commit
19d808d378
8 changed files with 64 additions and 137 deletions
|
@ -334,8 +334,11 @@ public:
|
||||||
fmt::throw_exception("Trying to get unknown shader program" HERE);
|
fmt::throw_exception("Trying to get unknown shader program" HERE);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Returns 2 booleans.
|
||||||
|
// First flag hints that there is more work to do (busy hint)
|
||||||
|
// Second flag is true if at least one program has been linked successfully (sync hint)
|
||||||
template<typename... Args>
|
template<typename... Args>
|
||||||
bool async_update(u32 max_decompile_count, Args&& ...args)
|
std::pair<bool, bool> async_update(u32 max_decompile_count, Args&& ...args)
|
||||||
{
|
{
|
||||||
// Decompile shaders and link one pipeline object per 'run'
|
// Decompile shaders and link one pipeline object per 'run'
|
||||||
// NOTE: Linking is much slower than decompilation step, so always decompile at least 1 unit
|
// NOTE: Linking is much slower than decompilation step, so always decompile at least 1 unit
|
||||||
|
@ -381,7 +384,7 @@ public:
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
return busy;
|
return { busy, false };
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -392,7 +395,7 @@ public:
|
||||||
m_storage[key] = std::move(pipeline);
|
m_storage[key] = std::move(pipeline);
|
||||||
m_link_queue.erase(key);
|
m_link_queue.erase(key);
|
||||||
|
|
||||||
return (busy || !m_link_queue.empty());
|
return { (busy || !m_link_queue.empty()), true };
|
||||||
}
|
}
|
||||||
|
|
||||||
template<typename... Args>
|
template<typename... Args>
|
||||||
|
|
|
@ -402,13 +402,12 @@ void GLGSRender::end()
|
||||||
|
|
||||||
//Bind textures and resolve external copy operations
|
//Bind textures and resolve external copy operations
|
||||||
std::chrono::time_point<steady_clock> textures_start = steady_clock::now();
|
std::chrono::time_point<steady_clock> textures_start = steady_clock::now();
|
||||||
int unused_location;
|
|
||||||
void *unused = nullptr;
|
void *unused = nullptr;
|
||||||
gl::texture_view* tmp_view;
|
gl::texture_view* tmp_view;
|
||||||
|
|
||||||
for (int i = 0; i < rsx::limits::fragment_textures_count; ++i)
|
for (int i = 0; i < rsx::limits::fragment_textures_count; ++i)
|
||||||
{
|
{
|
||||||
if (m_program->uniforms.has_location(rsx::constants::fragment_texture_names[i], &unused_location))
|
if (m_program->uniforms.has_location(rsx::constants::fragment_texture_names[i]))
|
||||||
{
|
{
|
||||||
auto sampler_state = static_cast<gl::texture_cache::sampled_image_descriptor*>(fs_sampler_state[i].get());
|
auto sampler_state = static_cast<gl::texture_cache::sampled_image_descriptor*>(fs_sampler_state[i].get());
|
||||||
auto &tex = rsx::method_registers.fragment_textures[i];
|
auto &tex = rsx::method_registers.fragment_textures[i];
|
||||||
|
@ -444,7 +443,7 @@ void GLGSRender::end()
|
||||||
|
|
||||||
for (int i = 0; i < rsx::limits::vertex_textures_count; ++i)
|
for (int i = 0; i < rsx::limits::vertex_textures_count; ++i)
|
||||||
{
|
{
|
||||||
if (m_program->uniforms.has_location(rsx::constants::vertex_texture_names[i], &unused_location))
|
if (m_program->uniforms.has_location(rsx::constants::vertex_texture_names[i]))
|
||||||
{
|
{
|
||||||
auto sampler_state = static_cast<gl::texture_cache::sampled_image_descriptor*>(vs_sampler_state[i].get());
|
auto sampler_state = static_cast<gl::texture_cache::sampled_image_descriptor*>(vs_sampler_state[i].get());
|
||||||
glActiveTexture(GL_TEXTURE0 + rsx::limits::fragment_textures_count + i);
|
glActiveTexture(GL_TEXTURE0 + rsx::limits::fragment_textures_count + i);
|
||||||
|
@ -1786,11 +1785,13 @@ void GLGSRender::on_decompiler_exit()
|
||||||
|
|
||||||
bool GLGSRender::on_decompiler_task()
|
bool GLGSRender::on_decompiler_task()
|
||||||
{
|
{
|
||||||
bool ret = m_prog_buffer.async_update(8);
|
const auto result = m_prog_buffer.async_update(8);
|
||||||
|
if (result.second)
|
||||||
|
{
|
||||||
|
// TODO: Proper synchronization with renderer
|
||||||
|
// Finish works well enough for now but it is not a proper soulution
|
||||||
|
glFinish();
|
||||||
|
}
|
||||||
|
|
||||||
// TODO: Proper synchronization with renderer
|
return result.first;
|
||||||
// Finish works well enough for now but it is not a proper soulution
|
|
||||||
glFinish();
|
|
||||||
|
|
||||||
return ret;
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -2435,35 +2435,51 @@ public:
|
||||||
|
|
||||||
bool has_location(const std::string &name, int *location = nullptr)
|
bool has_location(const std::string &name, int *location = nullptr)
|
||||||
{
|
{
|
||||||
int result = glGetUniformLocation(m_program.id(), name.c_str());
|
auto found = locations.find(name);
|
||||||
|
if (found != locations.end())
|
||||||
|
{
|
||||||
|
if (location)
|
||||||
|
{
|
||||||
|
*location = found->second;
|
||||||
|
}
|
||||||
|
|
||||||
if (result < 0)
|
return (found->second >= 0);
|
||||||
return false;
|
}
|
||||||
|
|
||||||
|
auto result = glGetUniformLocation(m_program.id(), name.c_str());
|
||||||
locations[name] = result;
|
locations[name] = result;
|
||||||
|
|
||||||
if (location)
|
if (location)
|
||||||
|
{
|
||||||
*location = result;
|
*location = result;
|
||||||
|
}
|
||||||
|
|
||||||
return true;
|
return (result >= 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
GLint location(const std::string &name)
|
GLint location(const std::string &name)
|
||||||
{
|
{
|
||||||
auto finded = locations.find(name);
|
auto found = locations.find(name);
|
||||||
|
if (found != locations.end())
|
||||||
if (finded != locations.end())
|
|
||||||
{
|
{
|
||||||
return finded->second;
|
if (found->second >= 0)
|
||||||
|
{
|
||||||
|
return found->second;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
throw not_found_exception(name);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
int result = glGetUniformLocation(m_program.id(), name.c_str());
|
auto result = glGetUniformLocation(m_program.id(), name.c_str());
|
||||||
|
|
||||||
if (result < 0)
|
if (result < 0)
|
||||||
|
{
|
||||||
throw not_found_exception(name);
|
throw not_found_exception(name);
|
||||||
|
}
|
||||||
|
|
||||||
locations[name] = result;
|
locations[name] = result;
|
||||||
|
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -2476,28 +2492,6 @@ public:
|
||||||
return active_texture;
|
return active_texture;
|
||||||
}
|
}
|
||||||
|
|
||||||
int texture(const std::string &name, int active_texture, const gl::texture_view& texture_)
|
|
||||||
{
|
|
||||||
return texture(location(name), active_texture, texture_);
|
|
||||||
}
|
|
||||||
|
|
||||||
int texture(const std::string &name, const gl::texture_view& texture_)
|
|
||||||
{
|
|
||||||
int atex;
|
|
||||||
auto finded = locations.find(name);
|
|
||||||
|
|
||||||
if (finded != locations.end())
|
|
||||||
{
|
|
||||||
atex = finded->second;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
atex = active_texture++;
|
|
||||||
}
|
|
||||||
|
|
||||||
return texture(name, atex, texture_);
|
|
||||||
}
|
|
||||||
|
|
||||||
uniform_t operator[](GLint location)
|
uniform_t operator[](GLint location)
|
||||||
{
|
{
|
||||||
return{ m_program, location };
|
return{ m_program, location };
|
||||||
|
@ -2515,83 +2509,6 @@ public:
|
||||||
}
|
}
|
||||||
} uniforms{ this };
|
} uniforms{ this };
|
||||||
|
|
||||||
class attribs_t
|
|
||||||
{
|
|
||||||
program& m_program;
|
|
||||||
std::unordered_map<std::string, GLint> m_locations;
|
|
||||||
|
|
||||||
public:
|
|
||||||
attribs_t(program* program) : m_program(*program)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void clear()
|
|
||||||
{
|
|
||||||
m_locations.clear();
|
|
||||||
}
|
|
||||||
|
|
||||||
GLint location(const std::string &name)
|
|
||||||
{
|
|
||||||
auto finded = m_locations.find(name);
|
|
||||||
|
|
||||||
if (finded != m_locations.end())
|
|
||||||
{
|
|
||||||
if (finded->second < 0)
|
|
||||||
throw not_found_exception(name);
|
|
||||||
|
|
||||||
return finded->second;
|
|
||||||
}
|
|
||||||
|
|
||||||
int result = glGetAttribLocation(m_program.id(), name.c_str());
|
|
||||||
|
|
||||||
if (result < 0)
|
|
||||||
throw not_found_exception(name);
|
|
||||||
|
|
||||||
m_locations[name] = result;
|
|
||||||
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool has_location(const std::string &name, int *location_ = nullptr)
|
|
||||||
{
|
|
||||||
auto finded = m_locations.find(name);
|
|
||||||
|
|
||||||
if (finded != m_locations.end())
|
|
||||||
{
|
|
||||||
if (finded->second < 0)
|
|
||||||
return false;
|
|
||||||
|
|
||||||
*location_ = finded->second;
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
int loc = glGetAttribLocation(m_program.id(), name.c_str());
|
|
||||||
|
|
||||||
m_locations[name] = loc;
|
|
||||||
|
|
||||||
if (loc < 0)
|
|
||||||
return false;
|
|
||||||
|
|
||||||
*location_ = loc;
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
attrib_t operator[](GLint location)
|
|
||||||
{
|
|
||||||
return{ location };
|
|
||||||
}
|
|
||||||
|
|
||||||
attrib_t operator[](const std::string &name)
|
|
||||||
{
|
|
||||||
return{ location(name) };
|
|
||||||
}
|
|
||||||
|
|
||||||
void swap(attribs_t& attribs)
|
|
||||||
{
|
|
||||||
m_locations.swap(attribs.m_locations);
|
|
||||||
}
|
|
||||||
} attribs{ this };
|
|
||||||
|
|
||||||
program& recreate()
|
program& recreate()
|
||||||
{
|
{
|
||||||
if (created())
|
if (created())
|
||||||
|
@ -2686,7 +2603,6 @@ public:
|
||||||
void set_id(uint id)
|
void set_id(uint id)
|
||||||
{
|
{
|
||||||
uniforms.clear();
|
uniforms.clear();
|
||||||
attribs.clear();
|
|
||||||
m_id = id;
|
m_id = id;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -2764,7 +2680,6 @@ public:
|
||||||
set_id(program_.id());
|
set_id(program_.id());
|
||||||
program_.set_id(my_old_id);
|
program_.set_id(my_old_id);
|
||||||
uniforms.swap(program_.uniforms);
|
uniforms.swap(program_.uniforms);
|
||||||
attribs.swap(program_.attribs);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
program& operator = (const program& rhs) = delete;
|
program& operator = (const program& rhs) = delete;
|
||||||
|
|
|
@ -437,10 +437,6 @@ namespace rsx
|
||||||
thread_ctrl::set_thread_affinity_mask(thread_ctrl::get_affinity_mask(thread_class::rsx));
|
thread_ctrl::set_thread_affinity_mask(thread_ctrl::get_affinity_mask(thread_class::rsx));
|
||||||
}
|
}
|
||||||
|
|
||||||
// Weak cpus need all the help they can get, sleep instead of yield loop
|
|
||||||
// Lowers decompiler responsiveness but improves emulator performance
|
|
||||||
const bool prefer_sleep = (std::thread::hardware_concurrency() < 6);
|
|
||||||
|
|
||||||
while (!Emu.IsStopped() && !m_rsx_thread_exiting)
|
while (!Emu.IsStopped() && !m_rsx_thread_exiting)
|
||||||
{
|
{
|
||||||
if (!on_decompiler_task())
|
if (!on_decompiler_task())
|
||||||
|
@ -449,13 +445,9 @@ namespace rsx
|
||||||
{
|
{
|
||||||
std::this_thread::sleep_for(1ms);
|
std::this_thread::sleep_for(1ms);
|
||||||
}
|
}
|
||||||
else if (prefer_sleep)
|
|
||||||
{
|
|
||||||
std::this_thread::sleep_for(500us);
|
|
||||||
}
|
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
std::this_thread::yield();
|
std::this_thread::sleep_for(500us);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -3442,5 +3442,5 @@ void VKGSRender::discard_occlusion_query(rsx::reports::occlusion_query_info* que
|
||||||
|
|
||||||
bool VKGSRender::on_decompiler_task()
|
bool VKGSRender::on_decompiler_task()
|
||||||
{
|
{
|
||||||
return m_prog_buffer->async_update(8, *m_device, pipeline_layout);
|
return m_prog_buffer->async_update(8, *m_device, pipeline_layout).first;
|
||||||
}
|
}
|
|
@ -780,7 +780,6 @@ namespace vk
|
||||||
const u16 section_depth = depth;
|
const u16 section_depth = depth;
|
||||||
const bool is_cubemap = type == rsx::texture_dimension_extended::texture_dimension_cubemap;
|
const bool is_cubemap = type == rsx::texture_dimension_extended::texture_dimension_cubemap;
|
||||||
VkFormat vk_format;
|
VkFormat vk_format;
|
||||||
VkComponentMapping mapping;
|
|
||||||
VkImageAspectFlags aspect_flags;
|
VkImageAspectFlags aspect_flags;
|
||||||
VkImageType image_type;
|
VkImageType image_type;
|
||||||
VkImageViewType image_view_type;
|
VkImageViewType image_view_type;
|
||||||
|
|
|
@ -371,12 +371,18 @@ namespace rsx
|
||||||
|
|
||||||
void set_transform_program_start(thread* rsx, u32, u32)
|
void set_transform_program_start(thread* rsx, u32, u32)
|
||||||
{
|
{
|
||||||
rsx->m_graphics_state |= rsx::pipeline_state::vertex_program_dirty;
|
if (method_registers.register_change_flag)
|
||||||
|
{
|
||||||
|
rsx->m_graphics_state |= rsx::pipeline_state::vertex_program_dirty;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void set_vertex_attribute_output_mask(thread* rsx, u32, u32)
|
void set_vertex_attribute_output_mask(thread* rsx, u32, u32)
|
||||||
{
|
{
|
||||||
rsx->m_graphics_state |= rsx::pipeline_state::vertex_program_dirty | rsx::pipeline_state::fragment_program_dirty;
|
if (method_registers.register_change_flag)
|
||||||
|
{
|
||||||
|
rsx->m_graphics_state |= rsx::pipeline_state::vertex_program_dirty | rsx::pipeline_state::fragment_program_dirty;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void set_begin_end(thread* rsxthr, u32 _reg, u32 arg)
|
void set_begin_end(thread* rsxthr, u32 _reg, u32 arg)
|
||||||
|
@ -1310,7 +1316,16 @@ namespace rsx
|
||||||
|
|
||||||
void rsx_state::decode(u32 reg, u32 value)
|
void rsx_state::decode(u32 reg, u32 value)
|
||||||
{
|
{
|
||||||
registers[reg] = value;
|
auto& old_value = registers[reg];
|
||||||
|
if (old_value != value)
|
||||||
|
{
|
||||||
|
register_change_flag = true;
|
||||||
|
old_value = value;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
register_change_flag = false;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
bool rsx_state::test(u32 reg, u32 value) const
|
bool rsx_state::test(u32 reg, u32 value) const
|
||||||
|
|
|
@ -159,6 +159,8 @@ namespace rsx
|
||||||
|
|
||||||
draw_clause current_draw_clause;
|
draw_clause current_draw_clause;
|
||||||
|
|
||||||
|
bool register_change_flag;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* RSX can sources vertex attributes from 2 places:
|
* RSX can sources vertex attributes from 2 places:
|
||||||
* 1. Immediate values passed by NV4097_SET_VERTEX_DATA*_M + ARRAY_ID write.
|
* 1. Immediate values passed by NV4097_SET_VERTEX_DATA*_M + ARRAY_ID write.
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue