From a62019a3fddb6e32a2143342e5e315d13babeaed Mon Sep 17 00:00:00 2001 From: Gregory Hainaut Date: Thu, 7 Apr 2016 22:17:22 +0200 Subject: [PATCH] gsdx-ogl: found_GL_ARB_buffer_storage is now mandatory --- plugins/GSdx/GLLoader.cpp | 2 +- plugins/GSdx/GLLoader.h | 1 - plugins/GSdx/GSTextureOGL.cpp | 73 +++++++++--------------------- plugins/GSdx/GSVertexArrayOGL.h | 80 ++++++++------------------------- plugins/GSdx/GSWnd.cpp | 2 +- 5 files changed, 41 insertions(+), 117 deletions(-) diff --git a/plugins/GSdx/GLLoader.cpp b/plugins/GSdx/GLLoader.cpp index 674f079202..ab8f5bc54c 100644 --- a/plugins/GSdx/GLLoader.cpp +++ b/plugins/GSdx/GLLoader.cpp @@ -475,7 +475,7 @@ namespace GLLoader { // GL4.3 status &= status_and_override(found_GL_ARB_copy_image, "GL_ARB_copy_image"); // GL4.4 - status &= status_and_override(found_GL_ARB_buffer_storage,"GL_ARB_buffer_storage"); + status &= status_and_override(found_GL_ARB_buffer_storage,"GL_ARB_buffer_storage", true); status &= status_and_override(found_GL_ARB_clear_texture,"GL_ARB_clear_texture"); // GL4.5 status &= status_and_override(found_GL_ARB_clip_control, "GL_ARB_clip_control", true); diff --git a/plugins/GSdx/GLLoader.h b/plugins/GSdx/GLLoader.h index 4e77e140c6..baf1746935 100644 --- a/plugins/GSdx/GLLoader.h +++ b/plugins/GSdx/GLLoader.h @@ -352,7 +352,6 @@ namespace GLLoader { extern bool found_GL_ARB_gpu_shader5; extern bool found_GL_ARB_shader_image_load_store; extern bool found_GL_ARB_clear_texture; - extern bool found_GL_ARB_buffer_storage; extern bool found_GL_ARB_direct_state_access; extern bool found_GL_EXT_texture_filter_anisotropic; } diff --git a/plugins/GSdx/GSTextureOGL.cpp b/plugins/GSdx/GSTextureOGL.cpp index 15ca86b3e7..b6a605063e 100644 --- a/plugins/GSdx/GSTextureOGL.cpp +++ b/plugins/GSdx/GSTextureOGL.cpp @@ -40,7 +40,6 @@ namespace PboPool { char* m_map[PBO_POOL_SIZE]; uint32 m_current_pbo = 0; uint32 m_size; - bool m_texture_storage; GLsync m_fence[PBO_POOL_SIZE]; const uint32 m_pbo_size = 8*1024*1024; @@ -62,19 +61,13 @@ namespace PboPool { // will use DMA CACHED memory as the source for buffer object operations void Init() { glGenBuffers(countof(m_pool), m_pool); - m_texture_storage = GLLoader::found_GL_ARB_buffer_storage; for (size_t i = 0; i < countof(m_pool); i++) { BindPbo(); - if (m_texture_storage) { - glBufferStorage(GL_PIXEL_UNPACK_BUFFER, m_pbo_size, NULL, create_flags); - m_map[m_current_pbo] = (char*)glMapBufferRange(GL_PIXEL_UNPACK_BUFFER, 0, m_pbo_size, map_flags); - m_fence[m_current_pbo] = 0; - } else { - glBufferData(GL_PIXEL_UNPACK_BUFFER, m_pbo_size, NULL, GL_STREAM_COPY); - m_map[m_current_pbo] = NULL; - } + glBufferStorage(GL_PIXEL_UNPACK_BUFFER, m_pbo_size, NULL, create_flags); + m_map[m_current_pbo] = (char*)glMapBufferRange(GL_PIXEL_UNPACK_BUFFER, 0, m_pbo_size, map_flags); + m_fence[m_current_pbo] = 0; NextPbo(); } @@ -89,44 +82,22 @@ namespace PboPool { fprintf(stderr, "BUG: PBO too small %d but need %d\n", m_pbo_size, m_size); } - if (m_texture_storage) { - if (m_offset[m_current_pbo] + m_size >= m_pbo_size) { - //NextPbo(); // For test purpose - NextPboWithSync(); - } - - // Note: texsubimage will access currently bound buffer - // Pbo ready let's get a pointer - BindPbo(); - - map = m_map[m_current_pbo] + m_offset[m_current_pbo]; - - } else { - GLbitfield flags = GL_MAP_WRITE_BIT | GL_MAP_UNSYNCHRONIZED_BIT | GL_MAP_INVALIDATE_RANGE_BIT; - - if (m_offset[m_current_pbo] + m_size >= m_pbo_size) { - NextPbo(); - - flags &= ~GL_MAP_INVALIDATE_RANGE_BIT; - flags |= GL_MAP_INVALIDATE_BUFFER_BIT; - } - - // Pbo ready let's get a pointer - BindPbo(); - - // Be sure the map is aligned - map = (char*)glMapBufferRange(GL_PIXEL_UNPACK_BUFFER, m_offset[m_current_pbo], m_size, flags); + if (m_offset[m_current_pbo] + m_size >= m_pbo_size) { + //NextPbo(); // For test purpose + NextPboWithSync(); } + // Note: texsubimage will access currently bound buffer + // Pbo ready let's get a pointer + BindPbo(); + + map = m_map[m_current_pbo] + m_offset[m_current_pbo]; + return map; } void Unmap() { - if (m_texture_storage) { - glFlushMappedBufferRange(GL_PIXEL_UNPACK_BUFFER, m_offset[m_current_pbo], m_size); - } else { - glUnmapBuffer(GL_PIXEL_UNPACK_BUFFER); - } + glFlushMappedBufferRange(GL_PIXEL_UNPACK_BUFFER, m_offset[m_current_pbo], m_size); } uptr Offset() { @@ -134,18 +105,16 @@ namespace PboPool { } void Destroy() { - if (m_texture_storage) { - for (size_t i = 0; i < countof(m_pool); i++) { - m_map[i] = NULL; - m_offset[i] = 0; - glDeleteSync(m_fence[i]); + for (size_t i = 0; i < countof(m_pool); i++) { + m_map[i] = NULL; + m_offset[i] = 0; + glDeleteSync(m_fence[i]); - // Don't know if we must do it - glBindBuffer(GL_PIXEL_UNPACK_BUFFER, m_pool[i]); - glUnmapBuffer(GL_PIXEL_UNPACK_BUFFER); - } - glBindBuffer(GL_PIXEL_UNPACK_BUFFER, 0); + // Don't know if we must do it + glBindBuffer(GL_PIXEL_UNPACK_BUFFER, m_pool[i]); + glUnmapBuffer(GL_PIXEL_UNPACK_BUFFER); } + glBindBuffer(GL_PIXEL_UNPACK_BUFFER, 0); glDeleteBuffers(countof(m_pool), m_pool); } diff --git a/plugins/GSdx/GSVertexArrayOGL.h b/plugins/GSdx/GSVertexArrayOGL.h index 5c6e31833f..5f2cf53735 100644 --- a/plugins/GSdx/GSVertexArrayOGL.h +++ b/plugins/GSdx/GSVertexArrayOGL.h @@ -43,7 +43,6 @@ class GSBufferOGL { const GLenum m_target; GLuint m_buffer_name; uint8* m_buffer_ptr; - const bool m_buffer_storage; GLsync m_fence[5]; public: @@ -52,7 +51,6 @@ class GSBufferOGL { , m_count(0) , m_limit(0) , m_target(target) - , m_buffer_storage(GLLoader::found_GL_ARB_buffer_storage) { glGenBuffers(1, &m_buffer_name); // Opengl works best with 1-4MB buffer. @@ -63,73 +61,37 @@ class GSBufferOGL { m_fence[i] = 0; } - if (m_buffer_storage) { - // TODO: if we do manually the synchronization, I'm not sure size is important. It worths to investigate it. - // => bigger buffer => less sync - bind(); - // coherency will be done by flushing - const GLbitfield common_flags = GL_MAP_WRITE_BIT | GL_MAP_PERSISTENT_BIT; - const GLbitfield map_flags = common_flags | GL_MAP_FLUSH_EXPLICIT_BIT; - const GLbitfield create_flags = common_flags | GL_CLIENT_STORAGE_BIT; + // TODO: if we do manually the synchronization, I'm not sure size is important. It worths to investigate it. + // => bigger buffer => less sync + bind(); + // coherency will be done by flushing + const GLbitfield common_flags = GL_MAP_WRITE_BIT | GL_MAP_PERSISTENT_BIT; + const GLbitfield map_flags = common_flags | GL_MAP_FLUSH_EXPLICIT_BIT; + const GLbitfield create_flags = common_flags | GL_CLIENT_STORAGE_BIT; - glBufferStorage(m_target, STRIDE * m_limit, NULL, create_flags ); - m_buffer_ptr = (uint8*) glMapBufferRange(m_target, 0, STRIDE * m_limit, map_flags); - if (!m_buffer_ptr) { - fprintf(stderr, "Failed to map buffer\n"); - throw GSDXError(); - } - } else { - m_buffer_ptr = NULL; + glBufferStorage(m_target, STRIDE * m_limit, NULL, create_flags ); + m_buffer_ptr = (uint8*) glMapBufferRange(m_target, 0, STRIDE * m_limit, map_flags); + if (!m_buffer_ptr) { + fprintf(stderr, "Failed to map buffer\n"); + throw GSDXError(); } } ~GSBufferOGL() { - if (m_buffer_storage) { - for (size_t i = 0; i < 5; i++) { - glDeleteSync(m_fence[i]); - } - // Don't know if we must do it - bind(); - glUnmapBuffer(m_target); + for (size_t i = 0; i < 5; i++) { + glDeleteSync(m_fence[i]); } + // Don't know if we must do it + bind(); + glUnmapBuffer(m_target); glDeleteBuffers(1, &m_buffer_name); } - void allocate() { allocate(m_limit); } - - void allocate(size_t new_limit) - { - if (!m_buffer_storage) { - m_start = 0; - m_limit = new_limit; - glBufferData(m_target, m_limit * STRIDE, NULL, GL_STREAM_DRAW); - } - } - void bind() { glBindBuffer(m_target, m_buffer_name); } - void subdata_upload(const void* src) - { - // Current GPU buffer is really too small need to allocate a new one - if (m_count > m_limit) { - //fprintf(stderr, "Allocate a new buffer\n %d", STRIDE); - allocate(std::max(m_count * 3 / 2, m_limit)); - - } else if (m_count > (m_limit - m_start) ) { - //fprintf(stderr, "Orphan the buffer %d\n", STRIDE); - - // Not enough left free room. Just go back at the beginning - m_start = 0; - // Orphan the buffer to avoid synchronization - allocate(m_limit); - } - - glBufferSubData(m_target, STRIDE * m_start, STRIDE * m_count, src); - } - void map_upload(const void* src) { ASSERT(m_count < m_limit); @@ -207,11 +169,7 @@ class GSBufferOGL { m_count = count; - if (m_buffer_storage) { - map_upload(src); - } else { - subdata_upload(src); - } + map_upload(src); } void EndScene() @@ -267,8 +225,6 @@ public: m_vb->bind(); m_ib->bind(); - m_vb->allocate(); - m_ib->allocate(); set_internal_format(layout, layout_nbr); } diff --git a/plugins/GSdx/GSWnd.cpp b/plugins/GSdx/GSWnd.cpp index be9552143d..042cd5684f 100644 --- a/plugins/GSdx/GSWnd.cpp +++ b/plugins/GSdx/GSWnd.cpp @@ -128,7 +128,7 @@ void GSWndGL::PopulateGlFunction() GL_EXT_LOAD_OPT(glDebugMessageControl); // GL4.4 GL_EXT_LOAD_OPT(glClearTexImage); - GL_EXT_LOAD_OPT(glBufferStorage); + GL_EXT_LOAD(glBufferStorage); // GL4.5 GL_EXT_LOAD_OPT(glCreateTextures);