summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorKenneth Graunke <kenneth@whitecape.org>2015-01-03 00:30:35 -0800
committerEric Anholt <eric@anholt.net>2015-02-04 16:54:27 -0800
commit8accb75b6eb9734716abd000f36b10af0b9823c5 (patch)
tree8d4f9141073701491e8063947a52ad57706e8985
parent63aca403e88a62f9699f2103bf7ff54a8f721aeb (diff)
glamor: Don't unbind the GL_ARRAY_BUFFER in glamor_put_vbo_space().glamor-testing-patch-from-ken
Mesa's implementation of glBindBuffer() checks to see if the supplied buffer name happens to be already bound. If so, it returns immediately, skipping the hash table lookup (mapping the GLuint buffer handle to the actual struct), the associated locking, and reference counting. Glamor uses a single VBO for everything - operations reserve space in the VBO via glamor_get_vbo_space(); if it fills up, we replace it with a fresh buffer (which is then used for everything). Ideally, Glamor would almost always hit the above optimization. Instead, it never hits it. Today, glamor_get_vbo_space() binds the VBO, and glamor_put_vbo_space() explicitly unbinds it. This means that our VBO is never bound on a get operation, so we pay the hash table cost every time we call glamor_get_vbo_space(). Every get/put also alter reference counts, so we pay that cost twice over. This patch removes the explicit unbind, which makes us hit the fast path on every get/put (except the rare ones which create a new buffer). When running a fullscreen GL application under xf86-video-modesetting (which doesn't do page flipping yet), glamor_get_vbo_space() accounted for 4.24% of the CPU instructions in each glamor_copy_fbo_fbo_draw() operation. With this patch, it became only 0.87%. v2: Make Xephyr unbind the array buffer, otherwise it'll sourcec frm the BO instead of the user pointers. Same for the glamor_pixmap.c paths. Signed-off-by: Kenneth Graunke <kenneth@whitecape.org> Cc: Eric Anholt <eric@anholt.net> Signed-off-by: Eric Anholt <eric@anholt.net> Reviewed-by: Eric Anholt <eric@anholt.net>
-rw-r--r--glamor/glamor_gradient.c1
-rw-r--r--glamor/glamor_pixmap.c2
-rw-r--r--glamor/glamor_vbo.c2
-rw-r--r--hw/kdrive/ephyr/ephyr_glamor_glx.c1
4 files changed, 4 insertions, 2 deletions
diff --git a/glamor/glamor_gradient.c b/glamor/glamor_gradient.c
index 2581aa69b..9e52d3e6c 100644
--- a/glamor/glamor_gradient.c
+++ b/glamor/glamor_gradient.c
@@ -732,6 +732,7 @@ _glamor_gradient_set_pixmap_destination(ScreenPtr screen,
glamor_make_current(glamor_priv);
+ glBindBuffer(GL_ARRAY_BUFFER, 0);
glVertexAttribPointer(GLAMOR_VERTEX_POS, 2, GL_FLOAT,
GL_FALSE, 0, vertices);
glVertexAttribPointer(GLAMOR_VERTEX_SOURCE, 2, GL_FLOAT,
diff --git a/glamor/glamor_pixmap.c b/glamor/glamor_pixmap.c
index 4ded7b64a..20e0a400a 100644
--- a/glamor/glamor_pixmap.c
+++ b/glamor/glamor_pixmap.c
@@ -820,6 +820,7 @@ _glamor_upload_bits_to_pixmap_texture(PixmapPtr pixmap, GLenum format,
vertices);
/* Slow path, we need to flip y or wire alpha to 1. */
glamor_make_current(glamor_priv);
+ glBindBuffer(GL_ARRAY_BUFFER, 0);
glVertexAttribPointer(GLAMOR_VERTEX_POS, 2, GL_FLOAT,
GL_FALSE, 2 * sizeof(float), vertices);
glEnableVertexAttribArray(GLAMOR_VERTEX_POS);
@@ -1104,6 +1105,7 @@ glamor_es2_pixmap_read_prepare(PixmapPtr source, int x, int y, int w, int h,
temp_xscale, temp_yscale, 0, 0, w, h,
vertices);
+ glBindBuffer(GL_ARRAY_BUFFER, 0);
glVertexAttribPointer(GLAMOR_VERTEX_POS, 2, GL_FLOAT, GL_FALSE,
2 * sizeof(float), vertices);
glEnableVertexAttribArray(GLAMOR_VERTEX_POS);
diff --git a/glamor/glamor_vbo.c b/glamor/glamor_vbo.c
index e90610102..5d7c55f6a 100644
--- a/glamor/glamor_vbo.c
+++ b/glamor/glamor_vbo.c
@@ -150,8 +150,6 @@ glamor_put_vbo_space(ScreenPtr screen)
glBufferData(GL_ARRAY_BUFFER, glamor_priv->vbo_offset,
glamor_priv->vb, GL_DYNAMIC_DRAW);
}
-
- glBindBuffer(GL_ARRAY_BUFFER, 0);
}
void
diff --git a/hw/kdrive/ephyr/ephyr_glamor_glx.c b/hw/kdrive/ephyr/ephyr_glamor_glx.c
index 582e3af96..7d751a98e 100644
--- a/hw/kdrive/ephyr/ephyr_glamor_glx.c
+++ b/hw/kdrive/ephyr/ephyr_glamor_glx.c
@@ -211,6 +211,7 @@ ephyr_glamor_damage_redisplay(struct ephyr_glamor *glamor,
glXMakeCurrent(dpy, glamor->glx_win, glamor->ctx);
+ glBindBuffer(GL_ARRAY_BUFFER, 0);
glBindFramebuffer(GL_FRAMEBUFFER, 0);
glUseProgram(glamor->texture_shader);
glViewport(0, 0, glamor->width, glamor->height);