Hello again.
Regarding my post 'Problem with GRX program termination on windows XP?' there is definetly a problem in how GRX terminates on XP when terminating GRX prg using the 'X' button on GRX window of the running app.
Here's what happens...
In 'src/setup/setdrvr.c:GrSetDriver' atexit is used to call void _GrCloseVideoDriver(void) (which then calls DRVINFO->vdriver->reset func) on program exit.
There are 2 possible ways that user can terminate GRX prg: 1. normal termination (prg reaches end of GRXMain) 2. let's call it abnormal termination (using 'X' button on GRX prg window)
The main problem is that 'reset' can be called from main thread or from WndThread depending on the situation. In situation 2, ExitProcess() is called from WndThread and 'reset' executes in WndThread context, WM_QUIT is never handled, GetMessage() loop is never exited and WndThread is waiting in 'reset' for itself to set 'isWindowThreadRunning' to 0 which never happens.
Here's the patch (this time I left ExitProcess :) and a little bigger info of what's goint is attached below. I say again, this happens on win XP, I did not debug under win2k to see why this situation never happens.
Best regards, Mario
Here's the patch: --- begin patch-grx-2.4.6-vd_win32-ExitProcess --- --- grx246/src/vdrivers/vd_win32.c 2003-04-14 21:49:54.000000000 +0200 +++ grx246.fix/src/vdrivers/vd_win32.c 2005-02-15 15:41:48.000000000 +0100 @@ -520,7 +520,10 @@ return 0; DestroyWindow(hWnd); if (!isMainWaitingTermination) + { + isWindowThreadRunning = 0; ExitProcess(1); + } break;
case WM_DESTROY: --- end patch-grx-2.4.6-vd_win32-ExitProcess ---
Here's what happens in a little bit more detail:
*** Situation 1. - main thread exits, atexit calls _GrCloseVideoDriver, calls DRVINFO->vdriver->reset - main thread 'reset' does: isMainWaitingTermination = 1; PostMessage(hGRXWnd, WM_CLOSE, 0, 0); while (isWindowThreadRunning == 1) Sleep(1); (waits for WndThread to finish) * WndThread handles WM_CLOSE which calls WM_DESTROY which posts WM_QUIT, no ExitProcess(1) is called because isMainWaitingTermination != 0 !!! * WndThread gets WM_QUIT and breaks while(GetMessage(...)), sets isWindowThreadRunning to 0, and terminates with ExitThread(0)
- main thread 'reset' breaks from while (isWindowThreadRunning == 1) Sleep(1); finishes cleanup and terminates == PROGRAM TERMINATE OK ==
*** Situation 2. * isMainWaitingTermination is 0 !!! * X button on GRX window is pressed so WndThread handles WM_CLOSE msg, raises dialog question: "This will abort the program\nare you sure?" * if yes is clicked, inside WM_CLOSE DestroyWindow is called, so WM_DESTROY is handled inside WM_CLOSE -- WM_DESTROY posts WM_QUIT msg but continues to finish handling WM_CLOSE * if (!isMainWaitingTermination) ExitProcess(1) is called, * atexit calls 'reset' inside WndThread * reset executes: while (isWindowThreadRunning == 1) Sleep(1); * WM_QUIT msg is never handled !!! WndThread never exits GetMessage(...) loop and never sets isWindowThreadRunning to 0 --- WndThread is waiting for itself to set isWindowsThreadRunning to 0, but it never does, so 'reset' never finishes and proces will never terminate == PROGRAM TERMINATE NOT OK ==