Resolve stability issues starting & stopping radeon driver.

Add drmtest program to exercise the drm without the added complications of
a full driver.

Bring fb driver uptodate with changes for hw drivers.
This commit is contained in:
Keith Whitwell 2002-12-25 12:51:21 +00:00
parent 9363bd862f
commit 39afeb7cf0
9 changed files with 349 additions and 63 deletions

View file

@ -1,4 +1,4 @@
# $Id: Makefile,v 1.1.2.5 2002/12/19 12:26:15 keithw Exp $
# $Id: Makefile,v 1.1.2.6 2002/12/25 12:51:21 keithw Exp $
# Mesa 3-D graphics library
# Version: 5.0
@ -7,7 +7,7 @@
MESA = ../../..
MESABUILDDIR = $(MESA)/src
MESABUILDDIR = ../..
INCLUDES = -I$(MESABUILDDIR) -I$(MESA)/include -I. -I../common \
-I$(MESABUILDDIR)/miniglx -Iserver
@ -65,10 +65,12 @@ OBJECTS = $(C_SOURCES:.c=.o) \
##### TARGETS #####
default: radeon_dri.so
default: radeon_dri.so install
radeon_dri.so: $(COREMESA) $(OBJECTS) Makefile
rm -f $@ && gcc -o $@ -shared $(OBJECTS) $(COREMESA) -L$(MESA)/src/miniglx -lGL -lc -lm && \
rm -f $@ && gcc -o $@ -shared $(OBJECTS) $(COREMESA) -L$(MESA)/src/miniglx -lGL -lc -lm
install:
rm -f $(MESA)/lib/fb_dri.so && \
install -C radeon_dri.so $(MESA)/lib/radeon_dri.so

View file

@ -92,6 +92,9 @@ extern int prevLockLine;
do { \
char __ret = 0; \
DEBUG_CHECK_LOCK(); \
fprintf(stderr, "LOCK_HARDWARE (fd %d, lock %p, ctx %d) in %s\n", \
rmesa->dri.fd, rmesa->dri.hwLock, rmesa->dri.hwContext, \
__FUNCTION__); \
DRM_CAS( rmesa->dri.hwLock, rmesa->dri.hwContext, \
(DRM_LOCK_HELD | rmesa->dri.hwContext), __ret ); \
if ( __ret ) \

View file

@ -49,7 +49,6 @@ static int RADEONDRIAgpInit( struct MiniGLXDisplayRec *dpy, RADEONInfoPtr info)
{
unsigned char *RADEONMMIO = dpy->MMIOAddress;
unsigned long mode;
unsigned int vendor, device;
int ret;
int s, l;
@ -66,8 +65,6 @@ static int RADEONDRIAgpInit( struct MiniGLXDisplayRec *dpy, RADEONInfoPtr info)
* particular combination of graphics card and AGP chipset.
*/
mode = drmAgpGetMode(dpy->drmFD); /* Default mode */
vendor = drmAgpVendorId(dpy->drmFD);
device = drmAgpDeviceId(dpy->drmFD);
/* Disable fast write entirely - too many lockups.
*/
@ -131,6 +128,7 @@ static int RADEONDRIAgpInit( struct MiniGLXDisplayRec *dpy, RADEONInfoPtr info)
}
fprintf(stderr, "[agp] ring handle = 0x%08lx\n", info->ringHandle);
#if 0
if (drmMap(dpy->drmFD, info->ringHandle, info->ringMapSize,
(drmAddressPtr)&info->ring) < 0) {
fprintf(stderr, "[agp] Could not map ring\n");
@ -139,8 +137,9 @@ static int RADEONDRIAgpInit( struct MiniGLXDisplayRec *dpy, RADEONInfoPtr info)
fprintf(stderr,
"[agp] Ring mapped at 0x%08lx\n",
(unsigned long)info->ring);
(unsigned long)info->ring);
#endif
if (drmAddMap(dpy->drmFD, info->ringReadOffset, info->ringReadMapSize,
DRM_AGP, DRM_READ_ONLY, &info->ringReadPtrHandle) < 0) {
fprintf(stderr,
@ -152,6 +151,7 @@ static int RADEONDRIAgpInit( struct MiniGLXDisplayRec *dpy, RADEONInfoPtr info)
"[agp] ring read ptr handle = 0x%08lx\n",
info->ringReadPtrHandle);
#if 0
if (drmMap(dpy->drmFD, info->ringReadPtrHandle, info->ringReadMapSize,
(drmAddressPtr)&info->ringReadPtr) < 0) {
fprintf(stderr,
@ -161,7 +161,8 @@ static int RADEONDRIAgpInit( struct MiniGLXDisplayRec *dpy, RADEONInfoPtr info)
fprintf(stderr,
"[agp] Ring read ptr mapped at 0x%08lx\n",
(unsigned long)info->ringReadPtr);
#endif
if (drmAddMap(dpy->drmFD, info->bufStart, info->bufMapSize,
DRM_AGP, 0, &info->bufHandle) < 0) {
fprintf(stderr,
@ -171,7 +172,8 @@ static int RADEONDRIAgpInit( struct MiniGLXDisplayRec *dpy, RADEONInfoPtr info)
fprintf(stderr,
"[agp] vertex/indirect buffers handle = 0x%08lx\n",
info->bufHandle);
#if 0
if (drmMap(dpy->drmFD, info->bufHandle, info->bufMapSize,
(drmAddressPtr)&info->buf) < 0) {
fprintf(stderr,
@ -181,7 +183,8 @@ static int RADEONDRIAgpInit( struct MiniGLXDisplayRec *dpy, RADEONInfoPtr info)
fprintf(stderr,
"[agp] Vertex/indirect buffers mapped at 0x%08lx\n",
(unsigned long)info->buf);
#endif
if (drmAddMap(dpy->drmFD, info->agpTexStart, info->agpTexMapSize,
DRM_AGP, 0, &info->agpTexHandle) < 0) {
fprintf(stderr,
@ -191,7 +194,8 @@ static int RADEONDRIAgpInit( struct MiniGLXDisplayRec *dpy, RADEONInfoPtr info)
fprintf(stderr,
"[agp] AGP texture map handle = 0x%08lx\n",
info->agpTexHandle);
#if 0
if (drmMap(dpy->drmFD, info->agpTexHandle, info->agpTexMapSize,
(drmAddressPtr)&info->agpTex) < 0) {
fprintf(stderr,
@ -201,7 +205,8 @@ static int RADEONDRIAgpInit( struct MiniGLXDisplayRec *dpy, RADEONInfoPtr info)
fprintf(stderr,
"[agp] AGP Texture map mapped at 0x%08lx\n",
(unsigned long)info->agpTex);
#endif
/* Initialize Radeon's AGP registers */
/* Ring buffer is at AGP offset 0 */
OUTREG(RADEON_AGP_BASE, info->ringHandle);
@ -305,6 +310,7 @@ static int RADEONDRIBufInit( struct MiniGLXDisplayRec *dpy, RADEONInfoPtr info )
"[drm] Added %d %d byte vertex/indirect buffers\n",
info->bufNumBufs, RADEON_BUFFER_SIZE);
#if 0
if (!(info->buffers = drmMapBufs(dpy->drmFD))) {
fprintf(stderr,
"[drm] Failed to map vertex/indirect buffers list\n");
@ -314,7 +320,8 @@ static int RADEONDRIBufInit( struct MiniGLXDisplayRec *dpy, RADEONInfoPtr info )
fprintf(stderr,
"[drm] Mapped %d vertex/indirect buffers\n",
info->buffers->count);
#endif
return 1;
}
@ -360,11 +367,6 @@ static void RADEONDRICPInit(struct MiniGLXDisplayRec *dpy, RADEONInfoPtr info)
/* info->CPStarted = 1; */
}
void *
DRIGetSAREAPrivate( struct MiniGLXDisplayRec *dpy )
{
return (void *)(((char*)dpy->pSAREA)+sizeof(XF86DRISAREARec));
}
/* Will fbdev set a pitch appropriate for 3d?
@ -402,6 +404,11 @@ static int DRIFinishScreenInit( struct MiniGLXDisplayRec *dpy )
return 0;
}
fprintf(stderr, "DRM_LOCK( %d %p %d )\n",
dpy->drmFD,
dpy->pSAREA,
dpy->serverContext);
DRM_LOCK(dpy->drmFD,
dpy->pSAREA,
dpy->serverContext,
@ -491,10 +498,9 @@ static int RADEONScreenInit( struct MiniGLXDisplayRec *dpy, RADEONInfoPtr info )
return 0;
}
memset(dpy->pSAREA, 0, dpy->SAREASize);
fprintf(stderr, "[drm] mapped SAREA 0x%08lx to %p\n",
dpy->hSAREA, dpy->pSAREA);
fprintf(stderr, "[drm] mapped SAREA 0x%08lx to %p, size %d\n",
dpy->hSAREA, dpy->pSAREA, dpy->SAREASize);
/* Need to AddMap the framebuffer and mmio regions here:
*/
if (drmAddMap( dpy->drmFD,
@ -504,7 +510,7 @@ static int RADEONScreenInit( struct MiniGLXDisplayRec *dpy, RADEONInfoPtr info )
0,
&dpy->hFrameBuffer) < 0)
{
drmUnmap(dpy->pSAREA, dpy->SAREASize);
/* drmUnmap(dpy->pSAREA, dpy->SAREASize); */
drmClose(dpy->drmFD);
fprintf(stderr, "[drm] drmAddMap framebuffer failed\n");
return 0;
@ -705,7 +711,8 @@ static int RADEONScreenInit( struct MiniGLXDisplayRec *dpy, RADEONInfoPtr info )
/* Initialize the SAREA private data structure */
{
RADEONSAREAPrivPtr pSAREAPriv;
pSAREAPriv = (RADEONSAREAPrivPtr)DRIGetSAREAPrivate( dpy );
pSAREAPriv = (RADEONSAREAPrivPtr)(((char*)dpy->pSAREA) +
sizeof(XF86DRISAREARec));
memset(pSAREAPriv, 0, sizeof(*pSAREAPriv));
}
@ -713,11 +720,24 @@ static int RADEONScreenInit( struct MiniGLXDisplayRec *dpy, RADEONInfoPtr info )
DRM_UNLOCK(dpy->drmFD, dpy->pSAREA, dpy->serverContext);
fprintf(stderr, "DRM_UNLOCK finished\n");
{
int i;
for (i = 0 ; i < 5 ; i++) {
fprintf(stderr, "%s: locking\n", __FUNCTION__);
DRM_LOCK(dpy->drmFD, dpy->pSAREA, dpy->serverContext, 0);
fprintf(stderr, "%s: locked\n", __FUNCTION__);
DRM_UNLOCK(dpy->drmFD, dpy->pSAREA, dpy->serverContext);
fprintf(stderr, "DRM_UNLOCK finished\n");
}
}
/* This is the struct passed to radeon_dri.so for its initialization */
dpy->driverInfo = malloc(sizeof(RADEONDRIRec));
dpy->driverInfoSize = sizeof(RADEONDRIRec);
pRADEONDRI = (RADEONDRIPtr)dpy->driverInfo;
dpy->driverClientMsg = malloc(sizeof(RADEONDRIRec));
dpy->driverClientMsgSize = sizeof(RADEONDRIRec);
pRADEONDRI = (RADEONDRIPtr)dpy->driverClientMsg;
pRADEONDRI->deviceID = info->Chipset;
pRADEONDRI->width = dpy->VarInfo.xres_virtual;
pRADEONDRI->height = dpy->VarInfo.yres_virtual;
@ -841,6 +861,12 @@ int __driInitFBDev( struct MiniGLXDisplayRec *dpy )
if (!RADEONScreenInit( dpy, info ))
return 0;
#if 0
fprintf(stderr, "Now closing drmFD\n");
drmClose(dpy->drmFD);
dpy->drmFD = 0;
#endif
return 1;
}
@ -851,6 +877,8 @@ int RADEONCPStop( struct MiniGLXDisplayRec *dpy )
drmRadeonCPStop stop;
int ret, i;
fprintf(stderr, "%s\n", __FUNCTION__);
stop.flush = 1;
stop.idle = 1;
@ -895,14 +923,34 @@ int RADEONCPStop( struct MiniGLXDisplayRec *dpy )
void __driHaltFBDev( struct MiniGLXDisplayRec *dpy )
{
drmRadeonInit drmInfo;
RADEONInfoPtr info = (RADEONInfoPtr) dpy->driverPrivate;
RADEONInfoPtr info = (RADEONInfoPtr) dpy->driverInfo;
if (!info)
fprintf(stderr, "%s\n", __FUNCTION__);
if (!info) {
fprintf(stderr, "no driverInfo\n");
return;
}
/* Stop the CP */
RADEONCPStop(dpy);
fprintf(stderr, "DRM_LOCK( %d %p %d )\n",
dpy->drmFD,
dpy->pSAREA,
dpy->serverContext);
fprintf(stderr, "%s: locking\n", __FUNCTION__);
DRM_LOCK(dpy->drmFD, dpy->pSAREA, dpy->serverContext, 0);
fprintf(stderr, "%s: locked\n", __FUNCTION__);
if (RADEONCPStop(dpy)) {
fprintf(stderr, "RADEONCPStop failed: %d\n", errno);
DRM_UNLOCK(dpy->drmFD, dpy->pSAREA, dpy->serverContext);
return;
}
fprintf(stderr, "%s: cp stoped\n", __FUNCTION__);
if (info->irq) {
drmCtlUninstHandler(dpy->drmFD);
info->irq = 0;
@ -915,11 +963,14 @@ void __driHaltFBDev( struct MiniGLXDisplayRec *dpy )
}
/* De-allocate all kernel resources */
fprintf(stderr, "%s: calling DRM_RADEON_CLEANUP_CP\n", __FUNCTION__);
memset(&drmInfo, 0, sizeof(drmRadeonInit));
drmInfo.func = DRM_RADEON_CLEANUP_CP;
drmCommandWrite(dpy->drmFD, DRM_RADEON_CP_INIT,
&drmInfo, sizeof(drmRadeonInit));
/* De-allocate all AGP resources */
if (info->agpTex) {
drmUnmap(info->agpTex, info->agpTexMapSize);
@ -948,9 +999,11 @@ void __driHaltFBDev( struct MiniGLXDisplayRec *dpy )
/* if (dpy->drmSIGIOHandlerInstalled) */
/* drmRemoveSIGIOHandler(dpy->drmFD); */
DRM_UNLOCK(dpy->drmFD, dpy->pSAREA, dpy->serverContext);
drmUnmap(dpy->pSAREA, dpy->SAREASize);
drmClose(dpy->drmFD);
free(info);
dpy->driverPrivate = 0;
dpy->driverInfo = 0;
}

View file

@ -19,11 +19,13 @@ LIBS = -ldl
default: libGL.so.1.2
default: libGL.so.1.2 install drmtest
libGL.so.1.2: $(OBJS) Makefile
gcc -shared -Wl,-soname,libGL.so -Wl,-Bsymbolic $(OBJS) $(LIBS) -o $@
install:
rm -f $(MESA)/lib/libGL.so*
install -D libGL.so.1.2 $(MESA)/lib/libGL.so.1.2
ln -s libGL.so.1.2 $(MESA)/lib/libGL.so.1
@ -32,6 +34,10 @@ libGL.so.1.2: $(OBJS) Makefile
#miniglx.a: $(OBJECTS) Makefile
# rm -f $@ && ar rcv $@ $(OBJECTS) && ranlib $@
drmtest: xf86drm.o drmtest.o
rm -f drmtest && $(CC) -o drmtest xf86drm.o drmtest.o
glapi.c: ../glapi.c
ln -s ../glapi.c .

View file

@ -408,13 +408,16 @@ static void *driCreateContext(Display *dpy, XVisualInfo *vis,
static void driDestroyScreen(Display *dpy, int scrn, void *screenPrivate)
{
__DRIscreenPrivate *psp = (__DRIscreenPrivate *) screenPrivate;
fprintf(stderr, "%s\n", __FUNCTION__);
if (psp) {
if (psp->DriverAPI.DestroyScreen)
(*psp->DriverAPI.DestroyScreen)(psp);
if (psp->fd) {
(void)drmUnmap((drmAddress)psp->pSAREA, SAREA_MAX);
/* (void)drmUnmap((drmAddress)psp->pSAREA, SAREA_MAX); */
fprintf(stderr, "%s: Closing DRM fd\n", __FUNCTION__);
(void)drmClose(psp->fd);
}
@ -431,9 +434,8 @@ __driUtilCreateScreen(Display *dpy, int scrn, __DRIscreen *psc,
{
__DRIscreenPrivate *psp;
char *driverName;
drmHandle hFB, hSAREA;
drmHandle hFB;
drmMagic magic;
char *BusID;
psp = (__DRIscreenPrivate *)malloc(sizeof(__DRIscreenPrivate));
if (!psp) {
@ -443,12 +445,7 @@ __driUtilCreateScreen(Display *dpy, int scrn, __DRIscreen *psc,
psp->display = dpy;
psp->myNum = scrn;
hSAREA = dpy->hSAREA;
BusID = dpy->pciBusID;
printf("hSAREA = 0x%x BusID = %s\n", (int) hSAREA, BusID);
psp->fd = drmOpen(NULL,BusID);
psp->fd = drmOpen(NULL,dpy->pciBusID);
if (psp->fd < 0) {
fprintf(stderr, "libGL error: failed to open DRM: %s\n", strerror(-psp->fd));
free(psp);
@ -498,8 +495,8 @@ __driUtilCreateScreen(Display *dpy, int scrn, __DRIscreen *psc,
psp->fbOrigin = 0;
psp->fbSize = dpy->FrameBufferSize;
psp->fbStride = dpy->VarInfo.xres_virtual * dpy->cpp;
psp->devPrivSize = dpy->driverInfoSize;
psp->pDevPriv = dpy->driverInfo;
psp->devPrivSize = dpy->driverClientMsgSize;
psp->pDevPriv = dpy->driverClientMsg;
psp->fbWidth = dpy->VarInfo.xres;
psp->fbHeight = dpy->VarInfo.yres;
psp->fbBPP = dpy->VarInfo.bits_per_pixel;
@ -509,7 +506,7 @@ __driUtilCreateScreen(Display *dpy, int scrn, __DRIscreen *psc,
if (psp->DriverAPI.InitDriver) {
if (!(*psp->DriverAPI.InitDriver)(psp)) {
fprintf(stderr, "libGL error: InitDriver failed\n");
(void)drmUnmap((drmAddress)psp->pSAREA, SAREA_MAX);
/* (void)drmUnmap((drmAddress)psp->pSAREA, SAREA_MAX); */
free(psp->pDevPriv);
(void)drmClose(psp->fd);
free(psp);

142
src/miniglx/drmtest.c Normal file
View file

@ -0,0 +1,142 @@
#include <assert.h>
#include <unistd.h>
#include <stdio.h>
#include "xf86drm.h"
char *pciBusID = "PCI:1:0:0";
#define DRM_PAGE_SIZE 4096
void *pSAREA;
int client()
{
int fd, ret, err;
drmContext clientContext;
fprintf(stderr, "Opening client drm\n");
fd = drmOpen(NULL,pciBusID);
if (fd < 0) {
fprintf(stderr, "failed to open DRM: %s\n", strerror(-fd));
return 1;
}
fprintf(stderr, "Create server context\n");
if ((err = drmCreateContext(fd, &clientContext)) != 0) {
fprintf(stderr, "%s: drmCreateContext failed %d\n", __FUNCTION__, err);
return 0;
}
fprintf(stderr, "DRM_LOCK( %d %p %d )\n", fd, pSAREA, clientContext);
DRM_LOCK(fd, pSAREA, clientContext, 0);
fprintf(stderr, "locked\n");
DRM_UNLOCK(fd, pSAREA, clientContext);
fprintf(stderr, "DRM_UNLOCK finished\n");
/* (void)drmUnmap((drmAddress)pSAREA, DRM_PAGE_SIZE); */
fprintf(stderr, "Closing client drm: %d\n", fd);
ret = drmClose(fd);
fprintf(stderr, "done %d\n", ret);
return ret;
}
int main()
{
char *drmModuleName = "radeon";
int drmFD;
int err;
int SAREASize;
drmHandle hSAREA;
drmContext serverContext;
/* Note that drmOpen will try to load the kernel module, if needed. */
drmFD = drmOpen(drmModuleName, NULL );
if (drmFD < 0) {
/* failed to open DRM */
fprintf(stderr, "[drm] drmOpen failed\n");
return 0;
}
if ((err = drmSetBusid(drmFD, pciBusID)) < 0) {
drmClose(drmFD);
fprintf(stderr, "[drm] drmSetBusid failed (%d, %s), %s\n",
drmFD, pciBusID, strerror(-err));
return 0;
}
SAREASize = DRM_PAGE_SIZE;
if (drmAddMap( drmFD,
0,
SAREASize,
DRM_SHM,
DRM_CONTAINS_LOCK,
&hSAREA) < 0)
{
drmClose(drmFD);
fprintf(stderr, "[drm] drmAddMap failed\n");
return 0;
}
fprintf(stderr, "[drm] added %d byte SAREA at 0x%08lx\n",
SAREASize, hSAREA);
if (drmMap( drmFD,
hSAREA,
SAREASize,
(drmAddressPtr)(&pSAREA)) < 0)
{
drmClose(drmFD);
fprintf(stderr, "[drm] drmMap failed\n");
return 0;
}
memset(pSAREA, 0, SAREASize);
fprintf(stderr, "[drm] mapped SAREA 0x%08lx to %p, size %d\n",
hSAREA, pSAREA, SAREASize);
fprintf(stderr, "Create server context\n");
if ((err = drmCreateContext(drmFD, &serverContext)) != 0) {
fprintf(stderr, "%s: drmCreateContext failed %d\n", __FUNCTION__, err);
return 0;
}
fprintf(stderr, "DRM_LOCK( %d %p %d )\n", drmFD, pSAREA, serverContext);
DRM_LOCK(drmFD, pSAREA, serverContext, 0);
fprintf(stderr, "locked\n");
DRM_UNLOCK(drmFD, pSAREA, serverContext);
fprintf(stderr, "DRM_UNLOCK finished\n");
client();
fprintf(stderr, "DRM_LOCK( %d %p %d )\n", drmFD, pSAREA, serverContext);
DRM_LOCK(drmFD, pSAREA, serverContext, 0);
fprintf(stderr, "locked\n");
DRM_UNLOCK(drmFD, pSAREA, serverContext);
fprintf(stderr, "DRM_UNLOCK finished\n");
drmUnmap(pSAREA, SAREASize);
fprintf(stderr, "[drm] unmapped SAREA 0x%08lx from %p, size %d\n",
hSAREA, pSAREA, SAREASize);
pSAREA = 0;
fprintf(stderr, "%s: Closing DRM fd\n", __FUNCTION__);
(void)drmClose(drmFD);
return 0;
}

View file

@ -22,7 +22,7 @@
* CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*/
/* $Id: miniglx.c,v 1.1.4.23 2002/12/22 17:11:05 jrfonseca Exp $ */
/* $Id: miniglx.c,v 1.1.4.24 2002/12/25 12:51:21 keithw Exp $ */
/**
@ -126,6 +126,10 @@
static GLXContext CurrentContext = NULL;
static void SwitchDisplay(int i_signal)
{
}
/**********************************************************************/
/** \name FBdev functions */
/**********************************************************************/
@ -185,6 +189,8 @@ OpenFBDev( Display *dpy )
/* some magic to restore the vt when we exit */
{
struct vt_mode vt;
struct sigaction sig_tty;
if (ioctl(dpy->ConsoleFD, VT_ACTIVATE, vtnumber) != 0)
printf("ioctl VT_ACTIVATE: %s\n", strerror(errno));
if (ioctl(dpy->ConsoleFD, VT_WAITACTIVE, vtnumber) != 0)
@ -195,7 +201,22 @@ OpenFBDev( Display *dpy )
return GL_FALSE;
}
/* Set-up tty signal handler to catch the signal we request below */
memset( &sig_tty, 0, sizeof( sig_tty ) );
sig_tty.sa_handler = SwitchDisplay;
sigemptyset( &sig_tty.sa_mask );
if( sigaction( SIGUSR1, &sig_tty, &dpy->OrigSigUsr1 ) )
{
fprintf(stderr, "error: can't set up signal handler (%s)",
strerror(errno) );
return GL_FALSE;
}
vt.mode = VT_PROCESS;
vt.waitv = 0;
vt.relsig = SIGUSR1;
vt.acqsig = SIGUSR1;
if (ioctl(dpy->ConsoleFD, VT_SETMODE, &vt) < 0) {
@ -379,7 +400,7 @@ SetupFBDev( Display *dpy, Window win )
dpy->cpp = dpy->VarInfo.bits_per_pixel / 8;
if (0)
if (1)
{
int x, y;
char *scrn = (char *)dpy->FrameBuffer;
@ -418,7 +439,8 @@ SetupFBDev( Display *dpy, Window win )
/**
* \brief Restore framebuffer to state it was in before we started.
* \brief Restore framebuffer to state it was in before we started
* (undoes work done in SetupFBDev).
*
* \sa Called from XDestroyWindow().
*/
@ -432,6 +454,10 @@ RestoreFBDev( Display *dpy )
return GL_FALSE;
}
dpy->VarInfo = dpy->OrigVarInfo;
munmap(dpy->FrameBuffer, dpy->FrameBufferSize);
munmap(dpy->MMIOAddress, dpy->MMIOSize);
return GL_TRUE;
}
@ -442,14 +468,10 @@ RestoreFBDev( Display *dpy )
* \sa Called from XCloseDisplay().
*/
static void
CleanupFBDev( Display *dpy )
CloseFBDev( Display *dpy )
{
struct vt_mode VT;
munmap(dpy->FrameBuffer, dpy->FrameBufferSize);
munmap(dpy->MMIOAddress, dpy->MMIOSize);
close(dpy->FrameBufferFD);
/* restore text mode */
ioctl(dpy->ConsoleFD, KDSETMODE, KD_TEXT);
@ -465,6 +487,7 @@ CleanupFBDev( Display *dpy )
dpy->OriginalVT = -1;
}
close(dpy->FrameBufferFD);
close(dpy->ConsoleFD);
}
@ -555,6 +578,7 @@ InitializeScreenConfigs(int *numConfigs, __GLXvisualConfig **configs)
*/
int __read_config_file( Display *dpy )
{
#if 1
dpy->fbdevDevice = "/dev/fb0";
dpy->clientDriverName = "radeon_dri.so";
dpy->drmModuleName = "radeon";
@ -566,6 +590,17 @@ int __read_config_file( Display *dpy )
sprintf((char *)dpy->pciBusID, "PCI:%d:%d:%d",
dpy->pciBus, dpy->pciDevice, dpy->pciFunc);
#else
dpy->fbdevDevice = "/dev/fb0";
dpy->clientDriverName = "fb_dri.so";
dpy->drmModuleName = 0;
dpy->pciBus = 0;
dpy->pciDevice = 0;
dpy->pciFunc = 0;
dpy->chipset = 0;
dpy->pciBusID = 0;
#endif
return 1;
}
@ -615,7 +650,7 @@ XOpenDisplay( const char *display_name )
if (!dpy->dlHandle) {
fprintf(stderr, "Unable to open %s: %s\n", dpy->clientDriverName,
dlerror());
CleanupFBDev(dpy);
CloseFBDev(dpy);
FREE(dpy);
return NULL;
}
@ -630,6 +665,16 @@ XOpenDisplay( const char *display_name )
return NULL;
}
dpy->driverHaltFBDev = (HaltFBDevFunc) dlsym(dpy->dlHandle,
"__driHaltFBDev");
if (!dpy->driverHaltFBDev) {
fprintf(stderr, "Couldn't find __driHaltFBDev in %s\n",
dpy->clientDriverName);
dlclose(dpy->dlHandle);
FREE(dpy);
return NULL;
}
dpy->createScreen = (CreateScreenFunc) dlsym(dpy->dlHandle,
"__driCreateScreen");
if (!dpy->createScreen) {
@ -661,9 +706,11 @@ XOpenDisplay( const char *display_name )
void
XCloseDisplay( Display *display )
{
(*display->driScreen.destroyScreen)(display, 0, display->driScreen.private);
if (display->NumWindows) {
XDestroyWindow( display, display->TheWindow );
}
dlclose(display->dlHandle);
CleanupFBDev(display);
CloseFBDev(display);
FREE(display);
}
@ -791,6 +838,7 @@ XCreateWindow( Display *display, Window parent, int x, int y,
*
* Need to shut down drm and free dri data in XDestroyWindow, too.
*/
#if 1
display->driScreen.private = (*display->createScreen)(display, 0,
&(display->driScreen),
display->numConfigs,
@ -813,10 +861,18 @@ XCreateWindow( Display *display, Window parent, int x, int y,
return NULL;
}
#endif
display->NumWindows++;
display->TheWindow = win;
return win;
if (0) {
fprintf(stderr, "Now, destroy it!\n");
XDestroyWindow( display, win );
return NULL;
}
else
return win;
}
@ -843,9 +899,25 @@ XDestroyWindow( Display *display, Window w )
if (w == curDraw) {
glXMakeCurrent( display, NULL, NULL);
}
(*w->driDrawable.destroyDrawable)(display, w->driDrawable.private);
/* Destroy the drawable.
*/
if (w->driDrawable.private)
(*w->driDrawable.destroyDrawable)(display, w->driDrawable.private);
/* As this is done in CreateWindow, need to undo it here:
*/
if (display->driScreen.private)
(*display->driScreen.destroyScreen)(display, 0,
display->driScreen.private);
/* As this is done in CreateWindow, need to undo it here:
*/
(*display->driverHaltFBDev)( display );
/* put framebuffer back to initial state */
RestoreFBDev(display);
FREE(w);
/* unlink window from display */
display->NumWindows--;

View file

@ -10,6 +10,7 @@
#ifndef _mini_GLX_client_h_
#define _mini_GLX_client_h_
#include <signal.h>
#include <linux/fb.h>
#include <GL/miniglx.h>
@ -60,6 +61,7 @@ typedef void *(*CreateScreenFunc)(Display *dpy, int scrn, __DRIscreen *psc,
int numConfigs, __GLXvisualConfig *config);
typedef void *(*InitFBDevFunc)( Display *dpy );
typedef void *(*HaltFBDevFunc)( Display *dpy );
/**
@ -234,6 +236,7 @@ struct MiniGLXContextRec {
struct MiniGLXDisplayRec {
struct fb_fix_screeninfo FixedInfo;
struct fb_var_screeninfo OrigVarInfo, VarInfo;
struct sigaction OrigSigUsr1;
int DesiredDepth;
int OriginalVT;
int ConsoleFD;
@ -259,7 +262,6 @@ struct MiniGLXDisplayRec {
* \name From __GLXdisplayPrivate
*/
/*@{*/
InitFBDevFunc driverInitFBDev;
CreateScreenFunc createScreen;
__DRIscreen driScreen;
void *dlHandle; /**<
@ -268,6 +270,13 @@ struct MiniGLXDisplayRec {
*/
/*@}*/
/**
* \name New driver hooks
*/
/*@{*/
InitFBDevFunc driverInitFBDev;
HaltFBDevFunc driverHaltFBDev;
/*@}*/
/**
* \name Configuration details
@ -304,9 +313,9 @@ struct MiniGLXDisplayRec {
* Populated by __driInitFBDev()
*/
/*@{*/
void *driverPrivate;
void *driverInfo;
int driverInfoSize;
void *driverClientMsg;
int driverClientMsgSize;
/*@}*/
};

View file

@ -404,6 +404,7 @@ do { register unsigned int __old __asm("o0"); \
#define DRM_LOCK(fd,lock,context,flags) \
do { \
fprintf(stderr, "DRM_LOCK(%d,%p,%d) in %s\n",fd,lock,context, __FUNCTION__); \
if (flags) drmGetLock(fd,context,flags); \
else DRM_LIGHT_LOCK(fd,lock,context); \
} while(0)
@ -411,6 +412,7 @@ do { register unsigned int __old __asm("o0"); \
#define DRM_UNLOCK(fd,lock,context) \
do { \
DRM_CAS_RESULT(__ret); \
fprintf(stderr, "DRM_UNLOCK in %s\n", __FUNCTION__); \
DRM_CAS(lock,DRM_LOCK_HELD|context,context,__ret); \
if (__ret) drmUnlock(fd,context); \
} while(0)