| From 5937a57ffb286314838b080db7cc126fbef56c67 Mon Sep 17 00:00:00 2001 |
| From: Brendan King <Brendan.King@imgtec.com> |
| Date: Tue, 11 Mar 2014 11:31:26 +0000 |
| Subject: [PATCH 09/33] Add EGL_IMG_context_priority EGL extension |
| |
| Add support for the EGL_IMG_context_priority extension to EGL, and the |
| DRI2 EGL driver. |
| --- |
| include/GL/internal/dri_interface.h | 30 +++++++++++++++++++++++++ |
| src/egl/drivers/dri2/egl_dri2.c | 40 ++++++++++++++++++++++++++++------ |
| src/egl/drivers/dri2/egl_dri2.h | 1 + |
| src/egl/main/eglapi.c | 1 + |
| src/egl/main/eglcontext.c | 18 +++++++++++++++ |
| src/egl/main/eglcontext.h | 1 + |
| src/egl/main/egldisplay.h | 2 ++ |
| src/mesa/drivers/dri/common/dri_util.c | 5 +++++ |
| src/mesa/drivers/dri/common/dri_util.h | 10 +++++++++ |
| 9 files changed, 101 insertions(+), 7 deletions(-) |
| |
| diff --git a/include/GL/internal/dri_interface.h b/include/GL/internal/dri_interface.h |
| index 0e32ec5..32be7ac 100644 |
| --- a/include/GL/internal/dri_interface.h |
| +++ b/include/GL/internal/dri_interface.h |
| @@ -1058,6 +1058,21 @@ struct __DRIdri2LoaderExtensionRec { |
| /*@}*/ |
| |
| /** |
| + * \requires __DRI_PRIORITY |
| + */ |
| +/* |
| + * NOTE: |
| + * The value of __DRI_CTX_ATTRIB_PRIORITY has been chosen to avoid clashes |
| + * when patching. If this patch is submitted upstream, adjust the value to |
| + * be properly in sequence. |
| + */ |
| +#define __DRI_CTX_ATTRIB_PRIORITY 0x7fff0004 |
| + |
| +#define __DRI_CTX_PRIORITY_LOW 0 |
| +#define __DRI_CTX_PRIORITY_MEDIUM 1 |
| +#define __DRI_CTX_PRIORITY_HIGH 2 |
| + |
| +/** |
| * \name Reasons that __DRIdri2Extension::createContextAttribs might fail |
| */ |
| /*@{*/ |
| @@ -1800,4 +1815,19 @@ struct __DRIbackgroundCallableExtensionRec { |
| GLboolean (*isThreadSafe)(void *loaderPrivate); |
| }; |
| |
| +/** |
| + * Context priority driver extension. |
| + * |
| + * Existence of this extension means the driver can accept the |
| + * \c __DRI_CTX_PRIORITY attribute in |
| + * \c __DRIdri2ExtensionRec::createContextAttribs. |
| + */ |
| +#define __DRI_PRIORITY "DRI_Priority" |
| +#define __DRI_PRIORITY_VERSION 1 |
| + |
| +typedef struct __DRIpriorityExtensionRec __DRIpriorityExtension; |
| +struct __DRIpriorityExtensionRec { |
| + __DRIextension base; |
| +}; |
| + |
| #endif |
| diff --git a/src/egl/drivers/dri2/egl_dri2.c b/src/egl/drivers/dri2/egl_dri2.c |
| index 3473369..eeba44f 100644 |
| --- a/src/egl/drivers/dri2/egl_dri2.c |
| +++ b/src/egl/drivers/dri2/egl_dri2.c |
| @@ -433,6 +433,7 @@ static const struct dri2_extension_match optional_core_extensions[] = { |
| { __DRI2_RENDERER_QUERY, 1, offsetof(struct dri2_egl_display, rendererQuery) }, |
| { __DRI2_INTEROP, 1, offsetof(struct dri2_egl_display, interop) }, |
| { __DRI_IMAGE, 1, offsetof(struct dri2_egl_display, image) }, |
| + { __DRI_PRIORITY, 1, offsetof(struct dri2_egl_display, priority) }, |
| { NULL, 0, 0 } |
| }; |
| |
| @@ -664,6 +665,9 @@ dri2_setup_screen(_EGLDisplay *disp) |
| |
| if (dri2_dpy->robustness) |
| disp->Extensions.EXT_create_context_robustness = EGL_TRUE; |
| + |
| + if (dri2_dpy->priority) |
| + disp->Extensions.IMG_context_priority = EGL_TRUE; |
| } |
| |
| if (dri2_dpy->fence) { |
| @@ -1050,7 +1054,7 @@ dri2_fill_context_attribs(struct dri2_egl_context *dri2_ctx, |
| { |
| int pos = 0; |
| |
| - assert(*num_attribs >= 8); |
| + assert(*num_attribs >= 10); |
| |
| ctx_attribs[pos++] = __DRI_CTX_ATTRIB_MAJOR_VERSION; |
| ctx_attribs[pos++] = dri2_ctx->base.ClientMajorVersion; |
| @@ -1086,6 +1090,28 @@ dri2_fill_context_attribs(struct dri2_egl_context *dri2_ctx, |
| ctx_attribs[pos++] = __DRI_CTX_RESET_LOSE_CONTEXT; |
| } |
| |
| + if (dri2_dpy->priority) { |
| + uint32_t priority; |
| + |
| + switch(dri2_ctx->base.Priority) { |
| + case EGL_CONTEXT_PRIORITY_HIGH_IMG: |
| + priority = __DRI_CTX_PRIORITY_HIGH; |
| + break; |
| + case EGL_CONTEXT_PRIORITY_MEDIUM_IMG: |
| + priority = __DRI_CTX_PRIORITY_MEDIUM; |
| + break; |
| + case EGL_CONTEXT_PRIORITY_LOW_IMG: |
| + priority = __DRI_CTX_PRIORITY_LOW; |
| + break; |
| + default: |
| + _eglError(EGL_BAD_ATTRIBUTE, "eglCreateContext"); |
| + return false; |
| + } |
| + |
| + ctx_attribs[pos++] = __DRI_CTX_ATTRIB_PRIORITY; |
| + ctx_attribs[pos++] = priority; |
| + } |
| + |
| *num_attribs = pos; |
| |
| return true; |
| @@ -1189,8 +1215,8 @@ dri2_create_context(_EGLDriver *drv, _EGLDisplay *disp, _EGLConfig *conf, |
| |
| if (dri2_dpy->image_driver) { |
| unsigned error; |
| - unsigned num_attribs = 8; |
| - uint32_t ctx_attribs[8]; |
| + unsigned num_attribs = 10; |
| + uint32_t ctx_attribs[10]; |
| |
| if (!dri2_fill_context_attribs(dri2_ctx, dri2_dpy, ctx_attribs, |
| &num_attribs)) |
| @@ -1209,8 +1235,8 @@ dri2_create_context(_EGLDriver *drv, _EGLDisplay *disp, _EGLConfig *conf, |
| } else if (dri2_dpy->dri2) { |
| if (dri2_dpy->dri2->base.version >= 3) { |
| unsigned error; |
| - unsigned num_attribs = 8; |
| - uint32_t ctx_attribs[8]; |
| + unsigned num_attribs = 10; |
| + uint32_t ctx_attribs[10]; |
| |
| if (!dri2_fill_context_attribs(dri2_ctx, dri2_dpy, ctx_attribs, |
| &num_attribs)) |
| @@ -1238,8 +1264,8 @@ dri2_create_context(_EGLDriver *drv, _EGLDisplay *disp, _EGLConfig *conf, |
| assert(dri2_dpy->swrast); |
| if (dri2_dpy->swrast->base.version >= 3) { |
| unsigned error; |
| - unsigned num_attribs = 8; |
| - uint32_t ctx_attribs[8]; |
| + unsigned num_attribs = 10; |
| + uint32_t ctx_attribs[10]; |
| |
| if (!dri2_fill_context_attribs(dri2_ctx, dri2_dpy, ctx_attribs, |
| &num_attribs)) |
| diff --git a/src/egl/drivers/dri2/egl_dri2.h b/src/egl/drivers/dri2/egl_dri2.h |
| index 4a5cf8e..a5dfe7e 100644 |
| --- a/src/egl/drivers/dri2/egl_dri2.h |
| +++ b/src/egl/drivers/dri2/egl_dri2.h |
| @@ -174,6 +174,7 @@ struct dri2_egl_display |
| const __DRI2fenceExtension *fence; |
| const __DRI2rendererQueryExtension *rendererQuery; |
| const __DRI2interopExtension *interop; |
| + const __DRIpriorityExtension *priority; |
| int fd; |
| |
| /* dri2_initialize/dri2_terminate increment/decrement this count, so does |
| diff --git a/src/egl/main/eglapi.c b/src/egl/main/eglapi.c |
| index 9b899d8..29771a8 100644 |
| --- a/src/egl/main/eglapi.c |
| +++ b/src/egl/main/eglapi.c |
| @@ -526,6 +526,7 @@ _eglCreateExtensionsString(_EGLDisplay *dpy) |
| _EGL_CHECK_EXTENSION(WL_bind_wayland_display); |
| _EGL_CHECK_EXTENSION(WL_create_wayland_buffer_from_image); |
| |
| + _EGL_CHECK_EXTENSION(IMG_context_priority); |
| #undef _EGL_CHECK_EXTENSION |
| } |
| |
| diff --git a/src/egl/main/eglcontext.c b/src/egl/main/eglcontext.c |
| index df8b45c..7732048 100644 |
| --- a/src/egl/main/eglcontext.c |
| +++ b/src/egl/main/eglcontext.c |
| @@ -312,6 +312,20 @@ _eglParseContextAttribList(_EGLContext *ctx, _EGLDisplay *dpy, |
| ctx->Flags |= EGL_CONTEXT_OPENGL_FORWARD_COMPATIBLE_BIT_KHR; |
| break; |
| |
| + case EGL_CONTEXT_PRIORITY_LEVEL_IMG: |
| + switch(val) { |
| + case EGL_CONTEXT_PRIORITY_HIGH_IMG: |
| + case EGL_CONTEXT_PRIORITY_MEDIUM_IMG: |
| + case EGL_CONTEXT_PRIORITY_LOW_IMG: |
| + if (dpy->Extensions.IMG_context_priority) |
| + ctx->Priority = val; |
| + break; |
| + default: |
| + err = EGL_BAD_ATTRIBUTE; |
| + break; |
| + } |
| + break; |
| + |
| default: |
| err = EGL_BAD_ATTRIBUTE; |
| break; |
| @@ -503,6 +517,7 @@ _eglInitContext(_EGLContext *ctx, _EGLDisplay *dpy, _EGLConfig *conf, |
| ctx->Flags = 0; |
| ctx->Profile = EGL_CONTEXT_OPENGL_CORE_PROFILE_BIT_KHR; |
| ctx->ResetNotificationStrategy = EGL_NO_RESET_NOTIFICATION_KHR; |
| + ctx->Priority = EGL_CONTEXT_PRIORITY_MEDIUM_IMG; |
| |
| err = _eglParseContextAttribList(ctx, dpy, attrib_list); |
| if (err == EGL_SUCCESS && ctx->Config) { |
| @@ -568,6 +583,9 @@ _eglQueryContext(_EGLDriver *drv, _EGLDisplay *dpy, _EGLContext *c, |
| case EGL_RENDER_BUFFER: |
| *value = _eglQueryContextRenderBuffer(c); |
| break; |
| + case EGL_CONTEXT_PRIORITY_LEVEL_IMG: |
| + *value = c->Priority; |
| + break; |
| default: |
| return _eglError(EGL_BAD_ATTRIBUTE, "eglQueryContext"); |
| } |
| diff --git a/src/egl/main/eglcontext.h b/src/egl/main/eglcontext.h |
| index f2fe806..8fdd70e 100644 |
| --- a/src/egl/main/eglcontext.h |
| +++ b/src/egl/main/eglcontext.h |
| @@ -62,6 +62,7 @@ struct _egl_context |
| EGLint Flags; |
| EGLint Profile; |
| EGLint ResetNotificationStrategy; |
| + EGLint Priority; |
| |
| /* The real render buffer when a window surface is bound */ |
| EGLint WindowRenderBuffer; |
| diff --git a/src/egl/main/egldisplay.h b/src/egl/main/egldisplay.h |
| index a13ff5b..7e5dff0 100644 |
| --- a/src/egl/main/egldisplay.h |
| +++ b/src/egl/main/egldisplay.h |
| @@ -133,6 +133,8 @@ struct _egl_extensions |
| |
| EGLBoolean WL_bind_wayland_display; |
| EGLBoolean WL_create_wayland_buffer_from_image; |
| + |
| + EGLBoolean IMG_context_priority; |
| }; |
| |
| |
| diff --git a/src/mesa/drivers/dri/common/dri_util.c b/src/mesa/drivers/dri/common/dri_util.c |
| index e24e1cd..766275b 100644 |
| --- a/src/mesa/drivers/dri/common/dri_util.c |
| +++ b/src/mesa/drivers/dri/common/dri_util.c |
| @@ -306,6 +306,7 @@ driCreateContextAttribs(__DRIscreen *screen, int api, |
| unsigned minor_version = 0; |
| uint32_t flags = 0; |
| bool notify_reset = false; |
| + unsigned priority = __DRI_CTX_PRIORITY_MEDIUM; |
| |
| assert((num_attribs == 0) || (attribs != NULL)); |
| |
| @@ -348,6 +349,9 @@ driCreateContextAttribs(__DRIscreen *screen, int api, |
| notify_reset = (attribs[i * 2 + 1] |
| != __DRI_CTX_RESET_NO_NOTIFICATION); |
| break; |
| + case __DRI_CTX_ATTRIB_PRIORITY: |
| + priority = attribs[i * 2 + 1]; |
| + break; |
| default: |
| /* We can't create a context that satisfies the requirements of an |
| * attribute that we don't understand. Return failure. |
| @@ -446,6 +450,7 @@ driCreateContextAttribs(__DRIscreen *screen, int api, |
| context->driScreenPriv = screen; |
| context->driDrawablePriv = NULL; |
| context->driReadablePriv = NULL; |
| + context->priority = priority; |
| |
| if (!screen->driver->CreateContext(mesa_api, modes, context, |
| major_version, minor_version, |
| diff --git a/src/mesa/drivers/dri/common/dri_util.h b/src/mesa/drivers/dri/common/dri_util.h |
| index 8fcd632..554caf7 100644 |
| --- a/src/mesa/drivers/dri/common/dri_util.h |
| +++ b/src/mesa/drivers/dri/common/dri_util.h |
| @@ -218,6 +218,16 @@ struct __DRIcontextRec { |
| int draw_stamp; |
| int read_stamp; |
| } dri2; |
| + |
| + /** |
| + * Context priority hint. |
| + * NOTE: |
| + * This should probably be an argument to the DRI driver CreateContext |
| + * entry point, but that would mean updating every DRI driver in Mesa. |
| + * Whilst support for context priority is supplied via a patch, pass |
| + * the priority as part of the DRI context structure. |
| + */ |
| + unsigned priority; |
| }; |
| |
| /** |
| -- |
| 2.7.4 |
| |