From: Kristian S. <kri...@fr...> - 2003-04-30 01:40:05
|
In case attachments are not accepted I resend again. Hi I discovered a problem when rendering to more than one GLXContext on a system with a Matrox Millennium G400 graphics card. The problem is illustrated by the attached program. It may be compiled with g++ main.C -lGL The problem that I see, is that only one of the two windows gets updated correctly. The other window looks as if nothing was rendered to it at all. The same program works correctly on a system with NVIDIA GeForce 2 MX (generic). So, I wonder if this is actually a bug in my code which by coincidence has no effect on GeForce 2, or if this is an error in a Matrox driver or in DRI or somthing like that. In the attached code I use only one thread for rendering. If I chnage that so it spawns two new threads for rendering to the two contexts, then it continues to work correctly on GeForce 2 but has even worse symptoms on Matrox G400. In this case it crashes XFree in random ways. The system with the Matrox G400 card is an SMP system with two 500 MHz GenuineIntel Pentium III (Katmai) processors and a default full RedHat8 distribution on it. The system with the GeForce 2 card is a SP system with one Intel(R) Pentium(R) 4 CPU 1.80GHz processor and a default full RedHat8 distribution on it and the NVIDIA drivers installed. Hope that one of you can figure out if the error is in my code or somewhere else. If the bug is in my code, I would like to know what it is. If the bug is in some system library, I would like to know if there is a known work-around. Thanks in advance. -Kristian- main.C: #include <GL/glx.h> #include <GL/gl.h> #include <iostream> using namespace std; void init() { glMatrixMode(GL_PROJECTION); glLoadIdentity(); double r = 0.2*tan(M_PI/8); glFrustum(-r, r, -r, r, 0.2, 200); glMatrixMode(GL_MODELVIEW); } void render() { glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); glBegin(GL_QUADS); glColor3f(1, 1, 1); glVertex3f(-1, 1, -4); glVertex3f(-1, -1, -4); glVertex3f( 1, -1, -4); glVertex3f( 1, 1, -4); glColor3f(1, 0, 1); glVertex3f(-1, 1, -8); glVertex3f(-1, -1, -8); glVertex3f( 1, -1, -8); glVertex3f( 1, 1, -8); glEnd(); } static int attributeList[] = { GLX_RGBA, GLX_DOUBLEBUFFER, GLX_RED_SIZE, 1, GLX_GREEN_SIZE, 1, GLX_BLUE_SIZE, 1, None }; static Bool WaitForNotify(Display *d, XEvent *e, char *arg) { return (e->type == MapNotify) && (e->xmap.window == (Window)arg); } int main(int argc, char **argv) { Display *dpy; XVisualInfo *vi; Colormap cmap1; Colormap cmap2; XSetWindowAttributes swa1; XSetWindowAttributes swa2; Window win1; Window win2; GLXContext cx1; GLXContext cx2; XEvent event; dpy = XOpenDisplay(0); vi = glXChooseVisual(dpy, DefaultScreen(dpy), attributeList); if(vi == 0) { cerr << "Visual not available\n"; exit(1); } cx1 = glXCreateContext(dpy, vi, 0, GL_TRUE); cmap1 = XCreateColormap(dpy, RootWindow(dpy, vi->screen), vi->visual, AllocNone); swa1.colormap = cmap1; swa1.border_pixel = 0; swa1.event_mask = StructureNotifyMask; win1 = XCreateWindow(dpy, RootWindow(dpy, vi->screen), 0, 0, 500, 500, 0, vi->depth, InputOutput, vi->visual, CWBorderPixel|CWColormap|CWEventMask, &swa1); XMapWindow(dpy, win1); XIfEvent(dpy, &event, WaitForNotify, (char*)win1); cx2 = glXCreateContext(dpy, vi, 0, GL_TRUE); cmap2 = XCreateColormap(dpy, RootWindow(dpy, vi->screen), vi->visual, AllocNone); swa2.colormap = cmap2; swa2.border_pixel = 0; swa2.event_mask = StructureNotifyMask; win2 = XCreateWindow(dpy, RootWindow(dpy, vi->screen), 0, 0, 500, 500, 0, vi->depth, InputOutput, vi->visual, CWBorderPixel|CWColormap|CWEventMask, &swa2); XMapWindow(dpy, win2); XIfEvent(dpy, &event, WaitForNotify, (char*)win2); glXMakeCurrent(dpy, win1, cx1); init(); glXMakeCurrent(dpy, None, 0); glXMakeCurrent(dpy, win2, cx2); init(); glXMakeCurrent(dpy, None, 0); for(;;) { glXMakeCurrent(dpy, win1, cx1); render(); glXMakeCurrent(dpy, None, 0); glXMakeCurrent(dpy, win2, cx2); render(); glXMakeCurrent(dpy, None, 0); glXSwapBuffers(dpy, win1); glXSwapBuffers(dpy, win2); } return 0; } |