From daf7fe69f7bd0caa955d30b43fc35b7ce0069b6b Mon Sep 17 00:00:00 2001 From: Jesse Barnes Date: Tue, 15 Sep 2009 23:23:09 -0700 Subject: DRI2: add OML_sync_control support Add OML_sync_control support, along with a simple program for testing it. This means adding support for the DRI2GetMSC, DRI2WaitMSC and DRI2WaitSBC requests. Signed-off-by: Jesse Barnes --- src/glx/x11/dri_common.c | 107 +++++++++++++++++++++++++++++++---------------- 1 file changed, 70 insertions(+), 37 deletions(-) (limited to 'src/glx/x11/dri_common.c') diff --git a/src/glx/x11/dri_common.c b/src/glx/x11/dri_common.c index 9c825ad74ab..a94c752194a 100644 --- a/src/glx/x11/dri_common.c +++ b/src/glx/x11/dri_common.c @@ -336,8 +336,9 @@ driConvertConfigs(const __DRIcoreExtension * core, return head.next; } +/* Bind DRI1 specific extensions */ _X_HIDDEN void -driBindExtensions(__GLXscreenConfigs * psc, int dri2) +driBindExtensions(__GLXscreenConfigs *psc) { const __DRIextension **extensions; int i; @@ -345,35 +346,13 @@ driBindExtensions(__GLXscreenConfigs * psc, int dri2) extensions = psc->core->getExtensions(psc->__driScreen); for (i = 0; extensions[i]; i++) { -#ifdef __DRI_COPY_SUB_BUFFER - if (strcmp(extensions[i]->name, __DRI_COPY_SUB_BUFFER) == 0) { - psc->driCopySubBuffer = - (__DRIcopySubBufferExtension *) extensions[i]; - __glXEnableDirectExtension(psc, "GLX_MESA_copy_sub_buffer"); - } -#endif - #ifdef __DRI_SWAP_CONTROL /* No DRI2 support for swap_control at the moment, since SwapBuffers * is done by the X server */ - if (strcmp(extensions[i]->name, __DRI_SWAP_CONTROL) == 0 && !dri2) { - psc->swapControl = (__DRIswapControlExtension *) extensions[i]; - __glXEnableDirectExtension(psc, "GLX_SGI_swap_control"); - __glXEnableDirectExtension(psc, "GLX_MESA_swap_control"); - } -#endif - -#ifdef __DRI_ALLOCATE - if (strcmp(extensions[i]->name, __DRI_ALLOCATE) == 0) { - psc->allocate = (__DRIallocateExtension *) extensions[i]; - __glXEnableDirectExtension(psc, "GLX_MESA_allocate_memory"); - } -#endif - -#ifdef __DRI_FRAME_TRACKING - if (strcmp(extensions[i]->name, __DRI_FRAME_TRACKING) == 0) { - psc->frameTracking = (__DRIframeTrackingExtension *) extensions[i]; - __glXEnableDirectExtension(psc, "GLX_MESA_swap_frame_usage"); + if (strcmp(extensions[i]->name, __DRI_SWAP_CONTROL) == 0) { + psc->swapControl = (__DRIswapControlExtension *) extensions[i]; + __glXEnableDirectExtension(psc, "GLX_SGI_swap_control"); + __glXEnableDirectExtension(psc, "GLX_MESA_swap_control"); } #endif @@ -390,23 +369,77 @@ driBindExtensions(__GLXscreenConfigs * psc, int dri2) * GLX_OML_sync_control if implemented. */ #endif -#ifdef __DRI_READ_DRAWABLE - if (strcmp(extensions[i]->name, __DRI_READ_DRAWABLE) == 0) { - __glXEnableDirectExtension(psc, "GLX_SGI_make_current_read"); + /* Ignore unknown extensions */ + } +} + +/* Bind DRI2 specific extensions */ +_X_HIDDEN void +dri2BindExtensions(__GLXscreenConfigs *psc) +{ + const __DRIextension **extensions; + int i; + + extensions = psc->core->getExtensions(psc->__driScreen); + + for (i = 0; extensions[i]; i++) { +#ifdef __DRI_TEX_BUFFER + if ((strcmp(extensions[i]->name, __DRI_TEX_BUFFER) == 0)) { + psc->texBuffer = (__DRItexBufferExtension *) extensions[i]; + __glXEnableDirectExtension(psc, "GLX_EXT_texture_from_pixmap"); } #endif -#ifdef __DRI_TEX_BUFFER - if ((strcmp(extensions[i]->name, __DRI_TEX_BUFFER) == 0) && dri2) { - psc->texBuffer = (__DRItexBufferExtension *) extensions[i]; - __glXEnableDirectExtension(psc, "GLX_EXT_texture_from_pixmap"); +#ifdef __DRI2_MEDIA_STREAM_COUNTER + if (strcmp(extensions[i]->name, __DRI2_MEDIA_STREAM_COUNTER) == 0) { + psc->msc = (__DRI2mediaStreamCounterExtension *) extensions[i]; + __glXEnableDirectExtension(psc, "GLX_SGI_video_sync"); } #endif #ifdef __DRI2_FLUSH - if ((strcmp(extensions[i]->name, __DRI2_FLUSH) == 0) && dri2) { - psc->f = (__DRI2flushExtension *) extensions[i]; - /* internal driver extension, no GL extension exposed */ + if ((strcmp(extensions[i]->name, __DRI2_FLUSH) == 0)) { + psc->f = (__DRI2flushExtension *) extensions[i]; + /* internal driver extension, no GL extension exposed */ + } +#endif + } +} + +/* Bind extensions common to DRI1 and DRI2 */ +_X_HIDDEN void +driBindCommonExtensions(__GLXscreenConfigs *psc) +{ + const __DRIextension **extensions; + int i; + + extensions = psc->core->getExtensions(psc->__driScreen); + + for (i = 0; extensions[i]; i++) { +#ifdef __DRI_COPY_SUB_BUFFER + if (strcmp(extensions[i]->name, __DRI_COPY_SUB_BUFFER) == 0) { + psc->driCopySubBuffer = (__DRIcopySubBufferExtension *) extensions[i]; + __glXEnableDirectExtension(psc, "GLX_MESA_copy_sub_buffer"); + } +#endif + +#ifdef __DRI_ALLOCATE + if (strcmp(extensions[i]->name, __DRI_ALLOCATE) == 0) { + psc->allocate = (__DRIallocateExtension *) extensions[i]; + __glXEnableDirectExtension(psc, "GLX_MESA_allocate_memory"); + } +#endif + +#ifdef __DRI_FRAME_TRACKING + if (strcmp(extensions[i]->name, __DRI_FRAME_TRACKING) == 0) { + psc->frameTracking = (__DRIframeTrackingExtension *) extensions[i]; + __glXEnableDirectExtension(psc, "GLX_MESA_swap_frame_usage"); + } +#endif + +#ifdef __DRI_READ_DRAWABLE + if (strcmp(extensions[i]->name, __DRI_READ_DRAWABLE) == 0) { + __glXEnableDirectExtension(psc, "GLX_SGI_make_current_read"); } #endif -- cgit v1.2.3 From efc82e7c703f9160cfdbe6d97e166ca6f5e75d86 Mon Sep 17 00:00:00 2001 From: Jesse Barnes Date: Tue, 10 Nov 2009 13:28:01 -0800 Subject: DRI2: add SwapInterval support Add support for the DRI2SwapInterval protocol request. This allows direct rendered clients to control their swap interval per the SGI_swap_control extension. Signed-off-by: Jesse Barnes --- src/glx/x11/dri2.c | 17 +++++++++++++++++ src/glx/x11/dri2.h | 3 +++ src/glx/x11/dri2_glx.c | 21 +++++++++++++++++++++ src/glx/x11/dri_common.c | 9 +++------ src/glx/x11/glxclient.h | 2 ++ src/glx/x11/glxcmds.c | 37 ++++++++++++++++++++++++++++++++++--- 6 files changed, 80 insertions(+), 9 deletions(-) (limited to 'src/glx/x11/dri_common.c') diff --git a/src/glx/x11/dri2.c b/src/glx/x11/dri2.c index 922edbdcf52..9ce633c40d4 100644 --- a/src/glx/x11/dri2.c +++ b/src/glx/x11/dri2.c @@ -537,4 +537,21 @@ Bool DRI2WaitSBC(Display *dpy, XID drawable, CARD64 target_sbc, CARD64 *ust, return True; } +void DRI2SwapInterval(Display *dpy, XID drawable, int interval) +{ + XExtDisplayInfo *info = DRI2FindDisplay(dpy); + xDRI2SwapIntervalReq *req; + + XextSimpleCheckExtension (dpy, info, dri2ExtensionName); + + LockDisplay(dpy); + GetReq(DRI2SwapInterval, req); + req->reqType = info->codes->major_opcode; + req->dri2ReqType = X_DRI2SwapInterval; + req->drawable = drawable; + req->interval = interval; + UnlockDisplay(dpy); + SyncHandle(); +} + #endif /* GLX_DIRECT_RENDERING */ diff --git a/src/glx/x11/dri2.h b/src/glx/x11/dri2.h index ae6030842cb..114e9f8f965 100644 --- a/src/glx/x11/dri2.h +++ b/src/glx/x11/dri2.h @@ -100,4 +100,7 @@ extern Bool DRI2WaitSBC(Display *dpy, XID drawable, CARD64 target_sbc, CARD64 *ust, CARD64 *msc, CARD64 *sbc); +extern void +DRI2SwapInterval(Display *dpy, XID drawable, int interval); + #endif diff --git a/src/glx/x11/dri2_glx.c b/src/glx/x11/dri2_glx.c index 86bfe46a855..83149062f31 100644 --- a/src/glx/x11/dri2_glx.c +++ b/src/glx/x11/dri2_glx.c @@ -47,6 +47,7 @@ #include "xf86drm.h" #include "dri2.h" #include "dri_common.h" +#include "../../mesa/drivers/dri/common/dri_util.h" #undef DRI2_MINOR #define DRI2_MINOR 1 @@ -83,6 +84,7 @@ struct __GLXDRIdrawablePrivateRec int width, height; int have_back; int have_fake_front; + int swap_interval; }; static void dri2WaitX(__GLXDRIdrawable * pdraw); @@ -438,6 +440,23 @@ dri2GetBuffersWithFormat(__DRIdrawable * driDrawable, return pdraw->buffers; } +static void +dri2SetSwapInterval(__GLXDRIdrawable *pdraw, int interval) +{ + __GLXDRIdrawablePrivate *priv = (__GLXDRIdrawablePrivate *) pdraw; + + DRI2SwapInterval(priv->base.psc->dpy, pdraw->xDrawable, interval); + priv->swap_interval = interval; +} + +static unsigned int +dri2GetSwapInterval(__GLXDRIdrawable *pdraw) +{ + __GLXDRIdrawablePrivate *priv = (__GLXDRIdrawablePrivate *) pdraw; + + return priv->swap_interval; +} + static const __DRIdri2LoaderExtension dri2LoaderExtension = { {__DRI_DRI2_LOADER, __DRI_DRI2_LOADER_VERSION}, dri2GetBuffers, @@ -559,6 +578,8 @@ dri2CreateScreen(__GLXscreenConfigs * psc, int screen, psp->getDrawableMSC = dri2DrawableGetMSC; psp->waitForMSC = dri2WaitForMSC; psp->waitForSBC = dri2WaitForSBC; + psp->setSwapInterval = dri2SetSwapInterval; + psp->getSwapInterval = dri2GetSwapInterval; /* DRI2 suports SubBuffer through DRI2CopyRegion, so it's always * available.*/ diff --git a/src/glx/x11/dri_common.c b/src/glx/x11/dri_common.c index a94c752194a..d1b77f308dd 100644 --- a/src/glx/x11/dri_common.c +++ b/src/glx/x11/dri_common.c @@ -390,12 +390,9 @@ dri2BindExtensions(__GLXscreenConfigs *psc) } #endif -#ifdef __DRI2_MEDIA_STREAM_COUNTER - if (strcmp(extensions[i]->name, __DRI2_MEDIA_STREAM_COUNTER) == 0) { - psc->msc = (__DRI2mediaStreamCounterExtension *) extensions[i]; - __glXEnableDirectExtension(psc, "GLX_SGI_video_sync"); - } -#endif + __glXEnableDirectExtension(psc, "GLX_SGI_video_sync"); + __glXEnableDirectExtension(psc, "GLX_SGI_swap_control"); + __glXEnableDirectExtension(psc, "GLX_MESA_swap_control"); #ifdef __DRI2_FLUSH if ((strcmp(extensions[i]->name, __DRI2_FLUSH) == 0)) { diff --git a/src/glx/x11/glxclient.h b/src/glx/x11/glxclient.h index 2b835a0a9ca..ded4f5a434a 100644 --- a/src/glx/x11/glxclient.h +++ b/src/glx/x11/glxclient.h @@ -148,6 +148,8 @@ struct __GLXDRIscreenRec { int64_t *msc, int64_t *sbc); int (*waitForSBC)(__GLXDRIdrawable *pdraw, int64_t target_sbc, int64_t *ust, int64_t *msc, int64_t *sbc); + void (*setSwapInterval)(__GLXDRIdrawable *pdraw, int interval); + int (*getSwapInterval)(__GLXDRIdrawable *pdraw); }; struct __GLXDRIcontextRec diff --git a/src/glx/x11/glxcmds.c b/src/glx/x11/glxcmds.c index c7ccaaa0b5f..fefdd99f559 100644 --- a/src/glx/x11/glxcmds.c +++ b/src/glx/x11/glxcmds.c @@ -1884,6 +1884,7 @@ __glXSwapIntervalSGI(int interval) { xGLXVendorPrivateReq *req; GLXContext gc = __glXGetCurrentContext(); + __GLXscreenConfigs *psc; Display *dpy; CARD32 *interval_ptr; CARD8 opcode; @@ -1912,6 +1913,16 @@ __glXSwapIntervalSGI(int interval) } } #endif + psc = GetGLXScreenConfigs( gc->currentDpy, gc->screen); + + if (gc->driContext && psc->driScreen && psc->driScreen->setSwapInterval) { + __GLXDRIdrawable *pdraw = GetGLXDRIDrawable(gc->currentDpy, + gc->currentDrawable, + NULL); + psc->driScreen->setSwapInterval(pdraw, interval); + return 0; + } + dpy = gc->currentDpy; opcode = __glXSetupForCommand(dpy); if (!opcode) { @@ -1943,13 +1954,13 @@ __glXSwapIntervalSGI(int interval) static int __glXSwapIntervalMESA(unsigned int interval) { -#ifdef __DRI_SWAP_CONTROL GLXContext gc = __glXGetCurrentContext(); if (interval < 0) { return GLX_BAD_VALUE; } +#ifdef __DRI_SWAP_CONTROL if (gc != NULL && gc->driContext) { __GLXscreenConfigs *const psc = GetGLXScreenConfigs(gc->currentDpy, gc->screen); @@ -1963,10 +1974,20 @@ __glXSwapIntervalMESA(unsigned int interval) } } } -#else - (void) interval; #endif + if (gc != NULL && gc->driContext) { + __GLXscreenConfigs *psc; + + psc = GetGLXScreenConfigs( gc->currentDpy, gc->screen); + if (psc->driScreen && psc->driScreen->setSwapInterval) { + __GLXDRIdrawable *pdraw = GetGLXDRIDrawable(gc->currentDpy, + gc->currentDrawable, NULL); + psc->driScreen->setSwapInterval(pdraw, interval); + return 0; + } + } + return GLX_BAD_CONTEXT; } @@ -1990,6 +2011,16 @@ __glXGetSwapIntervalMESA(void) } } #endif + if (gc != NULL && gc->driContext) { + __GLXscreenConfigs *psc; + + psc = GetGLXScreenConfigs( gc->currentDpy, gc->screen); + if (psc->driScreen && psc->driScreen->getSwapInterval) { + __GLXDRIdrawable *pdraw = GetGLXDRIDrawable(gc->currentDpy, + gc->currentDrawable, NULL); + return psc->driScreen->getSwapInterval(pdraw); + } + } return 0; } -- cgit v1.2.3 From 7f170573ea486f2f2dd474c2590346f1a0110773 Mon Sep 17 00:00:00 2001 From: Jesse Barnes Date: Thu, 12 Nov 2009 16:48:07 +0000 Subject: DRI2/GLX: add INTEL_swap_event support Add event support for the GLX swap buffers event, along with DRI2 protocol support for generating GLX swap buffers events in the direct rendered case. Signed-off-by: Jesse Barnes --- include/GL/glx.h | 19 +++++++++ include/GL/glxext.h | 8 ++++ src/glx/x11/dri2.c | 70 ++++++++++++++++++++++++++++++++- src/glx/x11/dri_common.c | 3 ++ src/glx/x11/glxext.c | 91 ++++++++++++++++++++++++++++++++++++++++++- src/glx/x11/glxextensions.c | 1 + src/glx/x11/glxextensions.h | 3 +- src/mesa/drivers/x11/glxapi.c | 3 ++ 8 files changed, 193 insertions(+), 5 deletions(-) (limited to 'src/glx/x11/dri_common.c') diff --git a/include/GL/glx.h b/include/GL/glx.h index 28844014069..82b0f221146 100644 --- a/include/GL/glx.h +++ b/include/GL/glx.h @@ -186,6 +186,16 @@ typedef XID GLXWindow; typedef XID GLXPbuffer; +/* +** Events. +** __GLX_NUMBER_EVENTS is set to 17 to account for the BufferClobberSGIX +** event - this helps initialization if the server supports the pbuffer +** extension and the client doesn't. +*/ +#define GLX_PbufferClobber 0 +#define GLX_BufferSwapComplete 1 + +#define __GLX_NUMBER_EVENTS 17 extern XVisualInfo* glXChooseVisual( Display *dpy, int screen, int *attribList ); @@ -507,8 +517,17 @@ typedef struct { int count; /* if nonzero, at least this many more */ } GLXPbufferClobberEvent; +typedef struct { + int event_type; + GLXDrawable drawable; + int64_t ust; + int64_t msc; + int64_t sbc; +} GLXBufferSwapComplete; + typedef union __GLXEvent { GLXPbufferClobberEvent glxpbufferclobber; + GLXBufferSwapComplete glxbufferswapcomplete; long pad[24]; } GLXEvent; diff --git a/include/GL/glxext.h b/include/GL/glxext.h index 9ac0592e053..36ee3665dfd 100644 --- a/include/GL/glxext.h +++ b/include/GL/glxext.h @@ -696,6 +696,14 @@ extern void glXJoinSwapGroupSGIX (Display *, GLXDrawable, GLXDrawable); typedef void ( * PFNGLXJOINSWAPGROUPSGIXPROC) (Display *dpy, GLXDrawable drawable, GLXDrawable member); #endif +#ifndef GLX_INTEL_swap_event +#define GLX_INTEL_swap_event +#define GLX_BUFFER_SWAP_COMPLETE_MASK 0x10000000 +#define GLX_EXCHANGE_COMPLETE 0x8024 +#define GLX_BLIT_COMPLETE 0x8025 +#define GLX_FLIP_COMPLETE 0x8026 +#endif + #ifndef GLX_SGIX_swap_barrier #define GLX_SGIX_swap_barrier 1 #ifdef GLX_GLXEXT_PROTOTYPES diff --git a/src/glx/x11/dri2.c b/src/glx/x11/dri2.c index 9ce633c40d4..2cb5d3463af 100644 --- a/src/glx/x11/dri2.c +++ b/src/glx/x11/dri2.c @@ -41,6 +41,8 @@ #include #include "xf86drm.h" #include "dri2.h" +#include "glxclient.h" +#include "GL/glxext.h" /* Allow the build to work with an older versions of dri2proto.h and * dri2tokens.h. @@ -56,6 +58,11 @@ static char dri2ExtensionName[] = DRI2_NAME; static XExtensionInfo *dri2Info; static XEXT_GENERATE_CLOSE_DISPLAY (DRI2CloseDisplay, dri2Info) +static Bool +DRI2WireToEvent(Display *dpy, XEvent *event, xEvent *wire); +static Status +DRI2EventToWire(Display *dpy, XEvent *event, xEvent *wire); + static /* const */ XExtensionHooks dri2ExtensionHooks = { NULL, /* create_gc */ NULL, /* copy_gc */ @@ -64,8 +71,8 @@ static /* const */ XExtensionHooks dri2ExtensionHooks = { NULL, /* create_font */ NULL, /* free_font */ DRI2CloseDisplay, /* close_display */ - NULL, /* wire_to_event */ - NULL, /* event_to_wire */ + DRI2WireToEvent, /* wire_to_event */ + DRI2EventToWire, /* event_to_wire */ NULL, /* error */ NULL, /* error_string */ }; @@ -76,6 +83,65 @@ static XEXT_GENERATE_FIND_DISPLAY (DRI2FindDisplay, &dri2ExtensionHooks, 0, NULL) +static Bool +DRI2WireToEvent(Display *dpy, XEvent *event, xEvent *wire) +{ + XExtDisplayInfo *info = DRI2FindDisplay(dpy); + + XextCheckExtension(dpy, info, dri2ExtensionName, False); + + switch ((wire->u.u.type & 0x7f) - info->codes->first_event) { + case DRI2_BufferSwapComplete: + { + GLXBufferSwapComplete *aevent = (GLXBufferSwapComplete *)event; + xDRI2BufferSwapComplete *awire = (xDRI2BufferSwapComplete *)wire; + switch (awire->type) { + case DRI2_EXCHANGE_COMPLETE: + aevent->event_type = GLX_EXCHANGE_COMPLETE; + break; + case DRI2_BLIT_COMPLETE: + aevent->event_type = GLX_BLIT_COMPLETE; + break; + case DRI2_FLIP_COMPLETE: + aevent->event_type = GLX_FLIP_COMPLETE; + break; + default: + /* unknown swap completion type */ + return False; + } + aevent->drawable = awire->drawable; + aevent->ust = ((CARD64)awire->ust_hi << 32) | awire->ust_lo; + aevent->msc = ((CARD64)awire->msc_hi << 32) | awire->msc_lo; + aevent->sbc = ((CARD64)awire->sbc_hi << 32) | awire->sbc_lo; + return True; + } + default: + /* client doesn't support server event */ + break; + } + + return False; +} + +/* We don't actually support this. It doesn't make sense for clients to + * send each other DRI2 events. + */ +static Status +DRI2EventToWire(Display *dpy, XEvent *event, xEvent *wire) +{ + XExtDisplayInfo *info = DRI2FindDisplay(dpy); + + XextCheckExtension(dpy, info, dri2ExtensionName, False); + + switch (event->type) { + default: + /* client doesn't support server event */ + break; + } + + return Success; +} + Bool DRI2QueryExtension(Display * dpy, int *eventBase, int *errorBase) { diff --git a/src/glx/x11/dri_common.c b/src/glx/x11/dri_common.c index d1b77f308dd..e4034161bb3 100644 --- a/src/glx/x11/dri_common.c +++ b/src/glx/x11/dri_common.c @@ -394,6 +394,9 @@ dri2BindExtensions(__GLXscreenConfigs *psc) __glXEnableDirectExtension(psc, "GLX_SGI_swap_control"); __glXEnableDirectExtension(psc, "GLX_MESA_swap_control"); + /* FIXME: if DRI2 version supports it... */ + __glXEnableDirectExtension(psc, "INTEL_swap_event"); + #ifdef __DRI2_FLUSH if ((strcmp(extensions[i]->name, __DRI2_FLUSH) == 0)) { psc->f = (__DRI2flushExtension *) extensions[i]; diff --git a/src/glx/x11/glxext.c b/src/glx/x11/glxext.c index 5633a3e4a29..fe65216c411 100644 --- a/src/glx/x11/glxext.c +++ b/src/glx/x11/glxext.c @@ -101,6 +101,10 @@ __glXCloseDisplay(Display * dpy, XExtCodes * codes) static XEXT_GENERATE_ERROR_STRING(__glXErrorString, __glXExtensionName, __GLX_NUMBER_ERRORS, error_list) +static Bool +__glXWireToEvent(Display *dpy, XEvent *event, xEvent *wire); +static Status +__glXEventToWire(Display *dpy, XEvent *event, xEvent *wire); static /* const */ XExtensionHooks __glXExtensionHooks = { NULL, /* create_gc */ @@ -110,8 +114,8 @@ static /* const */ XExtensionHooks __glXExtensionHooks = { NULL, /* create_font */ NULL, /* free_font */ __glXCloseDisplay, /* close_display */ - NULL, /* wire_to_event */ - NULL, /* event_to_wire */ + __glXWireToEvent, /* wire_to_event */ + __glXEventToWire, /* event_to_wire */ NULL, /* error */ __glXErrorString, /* error_string */ }; @@ -121,6 +125,89 @@ XEXT_GENERATE_FIND_DISPLAY(__glXFindDisplay, __glXExtensionInfo, __glXExtensionName, &__glXExtensionHooks, __GLX_NUMBER_EVENTS, NULL) +/* + * GLX events are a bit funky. We don't stuff the X event code into + * our user exposed (via XNextEvent) structure. Instead we use the GLX + * private event code namespace (and hope it doesn't conflict). Clients + * have to know that bit 15 in the event type field means they're getting + * a GLX event, and then handle the various sub-event types there, rather + * than simply checking the event code and handling it directly. + */ + +static Bool +__glXWireToEvent(Display *dpy, XEvent *event, xEvent *wire) +{ + XExtDisplayInfo *info = __glXFindDisplay(dpy); + + XextCheckExtension(dpy, info, __glXExtensionName, False); + + switch ((wire->u.u.type & 0x7f) - info->codes->first_event) { + case GLX_PbufferClobber: + { + GLXPbufferClobberEvent *aevent = (GLXPbufferClobberEvent *)event; + xGLXPbufferClobberEvent *awire = (xGLXPbufferClobberEvent *)wire; + aevent->event_type = awire->type; + aevent->serial = awire->sequenceNumber; + aevent->event_type = awire->event_type; + aevent->draw_type = awire->draw_type; + aevent->drawable = awire->drawable; + aevent->buffer_mask = awire->buffer_mask; + aevent->aux_buffer = awire->aux_buffer; + aevent->x = awire->x; + aevent->y = awire->y; + aevent->width = awire->width; + aevent->height = awire->height; + aevent->count = awire->count; + return True; + } + case GLX_BufferSwapComplete: + { + GLXBufferSwapComplete *aevent = (GLXBufferSwapComplete *)event; + xGLXBufferSwapComplete *awire = (xGLXBufferSwapComplete *)wire; + aevent->event_type = awire->event_type; + aevent->drawable = awire->drawable; + aevent->ust = ((CARD64)awire->ust_hi << 32) | awire->ust_lo; + aevent->msc = ((CARD64)awire->msc_hi << 32) | awire->msc_lo; + aevent->sbc = ((CARD64)awire->sbc_hi << 32) | awire->sbc_lo; + return True; + } + default: + /* client doesn't support server event */ + break; + } + + return False; +} + +/* We don't actually support this. It doesn't make sense for clients to + * send each other GLX events. + */ +static Status +__glXEventToWire(Display *dpy, XEvent *event, xEvent *wire) +{ + XExtDisplayInfo *info = __glXFindDisplay(dpy); + + XextCheckExtension(dpy, info, __glXExtensionName, False); + + switch (event->type) { + case GLX_DAMAGED: + break; + case GLX_SAVED: + break; + case GLX_EXCHANGE_COMPLETE: + break; + case GLX_BLIT_COMPLETE: + break; + case GLX_FLIP_COMPLETE: + break; + default: + /* client doesn't support server event */ + break; + } + + return Success; +} + /************************************************************************/ /* ** Free the per screen configs data as well as the array of diff --git a/src/glx/x11/glxextensions.c b/src/glx/x11/glxextensions.c index 6852128e2ae..25a5c492930 100644 --- a/src/glx/x11/glxextensions.c +++ b/src/glx/x11/glxextensions.c @@ -104,6 +104,7 @@ static const struct extension_info known_glx_extensions[] = { { GLX(SGIX_swap_group), VER(0,0), N, N, N, N }, { GLX(SGIX_visual_select_group), VER(0,0), Y, Y, N, N }, { GLX(EXT_texture_from_pixmap), VER(0,0), Y, N, N, N }, + { GLX(INTEL_swap_event), VER(1,4), Y, Y, N, N }, { NULL } }; diff --git a/src/glx/x11/glxextensions.h b/src/glx/x11/glxextensions.h index 652c5db1c81..f556b1239c9 100644 --- a/src/glx/x11/glxextensions.h +++ b/src/glx/x11/glxextensions.h @@ -65,7 +65,8 @@ enum SGIX_swap_barrier_bit, SGIX_swap_group_bit, SGIX_visual_select_group_bit, - EXT_texture_from_pixmap_bit + EXT_texture_from_pixmap_bit, + INTEL_swap_event_bit, }; enum diff --git a/src/mesa/drivers/x11/glxapi.c b/src/mesa/drivers/x11/glxapi.c index 02eea25a712..a17c2c3ffc6 100644 --- a/src/mesa/drivers/x11/glxapi.c +++ b/src/mesa/drivers/x11/glxapi.c @@ -1172,6 +1172,9 @@ _glxapi_get_extensions(void) #endif #ifdef GLX_EXT_texture_from_pixmap "GLX_EXT_texture_from_pixmap", +#endif +#ifdef GLX_INTEL_swap_event + "GLX_INTEL_swap_event", #endif NULL }; -- cgit v1.2.3