mirror of https://github.com/PCSX2/pcsx2.git
gsdx-ogl: found_GL_ARB_buffer_storage is now mandatory
This commit is contained in:
parent
52e3c3516d
commit
a62019a3fd
|
@ -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);
|
||||
|
|
|
@ -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;
|
||||
}
|
||||
|
|
|
@ -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);
|
||||
}
|
||||
|
||||
|
|
|
@ -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<int>(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);
|
||||
}
|
||||
|
||||
|
|
|
@ -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);
|
||||
|
|
Loading…
Reference in New Issue