Issue with 3D acceleration in OpenGL Multithreaded sample

Discussions about using Linux guests in VirtualBox.
Post Reply
theeta
Posts: 3
Joined: 6. Feb 2014, 10:45

Issue with 3D acceleration in OpenGL Multithreaded sample

Post by theeta »

I am facing a weird problem with an OpenGL sample on vbox with 3D acceleration enabled

Guest: Ubuntu 12.04
Host: Windows 7, nvidia Graphics
vbox version 4.3.6 with guest additions installed

This application runs properly on vbox when 3D acceleration is disabled and I have checked this on stand alone Linux PC as well. When the same is run with 3D acceleration enabled, its not able to get the GL function pointers and its giving errors - function is no-op

The App is Simple, Main thread creates 2 threads.

Main Thread - Create Thread 1, Create Thread 2
Thread 1 - Create a X-Window for Rendering
Thread 2 - Create Render thread (Draw OpenGL quad on the X-Window).

Here is the code for the sample app.

Code: Select all

#include<stdio.h>
#include<stdlib.h>
#include<X11/X.h>
#include<X11/Xlib.h>
#include<GL/gl.h>
#include<GL/glx.h>
//#include<GL/glu.h>
#include <dlfcn.h> /*dlopen*/
#include <pthread.h>
#include <unistd.h> /*sleep*/

Display                 *dpy;
Display                 *dpy2;
Window                  root;
GLint                   att[] = { GLX_RGBA, GLX_DEPTH_SIZE, 24, GLX_DOUBLEBUFFER, None };
XVisualInfo             *vi;
XVisualInfo             *vi2;
Colormap                cmap;
XSetWindowAttributes    swa;
Window                  win;
GLXContext              glc;
XWindowAttributes       gwa;
XEvent                  xev;
bool            render;


void DrawAQuad() 
{
    glClearColor(1.0, 1.0, 1.0, 1.0);
    glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);

    glMatrixMode(GL_PROJECTION);
    glLoadIdentity();
    glOrtho(-1., 1., -1., 1., 1., 20.);

    glMatrixMode(GL_MODELVIEW);
    glLoadIdentity();
    //gluLookAt(0., 0., 10., 0., 0., 0., 0., 1., 0.);
    glTranslatef(0.0, 0.0, -10.0);

    glBegin(GL_QUADS);
     glColor3f(1., 0., 0.); glVertex3f(-.75, -.75, 0.);
     glColor3f(0., 1., 0.); glVertex3f( .75, -.75, 0.);
     glColor3f(0., 0., 1.); glVertex3f( .75,  .75, 0.);
     glColor3f(1., 1., 0.); glVertex3f(-.75,  .75, 0.);
    glEnd();
}

void *CreateMainWindow(void* threadID)
{
    dpy = XOpenDisplay(NULL);
    if(dpy == NULL) 
    {
        printf("\n\tWindow Thread: cannot connect to X server\n\n");
        exit(0);
    }

    root = DefaultRootWindow(dpy);
    printf("\n *** CreateWindow: xopendisplay over *** \n");

    vi = (XVisualInfo*)glXChooseVisual(dpy, 0, att);
    if(vi == NULL) 
    {
        printf("\n\tWindow Thread: no appropriate visual found\n\n");
        exit(0);
    } 
    else 
    {
        printf("\n\tWindow Thread: visual %p selected\n", (void *)vi->visualid);
    }

    cmap = XCreateColormap(dpy, root, vi->visual, AllocNone);
    swa.colormap = cmap;
    swa.event_mask = ExposureMask | KeyPressMask;

    win = XCreateWindow(dpy, root, 0, 0, 600, 600, 0, vi->depth, InputOutput, vi->visual, CWColormap | CWEventMask, &swa);
    XMapWindow(dpy, win);
    XStoreName(dpy, win, "VERY SIMPLE APPLICATION");

    while(1) 
    {
        XNextEvent(dpy, &xev);
        printf("\nXEVENT\n");
        if(xev.type == Expose)
        {
            render = true;
        }
        else if(xev.type == KeyPress)
        {
            XDestroyWindow(dpy, win);
            XCloseDisplay(dpy);
            render = false;
            break;
            //exit(0);
        }
    }
}

void *RenderThread(void* threadID)
{
    vi2 = (XVisualInfo*)glXChooseVisual(dpy2, 0, att);
    printf("\n\tRenderThread : visual %p selected\n", (void *)vi2->visualid);

    glc = (GLXContext)glXCreateContext(dpy2, vi2, NULL, GL_TRUE);
    glXMakeCurrent(dpy2, win, glc);

    glEnable(GL_DEPTH_TEST); 

    while(render) 
    {
        //XGetWindowAttributes(dpy, win, &gwa);
        glViewport(0, 0, 600, 600);
        DrawAQuad(); 
        glXSwapBuffers(dpy2, win);
    } /* this closes while(render) */

    glXMakeCurrent(dpy2, None, NULL);
    glXDestroyContext(dpy2, glc);
    XCloseDisplay(dpy2);
}

int main(int argc, char *argv[]) 
{
    render = true;
    pthread_t thread1;
    pthread_t thread2;
    char *temp1;
    char *temp2;

    //For Async issue
    if(!XInitThreads())
    {
        fprintf(stderr, "XInitThread failed\n");
        return 0;
    }

    //Create Main Window
    int err = pthread_create(&thread1, NULL, CreateMainWindow, (void*)temp1);
    if (err != 0)
        printf("\n ERROR::can't create thread1 :[%d]", err);
    else
        printf("\n Thread1 created successfully\n");

    sleep(1); // Wait for thread 1 to complete

    dpy2 = XOpenDisplay(NULL);
    if(dpy2 == NULL) 
    {
        printf("\n\tMain : cannot connect to X server\n\n");
        exit(0);
    }

    //Create Render Thread
    err = pthread_create(&thread2, NULL, RenderThread, (void*)temp2);
    if (err != 0)
        printf("\n ERROR::can't create thread2 :[%d]", err);
    else
        printf("\n Thread2 created successfully\n");

    pthread_join( thread1, NULL);
    pthread_join( thread2, NULL);

} /* this is the } which closes int main(int argc, char *argv[]) { */
and to compile the code -

Code: Select all

g++ -o quad quad.cpp -lGL -lX11 -lXmu -lXi -lpthread -lm

Help me understand where the issue lies
Thanks.
mpack
Site Moderator
Posts: 39134
Joined: 4. Sep 2008, 17:09
Primary OS: MS Windows 10
VBox Version: VirtualBox+Oracle ExtPack
Guest OSses: Mostly XP

Re: Issue with 3D acceleration in OpenGL Multithreaded sampl

Post by mpack »

If 3D acceleration is enabled then your host handles all the 3D stuff. If acceleration is disabled then your guest does it in software. So, perhaps your host OpenGL library doesn't support the function you're calling. Have you checked for a host graphics driver update?
theeta
Posts: 3
Joined: 6. Feb 2014, 10:45

Re: Issue with 3D acceleration in OpenGL Multithreaded sampl

Post by theeta »

mpack wrote:If 3D acceleration is enabled then your host handles all the 3D stuff. If acceleration is disabled then your guest does it in software. So, perhaps your host OpenGL library doesn't support the function you're calling. Have you checked for a host graphics driver update?
That doesn't seem to be the problem, glxgears runs ok with 3D acceleration enabled
infact the sample which I shared runs with 3D acceleration enabled, when it is modified to single thread.
mpack
Site Moderator
Posts: 39134
Joined: 4. Sep 2008, 17:09
Primary OS: MS Windows 10
VBox Version: VirtualBox+Oracle ExtPack
Guest OSses: Mostly XP

Re: Issue with 3D acceleration in OpenGL Multithreaded sampl

Post by mpack »

Sorry, I don't use multithread 3D libraries in a VM, so I can't comment on that. If glxgears can run multithreaded inside the guest (otherwise I would have to ask why you mentioned it) then that would appear to exonerate VirtualBox.
theeta
Posts: 3
Joined: 6. Feb 2014, 10:45

Re: Issue with 3D acceleration in OpenGL Multithreaded sampl

Post by theeta »

mpack wrote:Sorry, I don't use multithread 3D libraries in a VM, so I can't comment on that. If glxgears can run multithreaded inside the guest (otherwise I would have to ask why you mentioned it) then that would appear to exonerate VirtualBox.
glxgears is not multithreaded, just mentioned it to say that the host graphics drivers are proper and are upto date. 3D acceleration is working for glxgears, but not for the sample.
Post Reply