toytoolkit: Don't draw shadows for maximized windows.
[profile/ivi/weston.git] / src / gles2-renderer.c
1 /*
2  * Copyright © 2012 Intel Corporation
3  *
4  * Permission to use, copy, modify, distribute, and sell this software and
5  * its documentation for any purpose is hereby granted without fee, provided
6  * that the above copyright notice appear in all copies and that both that
7  * copyright notice and this permission notice appear in supporting
8  * documentation, and that the name of the copyright holders not be used in
9  * advertising or publicity pertaining to distribution of the software
10  * without specific, written prior permission.  The copyright holders make
11  * no representations about the suitability of this software for any
12  * purpose.  It is provided "as is" without express or implied warranty.
13  *
14  * THE COPYRIGHT HOLDERS DISCLAIM ALL WARRANTIES WITH REGARD TO THIS
15  * SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND
16  * FITNESS, IN NO EVENT SHALL THE COPYRIGHT HOLDERS BE LIABLE FOR ANY
17  * SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER
18  * RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF
19  * CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
20  * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
21  */
22
23 #define _GNU_SOURCE
24
25 #include <stdlib.h>
26 #include <string.h>
27 #include <ctype.h>
28 #include <float.h>
29 #include <assert.h>
30
31 #include "compositor.h"
32
33 static const char *
34 egl_error_string(EGLint code)
35 {
36 #define MYERRCODE(x) case x: return #x;
37         switch (code) {
38         MYERRCODE(EGL_SUCCESS)
39         MYERRCODE(EGL_NOT_INITIALIZED)
40         MYERRCODE(EGL_BAD_ACCESS)
41         MYERRCODE(EGL_BAD_ALLOC)
42         MYERRCODE(EGL_BAD_ATTRIBUTE)
43         MYERRCODE(EGL_BAD_CONTEXT)
44         MYERRCODE(EGL_BAD_CONFIG)
45         MYERRCODE(EGL_BAD_CURRENT_SURFACE)
46         MYERRCODE(EGL_BAD_DISPLAY)
47         MYERRCODE(EGL_BAD_SURFACE)
48         MYERRCODE(EGL_BAD_MATCH)
49         MYERRCODE(EGL_BAD_PARAMETER)
50         MYERRCODE(EGL_BAD_NATIVE_PIXMAP)
51         MYERRCODE(EGL_BAD_NATIVE_WINDOW)
52         MYERRCODE(EGL_CONTEXT_LOST)
53         default:
54                 return "unknown";
55         }
56 #undef MYERRCODE
57 }
58
59 static void
60 print_egl_error_state(void)
61 {
62         EGLint code;
63
64         code = eglGetError();
65         weston_log("EGL error state: %s (0x%04lx)\n",
66                 egl_error_string(code), (long)code);
67 }
68
69 struct polygon8 {
70         GLfloat x[8];
71         GLfloat y[8];
72         int n;
73 };
74
75 struct clip_context {
76         struct {
77                 GLfloat x;
78                 GLfloat y;
79         } prev;
80
81         struct {
82                 GLfloat x1, y1;
83                 GLfloat x2, y2;
84         } clip;
85
86         struct {
87                 GLfloat *x;
88                 GLfloat *y;
89         } vertices;
90 };
91
92 static GLfloat
93 float_difference(GLfloat a, GLfloat b)
94 {
95         /* http://www.altdevblogaday.com/2012/02/22/comparing-floating-point-numbers-2012-edition/ */
96         static const GLfloat max_diff = 4.0f * FLT_MIN;
97         static const GLfloat max_rel_diff = 4.0e-5;
98         GLfloat diff = a - b;
99         GLfloat adiff = fabsf(diff);
100
101         if (adiff <= max_diff)
102                 return 0.0f;
103
104         a = fabsf(a);
105         b = fabsf(b);
106         if (adiff <= (a > b ? a : b) * max_rel_diff)
107                 return 0.0f;
108
109         return diff;
110 }
111
112 /* A line segment (p1x, p1y)-(p2x, p2y) intersects the line x = x_arg.
113  * Compute the y coordinate of the intersection.
114  */
115 static GLfloat
116 clip_intersect_y(GLfloat p1x, GLfloat p1y, GLfloat p2x, GLfloat p2y,
117                  GLfloat x_arg)
118 {
119         GLfloat a;
120         GLfloat diff = float_difference(p1x, p2x);
121
122         /* Practically vertical line segment, yet the end points have already
123          * been determined to be on different sides of the line. Therefore
124          * the line segment is part of the line and intersects everywhere.
125          * Return the end point, so we use the whole line segment.
126          */
127         if (diff == 0.0f)
128                 return p2y;
129
130         a = (x_arg - p2x) / diff;
131         return p2y + (p1y - p2y) * a;
132 }
133
134 /* A line segment (p1x, p1y)-(p2x, p2y) intersects the line y = y_arg.
135  * Compute the x coordinate of the intersection.
136  */
137 static GLfloat
138 clip_intersect_x(GLfloat p1x, GLfloat p1y, GLfloat p2x, GLfloat p2y,
139                  GLfloat y_arg)
140 {
141         GLfloat a;
142         GLfloat diff = float_difference(p1y, p2y);
143
144         /* Practically horizontal line segment, yet the end points have already
145          * been determined to be on different sides of the line. Therefore
146          * the line segment is part of the line and intersects everywhere.
147          * Return the end point, so we use the whole line segment.
148          */
149         if (diff == 0.0f)
150                 return p2x;
151
152         a = (y_arg - p2y) / diff;
153         return p2x + (p1x - p2x) * a;
154 }
155
156 enum path_transition {
157         PATH_TRANSITION_OUT_TO_OUT = 0,
158         PATH_TRANSITION_OUT_TO_IN = 1,
159         PATH_TRANSITION_IN_TO_OUT = 2,
160         PATH_TRANSITION_IN_TO_IN = 3,
161 };
162
163 static void
164 clip_append_vertex(struct clip_context *ctx, GLfloat x, GLfloat y)
165 {
166         *ctx->vertices.x++ = x;
167         *ctx->vertices.y++ = y;
168 }
169
170 static enum path_transition
171 path_transition_left_edge(struct clip_context *ctx, GLfloat x, GLfloat y)
172 {
173         return ((ctx->prev.x >= ctx->clip.x1) << 1) | (x >= ctx->clip.x1);
174 }
175
176 static enum path_transition
177 path_transition_right_edge(struct clip_context *ctx, GLfloat x, GLfloat y)
178 {
179         return ((ctx->prev.x < ctx->clip.x2) << 1) | (x < ctx->clip.x2);
180 }
181
182 static enum path_transition
183 path_transition_top_edge(struct clip_context *ctx, GLfloat x, GLfloat y)
184 {
185         return ((ctx->prev.y >= ctx->clip.y1) << 1) | (y >= ctx->clip.y1);
186 }
187
188 static enum path_transition
189 path_transition_bottom_edge(struct clip_context *ctx, GLfloat x, GLfloat y)
190 {
191         return ((ctx->prev.y < ctx->clip.y2) << 1) | (y < ctx->clip.y2);
192 }
193
194 static void
195 clip_polygon_leftright(struct clip_context *ctx,
196                        enum path_transition transition,
197                        GLfloat x, GLfloat y, GLfloat clip_x)
198 {
199         GLfloat yi;
200
201         switch (transition) {
202         case PATH_TRANSITION_IN_TO_IN:
203                 clip_append_vertex(ctx, x, y);
204                 break;
205         case PATH_TRANSITION_IN_TO_OUT:
206                 yi = clip_intersect_y(ctx->prev.x, ctx->prev.y, x, y, clip_x);
207                 clip_append_vertex(ctx, clip_x, yi);
208                 break;
209         case PATH_TRANSITION_OUT_TO_IN:
210                 yi = clip_intersect_y(ctx->prev.x, ctx->prev.y, x, y, clip_x);
211                 clip_append_vertex(ctx, clip_x, yi);
212                 clip_append_vertex(ctx, x, y);
213                 break;
214         case PATH_TRANSITION_OUT_TO_OUT:
215                 /* nothing */
216                 break;
217         default:
218                 assert(0 && "bad enum path_transition");
219         }
220
221         ctx->prev.x = x;
222         ctx->prev.y = y;
223 }
224
225 static void
226 clip_polygon_topbottom(struct clip_context *ctx,
227                        enum path_transition transition,
228                        GLfloat x, GLfloat y, GLfloat clip_y)
229 {
230         GLfloat xi;
231
232         switch (transition) {
233         case PATH_TRANSITION_IN_TO_IN:
234                 clip_append_vertex(ctx, x, y);
235                 break;
236         case PATH_TRANSITION_IN_TO_OUT:
237                 xi = clip_intersect_x(ctx->prev.x, ctx->prev.y, x, y, clip_y);
238                 clip_append_vertex(ctx, xi, clip_y);
239                 break;
240         case PATH_TRANSITION_OUT_TO_IN:
241                 xi = clip_intersect_x(ctx->prev.x, ctx->prev.y, x, y, clip_y);
242                 clip_append_vertex(ctx, xi, clip_y);
243                 clip_append_vertex(ctx, x, y);
244                 break;
245         case PATH_TRANSITION_OUT_TO_OUT:
246                 /* nothing */
247                 break;
248         default:
249                 assert(0 && "bad enum path_transition");
250         }
251
252         ctx->prev.x = x;
253         ctx->prev.y = y;
254 }
255
256 static void
257 clip_context_prepare(struct clip_context *ctx, const struct polygon8 *src,
258                       GLfloat *dst_x, GLfloat *dst_y)
259 {
260         ctx->prev.x = src->x[src->n - 1];
261         ctx->prev.y = src->y[src->n - 1];
262         ctx->vertices.x = dst_x;
263         ctx->vertices.y = dst_y;
264 }
265
266 static int
267 clip_polygon_left(struct clip_context *ctx, const struct polygon8 *src,
268                   GLfloat *dst_x, GLfloat *dst_y)
269 {
270         enum path_transition trans;
271         int i;
272
273         clip_context_prepare(ctx, src, dst_x, dst_y);
274         for (i = 0; i < src->n; i++) {
275                 trans = path_transition_left_edge(ctx, src->x[i], src->y[i]);
276                 clip_polygon_leftright(ctx, trans, src->x[i], src->y[i],
277                                        ctx->clip.x1);
278         }
279         return ctx->vertices.x - dst_x;
280 }
281
282 static int
283 clip_polygon_right(struct clip_context *ctx, const struct polygon8 *src,
284                    GLfloat *dst_x, GLfloat *dst_y)
285 {
286         enum path_transition trans;
287         int i;
288
289         clip_context_prepare(ctx, src, dst_x, dst_y);
290         for (i = 0; i < src->n; i++) {
291                 trans = path_transition_right_edge(ctx, src->x[i], src->y[i]);
292                 clip_polygon_leftright(ctx, trans, src->x[i], src->y[i],
293                                        ctx->clip.x2);
294         }
295         return ctx->vertices.x - dst_x;
296 }
297
298 static int
299 clip_polygon_top(struct clip_context *ctx, const struct polygon8 *src,
300                  GLfloat *dst_x, GLfloat *dst_y)
301 {
302         enum path_transition trans;
303         int i;
304
305         clip_context_prepare(ctx, src, dst_x, dst_y);
306         for (i = 0; i < src->n; i++) {
307                 trans = path_transition_top_edge(ctx, src->x[i], src->y[i]);
308                 clip_polygon_topbottom(ctx, trans, src->x[i], src->y[i],
309                                        ctx->clip.y1);
310         }
311         return ctx->vertices.x - dst_x;
312 }
313
314 static int
315 clip_polygon_bottom(struct clip_context *ctx, const struct polygon8 *src,
316                     GLfloat *dst_x, GLfloat *dst_y)
317 {
318         enum path_transition trans;
319         int i;
320
321         clip_context_prepare(ctx, src, dst_x, dst_y);
322         for (i = 0; i < src->n; i++) {
323                 trans = path_transition_bottom_edge(ctx, src->x[i], src->y[i]);
324                 clip_polygon_topbottom(ctx, trans, src->x[i], src->y[i],
325                                        ctx->clip.y2);
326         }
327         return ctx->vertices.x - dst_x;
328 }
329
330 #define max(a, b) (((a) > (b)) ? (a) : (b))
331 #define min(a, b) (((a) > (b)) ? (b) : (a))
332 #define clip(x, a, b)  min(max(x, a), b)
333
334 /*
335  * Compute the boundary vertices of the intersection of the global coordinate
336  * aligned rectangle 'rect', and an arbitrary quadrilateral produced from
337  * 'surf_rect' when transformed from surface coordinates into global coordinates.
338  * The vertices are written to 'ex' and 'ey', and the return value is the
339  * number of vertices. Vertices are produced in clockwise winding order.
340  * Guarantees to produce either zero vertices, or 3-8 vertices with non-zero
341  * polygon area.
342  */
343 static int
344 calculate_edges(struct weston_surface *es, pixman_box32_t *rect,
345                 pixman_box32_t *surf_rect, GLfloat *ex, GLfloat *ey)
346 {
347         struct polygon8 polygon;
348         struct clip_context ctx;
349         int i, n;
350         GLfloat min_x, max_x, min_y, max_y;
351         struct polygon8 surf = {
352                 { surf_rect->x1, surf_rect->x2, surf_rect->x2, surf_rect->x1 },
353                 { surf_rect->y1, surf_rect->y1, surf_rect->y2, surf_rect->y2 },
354                 4
355         };
356
357         ctx.clip.x1 = rect->x1;
358         ctx.clip.y1 = rect->y1;
359         ctx.clip.x2 = rect->x2;
360         ctx.clip.y2 = rect->y2;
361
362         /* transform surface to screen space: */
363         for (i = 0; i < surf.n; i++)
364                 weston_surface_to_global_float(es, surf.x[i], surf.y[i],
365                                                &surf.x[i], &surf.y[i]);
366
367         /* find bounding box: */
368         min_x = max_x = surf.x[0];
369         min_y = max_y = surf.y[0];
370
371         for (i = 1; i < surf.n; i++) {
372                 min_x = min(min_x, surf.x[i]);
373                 max_x = max(max_x, surf.x[i]);
374                 min_y = min(min_y, surf.y[i]);
375                 max_y = max(max_y, surf.y[i]);
376         }
377
378         /* First, simple bounding box check to discard early transformed
379          * surface rects that do not intersect with the clip region:
380          */
381         if ((min_x >= ctx.clip.x2) || (max_x <= ctx.clip.x1) ||
382             (min_y >= ctx.clip.y2) || (max_y <= ctx.clip.y1))
383                 return 0;
384
385         /* Simple case, bounding box edges are parallel to surface edges,
386          * there will be only four edges.  We just need to clip the surface
387          * vertices to the clip rect bounds:
388          */
389         if (!es->transform.enabled) {
390                 for (i = 0; i < surf.n; i++) {
391                         ex[i] = clip(surf.x[i], ctx.clip.x1, ctx.clip.x2);
392                         ey[i] = clip(surf.y[i], ctx.clip.y1, ctx.clip.y2);
393                 }
394                 return surf.n;
395         }
396
397         /* Transformed case: use a general polygon clipping algorithm to
398          * clip the surface rectangle with each side of 'rect'.
399          * The algorithm is Sutherland-Hodgman, as explained in
400          * http://www.codeguru.com/cpp/misc/misc/graphics/article.php/c8965/Polygon-Clipping.htm
401          * but without looking at any of that code.
402          */
403         polygon.n = clip_polygon_left(&ctx, &surf, polygon.x, polygon.y);
404         surf.n = clip_polygon_right(&ctx, &polygon, surf.x, surf.y);
405         polygon.n = clip_polygon_top(&ctx, &surf, polygon.x, polygon.y);
406         surf.n = clip_polygon_bottom(&ctx, &polygon, surf.x, surf.y);
407
408         /* Get rid of duplicate vertices */
409         ex[0] = surf.x[0];
410         ey[0] = surf.y[0];
411         n = 1;
412         for (i = 1; i < surf.n; i++) {
413                 if (float_difference(ex[n - 1], surf.x[i]) == 0.0f &&
414                     float_difference(ey[n - 1], surf.y[i]) == 0.0f)
415                         continue;
416                 ex[n] = surf.x[i];
417                 ey[n] = surf.y[i];
418                 n++;
419         }
420         if (float_difference(ex[n - 1], surf.x[0]) == 0.0f &&
421             float_difference(ey[n - 1], surf.y[0]) == 0.0f)
422                 n--;
423
424         if (n < 3)
425                 return 0;
426
427         return n;
428 }
429
430 static int
431 texture_region(struct weston_surface *es, pixman_region32_t *region,
432                 pixman_region32_t *surf_region)
433 {
434         struct weston_compositor *ec = es->compositor;
435         GLfloat *v, inv_width, inv_height;
436         unsigned int *vtxcnt, nvtx = 0;
437         pixman_box32_t *rects, *surf_rects;
438         int i, j, k, nrects, nsurf;
439
440         rects = pixman_region32_rectangles(region, &nrects);
441         surf_rects = pixman_region32_rectangles(surf_region, &nsurf);
442
443         /* worst case we can have 8 vertices per rect (ie. clipped into
444          * an octagon):
445          */
446         v = wl_array_add(&ec->vertices, nrects * nsurf * 8 * 4 * sizeof *v);
447         vtxcnt = wl_array_add(&ec->vtxcnt, nrects * nsurf * sizeof *vtxcnt);
448
449         inv_width = 1.0 / es->pitch;
450         inv_height = 1.0 / es->geometry.height;
451
452         for (i = 0; i < nrects; i++) {
453                 pixman_box32_t *rect = &rects[i];
454                 for (j = 0; j < nsurf; j++) {
455                         pixman_box32_t *surf_rect = &surf_rects[j];
456                         GLfloat sx, sy;
457                         GLfloat ex[8], ey[8];          /* edge points in screen space */
458                         int n;
459
460                         /* The transformed surface, after clipping to the clip region,
461                          * can have as many as eight sides, emitted as a triangle-fan.
462                          * The first vertex in the triangle fan can be chosen arbitrarily,
463                          * since the area is guaranteed to be convex.
464                          *
465                          * If a corner of the transformed surface falls outside of the
466                          * clip region, instead of emitting one vertex for the corner
467                          * of the surface, up to two are emitted for two corresponding
468                          * intersection point(s) between the surface and the clip region.
469                          *
470                          * To do this, we first calculate the (up to eight) points that
471                          * form the intersection of the clip rect and the transformed
472                          * surface.
473                          */
474                         n = calculate_edges(es, rect, surf_rect, ex, ey);
475                         if (n < 3)
476                                 continue;
477
478                         /* emit edge points: */
479                         for (k = 0; k < n; k++) {
480                                 weston_surface_from_global_float(es, ex[k], ey[k], &sx, &sy);
481                                 /* position: */
482                                 *(v++) = ex[k];
483                                 *(v++) = ey[k];
484                                 /* texcoord: */
485                                 *(v++) = sx * inv_width;
486                                 *(v++) = sy * inv_height;
487                         }
488
489                         vtxcnt[nvtx++] = n;
490                 }
491         }
492
493         return nvtx;
494 }
495
496 static void
497 triangle_fan_debug(struct weston_surface *surface, int first, int count)
498 {
499         struct weston_compositor *compositor = surface->compositor;
500         int i;
501         GLushort *buffer;
502         GLushort *index;
503         int nelems;
504         static int color_idx = 0;
505         static const GLfloat color[][4] = {
506                         { 1.0, 0.0, 0.0, 1.0 },
507                         { 0.0, 1.0, 0.0, 1.0 },
508                         { 0.0, 0.0, 1.0, 1.0 },
509                         { 1.0, 1.0, 1.0, 1.0 },
510         };
511
512         nelems = (count - 1 + count - 2) * 2;
513
514         buffer = malloc(sizeof(GLushort) * nelems);
515         index = buffer;
516
517         for (i = 1; i < count; i++) {
518                 *index++ = first;
519                 *index++ = first + i;
520         }
521
522         for (i = 2; i < count; i++) {
523                 *index++ = first + i - 1;
524                 *index++ = first + i;
525         }
526
527         glUseProgram(compositor->solid_shader.program);
528         glUniform4fv(compositor->solid_shader.color_uniform, 1,
529                         color[color_idx++ % ARRAY_LENGTH(color)]);
530         glDrawElements(GL_LINES, nelems, GL_UNSIGNED_SHORT, buffer);
531         glUseProgram(compositor->current_shader->program);
532         free(buffer);
533 }
534
535 static void
536 repaint_region(struct weston_surface *es, pixman_region32_t *region,
537                 pixman_region32_t *surf_region)
538 {
539         struct weston_compositor *ec = es->compositor;
540         GLfloat *v;
541         unsigned int *vtxcnt;
542         int i, first, nfans;
543
544         /* The final region to be painted is the intersection of
545          * 'region' and 'surf_region'. However, 'region' is in the global
546          * coordinates, and 'surf_region' is in the surface-local
547          * coordinates. texture_region() will iterate over all pairs of
548          * rectangles from both regions, compute the intersection
549          * polygon for each pair, and store it as a triangle fan if
550          * it has a non-zero area (at least 3 vertices, actually).
551          */
552         nfans = texture_region(es, region, surf_region);
553
554         v = ec->vertices.data;
555         vtxcnt = ec->vtxcnt.data;
556
557         /* position: */
558         glVertexAttribPointer(0, 2, GL_FLOAT, GL_FALSE, 4 * sizeof *v, &v[0]);
559         glEnableVertexAttribArray(0);
560
561         /* texcoord: */
562         glVertexAttribPointer(1, 2, GL_FLOAT, GL_FALSE, 4 * sizeof *v, &v[2]);
563         glEnableVertexAttribArray(1);
564
565         for (i = 0, first = 0; i < nfans; i++) {
566                 glDrawArrays(GL_TRIANGLE_FAN, first, vtxcnt[i]);
567                 if (ec->fan_debug)
568                         triangle_fan_debug(es, first, vtxcnt[i]);
569                 first += vtxcnt[i];
570         }
571
572         glDisableVertexAttribArray(1);
573         glDisableVertexAttribArray(0);
574
575         ec->vertices.size = 0;
576         ec->vtxcnt.size = 0;
577 }
578
579 static void
580 weston_compositor_use_shader(struct weston_compositor *compositor,
581                              struct weston_shader *shader)
582 {
583         if (compositor->current_shader == shader)
584                 return;
585
586         glUseProgram(shader->program);
587         compositor->current_shader = shader;
588 }
589
590 static void
591 weston_shader_uniforms(struct weston_shader *shader,
592                        struct weston_surface *surface,
593                        struct weston_output *output)
594 {
595         int i;
596
597         glUniformMatrix4fv(shader->proj_uniform,
598                            1, GL_FALSE, output->matrix.d);
599         glUniform4fv(shader->color_uniform, 1, surface->color);
600         glUniform1f(shader->alpha_uniform, surface->alpha);
601
602         for (i = 0; i < surface->num_textures; i++)
603                 glUniform1i(shader->tex_uniforms[i], i);
604 }
605
606 static void
607 draw_surface(struct weston_surface *es, struct weston_output *output,
608              pixman_region32_t *damage) /* in global coordinates */
609 {
610         struct weston_compositor *ec = es->compositor;
611         /* repaint bounding region in global coordinates: */
612         pixman_region32_t repaint;
613         /* non-opaque region in surface coordinates: */
614         pixman_region32_t surface_blend;
615         pixman_region32_t *buffer_damage;
616         GLint filter;
617         int i;
618
619         pixman_region32_init(&repaint);
620         pixman_region32_intersect(&repaint,
621                                   &es->transform.boundingbox, damage);
622         pixman_region32_subtract(&repaint, &repaint, &es->clip);
623
624         if (!pixman_region32_not_empty(&repaint))
625                 goto out;
626
627         buffer_damage = &output->buffer_damage[output->current_buffer];
628         pixman_region32_subtract(buffer_damage, buffer_damage, &repaint);
629
630         glBlendFunc(GL_ONE, GL_ONE_MINUS_SRC_ALPHA);
631
632         if (ec->fan_debug) {
633                 weston_compositor_use_shader(ec, &ec->solid_shader);
634                 weston_shader_uniforms(&ec->solid_shader, es, output);
635         }
636
637         weston_compositor_use_shader(ec, es->shader);
638         weston_shader_uniforms(es->shader, es, output);
639
640         if (es->transform.enabled || output->zoom.active)
641                 filter = GL_LINEAR;
642         else
643                 filter = GL_NEAREST;
644
645         for (i = 0; i < es->num_textures; i++) {
646                 glActiveTexture(GL_TEXTURE0 + i);
647                 glBindTexture(es->target, es->textures[i]);
648                 glTexParameteri(es->target, GL_TEXTURE_MIN_FILTER, filter);
649                 glTexParameteri(es->target, GL_TEXTURE_MAG_FILTER, filter);
650         }
651
652         /* blended region is whole surface minus opaque region: */
653         pixman_region32_init_rect(&surface_blend, 0, 0,
654                                   es->geometry.width, es->geometry.height);
655         pixman_region32_subtract(&surface_blend, &surface_blend, &es->opaque);
656
657         if (pixman_region32_not_empty(&es->opaque)) {
658                 if (es->shader == &ec->texture_shader_rgba) {
659                         /* Special case for RGBA textures with possibly
660                          * bad data in alpha channel: use the shader
661                          * that forces texture alpha = 1.0.
662                          * Xwayland surfaces need this.
663                          */
664                         weston_compositor_use_shader(ec, &ec->texture_shader_rgbx);
665                         weston_shader_uniforms(&ec->texture_shader_rgbx, es, output);
666                 }
667
668                 if (es->alpha < 1.0)
669                         glEnable(GL_BLEND);
670                 else
671                         glDisable(GL_BLEND);
672
673                 repaint_region(es, &repaint, &es->opaque);
674         }
675
676         if (pixman_region32_not_empty(&surface_blend)) {
677                 weston_compositor_use_shader(ec, es->shader);
678                 glEnable(GL_BLEND);
679                 repaint_region(es, &repaint, &surface_blend);
680         }
681
682         pixman_region32_fini(&surface_blend);
683
684 out:
685         pixman_region32_fini(&repaint);
686 }
687
688 static void
689 repaint_surfaces(struct weston_output *output, pixman_region32_t *damage)
690 {
691         struct weston_compositor *compositor = output->compositor;
692         struct weston_surface *surface;
693
694         wl_list_for_each_reverse(surface, &compositor->surface_list, link)
695                 if (surface->plane == &compositor->primary_plane)
696                         draw_surface(surface, output, damage);
697 }
698
699 static void
700 gles2_renderer_repaint_output(struct weston_output *output,
701                               pixman_region32_t *output_damage)
702 {
703         struct weston_compositor *compositor = output->compositor;
704         EGLBoolean ret;
705         static int errored;
706         int32_t width, height, i;
707
708         width = output->current->width +
709                 output->border.left + output->border.right;
710         height = output->current->height +
711                 output->border.top + output->border.bottom;
712
713         glViewport(0, 0, width, height);
714
715         ret = eglMakeCurrent(compositor->egl_display, output->egl_surface,
716                              output->egl_surface, compositor->egl_context);
717         if (ret == EGL_FALSE) {
718                 if (errored)
719                         return;
720                 errored = 1;
721                 weston_log("Failed to make EGL context current.\n");
722                 print_egl_error_state();
723                 return;
724         }
725
726         /* if debugging, redraw everything outside the damage to clean up
727          * debug lines from the previous draw on this buffer:
728          */
729         if (compositor->fan_debug) {
730                 pixman_region32_t undamaged;
731                 pixman_region32_init(&undamaged);
732                 pixman_region32_subtract(&undamaged, &output->region,
733                                          output_damage);
734                 compositor->fan_debug = 0;
735                 repaint_surfaces(output, &undamaged);
736                 compositor->fan_debug = 1;
737                 pixman_region32_fini(&undamaged);
738         }
739
740         for (i = 0; i < 2; i++)
741                 pixman_region32_union(&output->buffer_damage[i],
742                                       &output->buffer_damage[i],
743                                       output_damage);
744
745         pixman_region32_union(output_damage, output_damage,
746                               &output->buffer_damage[output->current_buffer]);
747
748         repaint_surfaces(output, output_damage);
749
750         wl_signal_emit(&output->frame_signal, output);
751
752         ret = eglSwapBuffers(compositor->egl_display, output->egl_surface);
753         if (ret == EGL_FALSE && !errored) {
754                 errored = 1;
755                 weston_log("Failed in eglSwapBuffers.\n");
756                 print_egl_error_state();
757         }
758
759         output->current_buffer ^= 1;
760
761 }
762
763 static void
764 gles2_renderer_flush_damage(struct weston_surface *surface)
765 {
766 #ifdef GL_UNPACK_ROW_LENGTH
767         pixman_box32_t *rectangles;
768         void *data;
769         int i, n;
770 #endif
771
772         glBindTexture(GL_TEXTURE_2D, surface->textures[0]);
773
774         if (!surface->compositor->has_unpack_subimage) {
775                 glTexImage2D(GL_TEXTURE_2D, 0, GL_BGRA_EXT,
776                              surface->pitch, surface->buffer->height, 0,
777                              GL_BGRA_EXT, GL_UNSIGNED_BYTE,
778                              wl_shm_buffer_get_data(surface->buffer));
779
780                 return;
781         }
782
783 #ifdef GL_UNPACK_ROW_LENGTH
784         /* Mesa does not define GL_EXT_unpack_subimage */
785         glPixelStorei(GL_UNPACK_ROW_LENGTH, surface->pitch);
786         data = wl_shm_buffer_get_data(surface->buffer);
787         rectangles = pixman_region32_rectangles(&surface->damage, &n);
788         for (i = 0; i < n; i++) {
789                 glPixelStorei(GL_UNPACK_SKIP_PIXELS, rectangles[i].x1);
790                 glPixelStorei(GL_UNPACK_SKIP_ROWS, rectangles[i].y1);
791                 glTexSubImage2D(GL_TEXTURE_2D, 0,
792                                 rectangles[i].x1, rectangles[i].y1,
793                                 rectangles[i].x2 - rectangles[i].x1,
794                                 rectangles[i].y2 - rectangles[i].y1,
795                                 GL_BGRA_EXT, GL_UNSIGNED_BYTE, data);
796         }
797 #endif
798 }
799
800 static void
801 ensure_textures(struct weston_surface *es, int num_textures)
802 {
803         int i;
804
805         if (num_textures <= es->num_textures)
806                 return;
807
808         for (i = es->num_textures; i < num_textures; i++) {
809                 glGenTextures(1, &es->textures[i]);
810                 glBindTexture(es->target, es->textures[i]);
811                 glTexParameteri(es->target,
812                                 GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
813                 glTexParameteri(es->target,
814                                 GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
815         }
816         es->num_textures = num_textures;
817         glBindTexture(es->target, 0);
818 }
819
820 static void
821 gles2_renderer_attach(struct weston_surface *es, struct wl_buffer *buffer)
822 {
823         struct weston_compositor *ec = es->compositor;
824         EGLint attribs[3], format;
825         int i, num_planes;
826
827         if (!buffer) {
828                 for (i = 0; i < es->num_images; i++) {
829                         ec->destroy_image(ec->egl_display, es->images[i]);
830                         es->images[i] = NULL;
831                 }
832                 es->num_images = 0;
833                 glDeleteTextures(es->num_textures, es->textures);
834                 es->num_textures = 0;
835                 return;
836         }
837
838         if (wl_buffer_is_shm(buffer)) {
839                 es->pitch = wl_shm_buffer_get_stride(buffer) / 4;
840                 es->target = GL_TEXTURE_2D;
841
842                 ensure_textures(es, 1);
843                 glBindTexture(GL_TEXTURE_2D, es->textures[0]);
844                 glTexImage2D(GL_TEXTURE_2D, 0, GL_BGRA_EXT,
845                              es->pitch, buffer->height, 0,
846                              GL_BGRA_EXT, GL_UNSIGNED_BYTE, NULL);
847                 if (wl_shm_buffer_get_format(buffer) == WL_SHM_FORMAT_XRGB8888)
848                         es->shader = &ec->texture_shader_rgbx;
849                 else
850                         es->shader = &ec->texture_shader_rgba;
851         } else if (ec->query_buffer(ec->egl_display, buffer,
852                                     EGL_TEXTURE_FORMAT, &format)) {
853                 for (i = 0; i < es->num_images; i++)
854                         ec->destroy_image(ec->egl_display, es->images[i]);
855                 es->num_images = 0;
856                 es->target = GL_TEXTURE_2D;
857                 switch (format) {
858                 case EGL_TEXTURE_RGB:
859                 case EGL_TEXTURE_RGBA:
860                 default:
861                         num_planes = 1;
862                         es->shader = &ec->texture_shader_rgba;
863                         break;
864                 case EGL_TEXTURE_EXTERNAL_WL:
865                         num_planes = 1;
866                         es->target = GL_TEXTURE_EXTERNAL_OES;
867                         es->shader = &ec->texture_shader_egl_external;
868                         break;
869                 case EGL_TEXTURE_Y_UV_WL:
870                         num_planes = 2;
871                         es->shader = &ec->texture_shader_y_uv;
872                         break;
873                 case EGL_TEXTURE_Y_U_V_WL:
874                         num_planes = 3;
875                         es->shader = &ec->texture_shader_y_u_v;
876                         break;
877                 case EGL_TEXTURE_Y_XUXV_WL:
878                         num_planes = 2;
879                         es->shader = &ec->texture_shader_y_xuxv;
880                         break;
881                 }
882
883                 ensure_textures(es, num_planes);
884                 for (i = 0; i < num_planes; i++) {
885                         attribs[0] = EGL_WAYLAND_PLANE_WL;
886                         attribs[1] = i;
887                         attribs[2] = EGL_NONE;
888                         es->images[i] = ec->create_image(ec->egl_display,
889                                                          NULL,
890                                                          EGL_WAYLAND_BUFFER_WL,
891                                                          buffer, attribs);
892                         if (!es->images[i]) {
893                                 weston_log("failed to create img for plane %d\n", i);
894                                 continue;
895                         }
896                         es->num_images++;
897
898                         glActiveTexture(GL_TEXTURE0 + i);
899                         glBindTexture(es->target, es->textures[i]);
900                         ec->image_target_texture_2d(es->target,
901                                                     es->images[i]);
902                 }
903
904                 es->pitch = buffer->width;
905         } else {
906                 weston_log("unhandled buffer type!\n");
907         }
908 }
909
910 static void
911 gles2_renderer_destroy_surface(struct weston_surface *surface)
912 {
913         struct weston_compositor *ec = surface->compositor;
914         int i;
915
916         glDeleteTextures(surface->num_textures, surface->textures);
917
918         for (i = 0; i < surface->num_images; i++)
919                 ec->destroy_image(ec->egl_display, surface->images[i]);
920 }
921
922 static const char vertex_shader[] =
923         "uniform mat4 proj;\n"
924         "attribute vec2 position;\n"
925         "attribute vec2 texcoord;\n"
926         "varying vec2 v_texcoord;\n"
927         "void main()\n"
928         "{\n"
929         "   gl_Position = proj * vec4(position, 0.0, 1.0);\n"
930         "   v_texcoord = texcoord;\n"
931         "}\n";
932
933 /* Declare common fragment shader uniforms */
934 #define FRAGMENT_CONVERT_YUV                                            \
935         "  y *= alpha;\n"                                               \
936         "  u *= alpha;\n"                                               \
937         "  v *= alpha;\n"                                               \
938         "  gl_FragColor.r = y + 1.59602678 * v;\n"                      \
939         "  gl_FragColor.g = y - 0.39176229 * u - 0.81296764 * v;\n"     \
940         "  gl_FragColor.b = y + 2.01723214 * u;\n"                      \
941         "  gl_FragColor.a = alpha;\n"
942
943 static const char texture_fragment_shader_rgba[] =
944         "precision mediump float;\n"
945         "varying vec2 v_texcoord;\n"
946         "uniform sampler2D tex;\n"
947         "uniform float alpha;\n"
948         "void main()\n"
949         "{\n"
950         "   gl_FragColor = alpha * texture2D(tex, v_texcoord)\n;"
951         "}\n";
952
953 static const char texture_fragment_shader_rgbx[] =
954         "precision mediump float;\n"
955         "varying vec2 v_texcoord;\n"
956         "uniform sampler2D tex;\n"
957         "uniform float alpha;\n"
958         "void main()\n"
959         "{\n"
960         "   gl_FragColor.rgb = alpha * texture2D(tex, v_texcoord).rgb\n;"
961         "   gl_FragColor.a = alpha;\n"
962         "}\n";
963
964 static const char texture_fragment_shader_egl_external[] =
965         "#extension GL_OES_EGL_image_external : require\n"
966         "precision mediump float;\n"
967         "varying vec2 v_texcoord;\n"
968         "uniform samplerExternalOES tex;\n"
969         "uniform float alpha;\n"
970         "void main()\n"
971         "{\n"
972         "   gl_FragColor = alpha * texture2D(tex, v_texcoord)\n;"
973         "}\n";
974
975 static const char texture_fragment_shader_y_uv[] =
976         "precision mediump float;\n"
977         "uniform sampler2D tex;\n"
978         "uniform sampler2D tex1;\n"
979         "varying vec2 v_texcoord;\n"
980         "uniform float alpha;\n"
981         "void main() {\n"
982         "  float y = 1.16438356 * (texture2D(tex, v_texcoord).x - 0.0625);\n"
983         "  float u = texture2D(tex1, v_texcoord).r - 0.5;\n"
984         "  float v = texture2D(tex1, v_texcoord).g - 0.5;\n"
985         FRAGMENT_CONVERT_YUV
986         "}\n";
987
988 static const char texture_fragment_shader_y_u_v[] =
989         "precision mediump float;\n"
990         "uniform sampler2D tex;\n"
991         "uniform sampler2D tex1;\n"
992         "uniform sampler2D tex2;\n"
993         "varying vec2 v_texcoord;\n"
994         "uniform float alpha;\n"
995         "void main() {\n"
996         "  float y = 1.16438356 * (texture2D(tex, v_texcoord).x - 0.0625);\n"
997         "  float u = texture2D(tex1, v_texcoord).x - 0.5;\n"
998         "  float v = texture2D(tex2, v_texcoord).x - 0.5;\n"
999         FRAGMENT_CONVERT_YUV
1000         "}\n";
1001
1002 static const char texture_fragment_shader_y_xuxv[] =
1003         "precision mediump float;\n"
1004         "uniform sampler2D tex;\n"
1005         "uniform sampler2D tex1;\n"
1006         "varying vec2 v_texcoord;\n"
1007         "uniform float alpha;\n"
1008         "void main() {\n"
1009         "  float y = 1.16438356 * (texture2D(tex, v_texcoord).x - 0.0625);\n"
1010         "  float u = texture2D(tex1, v_texcoord).g - 0.5;\n"
1011         "  float v = texture2D(tex1, v_texcoord).a - 0.5;\n"
1012         FRAGMENT_CONVERT_YUV
1013         "}\n";
1014
1015 static const char solid_fragment_shader[] =
1016         "precision mediump float;\n"
1017         "uniform vec4 color;\n"
1018         "uniform float alpha;\n"
1019         "void main()\n"
1020         "{\n"
1021         "   gl_FragColor = alpha * color\n;"
1022         "}\n";
1023
1024 static int
1025 compile_shader(GLenum type, const char *source)
1026 {
1027         GLuint s;
1028         char msg[512];
1029         GLint status;
1030
1031         s = glCreateShader(type);
1032         glShaderSource(s, 1, &source, NULL);
1033         glCompileShader(s);
1034         glGetShaderiv(s, GL_COMPILE_STATUS, &status);
1035         if (!status) {
1036                 glGetShaderInfoLog(s, sizeof msg, NULL, msg);
1037                 weston_log("shader info: %s\n", msg);
1038                 return GL_NONE;
1039         }
1040
1041         return s;
1042 }
1043
1044 static int
1045 weston_shader_init(struct weston_shader *shader,
1046                    const char *vertex_source, const char *fragment_source)
1047 {
1048         char msg[512];
1049         GLint status;
1050
1051         shader->vertex_shader =
1052                 compile_shader(GL_VERTEX_SHADER, vertex_source);
1053         shader->fragment_shader =
1054                 compile_shader(GL_FRAGMENT_SHADER, fragment_source);
1055
1056         shader->program = glCreateProgram();
1057         glAttachShader(shader->program, shader->vertex_shader);
1058         glAttachShader(shader->program, shader->fragment_shader);
1059         glBindAttribLocation(shader->program, 0, "position");
1060         glBindAttribLocation(shader->program, 1, "texcoord");
1061
1062         glLinkProgram(shader->program);
1063         glGetProgramiv(shader->program, GL_LINK_STATUS, &status);
1064         if (!status) {
1065                 glGetProgramInfoLog(shader->program, sizeof msg, NULL, msg);
1066                 weston_log("link info: %s\n", msg);
1067                 return -1;
1068         }
1069
1070         shader->proj_uniform = glGetUniformLocation(shader->program, "proj");
1071         shader->tex_uniforms[0] = glGetUniformLocation(shader->program, "tex");
1072         shader->tex_uniforms[1] = glGetUniformLocation(shader->program, "tex1");
1073         shader->tex_uniforms[2] = glGetUniformLocation(shader->program, "tex2");
1074         shader->alpha_uniform = glGetUniformLocation(shader->program, "alpha");
1075         shader->color_uniform = glGetUniformLocation(shader->program, "color");
1076
1077         return 0;
1078 }
1079
1080 static void
1081 log_extensions(const char *name, const char *extensions)
1082 {
1083         const char *p, *end;
1084         int l;
1085         int len;
1086
1087         l = weston_log("%s:", name);
1088         p = extensions;
1089         while (*p) {
1090                 end = strchrnul(p, ' ');
1091                 len = end - p;
1092                 if (l + len > 78)
1093                         l = weston_log_continue("\n" STAMP_SPACE "%.*s",
1094                                                 len, p);
1095                 else
1096                         l += weston_log_continue(" %.*s", len, p);
1097                 for (p = end; isspace(*p); p++)
1098                         ;
1099         }
1100         weston_log_continue("\n");
1101 }
1102
1103 static void
1104 log_egl_gl_info(EGLDisplay egldpy)
1105 {
1106         const char *str;
1107
1108         str = eglQueryString(egldpy, EGL_VERSION);
1109         weston_log("EGL version: %s\n", str ? str : "(null)");
1110
1111         str = eglQueryString(egldpy, EGL_VENDOR);
1112         weston_log("EGL vendor: %s\n", str ? str : "(null)");
1113
1114         str = eglQueryString(egldpy, EGL_CLIENT_APIS);
1115         weston_log("EGL client APIs: %s\n", str ? str : "(null)");
1116
1117         str = eglQueryString(egldpy, EGL_EXTENSIONS);
1118         log_extensions("EGL extensions", str ? str : "(null)");
1119
1120         str = (char *)glGetString(GL_VERSION);
1121         weston_log("GL version: %s\n", str ? str : "(null)");
1122
1123         str = (char *)glGetString(GL_SHADING_LANGUAGE_VERSION);
1124         weston_log("GLSL version: %s\n", str ? str : "(null)");
1125
1126         str = (char *)glGetString(GL_VENDOR);
1127         weston_log("GL vendor: %s\n", str ? str : "(null)");
1128
1129         str = (char *)glGetString(GL_RENDERER);
1130         weston_log("GL renderer: %s\n", str ? str : "(null)");
1131
1132         str = (char *)glGetString(GL_EXTENSIONS);
1133         log_extensions("GL extensions", str ? str : "(null)");
1134 }
1135
1136 struct gles2_renderer {
1137         struct weston_renderer base;
1138 };
1139
1140 WL_EXPORT void
1141 gles2_renderer_destroy(struct weston_compositor *ec)
1142 {
1143         if (ec->has_bind_display)
1144                 ec->unbind_display(ec->egl_display, ec->wl_display);
1145 }
1146
1147 WL_EXPORT int
1148 gles2_renderer_init(struct weston_compositor *ec)
1149 {
1150         struct gles2_renderer *renderer;
1151         const char *extensions;
1152         int has_egl_image_external = 0;
1153         struct weston_output *output;
1154         EGLBoolean ret;
1155
1156         static const EGLint context_attribs[] = {
1157                 EGL_CONTEXT_CLIENT_VERSION, 2,
1158                 EGL_NONE
1159         };
1160
1161         renderer = malloc(sizeof *renderer);
1162         if (renderer == NULL)
1163                 return -1;
1164
1165         if (!eglBindAPI(EGL_OPENGL_ES_API)) {
1166                 weston_log("failed to bind EGL_OPENGL_ES_API\n");
1167                 print_egl_error_state();
1168                 return -1;
1169         }
1170         ec->egl_context = eglCreateContext(ec->egl_display, ec->egl_config,
1171                                            EGL_NO_CONTEXT, context_attribs);
1172         if (ec->egl_context == NULL) {
1173                 weston_log("failed to create context\n");
1174                 print_egl_error_state();
1175                 return -1;
1176         }
1177
1178         output = container_of(ec->output_list.next,
1179                               struct weston_output, link);
1180         ret = eglMakeCurrent(ec->egl_display, output->egl_surface,
1181                              output->egl_surface, ec->egl_context);
1182         if (ret == EGL_FALSE) {
1183                 weston_log("Failed to make EGL context current.\n");
1184                 print_egl_error_state();
1185                 return -1;
1186         }
1187
1188         log_egl_gl_info(ec->egl_display);
1189
1190         ec->image_target_texture_2d =
1191                 (void *) eglGetProcAddress("glEGLImageTargetTexture2DOES");
1192         ec->image_target_renderbuffer_storage = (void *)
1193                 eglGetProcAddress("glEGLImageTargetRenderbufferStorageOES");
1194         ec->create_image = (void *) eglGetProcAddress("eglCreateImageKHR");
1195         ec->destroy_image = (void *) eglGetProcAddress("eglDestroyImageKHR");
1196         ec->bind_display =
1197                 (void *) eglGetProcAddress("eglBindWaylandDisplayWL");
1198         ec->unbind_display =
1199                 (void *) eglGetProcAddress("eglUnbindWaylandDisplayWL");
1200         ec->query_buffer =
1201                 (void *) eglGetProcAddress("eglQueryWaylandBufferWL");
1202
1203         extensions = (const char *) glGetString(GL_EXTENSIONS);
1204         if (!extensions) {
1205                 weston_log("Retrieving GL extension string failed.\n");
1206                 return -1;
1207         }
1208
1209         if (!strstr(extensions, "GL_EXT_texture_format_BGRA8888")) {
1210                 weston_log("GL_EXT_texture_format_BGRA8888 not available\n");
1211                 return -1;
1212         }
1213
1214         if (strstr(extensions, "GL_EXT_read_format_bgra"))
1215                 ec->read_format = GL_BGRA_EXT;
1216         else
1217                 ec->read_format = GL_RGBA;
1218
1219         if (strstr(extensions, "GL_EXT_unpack_subimage"))
1220                 ec->has_unpack_subimage = 1;
1221
1222         if (strstr(extensions, "GL_OES_EGL_image_external"))
1223                 has_egl_image_external = 1;
1224
1225         extensions =
1226                 (const char *) eglQueryString(ec->egl_display, EGL_EXTENSIONS);
1227         if (!extensions) {
1228                 weston_log("Retrieving EGL extension string failed.\n");
1229                 return -1;
1230         }
1231
1232         if (strstr(extensions, "EGL_WL_bind_wayland_display"))
1233                 ec->has_bind_display = 1;
1234         if (ec->has_bind_display)
1235                 ec->bind_display(ec->egl_display, ec->wl_display);
1236
1237         glActiveTexture(GL_TEXTURE0);
1238
1239         if (weston_shader_init(&ec->texture_shader_rgba,
1240                              vertex_shader, texture_fragment_shader_rgba) < 0)
1241                 return -1;
1242         if (weston_shader_init(&ec->texture_shader_rgbx,
1243                              vertex_shader, texture_fragment_shader_rgbx) < 0)
1244                 return -1;
1245         if (has_egl_image_external &&
1246                         weston_shader_init(&ec->texture_shader_egl_external,
1247                                 vertex_shader, texture_fragment_shader_egl_external) < 0)
1248                 return -1;
1249         if (weston_shader_init(&ec->texture_shader_y_uv,
1250                                vertex_shader, texture_fragment_shader_y_uv) < 0)
1251                 return -1;
1252         if (weston_shader_init(&ec->texture_shader_y_u_v,
1253                                vertex_shader, texture_fragment_shader_y_u_v) < 0)
1254                 return -1;
1255         if (weston_shader_init(&ec->texture_shader_y_xuxv,
1256                                vertex_shader, texture_fragment_shader_y_xuxv) < 0)
1257                 return -1;
1258         if (weston_shader_init(&ec->solid_shader,
1259                              vertex_shader, solid_fragment_shader) < 0)
1260                 return -1;
1261
1262         renderer->base.repaint_output = gles2_renderer_repaint_output;
1263         renderer->base.flush_damage = gles2_renderer_flush_damage;
1264         renderer->base.attach = gles2_renderer_attach;
1265         renderer->base.destroy_surface = gles2_renderer_destroy_surface;
1266         ec->renderer = &renderer->base;
1267
1268         return 0;
1269 }