1. Right now libGLcore has several entry-points for getting GLX visual information into the driver. The file programs/Xserver/GL/mesa/X/xf86glx.c contains all of this interface. The interface functions are __MESA_initVisuals, __MESA_setVisualConfigs, and __MESA_screenProbe. __MESA_screenProbe is analogous to __driCreateNewScreen. The other two functions server part of the purpose of __driCreateNewScreen, but they also do some work not related to the driver. They create a list of X (not GLX) visuals to give back to the X server. That functionality should be moved into libglx.a.
2. Mesa's X11 driver, which is the basis of libGLcore, depends on information from an X VisualInfo. Most of the uses can be eliminated trivially, but the depth / nplanes and ColomapEntries / colormap_size fields are another story. The problem here is that the __driCreateNewScreen doesn't, and can't, provide VIsualInfo structures to the driver.
3. libglx.a calls functions in directly instead of using a dispatch table. Let me clarify this a bit. On the client-side, the symbol glVertex3f is libGL.so. When an app calls that function, it looks up the "real" function and calls it. On the server-side, the symbol glVertex3f is in libGLcore.so (i.e., the driver). When a glVertex3f protocol message comes in, libglx.a calls this function directly. This function then may (or may not, as in the case of the Mac OS X libGLcore.a) do a dispatch table look-up. What should happen is the protocol functions should do the dispatch table look-up and call the function from the table.
Those are the big issues that I could find. The rest of it just looks like changing function parameters and data structures, or moving code from libGLcore to libglx. I've attached a patch that removes some of the dependance on the VisualInfo structure and removes some redundant fields from the mesa_visual structure. Unless there are objections, I will commit this soon. I've only tested this with stand-alone Mesa so far.
Index: include/GL/xmesa_x.h
===================================================================
RCS file: /cvs/mesa/Mesa/include/GL/xmesa_x.h,v
retrieving revision 1.3
diff -u -d -r1.3 xmesa_x.h
--- include/GL/xmesa_x.h 5 Jun 2003 00:50:26 -0000 1.3
+++ include/GL/xmesa_x.h 16 Feb 2004 20:55:20 -0000
@@ -74,16 +74,11 @@
#define XMesaFreeGC XFreeGC
#define GET_COLORMAP_SIZE(__v) __v->visinfo->colormap_size
-#define GET_REDMASK(__v) __v->visinfo->red_mask
-#define GET_GREENMASK(__v) __v->visinfo->green_mask
-#define GET_BLUEMASK(__v) __v->visinfo->blue_mask
-#if defined(__cplusplus) || defined(c_plusplus)
-#define GET_VISUAL_CLASS(__v) __v->visinfo->c_class
-#else
-#define GET_VISUAL_CLASS(__v) __v->visinfo->class
-#endif
+#define GET_REDMASK(__v) __v->mesa_visual.redMask
+#define GET_GREENMASK(__v) __v->mesa_visual.greenMask
+#define GET_BLUEMASK(__v) __v->mesa_visual.blueMask
#define GET_VISUAL_DEPTH(__v) __v->visinfo->depth
-#define GET_BLACK_PIXEL(__v) BlackPixel(__v->display, __v->visinfo->screen)
+#define GET_BLACK_PIXEL(__v) BlackPixel(__v->display, __v->mesa_visual.screen)
#define CHECK_BYTE_ORDER(__v) host_byte_order()==ImageByteOrder(__v->display)
#define CHECK_FOR_HPCR(__v) XInternAtom(__v->display, "_HP_RGB_SMOOTH_MAP_LIST",
True)
Index: include/GL/xmesa_xf86.h
===================================================================
RCS file: /cvs/mesa/Mesa/include/GL/xmesa_xf86.h,v
retrieving revision 1.6
diff -u -d -r1.6 xmesa_xf86.h
--- include/GL/xmesa_xf86.h 5 Jun 2003 00:50:26 -0000 1.6
+++ include/GL/xmesa_xf86.h 16 Feb 2004 20:55:20 -0000
@@ -175,10 +175,9 @@
} while (0)
#define GET_COLORMAP_SIZE(__v) __v->visinfo->ColormapEntries
-#define GET_REDMASK(__v) __v->visinfo->redMask
-#define GET_GREENMASK(__v) __v->visinfo->greenMask
-#define GET_BLUEMASK(__v) __v->visinfo->blueMask
-#define GET_VISUAL_CLASS(__v) __v->visinfo->class
+#define GET_REDMASK(__v) __v->mesa_visual.redMask
+#define GET_GREENMASK(__v) __v->mesa_visual.greenMask
+#define GET_BLUEMASK(__v) __v->mesa_visual.blueMask
#define GET_VISUAL_DEPTH(__v) __v->visinfo->nplanes
#define GET_BLACK_PIXEL(__v) __v->display->blackPixel
#define CHECK_BYTE_ORDER(__v) GL_TRUE
Index: src/mesa/drivers/x11/fakeglx.c
===================================================================
RCS file: /cvs/mesa/Mesa/src/mesa/drivers/x11/fakeglx.c,v
retrieving revision 1.89
diff -u -d -r1.89 fakeglx.c
--- src/mesa/drivers/x11/fakeglx.c 8 Feb 2004 00:11:14 -0000 1.89
+++ src/mesa/drivers/x11/fakeglx.c 16 Feb 2004 20:55:20 -0000
@@ -296,7 +296,7 @@
for (i=0; i<NumVisuals; i++) {
XMesaVisual v = VisualTable[i];
if (v->display == dpy
- && v->level == level
+ && v->mesa_visual.level == level
&& v->ximage_flag == ximageFlag
&& v->mesa_visual.rgbMode == rgbFlag
&& v->mesa_visual.doubleBufferMode == dbFlag
@@ -1559,7 +1559,7 @@
*value = xmvis->visinfo->depth;
return 0;
case GLX_LEVEL:
- *value = xmvis->level;
+ *value = xmvis->mesa_visual.level;
return 0;
case GLX_RGBA:
if (xmvis->mesa_visual.rgbMode) {
@@ -1623,11 +1623,11 @@
}
return 0;
case GLX_TRANSPARENT_TYPE_EXT:
- if (xmvis->level==0) {
+ if (xmvis->mesa_visual.level==0) {
/* normal planes */
*value = GLX_NONE_EXT;
}
- else if (xmvis->level>0) {
+ else if (xmvis->mesa_visual.level>0) {
/* overlay */
if (xmvis->mesa_visual.rgbMode) {
*value = GLX_TRANSPARENT_RGB_EXT;
@@ -1636,7 +1636,7 @@
*value = GLX_TRANSPARENT_INDEX_EXT;
}
}
- else if (xmvis->level<0) {
+ else if (xmvis->mesa_visual.level<0) {
/* underlay */
*value = GLX_NONE_EXT;
}
@@ -1668,8 +1668,8 @@
*/
case GLX_VISUAL_CAVEAT_EXT:
/* test for zero, just in case */
- if (xmvis->VisualCaveat > 0)
- *value = xmvis->VisualCaveat;
+ if (xmvis->mesa_visual.visualRating > 0)
+ *value = xmvis->mesa_visual.visualRating;
else
*value = GLX_NONE_EXT;
return 0;
Index: src/mesa/drivers/x11/xm_api.c
===================================================================
RCS file: /cvs/mesa/Mesa/src/mesa/drivers/x11/xm_api.c,v
retrieving revision 1.64
diff -u -d -r1.64 xm_api.c
--- src/mesa/drivers/x11/xm_api.c 20 Jan 2004 02:49:29 -0000 1.64
+++ src/mesa/drivers/x11/xm_api.c 16 Feb 2004 20:55:20 -0000
@@ -1200,26 +1200,25 @@
* being color indexed. This is weird but might be useful to someone.
*/
v->dithered_pf = v->undithered_pf = PF_Index;
- v->index_bits = GET_VISUAL_DEPTH(v);
+ v->mesa_visual.indexBits = GET_VISUAL_DEPTH(v);
}
else {
/* RGB WINDOW:
* We support RGB rendering into almost any kind of visual.
*/
- int xclass;
- xclass = GET_VISUAL_CLASS(v);
- if (xclass==TrueColor || xclass==DirectColor) {
+ const int xclass = v->mesa_visual.visualType;
+ if (xclass==GLX_TRUE_COLOR || xclass==GLX_DIRECT_COLOR) {
setup_truecolor( v, b, cmap );
}
- else if (xclass==StaticGray && GET_VISUAL_DEPTH(v)==1) {
+ else if (xclass==GLX_STATIC_GRAY && GET_VISUAL_DEPTH(v)==1) {
setup_monochrome( v, b );
}
- else if (xclass==GrayScale || xclass==StaticGray) {
+ else if (xclass==GLX_GRAY_SCALE || xclass==GLX_STATIC_GRAY) {
if (!setup_grayscale( client, v, b, cmap )) {
return GL_FALSE;
}
}
- else if ((xclass==PseudoColor || xclass==StaticColor)
+ else if ((xclass==GLX_PSEUDO_COLOR || xclass==GLX_STATIC_COLOR)
&& GET_VISUAL_DEPTH(v)>=4 && GET_VISUAL_DEPTH(v)<=16) {
if (!setup_dithered_color( client, v, b, cmap )) {
return GL_FALSE;
@@ -1229,7 +1228,7 @@
_mesa_warning(NULL, "XMesa: RGB mode rendering not supported in given
visual.");
return GL_FALSE;
}
- v->index_bits = 0;
+ v->mesa_visual.indexBits = 0;
if (_mesa_getenv("MESA_NO_DITHER")) {
v->dithered_pf = v->undithered_pf;
@@ -1246,7 +1245,7 @@
_mesa_printf("X/Mesa visual = %p\n", (void *) v);
_mesa_printf("X/Mesa dithered pf = %u\n", v->dithered_pf);
_mesa_printf("X/Mesa undithered pf = %u\n", v->undithered_pf);
- _mesa_printf("X/Mesa level = %d\n", v->level);
+ _mesa_printf("X/Mesa level = %d\n", v->mesa_visual.level);
_mesa_printf("X/Mesa depth = %d\n", GET_VISUAL_DEPTH(v));
_mesa_printf("X/Mesa bits per pixel = %d\n", v->BitsPerPixel);
}
@@ -1410,6 +1409,34 @@
}
+#define NUM_VISUAL_TYPES 6
+
+/**
+ * Convert an X visual type to a GLX visual type.
+ *
+ * \param visualType X visual type (i.e., \c TrueColor, \c StaticGray, etc.)
+ * to be converted.
+ * \return If \c visualType is a valid X visual type, a GLX visual type will
+ * be returned. Otherwise \c GLX_NONE will be returned.
+ *
+ * \note
+ * This code was lifted directly from lib/GL/glx/glcontextmodes.c in the
+ * DRI CVS tree.
+ */
+static GLint
+xmesa_convert_from_x_visual_type( int visualType )
+{
+ static const int glx_visual_types[ NUM_VISUAL_TYPES ] = {
+ GLX_STATIC_GRAY, GLX_GRAY_SCALE,
+ GLX_STATIC_COLOR, GLX_PSEUDO_COLOR,
+ GLX_TRUE_COLOR, GLX_DIRECT_COLOR
+ };
+
+ return ( (unsigned) visualType < NUM_VISUAL_TYPES )
+ ? glx_visual_types[ visualType ] : GLX_NONE;
+}
+
+
/**********************************************************************/
/***** Public Functions *****/
/**********************************************************************/
@@ -1499,19 +1526,6 @@
MEMCPY(v->visinfo, visinfo, sizeof(*visinfo));
#endif
-#ifdef XFree86Server
- /* Initialize the depth of the screen */
- {
- PixmapFormatRec *format;
-
- for (format = screenInfo.formats;
- format->depth != display->rootDepth;
- format++)
- ;
- v->screen_depth = format->bitsPerPixel;
- }
-#endif
-
/* check for MESA_GAMMA environment variable */
gamma = _mesa_getenv("MESA_GAMMA");
if (gamma) {
@@ -1526,15 +1540,32 @@
}
v->ximage_flag = ximage_flag;
- v->level = level;
- v->VisualCaveat = visualCaveat;
+
+#ifdef XFree86Server
+ v->mesa_visual.redMask = visinfo->redMask;
+ v->mesa_visual.greenMask = visinfo->greenMask;
+ v->mesa_visual.blueMask = visinfo->blueMask;
+#else
+ v->mesa_visual.redMask = visinfo->red_mask;
+ v->mesa_visual.greenMask = visinfo->green_mask;
+ v->mesa_visual.blueMask = visinfo->blue_mask;
+#endif
+
+#if defined(XFree86Server) || !(defined(__cplusplus) || defined(c_plusplus))
+ v->mesa_visual.visualType = xmesa_convert_from_x_visual_type(visinfo->class);
+#else
+ v->mesa_visual.visualType = xmesa_convert_from_x_visual_type(visinfo->c_class);
+#endif
+
+ v->mesa_visual.visualRating = visualCaveat;
+ v->mesa_visual.visualID = visinfo->visualid;
+ v->mesa_visual.screen = visinfo->screen;
(void) initialize_visual_and_buffer( 0, v, NULL, rgb_flag, 0, 0 );
{
- int xclass;
- xclass = GET_VISUAL_CLASS(v);
- if (xclass==TrueColor || xclass==DirectColor) {
+ const int xclass = v->mesa_visual.visualType;
+ if (xclass==GLX_TRUE_COLOR || xclass==GLX_DIRECT_COLOR) {
red_bits = bitcount(GET_REDMASK(v));
green_bits = bitcount(GET_GREENMASK(v));
blue_bits = bitcount(GET_BLUEMASK(v));
@@ -1561,12 +1592,14 @@
rgb_flag, db_flag, stereo_flag,
red_bits, green_bits,
blue_bits, alpha_bits,
- v->index_bits,
+ v->mesa_visual.indexBits,
depth_size,
stencil_size,
accum_red_size, accum_green_size,
accum_blue_size, accum_alpha_size,
0 );
+
+ v->mesa_visual.level = level;
return v;
}
@@ -1837,13 +1870,14 @@
}
-/*
+/**
* Create a new XMesaBuffer from an X pixmap.
- * Input: v - the XMesaVisual
- * p - the pixmap
- * cmap - the colormap, may be 0 if using a TrueColor or DirectColor
- * visual for the pixmap
- * Return: new XMesaBuffer or NULL if error
+ *
+ * \param v the XMesaVisual
+ * \param p the pixmap
+ * \param cmap the colormap, may be 0 if using a \c GLX_TRUE_COLOR or
+ * \c GLX_DIRECT_COLOR visual for the pixmap
+ * \returns new XMesaBuffer or NULL if error
*/
XMesaBuffer XMesaCreatePixmapBuffer( XMesaVisual v,
XMesaPixmap p, XMesaColormap cmap )
Index: src/mesa/drivers/x11/xm_dd.c
===================================================================
RCS file: /cvs/mesa/Mesa/src/mesa/drivers/x11/xm_dd.c,v
retrieving revision 1.59
diff -u -d -r1.59 xm_dd.c
--- src/mesa/drivers/x11/xm_dd.c 20 Jan 2004 02:49:29 -0000 1.59
+++ src/mesa/drivers/x11/xm_dd.c 16 Feb 2004 20:55:20 -0000
@@ -214,10 +214,10 @@
GLboolean rmask, GLboolean gmask, GLboolean bmask, GLboolean amask)
{
const XMesaContext xmesa = XMESA_CONTEXT(ctx);
- int xclass = GET_VISUAL_CLASS(xmesa->xm_visual);
+ const int xclass = xmesa->xm_visual->mesa_visual.visualType;
(void) amask;
- if (xclass == TrueColor || xclass == DirectColor) {
+ if (xclass == GLX_TRUE_COLOR || xclass == GLX_DIRECT_COLOR) {
unsigned long m;
if (rmask && gmask && bmask) {
m = ((unsigned long)~0L);
Index: src/mesa/drivers/x11/xmesaP.h
===================================================================
RCS file: /cvs/mesa/Mesa/src/mesa/drivers/x11/xmesaP.h,v
retrieving revision 1.39
diff -u -d -r1.39 xmesaP.h
--- src/mesa/drivers/x11/xmesaP.h 20 Jan 2004 02:49:29 -0000 1.39
+++ src/mesa/drivers/x11/xmesaP.h 16 Feb 2004 20:55:20 -0000
@@ -86,17 +86,12 @@
struct xmesa_visual {
GLvisual mesa_visual; /* Device independent visual parameters */
XMesaDisplay *display; /* The X11 display */
-#ifdef XFree86Server
- GLint screen_depth; /* The depth of the screen */
-#else
+#ifndef XFree86Server
XVisualInfo *vishandle; /* Only used in fakeglx.c */
#endif
XMesaVisualInfo visinfo; /* X's visual info (pointer to private copy) */
GLint BitsPerPixel; /* True bits per pixel for XImages */
- GLint level; /* 0=normal, 1=overlay, etc */
- GLint VisualCaveat; /* for GLX_EXT_visual_rating extension */
-
GLboolean ximage_flag; /* Use XImage for back buffer (not pixmap)? */
enum pixel_format dithered_pf; /* Pixel format when dithering */
@@ -106,9 +101,6 @@
GLfloat GreenGamma;
GLfloat BlueGamma;
- GLint rmult, gmult, bmult; /* Range of color values */
- GLint index_bits; /* Bits per pixel in CI mode */
-
/* For PF_TRUECOLOR */
GLint rshift, gshift, bshift;/* Pixel color component shifts */
GLubyte Kernel[16]; /* Dither kernel */
