xserver

xserver with xephyr scale patch
git clone https://git.neptards.moe/u3shit/xserver.git
Log | Files | Refs | README | LICENSE

glamor.c (38377B)


      1 /*
      2  * Copyright © 2008,2011 Intel Corporation
      3  *
      4  * Permission is hereby granted, free of charge, to any person obtaining a
      5  * copy of this software and associated documentation files (the "Software"),
      6  * to deal in the Software without restriction, including without limitation
      7  * the rights to use, copy, modify, merge, publish, distribute, sublicense,
      8  * and/or sell copies of the Software, and to permit persons to whom the
      9  * Software is furnished to do so, subject to the following conditions:
     10  *
     11  * The above copyright notice and this permission notice (including the next
     12  * paragraph) shall be included in all copies or substantial portions of the
     13  * Software.
     14  *
     15  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
     16  * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
     17  * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
     18  * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
     19  * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
     20  * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
     21  * IN THE SOFTWARE.
     22  *
     23  * Authors:
     24  *    Eric Anholt <eric@anholt.net>
     25  *    Zhigang Gong <zhigang.gong@linux.intel.com>
     26  *    Chad Versace <chad.versace@linux.intel.com>
     27  */
     28 
     29 /** @file glamor.c
     30  * This file covers the initialization and teardown of glamor, and has various
     31  * functions not responsible for performing rendering.
     32  */
     33 
     34 #include <stdlib.h>
     35 #include <unistd.h>
     36 
     37 #include "glamor_priv.h"
     38 #include "mipict.h"
     39 
     40 DevPrivateKeyRec glamor_screen_private_key;
     41 DevPrivateKeyRec glamor_pixmap_private_key;
     42 DevPrivateKeyRec glamor_gc_private_key;
     43 
     44 glamor_screen_private *
     45 glamor_get_screen_private(ScreenPtr screen)
     46 {
     47     return (glamor_screen_private *)
     48         dixLookupPrivate(&screen->devPrivates, &glamor_screen_private_key);
     49 }
     50 
     51 void
     52 glamor_set_screen_private(ScreenPtr screen, glamor_screen_private *priv)
     53 {
     54     dixSetPrivate(&screen->devPrivates, &glamor_screen_private_key, priv);
     55 }
     56 
     57 /**
     58  * glamor_get_drawable_pixmap() returns a backing pixmap for a given drawable.
     59  *
     60  * @param drawable the drawable being requested.
     61  *
     62  * This function returns the backing pixmap for a drawable, whether it is a
     63  * redirected window, unredirected window, or already a pixmap.  Note that
     64  * coordinate translation is needed when drawing to the backing pixmap of a
     65  * redirected window, and the translation coordinates are provided by calling
     66  * exaGetOffscreenPixmap() on the drawable.
     67  */
     68 PixmapPtr
     69 glamor_get_drawable_pixmap(DrawablePtr drawable)
     70 {
     71     if (drawable->type == DRAWABLE_WINDOW)
     72         return drawable->pScreen->GetWindowPixmap((WindowPtr) drawable);
     73     else
     74         return (PixmapPtr) drawable;
     75 }
     76 
     77 static void
     78 glamor_init_pixmap_private_small(PixmapPtr pixmap, glamor_pixmap_private *pixmap_priv)
     79 {
     80     pixmap_priv->box.x1 = 0;
     81     pixmap_priv->box.x2 = pixmap->drawable.width;
     82     pixmap_priv->box.y1 = 0;
     83     pixmap_priv->box.y2 = pixmap->drawable.height;
     84     pixmap_priv->block_w = pixmap->drawable.width;
     85     pixmap_priv->block_h = pixmap->drawable.height;
     86     pixmap_priv->block_hcnt = 1;
     87     pixmap_priv->block_wcnt = 1;
     88     pixmap_priv->box_array = &pixmap_priv->box;
     89     pixmap_priv->fbo_array = &pixmap_priv->fbo;
     90 }
     91 
     92 _X_EXPORT void
     93 glamor_set_pixmap_type(PixmapPtr pixmap, glamor_pixmap_type_t type)
     94 {
     95     glamor_pixmap_private *pixmap_priv;
     96 
     97     pixmap_priv = glamor_get_pixmap_private(pixmap);
     98     pixmap_priv->type = type;
     99     glamor_init_pixmap_private_small(pixmap, pixmap_priv);
    100 }
    101 
    102 _X_EXPORT Bool
    103 glamor_set_pixmap_texture(PixmapPtr pixmap, unsigned int tex)
    104 {
    105     ScreenPtr screen = pixmap->drawable.pScreen;
    106     glamor_pixmap_private *pixmap_priv;
    107     glamor_screen_private *glamor_priv;
    108     glamor_pixmap_fbo *fbo;
    109 
    110     glamor_priv = glamor_get_screen_private(screen);
    111     pixmap_priv = glamor_get_pixmap_private(pixmap);
    112 
    113     if (pixmap_priv->fbo) {
    114         fbo = glamor_pixmap_detach_fbo(pixmap_priv);
    115         glamor_destroy_fbo(glamor_priv, fbo);
    116     }
    117 
    118     fbo = glamor_create_fbo_from_tex(glamor_priv, pixmap,
    119                                      pixmap->drawable.width,
    120                                      pixmap->drawable.height, tex, 0);
    121 
    122     if (fbo == NULL) {
    123         ErrorF("XXX fail to create fbo.\n");
    124         return FALSE;
    125     }
    126 
    127     glamor_pixmap_attach_fbo(pixmap, fbo);
    128 
    129     return TRUE;
    130 }
    131 
    132 _X_EXPORT void
    133 glamor_clear_pixmap(PixmapPtr pixmap)
    134 {
    135     ScreenPtr screen = pixmap->drawable.pScreen;
    136     glamor_screen_private *glamor_priv;
    137     glamor_pixmap_private *pixmap_priv;
    138     const struct glamor_format *pixmap_format;
    139 
    140     glamor_priv = glamor_get_screen_private(screen);
    141     pixmap_priv = glamor_get_pixmap_private(pixmap);
    142     pixmap_format = glamor_format_for_pixmap(pixmap);
    143 
    144     assert(pixmap_priv->fbo != NULL);
    145 
    146     glamor_pixmap_clear_fbo(glamor_priv, pixmap_priv->fbo, pixmap_format);
    147 }
    148 
    149 uint32_t
    150 glamor_get_pixmap_texture(PixmapPtr pixmap)
    151 {
    152     glamor_pixmap_private *pixmap_priv = glamor_get_pixmap_private(pixmap);
    153 
    154     if (!pixmap_priv)
    155         return 0;
    156 
    157     if (!pixmap_priv->fbo)
    158         return 0;
    159 
    160     if (pixmap_priv->type != GLAMOR_TEXTURE_ONLY)
    161         return 0;
    162 
    163     return pixmap_priv->fbo->tex;
    164 }
    165 
    166 void
    167 glamor_bind_texture(glamor_screen_private *glamor_priv, GLenum texture,
    168                     glamor_pixmap_fbo *fbo, Bool destination_red)
    169 {
    170     glActiveTexture(texture);
    171     glBindTexture(GL_TEXTURE_2D, fbo->tex);
    172 
    173     /* If we're pulling data from a GL_RED texture, then whether we
    174      * want to make it an A,0,0,0 result or a 0,0,0,R result depends
    175      * on whether the destination is also a GL_RED texture.
    176      *
    177      * For GL_RED destinations, we need to leave the bits in the R
    178      * channel. For all other destinations, we need to clear out the R
    179      * channel so that it returns zero for R, G and B.
    180      *
    181      * Note that we're leaving the SWIZZLE_A value alone; for GL_RED
    182      * destinations, that means we'll actually be returning R,0,0,R,
    183      * but it doesn't matter as the bits in the alpha channel aren't
    184      * going anywhere.
    185      */
    186 
    187     /* Is the operand a GL_RED fbo?
    188      */
    189 
    190     if (fbo->is_red) {
    191         /* If destination is also GL_RED, then preserve the bits in
    192          * the R channel */
    193 
    194         if (destination_red)
    195             glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_SWIZZLE_R, GL_RED);
    196         else
    197             glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_SWIZZLE_R, GL_ZERO);
    198     }
    199 }
    200 
    201 PixmapPtr
    202 glamor_create_pixmap(ScreenPtr screen, int w, int h, int depth,
    203                      unsigned int usage)
    204 {
    205     PixmapPtr pixmap;
    206     glamor_pixmap_private *pixmap_priv;
    207     glamor_screen_private *glamor_priv = glamor_get_screen_private(screen);
    208     glamor_pixmap_fbo *fbo = NULL;
    209     int pitch;
    210 
    211     if (w > 32767 || h > 32767)
    212         return NullPixmap;
    213 
    214     if ((usage == GLAMOR_CREATE_PIXMAP_CPU
    215          || (usage == CREATE_PIXMAP_USAGE_GLYPH_PICTURE &&
    216              w <= glamor_priv->glyph_max_dim &&
    217              h <= glamor_priv->glyph_max_dim)
    218          || (w == 0 && h == 0)
    219          || !glamor_priv->formats[depth].rendering_supported))
    220         return fbCreatePixmap(screen, w, h, depth, usage);
    221     else
    222         pixmap = fbCreatePixmap(screen, 0, 0, depth, usage);
    223 
    224     pixmap_priv = glamor_get_pixmap_private(pixmap);
    225 
    226     pixmap_priv->is_cbcr = (usage == GLAMOR_CREATE_FORMAT_CBCR);
    227 
    228     pitch = (((w * pixmap->drawable.bitsPerPixel + 7) / 8) + 3) & ~3;
    229     screen->ModifyPixmapHeader(pixmap, w, h, 0, 0, pitch, NULL);
    230 
    231     pixmap_priv->type = GLAMOR_TEXTURE_ONLY;
    232 
    233     if (usage == GLAMOR_CREATE_PIXMAP_NO_TEXTURE) {
    234         glamor_init_pixmap_private_small(pixmap, pixmap_priv);
    235         return pixmap;
    236     }
    237     else if (usage == GLAMOR_CREATE_NO_LARGE ||
    238         glamor_check_fbo_size(glamor_priv, w, h))
    239     {
    240         glamor_init_pixmap_private_small(pixmap, pixmap_priv);
    241         fbo = glamor_create_fbo(glamor_priv, pixmap, w, h, usage);
    242     } else {
    243         int tile_size = glamor_priv->max_fbo_size;
    244         DEBUGF("Create LARGE pixmap %p width %d height %d, tile size %d\n",
    245                pixmap, w, h, tile_size);
    246         fbo = glamor_create_fbo_array(glamor_priv, pixmap, usage,
    247                                       tile_size, tile_size, pixmap_priv);
    248     }
    249 
    250     if (fbo == NULL) {
    251         fbDestroyPixmap(pixmap);
    252         return fbCreatePixmap(screen, w, h, depth, usage);
    253     }
    254 
    255     glamor_pixmap_attach_fbo(pixmap, fbo);
    256 
    257     return pixmap;
    258 }
    259 
    260 Bool
    261 glamor_destroy_pixmap(PixmapPtr pixmap)
    262 {
    263     if (pixmap->refcnt == 1) {
    264         glamor_pixmap_destroy_fbo(pixmap);
    265     }
    266 
    267     return fbDestroyPixmap(pixmap);
    268 }
    269 
    270 void
    271 glamor_block_handler(ScreenPtr screen)
    272 {
    273     glamor_screen_private *glamor_priv = glamor_get_screen_private(screen);
    274 
    275     glamor_make_current(glamor_priv);
    276     glFlush();
    277 }
    278 
    279 static void
    280 _glamor_block_handler(ScreenPtr screen, void *timeout)
    281 {
    282     glamor_screen_private *glamor_priv = glamor_get_screen_private(screen);
    283 
    284     glamor_make_current(glamor_priv);
    285     glFlush();
    286 
    287     screen->BlockHandler = glamor_priv->saved_procs.block_handler;
    288     screen->BlockHandler(screen, timeout);
    289     glamor_priv->saved_procs.block_handler = screen->BlockHandler;
    290     screen->BlockHandler = _glamor_block_handler;
    291 }
    292 
    293 static void
    294 glamor_set_debug_level(int *debug_level)
    295 {
    296     char *debug_level_string;
    297 
    298     debug_level_string = getenv("GLAMOR_DEBUG");
    299     if (debug_level_string
    300         && sscanf(debug_level_string, "%d", debug_level) == 1)
    301         return;
    302     *debug_level = 0;
    303 }
    304 
    305 int glamor_debug_level;
    306 
    307 void
    308 glamor_gldrawarrays_quads_using_indices(glamor_screen_private *glamor_priv,
    309                                         unsigned count)
    310 {
    311     unsigned i;
    312 
    313     /* For a single quad, don't bother with an index buffer. */
    314     if (count ==  1)
    315         goto fallback;
    316 
    317     if (glamor_priv->ib_size < count) {
    318         /* Basic GLES2 doesn't have any way to map buffer objects for
    319          * writing, but it's long past time for drivers to have
    320          * MapBufferRange.
    321          */
    322         if (!glamor_priv->has_map_buffer_range)
    323             goto fallback;
    324 
    325         /* Lazy create the buffer name, and only bind it once since
    326          * none of the glamor code binds it to anything else.
    327          */
    328         if (!glamor_priv->ib) {
    329             glGenBuffers(1, &glamor_priv->ib);
    330             glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, glamor_priv->ib);
    331         }
    332 
    333         /* For now, only support GL_UNSIGNED_SHORTs. */
    334         if (count > ((1 << 16) - 1) / 4) {
    335             goto fallback;
    336         } else {
    337             uint16_t *data;
    338             size_t size = count * 6 * sizeof(GLushort);
    339 
    340             glBufferData(GL_ELEMENT_ARRAY_BUFFER, size, NULL, GL_STATIC_DRAW);
    341             data = glMapBufferRange(GL_ELEMENT_ARRAY_BUFFER,
    342                                     0, size,
    343                                     GL_MAP_WRITE_BIT |
    344                                     GL_MAP_INVALIDATE_BUFFER_BIT);
    345             for (i = 0; i < count; i++) {
    346                 data[i * 6 + 0] = i * 4 + 0;
    347                 data[i * 6 + 1] = i * 4 + 1;
    348                 data[i * 6 + 2] = i * 4 + 2;
    349                 data[i * 6 + 3] = i * 4 + 0;
    350                 data[i * 6 + 4] = i * 4 + 2;
    351                 data[i * 6 + 5] = i * 4 + 3;
    352             }
    353             glUnmapBuffer(GL_ELEMENT_ARRAY_BUFFER);
    354 
    355             glamor_priv->ib_size = count;
    356             glamor_priv->ib_type = GL_UNSIGNED_SHORT;
    357         }
    358     }
    359 
    360     glDrawElements(GL_TRIANGLES, count * 6, glamor_priv->ib_type, NULL);
    361     return;
    362 
    363 fallback:
    364     for (i = 0; i < count; i++)
    365         glDrawArrays(GL_TRIANGLE_FAN, i * 4, 4);
    366 }
    367 
    368 
    369 static Bool
    370 glamor_check_instruction_count(int gl_version)
    371 {
    372     GLint max_native_alu_instructions;
    373 
    374     /* Avoid using glamor if the reported instructions limit is too low,
    375      * as this would cause glamor to fallback on sw due to large shaders
    376      * which ends up being unbearably slow.
    377      */
    378     if (gl_version < 30) {
    379         if (!epoxy_has_gl_extension("GL_ARB_fragment_program")) {
    380             ErrorF("GL_ARB_fragment_program required\n");
    381             return FALSE;
    382         }
    383 
    384         glGetProgramivARB(GL_FRAGMENT_PROGRAM_ARB,
    385                           GL_MAX_PROGRAM_NATIVE_ALU_INSTRUCTIONS_ARB,
    386                           &max_native_alu_instructions);
    387         if (max_native_alu_instructions < GLAMOR_MIN_ALU_INSTRUCTIONS) {
    388             LogMessage(X_WARNING,
    389                        "glamor requires at least %d instructions (%d reported)\n",
    390                        GLAMOR_MIN_ALU_INSTRUCTIONS, max_native_alu_instructions);
    391             return FALSE;
    392         }
    393     }
    394 
    395     return TRUE;
    396 }
    397 
    398 static void GLAPIENTRY
    399 glamor_debug_output_callback(GLenum source,
    400                              GLenum type,
    401                              GLuint id,
    402                              GLenum severity,
    403                              GLsizei length,
    404                              const GLchar *message,
    405                              const void *userParam)
    406 {
    407     ScreenPtr screen = (void *)userParam;
    408     glamor_screen_private *glamor_priv = glamor_get_screen_private(screen);
    409 
    410     if (glamor_priv->suppress_gl_out_of_memory_logging &&
    411         source == GL_DEBUG_SOURCE_API && type == GL_DEBUG_TYPE_ERROR) {
    412         return;
    413     }
    414 
    415     LogMessageVerb(X_ERROR, 0, "glamor%d: GL error: %*s\n",
    416                screen->myNum, length, message);
    417     xorg_backtrace();
    418 }
    419 
    420 /**
    421  * Configures GL_ARB_debug_output to give us immediate callbacks when
    422  * GL errors occur, so that we can log them.
    423  */
    424 static void
    425 glamor_setup_debug_output(ScreenPtr screen)
    426 {
    427     if (!epoxy_has_gl_extension("GL_KHR_debug") &&
    428         !epoxy_has_gl_extension("GL_ARB_debug_output"))
    429         return;
    430 
    431     glEnable(GL_DEBUG_OUTPUT_SYNCHRONOUS);
    432     /* Disable debugging messages other than GL API errors */
    433     glDebugMessageControl(GL_DONT_CARE, GL_DONT_CARE, GL_DONT_CARE, 0, NULL,
    434                           GL_FALSE);
    435     glDebugMessageControl(GL_DEBUG_SOURCE_API,
    436                           GL_DEBUG_TYPE_ERROR,
    437                           GL_DONT_CARE,
    438                           0, NULL, GL_TRUE);
    439     glDebugMessageCallback(glamor_debug_output_callback,
    440                            screen);
    441 
    442     /* If KHR_debug is present, all debug output is disabled by
    443      * default on non-debug contexts.
    444      */
    445     if (epoxy_has_gl_extension("GL_KHR_debug"))
    446         glEnable(GL_DEBUG_OUTPUT);
    447 }
    448 
    449 const struct glamor_format *
    450 glamor_format_for_pixmap(PixmapPtr pixmap)
    451 {
    452     ScreenPtr pScreen = pixmap->drawable.pScreen;
    453     glamor_screen_private *glamor_priv = glamor_get_screen_private(pScreen);
    454     glamor_pixmap_private *pixmap_priv = glamor_get_pixmap_private(pixmap);
    455 
    456     if (pixmap_priv->is_cbcr)
    457         return &glamor_priv->cbcr_format;
    458     else
    459         return &glamor_priv->formats[pixmap->drawable.depth];
    460 }
    461 
    462 static void
    463 glamor_add_format(ScreenPtr screen, int depth, CARD32 render_format,
    464                   GLenum internalformat, GLenum format, GLenum type,
    465                   Bool rendering_supported)
    466 {
    467     glamor_screen_private *glamor_priv = glamor_get_screen_private(screen);
    468     struct glamor_format *f = &glamor_priv->formats[depth];
    469 
    470     /* If we're trying to run on GLES, make sure that we get the read
    471      * formats that we're expecting, since glamor_transfer relies on
    472      * them matching to get data back out.  To avoid this limitation, we
    473      * would need to have a more general glReadPixels() path in
    474      * glamor_transfer that re-encoded the bits to the pixel format that
    475      * we intended after.
    476      *
    477      * Note that we can't just create a pixmap because we're in
    478      * screeninit.
    479      */
    480     if (rendering_supported && glamor_priv->is_gles) {
    481         unsigned fbo, tex;
    482         int read_format, read_type;
    483         GLenum status;
    484 
    485         glGenTextures(1, &tex);
    486         glBindTexture(GL_TEXTURE_2D, tex);
    487         glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
    488         glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
    489         glTexImage2D(GL_TEXTURE_2D, 0, internalformat, 1, 1, 0,
    490                      format, type, NULL);
    491 
    492         glGenFramebuffers(1, &fbo);
    493         glBindFramebuffer(GL_FRAMEBUFFER, fbo);
    494         glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0,
    495                                GL_TEXTURE_2D, tex, 0);
    496         status = glCheckFramebufferStatus(GL_FRAMEBUFFER);
    497         if (status != GL_FRAMEBUFFER_COMPLETE) {
    498             ErrorF("glamor: Test fbo for depth %d incomplete.  "
    499                    "Falling back to software.\n", depth);
    500             glDeleteTextures(1, &tex);
    501             glDeleteFramebuffers(1, &fbo);
    502             return;
    503         }
    504 
    505         glGetIntegerv(GL_IMPLEMENTATION_COLOR_READ_FORMAT, &read_format);
    506         glGetIntegerv(GL_IMPLEMENTATION_COLOR_READ_TYPE, &read_type);
    507 
    508         glDeleteTextures(1, &tex);
    509         glDeleteFramebuffers(1, &fbo);
    510 
    511         if (format != read_format || type != read_type) {
    512             ErrorF("glamor: Implementation returned 0x%x/0x%x read format/type "
    513                    "for depth %d, expected 0x%x/0x%x.  "
    514                    "Falling back to software.\n",
    515                    read_format, read_type, depth, format, type);
    516             return;
    517         }
    518     }
    519 
    520     f->depth = depth;
    521     f->render_format = render_format;
    522     f->internalformat = internalformat;
    523     f->format = format;
    524     f->type = type;
    525     f->rendering_supported = rendering_supported;
    526 }
    527 
    528 /* Set up the GL format/types that glamor will use for the various depths
    529  *
    530  * X11's pixel data doesn't have channels, but to store our data in GL
    531  * we have to pick some sort of format to move X11 pixel data in and
    532  * out with in glamor_transfer.c.  For X11 core operations, other than
    533  * GL logic ops (non-GXcopy GC ops) what the driver chooses internally
    534  * doesn't matter as long as it doesn't drop any bits (we expect them
    535  * to generally expand, if anything).  For Render, we can expect
    536  * clients to tend to render with PictFormats matching our channel
    537  * layouts here since ultimately X11 pixels tend to end up on the
    538  * screen.  The render implementation will fall back to fb if the
    539  * channels don't match.
    540  *
    541  * Note that these formats don't affect what glamor_egl.c or
    542  * Xwayland's EGL layer choose for surfaces exposed through DRI or
    543  * scanout.  For now, those layers need to match what we're choosing
    544  * here, or channels will end up swizzled around.  Similarly, the
    545  * driver's visual masks also need to match what we're doing here.
    546  */
    547 static void
    548 glamor_setup_formats(ScreenPtr screen)
    549 {
    550     glamor_screen_private *glamor_priv = glamor_get_screen_private(screen);
    551 
    552     /* Prefer r8 textures since they're required by GLES3 and core,
    553      * only falling back to a8 if we can't do them.
    554      */
    555     if (glamor_priv->is_gles || epoxy_has_gl_extension("GL_ARB_texture_rg")) {
    556         glamor_add_format(screen, 1, PICT_a1,
    557                           GL_R8, GL_RED, GL_UNSIGNED_BYTE, FALSE);
    558         glamor_add_format(screen, 8, PICT_a8,
    559                           GL_R8, GL_RED, GL_UNSIGNED_BYTE, TRUE);
    560     } else {
    561         glamor_add_format(screen, 1, PICT_a1,
    562                           GL_ALPHA, GL_ALPHA, GL_UNSIGNED_BYTE, FALSE);
    563         glamor_add_format(screen, 8, PICT_a8,
    564                           GL_ALPHA, GL_ALPHA, GL_UNSIGNED_BYTE, TRUE);
    565     }
    566 
    567     if (glamor_priv->is_gles) {
    568         /* For 15bpp, GLES supports format/type RGBA/5551, rather than
    569          * bgra/1555_rev.  GL_EXT_bgra lets the impl say the color
    570          * read format/type is bgra/1555 even if we had to create it
    571          * with rgba/5551, with Mesa does.  That means we can't use
    572          * the same format/type for TexSubImage and readpixels.
    573          *
    574          * Instead, just store 16 bits using the trusted 565 path, and
    575          * disable render accel for now.
    576          */
    577         glamor_add_format(screen, 15, PICT_x1r5g5b5,
    578                           GL_RGB5_A1, GL_RGBA, GL_UNSIGNED_SHORT_5_5_5_1, TRUE);
    579     } else {
    580         glamor_add_format(screen, 15, PICT_x1r5g5b5,
    581                           GL_RGBA, GL_BGRA, GL_UNSIGNED_SHORT_1_5_5_5_REV, TRUE);
    582     }
    583 
    584     glamor_add_format(screen, 16, PICT_r5g6b5,
    585                       GL_RGB, GL_RGB, GL_UNSIGNED_SHORT_5_6_5, TRUE);
    586 
    587     if (glamor_priv->is_gles) {
    588         assert(X_BYTE_ORDER == X_LITTLE_ENDIAN);
    589         glamor_add_format(screen, 24, PICT_x8b8g8r8,
    590                           GL_RGBA8, GL_RGBA, GL_UNSIGNED_BYTE, TRUE);
    591         glamor_add_format(screen, 32, PICT_a8b8g8r8,
    592                           GL_RGBA8, GL_RGBA, GL_UNSIGNED_BYTE, TRUE);
    593     } else {
    594         glamor_add_format(screen, 24, PICT_x8r8g8b8,
    595                           GL_RGBA, GL_BGRA, GL_UNSIGNED_INT_8_8_8_8_REV, TRUE);
    596         glamor_add_format(screen, 32, PICT_a8r8g8b8,
    597                           GL_RGBA, GL_BGRA, GL_UNSIGNED_INT_8_8_8_8_REV, TRUE);
    598     }
    599 
    600     if (glamor_priv->is_gles) {
    601         glamor_add_format(screen, 30, PICT_x2b10g10r10,
    602                           GL_RGB10_A2, GL_RGBA, GL_UNSIGNED_INT_2_10_10_10_REV, TRUE);
    603     } else {
    604         glamor_add_format(screen, 30, PICT_x2r10g10b10,
    605                           GL_RGB10_A2, GL_BGRA, GL_UNSIGNED_INT_2_10_10_10_REV, TRUE);
    606     }
    607 
    608     glamor_priv->cbcr_format.depth = 16;
    609     glamor_priv->cbcr_format.internalformat = GL_RG8;
    610     glamor_priv->cbcr_format.format = GL_RG;
    611     glamor_priv->cbcr_format.type = GL_UNSIGNED_BYTE;
    612     glamor_priv->cbcr_format.rendering_supported = TRUE;
    613 }
    614 
    615 /** Set up glamor for an already-configured GL context. */
    616 Bool
    617 glamor_init(ScreenPtr screen, unsigned int flags)
    618 {
    619     glamor_screen_private *glamor_priv;
    620     int gl_version;
    621     int glsl_major, glsl_minor;
    622     int max_viewport_size[2];
    623     const char *shading_version_string;
    624     int shading_version_offset;
    625 
    626     PictureScreenPtr ps = GetPictureScreenIfSet(screen);
    627 
    628     if (flags & ~GLAMOR_VALID_FLAGS) {
    629         ErrorF("glamor_init: Invalid flags %x\n", flags);
    630         return FALSE;
    631     }
    632     glamor_priv = calloc(1, sizeof(*glamor_priv));
    633     if (glamor_priv == NULL)
    634         return FALSE;
    635 
    636     glamor_priv->flags = flags;
    637 
    638     if (!dixRegisterPrivateKey(&glamor_screen_private_key, PRIVATE_SCREEN, 0)) {
    639         LogMessage(X_WARNING,
    640                    "glamor%d: Failed to allocate screen private\n",
    641                    screen->myNum);
    642         goto free_glamor_private;
    643     }
    644 
    645     glamor_set_screen_private(screen, glamor_priv);
    646 
    647     if (!dixRegisterPrivateKey(&glamor_pixmap_private_key, PRIVATE_PIXMAP,
    648                                sizeof(struct glamor_pixmap_private))) {
    649         LogMessage(X_WARNING,
    650                    "glamor%d: Failed to allocate pixmap private\n",
    651                    screen->myNum);
    652         goto free_glamor_private;
    653     }
    654 
    655     if (!dixRegisterPrivateKey(&glamor_gc_private_key, PRIVATE_GC,
    656                                sizeof (glamor_gc_private))) {
    657         LogMessage(X_WARNING,
    658                    "glamor%d: Failed to allocate gc private\n",
    659                    screen->myNum);
    660         goto free_glamor_private;
    661     }
    662 
    663     glamor_priv->saved_procs.close_screen = screen->CloseScreen;
    664     screen->CloseScreen = glamor_close_screen;
    665 
    666     glamor_priv->saved_procs.destroy_pixmap = screen->DestroyPixmap;
    667     screen->DestroyPixmap = glamor_destroy_pixmap;
    668 
    669     /* If we are using egl screen, call egl screen init to
    670      * register correct close screen function. */
    671     if (flags & GLAMOR_USE_EGL_SCREEN) {
    672         glamor_egl_screen_init(screen, &glamor_priv->ctx);
    673     } else {
    674         if (!glamor_glx_screen_init(&glamor_priv->ctx))
    675             goto fail;
    676     }
    677 
    678     glamor_make_current(glamor_priv);
    679 
    680     if (!epoxy_is_desktop_gl())
    681         glamor_priv->is_gles = TRUE;
    682 
    683     gl_version = epoxy_gl_version();
    684 
    685     /* assume a core profile if we are GL 3.1 and don't have ARB_compatibility */
    686     glamor_priv->is_core_profile =
    687         gl_version >= 31 && !epoxy_has_gl_extension("GL_ARB_compatibility");
    688 
    689     shading_version_string = (char *) glGetString(GL_SHADING_LANGUAGE_VERSION);
    690 
    691     if (!shading_version_string) {
    692         LogMessage(X_WARNING,
    693                    "glamor%d: Failed to get GLSL version\n",
    694                    screen->myNum);
    695         goto fail;
    696     }
    697 
    698     shading_version_offset = 0;
    699     if (strncmp("OpenGL ES GLSL ES ", shading_version_string, 18) == 0)
    700         shading_version_offset = 18;
    701 
    702     if (sscanf(shading_version_string + shading_version_offset,
    703                "%i.%i",
    704                &glsl_major,
    705                &glsl_minor) != 2) {
    706         LogMessage(X_WARNING,
    707                    "glamor%d: Failed to parse GLSL version string %s\n",
    708                    screen->myNum, shading_version_string);
    709         goto fail;
    710     }
    711     glamor_priv->glsl_version = glsl_major * 100 + glsl_minor;
    712 
    713     if (glamor_priv->is_gles) {
    714         /* Force us back to the base version of our programs on an ES
    715          * context, anyway.  Basically glamor only uses desktop 1.20
    716          * or 1.30 currently.  1.30's new features are also present in
    717          * ES 3.0, but our glamor_program.c constructions use a lot of
    718          * compatibility features (to reduce the diff between 1.20 and
    719          * 1.30 programs).
    720          */
    721         glamor_priv->glsl_version = 120;
    722     }
    723 
    724     /* We'd like to require GL_ARB_map_buffer_range or
    725      * GL_OES_map_buffer_range, since it offers more information to
    726      * the driver than plain old glMapBuffer() or glBufferSubData().
    727      * It's been supported on Mesa on the desktop since 2009 and on
    728      * GLES2 since October 2012.  It's supported on Apple's iOS
    729      * drivers for SGX535 and A7, but apparently not on most Android
    730      * devices (the OES extension spec wasn't released until June
    731      * 2012).
    732      *
    733      * 82% of 0 A.D. players (desktop GL) submitting hardware reports
    734      * have support for it, with most of the ones lacking it being on
    735      * Windows with Intel 4-series (G45) graphics or older.
    736      */
    737     if (!glamor_priv->is_gles) {
    738         if (gl_version < 21) {
    739             ErrorF("Require OpenGL version 2.1 or later.\n");
    740             goto fail;
    741         }
    742 
    743         if (!glamor_priv->is_core_profile &&
    744             !epoxy_has_gl_extension("GL_ARB_texture_border_clamp")) {
    745             ErrorF("GL_ARB_texture_border_clamp required\n");
    746             goto fail;
    747         }
    748 
    749         if (!glamor_check_instruction_count(gl_version))
    750             goto fail;
    751 
    752         /* Glamor rendering assumes that platforms with GLSL 130+
    753          * have instanced arrays, but this is not always the case.
    754          * etnaviv offers GLSL 140 with OpenGL 2.1.
    755          */
    756         if (glamor_glsl_has_ints(glamor_priv) &&
    757             !epoxy_has_gl_extension("GL_ARB_instanced_arrays"))
    758                 glamor_priv->glsl_version = 120;
    759     } else {
    760         if (gl_version < 20) {
    761             ErrorF("Require Open GLES2.0 or later.\n");
    762             goto fail;
    763         }
    764 
    765         if (!epoxy_has_gl_extension("GL_EXT_texture_format_BGRA8888")) {
    766             ErrorF("GL_EXT_texture_format_BGRA8888 required\n");
    767             goto fail;
    768         }
    769 
    770         if (!epoxy_has_gl_extension("GL_OES_texture_border_clamp")) {
    771             ErrorF("GL_OES_texture_border_clamp required\n");
    772             goto fail;
    773         }
    774     }
    775 
    776     if (!epoxy_has_gl_extension("GL_ARB_vertex_array_object") &&
    777         !epoxy_has_gl_extension("GL_OES_vertex_array_object")) {
    778         ErrorF("GL_{ARB,OES}_vertex_array_object required\n");
    779         goto fail;
    780     }
    781 
    782     if (!glamor_priv->is_gles && glamor_priv->glsl_version == 120 &&
    783         epoxy_has_gl_extension("GL_ARB_instanced_arrays"))
    784         glamor_priv->use_gpu_shader4 = epoxy_has_gl_extension("GL_EXT_gpu_shader4");
    785 
    786     glamor_priv->has_rw_pbo = FALSE;
    787     if (!glamor_priv->is_gles)
    788         glamor_priv->has_rw_pbo = TRUE;
    789 
    790     glamor_priv->has_khr_debug = epoxy_has_gl_extension("GL_KHR_debug");
    791     glamor_priv->has_pack_invert =
    792         epoxy_has_gl_extension("GL_MESA_pack_invert");
    793     glamor_priv->has_fbo_blit =
    794         epoxy_has_gl_extension("GL_EXT_framebuffer_blit");
    795     glamor_priv->has_map_buffer_range =
    796         epoxy_has_gl_extension("GL_ARB_map_buffer_range") ||
    797         epoxy_has_gl_extension("GL_EXT_map_buffer_range");
    798     glamor_priv->has_buffer_storage =
    799         epoxy_has_gl_extension("GL_ARB_buffer_storage");
    800     glamor_priv->has_mesa_tile_raster_order =
    801         epoxy_has_gl_extension("GL_MESA_tile_raster_order");
    802     glamor_priv->has_nv_texture_barrier =
    803         epoxy_has_gl_extension("GL_NV_texture_barrier");
    804     glamor_priv->has_unpack_subimage =
    805         !glamor_priv->is_gles ||
    806         epoxy_gl_version() >= 30 ||
    807         epoxy_has_gl_extension("GL_EXT_unpack_subimage");
    808     glamor_priv->has_pack_subimage =
    809         !glamor_priv->is_gles ||
    810         epoxy_gl_version() >= 30 ||
    811         epoxy_has_gl_extension("GL_NV_pack_subimage");
    812     glamor_priv->has_dual_blend =
    813         glamor_glsl_has_ints(glamor_priv) &&
    814         epoxy_has_gl_extension("GL_ARB_blend_func_extended");
    815     glamor_priv->has_clear_texture =
    816         epoxy_gl_version() >= 44 ||
    817         epoxy_has_gl_extension("GL_ARB_clear_texture");
    818 
    819     glamor_priv->can_copyplane = (gl_version >= 30);
    820 
    821     glamor_setup_debug_output(screen);
    822 
    823     glamor_priv->use_quads = !glamor_priv->is_gles &&
    824                              !glamor_priv->is_core_profile;
    825 
    826     /* Driver-specific hack: Avoid using GL_QUADS on VC4, where
    827      * they'll be emulated more expensively than we can with our
    828      * cached IB.
    829      */
    830     if (strstr((char *)glGetString(GL_VENDOR), "Broadcom") &&
    831         (strstr((char *)glGetString(GL_RENDERER), "VC4") ||
    832          strstr((char *)glGetString(GL_RENDERER), "V3D")))
    833         glamor_priv->use_quads = FALSE;
    834 
    835     glGetIntegerv(GL_MAX_RENDERBUFFER_SIZE, &glamor_priv->max_fbo_size);
    836     glGetIntegerv(GL_MAX_TEXTURE_SIZE, &glamor_priv->max_fbo_size);
    837     glGetIntegerv(GL_MAX_VIEWPORT_DIMS, max_viewport_size);
    838     glamor_priv->max_fbo_size = MIN(glamor_priv->max_fbo_size, max_viewport_size[0]);
    839     glamor_priv->max_fbo_size = MIN(glamor_priv->max_fbo_size, max_viewport_size[1]);
    840 #ifdef MAX_FBO_SIZE
    841     glamor_priv->max_fbo_size = MAX_FBO_SIZE;
    842 #endif
    843 
    844     glamor_priv->has_texture_swizzle =
    845         (epoxy_has_gl_extension("GL_ARB_texture_swizzle") ||
    846          (glamor_priv->is_gles && gl_version >= 30));
    847 
    848     glamor_setup_formats(screen);
    849 
    850     glamor_set_debug_level(&glamor_debug_level);
    851 
    852     if (!glamor_font_init(screen))
    853         goto fail;
    854 
    855     glamor_priv->saved_procs.block_handler = screen->BlockHandler;
    856     screen->BlockHandler = _glamor_block_handler;
    857 
    858     if (!glamor_composite_glyphs_init(screen)) {
    859         ErrorF("Failed to initialize composite masks\n");
    860         goto fail;
    861     }
    862 
    863     glamor_priv->saved_procs.create_gc = screen->CreateGC;
    864     screen->CreateGC = glamor_create_gc;
    865 
    866     glamor_priv->saved_procs.create_pixmap = screen->CreatePixmap;
    867     screen->CreatePixmap = glamor_create_pixmap;
    868 
    869     glamor_priv->saved_procs.get_spans = screen->GetSpans;
    870     screen->GetSpans = glamor_get_spans;
    871 
    872     glamor_priv->saved_procs.get_image = screen->GetImage;
    873     screen->GetImage = glamor_get_image;
    874 
    875     glamor_priv->saved_procs.change_window_attributes =
    876         screen->ChangeWindowAttributes;
    877     screen->ChangeWindowAttributes = glamor_change_window_attributes;
    878 
    879     glamor_priv->saved_procs.copy_window = screen->CopyWindow;
    880     screen->CopyWindow = glamor_copy_window;
    881 
    882     glamor_priv->saved_procs.bitmap_to_region = screen->BitmapToRegion;
    883     screen->BitmapToRegion = glamor_bitmap_to_region;
    884 
    885     glamor_priv->saved_procs.composite = ps->Composite;
    886     ps->Composite = glamor_composite;
    887 
    888     glamor_priv->saved_procs.trapezoids = ps->Trapezoids;
    889     ps->Trapezoids = glamor_trapezoids;
    890 
    891     glamor_priv->saved_procs.triangles = ps->Triangles;
    892     ps->Triangles = glamor_triangles;
    893 
    894     glamor_priv->saved_procs.addtraps = ps->AddTraps;
    895     ps->AddTraps = glamor_add_traps;
    896 
    897     glamor_priv->saved_procs.composite_rects = ps->CompositeRects;
    898     ps->CompositeRects = glamor_composite_rectangles;
    899 
    900     glamor_priv->saved_procs.glyphs = ps->Glyphs;
    901     ps->Glyphs = glamor_composite_glyphs;
    902 
    903     glamor_init_vbo(screen);
    904     glamor_init_gradient_shader(screen);
    905     glamor_pixmap_init(screen);
    906     glamor_sync_init(screen);
    907 
    908     glamor_priv->screen = screen;
    909 
    910     return TRUE;
    911 
    912  fail:
    913     /* Restore default CloseScreen and DestroyPixmap handlers */
    914     screen->CloseScreen = glamor_priv->saved_procs.close_screen;
    915     screen->DestroyPixmap = glamor_priv->saved_procs.destroy_pixmap;
    916 
    917  free_glamor_private:
    918     free(glamor_priv);
    919     glamor_set_screen_private(screen, NULL);
    920     return FALSE;
    921 }
    922 
    923 static void
    924 glamor_release_screen_priv(ScreenPtr screen)
    925 {
    926     glamor_screen_private *glamor_priv;
    927 
    928     glamor_priv = glamor_get_screen_private(screen);
    929     glamor_fini_vbo(screen);
    930     glamor_pixmap_fini(screen);
    931     free(glamor_priv);
    932 
    933     glamor_set_screen_private(screen, NULL);
    934 }
    935 
    936 Bool
    937 glamor_close_screen(ScreenPtr screen)
    938 {
    939     glamor_screen_private *glamor_priv;
    940     PixmapPtr screen_pixmap;
    941     PictureScreenPtr ps = GetPictureScreenIfSet(screen);
    942 
    943     glamor_priv = glamor_get_screen_private(screen);
    944     glamor_sync_close(screen);
    945     glamor_composite_glyphs_fini(screen);
    946     screen->CloseScreen = glamor_priv->saved_procs.close_screen;
    947 
    948     screen->CreateGC = glamor_priv->saved_procs.create_gc;
    949     screen->CreatePixmap = glamor_priv->saved_procs.create_pixmap;
    950     screen->DestroyPixmap = glamor_priv->saved_procs.destroy_pixmap;
    951     screen->GetSpans = glamor_priv->saved_procs.get_spans;
    952     screen->ChangeWindowAttributes =
    953         glamor_priv->saved_procs.change_window_attributes;
    954     screen->CopyWindow = glamor_priv->saved_procs.copy_window;
    955     screen->BitmapToRegion = glamor_priv->saved_procs.bitmap_to_region;
    956     screen->BlockHandler = glamor_priv->saved_procs.block_handler;
    957 
    958     ps->Composite = glamor_priv->saved_procs.composite;
    959     ps->Trapezoids = glamor_priv->saved_procs.trapezoids;
    960     ps->Triangles = glamor_priv->saved_procs.triangles;
    961     ps->CompositeRects = glamor_priv->saved_procs.composite_rects;
    962     ps->Glyphs = glamor_priv->saved_procs.glyphs;
    963 
    964     screen_pixmap = screen->GetScreenPixmap(screen);
    965     glamor_pixmap_destroy_fbo(screen_pixmap);
    966 
    967     glamor_release_screen_priv(screen);
    968 
    969     return screen->CloseScreen(screen);
    970 }
    971 
    972 void
    973 glamor_fini(ScreenPtr screen)
    974 {
    975     /* Do nothing currently. */
    976 }
    977 
    978 void
    979 glamor_enable_dri3(ScreenPtr screen)
    980 {
    981     glamor_screen_private *glamor_priv = glamor_get_screen_private(screen);
    982 
    983     glamor_priv->dri3_enabled = TRUE;
    984 }
    985 
    986 Bool
    987 glamor_supports_pixmap_import_export(ScreenPtr screen)
    988 {
    989     glamor_screen_private *glamor_priv = glamor_get_screen_private(screen);
    990 
    991     return glamor_priv->dri3_enabled;
    992 }
    993 
    994 _X_EXPORT void
    995 glamor_set_drawable_modifiers_func(ScreenPtr screen,
    996                                    GetDrawableModifiersFuncPtr func)
    997 {
    998     glamor_screen_private *glamor_priv = glamor_get_screen_private(screen);
    999 
   1000     glamor_priv->get_drawable_modifiers = func;
   1001 }
   1002 
   1003 _X_EXPORT Bool
   1004 glamor_get_drawable_modifiers(DrawablePtr draw, uint32_t format,
   1005                               uint32_t *num_modifiers, uint64_t **modifiers)
   1006 {
   1007     struct glamor_screen_private *glamor_priv =
   1008         glamor_get_screen_private(draw->pScreen);
   1009 
   1010     if (glamor_priv->get_drawable_modifiers) {
   1011         return glamor_priv->get_drawable_modifiers(draw, format,
   1012                                                    num_modifiers, modifiers);
   1013     }
   1014     *num_modifiers = 0;
   1015     *modifiers = NULL;
   1016     return TRUE;
   1017 }
   1018 
   1019 static int
   1020 _glamor_fds_from_pixmap(ScreenPtr screen, PixmapPtr pixmap, int *fds,
   1021                         uint32_t *strides, uint32_t *offsets,
   1022                         CARD32 *size, uint64_t *modifier)
   1023 {
   1024     glamor_pixmap_private *pixmap_priv = glamor_get_pixmap_private(pixmap);
   1025     glamor_screen_private *glamor_priv =
   1026         glamor_get_screen_private(pixmap->drawable.pScreen);
   1027 
   1028     if (!glamor_priv->dri3_enabled)
   1029         return 0;
   1030     switch (pixmap_priv->type) {
   1031     case GLAMOR_TEXTURE_DRM:
   1032     case GLAMOR_TEXTURE_ONLY:
   1033         if (!glamor_pixmap_ensure_fbo(pixmap, 0))
   1034             return 0;
   1035 
   1036         if (modifier) {
   1037             return glamor_egl_fds_from_pixmap(screen, pixmap, fds,
   1038                                               strides, offsets,
   1039                                               modifier);
   1040         } else {
   1041             CARD16 stride;
   1042 
   1043             fds[0] = glamor_egl_fd_from_pixmap(screen, pixmap, &stride, size);
   1044             strides[0] = stride;
   1045 
   1046             return fds[0] >= 0;
   1047         }
   1048     default:
   1049         break;
   1050     }
   1051     return 0;
   1052 }
   1053 
   1054 _X_EXPORT int
   1055 glamor_fds_from_pixmap(ScreenPtr screen, PixmapPtr pixmap, int *fds,
   1056                        uint32_t *strides, uint32_t *offsets,
   1057                        uint64_t *modifier)
   1058 {
   1059     return _glamor_fds_from_pixmap(screen, pixmap, fds, strides, offsets,
   1060                                    NULL, modifier);
   1061 }
   1062 
   1063 _X_EXPORT int
   1064 glamor_fd_from_pixmap(ScreenPtr screen,
   1065                       PixmapPtr pixmap, CARD16 *stride, CARD32 *size)
   1066 {
   1067     int fd;
   1068     int ret;
   1069     uint32_t stride32;
   1070 
   1071     ret = _glamor_fds_from_pixmap(screen, pixmap, &fd, &stride32, NULL, size,
   1072                                   NULL);
   1073     if (ret != 1)
   1074         return -1;
   1075 
   1076     *stride = stride32;
   1077     return fd;
   1078 }
   1079 
   1080 _X_EXPORT int
   1081 glamor_shareable_fd_from_pixmap(ScreenPtr screen,
   1082                                 PixmapPtr pixmap, CARD16 *stride, CARD32 *size)
   1083 {
   1084     unsigned orig_usage_hint = pixmap->usage_hint;
   1085     int ret;
   1086 
   1087     /*
   1088      * The actual difference between a shareable and non-shareable buffer
   1089      * is decided 4 call levels deep in glamor_make_pixmap_exportable()
   1090      * based on pixmap->usage_hint == CREATE_PIXMAP_USAGE_SHARED
   1091      * 2 of those calls are also exported API, so we cannot just add a flag.
   1092      */
   1093     pixmap->usage_hint = CREATE_PIXMAP_USAGE_SHARED;
   1094 
   1095     ret = glamor_fd_from_pixmap(screen, pixmap, stride, size);
   1096 
   1097     pixmap->usage_hint = orig_usage_hint;
   1098     return ret;
   1099 }
   1100 
   1101 int
   1102 glamor_name_from_pixmap(PixmapPtr pixmap, CARD16 *stride, CARD32 *size)
   1103 {
   1104     glamor_pixmap_private *pixmap_priv = glamor_get_pixmap_private(pixmap);
   1105 
   1106     switch (pixmap_priv->type) {
   1107     case GLAMOR_TEXTURE_DRM:
   1108     case GLAMOR_TEXTURE_ONLY:
   1109         if (!glamor_pixmap_ensure_fbo(pixmap, 0))
   1110             return -1;
   1111         return glamor_egl_fd_name_from_pixmap(pixmap->drawable.pScreen,
   1112                                               pixmap, stride, size);
   1113     default:
   1114         break;
   1115     }
   1116     return -1;
   1117 }
   1118 
   1119 void
   1120 glamor_finish(ScreenPtr screen)
   1121 {
   1122     glamor_screen_private *glamor_priv = glamor_get_screen_private(screen);
   1123 
   1124     glamor_make_current(glamor_priv);
   1125     glFinish();
   1126 }