Add DRI2 support.

Add EXA stubs.

Currently tested with i915.
This commit is contained in:
Alan Hourihane 2008-06-16 15:07:39 +01:00
parent 6a1910a0e5
commit 47969d7928
7 changed files with 521 additions and 123 deletions

View File

@ -37,6 +37,7 @@ modesetting_drv_la_SOURCES = \
driver.h \ driver.h \
output.c \ output.c \
crtc.c \ crtc.c \
exa.c exa.c \
dri2.c
EXTRA_DIST = EXTRA_DIST =

View File

@ -168,8 +168,11 @@ crtc_destroy(xf86CrtcPtr crtc)
modesettingPtr ms = modesettingPTR(crtc->scrn); modesettingPtr ms = modesettingPTR(crtc->scrn);
struct crtc_private *crtcp = crtc->driver_private; struct crtc_private *crtcp = crtc->driver_private;
drmBOUnreference(ms->fd, &crtcp->cursor_bo); if (crtcp->cursor_bo.handle)
drmBOUnreference(ms->fd, &crtcp->cursor_bo);
drmModeFreeCrtc(crtcp->drm_crtc); drmModeFreeCrtc(crtcp->drm_crtc);
xfree(crtcp);
} }
static void static void
@ -179,9 +182,17 @@ crtc_load_cursor_argb (xf86CrtcPtr crtc, CARD32 *image)
modesettingPtr ms = modesettingPTR(crtc->scrn); modesettingPtr ms = modesettingPTR(crtc->scrn);
struct crtc_private *crtcp = crtc->driver_private; struct crtc_private *crtcp = crtc->driver_private;
drmBOMap(ms->fd, &crtcp->cursor_bo, DRM_BO_FLAG_WRITE, 0, (void **)&ptr); if (!crtcp->cursor_bo.handle)
drmBOCreate(ms->fd, 64 * 64 * 4, 0, NULL,
DRM_BO_FLAG_READ | DRM_BO_FLAG_WRITE
| DRM_BO_FLAG_NO_EVICT | DRM_BO_FLAG_MAPPABLE |
DRM_BO_FLAG_MEM_VRAM,
DRM_BO_HINT_DONT_FENCE, &crtcp->cursor_bo);
memcpy (ptr, image, 64 * 64 * 4); drmBOMap(ms->fd, &crtcp->cursor_bo, DRM_BO_FLAG_WRITE, DRM_BO_HINT_DONT_FENCE, (void **)&ptr);
if (ptr)
memcpy (ptr, image, 64 * 64 * 4);
drmBOUnmap(ms->fd, &crtcp->cursor_bo); drmBOUnmap(ms->fd, &crtcp->cursor_bo);
} }
@ -201,7 +212,8 @@ crtc_show_cursor (xf86CrtcPtr crtc)
modesettingPtr ms = modesettingPTR(crtc->scrn); modesettingPtr ms = modesettingPTR(crtc->scrn);
struct crtc_private *crtcp = crtc->driver_private; struct crtc_private *crtcp = crtc->driver_private;
drmModeSetCursor(ms->fd, crtcp->drm_crtc->crtc_id, crtcp->cursor_bo.handle, 64, 64); if (crtcp->cursor_bo.handle)
drmModeSetCursor(ms->fd, crtcp->drm_crtc->crtc_id, crtcp->cursor_bo.handle, 64, 64);
} }
static void static void
@ -213,12 +225,6 @@ crtc_hide_cursor (xf86CrtcPtr crtc)
drmModeSetCursor(ms->fd, crtcp->drm_crtc->crtc_id, 0, 0, 0); drmModeSetCursor(ms->fd, crtcp->drm_crtc->crtc_id, 0, 0, 0);
} }
static void
crtc_set_cursor_colors (xf86CrtcPtr crtc, int bg, int fg)
{
ScrnInfoPtr scrn = crtc->scrn;
}
static const xf86CrtcFuncsRec crtc_funcs = { static const xf86CrtcFuncsRec crtc_funcs = {
.dpms = crtc_dpms, .dpms = crtc_dpms,
.save = NULL, .save = NULL,
@ -233,15 +239,27 @@ static const xf86CrtcFuncsRec crtc_funcs = {
.shadow_create = crtc_shadow_create, .shadow_create = crtc_shadow_create,
.shadow_allocate = crtc_shadow_allocate, .shadow_allocate = crtc_shadow_allocate,
.shadow_destroy = crtc_shadow_destroy, .shadow_destroy = crtc_shadow_destroy,
.set_cursor_colors = crtc_set_cursor_colors,
.set_cursor_position = crtc_set_cursor_position, .set_cursor_position = crtc_set_cursor_position,
.show_cursor = crtc_show_cursor, .show_cursor = crtc_show_cursor,
.hide_cursor = crtc_hide_cursor, .hide_cursor = crtc_hide_cursor,
.load_cursor_image = NULL, /* lets convert to argb only */ .load_cursor_image = NULL, /* lets convert to argb only */
.set_cursor_colors = NULL, /* using argb only */
.load_cursor_argb = crtc_load_cursor_argb, .load_cursor_argb = crtc_load_cursor_argb,
.destroy = crtc_destroy, .destroy = crtc_destroy,
}; };
void
cursor_destroy(xf86CrtcPtr crtc)
{
modesettingPtr ms = modesettingPTR(crtc->scrn);
struct crtc_private *crtcp = crtc->driver_private;
if (crtcp->cursor_bo.handle) {
drmBOSetStatus(ms->fd, &crtcp->cursor_bo, 0, 0, 0, 0, 0);
drmBOUnreference(ms->fd, &crtcp->cursor_bo);
}
}
void void
crtc_init(ScrnInfoPtr pScrn) crtc_init(ScrnInfoPtr pScrn)
{ {
@ -267,7 +285,7 @@ crtc_init(ScrnInfoPtr pScrn)
if (crtc == NULL) if (crtc == NULL)
goto out; goto out;
crtcp = xalloc(sizeof(struct crtc_private)); crtcp = xcalloc(1, sizeof(struct crtc_private));
if (!crtcp) { if (!crtcp) {
xf86CrtcDestroy(crtc); xf86CrtcDestroy(crtc);
goto out; goto out;
@ -277,11 +295,6 @@ crtc_init(ScrnInfoPtr pScrn)
crtc->driver_private = crtcp; crtc->driver_private = crtcp;
drmBOCreate(ms->fd, 64 * 64 * 4, 0, NULL,
DRM_BO_FLAG_READ | DRM_BO_FLAG_WRITE
| DRM_BO_FLAG_NO_EVICT | DRM_BO_FLAG_MAPPABLE |
DRM_BO_FLAG_MEM_VRAM | DRM_BO_FLAG_MEM_TT,
DRM_BO_HINT_DONT_FENCE, &crtcp->cursor_bo);
} }
out: out:

View File

@ -0,0 +1,127 @@
/*
* Copyright 2008 Tungsten Graphics, Inc., Cedar Park, Texas.
* All Rights Reserved.
*
* Permission is hereby granted, free of charge, to any person obtaining a
* copy of this software and associated documentation files (the
* "Software"), to deal in the Software without restriction, including
* without limitation the rights to use, copy, modify, merge, publish,
* distribute, sub license, and/or sell copies of the Software, and to
* permit persons to whom the Software is furnished to do so, subject to
* the following conditions:
*
* The above copyright notice and this permission notice (including the
* next paragraph) shall be included in all copies or substantial portions
* of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
* OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT.
* IN NO EVENT SHALL TUNGSTEN GRAPHICS AND/OR ITS SUPPLIERS BE LIABLE FOR
* ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*
*
* Author: Alan Hourihane <alanh@tungstengraphics.com>
*
*/
#ifdef HAVE_CONFIG_H
#include "config.h"
#endif
#include "xf86.h"
#include "xf86_OSproc.h"
#include "driver.h"
#include "dri2.h"
extern unsigned int
driGetPixmapHandle(PixmapPtr pPixmap, unsigned int *flags);
void
driLock(ScreenPtr pScreen)
{
ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum];
modesettingPtr ms = modesettingPTR(pScrn);
if (!ms->lock_held)
DRM_LOCK(ms->fd, ms->lock, ms->context, 0);
ms->lock_held = 1;
}
void
driUnlock(ScreenPtr pScreen)
{
ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum];
modesettingPtr ms = modesettingPTR(pScrn);
if (ms->lock_held)
DRM_UNLOCK(ms->fd, ms->lock, ms->context);
ms->lock_held = 0;
}
static void
driBeginClipNotify(ScreenPtr pScreen)
{
driLock(pScreen);
}
static void
driEndClipNotify(ScreenPtr pScreen)
{
driUnlock(pScreen);
}
struct __DRILock {
unsigned int block_header;
drm_hw_lock_t lock;
unsigned int next_id;
};
#define DRI2_SAREA_BLOCK_HEADER(type, size) (((type) << 16) | (size))
#define DRI2_SAREA_BLOCK_LOCK 0x0001
void
driScreenInit(ScreenPtr pScreen)
{
ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum];
modesettingPtr ms = modesettingPTR(pScrn);
DRI2InfoRec dri2info;
const char *driverName;
unsigned int sarea_handle;
struct __DRILock *DRILock;
void *p;
dri2info.version = 1;
dri2info.fd = ms->fd;
dri2info.driverSareaSize = sizeof(struct __DRILock);
dri2info.driverName = "i915"; /* FIXME */
dri2info.getPixmapHandle = driGetPixmapHandle;
dri2info.beginClipNotify = driBeginClipNotify;
dri2info.endClipNotify = driEndClipNotify;
p = DRI2ScreenInit(pScreen, &dri2info);
if (!p)
return;
DRILock = p;
DRILock->block_header =
DRI2_SAREA_BLOCK_HEADER(DRI2_SAREA_BLOCK_LOCK, sizeof *DRILock);
ms->lock = &DRILock->lock;
ms->context = 1;
DRILock->next_id = 2;
driLock(pScreen);
DRI2Connect(pScreen, &ms->fd, &driverName, &sarea_handle);
}
void
driCloseScreen(ScreenPtr pScreen)
{
driUnlock(pScreen);
DRI2CloseScreen(pScreen);
}

View File

@ -132,6 +132,16 @@ static const OptionInfoRec Options[] = {
{-1, NULL, OPTV_NONE, {0}, FALSE} {-1, NULL, OPTV_NONE, {0}, FALSE}
}; };
static const char *exaSymbols[] = {
"exaGetVersion",
"exaDriverInit",
"exaDriverFini",
"exaOffscreenAlloc",
"exaOffscreenFree",
"exaWaitSync",
NULL
};
static const char *fbSymbols[] = { static const char *fbSymbols[] = {
"fbPictureInit", "fbPictureInit",
"fbScreenInit", "fbScreenInit",
@ -190,7 +200,7 @@ Setup(pointer module, pointer opts, int *errmaj, int *errmin)
* Tell the loader about symbols from other modules that this module * Tell the loader about symbols from other modules that this module
* might refer to. * might refer to.
*/ */
LoaderRefSymLists(fbSymbols, shadowSymbols, ddcSymbols, NULL); LoaderRefSymLists(exaSymbols, fbSymbols, shadowSymbols, ddcSymbols, NULL);
/* /*
* The return value must be non-NULL on success even though there * The return value must be non-NULL on success even though there
@ -417,6 +427,8 @@ MapMem(ScrnInfoPtr pScrn)
drmBOMap(ms->fd, drmBOMap(ms->fd,
&ms->bo, DRM_BO_FLAG_READ | DRM_BO_FLAG_WRITE, 0, &ms->virtual); &ms->bo, DRM_BO_FLAG_READ | DRM_BO_FLAG_WRITE, 0, &ms->virtual);
ms->virtual = ms->bo.virtual;
return TRUE; return TRUE;
} }
@ -438,7 +450,7 @@ LoadPalette(ScrnInfoPtr pScrn, int numColors, int *indices,
} }
static Bool static Bool
crtc_resize(ScrnInfoPtr pScrn, int width, int height) CreateFrontBuffer(ScrnInfoPtr pScrn)
{ {
modesettingPtr ms = modesettingPTR(pScrn); modesettingPtr ms = modesettingPTR(pScrn);
ScreenPtr pScreen = pScrn->pScreen; ScreenPtr pScreen = pScrn->pScreen;
@ -446,37 +458,14 @@ crtc_resize(ScrnInfoPtr pScrn, int width, int height)
Bool fbAccessDisabled; Bool fbAccessDisabled;
CARD8 *fbstart; CARD8 *fbstart;
if (width == pScrn->virtualX && height == pScrn->virtualY)
return TRUE;
ErrorF("RESIZING TO %dx%d\n", width, height);
pScrn->virtualX = width;
pScrn->virtualY = height;
pScrn->displayWidth = (pScrn->virtualX + 63) & ~63;
if (ms->shadowMem) {
xfree(ms->shadowMem);
ms->shadowMem = NULL;
}
UnmapMem(pScrn);
/* move old buffer out of the way */
drmBOSetStatus(ms->fd, &ms->bo, DRM_BO_FLAG_READ | DRM_BO_FLAG_MEM_LOCAL,
DRM_BO_MASK_MEM | DRM_BO_FLAG_NO_EVICT,
DRM_BO_HINT_DONT_FENCE, 0, 0);
/* unreference it */
drmBOUnreference(ms->fd, &ms->bo);
drmBOCreate(ms->fd, drmBOCreate(ms->fd,
pScrn->virtualY * pScrn->displayWidth * pScrn->virtualY * pScrn->displayWidth *
pScrn->bitsPerPixel / 8, 0, NULL, pScrn->bitsPerPixel / 8, 0, NULL,
DRM_BO_FLAG_READ | DRM_BO_FLAG_WRITE | DRM_BO_FLAG_SHAREABLE DRM_BO_FLAG_READ | DRM_BO_FLAG_WRITE | DRM_BO_FLAG_SHAREABLE
| DRM_BO_FLAG_CACHED_MAPPED
| DRM_BO_FLAG_NO_EVICT | DRM_BO_FLAG_MAPPABLE | | DRM_BO_FLAG_NO_EVICT | DRM_BO_FLAG_MAPPABLE |
DRM_BO_FLAG_MEM_VRAM | DRM_BO_FLAG_MEM_TT, /*DRM_BO_FLAG_MEM_VRAM |*/ DRM_BO_FLAG_MEM_TT,
DRM_BO_HINT_DONT_FENCE, &ms->bo); 0, &ms->bo);
MapMem(pScrn); MapMem(pScrn);
@ -498,7 +487,7 @@ crtc_resize(ScrnInfoPtr pScrn, int width, int height)
} }
fbstart = ms->shadowMem; fbstart = ms->shadowMem;
} else { } else {
fbstart = ms->virtual; fbstart = ms->bo.virtual;
} }
/* /*
@ -526,9 +515,49 @@ crtc_resize(ScrnInfoPtr pScrn, int width, int height)
pScrn->frameY0 = 0; pScrn->frameY0 = 0;
AdjustFrame(pScrn->scrnIndex, pScrn->frameX0, pScrn->frameY0, 0); AdjustFrame(pScrn->scrnIndex, pScrn->frameX0, pScrn->frameY0, 0);
UnmapMem(pScrn);
ms->front = TRUE;
return TRUE; return TRUE;
} }
static Bool
crtc_resize(ScrnInfoPtr pScrn, int width, int height)
{
modesettingPtr ms = modesettingPTR(pScrn);
ScreenPtr pScreen = pScrn->pScreen;
PixmapPtr rootPixmap = pScreen->GetScreenPixmap(pScreen);
Bool fbAccessDisabled;
CARD8 *fbstart;
if (width == pScrn->virtualX && height == pScrn->virtualY)
return TRUE;
ErrorF("RESIZING TO %dx%d\n", width, height);
pScrn->virtualX = width;
pScrn->virtualY = height;
pScrn->displayWidth = (pScrn->virtualX + 63) & ~63;
if (ms->shadowMem) {
xfree(ms->shadowMem);
ms->shadowMem = NULL;
}
drmModeRmFB(ms->fd, ms->fb_id);
/* move old buffer out of the way */
drmBOSetStatus(ms->fd, &ms->bo, 0, 0, 0, 0, 0);
/* unreference it */
drmBOUnreference(ms->fd, &ms->bo);
ms->front = FALSE;
/* now create new frontbuffer */
return CreateFrontBuffer(pScrn);
}
static const xf86CrtcConfigFuncsRec crtc_config_funcs = { static const xf86CrtcConfigFuncsRec crtc_config_funcs = {
crtc_resize crtc_resize
}; };
@ -713,6 +742,12 @@ PreInit(ScrnInfoPtr pScrn, int flags)
xf86LoaderReqSymLists(fbSymbols, NULL); xf86LoaderReqSymLists(fbSymbols, NULL);
xf86LoadSubModule(pScrn, "exa");
#ifdef DRI2
xf86LoadSubModule(pScrn, "dri2");
#endif
return TRUE; return TRUE;
} }
@ -744,7 +779,7 @@ WindowLinear(ScreenPtr pScreen, CARD32 row, CARD32 offset, int mode,
*size = pScrn->displayWidth * pScrn->bitsPerPixel / 8; *size = pScrn->displayWidth * pScrn->bitsPerPixel / 8;
return ((CARD8 *) ms->virtual + row * (*size) + offset); return ((CARD8 *) ms->bo.virtual + row * (*size) + offset);
} }
static Bool static Bool
@ -752,15 +787,23 @@ CreateScreenResources(ScreenPtr pScreen)
{ {
ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum]; ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum];
modesettingPtr ms = modesettingPTR(pScrn); modesettingPtr ms = modesettingPTR(pScrn);
PixmapPtr rootPixmap = pScreen->GetScreenPixmap(pScreen);
Bool ret; Bool ret;
pScreen->CreateScreenResources = ms->createScreenResources; pScreen->CreateScreenResources = ms->createScreenResources;
ret = pScreen->CreateScreenResources(pScreen); ret = pScreen->CreateScreenResources(pScreen);
pScreen->CreateScreenResources = CreateScreenResources; pScreen->CreateScreenResources = CreateScreenResources;
shadowAdd(pScreen, pScreen->GetScreenPixmap(pScreen), if (ms->shadowFB)
shadowAdd(pScreen, rootPixmap,
ms->update, WindowLinear, 0, 0); ms->update, WindowLinear, 0, 0);
if (!pScreen->ModifyPixmapHeader(pScreen->GetScreenPixmap(pScreen),
-1, -1, -1, -1, -1,
ms->shadowFB ? (pointer)ms->shadowMem : (pointer)ms->bo.virtual))
FatalError("Couldn't adjust screen pixmap\n");
return ret; return ret;
} }
@ -775,6 +818,30 @@ ScreenInit(int scrnIndex, ScreenPtr pScreen, int argc, char **argv)
MessageType from; MessageType from;
CARD8 *fbstart; CARD8 *fbstart;
/* deal with server regeneration */
if (ms->fd < 0) {
char *BusID;
BusID = xalloc(64);
sprintf(BusID, "PCI:%d:%d:%d",
#if XSERVER_LIBPCIACCESS
((ms->PciInfo->domain << 8) | ms->PciInfo->bus),
ms->PciInfo->dev, ms->PciInfo->func
#else
((pciConfigPtr) ms->PciInfo->thisCard)->busnum,
((pciConfigPtr) ms->PciInfo->thisCard)->devnum,
((pciConfigPtr) ms->PciInfo->thisCard)->funcnum
#endif
);
ms->fd = drmOpen(NULL, BusID);
if (ms->fd < 0)
return FALSE;
}
pScrn->pScreen = pScreen;
pScrn->displayWidth = (pScrn->virtualX + 63) & ~63; pScrn->displayWidth = (pScrn->virtualX + 63) & ~63;
miClearVisualTypes(); miClearVisualTypes();
@ -787,9 +854,6 @@ ScreenInit(int scrnIndex, ScreenPtr pScreen, int argc, char **argv)
if (!miSetPixmapDepths()) if (!miSetPixmapDepths())
return FALSE; return FALSE;
if (!MapMem(pScrn))
return FALSE;
pScrn->memPhysBase = 0; pScrn->memPhysBase = 0;
pScrn->fbOffset = 0; pScrn->fbOffset = 0;
@ -797,9 +861,10 @@ ScreenInit(int scrnIndex, ScreenPtr pScreen, int argc, char **argv)
pScrn->virtualY * pScrn->displayWidth * pScrn->virtualY * pScrn->displayWidth *
pScrn->bitsPerPixel / 8, 0, NULL, pScrn->bitsPerPixel / 8, 0, NULL,
DRM_BO_FLAG_READ | DRM_BO_FLAG_WRITE | DRM_BO_FLAG_SHAREABLE DRM_BO_FLAG_READ | DRM_BO_FLAG_WRITE | DRM_BO_FLAG_SHAREABLE
| DRM_BO_FLAG_CACHED_MAPPED
| DRM_BO_FLAG_NO_EVICT | DRM_BO_FLAG_MAPPABLE | | DRM_BO_FLAG_NO_EVICT | DRM_BO_FLAG_MAPPABLE |
DRM_BO_FLAG_MEM_VRAM | DRM_BO_FLAG_MEM_TT, /*DRM_BO_FLAG_MEM_VRAM |*/ DRM_BO_FLAG_MEM_TT,
DRM_BO_HINT_DONT_FENCE, &ms->bo); 0, &ms->bo);
MapMem(pScrn); MapMem(pScrn);
@ -821,7 +886,7 @@ ScreenInit(int scrnIndex, ScreenPtr pScreen, int argc, char **argv)
} }
fbstart = ms->shadowMem; fbstart = ms->shadowMem;
} else { } else {
fbstart = ms->virtual; fbstart = ms->bo.virtual;
} }
if (!fbScreenInit(pScreen, fbstart, if (!fbScreenInit(pScreen, fbstart,
@ -853,18 +918,18 @@ ScreenInit(int scrnIndex, ScreenPtr pScreen, int argc, char **argv)
"Shadow framebuffer initialization failed.\n"); "Shadow framebuffer initialization failed.\n");
return FALSE; return FALSE;
} }
ms->createScreenResources = pScreen->CreateScreenResources;
pScreen->CreateScreenResources = CreateScreenResources;
} }
ms->createScreenResources = pScreen->CreateScreenResources;
pScreen->CreateScreenResources = CreateScreenResources;
xf86SetBlackWhitePixels(pScreen); xf86SetBlackWhitePixels(pScreen);
#if 0 #if 0
glucoseScreenInit(pScreen, 0); glucoseScreenInit(pScreen, 0);
#endif #endif
#if 0 #if 1
ms->pExa = ExaInit(pScreen); ms->pExa = ExaInit(pScrn);
#endif #endif
miInitializeBackingStore(pScreen); miInitializeBackingStore(pScreen);
@ -872,8 +937,9 @@ ScreenInit(int scrnIndex, ScreenPtr pScreen, int argc, char **argv)
xf86SetSilkenMouse(pScreen); xf86SetSilkenMouse(pScreen);
miDCInitialize(pScreen, xf86GetPointerScreenFuncs()); miDCInitialize(pScreen, xf86GetPointerScreenFuncs());
/* Need to extend HWcursor support in kernel to handle mask interleave ?? */ /* Need to extend HWcursor support to handle mask interleave */
xf86_cursors_init (pScreen, 64, 64, if (!ms->SWCursor)
xf86_cursors_init (pScreen, 64, 64,
HARDWARE_CURSOR_SOURCE_MASK_INTERLEAVE_64 | HARDWARE_CURSOR_SOURCE_MASK_INTERLEAVE_64 |
HARDWARE_CURSOR_ARGB); HARDWARE_CURSOR_ARGB);
@ -908,6 +974,14 @@ ScreenInit(int scrnIndex, ScreenPtr pScreen, int argc, char **argv)
if (serverGeneration == 1) if (serverGeneration == 1)
xf86ShowUnusedOptions(pScrn->scrnIndex, pScrn->options); xf86ShowUnusedOptions(pScrn->scrnIndex, pScrn->options);
#ifdef DRI2
driScreenInit(pScreen);
#endif
UnmapMem(pScrn);
ms->front = TRUE;
return EnterVT(scrnIndex, 0); return EnterVT(scrnIndex, 0);
} }
@ -944,6 +1018,8 @@ LeaveVT(int scrnIndex, int flags)
for (o = 0; o < config->num_crtc; o++) { for (o = 0; o < config->num_crtc; o++) {
xf86CrtcPtr crtc = config->crtc[o]; xf86CrtcPtr crtc = config->crtc[o];
cursor_destroy(crtc);
if (crtc->rotatedPixmap || crtc->rotatedData) { if (crtc->rotatedPixmap || crtc->rotatedData) {
crtc->funcs->shadow_destroy(crtc, crtc->rotatedPixmap, crtc->funcs->shadow_destroy(crtc, crtc->rotatedPixmap,
crtc->rotatedData); crtc->rotatedData);
@ -952,11 +1028,25 @@ LeaveVT(int scrnIndex, int flags)
} }
} }
xf86_hide_cursors(pScrn); drmModeRmFB(ms->fd, ms->fb_id);
drmMMLock(ms->fd, DRM_BO_MEM_VRAM, 1, 0); /* move old buffer out of the way */
drmBOSetStatus(ms->fd, &ms->bo, 0, 0, 0, 0, 0);
drmBOUnreference(ms->fd, &ms->bo);
ms->front = FALSE;
RestoreHWState(pScrn); RestoreHWState(pScrn);
#if 0
drmMMLock(ms->fd, DRM_BO_MEM_VRAM, 1, 0);
drmMMLock(ms->fd, DRM_BO_MEM_TT, 1, 0);
#endif
#ifdef DRI2
driLock(pScrn->pScreen);
#endif
pScrn->vtSema = FALSE;
} }
/* /*
@ -968,6 +1058,17 @@ EnterVT(int scrnIndex, int flags)
ScrnInfoPtr pScrn = xf86Screens[scrnIndex]; ScrnInfoPtr pScrn = xf86Screens[scrnIndex];
modesettingPtr ms = modesettingPTR(pScrn); modesettingPtr ms = modesettingPTR(pScrn);
#if 0
if (pScrn->vtSema) {
drmMMUnlock(ms->fd, DRM_BO_MEM_VRAM, 1);
drmMMUnlock(ms->fd, DRM_BO_MEM_TT, 1);
}
#endif
#ifdef DRI2
driUnlock(pScrn->pScreen);
#endif
/* /*
* Only save state once per server generation since that's what most * Only save state once per server generation since that's what most
* drivers do. Could change this to save state at each VT enter. * drivers do. Could change this to save state at each VT enter.
@ -977,7 +1078,8 @@ EnterVT(int scrnIndex, int flags)
SaveHWState(pScrn); SaveHWState(pScrn);
} }
drmMMUnlock(ms->fd, DRM_BO_MEM_VRAM, 1); if (!ms->front)
CreateFrontBuffer(pScrn);
if (!xf86SetDesiredModes(pScrn)) if (!xf86SetDesiredModes(pScrn))
return FALSE; return FALSE;
@ -1001,15 +1103,19 @@ CloseScreen(int scrnIndex, ScreenPtr pScreen)
ScrnInfoPtr pScrn = xf86Screens[scrnIndex]; ScrnInfoPtr pScrn = xf86Screens[scrnIndex];
modesettingPtr ms = modesettingPTR(pScrn); modesettingPtr ms = modesettingPTR(pScrn);
if (pScrn->vtSema == TRUE) { if (pScrn->vtSema) {
LeaveVT(scrnIndex, 0); LeaveVT(scrnIndex, 0);
drmMMUnlock(ms->fd, DRM_BO_MEM_VRAM, 1); #if 0
drmMMUnlock(ms->fd, DRM_BO_MEM_VRAM, 1);
drmMMUnlock(ms->fd, DRM_BO_MEM_TT, 1);
#endif
} }
UnmapMem(pScrn); #ifdef DRI2
driCloseScreen(pScreen);
#endif
if (ms->shadowFB) pScreen->CreateScreenResources = ms->createScreenResources;
pScreen->CreateScreenResources = ms->createScreenResources;
if (ms->shadowMem) { if (ms->shadowMem) {
xfree(ms->shadowMem); xfree(ms->shadowMem);
@ -1019,14 +1125,8 @@ CloseScreen(int scrnIndex, ScreenPtr pScreen)
if (ms->pExa) if (ms->pExa)
ExaClose(pScrn); ExaClose(pScrn);
/* move old buffer out of the way */
drmBOSetStatus(ms->fd, &ms->bo, DRM_BO_FLAG_READ | DRM_BO_FLAG_MEM_LOCAL,
DRM_BO_MASK_MEM | DRM_BO_FLAG_NO_EVICT,
DRM_BO_HINT_DONT_FENCE, 0, 0);
drmBOUnreference(ms->fd, &ms->bo);
drmClose(ms->fd); drmClose(ms->fd);
ms->fd = -1;
pScrn->vtSema = FALSE; pScrn->vtSema = FALSE;
pScreen->CloseScreen = ms->CloseScreen; pScreen->CloseScreen = ms->CloseScreen;

View File

@ -31,6 +31,7 @@
#include <drm.h> #include <drm.h>
#include <xf86drm.h> #include <xf86drm.h>
#include <xf86drmMode.h> #include <xf86drmMode.h>
#include <xf86mm.h>
#include "shadow.h" #include "shadow.h"
#include "exa.h" #include "exa.h"
@ -50,6 +51,7 @@ typedef struct _modesettingRec
unsigned int fb_id; unsigned int fb_id;
void *virtual; void *virtual;
drmBO bo; drmBO bo;
Bool front;
EntPtr entityPrivate; EntPtr entityPrivate;
@ -68,9 +70,6 @@ typedef struct _modesettingRec
Bool SWCursor; Bool SWCursor;
CloseScreenProcPtr CloseScreen; CloseScreenProcPtr CloseScreen;
Bool directRenderingDisabled; /* DRI disabled in PreInit. */
Bool directRenderingEnabled; /* DRI enabled this generation. */
/* Broken-out options. */ /* Broken-out options. */
OptionInfoPtr Options; OptionInfoPtr Options;
@ -85,6 +84,11 @@ typedef struct _modesettingRec
/* exa */ /* exa */
ExaDriverPtr pExa; ExaDriverPtr pExa;
drmBO exa_bo; drmBO exa_bo;
/* dri2 */
drm_context_t context;
drm_hw_lock_t *lock;
int lock_held;
} modesettingRec, *modesettingPtr; } modesettingRec, *modesettingPtr;
#define modesettingPTR(p) ((modesettingPtr)((p)->driverPrivate)) #define modesettingPTR(p) ((modesettingPtr)((p)->driverPrivate))

View File

@ -36,6 +36,14 @@
#include "driver.h" #include "driver.h"
struct PixmapPriv {
drmBO bo;
#if 0
dri_fence *fence;
#endif
int flags;
};
static void static void
ExaWaitMarker(ScreenPtr pScreen, int marker) ExaWaitMarker(ScreenPtr pScreen, int marker)
{ {
@ -44,10 +52,6 @@ ExaWaitMarker(ScreenPtr pScreen, int marker)
static int static int
ExaMarkSync(ScreenPtr pScreen) ExaMarkSync(ScreenPtr pScreen)
{ {
/*
* See ExaWaitMarker.
*/
return 1; return 1;
} }
@ -56,6 +60,30 @@ ExaPrepareAccess(PixmapPtr pPix, int index)
{ {
ScreenPtr pScreen = pPix->drawable.pScreen; ScreenPtr pScreen = pPix->drawable.pScreen;
ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum]; ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum];
modesettingPtr ms = modesettingPTR(pScrn);
PixmapPtr rootPixmap = pScreen->GetScreenPixmap(pScreen);
struct PixmapPriv *priv;
int ret;
priv = exaGetPixmapDriverPrivate(pPix);
if (!priv)
return FALSE;
if (priv->bo.handle) {
void *virtual;
ret = drmBOMap(ms->fd,
&priv->bo, DRM_BO_FLAG_READ | DRM_BO_FLAG_WRITE, 0, &virtual);
if (ret) {
driUnlock(pScreen);
FatalError("Failed to map pixmap: %s\n", strerror(-ret));
return;
}
pPix->devPrivate.ptr = priv->bo.virtual;
}
return TRUE; return TRUE;
} }
@ -65,6 +93,26 @@ ExaFinishAccess(PixmapPtr pPix, int index)
{ {
ScreenPtr pScreen = pPix->drawable.pScreen; ScreenPtr pScreen = pPix->drawable.pScreen;
ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum]; ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum];
modesettingPtr ms = modesettingPTR(pScrn);
PixmapPtr rootPixmap = pScreen->GetScreenPixmap(pScreen);
struct PixmapPriv *priv;
int ret;
priv = exaGetPixmapDriverPrivate(pPix);
if (!priv)
return;
if (priv->bo.handle) {
ret = drmBOUnmap(ms->fd, &priv->bo);
if (ret) {
driUnlock(pScreen);
FatalError("Failed to unmap pixmap: %s\n", strerror(-ret));
return;
}
pPix->devPrivate.ptr = NULL;
}
} }
static void static void
@ -84,6 +132,8 @@ ExaPrepareSolid(PixmapPtr pPixmap, int alu, Pixel planeMask, Pixel fg)
{ {
ScrnInfoPtr pScrn = xf86Screens[pPixmap->drawable.pScreen->myNum]; ScrnInfoPtr pScrn = xf86Screens[pPixmap->drawable.pScreen->myNum];
ErrorF("SOLID\n");
if (!EXA_PM_IS_SOLID(&pPixmap->drawable, planeMask)) if (!EXA_PM_IS_SOLID(&pPixmap->drawable, planeMask))
return FALSE; return FALSE;
@ -91,7 +141,7 @@ ExaPrepareSolid(PixmapPtr pPixmap, int alu, Pixel planeMask, Pixel fg)
if (pPixmap->drawable.depth == 4) if (pPixmap->drawable.depth == 4)
return FALSE; return FALSE;
return TRUE; return FALSE;
} }
static void static void
@ -106,11 +156,13 @@ ExaPrepareCopy(PixmapPtr pSrcPixmap, PixmapPtr pDstPixmap, int xdir,
{ {
ScrnInfoPtr pScrn = xf86Screens[pDstPixmap->drawable.pScreen->myNum]; ScrnInfoPtr pScrn = xf86Screens[pDstPixmap->drawable.pScreen->myNum];
ErrorF("COPY\n");
/* can't do depth 4 */ /* can't do depth 4 */
if (pSrcPixmap->drawable.depth == 4 || pDstPixmap->drawable.depth == 4) if (pSrcPixmap->drawable.depth == 4 || pDstPixmap->drawable.depth == 4)
return FALSE; return FALSE;
return TRUE; return FALSE;
} }
static void static void
@ -138,6 +190,8 @@ ExaUploadToScreen(PixmapPtr pDst, int x, int y, int w, int h, char *src,
ScreenPtr pScreen = pDst->drawable.pScreen; ScreenPtr pScreen = pDst->drawable.pScreen;
ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum]; ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum];
ErrorF("UPLOAD\n");
return FALSE; return FALSE;
} }
@ -158,18 +212,118 @@ ExaCheckComposite(int op,
int w = pDraw->width; int w = pDraw->width;
int h = pDraw->height; int h = pDraw->height;
return TRUE; return FALSE;
} }
static Bool static void *
ExaPixmapIsOffscreen(PixmapPtr p) ExaCreatePixmap(ScreenPtr pScreen, int size, int align)
{ {
ScreenPtr pScreen = p->drawable.pScreen;
ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum]; ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum];
modesettingPtr ms = modesettingPTR(pScrn);
struct PixmapPriv *priv;
void *virtual;
priv = xcalloc(1, sizeof(struct PixmapPriv));
if (!priv)
return NULL;
if (size == 0)
return priv;
drmBOCreate(ms->fd, size, 4096, NULL,
DRM_BO_FLAG_READ | DRM_BO_FLAG_WRITE | DRM_BO_FLAG_SHAREABLE
| DRM_BO_FLAG_MEM_TT | DRM_BO_FLAG_MAPPABLE |
DRM_BO_FLAG_CACHED_MAPPED,
0, &priv->bo);
return priv;
}
static void
ExaDestroyPixmap(ScreenPtr pScreen, void *dPriv)
{
struct PixmapPriv *priv = (struct PixmapPriv *)dPriv;
ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum];
modesettingPtr ms = modesettingPTR(pScrn);
if (!priv)
return;
if (priv->bo.handle)
drmBOUnreference(ms->fd, &priv->bo);
xfree(priv);
}
static Bool
ExaPixmapIsOffscreen(PixmapPtr pPixmap)
{
struct PixmapPriv *priv;
ScreenPtr pScreen = pPixmap->drawable.pScreen;
PixmapPtr rootPixmap = pScreen->GetScreenPixmap(pScreen);
priv = exaGetPixmapDriverPrivate(pPixmap);
if (!priv)
return FALSE;
if (priv->bo.handle)
return TRUE;
return FALSE; return FALSE;
} }
/* FIXME !! */
unsigned int
driGetPixmapHandle(PixmapPtr pPixmap, unsigned int *flags)
{
ScreenPtr pScreen = pPixmap->drawable.pScreen;
PixmapPtr rootPixmap = pScreen->GetScreenPixmap(pScreen);
ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum];
modesettingPtr ms = modesettingPTR(pScrn);
struct PixmapPriv *priv;
*flags = 0;
if (rootPixmap == pPixmap)
return ms->bo.handle;
if (!ms->pExa)
return 0;
priv = exaGetPixmapDriverPrivate(pPixmap);
if (!priv)
return 0;
if (priv->bo.handle)
return priv->bo.handle;
return 0;
}
static Bool
ExaModifyPixmapHeader(PixmapPtr pPixmap, int width, int height,
int depth, int bitsPerPixel, int devKind,
pointer pPixData)
{
ScreenPtr pScreen = pPixmap->drawable.pScreen;
ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum];
struct PixmapPriv *priv = exaGetPixmapDriverPrivate(pPixmap);
modesettingPtr ms = modesettingPTR(pScrn);
PixmapPtr rootPixmap = pScreen->GetScreenPixmap(pScreen);
if (rootPixmap == pPixmap) {
miModifyPixmapHeader(pPixmap, width, height, depth,
bitsPerPixel, devKind, NULL);
return TRUE;
}
return FALSE;
}
void void
ExaClose(ScrnInfoPtr pScrn) ExaClose(ScrnInfoPtr pScrn)
{ {
@ -177,7 +331,9 @@ ExaClose(ScrnInfoPtr pScrn)
exaDriverFini(pScrn->pScreen); exaDriverFini(pScrn->pScreen);
#if 0
drmBOUnreference(ms->fd, &ms->exa_bo); drmBOUnreference(ms->fd, &ms->exa_bo);
#endif
} }
ExaDriverPtr ExaDriverPtr
@ -191,20 +347,22 @@ ExaInit(ScrnInfoPtr pScrn)
goto out_err; goto out_err;
} }
#if 0
/* Create a 256KB offscreen area */ /* Create a 256KB offscreen area */
drmBOCreate(ms->fd, 256 * 1024, 0, NULL, drmBOCreate(ms->fd, 256 * 1024, 0, NULL,
DRM_BO_FLAG_READ | DRM_BO_FLAG_WRITE | DRM_BO_FLAG_MEM_TT, DRM_BO_FLAG_READ | DRM_BO_FLAG_WRITE | DRM_BO_FLAG_MEM_TT,
DRM_BO_HINT_DONT_FENCE, &ms->exa_bo); DRM_BO_HINT_DONT_FENCE, &ms->exa_bo);
#endif
memset(pExa, 0, sizeof(*pExa)); memset(pExa, 0, sizeof(*pExa));
pExa->exa_major = 2; pExa->exa_major = 2;
pExa->exa_minor = 2; pExa->exa_minor = 4;
pExa->memoryBase = ms->exa_bo.virtual; pExa->memoryBase = 0; /* ms->exa_bo.virtual; */
pExa->memorySize = 0; /* ms->exa_bo.size; */
pExa->offScreenBase = 0; pExa->offScreenBase = 0;
pExa->memorySize = ms->exa_bo.size;
pExa->pixmapOffsetAlign = 8; pExa->pixmapOffsetAlign = 8;
pExa->pixmapPitchAlign = 32 * 4; pExa->pixmapPitchAlign = 32 * 4;
pExa->flags = EXA_OFFSCREEN_PIXMAPS; pExa->flags = EXA_OFFSCREEN_PIXMAPS | EXA_HANDLES_PIXMAPS;
pExa->maxX = 8191; /* FIXME */ pExa->maxX = 8191; /* FIXME */
pExa->maxY = 8191; /* FIXME */ pExa->maxY = 8191; /* FIXME */
pExa->WaitMarker = ExaWaitMarker; pExa->WaitMarker = ExaWaitMarker;
@ -223,6 +381,9 @@ ExaInit(ScrnInfoPtr pScrn)
pExa->PrepareAccess = ExaPrepareAccess; pExa->PrepareAccess = ExaPrepareAccess;
pExa->FinishAccess = ExaFinishAccess; pExa->FinishAccess = ExaFinishAccess;
pExa->UploadToScreen = ExaUploadToScreen; pExa->UploadToScreen = ExaUploadToScreen;
pExa->CreatePixmap = ExaCreatePixmap;
pExa->DestroyPixmap = ExaDestroyPixmap;
pExa->ModifyPixmapHeader = ExaModifyPixmapHeader;
if (!exaDriverInit(pScrn->pScreen, pExa)) { if (!exaDriverInit(pScrn->pScreen, pExa)) {
goto out_err; goto out_err;

View File

@ -51,6 +51,23 @@
#include "driver.h" #include "driver.h"
static char *connector_enum_list[] = {
"Unknown",
"VGA",
"DVI-I",
"DVI-D",
"DVI-A",
"Composite",
"SVIDEO",
"LVDS",
"Component",
"9-pin DIN",
"DisplayPort",
"HDMI Type A",
"HDMI Type B",
};
static void static void
dpms(xf86OutputPtr output, int mode) dpms(xf86OutputPtr output, int mode)
{ {
@ -145,6 +162,7 @@ get_modes(xf86OutputPtr output)
mode->VRefresh = xf86ModeVRefresh(mode); mode->VRefresh = xf86ModeVRefresh(mode);
mode->Private = (void *)drm_mode; mode->Private = (void *)drm_mode;
xf86SetModeDefaultName(mode); xf86SetModeDefaultName(mode);
ErrorF("MODE %s\n",mode->name);
modes = xf86ModesAdd(modes, mode); modes = xf86ModesAdd(modes, mode);
xf86PrintModeline(0, mode); xf86PrintModeline(0, mode);
} }
@ -237,7 +255,6 @@ output_init(ScrnInfoPtr pScrn)
if (!drm_connector) if (!drm_connector)
goto out; goto out;
#if 0
for (p = 0; p < drm_connector->count_props; p++) { for (p = 0; p < drm_connector->count_props; p++) {
drmModePropertyPtr prop; drmModePropertyPtr prop;
@ -249,41 +266,16 @@ output_init(ScrnInfoPtr pScrn)
for (v = 0; v < prop->count_values; v++) for (v = 0; v < prop->count_values; v++)
ErrorF("%s %lld\n", prop->name, prop->values[v]); ErrorF("%s %lld\n", prop->name, prop->values[v]);
for (v = 0; v < prop->count_enums; v++) {
ErrorF("%s %s\n", prop->name, prop->enums[v].name);
if (drm_connector->prop_values[p] == prop->enums[v].value) {
if (!strncmp("Connector Type", prop->name, 14)) {
ErrorF("WE'VE GOT %s\n", prop->enums[v].name);
name = xalloc(strlen(prop->enums[v].name));
strncpy(name, prop->enums[v].name, strlen(name));
}
}
if (name)
break;
}
if (name)
break;
} }
} }
if (!name) name = connector_enum_list[drm_connector->connector_type];
continue;
#endif
#if 0
free(name);
#endif
name = "Unknown";
output = xf86OutputCreate(pScrn, &output_funcs, name); output = xf86OutputCreate(pScrn, &output_funcs, name);
if (!output) if (!output)
continue; continue;
drm_encoder = drmModeGetEncoder(ms->fd, drm_connector->encoder); drm_encoder = drmModeGetEncoder(ms->fd, drm_connector->encoders[0]);
if (drm_encoder) { if (drm_encoder) {
output->possible_crtcs = drm_encoder->crtcs; output->possible_crtcs = drm_encoder->crtcs;
output->possible_clones = drm_encoder->clones; output->possible_clones = drm_encoder->clones;