Remove XIDs from DRI interface (see #5714).
This commit is contained in:
parent
4ceefccbfa
commit
4a22ae8d44
|
@ -48,16 +48,16 @@
|
|||
* side library and the DRI (direct rendering infrastructure).
|
||||
*/
|
||||
/*@{*/
|
||||
typedef struct __DRIdisplayRec __DRIdisplay;
|
||||
typedef struct __DRIscreenRec __DRIscreen;
|
||||
typedef struct __DRIcontextRec __DRIcontext;
|
||||
typedef struct __DRIdrawableRec __DRIdrawable;
|
||||
typedef struct __DRIdriverRec __DRIdriver;
|
||||
typedef struct __DRIframebufferRec __DRIframebuffer;
|
||||
typedef struct __DRIversionRec __DRIversion;
|
||||
typedef struct __DRIinterfaceMethodsRec __DRIinterfaceMethods;
|
||||
typedef unsigned long __DRIid;
|
||||
typedef void __DRInativeDisplay;
|
||||
typedef struct __DRIdisplayRec __DRIdisplay;
|
||||
typedef struct __DRIscreenRec __DRIscreen;
|
||||
typedef struct __DRIcontextRec __DRIcontext;
|
||||
typedef struct __DRIdrawableRec __DRIdrawable;
|
||||
typedef struct __DRIdriverRec __DRIdriver;
|
||||
typedef struct __DRIframebufferRec __DRIframebuffer;
|
||||
typedef struct __DRIversionRec __DRIversion;
|
||||
typedef struct __DRIinterfaceMethodsRec __DRIinterfaceMethods;
|
||||
typedef unsigned long __DRIid;
|
||||
typedef void __DRInativeDisplay;
|
||||
/*@}*/
|
||||
|
||||
|
||||
|
@ -106,7 +106,7 @@ typedef void *(CREATENEWSCREENFUNC)(__DRInativeDisplay *dpy, int scrn,
|
|||
const __DRIinterfaceMethods * interface,
|
||||
__GLcontextModes ** driver_modes);
|
||||
typedef CREATENEWSCREENFUNC* PFNCREATENEWSCREENFUNC;
|
||||
extern CREATENEWSCREENFUNC __driCreateNewScreen_20050727;
|
||||
extern CREATENEWSCREENFUNC __driCreateNewScreen_20070105;
|
||||
|
||||
|
||||
/**
|
||||
|
@ -170,16 +170,6 @@ struct __DRIinterfaceMethodsRec {
|
|||
* the wire protocol (e.g., EGL) will implement glorified no-op functions.
|
||||
*/
|
||||
/*@{*/
|
||||
/**
|
||||
* Determine if the specified window ID still exists.
|
||||
*
|
||||
* \note
|
||||
* Implementations may assume that the driver will only pass an ID into
|
||||
* this function that actually corresponds to a window. On
|
||||
* implementations where windows can only be destroyed by the DRI driver
|
||||
* (e.g., EGL), this function is allowed to always return \c GL_TRUE.
|
||||
*/
|
||||
GLboolean (*windowExists)(__DRInativeDisplay *dpy, __DRIid draw);
|
||||
|
||||
/**
|
||||
* Create the server-side portion of the GL context.
|
||||
|
@ -306,12 +296,6 @@ struct __DRIscreenRec {
|
|||
__DRIid draw, __DRIdrawable *pdraw,
|
||||
int renderType, const int *attrs);
|
||||
|
||||
/**
|
||||
* Method to return a pointer to the DRI drawable data.
|
||||
*/
|
||||
__DRIdrawable *(*getDrawable)(__DRInativeDisplay *dpy, __DRIid draw,
|
||||
void *drawablePrivate);
|
||||
|
||||
/**
|
||||
* Opaque pointer to private per screen direct rendering data. \c NULL
|
||||
* if direct rendering is not supported on this screen. Never
|
||||
|
@ -392,28 +376,23 @@ struct __DRIcontextRec {
|
|||
*/
|
||||
void *private;
|
||||
|
||||
/**
|
||||
* Pointer to the mode used to create this context.
|
||||
*
|
||||
* \since Internal API version 20040317.
|
||||
*/
|
||||
const __GLcontextModes * mode;
|
||||
|
||||
/**
|
||||
* Method to bind a DRI drawable to a DRI graphics context.
|
||||
*
|
||||
* \since Internal API version 20050727.
|
||||
*/
|
||||
GLboolean (*bindContext)(__DRInativeDisplay *dpy, int scrn, __DRIid draw,
|
||||
__DRIid read, __DRIcontext *ctx);
|
||||
GLboolean (*bindContext)(__DRInativeDisplay *dpy, int scrn,
|
||||
__DRIdrawable *pdraw,
|
||||
__DRIdrawable *pread,
|
||||
__DRIcontext *ctx);
|
||||
|
||||
/**
|
||||
* Method to unbind a DRI drawable from a DRI graphics context.
|
||||
*
|
||||
* \since Internal API version 20050727.
|
||||
*/
|
||||
GLboolean (*unbindContext)(__DRInativeDisplay *dpy, int scrn, __DRIid draw,
|
||||
__DRIid read, __DRIcontext *ctx);
|
||||
GLboolean (*unbindContext)(__DRInativeDisplay *dpy, int scrn,
|
||||
__DRIcontext *ctx);
|
||||
};
|
||||
|
||||
/**
|
||||
|
|
|
@ -427,16 +427,37 @@ PUBLIC GLboolean XF86DRICreateDrawable( __DRInativeDisplay * ndpy, int screen,
|
|||
return True;
|
||||
}
|
||||
|
||||
static int noopErrorHandler(Display *dpy, XErrorEvent *xerr)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
PUBLIC GLboolean XF86DRIDestroyDrawable( __DRInativeDisplay * ndpy, int screen,
|
||||
__DRIid drawable )
|
||||
{
|
||||
Display * const dpy = (Display *) ndpy;
|
||||
XExtDisplayInfo *info = find_display (dpy);
|
||||
xXF86DRIDestroyDrawableReq *req;
|
||||
int (*oldXErrorHandler)(Display *, XErrorEvent *);
|
||||
|
||||
TRACE("DestroyDrawable...");
|
||||
XF86DRICheckExtension (dpy, info, False);
|
||||
|
||||
/* This is called from the DRI driver, which used call it like this
|
||||
*
|
||||
* if (windowExists(drawable))
|
||||
* destroyDrawable(drawable);
|
||||
*
|
||||
* which is a textbook race condition - the window may disappear
|
||||
* from the server between checking for its existance and
|
||||
* destroying it. Instead we change the semantics of
|
||||
* __DRIinterfaceMethodsRec::destroyDrawable() to succeed even if
|
||||
* the windows is gone, by wrapping the destroy call in an error
|
||||
* handler. */
|
||||
|
||||
XSync(dpy, GL_FALSE);
|
||||
oldXErrorHandler = XSetErrorHandler(noopErrorHandler);
|
||||
|
||||
LockDisplay(dpy);
|
||||
GetReq(XF86DRIDestroyDrawable, req);
|
||||
req->reqType = info->codes->major_opcode;
|
||||
|
@ -445,6 +466,9 @@ PUBLIC GLboolean XF86DRIDestroyDrawable( __DRInativeDisplay * ndpy, int screen,
|
|||
req->drawable = drawable;
|
||||
UnlockDisplay(dpy);
|
||||
SyncHandle();
|
||||
|
||||
XSetErrorHandler(oldXErrorHandler);
|
||||
|
||||
TRACE("DestroyDrawable... return True");
|
||||
return True;
|
||||
}
|
||||
|
|
|
@ -171,7 +171,7 @@ ExtractDir(int index, const char *paths, int dirLen, char *dir)
|
|||
* \todo
|
||||
* Create a macro or something so that this is automatically updated.
|
||||
*/
|
||||
static const char createNewScreenName[] = "__driCreateNewScreen_20050727";
|
||||
static const char createNewScreenName[] = "__driCreateNewScreen_20070105";
|
||||
|
||||
|
||||
/**
|
||||
|
|
|
@ -60,6 +60,7 @@
|
|||
#include "GL/internal/glcore.h"
|
||||
#include "glapitable.h"
|
||||
#include "glxextensions.h"
|
||||
#include "glxhash.h"
|
||||
#if defined( USE_XTHREADS )
|
||||
# include <X11/Xthreads.h>
|
||||
#elif defined( PTHREADS )
|
||||
|
@ -349,6 +350,11 @@ struct __GLXcontextRec {
|
|||
* Per context direct rendering interface functions and data.
|
||||
*/
|
||||
__DRIcontext driContext;
|
||||
|
||||
/**
|
||||
* Pointer to the mode used to create this context.
|
||||
*/
|
||||
const __GLcontextModes * mode;
|
||||
#endif
|
||||
|
||||
/**
|
||||
|
@ -456,6 +462,7 @@ typedef struct __GLXscreenConfigsRec {
|
|||
* Per screen direct rendering interface functions and data.
|
||||
*/
|
||||
__DRIscreen driScreen;
|
||||
__glxHashTable *drawHash;
|
||||
#endif
|
||||
|
||||
/**
|
||||
|
|
|
@ -61,41 +61,92 @@ static const char __glXGLXClientVersion[] = "1.4";
|
|||
|
||||
|
||||
/****************************************************************************/
|
||||
|
||||
#ifdef GLX_DIRECT_RENDERING
|
||||
|
||||
static Bool windowExistsFlag;
|
||||
static int windowExistsErrorHandler(Display *dpy, XErrorEvent *xerr)
|
||||
{
|
||||
if (xerr->error_code == BadWindow) {
|
||||
windowExistsFlag = GL_FALSE;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* Find drawables in the local hash that have been destroyed on the
|
||||
* server.
|
||||
*
|
||||
* \param dpy Display to destroy drawables for
|
||||
* \param screen Screen number to destroy drawables for
|
||||
*/
|
||||
static void GarbageCollectDRIDrawables(Display *dpy, int screen)
|
||||
{
|
||||
__GLXdisplayPrivate * const priv = __glXInitialize(dpy);
|
||||
__GLXscreenConfigs *sc;
|
||||
__DRIid draw;
|
||||
__DRIdrawable *pdraw;
|
||||
XWindowAttributes xwa;
|
||||
int (*oldXErrorHandler)(Display *, XErrorEvent *);
|
||||
|
||||
if (priv == NULL || priv->driDisplay.private == NULL)
|
||||
return;
|
||||
|
||||
/* Set no-op error handler so Xlib doesn't bail out if the windows
|
||||
* has alreay been destroyed on the server. */
|
||||
XSync(dpy, GL_FALSE);
|
||||
oldXErrorHandler = XSetErrorHandler(windowExistsErrorHandler);
|
||||
|
||||
sc = &priv->screenConfigs[screen];
|
||||
if (__glxHashFirst(sc->drawHash, &draw, (void *)&pdraw) == 1) {
|
||||
do {
|
||||
windowExistsFlag = GL_TRUE;
|
||||
XGetWindowAttributes(dpy, draw, &xwa); /* dummy request */
|
||||
if (!windowExistsFlag) {
|
||||
/* Destroy the local drawable data, if the drawable no
|
||||
longer exists in the Xserver */
|
||||
(*pdraw->destroyDrawable)(dpy, pdraw->private);
|
||||
Xfree(pdraw);
|
||||
}
|
||||
} while (__glxHashNext(sc->drawHash, &draw, (void *)&pdraw) == 1);
|
||||
}
|
||||
|
||||
XSetErrorHandler(oldXErrorHandler);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the __DRIdrawable for the drawable associated with a GLXContext
|
||||
*
|
||||
* \param dpy The display associated with \c drawable.
|
||||
* \param drawable GLXDrawable whose __DRIdrawable part is to be retrieved.
|
||||
* \param scrn_num If non-NULL, the drawables screen is stored there
|
||||
* \returns A pointer to the context's __DRIdrawable on success, or NULL if
|
||||
* the drawable is not associated with a direct-rendering context.
|
||||
*/
|
||||
|
||||
#ifdef GLX_DIRECT_RENDERING
|
||||
static __DRIdrawable *
|
||||
GetDRIDrawable( Display *dpy, GLXDrawable drawable, int * const scrn_num )
|
||||
{
|
||||
__GLXdisplayPrivate * const priv = __glXInitialize(dpy);
|
||||
__DRIdrawable * const pdraw;
|
||||
const unsigned screen_count = ScreenCount(dpy);
|
||||
unsigned i;
|
||||
__GLXscreenConfigs *sc;
|
||||
|
||||
if ( (priv != NULL) && (priv->driDisplay.private != NULL) ) {
|
||||
const unsigned screen_count = ScreenCount(dpy);
|
||||
unsigned i;
|
||||
|
||||
for ( i = 0 ; i < screen_count ; i++ ) {
|
||||
__DRIscreen * const psc = &priv->screenConfigs[i].driScreen;
|
||||
__DRIdrawable * const pdraw = (psc->private != NULL)
|
||||
? (*psc->getDrawable)(dpy, drawable, psc->private) : NULL;
|
||||
|
||||
if ( pdraw != NULL ) {
|
||||
if ( scrn_num != NULL ) {
|
||||
*scrn_num = i;
|
||||
}
|
||||
return pdraw;
|
||||
}
|
||||
if (priv == NULL || priv->driDisplay.private == NULL)
|
||||
return NULL;
|
||||
|
||||
for (i = 0; i < screen_count; i++) {
|
||||
sc = &priv->screenConfigs[i];
|
||||
if (__glxHashLookup(sc->drawHash, drawable, (void *) &pdraw) == 0) {
|
||||
if (scrn_num != NULL)
|
||||
*scrn_num = i;
|
||||
return pdraw;
|
||||
}
|
||||
}
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
|
@ -359,7 +410,7 @@ CreateContext(Display *dpy, XVisualInfo *vis,
|
|||
gc->screen = mode->screen;
|
||||
gc->vid = mode->visualID;
|
||||
gc->fbconfigID = mode->fbconfigID;
|
||||
gc->driContext.mode = mode;
|
||||
gc->mode = mode;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -473,6 +524,7 @@ DestroyContext(Display *dpy, GLXContext gc)
|
|||
gc->driContext.private);
|
||||
gc->driContext.private = NULL;
|
||||
}
|
||||
GarbageCollectDRIDrawables(dpy, gc->screen);
|
||||
}
|
||||
#endif
|
||||
|
||||
|
@ -1730,9 +1782,7 @@ static int __glXSwapIntervalMESA(unsigned int interval)
|
|||
if ( (psc != NULL) && (psc->driScreen.private != NULL)
|
||||
&& __glXExtensionBitIsEnabled( psc, MESA_swap_control_bit ) ) {
|
||||
__DRIdrawable * const pdraw =
|
||||
(*psc->driScreen.getDrawable)(gc->currentDpy,
|
||||
gc->currentDrawable,
|
||||
psc->driScreen.private);
|
||||
GetDRIDrawable(gc->currentDpy, gc->currentDrawable, NULL);
|
||||
if ( pdraw != NULL ) {
|
||||
pdraw->swap_interval = interval;
|
||||
return 0;
|
||||
|
@ -1759,9 +1809,7 @@ static int __glXGetSwapIntervalMESA(void)
|
|||
if ( (psc != NULL) && (psc->driScreen.private != NULL)
|
||||
&& __glXExtensionBitIsEnabled( psc, MESA_swap_control_bit ) ) {
|
||||
__DRIdrawable * const pdraw =
|
||||
(*psc->driScreen.getDrawable)(gc->currentDpy,
|
||||
gc->currentDrawable,
|
||||
psc->driScreen.private);
|
||||
GetDRIDrawable(gc->currentDpy, gc->currentDrawable, NULL);
|
||||
if ( pdraw != NULL ) {
|
||||
return pdraw->swap_interval;
|
||||
}
|
||||
|
@ -1919,9 +1967,7 @@ static int __glXWaitVideoSyncSGI(int divisor, int remainder, unsigned int *count
|
|||
if ( __glXExtensionBitIsEnabled( psc, SGI_video_sync_bit )
|
||||
&& psc->driScreen.private ) {
|
||||
__DRIdrawable * const pdraw =
|
||||
(*psc->driScreen.getDrawable)(gc->currentDpy,
|
||||
gc->currentDrawable,
|
||||
psc->driScreen.private);
|
||||
GetDRIDrawable(gc->currentDpy, gc->currentDrawable, NULL);
|
||||
if ( (pdraw != NULL) && (pdraw->waitForMSC != NULL) ) {
|
||||
int ret;
|
||||
int64_t msc;
|
||||
|
@ -2140,11 +2186,10 @@ Bool __glXGetMscRateOML(Display * dpy, GLXDrawable drawable,
|
|||
int i;
|
||||
|
||||
|
||||
GetDRIDrawable( dpy, drawable, & screen_num );
|
||||
if ( (screen_num != -1)
|
||||
&& XF86VidModeQueryVersion( dpy, & i, & i )
|
||||
&& XF86VidModeGetModeLine( dpy, screen_num, & dot_clock,
|
||||
& mode_line ) ) {
|
||||
if (GetDRIDrawable( dpy, drawable, & screen_num) != NULL
|
||||
&& XF86VidModeQueryVersion( dpy, & i, & i )
|
||||
&& XF86VidModeGetModeLine( dpy, screen_num, & dot_clock,
|
||||
& mode_line ) ) {
|
||||
unsigned n = dot_clock * 1000;
|
||||
unsigned d = mode_line.vtotal * mode_line.htotal;
|
||||
|
||||
|
@ -2889,50 +2934,6 @@ int __glXGetInternalVersion(void)
|
|||
}
|
||||
|
||||
|
||||
|
||||
static Bool windowExistsFlag;
|
||||
|
||||
static int windowExistsErrorHandler(Display *dpy, XErrorEvent *xerr)
|
||||
{
|
||||
if (xerr->error_code == BadWindow) {
|
||||
windowExistsFlag = GL_FALSE;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if a window associated with a \c GLXDrawable exists on the
|
||||
* X-server. This function is not used internally by libGL. It is provided
|
||||
* as a utility function for DRI drivers.
|
||||
* Drivers should not call this function directly. They should instead use
|
||||
* \c glXGetProcAddress to obtain a pointer to the function.
|
||||
*
|
||||
* \param dpy Display associated with the drawable to be queried.
|
||||
* \param draw \c GLXDrawable to test.
|
||||
*
|
||||
* \returns \c GL_TRUE if a window exists that is associated with \c draw,
|
||||
* otherwise \c GL_FALSE is returned.
|
||||
*
|
||||
* \warning This function is not currently thread-safe.
|
||||
*
|
||||
* \sa glXGetProcAddress
|
||||
*
|
||||
* \since Internal API version 20021128.
|
||||
*/
|
||||
Bool __glXWindowExists(Display *dpy, GLXDrawable draw)
|
||||
{
|
||||
XWindowAttributes xwa;
|
||||
int (*oldXErrorHandler)(Display *, XErrorEvent *);
|
||||
|
||||
XSync(dpy, GL_FALSE);
|
||||
windowExistsFlag = GL_TRUE;
|
||||
oldXErrorHandler = XSetErrorHandler(windowExistsErrorHandler);
|
||||
XGetWindowAttributes(dpy, draw, &xwa); /* dummy request */
|
||||
XSetErrorHandler(oldXErrorHandler);
|
||||
return windowExistsFlag;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Get the unadjusted system time (UST). Currently, the UST is measured in
|
||||
* microseconds since Epoc. The actual resolution of the UST may vary from
|
||||
|
|
|
@ -61,6 +61,7 @@
|
|||
#include <inttypes.h>
|
||||
#include <sys/mman.h>
|
||||
#include "xf86dri.h"
|
||||
#include "xf86drm.h"
|
||||
#include "sarea.h"
|
||||
#include "dri_glx.h"
|
||||
#endif
|
||||
|
@ -366,6 +367,7 @@ static void FreeScreenConfigs(__GLXdisplayPrivate *priv)
|
|||
(*psc->driScreen.destroyScreen)(priv->dpy, i,
|
||||
psc->driScreen.private);
|
||||
psc->driScreen.private = NULL;
|
||||
__glxHashDestroy(psc->drawHash);
|
||||
#endif
|
||||
}
|
||||
XFree((char*) priv->screenConfigs);
|
||||
|
@ -781,7 +783,6 @@ static const __DRIinterfaceMethods interface_methods = {
|
|||
_gl_context_modes_destroy,
|
||||
|
||||
__glXFindDRIScreen,
|
||||
__glXWindowExists,
|
||||
|
||||
XF86DRICreateContextWithConfig,
|
||||
XF86DRIDestroyContext,
|
||||
|
@ -816,7 +817,7 @@ static const __DRIinterfaceMethods interface_methods = {
|
|||
* returned by the client-side driver.
|
||||
*/
|
||||
static void *
|
||||
CallCreateNewScreen(Display *dpy, int scrn, __DRIscreen *psc,
|
||||
CallCreateNewScreen(Display *dpy, int scrn, __GLXscreenConfigs *psc,
|
||||
__DRIdisplay * driDpy,
|
||||
PFNCREATENEWSCREENFUNC createNewScreen)
|
||||
{
|
||||
|
@ -937,13 +938,12 @@ CallCreateNewScreen(Display *dpy, int scrn, __DRIscreen *psc,
|
|||
|
||||
if ( status == 0 ) {
|
||||
__GLcontextModes * driver_modes = NULL;
|
||||
__GLXscreenConfigs *configs = psc->screenConfigs;
|
||||
|
||||
err_msg = "InitDriver";
|
||||
err_extra = NULL;
|
||||
psp = (*createNewScreen)(dpy, scrn,
|
||||
psc,
|
||||
configs->configs,
|
||||
&psc->driScreen,
|
||||
psc->configs,
|
||||
& ddx_version,
|
||||
& dri_version,
|
||||
& drm_version,
|
||||
|
@ -954,7 +954,7 @@ CallCreateNewScreen(Display *dpy, int scrn, __DRIscreen *psc,
|
|||
& interface_methods,
|
||||
& driver_modes );
|
||||
|
||||
filter_modes( & configs->configs,
|
||||
filter_modes( & psc->configs,
|
||||
driver_modes );
|
||||
_gl_context_modes_destroy( driver_modes );
|
||||
}
|
||||
|
@ -1169,6 +1169,14 @@ static Bool AllocAndFetchScreenConfigs(Display *dpy, __GLXdisplayPrivate *priv)
|
|||
UnlockDisplay(dpy);
|
||||
|
||||
#ifdef GLX_DIRECT_RENDERING
|
||||
/* Create drawable hash */
|
||||
psc->drawHash = __glxHashCreate();
|
||||
if ( psc->drawHash == NULL ) {
|
||||
SyncHandle();
|
||||
FreeScreenConfigs(priv);
|
||||
return GL_FALSE;
|
||||
}
|
||||
|
||||
/* Initialize per screen dynamic client GLX extensions */
|
||||
psc->ext_list_first_time = GL_TRUE;
|
||||
/* Initialize the direct rendering per screen data and functions */
|
||||
|
@ -1181,7 +1189,7 @@ static Bool AllocAndFetchScreenConfigs(Display *dpy, __GLXdisplayPrivate *priv)
|
|||
|
||||
psc->driScreen.screenConfigs = (void *)psc;
|
||||
psc->driScreen.private =
|
||||
CallCreateNewScreen(dpy, i, & psc->driScreen,
|
||||
CallCreateNewScreen(dpy, i, psc,
|
||||
& priv->driDisplay,
|
||||
priv->driDisplay.createNewScreen[i] );
|
||||
}
|
||||
|
@ -1617,20 +1625,64 @@ static Bool SendMakeCurrentRequest(Display *dpy, CARD8 opcode,
|
|||
|
||||
|
||||
#ifdef GLX_DIRECT_RENDERING
|
||||
static __DRIdrawable *
|
||||
FetchDRIDrawable( Display *dpy, GLXDrawable drawable, GLXContext gc)
|
||||
{
|
||||
__GLXdisplayPrivate * const priv = __glXInitialize(dpy);
|
||||
__DRIdrawable *pdraw;
|
||||
__GLXscreenConfigs *sc;
|
||||
void *empty_attribute_list = NULL;
|
||||
|
||||
if (priv == NULL || priv->driDisplay.private == NULL)
|
||||
return NULL;
|
||||
|
||||
sc = &priv->screenConfigs[gc->screen];
|
||||
if (__glxHashLookup(sc->drawHash, drawable, (void *) &pdraw) == 0)
|
||||
return pdraw;
|
||||
|
||||
/* Allocate a new drawable */
|
||||
pdraw = (__DRIdrawable *)Xmalloc(sizeof(__DRIdrawable));
|
||||
if (!pdraw)
|
||||
return NULL;
|
||||
|
||||
/* Create a new drawable */
|
||||
pdraw->private =
|
||||
(*sc->driScreen.createNewDrawable)(dpy,
|
||||
gc->mode,
|
||||
drawable, pdraw,
|
||||
GLX_WINDOW_BIT,
|
||||
empty_attribute_list);
|
||||
|
||||
if (!pdraw->private) {
|
||||
/* ERROR!!! */
|
||||
Xfree(pdraw);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (__glxHashInsert(sc->drawHash, drawable, pdraw)) {
|
||||
(*pdraw->destroyDrawable)(dpy, pdraw->private);
|
||||
Xfree(pdraw);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
return pdraw;
|
||||
}
|
||||
|
||||
static Bool BindContextWrapper( Display *dpy, GLXContext gc,
|
||||
GLXDrawable draw, GLXDrawable read )
|
||||
{
|
||||
return (*gc->driContext.bindContext)(dpy, gc->screen, draw, read,
|
||||
__DRIdrawable *pdraw = FetchDRIDrawable(dpy, draw, gc);
|
||||
__DRIdrawable *pread = FetchDRIDrawable(dpy, read, gc);
|
||||
|
||||
return (*gc->driContext.bindContext)(dpy, gc->screen, pdraw, pread,
|
||||
& gc->driContext);
|
||||
}
|
||||
|
||||
|
||||
static Bool UnbindContextWrapper( GLXContext gc )
|
||||
{
|
||||
return (*gc->driContext.unbindContext)(gc->currentDpy, gc->screen,
|
||||
gc->currentDrawable,
|
||||
gc->currentReadable,
|
||||
& gc->driContext );
|
||||
return (*gc->driContext.unbindContext)(gc->currentDpy, gc->screen,
|
||||
&gc->driContext );
|
||||
}
|
||||
#endif /* GLX_DIRECT_RENDERING */
|
||||
|
||||
|
|
|
@ -1,4 +1,6 @@
|
|||
/* xf86drmHash.c -- Small hash table support for integer -> integer mapping
|
||||
/* glxhash.c -- Small hash table support for integer -> integer mapping
|
||||
* Taken from libdrm.
|
||||
*
|
||||
* Created: Sun Apr 18 09:35:45 1999 by faith@precisioninsight.com
|
||||
*
|
||||
* Copyright 1999 Precision Insight, Inc., Cedar Park, Texas.
|
||||
|
@ -25,8 +27,6 @@
|
|||
*
|
||||
* Authors: Rickard E. (Rik) Faith <faith@valinux.com>
|
||||
*
|
||||
* $XFree86: xc/programs/Xserver/hw/xfree86/os-support/linux/drm/xf86drmHash.c,v 1.4 2001/03/21 18:08:54 dawes Exp $
|
||||
*
|
||||
* DESCRIPTION
|
||||
*
|
||||
* This file contains a straightforward implementation of a fixed-sized
|
||||
|
|
|
@ -50,9 +50,10 @@ SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
|||
* 4.0.0: Original
|
||||
* 4.0.1: Patch to bump clipstamp when windows are destroyed, 28 May 02
|
||||
* 4.1.0: Add transition from single to multi in DRMInfo rec, 24 Jun 02
|
||||
* 5.0.0: Drop XIDs from DRI interface.
|
||||
*/
|
||||
#define XF86DRI_MAJOR_VERSION 4
|
||||
#define XF86DRI_MINOR_VERSION 1
|
||||
#define XF86DRI_MAJOR_VERSION 5
|
||||
#define XF86DRI_MINOR_VERSION 0
|
||||
#define XF86DRI_PATCH_VERSION 0
|
||||
|
||||
typedef struct _XF86DRIQueryVersion {
|
||||
|
|
|
@ -88,63 +88,6 @@ __driUtilMessage(const char *f, ...)
|
|||
}
|
||||
|
||||
|
||||
/*****************************************************************/
|
||||
/** \name Drawable list management */
|
||||
/*****************************************************************/
|
||||
/*@{*/
|
||||
|
||||
static GLboolean __driAddDrawable(void *drawHash, __DRIdrawable *pdraw)
|
||||
{
|
||||
__DRIdrawablePrivate *pdp = (__DRIdrawablePrivate *)pdraw->private;
|
||||
|
||||
if (drmHashInsert(drawHash, pdp->draw, pdraw))
|
||||
return GL_FALSE;
|
||||
|
||||
return GL_TRUE;
|
||||
}
|
||||
|
||||
static __DRIdrawable *__driFindDrawable(void *drawHash, __DRIid draw)
|
||||
{
|
||||
int retcode;
|
||||
__DRIdrawable *pdraw;
|
||||
|
||||
retcode = drmHashLookup(drawHash, draw, (void *)&pdraw);
|
||||
if (retcode)
|
||||
return NULL;
|
||||
|
||||
return pdraw;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Find drawables in the local hash that have been destroyed on the
|
||||
* server.
|
||||
*
|
||||
* \param drawHash Hash-table containing all know drawables.
|
||||
*/
|
||||
static void __driGarbageCollectDrawables(void *drawHash)
|
||||
{
|
||||
__DRIid draw;
|
||||
__DRInativeDisplay *dpy;
|
||||
__DRIdrawable *pdraw;
|
||||
|
||||
if (drmHashFirst(drawHash, &draw, (void *)&pdraw) == 1) {
|
||||
do {
|
||||
__DRIdrawablePrivate *pdp = (__DRIdrawablePrivate *)pdraw->private;
|
||||
dpy = pdp->driScreenPriv->display;
|
||||
if (! (*dri_interface->windowExists)(dpy, draw)) {
|
||||
/* Destroy the local drawable data, if the drawable no
|
||||
longer exists in the Xserver */
|
||||
(*pdraw->destroyDrawable)(dpy, pdraw->private);
|
||||
_mesa_free(pdraw);
|
||||
}
|
||||
} while (drmHashNext(drawHash, &draw, (void *)&pdraw) == 1);
|
||||
}
|
||||
}
|
||||
|
||||
/*@}*/
|
||||
|
||||
|
||||
/*****************************************************************/
|
||||
/** \name Context (un)binding functions */
|
||||
/*****************************************************************/
|
||||
|
@ -155,8 +98,6 @@ static void __driGarbageCollectDrawables(void *drawHash)
|
|||
*
|
||||
* \param dpy the display handle.
|
||||
* \param scrn the screen number.
|
||||
* \param draw drawable.
|
||||
* \param read Current reading drawable.
|
||||
* \param gc context.
|
||||
*
|
||||
* \return \c GL_TRUE on success, or \c GL_FALSE on failure.
|
||||
|
@ -170,12 +111,9 @@ static void __driGarbageCollectDrawables(void *drawHash)
|
|||
* into their respective real types it also assures they are not \c NULL.
|
||||
*/
|
||||
static GLboolean driUnbindContext(__DRInativeDisplay *dpy, int scrn,
|
||||
__DRIid draw, __DRIid read,
|
||||
__DRIcontext *ctx)
|
||||
__DRIcontext *ctx)
|
||||
{
|
||||
__DRIscreen *pDRIScreen;
|
||||
__DRIdrawable *pdraw;
|
||||
__DRIdrawable *pread;
|
||||
__DRIcontextPrivate *pcp;
|
||||
__DRIscreenPrivate *psp;
|
||||
__DRIdrawablePrivate *pdp;
|
||||
|
@ -186,7 +124,7 @@ static GLboolean driUnbindContext(__DRInativeDisplay *dpy, int scrn,
|
|||
** calling driUnbindContext.
|
||||
*/
|
||||
|
||||
if (ctx == NULL || draw == None || read == None) {
|
||||
if (ctx == NULL) {
|
||||
/* ERROR!!! */
|
||||
return GL_FALSE;
|
||||
}
|
||||
|
@ -199,26 +137,12 @@ static GLboolean driUnbindContext(__DRInativeDisplay *dpy, int scrn,
|
|||
|
||||
psp = (__DRIscreenPrivate *)pDRIScreen->private;
|
||||
pcp = (__DRIcontextPrivate *)ctx->private;
|
||||
|
||||
pdraw = __driFindDrawable(psp->drawHash, draw);
|
||||
if (!pdraw) {
|
||||
/* ERROR!!! */
|
||||
return GL_FALSE;
|
||||
}
|
||||
pdp = (__DRIdrawablePrivate *)pdraw->private;
|
||||
|
||||
pread = __driFindDrawable(psp->drawHash, read);
|
||||
if (!pread) {
|
||||
/* ERROR!!! */
|
||||
return GL_FALSE;
|
||||
}
|
||||
prp = (__DRIdrawablePrivate *)pread->private;
|
||||
|
||||
pdp = (__DRIdrawablePrivate *)pcp->driDrawablePriv;
|
||||
prp = (__DRIdrawablePrivate *)pcp->driReadablePriv;
|
||||
|
||||
/* Let driver unbind drawable from context */
|
||||
(*psp->DriverAPI.UnbindContext)(pcp);
|
||||
|
||||
|
||||
if (pdp->refcount == 0) {
|
||||
/* ERROR!!! */
|
||||
return GL_FALSE;
|
||||
|
@ -254,72 +178,20 @@ static GLboolean driUnbindContext(__DRInativeDisplay *dpy, int scrn,
|
|||
* This function takes both a read buffer and a draw buffer. This is needed
|
||||
* for \c glXMakeCurrentReadSGI or GLX 1.3's \c glXMakeContextCurrent
|
||||
* function.
|
||||
*
|
||||
* \bug This function calls \c driCreateNewDrawable in two places with the
|
||||
* \c renderType hard-coded to \c GLX_WINDOW_BIT. Some checking might
|
||||
* be needed in those places when support for pbuffers and / or pixmaps
|
||||
* is added. Is it safe to assume that the drawable is a window?
|
||||
*/
|
||||
static GLboolean DoBindContext(__DRInativeDisplay *dpy,
|
||||
__DRIid draw, __DRIid read,
|
||||
__DRIcontext *ctx, const __GLcontextModes * modes,
|
||||
__DRIscreenPrivate *psp)
|
||||
__DRIdrawable *pdraw,
|
||||
__DRIdrawable *pread,
|
||||
__DRIcontext *ctx,
|
||||
__DRIscreenPrivate *psp)
|
||||
{
|
||||
__DRIdrawable *pdraw;
|
||||
__DRIdrawablePrivate *pdp;
|
||||
__DRIdrawable *pread;
|
||||
__DRIdrawablePrivate *prp;
|
||||
__DRIcontextPrivate * const pcp = ctx->private;
|
||||
|
||||
|
||||
/* Find the _DRIdrawable which corresponds to the writing drawable. */
|
||||
pdraw = __driFindDrawable(psp->drawHash, draw);
|
||||
if (!pdraw) {
|
||||
/* Allocate a new drawable */
|
||||
pdraw = (__DRIdrawable *)_mesa_malloc(sizeof(__DRIdrawable));
|
||||
if (!pdraw) {
|
||||
/* ERROR!!! */
|
||||
return GL_FALSE;
|
||||
}
|
||||
|
||||
/* Create a new drawable */
|
||||
driCreateNewDrawable(dpy, modes, draw, pdraw, GLX_WINDOW_BIT,
|
||||
empty_attribute_list);
|
||||
if (!pdraw->private) {
|
||||
/* ERROR!!! */
|
||||
_mesa_free(pdraw);
|
||||
return GL_FALSE;
|
||||
}
|
||||
|
||||
}
|
||||
pdp = (__DRIdrawablePrivate *) pdraw->private;
|
||||
|
||||
/* Find the _DRIdrawable which corresponds to the reading drawable. */
|
||||
if (read == draw) {
|
||||
/* read buffer == draw buffer */
|
||||
prp = pdp;
|
||||
}
|
||||
else {
|
||||
pread = __driFindDrawable(psp->drawHash, read);
|
||||
if (!pread) {
|
||||
/* Allocate a new drawable */
|
||||
pread = (__DRIdrawable *)_mesa_malloc(sizeof(__DRIdrawable));
|
||||
if (!pread) {
|
||||
/* ERROR!!! */
|
||||
return GL_FALSE;
|
||||
}
|
||||
|
||||
/* Create a new drawable */
|
||||
driCreateNewDrawable(dpy, modes, read, pread, GLX_WINDOW_BIT,
|
||||
empty_attribute_list);
|
||||
if (!pread->private) {
|
||||
/* ERROR!!! */
|
||||
_mesa_free(pread);
|
||||
return GL_FALSE;
|
||||
}
|
||||
}
|
||||
prp = (__DRIdrawablePrivate *) pread->private;
|
||||
}
|
||||
prp = (__DRIdrawablePrivate *) pread->private;
|
||||
|
||||
/* Bind the drawable to the context */
|
||||
pcp->driDrawablePriv = pdp;
|
||||
|
@ -359,8 +231,9 @@ static GLboolean DoBindContext(__DRInativeDisplay *dpy,
|
|||
* function.
|
||||
*/
|
||||
static GLboolean driBindContext(__DRInativeDisplay *dpy, int scrn,
|
||||
__DRIid draw, __DRIid read,
|
||||
__DRIcontext * ctx)
|
||||
__DRIdrawable *pdraw,
|
||||
__DRIdrawable *pread,
|
||||
__DRIcontext * ctx)
|
||||
{
|
||||
__DRIscreen *pDRIScreen;
|
||||
|
||||
|
@ -369,7 +242,7 @@ static GLboolean driBindContext(__DRInativeDisplay *dpy, int scrn,
|
|||
** calling driBindContext.
|
||||
*/
|
||||
|
||||
if (ctx == NULL || draw == None || read == None) {
|
||||
if (ctx == NULL || pdraw == None || pread == None) {
|
||||
/* ERROR!!! */
|
||||
return GL_FALSE;
|
||||
}
|
||||
|
@ -380,7 +253,7 @@ static GLboolean driBindContext(__DRInativeDisplay *dpy, int scrn,
|
|||
return GL_FALSE;
|
||||
}
|
||||
|
||||
return DoBindContext( dpy, draw, read, ctx, ctx->mode,
|
||||
return DoBindContext( dpy, pdraw, pread, ctx,
|
||||
(__DRIscreenPrivate *)pDRIScreen->private );
|
||||
}
|
||||
/*@}*/
|
||||
|
@ -438,8 +311,7 @@ __driUtilUpdateDrawableInfo(__DRIdrawablePrivate *pdp)
|
|||
|
||||
DRM_SPINUNLOCK(&psp->pSAREA->drawable_lock, psp->drawLockID);
|
||||
|
||||
if (!__driFindDrawable(psp->drawHash, pdp->draw) ||
|
||||
! (*dri_interface->getDrawableInfo)(pdp->display, pdp->screen, pdp->draw,
|
||||
if (! (*dri_interface->getDrawableInfo)(pdp->display, pdp->screen, pdp->draw,
|
||||
&pdp->index, &pdp->lastStamp,
|
||||
&pdp->x, &pdp->y, &pdp->w, &pdp->h,
|
||||
&pdp->numClipRects, &pdp->pClipRects,
|
||||
|
@ -675,30 +547,9 @@ static void *driCreateNewDrawable(__DRInativeDisplay *dpy,
|
|||
|
||||
pdp->swapBuffers = psp->DriverAPI.SwapBuffers;
|
||||
|
||||
/* Add pdraw to drawable list */
|
||||
if (!__driAddDrawable(psp->drawHash, pdraw)) {
|
||||
/* ERROR!!! */
|
||||
(*pdraw->destroyDrawable)(dpy, pdp);
|
||||
_mesa_free(pdp);
|
||||
pdp = NULL;
|
||||
pdraw->private = NULL;
|
||||
}
|
||||
|
||||
return (void *) pdp;
|
||||
}
|
||||
|
||||
static __DRIdrawable *
|
||||
driGetDrawable(__DRInativeDisplay *dpy, __DRIid draw, void *screenPrivate)
|
||||
{
|
||||
__DRIscreenPrivate *psp = (__DRIscreenPrivate *) screenPrivate;
|
||||
|
||||
/*
|
||||
** Make sure this routine returns NULL if the drawable is not bound
|
||||
** to a direct rendering context!
|
||||
*/
|
||||
return __driFindDrawable(psp->drawHash, draw);
|
||||
}
|
||||
|
||||
static void
|
||||
driDestroyDrawable(__DRInativeDisplay *dpy, void *drawablePrivate)
|
||||
{
|
||||
|
@ -710,9 +561,7 @@ driDestroyDrawable(__DRInativeDisplay *dpy, void *drawablePrivate)
|
|||
psp = pdp->driScreenPriv;
|
||||
scrn = psp->myNum;
|
||||
(*psp->DriverAPI.DestroyBuffer)(pdp);
|
||||
if ((*dri_interface->windowExists)(dpy, pdp->draw))
|
||||
(void)(*dri_interface->destroyDrawable)(dpy, scrn, pdp->draw);
|
||||
drmHashDelete(psp->drawHash, pdp->draw);
|
||||
(void)(*dri_interface->destroyDrawable)(dpy, scrn, pdp->draw);
|
||||
if (pdp->pClipRects) {
|
||||
_mesa_free(pdp->pClipRects);
|
||||
pdp->pClipRects = NULL;
|
||||
|
@ -751,7 +600,6 @@ driDestroyContext(__DRInativeDisplay *dpy, int scrn, void *contextPrivate)
|
|||
|
||||
if (pcp) {
|
||||
(*pcp->driScreenPriv->DriverAPI.DestroyContext)(pcp);
|
||||
__driGarbageCollectDrawables(pcp->driScreenPriv->drawHash);
|
||||
(void) (*dri_interface->destroyContext)(dpy, scrn, pcp->contextID);
|
||||
_mesa_free(pcp);
|
||||
}
|
||||
|
@ -836,8 +684,6 @@ driCreateNewContext(__DRInativeDisplay *dpy, const __GLcontextModes *modes,
|
|||
return NULL;
|
||||
}
|
||||
|
||||
__driGarbageCollectDrawables(pcp->driScreenPriv->drawHash);
|
||||
|
||||
return pcp;
|
||||
}
|
||||
/*@}*/
|
||||
|
@ -874,15 +720,11 @@ static void driDestroyScreen(__DRInativeDisplay *dpy, int scrn, void *screenPriv
|
|||
|
||||
(void)drmUnmap((drmAddress)psp->pSAREA, SAREA_MAX);
|
||||
(void)drmUnmap((drmAddress)psp->pFB, psp->fbSize);
|
||||
_mesa_free(psp->pDevPriv);
|
||||
(void)drmCloseOnce(psp->fd);
|
||||
if ( psp->modes != NULL ) {
|
||||
(*dri_interface->destroyContextModes)( psp->modes );
|
||||
}
|
||||
|
||||
assert(psp->drawHash);
|
||||
drmHashDestroy(psp->drawHash);
|
||||
|
||||
_mesa_free(psp);
|
||||
}
|
||||
}
|
||||
|
@ -939,13 +781,6 @@ __driUtilCreateNewScreen(__DRInativeDisplay *dpy, int scrn, __DRIscreen *psc,
|
|||
return NULL;
|
||||
}
|
||||
|
||||
/* Create the hash table */
|
||||
psp->drawHash = drmHashCreate();
|
||||
if ( psp->drawHash == NULL ) {
|
||||
_mesa_free( psp );
|
||||
return NULL;
|
||||
}
|
||||
|
||||
psp->display = dpy;
|
||||
psp->myNum = scrn;
|
||||
psp->psc = psc;
|
||||
|
@ -993,7 +828,6 @@ __driUtilCreateNewScreen(__DRInativeDisplay *dpy, int scrn, __DRIscreen *psc,
|
|||
|
||||
psc->destroyScreen = driDestroyScreen;
|
||||
psc->createNewDrawable = driCreateNewDrawable;
|
||||
psc->getDrawable = driGetDrawable;
|
||||
psc->getMSC = driGetMSC;
|
||||
psc->createNewContext = driCreateNewContext;
|
||||
|
||||
|
|
|
@ -489,11 +489,6 @@ struct __DRIscreenPrivateRec {
|
|||
*/
|
||||
__DRIcontextPrivate dummyContextPriv;
|
||||
|
||||
/**
|
||||
* Hash table to hold the drawable information for this screen.
|
||||
*/
|
||||
void *drawHash;
|
||||
|
||||
/**
|
||||
* Device-dependent private information (not stored in the SAREA).
|
||||
*
|
||||
|
|
|
@ -431,7 +431,7 @@ static const struct __DriverAPIRec i810API = {
|
|||
* failure.
|
||||
*/
|
||||
PUBLIC
|
||||
void * __driCreateNewScreen_20050727( __DRInativeDisplay *dpy, int scrn, __DRIscreen *psc,
|
||||
void * __driCreateNewScreen_20070105( __DRInativeDisplay *dpy, int scrn, __DRIscreen *psc,
|
||||
const __GLcontextModes * modes,
|
||||
const __DRIversion * ddx_version,
|
||||
const __DRIversion * dri_version,
|
||||
|
|
Loading…
Reference in New Issue