backport some code from mesa current (and 7.5) so that the dri2 protocol
is correctly handled. without fixes to mesa and the ddx, the so-called backwards compat goop that was added just plain does not work and ends up with rendering bullshit.
This commit is contained in:
parent
11a94b33b4
commit
9997d7a073
39
dist/Mesa/include/GL/internal/dri_interface.h
vendored
39
dist/Mesa/include/GL/internal/dri_interface.h
vendored
@ -78,6 +78,7 @@ typedef struct __DRIswrastExtensionRec __DRIswrastExtension;
|
||||
typedef struct __DRIbufferRec __DRIbuffer;
|
||||
typedef struct __DRIdri2ExtensionRec __DRIdri2Extension;
|
||||
typedef struct __DRIdri2LoaderExtensionRec __DRIdri2LoaderExtension;
|
||||
typedef struct __DRI2flushExtensionRec __DRI2flushExtension;
|
||||
|
||||
/*@}*/
|
||||
|
||||
@ -245,6 +246,16 @@ struct __DRItexBufferExtensionRec {
|
||||
__DRIdrawable *pDraw);
|
||||
};
|
||||
|
||||
/**
|
||||
* Used by drivers that implement DRI2
|
||||
*/
|
||||
#define __DRI2_FLUSH "DRI2_Flush"
|
||||
#define __DRI2_FLUSH_VERSION 1
|
||||
struct __DRI2flushExtensionRec {
|
||||
__DRIextension base;
|
||||
void (*flush)(__DRIdrawable *drawable);
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* XML document describing the configuration options supported by the
|
||||
@ -626,6 +637,7 @@ struct __DRIswrastExtensionRec {
|
||||
#define __DRI_BUFFER_ACCUM 6
|
||||
#define __DRI_BUFFER_FAKE_FRONT_LEFT 7
|
||||
#define __DRI_BUFFER_FAKE_FRONT_RIGHT 8
|
||||
#define __DRI_BUFFER_DEPTH_STENCIL 9 /**< Only available with DRI2 1.1 */
|
||||
|
||||
struct __DRIbufferRec {
|
||||
unsigned int attachment;
|
||||
@ -636,7 +648,7 @@ struct __DRIbufferRec {
|
||||
};
|
||||
|
||||
#define __DRI_DRI2_LOADER "DRI_DRI2Loader"
|
||||
#define __DRI_DRI2_LOADER_VERSION 2
|
||||
#define __DRI_DRI2_LOADER_VERSION 3
|
||||
struct __DRIdri2LoaderExtensionRec {
|
||||
__DRIextension base;
|
||||
|
||||
@ -657,6 +669,31 @@ struct __DRIdri2LoaderExtensionRec {
|
||||
* into __DRIdri2ExtensionRec::createNewDrawable
|
||||
*/
|
||||
void (*flushFrontBuffer)(__DRIdrawable *driDrawable, void *loaderPrivate);
|
||||
|
||||
|
||||
/**
|
||||
* Get list of buffers from the server
|
||||
*
|
||||
* Gets a list of buffer for the specified set of attachments. Unlike
|
||||
* \c ::getBuffers, this function takes a list of attachments paired with
|
||||
* opaque \c unsigned \c int value describing the format of the buffer.
|
||||
* It is the responsibility of the caller to know what the service that
|
||||
* allocates the buffers will expect to receive for the format.
|
||||
*
|
||||
* \param driDrawable Drawable whose buffers are being queried.
|
||||
* \param width Output where the width of the buffers is stored.
|
||||
* \param height Output where the height of the buffers is stored.
|
||||
* \param attachments List of pairs of attachment ID and opaque format
|
||||
* requested for the drawable.
|
||||
* \param count Number of attachment / format pairs stored in
|
||||
* \c attachments.
|
||||
* \param loaderPrivate Loader's private data that was previously passed
|
||||
* into __DRIdri2ExtensionRec::createNewDrawable.
|
||||
*/
|
||||
__DRIbuffer *(*getBuffersWithFormat)(__DRIdrawable *driDrawable,
|
||||
int *width, int *height,
|
||||
unsigned int *attachments, int count,
|
||||
int *out_count, void *loaderPrivate);
|
||||
};
|
||||
|
||||
/**
|
||||
|
70
dist/Mesa/src/glx/x11/dri2.c
vendored
70
dist/Mesa/src/glx/x11/dri2.c
vendored
@ -39,6 +39,16 @@
|
||||
#include "xf86drm.h"
|
||||
#include "dri2.h"
|
||||
|
||||
/* Allow the build to work with an older versions of dri2proto.h and
|
||||
* dri2tokens.h.
|
||||
*/
|
||||
#if DRI2_MINOR < 1
|
||||
#undef DRI2_MINOR
|
||||
#define DRI2_MINOR 1
|
||||
#define X_DRI2GetBuffersWithFormat 7
|
||||
#endif
|
||||
|
||||
|
||||
static char dri2ExtensionName[] = DRI2_NAME;
|
||||
static XExtensionInfo *dri2Info;
|
||||
static XEXT_GENERATE_CLOSE_DISPLAY (DRI2CloseDisplay, dri2Info)
|
||||
@ -276,6 +286,66 @@ DRI2Buffer *DRI2GetBuffers(Display *dpy, XID drawable,
|
||||
return buffers;
|
||||
}
|
||||
|
||||
|
||||
DRI2Buffer *DRI2GetBuffersWithFormat(Display *dpy, XID drawable,
|
||||
int *width, int *height,
|
||||
unsigned int *attachments, int count,
|
||||
int *outCount)
|
||||
{
|
||||
XExtDisplayInfo *info = DRI2FindDisplay(dpy);
|
||||
xDRI2GetBuffersReply rep;
|
||||
xDRI2GetBuffersReq *req;
|
||||
DRI2Buffer *buffers;
|
||||
xDRI2Buffer repBuffer;
|
||||
CARD32 *p;
|
||||
int i;
|
||||
|
||||
XextCheckExtension (dpy, info, dri2ExtensionName, False);
|
||||
|
||||
LockDisplay(dpy);
|
||||
GetReqExtra(DRI2GetBuffers, count * (4 * 2), req);
|
||||
req->reqType = info->codes->major_opcode;
|
||||
req->dri2ReqType = X_DRI2GetBuffersWithFormat;
|
||||
req->drawable = drawable;
|
||||
req->count = count;
|
||||
p = (CARD32 *) &req[1];
|
||||
for (i = 0; i < (count * 2); i++)
|
||||
p[i] = attachments[i];
|
||||
|
||||
if (!_XReply(dpy, (xReply *)&rep, 0, xFalse)) {
|
||||
UnlockDisplay(dpy);
|
||||
SyncHandle();
|
||||
return NULL;
|
||||
}
|
||||
|
||||
*width = rep.width;
|
||||
*height = rep.height;
|
||||
*outCount = rep.count;
|
||||
|
||||
buffers = Xmalloc(rep.count * sizeof buffers[0]);
|
||||
if (buffers == NULL) {
|
||||
_XEatData(dpy, rep.count * sizeof repBuffer);
|
||||
UnlockDisplay(dpy);
|
||||
SyncHandle();
|
||||
return NULL;
|
||||
}
|
||||
|
||||
for (i = 0; i < rep.count; i++) {
|
||||
_XReadPad(dpy, (char *) &repBuffer, sizeof repBuffer);
|
||||
buffers[i].attachment = repBuffer.attachment;
|
||||
buffers[i].name = repBuffer.name;
|
||||
buffers[i].pitch = repBuffer.pitch;
|
||||
buffers[i].cpp = repBuffer.cpp;
|
||||
buffers[i].flags = repBuffer.flags;
|
||||
}
|
||||
|
||||
UnlockDisplay(dpy);
|
||||
SyncHandle();
|
||||
|
||||
return buffers;
|
||||
}
|
||||
|
||||
|
||||
void DRI2CopyRegion(Display *dpy, XID drawable, XserverRegion region,
|
||||
CARD32 dest, CARD32 src)
|
||||
{
|
||||
|
10
dist/Mesa/src/glx/x11/dri2.h
vendored
10
dist/Mesa/src/glx/x11/dri2.h
vendored
@ -63,6 +63,16 @@ DRI2GetBuffers(Display *dpy, XID drawable,
|
||||
unsigned int *attachments, int count,
|
||||
int *outCount);
|
||||
|
||||
/**
|
||||
* \note
|
||||
* This function is only supported with DRI2 version 1.1 or later.
|
||||
*/
|
||||
extern DRI2Buffer *
|
||||
DRI2GetBuffersWithFormat(Display *dpy, XID drawable,
|
||||
int *width, int *height,
|
||||
unsigned int *attachments, int count,
|
||||
int *outCount);
|
||||
|
||||
extern void
|
||||
DRI2CopyRegion(Display *dpy, XID drawable, XserverRegion region,
|
||||
CARD32 dest, CARD32 src);
|
||||
|
139
dist/Mesa/src/glx/x11/dri2_glx.c
vendored
139
dist/Mesa/src/glx/x11/dri2_glx.c
vendored
@ -47,6 +47,9 @@
|
||||
#include "dri2.h"
|
||||
#include "dri_common.h"
|
||||
|
||||
#undef DRI2_MINOR
|
||||
#define DRI2_MINOR 1
|
||||
|
||||
typedef struct __GLXDRIdisplayPrivateRec __GLXDRIdisplayPrivate;
|
||||
typedef struct __GLXDRIcontextPrivateRec __GLXDRIcontextPrivate;
|
||||
typedef struct __GLXDRIdrawablePrivateRec __GLXDRIdrawablePrivate;
|
||||
@ -77,6 +80,8 @@ struct __GLXDRIdrawablePrivateRec {
|
||||
int have_fake_front;
|
||||
};
|
||||
|
||||
static void dri2WaitX(__GLXDRIdrawable *pdraw);
|
||||
|
||||
static void dri2DestroyContext(__GLXDRIcontext *context,
|
||||
__GLXscreenConfigs *psc, Display *dpy)
|
||||
{
|
||||
@ -202,10 +207,21 @@ static void dri2CopySubBuffer(__GLXDRIdrawable *pdraw,
|
||||
xrect.width = width;
|
||||
xrect.height = height;
|
||||
|
||||
#ifdef __DRI2_FLUSH
|
||||
if (pdraw->psc->f)
|
||||
(*pdraw->psc->f->flush)(pdraw->driDrawable);
|
||||
#endif
|
||||
|
||||
region = XFixesCreateRegion(pdraw->psc->dpy, &xrect, 1);
|
||||
/* should get a fence ID back from here at some point */
|
||||
DRI2CopyRegion(pdraw->psc->dpy, pdraw->drawable, region,
|
||||
DRI2BufferFrontLeft, DRI2BufferBackLeft);
|
||||
XFixesDestroyRegion(pdraw->psc->dpy, region);
|
||||
|
||||
/* Refresh the fake front (if present) after we just damaged the real
|
||||
* front.
|
||||
*/
|
||||
dri2WaitX(pdraw);
|
||||
}
|
||||
|
||||
static void dri2SwapBuffers(__GLXDRIdrawable *pdraw)
|
||||
@ -230,6 +246,11 @@ static void dri2WaitX(__GLXDRIdrawable *pdraw)
|
||||
xrect.width = priv->width;
|
||||
xrect.height = priv->height;
|
||||
|
||||
#ifdef __DRI2_FLUSH
|
||||
if (pdraw->psc->f)
|
||||
(*pdraw->psc->f->flush)(pdraw->driDrawable);
|
||||
#endif
|
||||
|
||||
region = XFixesCreateRegion(pdraw->psc->dpy, &xrect, 1);
|
||||
DRI2CopyRegion(pdraw->psc->dpy, pdraw->drawable, region,
|
||||
DRI2BufferFakeFrontLeft, DRI2BufferFrontLeft);
|
||||
@ -250,6 +271,11 @@ static void dri2WaitGL(__GLXDRIdrawable *pdraw)
|
||||
xrect.width = priv->width;
|
||||
xrect.height = priv->height;
|
||||
|
||||
#ifdef __DRI2_FLUSH
|
||||
if (pdraw->psc->f)
|
||||
(*pdraw->psc->f->flush)(pdraw->driDrawable);
|
||||
#endif
|
||||
|
||||
region = XFixesCreateRegion(pdraw->psc->dpy, &xrect, 1);
|
||||
DRI2CopyRegion(pdraw->psc->dpy, pdraw->drawable, region,
|
||||
DRI2BufferFrontLeft, DRI2BufferFakeFrontLeft);
|
||||
@ -273,30 +299,25 @@ static void dri2DestroyScreen(__GLXscreenConfigs *psc)
|
||||
psc->__driScreen = NULL;
|
||||
}
|
||||
|
||||
static __DRIbuffer *
|
||||
dri2GetBuffers(__DRIdrawable *driDrawable,
|
||||
int *width, int *height,
|
||||
unsigned int *attachments, int count,
|
||||
int *out_count, void *loaderPrivate)
|
||||
/**
|
||||
* Process list of buffer received from the server
|
||||
*
|
||||
* Processes the list of buffers received in a reply from the server to either
|
||||
* \c DRI2GetBuffers or \c DRI2GetBuffersWithFormat.
|
||||
*/
|
||||
static void
|
||||
process_buffers(__GLXDRIdrawablePrivate *pdraw, DRI2Buffer *buffers,
|
||||
unsigned count)
|
||||
{
|
||||
__GLXDRIdrawablePrivate *pdraw = loaderPrivate;
|
||||
DRI2Buffer *buffers;
|
||||
int i;
|
||||
|
||||
buffers = DRI2GetBuffers(pdraw->base.psc->dpy, pdraw->base.xDrawable,
|
||||
width, height, attachments, count, out_count);
|
||||
if (buffers == NULL)
|
||||
return NULL;
|
||||
|
||||
pdraw->width = *width;
|
||||
pdraw->height = *height;
|
||||
pdraw->bufferCount = *out_count;
|
||||
pdraw->bufferCount = count;
|
||||
pdraw->have_fake_front = 0;
|
||||
pdraw->have_back = 0;
|
||||
|
||||
/* This assumes the DRI2 buffer attachment tokens matches the
|
||||
* __DRIbuffer tokens. */
|
||||
for (i = 0; i < *out_count; i++) {
|
||||
for (i = 0; i < count; i++) {
|
||||
pdraw->buffers[i].attachment = buffers[i].attachment;
|
||||
pdraw->buffers[i].name = buffers[i].name;
|
||||
pdraw->buffers[i].pitch = buffers[i].pitch;
|
||||
@ -308,6 +329,51 @@ dri2GetBuffers(__DRIdrawable *driDrawable,
|
||||
pdraw->have_back = 1;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
static __DRIbuffer *
|
||||
dri2GetBuffers(__DRIdrawable *driDrawable,
|
||||
int *width, int *height,
|
||||
unsigned int *attachments, int count,
|
||||
int *out_count, void *loaderPrivate)
|
||||
{
|
||||
__GLXDRIdrawablePrivate *pdraw = loaderPrivate;
|
||||
DRI2Buffer *buffers;
|
||||
|
||||
buffers = DRI2GetBuffers(pdraw->base.psc->dpy, pdraw->base.xDrawable,
|
||||
width, height, attachments, count, out_count);
|
||||
if (buffers == NULL)
|
||||
return NULL;
|
||||
|
||||
pdraw->width = *width;
|
||||
pdraw->height = *height;
|
||||
process_buffers(pdraw, buffers, *out_count);
|
||||
|
||||
Xfree(buffers);
|
||||
|
||||
return pdraw->buffers;
|
||||
}
|
||||
|
||||
static __DRIbuffer *
|
||||
dri2GetBuffersWithFormat(__DRIdrawable *driDrawable,
|
||||
int *width, int *height,
|
||||
unsigned int *attachments, int count,
|
||||
int *out_count, void *loaderPrivate)
|
||||
{
|
||||
__GLXDRIdrawablePrivate *pdraw = loaderPrivate;
|
||||
DRI2Buffer *buffers;
|
||||
|
||||
buffers = DRI2GetBuffersWithFormat(pdraw->base.psc->dpy,
|
||||
pdraw->base.xDrawable,
|
||||
width, height, attachments,
|
||||
count, out_count);
|
||||
if (buffers == NULL)
|
||||
return NULL;
|
||||
|
||||
pdraw->width = *width;
|
||||
pdraw->height = *height;
|
||||
process_buffers(pdraw, buffers, *out_count);
|
||||
|
||||
Xfree(buffers);
|
||||
|
||||
return pdraw->buffers;
|
||||
@ -316,7 +382,15 @@ dri2GetBuffers(__DRIdrawable *driDrawable,
|
||||
static const __DRIdri2LoaderExtension dri2LoaderExtension = {
|
||||
{ __DRI_DRI2_LOADER, __DRI_DRI2_LOADER_VERSION },
|
||||
dri2GetBuffers,
|
||||
dri2FlushFrontBuffer
|
||||
dri2FlushFrontBuffer,
|
||||
dri2GetBuffersWithFormat,
|
||||
};
|
||||
|
||||
static const __DRIdri2LoaderExtension dri2LoaderExtension_old = {
|
||||
{ __DRI_DRI2_LOADER, __DRI_DRI2_LOADER_VERSION },
|
||||
dri2GetBuffers,
|
||||
dri2FlushFrontBuffer,
|
||||
NULL,
|
||||
};
|
||||
|
||||
static const __DRIextension *loader_extensions[] = {
|
||||
@ -325,11 +399,19 @@ static const __DRIextension *loader_extensions[] = {
|
||||
NULL
|
||||
};
|
||||
|
||||
static const __DRIextension *loader_extensions_old[] = {
|
||||
&dri2LoaderExtension_old.base,
|
||||
&systemTimeExtension.base,
|
||||
NULL
|
||||
};
|
||||
|
||||
static __GLXDRIscreen *dri2CreateScreen(__GLXscreenConfigs *psc, int screen,
|
||||
__GLXdisplayPrivate *priv)
|
||||
{
|
||||
const __DRIconfig **driver_configs;
|
||||
const __DRIextension **extensions;
|
||||
const __GLXDRIdisplayPrivate *const pdp = (__GLXDRIdisplayPrivate *)
|
||||
priv->dri2Display;
|
||||
__GLXDRIscreen *psp;
|
||||
char *driverName, *deviceName;
|
||||
drm_magic_t magic;
|
||||
@ -347,8 +429,10 @@ static __GLXDRIscreen *dri2CreateScreen(__GLXscreenConfigs *psc, int screen,
|
||||
return NULL;
|
||||
|
||||
psc->driver = driOpenDriver(driverName);
|
||||
if (psc->driver == NULL)
|
||||
if (psc->driver == NULL) {
|
||||
ErrorMessageF("driver pointer missing\n");
|
||||
goto handle_error;
|
||||
}
|
||||
|
||||
extensions = dlsym(psc->driver, __DRI_DRIVER_EXTENSIONS);
|
||||
if (extensions == NULL) {
|
||||
@ -374,15 +458,26 @@ static __GLXDRIscreen *dri2CreateScreen(__GLXscreenConfigs *psc, int screen,
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (drmGetMagic(psc->fd, &magic))
|
||||
if (drmGetMagic(psc->fd, &magic)) {
|
||||
ErrorMessageF("failed to get magic\n");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (!DRI2Authenticate(psc->dpy, RootWindow(psc->dpy, screen), magic))
|
||||
if (!DRI2Authenticate(psc->dpy, RootWindow(psc->dpy, screen), magic)) {
|
||||
ErrorMessageF("failed to authenticate magic %d\n", magic);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
/* If the server does not support the protocol for
|
||||
* DRI2GetBuffersWithFormat, don't supply that interface to the driver.
|
||||
*/
|
||||
psc->__driScreen =
|
||||
psc->dri2->createNewScreen(screen, psc->fd,
|
||||
loader_extensions, &driver_configs, psc);
|
||||
psc->dri2->createNewScreen(screen, psc->fd,
|
||||
((pdp->driMinor < 1)
|
||||
? loader_extensions_old
|
||||
: loader_extensions),
|
||||
&driver_configs, psc);
|
||||
|
||||
if (psc->__driScreen == NULL) {
|
||||
ErrorMessageF("failed to create dri screen\n");
|
||||
return NULL;
|
||||
|
11
dist/Mesa/src/glx/x11/dri_common.c
vendored
11
dist/Mesa/src/glx/x11/dri_common.c
vendored
@ -345,7 +345,9 @@ driBindExtensions(__GLXscreenConfigs *psc, int dri2)
|
||||
#endif
|
||||
|
||||
#ifdef __DRI_SWAP_CONTROL
|
||||
if (strcmp(extensions[i]->name, __DRI_SWAP_CONTROL) == 0) {
|
||||
/* 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");
|
||||
@ -392,6 +394,13 @@ driBindExtensions(__GLXscreenConfigs *psc, int dri2)
|
||||
}
|
||||
#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 */
|
||||
}
|
||||
#endif
|
||||
|
||||
/* Ignore unknown extensions */
|
||||
}
|
||||
}
|
||||
|
79
dist/Mesa/src/glx/x11/dri_glx.c
vendored
79
dist/Mesa/src/glx/x11/dri_glx.c
vendored
@ -40,6 +40,7 @@ SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
||||
#include "glxclient.h"
|
||||
#include "glcontextmodes.h"
|
||||
#include "xf86dri.h"
|
||||
#include "dri2.h"
|
||||
#include "sarea.h"
|
||||
#include <dlfcn.h>
|
||||
#include <sys/types.h>
|
||||
@ -75,32 +76,45 @@ struct __GLXDRIcontextPrivateRec {
|
||||
*/
|
||||
static Bool driGetDriverName(Display *dpy, int scrNum, char **driverName)
|
||||
{
|
||||
int directCapable;
|
||||
Bool b;
|
||||
int driverMajor, driverMinor, driverPatch;
|
||||
int directCapable;
|
||||
Bool b;
|
||||
int event, error;
|
||||
int driverMajor, driverMinor, driverPatch;
|
||||
|
||||
*driverName = NULL;
|
||||
*driverName = NULL;
|
||||
|
||||
if (!XF86DRIQueryDirectRenderingCapable(dpy, scrNum, &directCapable)) {
|
||||
ErrorMessageF("XF86DRIQueryDirectRenderingCapable failed\n");
|
||||
return False;
|
||||
}
|
||||
if (!directCapable) {
|
||||
ErrorMessageF("XF86DRIQueryDirectRenderingCapable returned false\n");
|
||||
return False;
|
||||
}
|
||||
if (XF86DRIQueryExtension(dpy, &event, &error)) { /* DRI1 */
|
||||
if (!XF86DRIQueryDirectRenderingCapable(dpy, scrNum, &directCapable)) {
|
||||
ErrorMessageF("XF86DRIQueryDirectRenderingCapable failed\n");
|
||||
return False;
|
||||
}
|
||||
if (!directCapable) {
|
||||
ErrorMessageF("XF86DRIQueryDirectRenderingCapable returned false\n");
|
||||
return False;
|
||||
}
|
||||
|
||||
b = XF86DRIGetClientDriverName(dpy, scrNum, &driverMajor, &driverMinor,
|
||||
&driverPatch, driverName);
|
||||
if (!b) {
|
||||
ErrorMessageF("Cannot determine driver name for screen %d\n", scrNum);
|
||||
return False;
|
||||
}
|
||||
b = XF86DRIGetClientDriverName(dpy, scrNum, &driverMajor, &driverMinor,
|
||||
&driverPatch, driverName);
|
||||
if (!b) {
|
||||
ErrorMessageF("Cannot determine driver name for screen %d\n", scrNum);
|
||||
return False;
|
||||
}
|
||||
|
||||
InfoMessageF("XF86DRIGetClientDriverName: %d.%d.%d %s (screen %d)\n",
|
||||
driverMajor, driverMinor, driverPatch, *driverName, scrNum);
|
||||
InfoMessageF("XF86DRIGetClientDriverName: %d.%d.%d %s (screen %d)\n",
|
||||
driverMajor, driverMinor, driverPatch, *driverName, scrNum);
|
||||
|
||||
return True;
|
||||
return True;
|
||||
} else if (DRI2QueryExtension(dpy, &event, &error)) { /* DRI2 */
|
||||
char *dev;
|
||||
Bool ret = DRI2Connect(dpy, RootWindow(dpy, scrNum), driverName, &dev);
|
||||
|
||||
if (ret)
|
||||
Xfree(dev);
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
return False;
|
||||
}
|
||||
|
||||
/*
|
||||
@ -291,6 +305,7 @@ CallCreateNewScreen(Display *dpy, int scrn, __GLXscreenConfigs *psc,
|
||||
drm_handle_t hFB;
|
||||
int junk;
|
||||
const __DRIconfig **driver_configs;
|
||||
__GLcontextModes *visual;
|
||||
|
||||
/* DRI protocol version. */
|
||||
dri_version.major = driDpy->driMajor;
|
||||
@ -403,6 +418,28 @@ CallCreateNewScreen(Display *dpy, int scrn, __GLXscreenConfigs *psc,
|
||||
psc->configs = driConvertConfigs(psc->core, psc->configs, driver_configs);
|
||||
psc->visuals = driConvertConfigs(psc->core, psc->visuals, driver_configs);
|
||||
|
||||
/* Visuals with depth != screen depth are subject to automatic compositing
|
||||
* in the X server, so DRI1 can't render to them properly. Mark them as
|
||||
* non-conformant to prevent apps from picking them up accidentally.
|
||||
*/
|
||||
for (visual = psc->visuals; visual; visual = visual->next) {
|
||||
XVisualInfo template;
|
||||
XVisualInfo *visuals;
|
||||
int num_visuals;
|
||||
long mask;
|
||||
|
||||
template.visualid = visual->visualID;
|
||||
mask = VisualIDMask;
|
||||
visuals = XGetVisualInfo(dpy, mask, &template, &num_visuals);
|
||||
|
||||
if (visuals) {
|
||||
if (num_visuals > 0 && visuals->depth != DefaultDepth(dpy, scrn))
|
||||
visual->visualRating = GLX_NON_CONFORMANT_CONFIG;
|
||||
|
||||
XFree(visuals);
|
||||
}
|
||||
}
|
||||
|
||||
return psp;
|
||||
|
||||
handle_error:
|
||||
|
4
dist/Mesa/src/glx/x11/drisw_glx.c
vendored
4
dist/Mesa/src/glx/x11/drisw_glx.c
vendored
@ -401,10 +401,14 @@ driCreateScreen(__GLXscreenConfigs * psc, int screen,
|
||||
psc->configs = driConvertConfigs(psc->core, psc->configs, driver_configs);
|
||||
psc->visuals = driConvertConfigs(psc->core, psc->visuals, driver_configs);
|
||||
|
||||
free(driver_configs);
|
||||
|
||||
psp->destroyScreen = driDestroyScreen;
|
||||
psp->createContext = driCreateContext;
|
||||
psp->createDrawable = driCreateDrawable;
|
||||
psp->swapBuffers = driSwapBuffers;
|
||||
psp->waitX = NULL;
|
||||
psp->waitGL = NULL;
|
||||
|
||||
return psp;
|
||||
|
||||
|
4
dist/Mesa/src/glx/x11/glxclient.h
vendored
4
dist/Mesa/src/glx/x11/glxclient.h
vendored
@ -519,6 +519,10 @@ struct __GLXscreenConfigsRec {
|
||||
const __DRItexBufferExtension *texBuffer;
|
||||
#endif
|
||||
|
||||
#ifdef __DRI2_FLUSH
|
||||
const __DRI2flushExtension *f;
|
||||
#endif
|
||||
|
||||
#endif
|
||||
|
||||
/**
|
||||
|
@ -332,8 +332,19 @@ intelDrawBuffer(GLcontext * ctx, GLenum mode)
|
||||
{
|
||||
if ((ctx->DrawBuffer != NULL) && (ctx->DrawBuffer->Name == 0)) {
|
||||
struct intel_context *const intel = intel_context(ctx);
|
||||
const GLboolean was_front_buffer_rendering =
|
||||
intel->is_front_buffer_rendering;
|
||||
|
||||
intel->is_front_buffer_rendering = (mode == GL_FRONT_LEFT);
|
||||
intel->is_front_buffer_rendering = (mode == GL_FRONT_LEFT)
|
||||
|| (mode == GL_FRONT);
|
||||
|
||||
/* If we weren't front-buffer rendering before but we are now, make sure
|
||||
* that the front-buffer has actually been allocated.
|
||||
*/
|
||||
if (!was_front_buffer_rendering && intel->is_front_buffer_rendering) {
|
||||
intel_update_renderbuffers(intel->driContext,
|
||||
intel->driContext->driDrawablePriv);
|
||||
}
|
||||
}
|
||||
|
||||
intel_draw_buffer(ctx, ctx->DrawBuffer);
|
||||
@ -343,6 +354,23 @@ intelDrawBuffer(GLcontext * ctx, GLenum mode)
|
||||
static void
|
||||
intelReadBuffer(GLcontext * ctx, GLenum mode)
|
||||
{
|
||||
if ((ctx->DrawBuffer != NULL) && (ctx->DrawBuffer->Name == 0)) {
|
||||
struct intel_context *const intel = intel_context(ctx);
|
||||
const GLboolean was_front_buffer_reading =
|
||||
intel->is_front_buffer_reading;
|
||||
|
||||
intel->is_front_buffer_reading = (mode == GL_FRONT_LEFT)
|
||||
|| (mode == GL_FRONT);
|
||||
|
||||
/* If we weren't front-buffer reading before but we are now, make sure
|
||||
* that the front-buffer has actually been allocated.
|
||||
*/
|
||||
if (!was_front_buffer_reading && intel->is_front_buffer_reading) {
|
||||
intel_update_renderbuffers(intel->driContext,
|
||||
intel->driContext->driDrawablePriv);
|
||||
}
|
||||
}
|
||||
|
||||
if (ctx->ReadBuffer == ctx->DrawBuffer) {
|
||||
/* This will update FBO completeness status.
|
||||
* A framebuffer will be incomplete if the GL_READ_BUFFER setting
|
||||
|
177
dist/Mesa/src/mesa/drivers/dri/intel/intel_context.c
vendored
177
dist/Mesa/src/mesa/drivers/dri/intel/intel_context.c
vendored
@ -25,12 +25,12 @@
|
||||
*
|
||||
**************************************************************************/
|
||||
|
||||
|
||||
#include "main/glheader.h"
|
||||
#include "main/context.h"
|
||||
#include "main/matrix.h"
|
||||
#include "main/simple_list.h"
|
||||
#include "main/extensions.h"
|
||||
#include "main/arrayobj.h"
|
||||
#include "main/framebuffer.h"
|
||||
#include "main/imports.h"
|
||||
#include "main/points.h"
|
||||
@ -66,6 +66,7 @@
|
||||
#include "vblank.h"
|
||||
#include "utils.h"
|
||||
#include "xmlpool.h" /* for symbolic values of enum-type options */
|
||||
|
||||
#ifndef INTEL_DEBUG
|
||||
int INTEL_DEBUG = (0);
|
||||
#endif
|
||||
@ -100,6 +101,9 @@ int INTEL_DEBUG = (0);
|
||||
#define DRIVER_DATE "20090418 2009Q1"
|
||||
#define DRIVER_DATE_GEM "GEM " DRIVER_DATE
|
||||
|
||||
|
||||
static void intel_flush(GLcontext *ctx, GLboolean needs_mi_flush);
|
||||
|
||||
static const GLubyte *
|
||||
intelGetString(GLcontext * ctx, GLenum name)
|
||||
{
|
||||
@ -203,6 +207,24 @@ intelGetString(GLcontext * ctx, GLenum name)
|
||||
}
|
||||
}
|
||||
|
||||
static unsigned
|
||||
intel_bits_per_pixel(const struct intel_renderbuffer *rb)
|
||||
{
|
||||
switch (rb->Base._ActualFormat) {
|
||||
case GL_RGB5:
|
||||
case GL_DEPTH_COMPONENT16:
|
||||
return 16;
|
||||
case GL_RGB8:
|
||||
case GL_RGBA8:
|
||||
case GL_DEPTH_COMPONENT24:
|
||||
case GL_DEPTH24_STENCIL8_EXT:
|
||||
case GL_STENCIL_INDEX8_EXT:
|
||||
return 32;
|
||||
default:
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
intel_update_renderbuffers(__DRIcontext *context, __DRIdrawable *drawable)
|
||||
{
|
||||
@ -210,7 +232,7 @@ intel_update_renderbuffers(__DRIcontext *context, __DRIdrawable *drawable)
|
||||
struct intel_renderbuffer *rb;
|
||||
struct intel_region *region, *depth_region;
|
||||
struct intel_context *intel = context->driverPrivate;
|
||||
__DRIbuffer *buffers;
|
||||
__DRIbuffer *buffers = NULL;
|
||||
__DRIscreen *screen;
|
||||
int i, count;
|
||||
unsigned int attachments[10];
|
||||
@ -222,22 +244,65 @@ intel_update_renderbuffers(__DRIcontext *context, __DRIdrawable *drawable)
|
||||
|
||||
screen = intel->intelScreen->driScrnPriv;
|
||||
|
||||
i = 0;
|
||||
if (intel_fb->color_rb[0])
|
||||
attachments[i++] = __DRI_BUFFER_FRONT_LEFT;
|
||||
if (intel_fb->color_rb[1])
|
||||
attachments[i++] = __DRI_BUFFER_BACK_LEFT;
|
||||
if (intel_get_renderbuffer(&intel_fb->Base, BUFFER_DEPTH))
|
||||
attachments[i++] = __DRI_BUFFER_DEPTH;
|
||||
if (intel_get_renderbuffer(&intel_fb->Base, BUFFER_STENCIL))
|
||||
attachments[i++] = __DRI_BUFFER_STENCIL;
|
||||
if (screen->dri2.loader
|
||||
&& (screen->dri2.loader->base.version > 2)
|
||||
&& (screen->dri2.loader->getBuffersWithFormat != NULL)) {
|
||||
struct intel_renderbuffer *depth_rb;
|
||||
struct intel_renderbuffer *stencil_rb;
|
||||
|
||||
buffers = (*screen->dri2.loader->getBuffers)(drawable,
|
||||
&drawable->w,
|
||||
&drawable->h,
|
||||
attachments, i,
|
||||
&count,
|
||||
drawable->loaderPrivate);
|
||||
i = 0;
|
||||
if ((intel->is_front_buffer_rendering ||
|
||||
intel->is_front_buffer_reading ||
|
||||
!intel_fb->color_rb[1])
|
||||
&& intel_fb->color_rb[0]) {
|
||||
attachments[i++] = __DRI_BUFFER_FRONT_LEFT;
|
||||
attachments[i++] = intel_bits_per_pixel(intel_fb->color_rb[0]);
|
||||
}
|
||||
|
||||
if (intel_fb->color_rb[1]) {
|
||||
attachments[i++] = __DRI_BUFFER_BACK_LEFT;
|
||||
attachments[i++] = intel_bits_per_pixel(intel_fb->color_rb[1]);
|
||||
}
|
||||
|
||||
depth_rb = intel_get_renderbuffer(&intel_fb->Base, BUFFER_DEPTH);
|
||||
stencil_rb = intel_get_renderbuffer(&intel_fb->Base, BUFFER_STENCIL);
|
||||
|
||||
if ((depth_rb != NULL) && (stencil_rb != NULL)) {
|
||||
attachments[i++] = __DRI_BUFFER_DEPTH_STENCIL;
|
||||
attachments[i++] = intel_bits_per_pixel(depth_rb);
|
||||
} else if (depth_rb != NULL) {
|
||||
attachments[i++] = __DRI_BUFFER_DEPTH;
|
||||
attachments[i++] = intel_bits_per_pixel(depth_rb);
|
||||
} else if (stencil_rb != NULL) {
|
||||
attachments[i++] = __DRI_BUFFER_STENCIL;
|
||||
attachments[i++] = intel_bits_per_pixel(stencil_rb);
|
||||
}
|
||||
|
||||
buffers =
|
||||
(*screen->dri2.loader->getBuffersWithFormat)(drawable,
|
||||
&drawable->w,
|
||||
&drawable->h,
|
||||
attachments, i / 2,
|
||||
&count,
|
||||
drawable->loaderPrivate);
|
||||
} else if (screen->dri2.loader) {
|
||||
i = 0;
|
||||
if (intel_fb->color_rb[0])
|
||||
attachments[i++] = __DRI_BUFFER_FRONT_LEFT;
|
||||
if (intel_fb->color_rb[1])
|
||||
attachments[i++] = __DRI_BUFFER_BACK_LEFT;
|
||||
if (intel_get_renderbuffer(&intel_fb->Base, BUFFER_DEPTH))
|
||||
attachments[i++] = __DRI_BUFFER_DEPTH;
|
||||
if (intel_get_renderbuffer(&intel_fb->Base, BUFFER_STENCIL))
|
||||
attachments[i++] = __DRI_BUFFER_STENCIL;
|
||||
|
||||
buffers = (*screen->dri2.loader->getBuffers)(drawable,
|
||||
&drawable->w,
|
||||
&drawable->h,
|
||||
attachments, i,
|
||||
&count,
|
||||
drawable->loaderPrivate);
|
||||
}
|
||||
|
||||
if (buffers == NULL)
|
||||
return;
|
||||
@ -280,6 +345,11 @@ intel_update_renderbuffers(__DRIcontext *context, __DRIdrawable *drawable)
|
||||
region_name = "dri2 depth buffer";
|
||||
break;
|
||||
|
||||
case __DRI_BUFFER_DEPTH_STENCIL:
|
||||
rb = intel_get_renderbuffer(&intel_fb->Base, BUFFER_DEPTH);
|
||||
region_name = "dri2 depth / stencil buffer";
|
||||
break;
|
||||
|
||||
case __DRI_BUFFER_STENCIL:
|
||||
rb = intel_get_renderbuffer(&intel_fb->Base, BUFFER_STENCIL);
|
||||
region_name = "dri2 stencil buffer";
|
||||
@ -326,6 +396,23 @@ intel_update_renderbuffers(__DRIcontext *context, __DRIdrawable *drawable)
|
||||
|
||||
intel_renderbuffer_set_region(rb, region);
|
||||
intel_region_release(®ion);
|
||||
|
||||
if (buffers[i].attachment == __DRI_BUFFER_DEPTH_STENCIL) {
|
||||
rb = intel_get_renderbuffer(&intel_fb->Base, BUFFER_STENCIL);
|
||||
if (rb != NULL) {
|
||||
struct intel_region *stencil_region = NULL;
|
||||
|
||||
if (rb->region) {
|
||||
dri_bo_flink(rb->region->buffer, &name);
|
||||
if (name == buffers[i].name)
|
||||
continue;
|
||||
}
|
||||
|
||||
intel_region_reference(&stencil_region, region);
|
||||
intel_renderbuffer_set_region(rb, stencil_region);
|
||||
intel_region_release(&stencil_region);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
driUpdateFramebufferSize(&intel->ctx, drawable);
|
||||
@ -534,8 +621,8 @@ intel_flush(GLcontext *ctx, GLboolean needs_mi_flush)
|
||||
if ((ctx->DrawBuffer->Name == 0) && intel->front_buffer_dirty) {
|
||||
__DRIscreen *const screen = intel->intelScreen->driScrnPriv;
|
||||
|
||||
if (screen->dri2.loader
|
||||
&& (screen->dri2.loader->base.version >= 2)
|
||||
if (screen->dri2.loader &&
|
||||
(screen->dri2.loader->base.version >= 2)
|
||||
&& (screen->dri2.loader->flushFrontBuffer != NULL)) {
|
||||
(*screen->dri2.loader->flushFrontBuffer)(intel->driDrawable,
|
||||
intel->driDrawable->loaderPrivate);
|
||||
@ -578,7 +665,7 @@ intelFinish(GLcontext * ctx)
|
||||
|
||||
irb = intel_renderbuffer(fb->_ColorDrawBuffers[i]);
|
||||
|
||||
if (irb->region)
|
||||
if (irb && irb->region)
|
||||
dri_bo_wait_rendering(irb->region->buffer);
|
||||
}
|
||||
if (fb->_DepthBuffer) {
|
||||
@ -704,6 +791,13 @@ intelInitContext(struct intel_context *intel,
|
||||
_mesa_init_point(ctx);
|
||||
|
||||
ctx->Const.MaxColorAttachments = 4; /* XXX FBO: review this */
|
||||
if (IS_965(intelScreen->deviceID)) {
|
||||
if (MAX_WIDTH > 8192)
|
||||
ctx->Const.MaxRenderbufferSize = 8192;
|
||||
} else {
|
||||
if (MAX_WIDTH > 2048)
|
||||
ctx->Const.MaxRenderbufferSize = 2048;
|
||||
}
|
||||
|
||||
/* Initialize the software rasterizer and helper modules. */
|
||||
_swrast_CreateContext(ctx);
|
||||
@ -821,13 +915,50 @@ intelDestroyContext(__DRIcontextPrivate * driContextPriv)
|
||||
intel->prim.vb_bo = NULL;
|
||||
|
||||
if (release_texture_heaps) {
|
||||
/* This share group is about to go away, free our private
|
||||
* texture object data.
|
||||
/* Nothing is currently done here to free texture heaps;
|
||||
* but we're not using the texture heap utilities, so I
|
||||
* rather think we shouldn't. I've taken a look, and can't
|
||||
* find any private texture data hanging around anywhere, but
|
||||
* I'm not yet certain there isn't any at all...
|
||||
*/
|
||||
if (INTEL_DEBUG & DEBUG_TEXTURE)
|
||||
/* if (INTEL_DEBUG & DEBUG_TEXTURE)
|
||||
fprintf(stderr, "do something to free texture heaps\n");
|
||||
*/
|
||||
}
|
||||
|
||||
/* XXX In intelMakeCurrent() below, the context's static regions are
|
||||
* referenced inside the frame buffer; it's listed as a hack,
|
||||
* with a comment of "XXX FBO temporary fix-ups!", but
|
||||
* as long as it's there, we should release the regions here.
|
||||
* The do/while loop around the block is used to allow the
|
||||
* "continue" statements inside the block to exit the block,
|
||||
* to avoid many layers of "if" constructs.
|
||||
*/
|
||||
do {
|
||||
__DRIdrawablePrivate * driDrawPriv = intel->driDrawable;
|
||||
struct intel_framebuffer *intel_fb;
|
||||
struct intel_renderbuffer *irbDepth, *irbStencil;
|
||||
if (!driDrawPriv) {
|
||||
/* We're already detached from the drawable; exit this block. */
|
||||
continue;
|
||||
}
|
||||
intel_fb = (struct intel_framebuffer *) driDrawPriv->driverPrivate;
|
||||
if (!intel_fb) {
|
||||
/* The frame buffer is already gone; exit this block. */
|
||||
continue;
|
||||
}
|
||||
irbDepth = intel_get_renderbuffer(&intel_fb->Base, BUFFER_DEPTH);
|
||||
irbStencil = intel_get_renderbuffer(&intel_fb->Base, BUFFER_STENCIL);
|
||||
|
||||
/* Usually, the stencil buffer is the same as the depth buffer;
|
||||
* but they're handled separately in MakeCurrent, so we'll
|
||||
* handle them separately here.
|
||||
*/
|
||||
if (irbStencil && irbStencil->region == intel->depth_region) {
|
||||
intel_renderbuffer_set_region(irbStencil, NULL);
|
||||
}
|
||||
} while (0);
|
||||
|
||||
intel_region_release(&intel->front_region);
|
||||
intel_region_release(&intel->back_region);
|
||||
intel_region_release(&intel->depth_region);
|
||||
|
@ -282,6 +282,14 @@ struct intel_context
|
||||
* easily.
|
||||
*/
|
||||
GLboolean is_front_buffer_rendering;
|
||||
/**
|
||||
* Track whether front-buffer is the current read target.
|
||||
*
|
||||
* This is closely associated with is_front_buffer_rendering, but may
|
||||
* be set separately. The DRI2 fake front buffer must be referenced
|
||||
* either way.
|
||||
*/
|
||||
GLboolean is_front_buffer_reading;
|
||||
|
||||
drm_clip_rect_t fboRect; /**< cliprect for FBO rendering */
|
||||
|
||||
|
@ -688,12 +688,15 @@ intel_set_span_functions(struct intel_context *intel,
|
||||
struct intel_renderbuffer *irb = (struct intel_renderbuffer *) rb;
|
||||
uint32_t tiling;
|
||||
|
||||
#ifndef __OpenBSD__ /* openbsd uses fenced gtt writes for tiles p{read,write} */
|
||||
/* If in GEM mode, we need to do the tile address swizzling ourselves,
|
||||
* instead of the fence registers handling it.
|
||||
*/
|
||||
|
||||
if (intel->ttm)
|
||||
tiling = irb->region->tiling;
|
||||
else
|
||||
#endif
|
||||
tiling = I915_TILING_NONE;
|
||||
|
||||
if (rb->_ActualFormat == GL_RGB5) {
|
||||
|
@ -1,2 +1,2 @@
|
||||
major=9
|
||||
minor=0
|
||||
minor=1
|
||||
|
Loading…
Reference in New Issue
Block a user