OpenGL multi-threaded cpu drainage

Hi there.
I have a Rendering thread and a Loader thread.
They share lists

wglShareLists(this->renderingContext, renderingContext2);

Rendering thread loops

while(this->isRunning){
this->draw();
SwapBuffers(window1->getDeviceContext()); //blocking for verticalSync
}

Loader thread loops

while(this->isRunning){
look for jobs
do jobs
delete jobs
Sleep(10000);
}

when loader thread is deactivated the game uses 1% according to windows taskmanager

when loader thread is activated the game uses 60%

this isnt so much of a problem but id like to optimize and im curious of why this is happening.

Is there a similar cpu usage with a simple loader thread like this one :

while(this->isRunning){
Sleep(10000);
}

yes

What gfx HW? (NVIDIA?)

“Sleep(10000);”

That’s one whale of a snooze! (Wake me when it’s over. ;-))

@Brolingstanz: depends on the unit, what about microseconds ?

lol… or light years?

C’mon, a light year is a (big) unit of distance, not time :smiley:

Seriously, what Sleep() is that ? Time units, implementation details ? Does varying the value change the cpu usage, still on the while-isrunning-sleep loop ? (ie. doing 1000, 100 , 10, 100000 …)

Just the standard windows library Sleep(dword miliseconds) anyone else tried this on their computers?

And yes NVidia Geforce 9600M GT TurboCache

try this:

Open NVIDIA Control Panel (RMB on desktop or in Control Panels) Select „Manage 3D settings“, tab „Global Settings“, scroll
down the list and select line „Threaded optimization“, choose Off

nope no diffrence
i did try this while i was in there:
i turned off vertical sync and added a Sleep(1000/60) in the rendering thread. cpu usage went down to 2%

Do use glFinish() and or glFLush() ?
glFinish on nvidia used busywait last I checked, which means 100%cpu usage.

woohoo glFinish() combined with a Sleep(1000/70) did the trick cpu usage drop to 18% while maintaining 60 in fps thanks.

glFlush(); didnt do anything.

woohoo put glFinish on my loader-thread aswell cpu-usage droped to 6% really nice thanks man

In software engineering, busy waiting or spinning is a technique in which a process repeatedly checks to see if a condition is true, (aka cpu waster)

seems to have also fixed another bug where gl display lists wouldnt be compiled or called correctly, although im not sure.

Your workaround is nice, but it is not a solution.
It works because your scene is simple for your GPU.
When you add more complexity the render time grows.
Then the Sleep value will be too high and fps will drop.

On the other hand there is no real solution until NV improves the driver.

yeah already noticed that :stuck_out_tongue: but i think i can fix it if i do some fps calcs on the sleeptime

Dont count on that… Sleep(N) in windows doesn’t mean it will sleep N miliseconds. Depending on hardware, drivers and application timer cofiguration, Sleep(N) works different.
Sleep(1) can sleep 15-16ms, Sleep(16) can sleep 30-32ms…

Im satisfied with my answer thanks all.

That loader loop is odd. Why are you spinning when you know there’s no work todo? Try implementing a loop like this:

while (true)
{
    nextJob = getNextJob(); //may block waiting for the next job
    do(nextJob);
}

Regards
elFarto

was going to switch the sleep for a yield later on

i thought up a better way to do the loading.

if i only start the loaderThread when theres work to do and delete the thread when there is no work to do the OpenGL wouldn’t have make the costfull switching between the threads. That way for most of the time only the renderingThread would be running.

So I tried this but it didnt work. Once the loaderThread has been started it can also be stopped, but OpenGL doesn’t seem to recognise this even though there’s is no longer any thread for it to contextswitch too, cpu usage 50% average, ill have to guess i’m missing some kind of OpenGL deloading code.

So my questions is what is the code? I’ve tested some that didnt work.

Note as before I also tried to never start the loaderThread and let the renderingThread handle all the rendering, cpu usage 6% average.


LoaderThreadStart(){
    this->thread = new Thread(this);
}

LoaderThreadStop(){
    delete this->thread;
}

LoaderThreadRun(){
    if(!wglMakeCurrent( this->window1->getDeviceContext(), this->renderingContext)){
        throw "Loader: run: wglMakeCurrent failed
";
    }
    
    this->doJobs();
    
    //jobs are done so this thread can return

    //glFinish(); //tested no effect
    //wglMakeCurrent(0,0); //tested no effect
    //wglDeleteContext(this->renderingContext); //tested no effect
}