[Glamor] [PATCH 1/2] Change the trapezoid render to use VBO
He Junyan
junyan.he at linux.intel.com
Tue Jul 17 00:02:01 PDT 2012
On my IVB platform, the cairo benchmark of firefox-canvas.trace will get
about 40% improvement,
but firefox-fishtank.trace seems just have 5%. I think this may caused
by firefox-canvas.trace use
a lot of trapezoid rendering for every pixmap.
> From: Junyan He <junyan.he at linux.intel.com>
>
> Because some uniform variables need to be set for every
> trapezoid rendering, we can not use vbo to render multi
> trapezoids one time, which have performance big loss.
> We now add attributes which contain the same value to bypass
> the uniform variable problem. The uniform value for one
> trapezoid will be set to the same value to all the vertex
> of that trapezoid as an attribute, then in FS, it is still
> a constant.
>
> Signed-off-by: Junyan He <junyan.he at linux.intel.com>
> ---
> src/glamor_trapezoid.c | 460 ++++++++++++++++++++++++++++++------------------
> src/glamor_utils.h | 29 +++
> 2 files changed, 316 insertions(+), 173 deletions(-)
>
> diff --git a/src/glamor_trapezoid.c b/src/glamor_trapezoid.c
> index 5dd2792..969fbac 100644
> --- a/src/glamor_trapezoid.c
> +++ b/src/glamor_trapezoid.c
> @@ -38,6 +38,10 @@
>
> #ifdef GLAMOR_TRAPEZOID_SHADER
>
> +#define GLAMOR_VERTEX_TOP_BOTTOM (GLAMOR_VERTEX_SOURCE + 1)
> +#define GLAMOR_VERTEX_LEFT_PARAM (GLAMOR_VERTEX_SOURCE + 2)
> +#define GLAMOR_VERTEX_RIGHT_PARAM (GLAMOR_VERTEX_SOURCE + 3)
> +
> #define DEBUG_CLIP_VTX 0
>
> #define POINT_INSIDE_CLIP_RECT(point, rect) \
> @@ -112,10 +116,10 @@ point_inside_trapezoid(int point[2], xTrapezoid * trap, xFixed cut_y)
> ret = FALSE;
> if (DEBUG_CLIP_VTX) {
> ErrorF("Out of Trap top, point[1] = %d(0x%x)), "
> - "top = %d(0x%x)\n",
> - (unsigned int)xFixedToInt(point[1]), point[1],
> - (unsigned int)xFixedToInt(trap->top),
> - (unsigned int)trap->top);
> + "top = %d(0x%x)\n",
> + (unsigned int)xFixedToInt(point[1]), point[1],
> + (unsigned int)xFixedToInt(trap->top),
> + (unsigned int)trap->top);
> }
>
> return ret;
> @@ -556,6 +560,85 @@ _glamor_clip_trapezoid_vertex(xTrapezoid * trap, BoxPtr pbox,
> return TRUE;
> }
>
> +static void
> +glamor_setup_composite_vbo_for_trapezoid(ScreenPtr screen, int n_verts)
> +{
> + glamor_screen_private *glamor_priv =
> + glamor_get_screen_private(screen);
> + glamor_gl_dispatch *dispatch;
> + int stride;
> +
> + glamor_priv->vbo_offset = 0;
> + glamor_priv->render_nr_verts = 0;
> +
> + /* For GLAMOR_VERTEX_POS */
> + glamor_priv->vb_stride = 2 * sizeof(float);
> +
> + /* For GLAMOR_GLAMOR_VERTEX_SOURCE */
> + glamor_priv->vb_stride += 2 * sizeof(float);
> +
> + /* For GLAMOR_VERTEX_TOP_BOTTOM */
> + glamor_priv->vb_stride += 2 * sizeof(float);
> +
> + /* For GLAMOR_VERTEX_LEFT_PARAM */
> + glamor_priv->vb_stride += 4 * sizeof(float);
> +
> + /* For GLAMOR_VERTEX_RIGHT_PARAM */
> + glamor_priv->vb_stride += 4 * sizeof(float);
> +
> + glamor_priv->vbo_size = n_verts * glamor_priv->vb_stride;
> +
> + dispatch = glamor_get_dispatch(glamor_priv);
> +
> + dispatch->glDisableVertexAttribArray(GLAMOR_VERTEX_POS);
> + dispatch->glDisableVertexAttribArray(GLAMOR_VERTEX_SOURCE);
> + dispatch->glDisableVertexAttribArray(GLAMOR_VERTEX_TOP_BOTTOM);
> + dispatch->glDisableVertexAttribArray(GLAMOR_VERTEX_LEFT_PARAM);
> + dispatch->glDisableVertexAttribArray(GLAMOR_VERTEX_RIGHT_PARAM);
> +
> + dispatch->glBindBuffer(GL_ARRAY_BUFFER, glamor_priv->vbo);
> + if (glamor_priv->gl_flavor == GLAMOR_GL_DESKTOP) {
> + dispatch->glBufferData(GL_ARRAY_BUFFER,
> + glamor_priv->vbo_size,
> + NULL, GL_DYNAMIC_DRAW);
> + glamor_priv->vb = dispatch->glMapBuffer(GL_ARRAY_BUFFER, GL_READ_WRITE);
> + }
> +
> + dispatch->glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, glamor_priv->ebo);
> +
> + /* Set the vertex pointer. */
> + dispatch->glVertexAttribPointer(GLAMOR_VERTEX_POS, 2, GL_FLOAT,
> + GL_FALSE, glamor_priv->vb_stride,
> + (void *) ((long)glamor_priv->vbo_offset));
> + dispatch->glEnableVertexAttribArray(GLAMOR_VERTEX_POS);
> + stride = 2;
> +
> + dispatch->glVertexAttribPointer(GLAMOR_VERTEX_SOURCE, 2, GL_FLOAT,
> + GL_FALSE, glamor_priv->vb_stride,
> + (void *) ((long)glamor_priv->vbo_offset + stride * sizeof(float)));
> + dispatch->glEnableVertexAttribArray(GLAMOR_VERTEX_SOURCE);
> + stride += 2;
> +
> + dispatch->glVertexAttribPointer(GLAMOR_VERTEX_TOP_BOTTOM, 2, GL_FLOAT,
> + GL_FALSE, glamor_priv->vb_stride,
> + (void *) ((long)glamor_priv->vbo_offset + stride * sizeof(float)));
> + dispatch->glEnableVertexAttribArray(GLAMOR_VERTEX_TOP_BOTTOM);
> + stride += 2;
> +
> + dispatch->glVertexAttribPointer(GLAMOR_VERTEX_LEFT_PARAM, 4, GL_FLOAT,
> + GL_FALSE, glamor_priv->vb_stride,
> + (void *) ((long)glamor_priv->vbo_offset + stride * sizeof(float)));
> + dispatch->glEnableVertexAttribArray(GLAMOR_VERTEX_LEFT_PARAM);
> + stride += 4;
> +
> + dispatch->glVertexAttribPointer(GLAMOR_VERTEX_RIGHT_PARAM, 4, GL_FLOAT,
> + GL_FALSE, glamor_priv->vb_stride,
> + (void *) ((long)glamor_priv->vbo_offset + stride * sizeof(float)));
> + dispatch->glEnableVertexAttribArray(GLAMOR_VERTEX_RIGHT_PARAM);
> +
> + glamor_put_dispatch(glamor_priv);
> +}
> +
> static Bool
> _glamor_trapezoids_with_shader(CARD8 op,
> PicturePtr src, PicturePtr dst,
> @@ -565,6 +648,8 @@ _glamor_trapezoids_with_shader(CARD8 op,
> ScreenPtr screen = dst->pDrawable->pScreen;
> glamor_screen_private *glamor_priv = glamor_get_screen_private(screen);
> struct shader_key key;
> + glamor_composite_shader *shader = NULL;
> + struct blendinfo op_info;
> PictFormatShort saved_source_format = 0;
> PixmapPtr source_pixmap = NULL;
> PixmapPtr dest_pixmap = NULL;
> @@ -707,7 +792,7 @@ _glamor_trapezoids_with_shader(CARD8 op,
> goto TRAPEZOID_RESET_GL;
> }
> glamor_set_destination_pixmap_priv_nc(dest_pixmap_priv);
> - glamor_composite_set_shader_blend(dest_pixmap_priv, &key, shader, op_info);
> + glamor_composite_set_shader_blend(dest_pixmap_priv, &key, shader, &op_info);
> glamor_priv->has_source_coords = key.source != SHADER_SOURCE_SOLID;
> glamor_priv->has_mask_coords = (key.mask != SHADER_MASK_NONE &&
> key.mask != SHADER_MASK_SOLID);
> @@ -888,13 +973,45 @@ glamor_init_trapezoid_shader(ScreenPtr screen)
> const char *trapezoid_vs =
> GLAMOR_DEFAULT_PRECISION
> "attribute vec4 v_position;\n"
> - "attribute vec4 v_texcoord;\n"
> + "attribute vec2 v_texcoord;\n"
> + /* v_top_bottom, v_left_param and v_right_param contain the
> + constant value for all the vertex of one rect. Using uniform
> + is more suitable but we need to reset the uniform variables
> + for every rect rendering and can not use the vbo, which causes
> + performance loss. So we set these attributes to same value
> + for every vertex of one rect and so it is also a constant in FS */
> + "attribute vec2 v_top_bottom;\n"
> + "attribute vec4 v_left_param;\n"
> + "attribute vec4 v_right_param;\n"
> + "\n"
> "varying vec2 source_texture;\n"
> + "varying float trap_top;\n"
> + "varying float trap_bottom;\n"
> + "varying float trap_left_x;\n"
> + "varying float trap_left_y;\n"
> + "varying float trap_left_slope;\n"
> + "varying float trap_left_vertical_f;\n"
> + "varying float trap_right_x;\n"
> + "varying float trap_right_y;\n"
> + "varying float trap_right_slope;\n"
> + "varying float trap_right_vertical_f;\n"
> "\n"
> "void main()\n"
> "{\n"
> " gl_Position = v_position;\n"
> " source_texture = v_texcoord.xy;\n"
> + " trap_top = v_top_bottom.x;\n"
> + " trap_bottom = v_top_bottom.y;\n"
> + " \n"
> + " trap_left_x = v_left_param.x;\n"
> + " trap_left_y = v_left_param.y;\n"
> + " trap_left_slope = v_left_param.z;\n"
> + " trap_left_vertical_f = v_left_param.w;\n"
> + " \n"
> + " trap_right_x = v_right_param.x;\n"
> + " trap_right_y = v_right_param.y;\n"
> + " trap_right_slope = v_right_param.z;\n"
> + " trap_right_vertical_f = v_right_param.w;\n"
> "}\n";
>
> /*
> @@ -925,18 +1042,20 @@ glamor_init_trapezoid_shader(ScreenPtr screen)
> const char *trapezoid_fs =
> GLAMOR_DEFAULT_PRECISION
> "varying vec2 source_texture; \n"
> - "uniform float x_per_pix; \n"
> - "uniform float y_per_pix; \n"
> - "uniform float trap_top; \n"
> - "uniform float trap_bottom; \n"
> - "uniform float trap_left_x; \n"
> - "uniform float trap_left_y; \n"
> - "uniform float trap_left_slope; \n"
> - "uniform int trap_left_vertical; \n"
> - "uniform float trap_right_x; \n"
> - "uniform float trap_right_y; \n"
> - "uniform float trap_right_slope; \n"
> - "uniform int trap_right_vertical; \n"
> + "varying float trap_top; \n"
> + "varying float trap_bottom; \n"
> + "varying float trap_left_x; \n"
> + "varying float trap_left_y; \n"
> + "varying float trap_left_slope; \n"
> + "varying float trap_left_vertical_f; \n"
> + "varying float trap_right_x; \n"
> + "varying float trap_right_y; \n"
> + "varying float trap_right_slope; \n"
> + "varying float trap_right_vertical_f; \n"
> + "float x_per_pix = 1.0;"
> + "float y_per_pix = 1.0;"
> + "bool trap_left_vertical = (abs(trap_left_vertical_f - 1.0) <= 0.0001);\n"
> + "bool trap_right_vertical = (abs(trap_right_vertical_f - 1.0) <= 0.0001);\n"
> "\n"
> "float get_alpha_val() \n"
> "{ \n"
> @@ -945,7 +1064,7 @@ glamor_init_trapezoid_shader(ScreenPtr screen)
> " float x_up_cut_right; \n"
> " float x_bottom_cut_right; \n"
> " \n"
> - " if(trap_left_vertical == 1) { \n"
> + " if(trap_left_vertical == true) { \n"
> " x_up_cut_left = trap_left_x; \n"
> " x_bottom_cut_left = trap_left_x; \n"
> " } else { \n"
> @@ -957,7 +1076,7 @@ glamor_init_trapezoid_shader(ScreenPtr screen)
> " / trap_left_slope; \n"
> " } \n"
> " \n"
> - " if(trap_right_vertical == 1) { \n"
> + " if(trap_right_vertical == true) { \n"
> " x_up_cut_right = trap_right_x; \n"
> " x_bottom_cut_right = trap_right_x; \n"
> " } else { \n"
> @@ -1002,12 +1121,12 @@ glamor_init_trapezoid_shader(ScreenPtr screen)
> " \n"
> " percent = (bottom - up) / y_per_pix; \n"
> " \n"
> - " if(trap_left_vertical == 1) { \n"
> + " if(trap_left_vertical == true) { \n"
> " if(trap_left_x > source_texture.x - x_per_pix/2.0 && \n"
> " trap_left_x < source_texture.x + x_per_pix/2.0) \n"
> " left = trap_left_x; \n"
> " } \n"
> - " if(trap_right_vertical == 1) { \n"
> + " if(trap_right_vertical == true) { \n"
> " if(trap_right_x > source_texture.x - x_per_pix/2.0 && \n"
> " trap_right_x < source_texture.x + x_per_pix/2.0) \n"
> " right = trap_right_x; \n"
> @@ -1016,10 +1135,10 @@ glamor_init_trapezoid_shader(ScreenPtr screen)
> " return 0.0; \n"
> " \n"
> " percent = percent * ((right - left)/x_per_pix); \n"
> - " if(trap_left_vertical == 1 && trap_right_vertical == 1) \n"
> + " if(trap_left_vertical == true && trap_right_vertical == true) \n"
> " return percent; \n"
> " \n"
> - " if(trap_left_vertical != 1) { \n"
> + " if(trap_left_vertical != true) { \n"
> " float area; \n"
> // the slope should never be 0.0 here
> " float up_x = trap_left_x + (up - trap_left_y)/trap_left_slope; \n"
> @@ -1090,7 +1209,7 @@ glamor_init_trapezoid_shader(ScreenPtr screen)
> " } \n"
> " } \n"
> " \n"
> - " if(trap_right_vertical != 1) { \n"
> + " if(trap_right_vertical != true) { \n"
> " float area; \n"
> // the slope should never be 0.0 here
> " float up_x = trap_right_x + (up - trap_right_y)/trap_right_slope; \n"
> @@ -1184,9 +1303,15 @@ glamor_init_trapezoid_shader(ScreenPtr screen)
> dispatch->glAttachShader(glamor_priv->trapezoid_prog, fs_prog);
>
> dispatch->glBindAttribLocation(glamor_priv->trapezoid_prog,
> - GLAMOR_VERTEX_POS, "v_positionsition");
> + GLAMOR_VERTEX_POS, "v_positionsition");
> dispatch->glBindAttribLocation(glamor_priv->trapezoid_prog,
> - GLAMOR_VERTEX_SOURCE, "v_texcoord");
> + GLAMOR_VERTEX_SOURCE, "v_texcoord");
> + dispatch->glBindAttribLocation(glamor_priv->trapezoid_prog,
> + GLAMOR_VERTEX_TOP_BOTTOM, "v_top_bottom");
> + dispatch->glBindAttribLocation(glamor_priv->trapezoid_prog,
> + GLAMOR_VERTEX_LEFT_PARAM, "v_left_param");
> + dispatch->glBindAttribLocation(glamor_priv->trapezoid_prog,
> + GLAMOR_VERTEX_RIGHT_PARAM, "v_right_param");
>
> glamor_link_glsl_prog(dispatch, glamor_priv->trapezoid_prog);
>
> @@ -1215,28 +1340,16 @@ _glamor_generate_trapezoid_with_shader(ScreenPtr screen, PicturePtr picture,
> glamor_gl_dispatch *dispatch;
> glamor_pixmap_private *pixmap_priv;
> PixmapPtr pixmap = NULL;
> - GLint x_per_pix_uniform_location;
> - GLint y_per_pix_uniform_location;
> - GLint trap_top_uniform_location;
> - GLint trap_bottom_uniform_location;
> - GLint trap_left_x_uniform_location;
> - GLint trap_left_y_uniform_location;
> - GLint trap_left_slope_uniform_location;
> - GLint trap_right_x_uniform_location;
> - GLint trap_right_y_uniform_location;
> - GLint trap_right_slope_uniform_location;
> - GLint trap_left_vertical_uniform_location;
> - GLint trap_right_vertical_uniform_location;
> GLint trapezoid_prog;
> float width, height;
> - xFixed width_fix, height_fix;
> GLfloat xscale, yscale;
> float left_slope, right_slope;
> xTrapezoid *ptrap;
> BoxRec one_trap_bound;
> - float vertices[8];
> - float tex_vertices[8];
> - int i;
> + int nrect_max;
> + int i, j;
> + float *vertices;
> + float params[4];
>
> glamor_priv = glamor_get_screen_private(screen);
> trapezoid_prog = glamor_priv->trapezoid_prog;
> @@ -1245,7 +1358,7 @@ _glamor_generate_trapezoid_with_shader(ScreenPtr screen, PicturePtr picture,
> pixmap_priv = glamor_get_pixmap_private(pixmap);
>
> if (!GLAMOR_PIXMAP_PRIV_HAS_FBO(pixmap_priv)
> - || pixmap_priv->type == GLAMOR_TEXTURE_LARGE) { /* should always have here. */
> + || pixmap_priv->type == GLAMOR_TEXTURE_LARGE) { /* should always have here. */
> DEBUGF("GLAMOR_PIXMAP_PRIV_HAS_FBO check failed, fallback\n");
> return FALSE;
> }
> @@ -1260,155 +1373,153 @@ _glamor_generate_trapezoid_with_shader(ScreenPtr screen, PicturePtr picture,
>
> dispatch = glamor_get_dispatch(glamor_priv);
>
> - /* Bind all the uniform vars .*/
> - x_per_pix_uniform_location =
> - dispatch->glGetUniformLocation(trapezoid_prog, "x_per_pix");
> - y_per_pix_uniform_location =
> - dispatch->glGetUniformLocation(trapezoid_prog, "y_per_pix");
> - trap_top_uniform_location =
> - dispatch->glGetUniformLocation(trapezoid_prog, "trap_top");
> - trap_bottom_uniform_location =
> - dispatch->glGetUniformLocation(trapezoid_prog, "trap_bottom");
> - trap_left_x_uniform_location =
> - dispatch->glGetUniformLocation(trapezoid_prog, "trap_left_x");
> - trap_left_y_uniform_location =
> - dispatch->glGetUniformLocation(trapezoid_prog, "trap_left_y");
> - trap_left_slope_uniform_location =
> - dispatch->glGetUniformLocation(trapezoid_prog, "trap_left_slope");
> - trap_left_vertical_uniform_location =
> - dispatch->glGetUniformLocation(trapezoid_prog, "trap_left_vertical");
> - trap_right_x_uniform_location =
> - dispatch->glGetUniformLocation(trapezoid_prog, "trap_right_x");
> - trap_right_y_uniform_location =
> - dispatch->glGetUniformLocation(trapezoid_prog, "trap_right_y");
> - trap_right_slope_uniform_location =
> - dispatch->glGetUniformLocation(trapezoid_prog, "trap_right_slope");
> - trap_right_vertical_uniform_location =
> - dispatch->glGetUniformLocation(trapezoid_prog, "trap_right_vertical");
> -
> glamor_set_destination_pixmap_priv_nc(pixmap_priv);
>
> pixmap_priv_get_dest_scale(pixmap_priv, (&xscale), (&yscale));
>
> width = (float)(bounds->x2 - bounds->x1);
> height = (float)(bounds->y2 - bounds->y1);
> - width_fix = IntToxFixed((bounds->x2 - bounds->x1));
> - height_fix = IntToxFixed((bounds->y2 - bounds->y1));
>
> dispatch->glBindBuffer(GL_ARRAY_BUFFER, 0);
> dispatch->glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, 0);
>
> - dispatch->glDisableVertexAttribArray(GLAMOR_VERTEX_POS);
> - dispatch->glDisableVertexAttribArray(GLAMOR_VERTEX_SOURCE);
> -
> /* Now draw the Trapezoid mask. */
> dispatch->glUseProgram(trapezoid_prog);
> - dispatch->glVertexAttribPointer(GLAMOR_VERTEX_POS, 2, GL_FLOAT,
> - GL_FALSE, 0, vertices);
> - dispatch->glVertexAttribPointer(GLAMOR_VERTEX_SOURCE, 2, GL_FLOAT,
> - GL_FALSE, 0, tex_vertices);
> - dispatch->glEnableVertexAttribArray(GLAMOR_VERTEX_POS);
> - dispatch->glEnableVertexAttribArray(GLAMOR_VERTEX_SOURCE);
>
> dispatch->glEnable(GL_BLEND);
> dispatch->glBlendFunc(GL_ONE, GL_ONE);
>
> - for (i = 0; i < ntrap; i++) {
> - ptrap = traps + i;
> -
> - DEBUGF("--- The parameter of xTrapezoid is:\ntop: %d 0x%x\tbottom: %d 0x%x\n"
> - "left: p1 (%d 0x%x, %d 0x%x)\tp2 (%d 0x%x, %d 0x%x)\n"
> - "right: p1 (%d 0x%x, %d 0x%x)\tp2 (%d 0x%x, %d 0x%x)\n",
> - xFixedToInt(ptrap->top), ptrap->top,
> - xFixedToInt(ptrap->bottom), ptrap->bottom,
> - xFixedToInt(ptrap->left.p1.x), ptrap->left.p1.x,
> - xFixedToInt(ptrap->left.p1.y), ptrap->left.p1.y,
> - xFixedToInt(ptrap->left.p2.x), ptrap->left.p2.x,
> - xFixedToInt(ptrap->left.p2.y), ptrap->left.p2.y,
> - xFixedToInt(ptrap->right.p1.x), ptrap->right.p1.x,
> - xFixedToInt(ptrap->right.p1.y), ptrap->right.p1.y,
> - xFixedToInt(ptrap->right.p2.x), ptrap->right.p2.x,
> - xFixedToInt(ptrap->right.p2.y), ptrap->right.p2.y);
> -
> - miTrapezoidBounds(1, ptrap, &one_trap_bound);
> - glamor_set_tcoords_tri_strip((pixmap_priv->base.pixmap->drawable.width),
> - (pixmap_priv->base.pixmap->drawable.height),
> - (one_trap_bound.x1),
> - (one_trap_bound.y1),
> - (one_trap_bound.x2),
> - (one_trap_bound.y2),
> - glamor_priv->yInverted, tex_vertices);
> -
> - /* Need to rebase. */
> - one_trap_bound.x1 -= bounds->x1;
> - one_trap_bound.x2 -= bounds->x1;
> - one_trap_bound.y1 -= bounds->y1;
> - one_trap_bound.y2 -= bounds->y1;
> - glamor_set_normalize_vcoords_tri_strip(xscale, yscale,
> - one_trap_bound.x1, one_trap_bound.y1,
> - one_trap_bound.x2, one_trap_bound.y2,
> - glamor_priv->yInverted, vertices);
> -
> - DEBUGF("vertices --> leftup : %f X %f, rightup: %f X %f,"
> - "rightbottom: %f X %f, leftbottom : %f X %f\n",
> - vertices[0], vertices[1], vertices[2], vertices[3],
> - vertices[4], vertices[5], vertices[6], vertices[7]);
> - DEBUGF("tex_vertices --> leftup : %f X %f, rightup: %f X %f,"
> - "rightbottom: %f X %f, leftbottom : %f X %f\n",
> - tex_vertices[0], tex_vertices[1], tex_vertices[2], tex_vertices[3],
> - tex_vertices[4], tex_vertices[5], tex_vertices[6], tex_vertices[7]);
> -
> - if (ptrap->left.p1.x == ptrap->left.p2.x) {
> - left_slope = 0.0;
> - dispatch->glUniform1i(trap_left_vertical_uniform_location, 1);
> - } else {
> - left_slope = ((float)(ptrap->left.p1.y - ptrap->left.p2.y))
> - / ((float)(ptrap->left.p1.x - ptrap->left.p2.x));
> - dispatch->glUniform1i(trap_left_vertical_uniform_location, 0);
> + nrect_max = GLAMOR_COMPOSITE_VBO_VERT_CNT / (4 * GLAMOR_VERTEX_RIGHT_PARAM);
> +
> + for (i = 0; i < ntrap;) {
> + int mrect;
> + int stride;
> +
> + mrect = (ntrap - i) > nrect_max ? nrect_max : (ntrap - i);
> + glamor_setup_composite_vbo_for_trapezoid(screen, 4 * mrect);
> + stride = glamor_priv->vb_stride / sizeof(float);
> +
> + for (j = 0; j < mrect; j++) {
> + ptrap = traps + i + j;
> +
> + DEBUGF("--- The parameter of xTrapezoid is:\ntop: %d 0x%x\tbottom: %d 0x%x\n"
> + "left: p1 (%d 0x%x, %d 0x%x)\tp2 (%d 0x%x, %d 0x%x)\n"
> + "right: p1 (%d 0x%x, %d 0x%x)\tp2 (%d 0x%x, %d 0x%x)\n",
> + xFixedToInt(ptrap->top), ptrap->top,
> + xFixedToInt(ptrap->bottom), ptrap->bottom,
> + xFixedToInt(ptrap->left.p1.x), ptrap->left.p1.x,
> + xFixedToInt(ptrap->left.p1.y), ptrap->left.p1.y,
> + xFixedToInt(ptrap->left.p2.x), ptrap->left.p2.x,
> + xFixedToInt(ptrap->left.p2.y), ptrap->left.p2.y,
> + xFixedToInt(ptrap->right.p1.x), ptrap->right.p1.x,
> + xFixedToInt(ptrap->right.p1.y), ptrap->right.p1.y,
> + xFixedToInt(ptrap->right.p2.x), ptrap->right.p2.x,
> + xFixedToInt(ptrap->right.p2.y), ptrap->right.p2.y);
> +
> + miTrapezoidBounds(1, ptrap, &one_trap_bound);
> +
> + vertices = (float*)(glamor_priv->vb + glamor_priv->vbo_offset) + 2;
> + glamor_set_tcoords_ext((pixmap_priv->base.pixmap->drawable.width),
> + (pixmap_priv->base.pixmap->drawable.height),
> + (one_trap_bound.x1),
> + (one_trap_bound.y1),
> + (one_trap_bound.x2),
> + (one_trap_bound.y2),
> + glamor_priv->yInverted, vertices, stride);
> + DEBUGF("tex_vertices --> leftup : %f X %f, rightup: %f X %f,"
> + "rightbottom: %f X %f, leftbottom : %f X %f\n",
> + vertices[0], vertices[1],
> + vertices[1*stride], vertices[1*stride + 1],
> + vertices[2*stride], vertices[2*stride + 1],
> + vertices[3*stride], vertices[3*stride + 1]);
> +
> + /* Need to rebase. */
> + one_trap_bound.x1 -= bounds->x1;
> + one_trap_bound.x2 -= bounds->x1;
> + one_trap_bound.y1 -= bounds->y1;
> + one_trap_bound.y2 -= bounds->y1;
> +
> + vertices -= 2;
> +
> + glamor_set_normalize_vcoords_ext(pixmap_priv, xscale, yscale,
> + one_trap_bound.x1, one_trap_bound.y1,
> + one_trap_bound.x2, one_trap_bound.y2,
> + glamor_priv->yInverted, vertices, stride);
> + DEBUGF("vertices --> leftup : %f X %f, rightup: %f X %f,"
> + "rightbottom: %f X %f, leftbottom : %f X %f\n",
> + vertices[0], vertices[1],
> + vertices[1*stride], vertices[1*stride + 1],
> + vertices[2*stride], vertices[2*stride + 1],
> + vertices[3*stride], vertices[3*stride + 1]);
> + vertices += 4;
> +
> + /* Set the top and bottom. */
> + params[0] = ((float)ptrap->top) / 65536;
> + params[1] = ((float)ptrap->bottom) / 65536;
> + glamor_set_const_ext(params, 2, vertices, 4, stride);
> + vertices += 2;
> +
> + /* Set the left params. */
> + params[0] = ((float)ptrap->left.p1.x) / 65536;
> + params[1] = ((float)ptrap->left.p1.y) / 65536;
> +
> + if (ptrap->left.p1.x == ptrap->left.p2.x) {
> + left_slope = 0.0;
> + params[3] = 1.0;
> + } else {
> + left_slope = ((float)(ptrap->left.p1.y - ptrap->left.p2.y))
> + / ((float)(ptrap->left.p1.x - ptrap->left.p2.x));
> + params[3] = 0.0;
> + }
> + params[2] = left_slope;
> + glamor_set_const_ext(params, 4, vertices, 4, stride);
> + vertices += 4;
> +
> + /* Set the left params. */
> + params[0] = ((float)ptrap->right.p1.x) / 65536;
> + params[1] = ((float)ptrap->right.p1.y) / 65536;
> +
> + if (ptrap->right.p1.x == ptrap->right.p2.x) {
> + right_slope = 0.0;
> + params[3] = 1.0;
> + } else {
> + right_slope = ((float)(ptrap->right.p1.y - ptrap->right.p2.y))
> + / ((float)(ptrap->right.p1.x - ptrap->right.p2.x));
> + params[3] = 0.0;
> + }
> + params[2] = right_slope;
> + glamor_set_const_ext(params, 4, vertices, 4, stride);
> +
> + DEBUGF("trap_top = %f, trap_bottom = %f, "
> + "trap_left_x = %f, trap_left_y = %f, left_slope = %f, "
> + "trap_right_x = %f, trap_right_y = %f, right_slope = %f\n",
> + ((float)ptrap->top) / 65536, ((float)ptrap->bottom) / 65536,
> + ((float)ptrap->left.p1.x) / 65536, ((float)ptrap->left.p1.y) / 65536,
> + left_slope,
> + ((float)ptrap->right.p1.x) / 65536, ((float)ptrap->right.p1.y) / 65536,
> + right_slope);
> +
> + glamor_priv->render_nr_verts += 4;
> + glamor_priv->vbo_offset += glamor_priv->vb_stride * 4;
> }
> - dispatch->glUniform1f(trap_left_slope_uniform_location, left_slope);
>
> - if (ptrap->right.p1.x == ptrap->right.p2.x) {
> - right_slope = 0.0;
> - dispatch->glUniform1i(trap_right_vertical_uniform_location, 1);
> - } else {
> - right_slope = ((float)(ptrap->right.p1.y - ptrap->right.p2.y))
> - / ((float)(ptrap->right.p1.x - ptrap->right.p2.x));
> - dispatch->glUniform1i(trap_right_vertical_uniform_location, 0);
> - }
> - dispatch->glUniform1f(trap_right_slope_uniform_location, right_slope);
> -
> - dispatch->glUniform1f(x_per_pix_uniform_location,
> - ((float)width_fix) / (65536 * width));
> - dispatch->glUniform1f(y_per_pix_uniform_location,
> - ((float)height_fix) / (65536 * height));
> -
> - dispatch->glUniform1f(trap_top_uniform_location,
> - ((float)ptrap->top) / 65536);
> - dispatch->glUniform1f(trap_bottom_uniform_location,
> - ((float)ptrap->bottom) / 65536);
> -
> - dispatch->glUniform1f(trap_left_x_uniform_location,
> - ((float)ptrap->left.p1.x) / 65536);
> - dispatch->glUniform1f(trap_left_y_uniform_location,
> - ((float)ptrap->left.p1.y) / 65536);
> - dispatch->glUniform1f(trap_right_x_uniform_location,
> - ((float)ptrap->right.p1.x) / 65536);
> - dispatch->glUniform1f(trap_right_y_uniform_location,
> - ((float)ptrap->right.p1.y) / 65536);
> -
> - DEBUGF("x_per_pix = %f, y_per_pix = %f, trap_top = %f, trap_bottom = %f, "
> - "trap_left_x = %f, trap_left_y = %f, left_slope = %f, "
> - "trap_right_x = %f, trap_right_y = %f, right_slope = %f\n",
> - ((float)width_fix) / (65536*width), ((float)height_fix) / (65536*height),
> - ((float)ptrap->top) / 65536, ((float)ptrap->bottom) / 65536,
> - ((float)ptrap->left.p1.x) / 65536, ((float)ptrap->left.p1.y) / 65536,
> - left_slope,
> - ((float)ptrap->right.p1.x) / 65536, ((float)ptrap->right.p1.y) / 65536,
> - right_slope);
> + i += mrect;
>
> /* Now rendering. */
> - dispatch->glDrawArrays(GL_TRIANGLE_STRIP, 0, 4);
> + if (!glamor_priv->render_nr_verts)
> + continue;
> +
> + if (glamor_priv->gl_flavor == GLAMOR_GL_DESKTOP)
> + dispatch->glUnmapBuffer(GL_ARRAY_BUFFER);
> + else {
> + dispatch->glBindBuffer(GL_ARRAY_BUFFER, glamor_priv->vbo);
> + dispatch->glBufferData(GL_ARRAY_BUFFER,
> + glamor_priv->vbo_offset,
> + glamor_priv->vb, GL_DYNAMIC_DRAW);
> + }
> +
> + dispatch->glDrawElements(GL_TRIANGLES, (glamor_priv->render_nr_verts * 3) / 2,
> + GL_UNSIGNED_SHORT, NULL);
> }
>
> dispatch->glBindBuffer(GL_ARRAY_BUFFER, 0);
> @@ -1417,6 +1528,9 @@ _glamor_generate_trapezoid_with_shader(ScreenPtr screen, PicturePtr picture,
> dispatch->glDisable(GL_BLEND);
> dispatch->glDisableVertexAttribArray(GLAMOR_VERTEX_POS);
> dispatch->glDisableVertexAttribArray(GLAMOR_VERTEX_SOURCE);
> + dispatch->glDisableVertexAttribArray(GLAMOR_VERTEX_TOP_BOTTOM);
> + dispatch->glDisableVertexAttribArray(GLAMOR_VERTEX_LEFT_PARAM);
> + dispatch->glDisableVertexAttribArray(GLAMOR_VERTEX_RIGHT_PARAM);
> dispatch->glUseProgram(0);
> glamor_put_dispatch(glamor_priv);
> return TRUE;
> diff --git a/src/glamor_utils.h b/src/glamor_utils.h
> index a282985..c0445b5 100644
> --- a/src/glamor_utils.h
> +++ b/src/glamor_utils.h
> @@ -629,6 +629,25 @@
> (vertices)[7] = (vertices)[5]; \
> } while(0)
>
> +#define glamor_set_tcoords_ext(width, height, x1, y1, x2, y2, \
> + yInverted, vertices, stride) \
> + do { \
> + (vertices)[0] = (x1); \
> + (vertices)[1*stride] = (x2); \
> + (vertices)[2*stride] = (vertices)[1*stride]; \
> + (vertices)[3*stride] = (vertices)[0]; \
> + if (likely(yInverted)) { \
> + (vertices)[1] = (y1); \
> + (vertices)[2*stride + 1] = (y2); \
> + } \
> + else { \
> + (vertices)[1] = height - (y2); \
> + (vertices)[2*stride + 1] = height - (y1); \
> + } \
> + (vertices)[1*stride + 1] = (vertices)[1]; \
> + (vertices)[3*stride + 1] = (vertices)[2*stride + 1]; \
> + } while(0)
> +
> #define glamor_set_normalize_one_vcoord(xscale, yscale, x, y, \
> yInverted, vertices) \
> do { \
> @@ -713,6 +732,16 @@
> yInverted, vertices, 2); \
> } while(0)
>
> +#define glamor_set_const_ext(params, nparam, vertices, nverts, stride) \
> + do { \
> + int i = 0, j = 0; \
> + for(; i < nverts; i++) { \
> + for(j = 0; j < nparam; j++) { \
> + vertices[stride*i + j] = params[j]; \
> + } \
> + } \
> + } while(0)
> +
> #define glamor_set_normalize_vcoords_tri_strip(xscale, yscale, \
> x1, y1, x2, y2, \
> yInverted, vertices) \
>
More information about the Glamor
mailing list