use wrappers from imports.h rather than stdio, stdlib, etc functions.
[mesa.git] / src / mesa / drivers / x11 / xm_api.c
index 5bb7b05f86a56a88a16814ac2a3d0b07deaaf1b4..6dbb3f38567512888c9459eb048558b568cac9cd 100644 (file)
@@ -1,10 +1,10 @@
-/* $Id: xm_api.c,v 1.21 2001/04/27 21:18:25 brianp Exp $ */
+/* $Id: xm_api.c,v 1.50 2002/10/30 20:24:46 brianp Exp $ */
 
 /*
  * Mesa 3-D graphics library
- * Version:  3.5
+ * Version:  5.0
  *
- * Copyright (C) 1999-2000  Brian Paul   All Rights Reserved.
+ * Copyright (C) 1999-2002  Brian Paul   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"),
@@ -23,7 +23,7 @@
  * 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.
  */
-
+/* $XFree86: xc/extras/Mesa/src/X/xm_api.c,v 1.2 2002/02/26 23:37:31 tsi Exp $ */
 
 /*
  * This file contains the implementations of all the XMesa* functions.
 #include "context.h"
 #include "extensions.h"
 #include "glthread.h"
+#include "imports.h"
 #include "matrix.h"
-#include "mem.h"
 #include "mmath.h"
 #include "mtypes.h"
-#ifdef HAVE_CONFIG_H
-#include "conf.h"
-#endif
 #include "macros.h"
+#include "texformat.h"
+#include "texstore.h"
 #include "swrast/swrast.h"
 #include "swrast_setup/swrast_setup.h"
 #include "array_cache/acache.h"
@@ -161,16 +160,6 @@ static short hpcr_rgbTbl[3][256] = {
 /**********************************************************************/
 
 
-/*
- * X/Mesa error reporting function:
- */
-static void error( const char *msg )
-{
-   if (getenv("MESA_DEBUG"))
-      fprintf( stderr, "X/Mesa error: %s\n", msg );
-}
-
-
 /*
  * Return the host's byte order as LSBFirst or MSBFirst ala X.
  */
@@ -265,7 +254,7 @@ static GLint gamma_adjust( GLfloat gamma, GLint value, GLint max )
    }
    else {
       double x = (double) value / (double) max;
-      return IROUND_POS((GLfloat) max * pow(x, 1.0F/gamma));
+      return IROUND_POS((GLfloat) max * _mesa_pow(x, 1.0F/gamma));
    }
 }
 
@@ -279,8 +268,6 @@ static GLint gamma_adjust( GLfloat gamma, GLint value, GLint max )
  *         visinfo - desribes the visual to be used for XImages
  * Return:  true number of bits per pixel for XImages
  */
-#define GET_BITS_PER_PIXEL(xmv) bits_per_pixel(xmv)
-
 #ifdef XFree86Server
 
 static int bits_per_pixel( XMesaVisual xmv )
@@ -497,7 +484,7 @@ static GLboolean alloc_shm_back_buffer( XMesaBuffer b )
                                   ZPixmap, NULL, &b->shminfo,
                                   b->width, b->height );
    if (b->backimage == NULL) {
-      error("alloc_back_buffer: Shared memory error (XShmCreateImage), disabling.");
+      _mesa_warning(NULL, "alloc_back_buffer: Shared memory error (XShmCreateImage), disabling.");
       b->shm = 0;
       return GL_FALSE;
    }
@@ -505,11 +492,10 @@ static GLboolean alloc_shm_back_buffer( XMesaBuffer b )
    b->shminfo.shmid = shmget( IPC_PRIVATE, b->backimage->bytes_per_line
                             * b->backimage->height, IPC_CREAT|0777 );
    if (b->shminfo.shmid < 0) {
-      if (getenv("MESA_DEBUG"))
-          perror("alloc_back_buffer");
+      _mesa_warning(NULL, "shmget failed while allocating back buffer");
       XDestroyImage( b->backimage );
       b->backimage = NULL;
-      error("alloc_back_buffer: Shared memory error (shmget), disabling.");
+      _mesa_warning(NULL, "alloc_back_buffer: Shared memory error (shmget), disabling.");
       b->shm = 0;
       return GL_FALSE;
    }
@@ -517,12 +503,11 @@ static GLboolean alloc_shm_back_buffer( XMesaBuffer b )
    b->shminfo.shmaddr = b->backimage->data
                       = (char*)shmat( b->shminfo.shmid, 0, 0 );
    if (b->shminfo.shmaddr == (char *) -1) {
-      if (getenv("MESA_DEBUG"))
-          perror("alloc_back_buffer");
+      _mesa_warning(NULL, "shmat() failed while allocating back buffer");
       XDestroyImage( b->backimage );
       shmctl( b->shminfo.shmid, IPC_RMID, 0 );
       b->backimage = NULL;
-      error("alloc_back_buffer: Shared memory error (shmat), disabling.");
+      _mesa_warning(NULL, "alloc_back_buffer: Shared memory error (shmat), disabling.");
       b->shm = 0;
       return GL_FALSE;
    }
@@ -625,9 +610,7 @@ void xmesa_alloc_back_buffer( XMesaBuffer b )
         b->backimage = XMesaCreateImage(b->xm_visual->BitsPerPixel,
                                         b->width, b->height, NULL);
 #else
-      if (b->shm==0
-         || alloc_shm_back_buffer(b)==GL_FALSE
-         ) {
+      if (b->shm==0 || alloc_shm_back_buffer(b)==GL_FALSE) {
         /* Allocate a regular XImage for the back buffer. */
         b->backimage = XCreateImage( b->xm_visual->display,
                                       b->xm_visual->visinfo->visual,
@@ -637,12 +620,12 @@ void xmesa_alloc_back_buffer( XMesaBuffer b )
                                      8, 0 );  /* pad, bytes_per_line */
 #endif
         if (!b->backimage) {
-           error("alloc_back_buffer: XCreateImage failed.");
+           _mesa_warning(NULL, "alloc_back_buffer: XCreateImage failed.");
         }
          b->backimage->data = (char *) MALLOC( b->backimage->height
                                              * b->backimage->bytes_per_line );
          if (!b->backimage->data) {
-            error("alloc_back_buffer: MALLOC failed.");
+            _mesa_warning(NULL, "alloc_back_buffer: MALLOC failed.");
             XMesaDestroyImage( b->backimage );
             b->backimage = NULL;
          }
@@ -875,8 +858,8 @@ static GLboolean setup_grayscale( int client, XMesaVisual v,
             buffer->pixel_to_b[xcol.pixel] = gray;
          }
 
-         if (colorsfailed && getenv("MESA_DEBUG")) {
-            fprintf( stderr,
+         if (colorsfailed && _mesa_getenv("MESA_DEBUG")) {
+            _mesa_warning(NULL,
                   "Note: %d out of 256 needed colors do not match exactly.\n",
                   colorsfailed );
          }
@@ -955,8 +938,8 @@ static GLboolean setup_dithered_color( int client, XMesaVisual v,
             }
          }
 
-         if (colorsfailed && getenv("MESA_DEBUG")) {
-            fprintf( stderr,
+         if (colorsfailed && _mesa_getenv("MESA_DEBUG")) {
+            _mesa_warning(NULL,
                   "Note: %d out of %d needed colors do not match exactly.\n",
                   colorsfailed, _R*_G*_B );
          }
@@ -989,19 +972,19 @@ static void setup_8bit_hpcr( XMesaVisual v )
 
    g = 1.0 / v->RedGamma;
    for (i=0; i<256; i++) {
-      GLint red = IROUND_POS(255.0 * pow( hpcr_rgbTbl[0][i]/255.0, g ));
+      GLint red = IROUND_POS(255.0 * _mesa_pow( hpcr_rgbTbl[0][i]/255.0, g ));
       v->hpcr_rgbTbl[0][i] = CLAMP( red, 16, 239 );
    }
 
    g = 1.0 / v->GreenGamma;
    for (i=0; i<256; i++) {
-      GLint green = IROUND_POS(255.0 * pow( hpcr_rgbTbl[1][i]/255.0, g ));
+      GLint green = IROUND_POS(255.0 * _mesa_pow( hpcr_rgbTbl[1][i]/255.0, g ));
       v->hpcr_rgbTbl[1][i] = CLAMP( green, 16, 239 );
    }
 
    g = 1.0 / v->BlueGamma;
    for (i=0; i<256; i++) {
-      GLint blue = IROUND_POS(255.0 * pow( hpcr_rgbTbl[2][i]/255.0, g ));
+      GLint blue = IROUND_POS(255.0 * _mesa_pow( hpcr_rgbTbl[2][i]/255.0, g ));
       v->hpcr_rgbTbl[2][i] = CLAMP( blue, 32, 223 );
    }
    v->undithered_pf = PF_HPCR;  /* can't really disable dithering for now */
@@ -1010,7 +993,7 @@ static void setup_8bit_hpcr( XMesaVisual v )
    /* which method should I use to clear */
    /* GL_FALSE: keep the ordinary method  */
    /* GL_TRUE : clear with dither pattern */
-   v->hpcr_clear_flag = getenv("MESA_HPCR_CLEAR") ? GL_TRUE : GL_FALSE;
+   v->hpcr_clear_flag = _mesa_getenv("MESA_HPCR_CLEAR") ? GL_TRUE : GL_FALSE;
 
    if (v->hpcr_clear_flag) {
       v->hpcr_clear_pixmap = XMesaCreatePixmap(v->display,
@@ -1028,11 +1011,10 @@ static void setup_8bit_hpcr( XMesaVisual v )
  * Setup RGB rendering for a window with a True/DirectColor visual.
  */
 static void setup_truecolor( XMesaVisual v, XMesaBuffer buffer,
-                             XMesaWindow window, XMesaColormap cmap )
+                             XMesaColormap cmap )
 {
    unsigned long rmask, gmask, bmask;
    (void) buffer;
-   (void) window;
    (void) cmap;
 
    /* Compute red multiplier (mask) and bit shift */
@@ -1194,8 +1176,7 @@ static GLboolean initialize_visual_and_buffer( int client,
                                                XMesaBuffer b,
                                                GLboolean rgb_flag,
                                                XMesaDrawable window,
-                                               XMesaColormap cmap
-                                             )
+                                               XMesaColormap cmap )
 {
 #ifndef XFree86Server
    XGCValues gcvalues;
@@ -1206,7 +1187,7 @@ static GLboolean initialize_visual_and_buffer( int client,
    }
 
    /* Save true bits/pixel */
-   v->BitsPerPixel = GET_BITS_PER_PIXEL(v);
+   v->BitsPerPixel = bits_per_pixel(v);
    assert(v->BitsPerPixel > 0);
 
 
@@ -1225,7 +1206,7 @@ static GLboolean initialize_visual_and_buffer( int client,
       int xclass;
       xclass = GET_VISUAL_CLASS(v);
       if (xclass==TrueColor || xclass==DirectColor) {
-        setup_truecolor( v, b, (XMesaWindow)window, cmap );
+        setup_truecolor( v, b, cmap );
       }
       else if (xclass==StaticGray && GET_VISUAL_DEPTH(v)==1) {
         setup_monochrome( v, b );
@@ -1242,12 +1223,12 @@ static GLboolean initialize_visual_and_buffer( int client,
          }
       }
       else {
-        error("XMesa: RGB mode rendering not supported in given visual.");
+        _mesa_warning(NULL, "XMesa: RGB mode rendering not supported in given visual.");
         return GL_FALSE;
       }
       v->index_bits = 0;
 
-      if (getenv("MESA_NO_DITHER")) {
+      if (_mesa_getenv("MESA_NO_DITHER")) {
         v->dithered_pf = v->undithered_pf;
       }
    }
@@ -1258,13 +1239,13 @@ static GLboolean initialize_visual_and_buffer( int client,
     * which can help Brian figure out what's going on when a user
     * reports bugs.
     */
-   if (getenv("MESA_INFO")) {
-      fprintf(stderr, "X/Mesa visual = %p\n", v);
-      fprintf(stderr, "X/Mesa dithered pf = %u\n", v->dithered_pf);
-      fprintf(stderr, "X/Mesa undithered pf = %u\n", v->undithered_pf);
-      fprintf(stderr, "X/Mesa level = %d\n", v->level);
-      fprintf(stderr, "X/Mesa depth = %d\n", GET_VISUAL_DEPTH(v));
-      fprintf(stderr, "X/Mesa bits per pixel = %d\n", v->BitsPerPixel);
+   if (_mesa_getenv("MESA_INFO")) {
+      _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 depth = %d\n", GET_VISUAL_DEPTH(v));
+      _mesa_printf("X/Mesa bits per pixel = %d\n", v->BitsPerPixel);
    }
 
    if (b && window) {
@@ -1305,23 +1286,31 @@ static GLboolean initialize_visual_and_buffer( int client,
 #endif
       XMesaSetFunction( v->display, b->gc, GXcopy );
 
+      /* cleargc - for glClear() */
+#ifdef XFree86Server
+      b->cleargc = CreateScratchGC(v->display, window->depth);
+#else
+      b->cleargc = XCreateGC( v->display, window, 0, NULL );
+#endif
+      XMesaSetFunction( v->display, b->cleargc, GXcopy );
+
       /*
        * Don't generate Graphics Expose/NoExpose events in swapbuffers().
        * Patch contributed by Michael Pichler May 15, 1995.
        */
 #ifdef XFree86Server
-      b->cleargc = CreateScratchGC(v->display, window->depth);
+      b->swapgc = CreateScratchGC(v->display, window->depth);
       {
          CARD32 v[1];
          v[0] = FALSE;
-         dixChangeGC(NullClient, b->cleargc, GCGraphicsExposures, v, NULL);
+         dixChangeGC(NullClient, b->swapgc, GCGraphicsExposures, v, NULL);
       }
 #else
       gcvalues.graphics_exposures = False;
-      b->cleargc = XCreateGC( v->display, window,
+      b->swapgc = XCreateGC( v->display, window,
                               GCGraphicsExposures, &gcvalues);
 #endif
-      XMesaSetFunction( v->display, b->cleargc, GXcopy );
+      XMesaSetFunction( v->display, b->swapgc, GXcopy );
       /*
        * Set fill style and tile pixmap once for all for HPCR stuff
        * (instead of doing it each time in clear_color_HPCR_pixmap())
@@ -1468,7 +1457,7 @@ XMesaVisual XMesaCreateVisual( XMesaDisplay *display,
    GLint red_bits, green_bits, blue_bits, alpha_bits;
 
    /* For debugging only */
-   if (getenv("MESA_XSYNC")) {
+   if (_mesa_getenv("MESA_XSYNC")) {
       /* This makes debugging X easier.
        * In your debugger, set a breakpoint on _XError to stop when an
        * X protocol error is generated.
@@ -1526,7 +1515,7 @@ XMesaVisual XMesaCreateVisual( XMesaDisplay *display,
 #endif
 
    /* check for MESA_GAMMA environment variable */
-   gamma = getenv("MESA_GAMMA");
+   gamma = _mesa_getenv("MESA_GAMMA");
    if (gamma) {
       v->RedGamma = v->GreenGamma = v->BlueGamma = 0.0;
       sscanf( gamma, "%f %f %f", &v->RedGamma, &v->GreenGamma, &v->BlueGamma );
@@ -1609,11 +1598,10 @@ void XMesaDestroyVisual( XMesaVisual v )
  */
 XMesaContext XMesaCreateContext( XMesaVisual v, XMesaContext share_list )
 {
+   static GLboolean firstTime = GL_TRUE;
    XMesaContext c;
    GLcontext *ctx;
-   GLboolean direct = GL_TRUE; /* XXXX */
-   /* NOT_DONE: should this be GL_FALSE??? */
-   static GLboolean firstTime = GL_TRUE;
+   GLboolean direct = GL_TRUE; /* not really */
 
    if (firstTime) {
       _glthread_INIT_MUTEX(_xmesa_lock);
@@ -1627,13 +1615,15 @@ XMesaContext XMesaCreateContext( XMesaVisual v, XMesaContext share_list )
 
    ctx = c->gl_ctx = _mesa_create_context( &v->mesa_visual,
                       share_list ? share_list->gl_ctx : (GLcontext *) NULL,
-                      (void *) c, direct );
+                      (void *) c, direct);
    if (!c->gl_ctx) {
       FREE(c);
       return NULL;
    }
 
    _mesa_enable_sw_extensions(ctx);
+   _mesa_enable_1_3_extensions(ctx);
+   _mesa_enable_1_4_extensions(ctx);
 
    if (CHECK_BYTE_ORDER(v)) {
       c->swapbytes = GL_FALSE;
@@ -1643,16 +1633,14 @@ XMesaContext XMesaCreateContext( XMesaVisual v, XMesaContext share_list )
    }
 
    c->xm_visual = v;
+   c->xm_draw_buffer = NULL;   /* set later by XMesaMakeCurrent */
+   c->xm_read_buffer = NULL;   /* set later by XMesaMakeCurrent */
    c->xm_buffer = NULL;   /* set later by XMesaMakeCurrent */
    c->display = v->display;
    c->pixelformat = v->dithered_pf;      /* Dithering is enabled by default */
 
    ctx->Driver.UpdateState = xmesa_update_state;
 
-#if defined(GLX_DIRECT_RENDERING) && !defined(XFree86Server)
-   c->driContextPriv = driContextPriv;
-#endif
-
    /* Initialize the software rasterizer and helper modules.
     */
    _swrast_CreateContext( ctx );
@@ -1666,12 +1654,6 @@ XMesaContext XMesaCreateContext( XMesaVisual v, XMesaContext share_list )
     */
    xmesa_init_pointers( ctx );
 
-
-   /* Run the config file
-    */
-   _mesa_context_initialize( ctx );
-
-
    return c;
 }
 
@@ -1681,8 +1663,8 @@ XMesaContext XMesaCreateContext( XMesaVisual v, XMesaContext share_list )
 void XMesaDestroyContext( XMesaContext c )
 {
 #ifdef FX
-   if (c->xm_buffer && c->xm_buffer->FXctx)
-      fxMesaDestroyContext(c->xm_buffer->FXctx);
+   if (c->xm_draw_buffer && c->xm_buffer->FXctx)
+      fxMesaDestroyContext(c->xm_draw_buffer->FXctx);
 #endif
    if (c->gl_ctx) {
       _swsetup_DestroyContext( c->gl_ctx );
@@ -1692,32 +1674,6 @@ void XMesaDestroyContext( XMesaContext c )
       _mesa_destroy_context( c->gl_ctx );
    }
 
-   /* Disassociate old buffer with this context */
-   if (c->xm_buffer)
-       c->xm_buffer->xm_context = NULL;
-
-   /* Destroy any buffers which are using this context.  If we don't
-    * we may have dangling references.  Hmm, maybe we should just
-    * set the buffer's context pointer to NULL instead of deleting it?
-    * Let's see if we get any bug reports...
-    * This contributed by Doug Rabson <dfr@calcaphon.com>
-    */
-   {
-      XMesaBuffer b, next;
-      for (b = XMesaBufferList; b; b = next) {
-         next = b->Next;
-         if (!b->pixmap_flag) {
-#ifndef XFree86Server
-            XSync(b->display, False);
-#endif
-            if (b->xm_context == c) {
-               /* found a context created for this context */
-               XMesaDestroyBuffer( b );
-            }
-         }
-      }
-   }
-
    FREE( c );
 }
 
@@ -1762,16 +1718,12 @@ XMesaBuffer XMesaCreateWindowBuffer2( XMesaVisual v, XMesaWindow w,
 
    if (GET_VISUAL_DEPTH(v) != attr.depth) {
 #endif
-      if (getenv("MESA_DEBUG")) {
-         fprintf(stderr, "XMesaCreateWindowBuffer: depth mismatch between visual and window!\n");
-      }
+      _mesa_warning(NULL, "XMesaCreateWindowBuffer: depth mismatch between visual and window!\n");
       return NULL;
    }
 
-   b->xm_context = NULL; /* Associate no context with this buffer */
-
    b->xm_visual = v;
-   b->pixmap_flag = GL_FALSE;
+   b->type = WINDOW;
    b->display = v->display;
 #ifdef XFree86Server
    b->cmap = (ColormapPtr)LookupIDByType(wColormap(w), RT_COLORMAP);
@@ -1780,9 +1732,7 @@ XMesaBuffer XMesaCreateWindowBuffer2( XMesaVisual v, XMesaWindow w,
       b->cmap = attr.colormap;
    }
    else {
-      if (getenv("MESA_DEBUG")) {
-         fprintf(stderr, "Window %u has no colormap!\n", (unsigned int) w);
-      }
+      _mesa_warning(NULL, "Window %u has no colormap!\n", (unsigned int) w);
       /* this is weird, a window w/out a colormap!? */
       /* OK, let's just allocate a new one and hope for the best */
       b->cmap = XCreateColormap(v->display, w, attr.visual, AllocNone);
@@ -1816,7 +1766,7 @@ XMesaBuffer XMesaCreateWindowBuffer2( XMesaVisual v, XMesaWindow w,
    }
 
 #ifdef FX
-   fxEnvVar = getenv("MESA_GLX_FX");
+   fxEnvVar = _mesa_getenv("MESA_GLX_FX");
    if (fxEnvVar) {
      if (fxEnvVar[0]!='d') {
        int attribs[100];
@@ -1875,17 +1825,13 @@ XMesaBuffer XMesaCreateWindowBuffer2( XMesaVisual v, XMesaWindow w,
      }
    }
    else {
-      fprintf(stderr,"WARNING: This Mesa Library includes the Glide driver but\n");
-      fprintf(stderr,"         you have not defined the MESA_GLX_FX env. var.\n");
-      fprintf(stderr,"         (check the README.3DFX file for more information).\n\n");
-      fprintf(stderr,"         you can disable this message with a 'export MESA_GLX_FX=disable'.\n");
+      _mesa_warning(NULL, "WARNING: This Mesa Library includes the Glide driver but\n");
+      _mesa_warning(NULL, "         you have not defined the MESA_GLX_FX env. var.\n");
+      _mesa_warning(NULL, "         (check the README.3DFX file for more information).\n\n");
+      _mesa_warning(NULL, "         you can disable this message with a 'export MESA_GLX_FX=disable'.\n");
    }
 #endif
 
-#if defined(GLX_DIRECT_RENDERING) && !defined(XFree86Server)
-   b->driDrawPriv = driDrawPriv;
-#endif
-
    return b;
 }
 
@@ -1920,10 +1866,8 @@ XMesaBuffer XMesaCreatePixmapBuffer( XMesaVisual v,
 
    assert(v);
 
-   b->xm_context = NULL; /* Associate no context with this buffer */
-
    b->xm_visual = v;
-   b->pixmap_flag = GL_TRUE;
+   b->type = PIXMAP;
    b->display = v->display;
    b->cmap = cmap;
 
@@ -1955,11 +1899,64 @@ XMesaBuffer XMesaCreatePixmapBuffer( XMesaVisual v,
       return NULL;
    }
 
-#if defined(GLX_DIRECT_RENDERING) && !defined(XFree86Server)
-   b->driDrawPriv = driDrawPriv;
-#endif
+   return b;
+}
+
+
+
+XMesaBuffer XMesaCreatePBuffer( XMesaVisual v, XMesaColormap cmap,
+                                unsigned int width, unsigned int height )
+{
+#ifdef XFree86Server
+   return 0;
+#else
+   int client = 0;
+   XMesaWindow root;
+   XMesaDrawable drawable;  /* X Pixmap Drawable */
+   XMesaBuffer b = alloc_xmesa_buffer();
+   if (!b) {
+      return NULL;
+   }
+
+   b->xm_visual = v;
+   b->type = PBUFFER;
+   b->display = v->display;
+   b->cmap = cmap;
+
+   /* allocate pixmap for front buffer */
+   root = RootWindow( v->display, v->visinfo->screen );
+   drawable = XCreatePixmap( v->display, root, width, height, v->visinfo->depth );
+
+   /* determine back buffer implementation */
+   if (v->mesa_visual.doubleBufferMode) {
+      if (v->ximage_flag) {
+        b->db_state = BACK_XIMAGE;
+      }
+      else {
+        b->db_state = BACK_PIXMAP;
+      }
+   }
+   else {
+      b->db_state = 0;
+   }
+
+   _mesa_initialize_framebuffer(&b->mesa_buffer,
+                                &v->mesa_visual,
+                                v->mesa_visual.depthBits > 0,
+                                v->mesa_visual.stencilBits > 0,
+                                v->mesa_visual.accumRedBits +
+                                v->mesa_visual.accumGreenBits +
+                                v->mesa_visual.accumBlueBits > 0,
+                                v->mesa_visual.alphaBits > 0 );
+
+   if (!initialize_visual_and_buffer(client, v, b, v->mesa_visual.rgbMode,
+                                    drawable, cmap)) {
+      free_xmesa_buffer(client, b);
+      return NULL;
+   }
 
    return b;
+#endif
 }
 
 
@@ -1978,6 +1975,7 @@ void XMesaDestroyBuffer( XMesaBuffer b )
 
    if (b->gc)  XMesaFreeGC( b->xm_visual->display, b->gc );
    if (b->cleargc)  XMesaFreeGC( b->xm_visual->display, b->cleargc );
+   if (b->swapgc)  XMesaFreeGC( b->xm_visual->display, b->swapgc );
 
    if (b->backimage) {
 #if defined(USE_XSHM) && !defined(XFree86Server)
@@ -2004,9 +2002,6 @@ void XMesaDestroyBuffer( XMesaBuffer b )
       XMesaDestroyImage( b->rowimage );
    }
 
-   if (b->xm_context)
-       b->xm_context->xm_buffer = NULL;
-
    free_xmesa_buffer(client, b);
 }
 
@@ -2035,36 +2030,24 @@ GLboolean XMesaMakeCurrent2( XMesaContext c, XMesaBuffer drawBuffer,
       if (drawBuffer->FXctx) {
          fxMesaMakeCurrent(drawBuffer->FXctx);
 
-         /* Disassociate old buffer from this context */
-         if (c->xm_buffer)
-            c->xm_buffer->xm_context = NULL;
-
-         /* Associate the context with this buffer */
-         drawBuffer->xm_context = c;
-
-         c->xm_buffer = drawBuffer;
+         c->xm_draw_buffer = drawBuffer;
          c->xm_read_buffer = readBuffer;
-         c->use_read_buffer = (drawBuffer != readBuffer);
+         c->xm_buffer = drawBuffer;
 
          return GL_TRUE;
       }
 #endif
       if (c->gl_ctx == _mesa_get_current_context()
-          && c->xm_buffer == drawBuffer
+          && c->xm_draw_buffer == drawBuffer
           && c->xm_read_buffer == readBuffer
-          && c->xm_buffer->wasCurrent) {
+          && c->xm_draw_buffer->wasCurrent) {
          /* same context and buffer, do nothing */
          return GL_TRUE;
       }
 
-      /* Disassociate old buffer with this context */
-      if (c->xm_buffer)
-         c->xm_buffer->xm_context = NULL;
-      drawBuffer->xm_context = c; /* Associate the context with this buffer */
-
-      c->xm_buffer = drawBuffer;
+      c->xm_draw_buffer = drawBuffer;
       c->xm_read_buffer = readBuffer;
-      c->use_read_buffer = (drawBuffer != readBuffer);
+      c->xm_buffer = drawBuffer;
 
       _mesa_make_current2(c->gl_ctx,
                           &drawBuffer->mesa_buffer,
@@ -2088,11 +2071,11 @@ GLboolean XMesaMakeCurrent2( XMesaContext c, XMesaBuffer drawBuffer,
                                                c->clearcolor[2],
                                                c->clearcolor[3],
                                                c->xm_visual->undithered_pf);
-         XMesaSetForeground(c->display, c->xm_buffer->cleargc, c->clearpixel);
+         XMesaSetForeground(c->display, c->xm_draw_buffer->cleargc, c->clearpixel);
       }
 
       /* Solution to Stephane Rehel's problem with glXReleaseBuffersMESA(): */
-      c->xm_buffer->wasCurrent = GL_TRUE;
+      c->xm_draw_buffer->wasCurrent = GL_TRUE;
    }
    else {
       /* Detach */
@@ -2130,7 +2113,7 @@ XMesaBuffer XMesaGetCurrentBuffer( void )
    GET_CURRENT_CONTEXT(ctx);
    if (ctx) {
       XMesaContext xmesa = (XMesaContext) ctx->DriverCtx;
-      return xmesa->xm_buffer;
+      return xmesa->xm_draw_buffer;
    }
    else {
       return 0;
@@ -2144,7 +2127,7 @@ XMesaBuffer XMesaGetCurrentReadBuffer( void )
    GET_CURRENT_CONTEXT(ctx);
    if (ctx) {
       XMesaContext xmesa = (XMesaContext) ctx->DriverCtx;
-      return xmesa->xm_buffer;
+      return xmesa->xm_read_buffer;
    }
    else {
       return 0;
@@ -2156,7 +2139,7 @@ GLboolean XMesaForceCurrent(XMesaContext c)
 {
    if (c) {
       if (c->gl_ctx != _mesa_get_current_context()) {
-        _mesa_make_current(c->gl_ctx, &c->xm_buffer->mesa_buffer);
+        _mesa_make_current(c->gl_ctx, &c->xm_draw_buffer->mesa_buffer);
       }
    }
    else {
@@ -2180,7 +2163,7 @@ GLboolean XMesaLoseCurrent(XMesaContext c)
 GLboolean XMesaSetFXmode( GLint mode )
 {
 #ifdef FX
-   const char *fx = getenv("MESA_GLX_FX");
+   const char *fx = _mesa_getenv("MESA_GLX_FX");
    if (fx && fx[0] != 'd') {
       GET_CURRENT_CONTEXT(ctx);
       GrHwConfiguration hw;
@@ -2195,15 +2178,15 @@ GLboolean XMesaSetFXmode( GLint mode )
       if (ctx) {
          XMesaContext xmesa = (XMesaContext) ctx->DriverCtx;
          if (mode == XMESA_FX_WINDOW) {
-           if (xmesa->xm_buffer->FXisHackUsable) {
+           if (xmesa->xm_draw_buffer->FXisHackUsable) {
               FX_grSstControl(GR_CONTROL_DEACTIVATE);
-              xmesa->xm_buffer->FXwindowHack = GL_TRUE;
+              xmesa->xm_draw_buffer->FXwindowHack = GL_TRUE;
               return GL_TRUE;
            }
         }
         else if (mode == XMESA_FX_FULLSCREEN) {
            FX_grSstControl(GR_CONTROL_ACTIVATE);
-           xmesa->xm_buffer->FXwindowHack = GL_FALSE;
+           xmesa->xm_draw_buffer->FXwindowHack = GL_FALSE;
            return GL_TRUE;
         }
         else {
@@ -2226,14 +2209,13 @@ GLboolean XMesaSetFXmode( GLint mode )
  */
 static void FXgetImage( XMesaBuffer b )
 {
+   GET_CURRENT_CONTEXT(ctx);
    static unsigned short pixbuf[MAX_WIDTH];
    GLuint x, y;
    int xpos, ypos;
    XMesaWindow root;
    unsigned int bw, depth, width, height;
-   XMesaContext xmesa = (XMesaContext) b->xm_context->gl_ctx->DriverCtx;
-
-   assert(xmesa->xm_buffer->FXctx);
+   XMesaContext xmesa = (XMesaContext) ctx->DriverCtx;
 
 #ifdef XFree86Server
    x = b->frontbuffer->x;
@@ -2242,37 +2224,37 @@ static void FXgetImage( XMesaBuffer b )
    height = b->frontbuffer->height;
    depth = b->frontbuffer->depth;
 #else
-   XGetGeometry( xmesa->xm_visual->display, b->frontbuffer,
+   XGetGeometry( b->xm_visual->display, b->frontbuffer,
                  &root, &xpos, &ypos, &width, &height, &bw, &depth);
 #endif
    if (b->width != width || b->height != height) {
-      b->width = MIN2((int)width, xmesa->xm_buffer->FXctx->width);
-      b->height = MIN2((int)height, xmesa->xm_buffer->FXctx->height);
+      b->width = MIN2((int)width, b->FXctx->width);
+      b->height = MIN2((int)height, b->FXctx->height);
       if (b->width & 1)
          b->width--;  /* prevent odd width */
       xmesa_alloc_back_buffer( b );
    }
 
    grLfbWriteColorFormat(GR_COLORFORMAT_ARGB);
-   if (xmesa->xm_visual->undithered_pf==PF_5R6G5B) {
+   if (b->xm_visual->undithered_pf==PF_5R6G5B) {
       /* Special case: 16bpp RGB */
       grLfbReadRegion( GR_BUFFER_FRONTBUFFER,       /* src buffer */
-                       0, xmesa->xm_buffer->FXctx->height - b->height,  /*pos*/
+                       0, b->FXctx->height - b->height,  /*pos*/
                        b->width, b->height,         /* size */
                        b->width * sizeof(GLushort), /* stride */
                        b->backimage->data);         /* dest buffer */
    }
-   else if (xmesa->xm_visual->dithered_pf==PF_DITHER
-           && GET_VISUAL_DEPTH(xmesa->xm_visual)==8) {
+   else if (b->xm_visual->dithered_pf==PF_DITHER
+           && GET_VISUAL_DEPTH(b->xm_visual)==8) {
       /* Special case: 8bpp RGB */
       for (y=0;y<b->height;y++) {
-         GLubyte *ptr = (GLubyte*) xmesa->xm_buffer->backimage->data
-                        + xmesa->xm_buffer->backimage->bytes_per_line * y;
+         GLubyte *ptr = (GLubyte*) b->backimage->data
+                        + b->backimage->bytes_per_line * y;
          XDITHER_SETUP(y);
 
          /* read row from 3Dfx frame buffer */
          grLfbReadRegion( GR_BUFFER_FRONTBUFFER,
-                          0, xmesa->xm_buffer->FXctx->height-(b->height-y),
+                          0, b->FXctx->height-(b->height-y),
                           b->width, 1,
                           0,
                           pixbuf );
@@ -2291,7 +2273,7 @@ static void FXgetImage( XMesaBuffer b )
       for (y=0;y<b->height;y++) {
          /* read row from 3Dfx frame buffer */
          grLfbReadRegion( GR_BUFFER_FRONTBUFFER,
-                          0, xmesa->xm_buffer->FXctx->height-(b->height-y),
+                          0, b->FXctx->height-(b->height-y),
                           b->width, 1,
                           0,
                           pixbuf );
@@ -2303,7 +2285,8 @@ static void FXgetImage( XMesaBuffer b )
                                               (pixbuf[x] & 0xf800) >> 8,
                                               (pixbuf[x] & 0x07e0) >> 3,
                                               (pixbuf[x] & 0x001f) << 3,
-                                              0xff, xmesa->pixelformat));
+                                              0xff,
+                                               b->xm_visual->undithered_pf));
          }
       }
    }
@@ -2323,8 +2306,8 @@ void XMesaSwapBuffers( XMesaBuffer b )
    /* If we're swapping the buffer associated with the current context
     * we have to flush any pending rendering commands first.
     */
-   if (b->xm_context && b->xm_context->gl_ctx == ctx)
-      _mesa_swapbuffers(ctx);
+   if (ctx && ctx->DrawBuffer == &(b->mesa_buffer))
+      _mesa_notifySwapBuffers(ctx);
 
    if (b->db_state) {
 #ifdef FX
@@ -2343,7 +2326,7 @@ void XMesaSwapBuffers( XMesaBuffer b )
         if (b->shm) {
             /*_glthread_LOCK_MUTEX(_xmesa_lock);*/
            XShmPutImage( b->xm_visual->display, b->frontbuffer,
-                         b->cleargc,
+                         b->swapgc,
                          b->backimage, 0, 0,
                          0, 0, b->width, b->height, False );
             /*_glthread_UNLOCK_MUTEX(_xmesa_lock);*/
@@ -2351,16 +2334,12 @@ void XMesaSwapBuffers( XMesaBuffer b )
         else
 #endif
          {
-#if defined(GLX_DIRECT_RENDERING) && !defined(XFree86Server)
-           XMesaDriSwapBuffers( b );
-#else
             /*_glthread_LOCK_MUTEX(_xmesa_lock);*/
             XMesaPutImage( b->xm_visual->display, b->frontbuffer,
-                          b->cleargc,
+                          b->swapgc,
                           b->backimage, 0, 0,
                           0, 0, b->width, b->height );
             /*_glthread_UNLOCK_MUTEX(_xmesa_lock);*/
-#endif
          }
       }
       else {
@@ -2369,14 +2348,14 @@ void XMesaSwapBuffers( XMesaBuffer b )
         XMesaCopyArea( b->xm_visual->display,
                        b->backpixmap,   /* source drawable */
                        b->frontbuffer,  /* dest. drawable */
-                       b->cleargc,
+                       b->swapgc,
                        0, 0, b->width, b->height,  /* source region */
                        0, 0                 /* dest region */
                      );
          /*_glthread_UNLOCK_MUTEX(_xmesa_lock);*/
       }
    }
-#if !defined(GLX_DIRECT_RENDERING) && !defined(XFree86Server)
+#if !defined(XFree86Server)
    XSync( b->xm_visual->display, False );
 #endif
 }
@@ -2393,8 +2372,8 @@ void XMesaCopySubBuffer( XMesaBuffer b, int x, int y, int width, int height )
    /* If we're swapping the buffer associated with the current context
     * we have to flush any pending rendering commands first.
     */
-   if (b->xm_context->gl_ctx == ctx)
-      _mesa_swapbuffers(ctx);
+   if (ctx && ctx->DrawBuffer == &(b->mesa_buffer))
+      _mesa_notifySwapBuffers(ctx);
 
    if (b->db_state) {
       int yTop = b->height - y - height;
@@ -2413,7 +2392,7 @@ void XMesaCopySubBuffer( XMesaBuffer b, int x, int y, int width, int height )
          if (b->shm) {
             /* XXX assuming width and height aren't too large! */
             XShmPutImage( b->xm_visual->display, b->frontbuffer,
-                          b->cleargc,
+                          b->swapgc,
                           b->backimage, x, yTop,
                           x, yTop, width, height, False );
             /* wait for finished event??? */
@@ -2423,7 +2402,7 @@ void XMesaCopySubBuffer( XMesaBuffer b, int x, int y, int width, int height )
          {
             /* XXX assuming width and height aren't too large! */
             XMesaPutImage( b->xm_visual->display, b->frontbuffer,
-                          b->cleargc,
+                          b->swapgc,
                           b->backimage, x, yTop,
                           x, yTop, width, height );
          }
@@ -2433,7 +2412,7 @@ void XMesaCopySubBuffer( XMesaBuffer b, int x, int y, int width, int height )
          XMesaCopyArea( b->xm_visual->display,
                        b->backpixmap,           /* source drawable */
                        b->frontbuffer,          /* dest. drawable */
-                       b->cleargc,
+                       b->swapgc,
                        x, yTop, width, height,  /* source region */
                        x, yTop                  /* dest region */
                       );
@@ -2513,7 +2492,7 @@ const char *XMesaGetString( XMesaContext c, int name )
 {
    (void) c;
    if (name==XMESA_VERSION) {
-      return "3.1";
+      return "5.0";
    }
    else if (name==XMESA_EXTENSIONS) {
       return "";
@@ -2547,7 +2526,7 @@ void XMesaGarbageCollect( void )
    XMesaBuffer b, next;
    for (b=XMesaBufferList; b; b=next) {
       next = b->Next;
-      if (!b->pixmap_flag) {
+      if (b->display && b->frontbuffer && b->type == WINDOW) {
 #ifdef XFree86Server
         /* NOT_NEEDED */
 #else
@@ -2627,3 +2606,13 @@ unsigned long XMesaDitherColor( XMesaContext xmesa, GLint x, GLint y,
 }
 
 
+/*
+ * This is typically called when the window size changes and we need
+ * to reallocate the buffer's back/depth/stencil/accum buffers.
+ */
+void XMesaResizeBuffers( XMesaBuffer b )
+{
+   xmesa_resize_buffers( &(b->mesa_buffer) );
+
+}
+