[Mesa-dev] [PATCH] dri_interface, egl, gallium: only expose RGBA visuals on Android

Emil Velikov emil.l.velikov at gmail.com
Mon Jul 31 12:14:56 UTC 2017


Hi Marek,

On 28 July 2017 at 18:38, Marek Olšák <maraeo at gmail.com> wrote:
> From: Marek Olšák <marek.olsak at amd.com>
>
> X/GLX can't handle them. This removes almost 500 GLX visuals that were
> incorrectly exposed.
>
> Add an optional getCapability callback for querying what the loader can do.
>
> I'm not splitting this patch, because it's already too small.
>
> v2: also add the callback to __DRIimageLoaderExtension
> ---
>  include/GL/internal/dri_interface.h         | 28 ++++++++++++++++++++++++++--
>  src/egl/drivers/dri2/platform_android.c     | 18 ++++++++++++++++--
>  src/gallium/state_trackers/dri/dri_screen.c | 24 +++++++++++++++++++++++-
>  3 files changed, 65 insertions(+), 5 deletions(-)
>
> diff --git a/include/GL/internal/dri_interface.h b/include/GL/internal/dri_interface.h
> index a8f5af1..c314a43 100644
> --- a/include/GL/internal/dri_interface.h
> +++ b/include/GL/internal/dri_interface.h
> @@ -960,21 +960,29 @@ typedef unsigned int
>
>  struct __DRIbufferRec {
>      unsigned int attachment;
>      unsigned int name;
>      unsigned int pitch;
>      unsigned int cpp;
>      unsigned int flags;
>  };
>
>  #define __DRI_DRI2_LOADER "DRI_DRI2Loader"
> -#define __DRI_DRI2_LOADER_VERSION 3
> +#define __DRI_DRI2_LOADER_VERSION 4
> +
> +enum dri_loader_cap {
> +   /* Whether the loader handles RGBA channel ordering correctly. If not,
> +    * only BGRA ordering can be exposed.
> +    */
> +   DRI_LOADER_CAP_RGBA_ORDERING,
> +};
> +
>  struct __DRIdri2LoaderExtensionRec {
>      __DRIextension base;
>
>      __DRIbuffer *(*getBuffers)(__DRIdrawable *driDrawable,
>                                int *width, int *height,
>                                unsigned int *attachments, int count,
>                                int *out_count, void *loaderPrivate);
>
>      /**
>       * Flush pending front-buffer rendering
> @@ -1010,20 +1018,28 @@ struct __DRIdri2LoaderExtensionRec {
>       *                       \c attachments.
>       * \param loaderPrivate  Loader's private data that was previously passed
>       *                       into __DRIdri2ExtensionRec::createNewDrawable.
>       *
>       * \since 3
>       */
>      __DRIbuffer *(*getBuffersWithFormat)(__DRIdrawable *driDrawable,
>                                          int *width, int *height,
>                                          unsigned int *attachments, int count,
>                                          int *out_count, void *loaderPrivate);
> +
> +    /**
> +     * Return a loader capability value. If the loader doesn't know the enum,
> +     * it will return 0.
> +     *
> +     * \since 4
> +     */
> +    unsigned (*getCapability)(void *loaderPrivate, enum dri_loader_cap cap);
>  };
>
>  /**
>   * This extension provides alternative screen, drawable and context
>   * constructors for DRI2.
>   */
>  #define __DRI_DRI2 "DRI_DRI2"
>  #define __DRI_DRI2_VERSION 4
>
>  #define __DRI_API_OPENGL       0       /**< OpenGL compatibility profile */
> @@ -1704,21 +1720,21 @@ enum __DRIimageBufferMask {
>     __DRI_IMAGE_BUFFER_FRONT = (1 << 1)
>  };
>
>  struct __DRIimageList {
>     uint32_t image_mask;
>     __DRIimage *back;
>     __DRIimage *front;
>  };
>
>  #define __DRI_IMAGE_LOADER "DRI_IMAGE_LOADER"
> -#define __DRI_IMAGE_LOADER_VERSION 1
> +#define __DRI_IMAGE_LOADER_VERSION 2
>
>  struct __DRIimageLoaderExtensionRec {
>      __DRIextension base;
>
>     /**
>      * Allocate color buffers.
>      *
>      * \param driDrawable
>      * \param width              Width of allocated buffers
>      * \param height             Height of allocated buffers
> @@ -1740,20 +1756,28 @@ struct __DRIimageLoaderExtensionRec {
>       * Flush pending front-buffer rendering
>       *
>       * Any rendering that has been performed to the
>       * fake front will be flushed to the front
>       *
>       * \param driDrawable    Drawable whose front-buffer is to be flushed
>       * \param loaderPrivate  Loader's private data that was previously passed
>       *                       into __DRIdri2ExtensionRec::createNewDrawable
>       */
>      void (*flushFrontBuffer)(__DRIdrawable *driDrawable, void *loaderPrivate);
> +
> +    /**
> +     * Return a loader capability value. If the loader doesn't know the enum,
> +     * it will return 0.
> +     *
> +     * \since 2
> +     */
> +    unsigned (*getCapability)(void *loaderPrivate, enum dri_loader_cap cap);
>  };
>
>  /**
>   * DRI extension.
>   */
>
>  #define __DRI_IMAGE_DRIVER           "DRI_IMAGE_DRIVER"
>  #define __DRI_IMAGE_DRIVER_VERSION   1
>
>  struct __DRIimageDriverExtensionRec {
> diff --git a/src/egl/drivers/dri2/platform_android.c b/src/egl/drivers/dri2/platform_android.c
> index 300e2d9..bae4241 100644
> --- a/src/egl/drivers/dri2/platform_android.c
> +++ b/src/egl/drivers/dri2/platform_android.c
> @@ -1006,20 +1006,32 @@ droid_get_buffers_with_format(__DRIdrawable * driDrawable,
>     *out_count = droid_get_buffers_parse_attachments(dri2_surf, attachments, count);
>
>     if (width)
>        *width = dri2_surf->base.Width;
>     if (height)
>        *height = dri2_surf->base.Height;
>
>     return dri2_surf->buffers;
>  }
>
> +static unsigned
> +droid_get_capability(void *loaderPrivate, enum dri_loader_cap cap)
> +{
> +   /* Note: loaderPrivate is _EGLDisplay* */
> +   switch (cap) {
> +   case DRI_LOADER_CAP_RGBA_ORDERING:
> +      return 1;
> +   default:
> +      return 0;
> +   }
> +}
> +
>  static EGLBoolean
>  droid_add_configs_for_visuals(_EGLDriver *drv, _EGLDisplay *dpy)
>  {
>     struct dri2_egl_display *dri2_dpy = dri2_egl_display(dpy);
>     static const struct {
>        int format;
>        unsigned int rgba_masks[4];
>     } visuals[] = {
>        { HAL_PIXEL_FORMAT_RGBA_8888, { 0x000000ff, 0x0000ff00, 0x00ff0000, 0xff000000 } },
>        { HAL_PIXEL_FORMAT_RGBX_8888, { 0x000000ff, 0x0000ff00, 0x00ff0000, 0x00000000 } },
> @@ -1118,32 +1130,34 @@ static const struct dri2_egl_display_vtbl droid_display_vtbl = {
>     .post_sub_buffer = dri2_fallback_post_sub_buffer,
>     .copy_buffers = dri2_fallback_copy_buffers,
>     .query_buffer_age = droid_query_buffer_age,
>     .query_surface = droid_query_surface,
>     .create_wayland_buffer_from_image = dri2_fallback_create_wayland_buffer_from_image,
>     .get_sync_values = dri2_fallback_get_sync_values,
>     .get_dri_drawable = dri2_surface_get_dri_drawable,
>  };
>
>  static const __DRIdri2LoaderExtension droid_dri2_loader_extension = {
> -   .base = { __DRI_DRI2_LOADER, 3 },
> +   .base = { __DRI_DRI2_LOADER, 4 },
>
>     .getBuffers           = NULL,
>     .flushFrontBuffer     = droid_flush_front_buffer,
>     .getBuffersWithFormat = droid_get_buffers_with_format,
> +   .getCapability        = droid_get_capability;
>  };
>
>  static const __DRIimageLoaderExtension droid_image_loader_extension = {
> -   .base = { __DRI_IMAGE_LOADER, 1 },
> +   .base = { __DRI_IMAGE_LOADER, 2 },
>
>     .getBuffers          = droid_image_get_buffers,
>     .flushFrontBuffer    = droid_flush_front_buffer,
> +   .getCapability       = droid_get_capability,
>  };
>
>  static const __DRIextension *droid_dri2_loader_extensions[] = {
>     &droid_dri2_loader_extension.base,
>     &image_lookup_extension.base,
>     &use_invalidate.base,
>     NULL,
>  };
>
>  static const __DRIextension *droid_image_loader_extensions[] = {
> diff --git a/src/gallium/state_trackers/dri/dri_screen.c b/src/gallium/state_trackers/dri/dri_screen.c
> index 59a850b..890a8bf 100644
> --- a/src/gallium/state_trackers/dri/dri_screen.c
> +++ b/src/gallium/state_trackers/dri/dri_screen.c
> @@ -117,20 +117,35 @@ dri_fill_st_options(struct dri_screen *screen)
>        driQueryOptionb(optionCache, "allow_glsl_builtin_variable_redeclaration");
>     options->allow_higher_compat_version =
>        driQueryOptionb(optionCache, "allow_higher_compat_version");
>     options->glsl_zero_init = driQueryOptionb(optionCache, "glsl_zero_init");
>     options->force_glsl_abs_sqrt =
>        driQueryOptionb(optionCache, "force_glsl_abs_sqrt");
>
>     driComputeOptionsSha1(optionCache, options->config_options_sha1);
>  }
>
> +static unsigned
> +dri_loader_get_cap(struct dri_screen *screen, enum dri_loader_cap cap)
> +{
> +   const __DRIdri2LoaderExtension *dri2_loader = screen->sPriv->dri2.loader;
> +   const __DRIimageLoaderExtension *image_loader = screen->sPriv->image.loader;
> +
> +   if (dri2_loader && dri2_loader->base.version >= 4)
> +      return dri2_loader->getCapability(screen->sPriv->loaderPrivate, cap);
> +
> +   if (image_loader && image_loader->base.version >= 2)
> +      return image_loader->getCapability(screen->sPriv->loaderPrivate, cap);
> +
These two need a NULL check.


> +   return 0;
> +}
> +
>  static const __DRIconfig **
>  dri_fill_in_modes(struct dri_screen *screen)
>  {
>     static const mesa_format mesa_formats[] = {
>        MESA_FORMAT_B8G8R8A8_UNORM,
>        MESA_FORMAT_B8G8R8X8_UNORM,
>        MESA_FORMAT_B8G8R8A8_SRGB,
>        MESA_FORMAT_B8G8R8X8_SRGB,
>        MESA_FORMAT_B5G6R5_UNORM,
>
> @@ -228,22 +243,29 @@ dri_fill_in_modes(struct dri_screen *screen)
>     if (pf_z32) {
>        depth_bits_array[depth_buffer_factor] = 32;
>        stencil_bits_array[depth_buffer_factor++] = 0;
>     }
>
>     mixed_color_depth =
>        p_screen->get_param(p_screen, PIPE_CAP_MIXED_COLOR_DEPTH_BITS);
>
>     assert(ARRAY_SIZE(mesa_formats) == ARRAY_SIZE(pipe_formats));
>
> +   /* Expose only BGRA ordering if the loader doesn't support RGBA ordering. */
> +   unsigned num_formats;
> +   if (dri_loader_get_cap(screen, DRI_LOADER_CAP_RGBA_ORDERING))
> +      num_formats = ARRAY_SIZE(mesa_formats);
> +   else
> +      num_formats = 5;
> +
The Intel driver would need a similar fix, would it?

I'll send a follow-up fix in a moment.

Thanks
Emil


More information about the mesa-dev mailing list