mirror of
https://gitlab.freedesktop.org/xorg/xserver.git
synced 2026-01-26 12:00:25 +01:00
Merge commit 'origin/server-1.6-branch' into xorg-server-1.6-apple
This commit is contained in:
commit
09354a4098
10 changed files with 484 additions and 95 deletions
|
|
@ -859,7 +859,7 @@ if test "x$DRI" = xyes; then
|
|||
AC_SUBST(GL_CFLAGS)
|
||||
fi
|
||||
|
||||
PKG_CHECK_MODULES([DRI2PROTO], [dri2proto >= 1.99.3],
|
||||
PKG_CHECK_MODULES([DRI2PROTO], [dri2proto >= 2.1],
|
||||
[HAVE_DRI2PROTO=yes], [HAVE_DRI2PROTO=no])
|
||||
case "$DRI2,$HAVE_DRI2PROTO" in
|
||||
yes,no)
|
||||
|
|
|
|||
|
|
@ -82,6 +82,8 @@ struct __GLXDRIcontext {
|
|||
__DRIcontext *driContext;
|
||||
};
|
||||
|
||||
#define MAX_DRAWABLE_BUFFERS 5
|
||||
|
||||
struct __GLXDRIdrawable {
|
||||
__GLXdrawable base;
|
||||
__DRIdrawable *driDrawable;
|
||||
|
|
@ -90,7 +92,7 @@ struct __GLXDRIdrawable {
|
|||
/* Dimensions as last reported by DRI2GetBuffers. */
|
||||
int width;
|
||||
int height;
|
||||
__DRIbuffer buffers[5];
|
||||
__DRIbuffer buffers[MAX_DRAWABLE_BUFFERS];
|
||||
int count;
|
||||
};
|
||||
|
||||
|
|
@ -359,12 +361,13 @@ dri2GetBuffers(__DRIdrawable *driDrawable,
|
|||
int *out_count, void *loaderPrivate)
|
||||
{
|
||||
__GLXDRIdrawable *private = loaderPrivate;
|
||||
DRI2BufferPtr buffers;
|
||||
DRI2BufferPtr *buffers;
|
||||
int i;
|
||||
int j;
|
||||
|
||||
buffers = DRI2GetBuffers(private->base.pDraw,
|
||||
width, height, attachments, count, out_count);
|
||||
if (*out_count > 5) {
|
||||
if (*out_count > MAX_DRAWABLE_BUFFERS) {
|
||||
*out_count = 0;
|
||||
return NULL;
|
||||
}
|
||||
|
|
@ -374,20 +377,83 @@ dri2GetBuffers(__DRIdrawable *driDrawable,
|
|||
|
||||
/* This assumes the DRI2 buffer attachment tokens matches the
|
||||
* __DRIbuffer tokens. */
|
||||
j = 0;
|
||||
for (i = 0; i < *out_count; i++) {
|
||||
private->buffers[i].attachment = buffers[i].attachment;
|
||||
private->buffers[i].name = buffers[i].name;
|
||||
private->buffers[i].pitch = buffers[i].pitch;
|
||||
private->buffers[i].cpp = buffers[i].cpp;
|
||||
private->buffers[i].flags = buffers[i].flags;
|
||||
/* Do not send the real front buffer of a window to the client.
|
||||
*/
|
||||
if ((private->base.pDraw->type == DRAWABLE_WINDOW)
|
||||
&& (buffers[i]->attachment == DRI2BufferFrontLeft)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
private->buffers[j].attachment = buffers[i]->attachment;
|
||||
private->buffers[j].name = buffers[i]->name;
|
||||
private->buffers[j].pitch = buffers[i]->pitch;
|
||||
private->buffers[j].cpp = buffers[i]->cpp;
|
||||
private->buffers[j].flags = buffers[i]->flags;
|
||||
j++;
|
||||
}
|
||||
|
||||
*out_count = j;
|
||||
return private->buffers;
|
||||
}
|
||||
|
||||
static __DRIbuffer *
|
||||
dri2GetBuffersWithFormat(__DRIdrawable *driDrawable,
|
||||
int *width, int *height,
|
||||
unsigned int *attachments, int count,
|
||||
int *out_count, void *loaderPrivate)
|
||||
{
|
||||
__GLXDRIdrawable *private = loaderPrivate;
|
||||
DRI2BufferPtr *buffers;
|
||||
int i;
|
||||
int j = 0;
|
||||
|
||||
buffers = DRI2GetBuffersWithFormat(private->base.pDraw,
|
||||
width, height, attachments, count,
|
||||
out_count);
|
||||
if (*out_count > MAX_DRAWABLE_BUFFERS) {
|
||||
*out_count = 0;
|
||||
return NULL;
|
||||
}
|
||||
|
||||
private->width = *width;
|
||||
private->height = *height;
|
||||
|
||||
/* This assumes the DRI2 buffer attachment tokens matches the
|
||||
* __DRIbuffer tokens. */
|
||||
for (i = 0; i < *out_count; i++) {
|
||||
/* Do not send the real front buffer of a window to the client.
|
||||
*/
|
||||
if ((private->base.pDraw->type == DRAWABLE_WINDOW)
|
||||
&& (buffers[i]->attachment == DRI2BufferFrontLeft)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
private->buffers[j].attachment = buffers[i]->attachment;
|
||||
private->buffers[j].name = buffers[i]->name;
|
||||
private->buffers[j].pitch = buffers[i]->pitch;
|
||||
private->buffers[j].cpp = buffers[i]->cpp;
|
||||
private->buffers[j].flags = buffers[i]->flags;
|
||||
j++;
|
||||
}
|
||||
|
||||
*out_count = j;
|
||||
return private->buffers;
|
||||
}
|
||||
|
||||
static void
|
||||
dri2FlushFrontBuffer(__DRIdrawable *driDrawable, void *loaderPrivate)
|
||||
{
|
||||
(void) driDrawable;
|
||||
__glXDRIdrawableWaitGL((__GLXdrawable *) loaderPrivate);
|
||||
}
|
||||
|
||||
static const __DRIdri2LoaderExtension loaderExtension = {
|
||||
{ __DRI_DRI2_LOADER, __DRI_DRI2_LOADER_VERSION },
|
||||
dri2GetBuffers,
|
||||
dri2FlushFrontBuffer,
|
||||
dri2GetBuffersWithFormat,
|
||||
};
|
||||
|
||||
static const __DRIextension *loader_extensions[] = {
|
||||
|
|
|
|||
|
|
@ -862,8 +862,6 @@ vfbScreenInit(int index, ScreenPtr pScreen, int argc, char **argv)
|
|||
pbits = vfbAllocateFramebufferMemory(pvfb);
|
||||
if (!pbits) return FALSE;
|
||||
|
||||
miSetPixmapDepths ();
|
||||
|
||||
switch (pvfb->depth) {
|
||||
case 8:
|
||||
miSetVisualTypesAndMasks (8,
|
||||
|
|
@ -875,20 +873,6 @@ vfbScreenInit(int index, ScreenPtr pScreen, int argc, char **argv)
|
|||
(1 << DirectColor)),
|
||||
8, PseudoColor, 0, 0, 0);
|
||||
break;
|
||||
#if 0
|
||||
/* 12bit PseudoColor with 12bit color resolution
|
||||
* (to simulate SGI hardware and the 12bit PseudoColor emulation layer) */
|
||||
case 12:
|
||||
miSetVisualTypesAndMasks (12,
|
||||
((1 << StaticGray) |
|
||||
(1 << GrayScale) |
|
||||
(1 << StaticColor) |
|
||||
(1 << PseudoColor) |
|
||||
(1 << TrueColor) |
|
||||
(1 << DirectColor)),
|
||||
12, PseudoColor, 0, 0, 0);
|
||||
break;
|
||||
#endif
|
||||
case 15:
|
||||
miSetVisualTypesAndMasks (15,
|
||||
((1 << TrueColor) |
|
||||
|
|
@ -907,18 +891,10 @@ vfbScreenInit(int index, ScreenPtr pScreen, int argc, char **argv)
|
|||
(1 << DirectColor)),
|
||||
8, TrueColor, 0xff0000, 0x00ff00, 0x0000ff);
|
||||
break;
|
||||
#if 0
|
||||
/* 30bit TrueColor (to simulate Sun's XVR-1000/-4000 high quality
|
||||
* framebuffer series) */
|
||||
case 30:
|
||||
miSetVisualTypesAndMasks (30,
|
||||
((1 << TrueColor) |
|
||||
(1 << DirectColor)),
|
||||
10, TrueColor, 0x3ff00000, 0x000ffc00, 0x000003ff);
|
||||
break;
|
||||
#endif
|
||||
}
|
||||
|
||||
|
||||
miSetPixmapDepths ();
|
||||
|
||||
ret = fbScreenInit(pScreen, pbits, pvfb->width, pvfb->height,
|
||||
dpix, dpiy, pvfb->paddedWidth,pvfb->bitsPerPixel);
|
||||
#ifdef RENDER
|
||||
|
|
|
|||
|
|
@ -417,18 +417,16 @@ xf86PciProbe(void)
|
|||
if (xf86IsPrimaryPci(info))
|
||||
prim = "*";
|
||||
|
||||
xf86Msg( X_PROBED, "PCI:%s(%u@%u:%u:%u) ", prim, info->domain,
|
||||
info->bus, info->dev, info->func );
|
||||
xf86Msg(X_PROBED, "PCI:%s(%u:%u:%u:%u) %04x:%04x:%04x:%04x ", prim,
|
||||
info->domain, info->bus, info->dev, info->func,
|
||||
info->vendor_id, info->device_id,
|
||||
info->subvendor_id, info->subdevice_id);
|
||||
|
||||
if (vendorname)
|
||||
xf86ErrorF("%s ", vendorname);
|
||||
else
|
||||
xf86ErrorF("unknown vendor (0x%04x) ", info->vendor_id);
|
||||
|
||||
if (chipname)
|
||||
xf86ErrorF("%s ", chipname);
|
||||
else
|
||||
xf86ErrorF("unknown chipset (0x%04x) ", info->device_id);
|
||||
|
||||
xf86ErrorF("rev %d", info->revision);
|
||||
|
||||
|
|
|
|||
|
|
@ -527,7 +527,7 @@ struct detailed_monitor_section {
|
|||
struct whitePoints wp[2]; /* 32 */
|
||||
/* color management data */
|
||||
struct cvt_timings cvt[4]; /* 64 */
|
||||
/* established timings III */
|
||||
Uchar est_iii[6]; /* 6 */
|
||||
} section; /* max: 80 */
|
||||
};
|
||||
|
||||
|
|
|
|||
|
|
@ -284,6 +284,8 @@ get_std_timing_section(Uchar *c, struct std_timings *r,
|
|||
}
|
||||
}
|
||||
|
||||
static const unsigned char empty_block[18];
|
||||
|
||||
static void
|
||||
get_dt_md_section(Uchar *c, struct edid_version *ver,
|
||||
struct detailed_monitor_section *det_mon)
|
||||
|
|
@ -327,6 +329,7 @@ get_dt_md_section(Uchar *c, struct edid_version *ver,
|
|||
break;
|
||||
case ADD_EST_TIMINGS:
|
||||
det_mon[i].type = DS_EST_III;
|
||||
memcpy(det_mon[i].section.est_iii, c + 6, 6);
|
||||
break;
|
||||
case ADD_DUMMY:
|
||||
det_mon[i].type = DS_DUMMY;
|
||||
|
|
@ -335,10 +338,10 @@ get_dt_md_section(Uchar *c, struct edid_version *ver,
|
|||
det_mon[i].type = DS_UNKOWN;
|
||||
break;
|
||||
}
|
||||
if (c[3] <= 0x0F) {
|
||||
if (c[3] <= 0x0F && memcmp(c, empty_block, sizeof(empty_block))) {
|
||||
det_mon[i].type = DS_VENDOR + c[3];
|
||||
}
|
||||
} else {
|
||||
} else {
|
||||
det_mon[i].type = DT;
|
||||
get_detailed_timing_section(c,&det_mon[i].section.d_timings);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -53,7 +53,7 @@ typedef struct _DRI2Drawable {
|
|||
unsigned int refCount;
|
||||
int width;
|
||||
int height;
|
||||
DRI2BufferPtr buffers;
|
||||
DRI2BufferPtr *buffers;
|
||||
int bufferCount;
|
||||
unsigned int pendingSequence;
|
||||
} DRI2DrawableRec, *DRI2DrawablePtr;
|
||||
|
|
@ -63,8 +63,8 @@ typedef struct _DRI2Screen {
|
|||
const char *deviceName;
|
||||
int fd;
|
||||
unsigned int lastSequence;
|
||||
DRI2CreateBuffersProcPtr CreateBuffers;
|
||||
DRI2DestroyBuffersProcPtr DestroyBuffers;
|
||||
DRI2CreateBufferProcPtr CreateBuffer;
|
||||
DRI2DestroyBufferProcPtr DestroyBuffer;
|
||||
DRI2CopyRegionProcPtr CopyRegion;
|
||||
|
||||
HandleExposuresProcPtr HandleExposures;
|
||||
|
|
@ -132,32 +132,174 @@ DRI2CreateDrawable(DrawablePtr pDraw)
|
|||
return Success;
|
||||
}
|
||||
|
||||
DRI2BufferPtr
|
||||
DRI2GetBuffers(DrawablePtr pDraw, int *width, int *height,
|
||||
unsigned int *attachments, int count, int *out_count)
|
||||
static int
|
||||
find_attachment(DRI2BufferPtr *buffer_list, int count, unsigned attachment)
|
||||
{
|
||||
int i;
|
||||
|
||||
if (buffer_list == NULL) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
for (i = 0; i < count; i++) {
|
||||
if ((buffer_list[i] != NULL)
|
||||
&& (buffer_list[i]->attachment == attachment)) {
|
||||
return i;
|
||||
}
|
||||
}
|
||||
|
||||
return -1;
|
||||
}
|
||||
|
||||
static DRI2BufferPtr
|
||||
allocate_or_reuse_buffer(DrawablePtr pDraw, DRI2ScreenPtr ds,
|
||||
DRI2DrawablePtr pPriv,
|
||||
unsigned int attachment, unsigned int format,
|
||||
int dimensions_match)
|
||||
{
|
||||
DRI2BufferPtr buffer;
|
||||
int old_buf;
|
||||
|
||||
old_buf = find_attachment(pPriv->buffers, pPriv->bufferCount, attachment);
|
||||
|
||||
if ((old_buf < 0)
|
||||
|| !dimensions_match
|
||||
|| (pPriv->buffers[old_buf]->format != format)) {
|
||||
buffer = (*ds->CreateBuffer)(pDraw, attachment, format);
|
||||
} else {
|
||||
buffer = pPriv->buffers[old_buf];
|
||||
pPriv->buffers[old_buf] = NULL;
|
||||
}
|
||||
|
||||
return buffer;
|
||||
}
|
||||
|
||||
static DRI2BufferPtr *
|
||||
do_get_buffers(DrawablePtr pDraw, int *width, int *height,
|
||||
unsigned int *attachments, int count, int *out_count,
|
||||
int has_format)
|
||||
{
|
||||
DRI2ScreenPtr ds = DRI2GetScreen(pDraw->pScreen);
|
||||
DRI2DrawablePtr pPriv = DRI2GetDrawable(pDraw);
|
||||
DRI2BufferPtr buffers;
|
||||
DRI2BufferPtr *buffers;
|
||||
int need_real_front = 0;
|
||||
int need_fake_front = 0;
|
||||
int have_fake_front = 0;
|
||||
int front_format = 0;
|
||||
const int dimensions_match = (pDraw->width == pPriv->width)
|
||||
&& (pDraw->height == pPriv->height);
|
||||
int i;
|
||||
|
||||
if (pPriv->buffers == NULL ||
|
||||
pDraw->width != pPriv->width || pDraw->height != pPriv->height)
|
||||
{
|
||||
buffers = (*ds->CreateBuffers)(pDraw, attachments, count);
|
||||
(*ds->DestroyBuffers)(pDraw, pPriv->buffers, pPriv->bufferCount);
|
||||
pPriv->buffers = buffers;
|
||||
pPriv->bufferCount = count;
|
||||
pPriv->width = pDraw->width;
|
||||
pPriv->height = pDraw->height;
|
||||
|
||||
buffers = xalloc((count + 1) * sizeof(buffers[0]));
|
||||
|
||||
for (i = 0; i < count; i++) {
|
||||
const unsigned attachment = *(attachments++);
|
||||
const unsigned format = (has_format) ? *(attachments++) : 0;
|
||||
|
||||
buffers[i] = allocate_or_reuse_buffer(pDraw, ds, pPriv, attachment,
|
||||
format, dimensions_match);
|
||||
|
||||
|
||||
/* If the drawable is a window and the front-buffer is requested,
|
||||
* silently add the fake front-buffer to the list of requested
|
||||
* attachments. The counting logic in the loop accounts for the case
|
||||
* where the client requests both the fake and real front-buffer.
|
||||
*/
|
||||
if (attachment == DRI2BufferBackLeft) {
|
||||
need_real_front++;
|
||||
front_format = format;
|
||||
}
|
||||
|
||||
if (attachment == DRI2BufferFrontLeft) {
|
||||
need_real_front--;
|
||||
front_format = format;
|
||||
|
||||
if (pDraw->type == DRAWABLE_WINDOW) {
|
||||
need_fake_front++;
|
||||
}
|
||||
}
|
||||
|
||||
if (pDraw->type == DRAWABLE_WINDOW) {
|
||||
if (attachment == DRI2BufferFakeFrontLeft) {
|
||||
need_fake_front--;
|
||||
have_fake_front = 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (need_real_front > 0) {
|
||||
buffers[i++] = allocate_or_reuse_buffer(pDraw, ds, pPriv,
|
||||
DRI2BufferFrontLeft,
|
||||
front_format, dimensions_match);
|
||||
}
|
||||
|
||||
if (need_fake_front > 0) {
|
||||
buffers[i++] = allocate_or_reuse_buffer(pDraw, ds, pPriv,
|
||||
DRI2BufferFakeFrontLeft,
|
||||
front_format, dimensions_match);
|
||||
have_fake_front = 1;
|
||||
}
|
||||
|
||||
*out_count = i;
|
||||
|
||||
|
||||
if (pPriv->buffers != NULL) {
|
||||
for (i = 0; i < pPriv->bufferCount; i++) {
|
||||
if (pPriv->buffers[i] != NULL) {
|
||||
(*ds->DestroyBuffer)(pDraw, pPriv->buffers[i]);
|
||||
}
|
||||
}
|
||||
|
||||
xfree(pPriv->buffers);
|
||||
}
|
||||
|
||||
|
||||
pPriv->buffers = buffers;
|
||||
pPriv->bufferCount = *out_count;
|
||||
pPriv->width = pDraw->width;
|
||||
pPriv->height = pDraw->height;
|
||||
*width = pPriv->width;
|
||||
*height = pPriv->height;
|
||||
*out_count = pPriv->bufferCount;
|
||||
|
||||
|
||||
/* If the client is getting a fake front-buffer, pre-fill it with the
|
||||
* contents of the real front-buffer. This ensures correct operation of
|
||||
* applications that call glXWaitX before calling glDrawBuffer.
|
||||
*/
|
||||
if (have_fake_front) {
|
||||
BoxRec box;
|
||||
RegionRec region;
|
||||
|
||||
box.x1 = 0;
|
||||
box.y1 = 0;
|
||||
box.x2 = pPriv->width;
|
||||
box.y2 = pPriv->height;
|
||||
REGION_INIT(pDraw->pScreen, ®ion, &box, 0);
|
||||
|
||||
DRI2CopyRegion(pDraw, ®ion, DRI2BufferFakeFrontLeft,
|
||||
DRI2BufferFrontLeft);
|
||||
}
|
||||
|
||||
return pPriv->buffers;
|
||||
}
|
||||
|
||||
DRI2BufferPtr *
|
||||
DRI2GetBuffers(DrawablePtr pDraw, int *width, int *height,
|
||||
unsigned int *attachments, int count, int *out_count)
|
||||
{
|
||||
return do_get_buffers(pDraw, width, height, attachments, count,
|
||||
out_count, FALSE);
|
||||
}
|
||||
|
||||
DRI2BufferPtr *
|
||||
DRI2GetBuffersWithFormat(DrawablePtr pDraw, int *width, int *height,
|
||||
unsigned int *attachments, int count, int *out_count)
|
||||
{
|
||||
return do_get_buffers(pDraw, width, height, attachments, count,
|
||||
out_count, TRUE);
|
||||
}
|
||||
|
||||
int
|
||||
DRI2CopyRegion(DrawablePtr pDraw, RegionPtr pRegion,
|
||||
unsigned int dest, unsigned int src)
|
||||
|
|
@ -175,10 +317,10 @@ DRI2CopyRegion(DrawablePtr pDraw, RegionPtr pRegion,
|
|||
pSrcBuffer = NULL;
|
||||
for (i = 0; i < pPriv->bufferCount; i++)
|
||||
{
|
||||
if (pPriv->buffers[i].attachment == dest)
|
||||
pDestBuffer = &pPriv->buffers[i];
|
||||
if (pPriv->buffers[i].attachment == src)
|
||||
pSrcBuffer = &pPriv->buffers[i];
|
||||
if (pPriv->buffers[i]->attachment == dest)
|
||||
pDestBuffer = pPriv->buffers[i];
|
||||
if (pPriv->buffers[i]->attachment == src)
|
||||
pSrcBuffer = pPriv->buffers[i];
|
||||
}
|
||||
if (pSrcBuffer == NULL || pDestBuffer == NULL)
|
||||
return BadValue;
|
||||
|
|
@ -204,7 +346,16 @@ DRI2DestroyDrawable(DrawablePtr pDraw)
|
|||
if (pPriv->refCount > 0)
|
||||
return;
|
||||
|
||||
(*ds->DestroyBuffers)(pDraw, pPriv->buffers, pPriv->bufferCount);
|
||||
if (pPriv->buffers != NULL) {
|
||||
int i;
|
||||
|
||||
for (i = 0; i < pPriv->bufferCount; i++) {
|
||||
(*ds->DestroyBuffer)(pDraw, pPriv->buffers[i]);
|
||||
}
|
||||
|
||||
xfree(pPriv->buffers);
|
||||
}
|
||||
|
||||
xfree(pPriv);
|
||||
|
||||
if (pDraw->type == DRAWABLE_WINDOW)
|
||||
|
|
@ -258,11 +409,18 @@ DRI2ScreenInit(ScreenPtr pScreen, DRI2InfoPtr info)
|
|||
if (!ds)
|
||||
return FALSE;
|
||||
|
||||
if ((info->version < 2)
|
||||
|| (info->CreateBuffer == NULL)
|
||||
|| (info->DestroyBuffer == NULL)) {
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
|
||||
ds->fd = info->fd;
|
||||
ds->driverName = info->driverName;
|
||||
ds->deviceName = info->deviceName;
|
||||
ds->CreateBuffers = info->CreateBuffers;
|
||||
ds->DestroyBuffers = info->DestroyBuffers;
|
||||
ds->CreateBuffer = info->CreateBuffer;
|
||||
ds->DestroyBuffer = info->DestroyBuffer;
|
||||
ds->CopyRegion = info->CopyRegion;
|
||||
|
||||
dixSetPrivate(&pScreen->devPrivates, dri2ScreenPrivateKey, ds);
|
||||
|
|
@ -309,7 +467,7 @@ static XF86ModuleVersionInfo DRI2VersRec =
|
|||
MODINFOSTRING1,
|
||||
MODINFOSTRING2,
|
||||
XORG_VERSION_CURRENT,
|
||||
1, 0, 0,
|
||||
1, 1, 0,
|
||||
ABI_CLASS_EXTENSION,
|
||||
ABI_EXTENSION_VERSION,
|
||||
MOD_CLASS_NONE,
|
||||
|
|
@ -318,3 +476,12 @@ static XF86ModuleVersionInfo DRI2VersRec =
|
|||
|
||||
_X_EXPORT XF86ModuleData dri2ModuleData = { &DRI2VersRec, DRI2Setup, NULL };
|
||||
|
||||
void
|
||||
DRI2Version(int *major, int *minor)
|
||||
{
|
||||
if (major != NULL)
|
||||
*major = DRI2VersRec.majorversion;
|
||||
|
||||
if (minor != NULL)
|
||||
*minor = DRI2VersRec.minorversion;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -41,6 +41,7 @@ typedef struct {
|
|||
unsigned int pitch;
|
||||
unsigned int cpp;
|
||||
unsigned int flags;
|
||||
unsigned int format;
|
||||
void *driverPrivate;
|
||||
} DRI2BufferRec, *DRI2BufferPtr;
|
||||
|
||||
|
|
@ -58,8 +59,19 @@ typedef void (*DRI2CopyRegionProcPtr)(DrawablePtr pDraw,
|
|||
typedef void (*DRI2WaitProcPtr)(WindowPtr pWin,
|
||||
unsigned int sequence);
|
||||
|
||||
typedef DRI2BufferPtr (*DRI2CreateBufferProcPtr)(DrawablePtr pDraw,
|
||||
unsigned int attachment,
|
||||
unsigned int format);
|
||||
typedef void (*DRI2DestroyBufferProcPtr)(DrawablePtr pDraw,
|
||||
DRI2BufferPtr buffer);
|
||||
|
||||
/**
|
||||
* Version of the DRI2InfoRec structure defined in this header
|
||||
*/
|
||||
#define DRI2INFOREC_VERSION 2
|
||||
|
||||
typedef struct {
|
||||
unsigned int version; /* Version of this struct */
|
||||
unsigned int version; /**< Version of this struct */
|
||||
int fd;
|
||||
const char *driverName;
|
||||
const char *deviceName;
|
||||
|
|
@ -69,6 +81,14 @@ typedef struct {
|
|||
DRI2CopyRegionProcPtr CopyRegion;
|
||||
DRI2WaitProcPtr Wait;
|
||||
|
||||
/**
|
||||
* \name Fields added in version 2 of the structure.
|
||||
*/
|
||||
/*@{*/
|
||||
DRI2CreateBufferProcPtr CreateBuffer;
|
||||
DRI2DestroyBufferProcPtr DestroyBuffer;
|
||||
/*@}*/
|
||||
|
||||
} DRI2InfoRec, *DRI2InfoPtr;
|
||||
|
||||
Bool DRI2ScreenInit(ScreenPtr pScreen,
|
||||
|
|
@ -88,7 +108,7 @@ int DRI2CreateDrawable(DrawablePtr pDraw);
|
|||
|
||||
void DRI2DestroyDrawable(DrawablePtr pDraw);
|
||||
|
||||
DRI2BufferPtr DRI2GetBuffers(DrawablePtr pDraw,
|
||||
DRI2BufferPtr *DRI2GetBuffers(DrawablePtr pDraw,
|
||||
int *width,
|
||||
int *height,
|
||||
unsigned int *attachments,
|
||||
|
|
@ -100,4 +120,26 @@ int DRI2CopyRegion(DrawablePtr pDraw,
|
|||
unsigned int dest,
|
||||
unsigned int src);
|
||||
|
||||
/**
|
||||
* Determine the major and minor version of the DRI2 extension.
|
||||
*
|
||||
* Provides a mechanism to other modules (e.g., 2D drivers) to determine the
|
||||
* version of the DRI2 extension. While it is possible to peek directly at
|
||||
* the \c XF86ModuleData from a layered module, such a module will fail to
|
||||
* load (due to an unresolved symbol) if the DRI2 extension is not loaded.
|
||||
*
|
||||
* \param major Location to store the major verion of the DRI2 extension
|
||||
* \param minor Location to store the minor verion of the DRI2 extension
|
||||
*
|
||||
* \note
|
||||
* This interface was added some time after the initial release of the DRI2
|
||||
* module. Layered modules that wish to use this interface must first test
|
||||
* its existance by calling \c xf86LoaderCheckSymbol.
|
||||
*/
|
||||
extern _X_EXPORT void DRI2Version(int *major, int *minor);
|
||||
|
||||
extern _X_EXPORT DRI2BufferPtr *DRI2GetBuffersWithFormat(DrawablePtr pDraw,
|
||||
int *width, int *height, unsigned int *attachments, int count,
|
||||
int *out_count);
|
||||
|
||||
#endif
|
||||
|
|
|
|||
|
|
@ -81,7 +81,7 @@ ProcDRI2QueryVersion(ClientPtr client)
|
|||
rep.length = 0;
|
||||
rep.sequenceNumber = client->sequence;
|
||||
rep.majorVersion = 1;
|
||||
rep.minorVersion = 0;
|
||||
rep.minorVersion = 1;
|
||||
|
||||
if (client->swapped) {
|
||||
swaps(&rep.sequenceNumber, n);
|
||||
|
|
@ -193,16 +193,62 @@ ProcDRI2DestroyDrawable(ClientPtr client)
|
|||
return client->noClientException;
|
||||
}
|
||||
|
||||
|
||||
static void
|
||||
send_buffers_reply(ClientPtr client, DrawablePtr pDrawable,
|
||||
DRI2BufferPtr *buffers, int count, int width, int height)
|
||||
{
|
||||
xDRI2GetBuffersReply rep;
|
||||
int skip = 0;
|
||||
int i;
|
||||
|
||||
if (pDrawable->type == DRAWABLE_WINDOW) {
|
||||
for (i = 0; i < count; i++) {
|
||||
/* Do not send the real front buffer of a window to the client.
|
||||
*/
|
||||
if (buffers[i]->attachment == DRI2BufferFrontLeft) {
|
||||
skip++;
|
||||
continue;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
rep.type = X_Reply;
|
||||
rep.length = (count - skip) * sizeof(xDRI2Buffer) / 4;
|
||||
rep.sequenceNumber = client->sequence;
|
||||
rep.width = width;
|
||||
rep.height = height;
|
||||
rep.count = count - skip;
|
||||
WriteToClient(client, sizeof(xDRI2GetBuffersReply), &rep);
|
||||
|
||||
for (i = 0; i < count; i++) {
|
||||
xDRI2Buffer buffer;
|
||||
|
||||
/* Do not send the real front buffer of a window to the client.
|
||||
*/
|
||||
if ((pDrawable->type == DRAWABLE_WINDOW)
|
||||
&& (buffers[i]->attachment == DRI2BufferFrontLeft)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
buffer.attachment = buffers[i]->attachment;
|
||||
buffer.name = buffers[i]->name;
|
||||
buffer.pitch = buffers[i]->pitch;
|
||||
buffer.cpp = buffers[i]->cpp;
|
||||
buffer.flags = buffers[i]->flags;
|
||||
WriteToClient(client, sizeof(xDRI2Buffer), &buffer);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
static int
|
||||
ProcDRI2GetBuffers(ClientPtr client)
|
||||
{
|
||||
REQUEST(xDRI2GetBuffersReq);
|
||||
xDRI2GetBuffersReply rep;
|
||||
DrawablePtr pDrawable;
|
||||
DRI2BufferPtr buffers;
|
||||
int i, status, width, height, count;
|
||||
DRI2BufferPtr *buffers;
|
||||
int status, width, height, count;
|
||||
unsigned int *attachments;
|
||||
xDRI2Buffer buffer;
|
||||
|
||||
REQUEST_FIXED_SIZE(xDRI2GetBuffersReq, stuff->count * 4);
|
||||
if (!validDrawable(client, stuff->drawable, &pDrawable, &status))
|
||||
|
|
@ -212,22 +258,30 @@ ProcDRI2GetBuffers(ClientPtr client)
|
|||
buffers = DRI2GetBuffers(pDrawable, &width, &height,
|
||||
attachments, stuff->count, &count);
|
||||
|
||||
rep.type = X_Reply;
|
||||
rep.length = count * sizeof(xDRI2Buffer) / 4;
|
||||
rep.sequenceNumber = client->sequence;
|
||||
rep.width = width;
|
||||
rep.height = height;
|
||||
rep.count = count;
|
||||
WriteToClient(client, sizeof(xDRI2GetBuffersReply), &rep);
|
||||
|
||||
for (i = 0; i < count; i++) {
|
||||
buffer.attachment = buffers[i].attachment;
|
||||
buffer.name = buffers[i].name;
|
||||
buffer.pitch = buffers[i].pitch;
|
||||
buffer.cpp = buffers[i].cpp;
|
||||
buffer.flags = buffers[i].flags;
|
||||
WriteToClient(client, sizeof(xDRI2Buffer), &buffer);
|
||||
}
|
||||
send_buffers_reply(client, pDrawable, buffers, count, width, height);
|
||||
|
||||
return client->noClientException;
|
||||
}
|
||||
|
||||
static int
|
||||
ProcDRI2GetBuffersWithFormat(ClientPtr client)
|
||||
{
|
||||
REQUEST(xDRI2GetBuffersReq);
|
||||
DrawablePtr pDrawable;
|
||||
DRI2BufferPtr *buffers;
|
||||
int status, width, height, count;
|
||||
unsigned int *attachments;
|
||||
|
||||
REQUEST_FIXED_SIZE(xDRI2GetBuffersReq, stuff->count * (2 * 4));
|
||||
if (!validDrawable(client, stuff->drawable, &pDrawable, &status))
|
||||
return status;
|
||||
|
||||
attachments = (unsigned int *) &stuff[1];
|
||||
buffers = DRI2GetBuffersWithFormat(pDrawable, &width, &height,
|
||||
attachments, stuff->count, &count);
|
||||
|
||||
send_buffers_reply(client, pDrawable, buffers, count, width, height);
|
||||
|
||||
return client->noClientException;
|
||||
}
|
||||
|
|
@ -294,6 +348,8 @@ ProcDRI2Dispatch (ClientPtr client)
|
|||
return ProcDRI2GetBuffers(client);
|
||||
case X_DRI2CopyRegion:
|
||||
return ProcDRI2CopyRegion(client);
|
||||
case X_DRI2GetBuffersWithFormat:
|
||||
return ProcDRI2GetBuffersWithFormat(client);
|
||||
default:
|
||||
return BadRequest;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -628,6 +628,85 @@ DDCModesFromCVT(int scrnIndex, struct cvt_timings *t)
|
|||
}
|
||||
#endif
|
||||
|
||||
static const struct {
|
||||
short w;
|
||||
short h;
|
||||
short r;
|
||||
short rb;
|
||||
} EstIIIModes[] = {
|
||||
/* byte 6 */
|
||||
{ 640, 350, 85, 0 },
|
||||
{ 640, 400, 85, 0 },
|
||||
{ 720, 400, 85, 0 },
|
||||
{ 640, 480, 85, 0 },
|
||||
{ 848, 480, 60, 0 },
|
||||
{ 800, 600, 85, 0 },
|
||||
{ 1024, 768, 85, 0 },
|
||||
{ 1152, 864, 75, 0 },
|
||||
/* byte 7 */
|
||||
{ 1280, 768, 60, 1 },
|
||||
{ 1280, 768, 60, 0 },
|
||||
{ 1280, 768, 75, 0 },
|
||||
{ 1280, 768, 85, 0 },
|
||||
{ 1280, 960, 60, 0 },
|
||||
{ 1280, 960, 85, 0 },
|
||||
{ 1280, 1024, 60, 0 },
|
||||
{ 1280, 1024, 85, 0 },
|
||||
/* byte 8 */
|
||||
{ 1360, 768, 60, 0 },
|
||||
{ 1440, 900, 60, 1 },
|
||||
{ 1440, 900, 60, 0 },
|
||||
{ 1440, 900, 75, 0 },
|
||||
{ 1440, 900, 85, 0 },
|
||||
{ 1400, 1050, 60, 1 },
|
||||
{ 1400, 1050, 60, 0 },
|
||||
{ 1400, 1050, 75, 0 },
|
||||
/* byte 9 */
|
||||
{ 1400, 1050, 85, 0 },
|
||||
{ 1680, 1050, 60, 1 },
|
||||
{ 1680, 1050, 60, 0 },
|
||||
{ 1680, 1050, 75, 0 },
|
||||
{ 1680, 1050, 85, 0 },
|
||||
{ 1600, 1200, 60, 0 },
|
||||
{ 1600, 1200, 65, 0 },
|
||||
{ 1600, 1200, 70, 0 },
|
||||
/* byte 10 */
|
||||
{ 1600, 1200, 75, 0 },
|
||||
{ 1600, 1200, 85, 0 },
|
||||
{ 1792, 1344, 60, 0 },
|
||||
{ 1792, 1344, 85, 0 },
|
||||
{ 1856, 1392, 60, 0 },
|
||||
{ 1856, 1392, 75, 0 },
|
||||
{ 1920, 1200, 60, 1 },
|
||||
{ 1920, 1200, 60, 0 },
|
||||
/* byte 11 */
|
||||
{ 1920, 1200, 75, 0 },
|
||||
{ 1920, 1200, 85, 0 },
|
||||
{ 1920, 1440, 60, 0 },
|
||||
{ 1920, 1440, 75, 0 },
|
||||
};
|
||||
|
||||
static DisplayModePtr
|
||||
DDCModesFromEstIII(unsigned char *est)
|
||||
{
|
||||
DisplayModePtr modes = NULL;
|
||||
int i, j, m;
|
||||
|
||||
for (i = 0; i < 6; i++) {
|
||||
for (j = 7; j > 0; j--) {
|
||||
if (est[i] & (1 << j)) {
|
||||
m = (i * 8) + (7 - j);
|
||||
modes = xf86ModesAdd(modes,
|
||||
FindDMTMode(EstIIIModes[m].w,
|
||||
EstIIIModes[m].h,
|
||||
EstIIIModes[m].r,
|
||||
EstIIIModes[m].rb));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return modes;
|
||||
}
|
||||
|
||||
/*
|
||||
* This is only valid when the sink claims to be continuous-frequency
|
||||
|
|
@ -798,6 +877,7 @@ xf86DDCGetModes(int scrnIndex, xf86MonPtr DDC)
|
|||
for (i = 0; i < DET_TIMINGS; i++) {
|
||||
struct detailed_monitor_section *det_mon = &DDC->det_mon[i];
|
||||
|
||||
Mode = NULL;
|
||||
switch (det_mon->type) {
|
||||
case DT:
|
||||
Mode = DDCModeFromDetailedTiming(scrnIndex,
|
||||
|
|
@ -805,22 +885,23 @@ xf86DDCGetModes(int scrnIndex, xf86MonPtr DDC)
|
|||
preferred,
|
||||
quirks);
|
||||
preferred = FALSE;
|
||||
Modes = xf86ModesAdd(Modes, Mode);
|
||||
break;
|
||||
case DS_STD_TIMINGS:
|
||||
Mode = DDCModesFromStandardTiming(det_mon->section.std_t,
|
||||
quirks, timing_level, rb);
|
||||
Modes = xf86ModesAdd(Modes, Mode);
|
||||
break;
|
||||
#if XORG_VERSION_CURRENT < XORG_VERSION_NUMERIC(7,0,0,0,0)
|
||||
case DS_CVT:
|
||||
Mode = DDCModesFromCVT(scrnIndex, det_mon->section.cvt);
|
||||
Modes = xf86ModesAdd(Modes, Mode);
|
||||
break;
|
||||
#endif
|
||||
case DS_EST_III:
|
||||
Mode = DDCModesFromEstIII(det_mon->section.est_iii);
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
Modes = xf86ModesAdd(Modes, Mode);
|
||||
}
|
||||
|
||||
/* Add established timings */
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue