[SOLVED]wglMakeCurrent() failed in Win32 MultiWindow OpenGL

AliAkdurak

17-02-2011 12:24:39

Hello

We have simple simulation program where there is a main thread and a Render Thread. From our main thread we send message to ever-running render thread to start loading graphic engine make multiple render windows (Per display + One more) then create cameras create scene start rendering loop with render thread and so on. first time it runs it runs perfectly well.

Then we shutdown all the render windows with this code from the render thread.

void ClassMogrePanel_FormClosing(object sender, System.Windows.Forms.FormClosingEventArgs e)
{
try
{
_RWindowMCD.RemoveAllViewports();
_ViewportMCD.Dispose();
_ViewportMCD = null;
Mogre.Root.Singleton.DetachRenderTarget(_RWindowMCD);
}
catch (System.Runtime.InteropServices.SEHException ex)
{
if (Mogre.OgreException.IsThrown)
{
//TODO Multi language yapılacak
System.Windows.Forms.MessageBox.Show(Mogre.OgreException.LastException.FullDescription, "An Ogre exception has occured!", System.Windows.Forms.MessageBoxButtons.OK, System.Windows.Forms.MessageBoxIcon.Error);
}
else
{
System.Windows.Forms.MessageBox.Show(ex.ToString(), "An error has occured");
}
}
}


And clean our scene like this.


private void ShutdownAndCloseSingleThreaded()
{

this.QueueEndRendering();
MissionRuntime.SceneController.EffectController.RemoveEffects();
//Render queue ile yaptım fakat mogre kapanasaya kadar render queue erişim gecikiyor o yüzden direkt çağırdım
//RCommandRemoveEffects RemoveEffect = new RCommandRemoveEffects(this.SceneController.EffectController);
//_RuntimeGUILink.BroadCastCommand(RemoveEffect);

RCommandCloseControlForms CloseControlFormsCommand = new RCommandCloseControlForms();
MissionRuntime.RuntimeGUILink.BroadCastCommand(CloseControlFormsCommand);

RCommandCloseShootingForms CloseGraphicFormsCommand = new RCommandCloseShootingForms();
MissionRuntime.RuntimeGUILink.BroadCastCommand(CloseGraphicFormsCommand);

MissionRuntime.TargetController.ShutdownRegisteredTargets();


Mogre.SceneManagerEnumerator.SceneManagerIterator ISM = Mogre.Root.Singleton.GetSceneManagerIterator();

while (ISM.MoveNext())
{
ISM.Current.ClearScene();
ISM.Current.DestroyAllCameras();
ISM.Current.DestroyAllMovableObjects();
Mogre.Root.Singleton.DestroySceneManager(ISM.Current);
}

_SceneManager = null;

_CompletedSystemStates = _CompletedSystemStates | RenderSystemState.RenderSystemShutdown;
}


So my problem is that after this when we start a new mission CreateRenderWindow function throws a wglMakeCurrent() failed message. I can't deduct why this could happen does anybody have any idea.

Note: This is my post at the Ogre Forums I am posting it here as it seems nobody stumbled upon or new anything why this could happen ?.

My application is a multi render window multi display application where render windows keep getting destroyed and created.

AliAkdurak

17-02-2011 13:36:59

Recently I started use a memory profiler just to solve this problem and I noticed something strange. It seems that somewhere along the line GCHandle.Alloc is called to pin the render windows which makes them unmovable or indestructible in the memory. Does anybody know what may cause this situation

AliAkdurak

17-02-2011 15:55:10

Ok I solved the problem by the help of an excellent memory profiler tool I will not right its name as I do not know if this will be perceived as advertisement or not.

Anyway for anyone who might encounter same problem my problem was this: Our renderwindows which are integrated into win forms as panels were handled by the forms closing events. By my mis-knowledge I thought that I should detach them from the system at the form closing and destroy them after I stopped rendering loop. But once a renderwindow is detached from the render system you cannot retrieve it by a Render Target Iterator which is completely logical as you just did detached it from the render system!. A point I totally missed in our huge code base. So there is no problem closing a window which has an embedded renderwindow while rendering. Just do not forget to clean the renderwindows later on.

Edit: wglMakecurrent was thrown by the previously should-be-destroyed render windows where I mis-interpreted this exception was thrown from the newly created window.