diff options
author | Eric Anholt <eric@anholt.net> | 2015-11-09 15:47:05 -0800 |
---|---|---|
committer | Eric Anholt <eric@anholt.net> | 2015-11-09 15:58:36 -0800 |
commit | ae79ff6c154b35d809cbbc10338cc13f0f03a72c (patch) | |
tree | 9caa78b9ee93cef51481515923ae43edfe476185 | |
parent | 7d1e4783853f9830344d101ceab087feb19995be (diff) |
glamor: Avoid GL errors on mapping with size == 0.glamor-map-zero
GL 4.5 / GLES 3.0 require throwing GL errors at map time, abd Mesa
before that might throw errors accidentally if a malloc(0) call was
made to return the mapping.
Signed-off-by: Eric Anholt <eric@anholt.net>
-rw-r--r-- | glamor/glamor_priv.h | 1 | ||||
-rw-r--r-- | glamor/glamor_vbo.c | 16 |
2 files changed, 15 insertions, 2 deletions
diff --git a/glamor/glamor_priv.h b/glamor/glamor_priv.h index f3950f12c..f89d56d9e 100644 --- a/glamor/glamor_priv.h +++ b/glamor/glamor_priv.h @@ -251,6 +251,7 @@ typedef struct glamor_screen_private { /** Next offset within the VBO that glamor_get_vbo_space() will use. */ int vbo_offset; int vbo_size; + Bool vbo_mapped; /** * Pointer to glamor_get_vbo_space()'s current VBO mapping. * diff --git a/glamor/glamor_vbo.c b/glamor/glamor_vbo.c index d74a00580..c04a76174 100644 --- a/glamor/glamor_vbo.c +++ b/glamor/glamor_vbo.c @@ -96,6 +96,15 @@ glamor_get_vbo_space(ScreenPtr screen, unsigned size, char **vbo_offset) data = glamor_priv->vb + glamor_priv->vbo_offset; glamor_priv->vbo_offset += size; } else if (glamor_priv->has_map_buffer_range) { + /* Avoid GL errors on GL 4.5 / ES 3.0 with mapping size == 0, + * which callers may sometimes pass us (for example, if + * clipping leads to zero rectangles left). (Prior to that + * version, Mesa would sometimes throw errors on unmapping a + * zero-size mapping) + */ + if (size == 0) + return NULL; + if (glamor_priv->vbo_size < glamor_priv->vbo_offset + size) { glamor_priv->vbo_size = MAX(GLAMOR_VBO_SIZE, size); glamor_priv->vbo_offset = 0; @@ -109,9 +118,9 @@ glamor_get_vbo_space(ScreenPtr screen, unsigned size, char **vbo_offset) GL_MAP_WRITE_BIT | GL_MAP_UNSYNCHRONIZED_BIT | GL_MAP_INVALIDATE_RANGE_BIT); - assert(data != NULL); *vbo_offset = (char *)(uintptr_t)glamor_priv->vbo_offset; glamor_priv->vbo_offset += size; + glamor_priv->vbo_mapped = TRUE; } else { /* Return a pointer to the statically allocated non-VBO * memory. We'll upload it through glBufferData() later. @@ -145,7 +154,10 @@ glamor_put_vbo_space(ScreenPtr screen) * reach the end of the buffer. */ } else if (glamor_priv->has_map_buffer_range) { - glUnmapBuffer(GL_ARRAY_BUFFER); + if (glamor_priv->vbo_mapped) { + glUnmapBuffer(GL_ARRAY_BUFFER); + glamor_priv->vbo_mapped = FALSE; + } } else { glBufferData(GL_ARRAY_BUFFER, glamor_priv->vbo_offset, glamor_priv->vb, GL_DYNAMIC_DRAW); |