19bd392adSmrg/* $XFree86: xc/lib/GL/dri/XF86dri.c,v 1.13 2002/10/30 12:51:25 alanh Exp $ */
29bd392adSmrg/**************************************************************************
39bd392adSmrg
49bd392adSmrgCopyright 1998-1999 Precision Insight, Inc., Cedar Park, Texas.
59bd392adSmrgCopyright 2000 VA Linux Systems, Inc.
69bd392adSmrgAll Rights Reserved.
79bd392adSmrg
89bd392adSmrgPermission is hereby granted, free of charge, to any person obtaining a
99bd392adSmrgcopy of this software and associated documentation files (the
109bd392adSmrg"Software"), to deal in the Software without restriction, including
119bd392adSmrgwithout limitation the rights to use, copy, modify, merge, publish,
129bd392adSmrgdistribute, sub license, and/or sell copies of the Software, and to
139bd392adSmrgpermit persons to whom the Software is furnished to do so, subject to
149bd392adSmrgthe following conditions:
159bd392adSmrg
169bd392adSmrgThe above copyright notice and this permission notice (including the
179bd392adSmrgnext paragraph) shall be included in all copies or substantial portions
189bd392adSmrgof the Software.
199bd392adSmrg
209bd392adSmrgTHE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
219bd392adSmrgOR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
229bd392adSmrgMERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT.
239bd392adSmrgIN NO EVENT SHALL PRECISION INSIGHT AND/OR ITS SUPPLIERS BE LIABLE FOR
249bd392adSmrgANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
259bd392adSmrgTORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
269bd392adSmrgSOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
279bd392adSmrg
289bd392adSmrg**************************************************************************/
299bd392adSmrg
309bd392adSmrg/*
319bd392adSmrg * Authors:
329bd392adSmrg *   Kevin E. Martin <martin@valinux.com>
339bd392adSmrg *   Jens Owen <jens@tungstengraphics.com>
349bd392adSmrg *   Rickard E. (Rik) Faith <faith@valinux.com>
359bd392adSmrg *
369bd392adSmrg */
379bd392adSmrg
389bd392adSmrg/* THIS IS NOT AN X CONSORTIUM STANDARD */
399bd392adSmrg
409bd392adSmrg#ifdef HAVE_CONFIG_H
419bd392adSmrg#include "config.h"
429bd392adSmrg#endif
439bd392adSmrg
449bd392adSmrg#include <X11/Xlibint.h>
459bd392adSmrg#include <X11/extensions/Xext.h>
469bd392adSmrg#include <X11/extensions/extutil.h>
479bd392adSmrg#include <stdint.h>
489bd392adSmrg#include "xf86dristr.h"
499bd392adSmrg
509bd392adSmrgstatic XExtensionInfo _xf86dri_info_data;
519bd392adSmrgstatic XExtensionInfo *xf86dri_info = &_xf86dri_info_data;
529bd392adSmrgstatic char xf86dri_extension_name[] = XF86DRINAME;
539bd392adSmrg
549bd392adSmrg#define uniDRICheckExtension(dpy,i,val) \
559bd392adSmrg  XextCheckExtension (dpy, i, xf86dri_extension_name, val)
569bd392adSmrg
579bd392adSmrg/*****************************************************************************
589bd392adSmrg *                                                                           *
599bd392adSmrg *			   private utility routines                          *
609bd392adSmrg *                                                                           *
619bd392adSmrg *****************************************************************************/
629bd392adSmrg
639bd392adSmrgstatic int close_display(Display * dpy, XExtCodes * extCodes);
649bd392adSmrgstatic /* const */ XExtensionHooks xf86dri_extension_hooks = {
659bd392adSmrg    NULL,			       /* create_gc */
669bd392adSmrg    NULL,			       /* copy_gc */
679bd392adSmrg    NULL,			       /* flush_gc */
689bd392adSmrg    NULL,			       /* free_gc */
699bd392adSmrg    NULL,			       /* create_font */
709bd392adSmrg    NULL,			       /* free_font */
719bd392adSmrg    close_display,		       /* close_display */
729bd392adSmrg    NULL,			       /* wire_to_event */
739bd392adSmrg    NULL,			       /* event_to_wire */
749bd392adSmrg    NULL,			       /* error */
759bd392adSmrg    NULL,			       /* error_string */
769bd392adSmrg};
779bd392adSmrg
789bd392adSmrgstatic
799bd392adSmrgXEXT_GENERATE_FIND_DISPLAY(find_display, xf86dri_info,
809bd392adSmrg    xf86dri_extension_name, &xf86dri_extension_hooks, 0, NULL)
819bd392adSmrg
829bd392adSmrg    static XEXT_GENERATE_CLOSE_DISPLAY(close_display, xf86dri_info)
839bd392adSmrg
849bd392adSmrg/*****************************************************************************
859bd392adSmrg *                                                                           *
869bd392adSmrg *		    public XFree86-DRI Extension routines                    *
879bd392adSmrg *                                                                           *
889bd392adSmrg *****************************************************************************/
899bd392adSmrg#if 0
909bd392adSmrg#include <stdio.h>
919bd392adSmrg#define TRACE(msg)  fprintf(stderr,"uniDRI%s\n", msg);
929bd392adSmrg#else
939bd392adSmrg#define TRACE(msg)
949bd392adSmrg#endif
959bd392adSmrg    Bool uniDRIQueryExtension(dpy, event_basep, error_basep)
969bd392adSmrg    Display *dpy;
979bd392adSmrg    int *event_basep, *error_basep;
989bd392adSmrg{
999bd392adSmrg    XExtDisplayInfo *info = find_display(dpy);
1009bd392adSmrg
1019bd392adSmrg    TRACE("QueryExtension...");
1029bd392adSmrg    if (XextHasExtension(info)) {
1039bd392adSmrg	*event_basep = info->codes->first_event;
1049bd392adSmrg	*error_basep = info->codes->first_error;
1059bd392adSmrg	TRACE("QueryExtension... return True");
1069bd392adSmrg	return True;
1079bd392adSmrg    } else {
1089bd392adSmrg	TRACE("QueryExtension... return False");
1099bd392adSmrg	return False;
1109bd392adSmrg    }
1119bd392adSmrg}
1129bd392adSmrg
1139bd392adSmrgBool
1149bd392adSmrguniDRIQueryVersion(dpy, majorVersion, minorVersion, patchVersion)
1159bd392adSmrg    Display *dpy;
1169bd392adSmrg    int *majorVersion;
1179bd392adSmrg    int *minorVersion;
1189bd392adSmrg    int *patchVersion;
1199bd392adSmrg{
1209bd392adSmrg    XExtDisplayInfo *info = find_display(dpy);
1219bd392adSmrg    xXF86DRIQueryVersionReply rep;
1229bd392adSmrg    xXF86DRIQueryVersionReq *req;
1239bd392adSmrg
1249bd392adSmrg    TRACE("QueryVersion...");
1259bd392adSmrg    uniDRICheckExtension(dpy, info, False);
1269bd392adSmrg
1279bd392adSmrg    LockDisplay(dpy);
1289bd392adSmrg    GetReq(XF86DRIQueryVersion, req);
1299bd392adSmrg    req->reqType = info->codes->major_opcode;
1309bd392adSmrg    req->driReqType = X_XF86DRIQueryVersion;
1319bd392adSmrg    if (!_XReply(dpy, (xReply *) & rep, 0, xFalse)) {
1329bd392adSmrg	UnlockDisplay(dpy);
1339bd392adSmrg	SyncHandle();
1349bd392adSmrg	TRACE("QueryVersion... return False");
1359bd392adSmrg	return False;
1369bd392adSmrg    }
1379bd392adSmrg    *majorVersion = rep.majorVersion;
1389bd392adSmrg    *minorVersion = rep.minorVersion;
1399bd392adSmrg    *patchVersion = rep.patchVersion;
1409bd392adSmrg    UnlockDisplay(dpy);
1419bd392adSmrg    SyncHandle();
1429bd392adSmrg    TRACE("QueryVersion... return True");
1439bd392adSmrg    return True;
1449bd392adSmrg}
1459bd392adSmrg
1469bd392adSmrgBool
1479bd392adSmrguniDRIQueryDirectRenderingCapable(dpy, screen, isCapable)
1489bd392adSmrg    Display *dpy;
1499bd392adSmrg    int screen;
1509bd392adSmrg    Bool *isCapable;
1519bd392adSmrg{
1529bd392adSmrg    XExtDisplayInfo *info = find_display(dpy);
1539bd392adSmrg    xXF86DRIQueryDirectRenderingCapableReply rep;
1549bd392adSmrg    xXF86DRIQueryDirectRenderingCapableReq *req;
1559bd392adSmrg
1569bd392adSmrg    TRACE("QueryDirectRenderingCapable...");
1579bd392adSmrg    uniDRICheckExtension(dpy, info, False);
1589bd392adSmrg
1599bd392adSmrg    LockDisplay(dpy);
1609bd392adSmrg    GetReq(XF86DRIQueryDirectRenderingCapable, req);
1619bd392adSmrg    req->reqType = info->codes->major_opcode;
1629bd392adSmrg    req->driReqType = X_XF86DRIQueryDirectRenderingCapable;
1639bd392adSmrg    req->screen = screen;
1649bd392adSmrg    if (!_XReply(dpy, (xReply *) & rep, 0, xFalse)) {
1659bd392adSmrg	UnlockDisplay(dpy);
1669bd392adSmrg	SyncHandle();
1679bd392adSmrg	TRACE("QueryDirectRenderingCapable... return False");
1689bd392adSmrg	return False;
1699bd392adSmrg    }
1709bd392adSmrg    *isCapable = rep.isCapable;
1719bd392adSmrg    UnlockDisplay(dpy);
1729bd392adSmrg    SyncHandle();
1739bd392adSmrg    TRACE("QueryDirectRenderingCapable... return True");
1749bd392adSmrg    return True;
1759bd392adSmrg}
1769bd392adSmrg
1779bd392adSmrgBool
1789bd392adSmrguniDRIOpenConnection(dpy, screen, hSAREA, busIdString)
1799bd392adSmrg    Display *dpy;
1809bd392adSmrg    int screen;
1819bd392adSmrg    drm_handle_t *hSAREA;
1829bd392adSmrg    char **busIdString;
1839bd392adSmrg{
1849bd392adSmrg    XExtDisplayInfo *info = find_display(dpy);
1859bd392adSmrg    xXF86DRIOpenConnectionReply rep;
1869bd392adSmrg    xXF86DRIOpenConnectionReq *req;
1879bd392adSmrg
1889bd392adSmrg    TRACE("OpenConnection...");
1899bd392adSmrg    uniDRICheckExtension(dpy, info, False);
1909bd392adSmrg
1919bd392adSmrg    LockDisplay(dpy);
1929bd392adSmrg    GetReq(XF86DRIOpenConnection, req);
1939bd392adSmrg    req->reqType = info->codes->major_opcode;
1949bd392adSmrg    req->driReqType = X_XF86DRIOpenConnection;
1959bd392adSmrg    req->screen = screen;
1969bd392adSmrg    if (!_XReply(dpy, (xReply *) & rep, 0, xFalse)) {
1979bd392adSmrg	UnlockDisplay(dpy);
1989bd392adSmrg	SyncHandle();
1999bd392adSmrg	TRACE("OpenConnection... return False");
2009bd392adSmrg	return False;
2019bd392adSmrg    }
2029bd392adSmrg
2039bd392adSmrg    *hSAREA = rep.hSAREALow;
2049bd392adSmrg#ifdef LONG64
2059bd392adSmrg    if (sizeof(drm_handle_t) == 8) {
2069bd392adSmrg	*hSAREA |= ((unsigned long)rep.hSAREAHigh) << 32;
2079bd392adSmrg    }
2089bd392adSmrg#endif
2099bd392adSmrg    if (rep.length) {
2109bd392adSmrg	if (!(*busIdString = (char *)Xcalloc(rep.busIdStringLength + 1, 1))) {
2119bd392adSmrg	    _XEatData(dpy, ((rep.busIdStringLength + 3) & ~3));
2129bd392adSmrg	    UnlockDisplay(dpy);
2139bd392adSmrg	    SyncHandle();
2149bd392adSmrg	    TRACE("OpenConnection... return False");
2159bd392adSmrg	    return False;
2169bd392adSmrg	}
2179bd392adSmrg	_XReadPad(dpy, *busIdString, rep.busIdStringLength);
2189bd392adSmrg    } else {
2199bd392adSmrg	*busIdString = NULL;
2209bd392adSmrg    }
2219bd392adSmrg    UnlockDisplay(dpy);
2229bd392adSmrg    SyncHandle();
2239bd392adSmrg    TRACE("OpenConnection... return True");
2249bd392adSmrg    return True;
2259bd392adSmrg}
2269bd392adSmrg
2279bd392adSmrgBool
2289bd392adSmrguniDRIAuthConnection(dpy, screen, magic)
2299bd392adSmrg    Display *dpy;
2309bd392adSmrg    int screen;
2319bd392adSmrg    drm_magic_t magic;
2329bd392adSmrg{
2339bd392adSmrg    XExtDisplayInfo *info = find_display(dpy);
2349bd392adSmrg    xXF86DRIAuthConnectionReq *req;
2359bd392adSmrg    xXF86DRIAuthConnectionReply rep;
2369bd392adSmrg
2379bd392adSmrg    TRACE("AuthConnection...");
2389bd392adSmrg    uniDRICheckExtension(dpy, info, False);
2399bd392adSmrg
2409bd392adSmrg    LockDisplay(dpy);
2419bd392adSmrg    GetReq(XF86DRIAuthConnection, req);
2429bd392adSmrg    req->reqType = info->codes->major_opcode;
2439bd392adSmrg    req->driReqType = X_XF86DRIAuthConnection;
2449bd392adSmrg    req->screen = screen;
2459bd392adSmrg    req->magic = magic;
2469bd392adSmrg    rep.authenticated = 0;
2479bd392adSmrg    if (!_XReply(dpy, (xReply *) & rep, 0, xFalse) || !rep.authenticated) {
2489bd392adSmrg	UnlockDisplay(dpy);
2499bd392adSmrg	SyncHandle();
2509bd392adSmrg	TRACE("AuthConnection... return False");
2519bd392adSmrg	return False;
2529bd392adSmrg    }
2539bd392adSmrg    UnlockDisplay(dpy);
2549bd392adSmrg    SyncHandle();
2559bd392adSmrg    TRACE("AuthConnection... return True");
2569bd392adSmrg    return True;
2579bd392adSmrg}
2589bd392adSmrg
2599bd392adSmrgBool
2609bd392adSmrguniDRICloseConnection(dpy, screen)
2619bd392adSmrg    Display *dpy;
2629bd392adSmrg    int screen;
2639bd392adSmrg{
2649bd392adSmrg    XExtDisplayInfo *info = find_display(dpy);
2659bd392adSmrg    xXF86DRICloseConnectionReq *req;
2669bd392adSmrg
2679bd392adSmrg    TRACE("CloseConnection...");
2689bd392adSmrg
2699bd392adSmrg    uniDRICheckExtension(dpy, info, False);
2709bd392adSmrg
2719bd392adSmrg    LockDisplay(dpy);
2729bd392adSmrg    GetReq(XF86DRICloseConnection, req);
2739bd392adSmrg    req->reqType = info->codes->major_opcode;
2749bd392adSmrg    req->driReqType = X_XF86DRICloseConnection;
2759bd392adSmrg    req->screen = screen;
2769bd392adSmrg    UnlockDisplay(dpy);
2779bd392adSmrg    SyncHandle();
2789bd392adSmrg    TRACE("CloseConnection... return True");
2799bd392adSmrg    return True;
2809bd392adSmrg}
2819bd392adSmrg
2829bd392adSmrgBool
2839bd392adSmrguniDRIGetClientDriverName(dpy, screen, ddxDriverMajorVersion,
2849bd392adSmrg    ddxDriverMinorVersion, ddxDriverPatchVersion, clientDriverName)
2859bd392adSmrg    Display *dpy;
2869bd392adSmrg    int screen;
2879bd392adSmrg    int *ddxDriverMajorVersion;
2889bd392adSmrg    int *ddxDriverMinorVersion;
2899bd392adSmrg    int *ddxDriverPatchVersion;
2909bd392adSmrg    char **clientDriverName;
2919bd392adSmrg{
2929bd392adSmrg    XExtDisplayInfo *info = find_display(dpy);
2939bd392adSmrg    xXF86DRIGetClientDriverNameReply rep;
2949bd392adSmrg    xXF86DRIGetClientDriverNameReq *req;
2959bd392adSmrg
2969bd392adSmrg    TRACE("GetClientDriverName...");
2979bd392adSmrg    uniDRICheckExtension(dpy, info, False);
2989bd392adSmrg
2999bd392adSmrg    LockDisplay(dpy);
3009bd392adSmrg    GetReq(XF86DRIGetClientDriverName, req);
3019bd392adSmrg    req->reqType = info->codes->major_opcode;
3029bd392adSmrg    req->driReqType = X_XF86DRIGetClientDriverName;
3039bd392adSmrg    req->screen = screen;
3049bd392adSmrg    if (!_XReply(dpy, (xReply *) & rep, 0, xFalse)) {
3059bd392adSmrg	UnlockDisplay(dpy);
3069bd392adSmrg	SyncHandle();
3079bd392adSmrg	TRACE("GetClientDriverName... return False");
3089bd392adSmrg	return False;
3099bd392adSmrg    }
3109bd392adSmrg
3119bd392adSmrg    *ddxDriverMajorVersion = rep.ddxDriverMajorVersion;
3129bd392adSmrg    *ddxDriverMinorVersion = rep.ddxDriverMinorVersion;
3139bd392adSmrg    *ddxDriverPatchVersion = rep.ddxDriverPatchVersion;
3149bd392adSmrg
3159bd392adSmrg    if (rep.length) {
3169bd392adSmrg	if (!(*clientDriverName =
3179bd392adSmrg		(char *)Xcalloc(rep.clientDriverNameLength + 1, 1))) {
3189bd392adSmrg	    _XEatData(dpy, ((rep.clientDriverNameLength + 3) & ~3));
3199bd392adSmrg	    UnlockDisplay(dpy);
3209bd392adSmrg	    SyncHandle();
3219bd392adSmrg	    TRACE("GetClientDriverName... return False");
3229bd392adSmrg	    return False;
3239bd392adSmrg	}
3249bd392adSmrg	_XReadPad(dpy, *clientDriverName, rep.clientDriverNameLength);
3259bd392adSmrg    } else {
3269bd392adSmrg	*clientDriverName = NULL;
3279bd392adSmrg    }
3289bd392adSmrg    UnlockDisplay(dpy);
3299bd392adSmrg    SyncHandle();
3309bd392adSmrg    TRACE("GetClientDriverName... return True");
3319bd392adSmrg    return True;
3329bd392adSmrg}
3339bd392adSmrg
3349bd392adSmrgBool
3359bd392adSmrguniDRICreateContextWithConfig(dpy, screen, configID, context, hHWContext)
3369bd392adSmrg    Display *dpy;
3379bd392adSmrg    int screen;
3389bd392adSmrg    int configID;
3399bd392adSmrg    XID *context;
3409bd392adSmrg    drm_context_t *hHWContext;
3419bd392adSmrg{
3429bd392adSmrg    XExtDisplayInfo *info = find_display(dpy);
3439bd392adSmrg    xXF86DRICreateContextReply rep;
3449bd392adSmrg    xXF86DRICreateContextReq *req;
3459bd392adSmrg
3469bd392adSmrg    TRACE("CreateContext...");
3479bd392adSmrg    uniDRICheckExtension(dpy, info, False);
3489bd392adSmrg
3499bd392adSmrg    LockDisplay(dpy);
3509bd392adSmrg    GetReq(XF86DRICreateContext, req);
3519bd392adSmrg    req->reqType = info->codes->major_opcode;
3529bd392adSmrg    req->driReqType = X_XF86DRICreateContext;
3539bd392adSmrg    req->visual = configID;
3549bd392adSmrg    req->screen = screen;
3559bd392adSmrg    *context = XAllocID(dpy);
3569bd392adSmrg    req->context = *context;
3579bd392adSmrg    if (!_XReply(dpy, (xReply *) & rep, 0, xFalse)) {
3589bd392adSmrg	UnlockDisplay(dpy);
3599bd392adSmrg	SyncHandle();
3609bd392adSmrg	TRACE("CreateContext... return False");
3619bd392adSmrg	return False;
3629bd392adSmrg    }
3639bd392adSmrg    *hHWContext = rep.hHWContext;
3649bd392adSmrg    UnlockDisplay(dpy);
3659bd392adSmrg    SyncHandle();
3669bd392adSmrg    TRACE("CreateContext... return True");
3679bd392adSmrg    return True;
3689bd392adSmrg}
3699bd392adSmrg
3709bd392adSmrgBool
3719bd392adSmrguniDRICreateContext(dpy, screen, visual, context, hHWContext)
3729bd392adSmrg    Display *dpy;
3739bd392adSmrg    int screen;
3749bd392adSmrg    Visual *visual;
3759bd392adSmrg    XID *context;
3769bd392adSmrg    drm_context_t *hHWContext;
3779bd392adSmrg{
3789bd392adSmrg    return uniDRICreateContextWithConfig(dpy, screen, visual->visualid,
3799bd392adSmrg	context, hHWContext);
3809bd392adSmrg}
3819bd392adSmrg
3829bd392adSmrgBool
3839bd392adSmrguniDRIDestroyContext(Display * ndpy, int screen, XID context)
3849bd392adSmrg{
3859bd392adSmrg    Display *const dpy = (Display *) ndpy;
3869bd392adSmrg    XExtDisplayInfo *info = find_display(dpy);
3879bd392adSmrg    xXF86DRIDestroyContextReq *req;
3889bd392adSmrg
3899bd392adSmrg    TRACE("DestroyContext...");
3909bd392adSmrg    uniDRICheckExtension(dpy, info, False);
3919bd392adSmrg
3929bd392adSmrg    LockDisplay(dpy);
3939bd392adSmrg    GetReq(XF86DRIDestroyContext, req);
3949bd392adSmrg    req->reqType = info->codes->major_opcode;
3959bd392adSmrg    req->driReqType = X_XF86DRIDestroyContext;
3969bd392adSmrg    req->screen = screen;
3979bd392adSmrg    req->context = context;
3989bd392adSmrg    UnlockDisplay(dpy);
3999bd392adSmrg    SyncHandle();
4009bd392adSmrg    TRACE("DestroyContext... return True");
4019bd392adSmrg    return True;
4029bd392adSmrg}
4039bd392adSmrg
4049bd392adSmrgBool
4059bd392adSmrguniDRICreateDrawable(Display * ndpy, int screen,
4069bd392adSmrg    Drawable drawable, drm_drawable_t * hHWDrawable)
4079bd392adSmrg{
4089bd392adSmrg    Display *const dpy = (Display *) ndpy;
4099bd392adSmrg    XExtDisplayInfo *info = find_display(dpy);
4109bd392adSmrg    xXF86DRICreateDrawableReply rep;
4119bd392adSmrg    xXF86DRICreateDrawableReq *req;
4129bd392adSmrg
4139bd392adSmrg    TRACE("CreateDrawable...");
4149bd392adSmrg    uniDRICheckExtension(dpy, info, False);
4159bd392adSmrg
4169bd392adSmrg    LockDisplay(dpy);
4179bd392adSmrg    GetReq(XF86DRICreateDrawable, req);
4189bd392adSmrg    req->reqType = info->codes->major_opcode;
4199bd392adSmrg    req->driReqType = X_XF86DRICreateDrawable;
4209bd392adSmrg    req->screen = screen;
4219bd392adSmrg    req->drawable = drawable;
4229bd392adSmrg    if (!_XReply(dpy, (xReply *) & rep, 0, xFalse)) {
4239bd392adSmrg	UnlockDisplay(dpy);
4249bd392adSmrg	SyncHandle();
4259bd392adSmrg	TRACE("CreateDrawable... return False");
4269bd392adSmrg	return False;
4279bd392adSmrg    }
4289bd392adSmrg    *hHWDrawable = rep.hHWDrawable;
4299bd392adSmrg    UnlockDisplay(dpy);
4309bd392adSmrg    SyncHandle();
4319bd392adSmrg    TRACE("CreateDrawable... return True");
4329bd392adSmrg    return True;
4339bd392adSmrg}
4349bd392adSmrg
4359bd392adSmrgBool
4369bd392adSmrguniDRIDestroyDrawable(Display * ndpy, int screen, Drawable drawable)
4379bd392adSmrg{
4389bd392adSmrg    Display *const dpy = (Display *) ndpy;
4399bd392adSmrg    XExtDisplayInfo *info = find_display(dpy);
4409bd392adSmrg    xXF86DRIDestroyDrawableReq *req;
4419bd392adSmrg
4429bd392adSmrg    TRACE("DestroyDrawable...");
4439bd392adSmrg    uniDRICheckExtension(dpy, info, False);
4449bd392adSmrg
4459bd392adSmrg    LockDisplay(dpy);
4469bd392adSmrg    GetReq(XF86DRIDestroyDrawable, req);
4479bd392adSmrg    req->reqType = info->codes->major_opcode;
4489bd392adSmrg    req->driReqType = X_XF86DRIDestroyDrawable;
4499bd392adSmrg    req->screen = screen;
4509bd392adSmrg    req->drawable = drawable;
4519bd392adSmrg    UnlockDisplay(dpy);
4529bd392adSmrg    SyncHandle();
4539bd392adSmrg    TRACE("DestroyDrawable... return True");
4549bd392adSmrg    return True;
4559bd392adSmrg}
4569bd392adSmrg
4579bd392adSmrgBool
4589bd392adSmrguniDRIGetDrawableInfo(Display * dpy, int screen, Drawable drawable,
4599bd392adSmrg    unsigned int *index, unsigned int *stamp,
4609bd392adSmrg    int *X, int *Y, int *W, int *H,
4619bd392adSmrg    int *numClipRects, drm_clip_rect_t ** pClipRects,
4629bd392adSmrg    int *backX, int *backY,
4639bd392adSmrg    int *numBackClipRects, drm_clip_rect_t ** pBackClipRects)
4649bd392adSmrg{
4659bd392adSmrg    XExtDisplayInfo *info = find_display(dpy);
4669bd392adSmrg    xXF86DRIGetDrawableInfoReply rep;
4679bd392adSmrg    xXF86DRIGetDrawableInfoReq *req;
4689bd392adSmrg    int total_rects;
4699bd392adSmrg
4709bd392adSmrg    TRACE("GetDrawableInfo...");
4719bd392adSmrg    uniDRICheckExtension(dpy, info, False);
4729bd392adSmrg
4739bd392adSmrg    LockDisplay(dpy);
4749bd392adSmrg    GetReq(XF86DRIGetDrawableInfo, req);
4759bd392adSmrg    req->reqType = info->codes->major_opcode;
4769bd392adSmrg    req->driReqType = X_XF86DRIGetDrawableInfo;
4779bd392adSmrg    req->screen = screen;
4789bd392adSmrg    req->drawable = drawable;
4799bd392adSmrg
4809bd392adSmrg    if (!_XReply(dpy, (xReply *) & rep, 1, xFalse)) {
4819bd392adSmrg	UnlockDisplay(dpy);
4829bd392adSmrg	SyncHandle();
4839bd392adSmrg	TRACE("GetDrawableInfo... return False");
4849bd392adSmrg	return False;
4859bd392adSmrg    }
4869bd392adSmrg    *index = rep.drawableTableIndex;
4879bd392adSmrg    *stamp = rep.drawableTableStamp;
4889bd392adSmrg    *X = (int)rep.drawableX;
4899bd392adSmrg    *Y = (int)rep.drawableY;
4909bd392adSmrg    *W = (int)rep.drawableWidth;
4919bd392adSmrg    *H = (int)rep.drawableHeight;
4929bd392adSmrg    *numClipRects = rep.numClipRects;
4939bd392adSmrg    total_rects = *numClipRects;
4949bd392adSmrg
4959bd392adSmrg    *backX = rep.backX;
4969bd392adSmrg    *backY = rep.backY;
4979bd392adSmrg    *numBackClipRects = rep.numBackClipRects;
4989bd392adSmrg    total_rects += *numBackClipRects;
4999bd392adSmrg
5009bd392adSmrg#if 0
5019bd392adSmrg    /* Because of the fix in Xserver/GL/dri/xf86dri.c, this check breaks
5029bd392adSmrg     * backwards compatibility (Because of the >> 2 shift) but the fix
5039bd392adSmrg     * enables multi-threaded apps to work.
5049bd392adSmrg     */
5059bd392adSmrg    if (rep.length != ((((SIZEOF(xXF86DRIGetDrawableInfoReply) -
5069bd392adSmrg			SIZEOF(xGenericReply) +
5079bd392adSmrg			total_rects * sizeof(drm_clip_rect_t)) +
5089bd392adSmrg		    3) & ~3) >> 2)) {
5099bd392adSmrg	_XEatData(dpy, rep.length);
5109bd392adSmrg	UnlockDisplay(dpy);
5119bd392adSmrg	SyncHandle();
5129bd392adSmrg	TRACE("GetDrawableInfo... return False");
5139bd392adSmrg	return False;
5149bd392adSmrg    }
5159bd392adSmrg#endif
5169bd392adSmrg
5179bd392adSmrg    if (*numClipRects) {
5189bd392adSmrg	int len = sizeof(drm_clip_rect_t) * (*numClipRects);
5199bd392adSmrg
5209bd392adSmrg	*pClipRects = (drm_clip_rect_t *) Xcalloc(len, 1);
5219bd392adSmrg	if (*pClipRects)
5229bd392adSmrg	    _XRead(dpy, (char *)*pClipRects, len);
5239bd392adSmrg    } else {
5249bd392adSmrg	*pClipRects = NULL;
5259bd392adSmrg    }
5269bd392adSmrg
5279bd392adSmrg    if (*numBackClipRects) {
5289bd392adSmrg	int len = sizeof(drm_clip_rect_t) * (*numBackClipRects);
5299bd392adSmrg
5309bd392adSmrg	*pBackClipRects = (drm_clip_rect_t *) Xcalloc(len, 1);
5319bd392adSmrg	if (*pBackClipRects)
5329bd392adSmrg	    _XRead(dpy, (char *)*pBackClipRects, len);
5339bd392adSmrg    } else {
5349bd392adSmrg	*pBackClipRects = NULL;
5359bd392adSmrg    }
5369bd392adSmrg
5379bd392adSmrg    UnlockDisplay(dpy);
5389bd392adSmrg    SyncHandle();
5399bd392adSmrg    TRACE("GetDrawableInfo... return True");
5409bd392adSmrg    return True;
5419bd392adSmrg}
5429bd392adSmrg
5439bd392adSmrgBool
5449bd392adSmrguniDRIGetDeviceInfo(dpy, screen, hFrameBuffer,
5459bd392adSmrg    fbOrigin, fbSize, fbStride, devPrivateSize, pDevPrivate)
5469bd392adSmrg    Display *dpy;
5479bd392adSmrg    int screen;
5489bd392adSmrg    drm_handle_t *hFrameBuffer;
5499bd392adSmrg    int *fbOrigin;
5509bd392adSmrg    int *fbSize;
5519bd392adSmrg    int *fbStride;
5529bd392adSmrg    int *devPrivateSize;
5539bd392adSmrg    void **pDevPrivate;
5549bd392adSmrg{
5559bd392adSmrg    XExtDisplayInfo *info = find_display(dpy);
5569bd392adSmrg    xXF86DRIGetDeviceInfoReply rep;
5579bd392adSmrg    xXF86DRIGetDeviceInfoReq *req;
5589bd392adSmrg
5599bd392adSmrg    TRACE("GetDeviceInfo...");
5609bd392adSmrg    uniDRICheckExtension(dpy, info, False);
5619bd392adSmrg
5629bd392adSmrg    LockDisplay(dpy);
5639bd392adSmrg    GetReq(XF86DRIGetDeviceInfo, req);
5649bd392adSmrg    req->reqType = info->codes->major_opcode;
5659bd392adSmrg    req->driReqType = X_XF86DRIGetDeviceInfo;
5669bd392adSmrg    req->screen = screen;
5679bd392adSmrg    if (!_XReply(dpy, (xReply *) & rep, 0, xFalse)) {
5689bd392adSmrg	UnlockDisplay(dpy);
5699bd392adSmrg	SyncHandle();
5709bd392adSmrg	TRACE("GetDeviceInfo... return False");
5719bd392adSmrg	return False;
5729bd392adSmrg    }
5739bd392adSmrg
5749bd392adSmrg    *hFrameBuffer = rep.hFrameBufferLow;
5759bd392adSmrg#ifdef LONG64
5769bd392adSmrg    if (sizeof(drm_handle_t) == 8) {
5779bd392adSmrg	*hFrameBuffer |= ((unsigned long)rep.hFrameBufferHigh) << 32;
5789bd392adSmrg    }
5799bd392adSmrg#endif
5809bd392adSmrg
5819bd392adSmrg    *fbOrigin = rep.framebufferOrigin;
5829bd392adSmrg    *fbSize = rep.framebufferSize;
5839bd392adSmrg    *fbStride = rep.framebufferStride;
5849bd392adSmrg    *devPrivateSize = rep.devPrivateSize;
5859bd392adSmrg
5869bd392adSmrg    if (rep.length) {
5879bd392adSmrg	if (!(*pDevPrivate = (void *)Xcalloc(rep.devPrivateSize, 1))) {
5889bd392adSmrg	    _XEatData(dpy, ((rep.devPrivateSize + 3) & ~3));
5899bd392adSmrg	    UnlockDisplay(dpy);
5909bd392adSmrg	    SyncHandle();
5919bd392adSmrg	    TRACE("GetDeviceInfo... return False");
5929bd392adSmrg	    return False;
5939bd392adSmrg	}
5949bd392adSmrg	_XRead(dpy, (char *)*pDevPrivate, rep.devPrivateSize);
5959bd392adSmrg    } else {
5969bd392adSmrg	*pDevPrivate = NULL;
5979bd392adSmrg    }
5989bd392adSmrg
5999bd392adSmrg    UnlockDisplay(dpy);
6009bd392adSmrg    SyncHandle();
6019bd392adSmrg    TRACE("GetDeviceInfo... return True");
6029bd392adSmrg    return True;
6039bd392adSmrg}
604