summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorEric Anholt <anholt@freebsd.org>2004-01-25 01:30:33 +0000
committerEric Anholt <anholt@freebsd.org>2004-01-25 01:30:33 +0000
commit01e9cc858ac646b3140d1d85ea9c069bc708fb28 (patch)
tree78414c63d5ca3c007066754ac773f2ca69b79cce
parentf2bedd17af7c3b9241c02dc1c899f32fc0cd2f10 (diff)
- Add glx visuals code based on XFree86's Radeon driver.
- Reserve areas for back/depth/span when USING_DRI && GLXEXT. This would be better in a TransitionTo3d, but we'd need to work with the offscreen memory manager for that. - Misc. fixes to ati_dri.c for DRI+GLX. Needs more work still.
-rw-r--r--hw/kdrive/ati/ati.c82
-rw-r--r--hw/kdrive/ati/ati.h13
-rw-r--r--hw/kdrive/ati/ati_dri.c200
-rw-r--r--hw/kdrive/ati/radeon_composite.c13
4 files changed, 260 insertions, 48 deletions
diff --git a/hw/kdrive/ati/ati.c b/hw/kdrive/ati/ati.c
index 97a28f2e4..69d0ef6d5 100644
--- a/hw/kdrive/ati/ati.c
+++ b/hw/kdrive/ati/ati.c
@@ -28,6 +28,9 @@
#endif
#include "ati.h"
#include "ati_reg.h"
+#if defined(USE_DRI) && defined(GLXEXT)
+#include "ati_sarea.h"
+#endif
#define CAP_R128 0x1 /* If it's a Rage 128 */
#define CAP_R100 0x2 /* If it's an r100 series radeon. */
@@ -270,7 +273,11 @@ ATIScreenInit(KdScreenInfo *screen)
{
ATIScreenInfo *atis;
ATICardInfo(screen);
- int success = FALSE;
+ Bool success = FALSE;
+ int screen_size = 0;
+#if defined(USE_DRI) && defined(GLXEXT)
+ int l;
+#endif
atis = xcalloc(sizeof(ATIScreenInfo), 1);
if (atis == NULL)
@@ -285,8 +292,7 @@ ATIScreenInit(KdScreenInfo *screen)
success = fbdevScreenInitialize(screen,
&atis->backend_priv.fbdev);
screen->memory_size = atic->backend_priv.fbdev.fix.smem_len;
- screen->off_screen_base =
- atic->backend_priv.fbdev.var.yres_virtual *
+ screen_size = atic->backend_priv.fbdev.var.yres_virtual *
screen->fb[0].byteStride;
}
#endif
@@ -296,6 +302,7 @@ ATIScreenInit(KdScreenInfo *screen)
screen->fb[0].depth = 16;
success = vesaScreenInitialize(screen,
&atis->backend_priv.vesa);
+ screen_size = screen->off_screen_base;
}
#endif
@@ -305,16 +312,66 @@ ATIScreenInit(KdScreenInfo *screen)
return FALSE;
}
+ screen->off_screen_base = screen_size;
+#if defined(USE_DRI) && defined(GLXEXT)
+ /* Reserve a static area for the back buffer the same size as the
+ * visible screen. XXX: This would be better initialized in ati_dri.c
+ * when GLX is set up, but I'm not sure when the offscreen memory
+ * manager gets set up.
+ */
+ atis->frontOffset = 0;
+ atis->frontPitch = screen->fb[0].byteStride;
+
+ if (screen->off_screen_base + screen_size <= screen->memory_size) {
+ atis->backOffset = screen->off_screen_base;
+ atis->backPitch = screen->fb[0].byteStride;
+ screen->off_screen_base += screen_size;
+ }
+
+ /* Reserve the depth span for Rage 128 */
+ if (!atic->is_radeon && screen->off_screen_base +
+ screen->fb[0].byteStride <= screen->memory_size) {
+ atis->spanOffset = screen->off_screen_base;
+ screen->off_screen_base += screen->fb[0].byteStride;
+ }
+
+ /* Reserve the static depth buffer, which happens to be the same
+ * bitsPerPixel as the screen.
+ */
+ if (screen->off_screen_base + screen_size <= screen->memory_size) {
+ atis->depthOffset = screen->off_screen_base;
+ atis->depthPitch = screen->fb[0].byteStride;
+ screen->off_screen_base += screen_size;
+ }
+
+ /* Reserve approx. half of remaining offscreen memory for local
+ * textures. Round down to a whole number of texture regions.
+ */
+ atis->textureSize = (screen->memory_size - screen->off_screen_base) / 2;
+ l = ATILog2(atis->textureSize / ATI_NR_TEX_REGIONS);
+ if (l < ATI_LOG_TEX_GRANULARITY)
+ l = ATI_LOG_TEX_GRANULARITY;
+ atis->textureSize = (atis->textureSize >> l) << l;
+ if (atis->textureSize >= 512 * 1024) {
+ atis->textureOffset = screen->off_screen_base;
+ screen->off_screen_base += atis->textureSize;
+ } else {
+ /* Minimum texture size is for 2 256x256x32bpp textures */
+ atis->textureSize = 0;
+ }
+#endif /* USE_DRI && GLXEXT */
+
/* Reserve a scratch area. It'll be used for storing glyph data during
* Composite operations, because glyphs aren't in real pixmaps and thus
* can't be migrated.
*/
atis->scratch_size = 65536; /* big enough for 128x128@32bpp */
- if (screen->off_screen_base + atis->scratch_size > screen->memory_size)
- atis->scratch_size = 0;
- else {
+ if (screen->off_screen_base + atis->scratch_size <= screen->memory_size)
+ {
atis->scratch_offset = screen->off_screen_base;
screen->off_screen_base += atis->scratch_size;
+ } else {
+ atis->scratch_size = 0;
}
return TRUE;
@@ -458,6 +515,19 @@ ATIPutColors(ScreenPtr pScreen, int fb, int n, xColorItem *pdefs)
atic->backend_funcs.putColors(pScreen, fb, n, pdefs);
}
+/* Compute log base 2 of val. */
+int
+ATILog2(int val)
+{
+ int bits;
+
+ if (!val)
+ return 1;
+ for (bits = 0; val != 0; val >>= 1, ++bits)
+ ;
+ return bits;
+}
+
KdCardFuncs ATIFuncs = {
ATICardInit, /* cardinit */
ATIScreenInit, /* scrinit */
diff --git a/hw/kdrive/ati/ati.h b/hw/kdrive/ati/ati.h
index ea95abdb4..9270f080b 100644
--- a/hw/kdrive/ati/ati.h
+++ b/hw/kdrive/ati/ati.h
@@ -39,6 +39,11 @@
#define USE_DRI
#include "libdrm.h"
#include "dri.h"
+#ifdef GLXEXT
+#include "GL/glxint.h"
+#include "GL/glxtokens.h"
+#include "ati_dripriv.h"
+#endif
#endif
#define RADEON_REG_BASE(c) ((c)->attr.address[1])
@@ -224,6 +229,11 @@ typedef struct _ATIScreenInfo {
int serverContext;
DRIInfoPtr pDRIInfo;
+#ifdef GLXEXT
+ int numVisualConfigs;
+ __GLXvisualConfig *pVisualConfigs;
+ ATIConfigPrivPtr pVisualConfigsPriv;
+#endif /* GLXEXT */
#endif /* USE_DRI */
} ATIScreenInfo;
@@ -262,6 +272,9 @@ void
ATIDRICloseScreen(ScreenPtr pScreen);
#endif /* USE_DRI */
+int
+ATILog2(int val);
+
extern KdCardFuncs ATIFuncs;
#endif /* _ATI_H_ */
diff --git a/hw/kdrive/ati/ati_dri.c b/hw/kdrive/ati/ati_dri.c
index a6f92ae37..c6da406fe 100644
--- a/hw/kdrive/ati/ati_dri.c
+++ b/hw/kdrive/ati/ati_dri.c
@@ -48,19 +48,169 @@
void XFree86DRIExtensionInit(void);
-static Bool ATIDRIFinishScreenInit(ScreenPtr pScreen);
-
-/* Compute log base 2 of val. */
-static int
-ATILog2(int val)
+/* Initialize the visual configs that are supported by the hardware.
+ * These are combined with the visual configs that the indirect
+ * rendering core supports, and the intersection is exported to the
+ * client.
+ */
+static Bool ATIInitVisualConfigs(ScreenPtr pScreen)
{
- int bits;
+ KdScreenPriv(pScreen);
+ ATIScreenInfo(pScreenPriv);
+ int numConfigs = 0;
+ __GLXvisualConfig *pConfigs = NULL;
+ ATIConfigPrivPtr pATIConfigs = NULL;
+ ATIConfigPrivPtr *pATIConfigPtrs = NULL;
+ int i, accum, stencil, db, use_db;
+ int depth = pScreenPriv->screen->fb[0].depth;
+ int bpp = pScreenPriv->screen->fb[0].bitsPerPixel;
+
+ if (depth != 16 && (depth != 24 || bpp != 32))
+ ErrorF("DRI GLX unsupported at %d/%d depth/bpp\n", depth, bpp);
+
+ /* Same number of configs for 16 and 24bpp, so I factored this part out.
+ */
+ if (atis->depthOffset != 0)
+ use_db = 1;
+ else
+ use_db = 0;
+
+ numConfigs = 4;
+ if (use_db)
+ numConfigs *= 2;
+
+ pConfigs = xcalloc(sizeof(__GLXvisualConfig), numConfigs);
+ pATIConfigs = xcalloc(sizeof(ATIConfigPrivRec), numConfigs);
+ pATIConfigPtrs = xcalloc(sizeof(ATIConfigPrivPtr), numConfigs);
+ if (pConfigs == NULL || pATIConfigs == NULL || pATIConfigPtrs == NULL) {
+ xfree(pConfigs);
+ xfree(pATIConfigs);
+ xfree(pATIConfigPtrs);
+ return FALSE;
+ }
- if (!val)
- return 1;
- for (bits = 0; val != 0; val >>= 1, ++bits)
- ;
- return bits;
+ i = 0;
+ if (depth == 16) {
+ for (db = 0; db <= use_db; db++) {
+ for (accum = 0; accum <= 1; accum++) {
+ for (stencil = 0; stencil <= 1; stencil++) {
+ pATIConfigPtrs[i] = &pATIConfigs[i];
+
+ pConfigs[i].vid = (VisualID)(-1);
+ pConfigs[i].class = -1;
+ pConfigs[i].rgba = TRUE;
+ pConfigs[i].redSize = 5;
+ pConfigs[i].greenSize = 6;
+ pConfigs[i].blueSize = 5;
+ pConfigs[i].alphaSize = 0;
+ pConfigs[i].redMask = 0x0000F800;
+ pConfigs[i].greenMask = 0x000007E0;
+ pConfigs[i].blueMask = 0x0000001F;
+ pConfigs[i].alphaMask = 0x00000000;
+ if (accum) { /* Simulated in software */
+ pConfigs[i].accumRedSize = 16;
+ pConfigs[i].accumGreenSize = 16;
+ pConfigs[i].accumBlueSize = 16;
+ pConfigs[i].accumAlphaSize = 0;
+ } else {
+ pConfigs[i].accumRedSize = 0;
+ pConfigs[i].accumGreenSize = 0;
+ pConfigs[i].accumBlueSize = 0;
+ pConfigs[i].accumAlphaSize = 0;
+ }
+ if (db)
+ pConfigs[i].doubleBuffer = TRUE;
+ else
+ pConfigs[i].doubleBuffer = FALSE;
+ pConfigs[i].stereo = FALSE;
+ pConfigs[i].bufferSize = 16;
+ pConfigs[i].depthSize = 16;
+ if (stencil)
+ pConfigs[i].stencilSize = 8;
+ else
+ pConfigs[i].stencilSize = 0;
+ pConfigs[i].auxBuffers = 0;
+ pConfigs[i].level = 0;
+ if (accum) {
+ pConfigs[i].visualRating = GLX_SLOW_CONFIG;
+ } else {
+ pConfigs[i].visualRating = GLX_NONE;
+ }
+ pConfigs[i].transparentPixel = GLX_NONE;
+ pConfigs[i].transparentRed = 0;
+ pConfigs[i].transparentGreen = 0;
+ pConfigs[i].transparentBlue = 0;
+ pConfigs[i].transparentAlpha = 0;
+ pConfigs[i].transparentIndex = 0;
+ i++;
+ }
+ }
+ }
+ } else {
+ for (db = 0; db <= use_db; db++) {
+ for (accum = 0; accum <= 1; accum++) {
+ for (stencil = 0; stencil <= 1; stencil++) {
+ pATIConfigPtrs[i] = &pATIConfigs[i];
+
+ pConfigs[i].vid = (VisualID)(-1);
+ pConfigs[i].class = -1;
+ pConfigs[i].rgba = TRUE;
+ pConfigs[i].redSize = 8;
+ pConfigs[i].greenSize = 8;
+ pConfigs[i].blueSize = 8;
+ pConfigs[i].alphaSize = 8;
+ pConfigs[i].redMask = 0x00FF0000;
+ pConfigs[i].greenMask = 0x0000FF00;
+ pConfigs[i].blueMask = 0x000000FF;
+ pConfigs[i].alphaMask = 0xFF000000;
+ if (accum) { /* Simulated in software */
+ pConfigs[i].accumRedSize = 16;
+ pConfigs[i].accumGreenSize = 16;
+ pConfigs[i].accumBlueSize = 16;
+ pConfigs[i].accumAlphaSize = 16;
+ } else {
+ pConfigs[i].accumRedSize = 0;
+ pConfigs[i].accumGreenSize = 0;
+ pConfigs[i].accumBlueSize = 0;
+ pConfigs[i].accumAlphaSize = 0;
+ }
+ if (db)
+ pConfigs[i].doubleBuffer = TRUE;
+ else
+ pConfigs[i].doubleBuffer = FALSE;
+ pConfigs[i].stereo = FALSE;
+ pConfigs[i].bufferSize = 32;
+ if (stencil) {
+ pConfigs[i].depthSize = 24;
+ pConfigs[i].stencilSize = 8;
+ } else {
+ pConfigs[i].depthSize = 24;
+ pConfigs[i].stencilSize = 0;
+ }
+ pConfigs[i].auxBuffers = 0;
+ pConfigs[i].level = 0;
+ if (accum) {
+ pConfigs[i].visualRating = GLX_SLOW_CONFIG;
+ } else {
+ pConfigs[i].visualRating = GLX_NONE;
+ }
+ pConfigs[i].transparentPixel = GLX_NONE;
+ pConfigs[i].transparentRed = 0;
+ pConfigs[i].transparentGreen = 0;
+ pConfigs[i].transparentBlue = 0;
+ pConfigs[i].transparentAlpha = 0;
+ pConfigs[i].transparentIndex = 0;
+ i++;
+ }
+ }
+ }
+ }
+
+ atis->numVisualConfigs = numConfigs;
+ atis->pVisualConfigs = pConfigs;
+ atis->pVisualConfigsPriv = pATIConfigs;
+ GlxSetVisualConfigs(numConfigs, pConfigs, (void**)pATIConfigPtrs);
+ return TRUE;
}
static void
@@ -225,7 +375,7 @@ ATIDRIAgpInit(ScreenPtr pScreen)
R128_BM_PM4_RD_FORCE_TO_PCI |
R128_BM_GLOBAL_FORCE_TO_PCI);
MMIO_OUT32(mmio, R128_REG_BM_CHUNK_0_VAL, chunk);
-
+
/* Ensure AGP GART is used (for now) */
MMIO_OUT32(mmio, R128_REG_PCI_GART_PAGE, 1);
}
@@ -307,8 +457,8 @@ R128DRIKernelInit(ScreenPtr pScreen)
drmInfo.ring_size = atis->ringSize*1024*1024;
drmInfo.usec_timeout = atis->DMAusecTimeout;
- drmInfo.fb_bpp = pScreenPriv->screen->fb[0].depth;
- drmInfo.depth_bpp = pScreenPriv->screen->fb[0].depth;
+ drmInfo.fb_bpp = pScreenPriv->screen->fb[0].bitsPerPixel;
+ drmInfo.depth_bpp = pScreenPriv->screen->fb[0].bitsPerPixel;
/* XXX: pitches are in pixels on r128. */
drmInfo.front_offset = atis->frontOffset;
@@ -358,8 +508,8 @@ RadeonDRIKernelInit(ScreenPtr pScreen)
drmInfo.ring_size = atis->ringSize*1024*1024;
drmInfo.usec_timeout = atis->DMAusecTimeout;
- drmInfo.fb_bpp = pScreenPriv->screen->fb[0].depth;
- drmInfo.depth_bpp = pScreenPriv->screen->fb[0].depth;
+ drmInfo.fb_bpp = pScreenPriv->screen->fb[0].bitsPerPixel;
+ drmInfo.depth_bpp = pScreenPriv->screen->fb[0].bitsPerPixel;
drmInfo.front_offset = atis->frontOffset;
drmInfo.front_pitch = atis->frontPitch;
@@ -452,8 +602,7 @@ static void ATIDRISwapContext(ScreenPtr pScreen, DRISyncType syncType,
if ((syncType==DRI_3D_SYNC) && (oldContextType==DRI_2D_CONTEXT) &&
(newContextType==DRI_2D_CONTEXT)) {
/* Entering from Wakeup */
- /* XXX: XFree86 sets NeedToSync */
-
+ KdMarkSync(pScreen);
}
if ((syncType==DRI_2D_SYNC) && (oldContextType==DRI_NO_CONTEXT) &&
(newContextType==DRI_2D_CONTEXT)) {
@@ -463,6 +612,8 @@ static void ATIDRISwapContext(ScreenPtr pScreen, DRISyncType syncType,
}
}
+static Bool ATIDRIFinishScreenInit(ScreenPtr pScreen);
+
/* Initialize the screen-specific data structures for the DRI and the
Rage 128. This is the main entry point to the device-specific
initialization code. It calls device-independent DRI functions to
@@ -497,14 +648,6 @@ ATIDRIScreenInit(ScreenPtr pScreen)
atis->gartTexSize = 1;
atis->DMAusecTimeout = 10000;
- atis->frontOffset = 0;
- atis->frontPitch = pScreenPriv->screen->fb[0].byteStride;
- atis->backOffset = 0; /* XXX */
- atis->backPitch = pScreenPriv->screen->fb[0].byteStride;
- atis->depthOffset = 0; /* XXX */
- atis->depthPitch = 0; /* XXX */
- atis->spanOffset = 0; /* XXX */
-
if (atic->drmFd < 0)
return FALSE;
@@ -549,6 +692,7 @@ ATIDRIScreenInit(ScreenPtr pScreen)
pDRIInfo->ddxDriverMajorVersion = 4;
pDRIInfo->ddxDriverMinorVersion = 0;
pDRIInfo->ddxDriverPatchVersion = 0;
+ /* XXX: RADEON_FB_BASE(pScreenPriv->card); */
pDRIInfo->frameBufferPhysicalAddress =
(unsigned long)pScreenPriv->screen->memory_base;
pDRIInfo->frameBufferSize = pScreenPriv->screen->memory_size;
@@ -634,7 +778,7 @@ ATIDRIScreenInit(ScreenPtr pScreen)
}
#ifdef GLXEXT
- if (!R128InitVisualConfigs(pScreen)) {
+ if (!ATIInitVisualConfigs(pScreen)) {
ATIDRICloseScreen(pScreen);
return FALSE;
}
@@ -824,8 +968,6 @@ ATIDRIFinishScreenInit(ScreenPtr pScreen)
}
}
- XFree86DRIExtensionInit();
-
atis->using_dri = TRUE;
return TRUE;
diff --git a/hw/kdrive/ati/radeon_composite.c b/hw/kdrive/ati/radeon_composite.c
index 7dc368dbd..94f43e2a1 100644
--- a/hw/kdrive/ati/radeon_composite.c
+++ b/hw/kdrive/ati/radeon_composite.c
@@ -79,19 +79,6 @@ static CARD32 RadeonBlendOp[] = {
RADEON_SRC_BLEND_GL_ZERO | RADEON_DST_BLEND_GL_ONE,
};
-/* Compute log base 2 of val. */
-static int
-ATILog2(int val)
-{
- int bits;
-
- if (!val)
- return 1;
- for (bits = 0; val != 0; val >>= 1, ++bits)
- ;
- return bits;
-}
-
static Bool
RadeonTextureSetup(PicturePtr pPict, PixmapPtr pPix, int unit)
{