Namey
Namey

Reputation: 1212

C Program Handing Control to TCL/Tk GUI - How to run code on closing app?

I have a problem that I can't seem to find the answer to, but I'm willing to bet it's probably a pretty simple one for anybody who has worked with this sort of application setup before.

I'm working with an application that is written in C, but calls a TCL/TK gui to do lots of nice pretty stuff on the screen. However, due to the way that TCL/TK works when run from C, once you've handed over control- you never get it back (i.e. the TCL/TK interpreter handles the application exit, rather than returning to the original main() function).

So basically, there is some code like this:

int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpszCmdLine, int  nCmdShow){  
    Tk_Main(1,argv,Tcl_AppInit);  // Tcl_AppInit is a function that runs at the start
    // All code after this point will never, ever run  
    return 0;                     // This return never actually occurs  
}

This causes a slight issue. I want to be able to destroy data structures, close files, check for memory leaks, and do other necessary things before the program exits. However, I can't do it after Tk_Main. I have to figure out the hook in the TCL/TK interpreter that runs when it shuts down, then tell that to run my teardown function before quitting.

Anybody know how or where to do this?

Upvotes: 0

Views: 964

Answers (2)

schlenk
schlenk

Reputation: 7237

There are in fact a few ways to do it:

  1. Do not use Tk_Main(), instead write your own version for embedding that does not call Tcl_Exit() when done. The code to start from can be found in generic/tkMain.c in the Tk source.
  2. Use Tcl_SetExitProc() to register your own exit handler that gets called instead of exit(), allowing you to return control back to your program.
  3. Use Tcl_CreateExitHandler() to register only some cleanup callbacks before the Tcl_Finalize() happens, but exit the process anyway.

Preferred way to handle your case would probably be 2. The manpage for Tcl_Exit() has all the details you should need: http://www.tcl.tk/man/tcl8.5/TclLib/Exit.htm

Upvotes: 2

mu is too short
mu is too short

Reputation: 434615

You could try using atexit(). You pass it a void (*f)(void) function to be called when the process terminates. I'm not sure how well that works under Windows though.

A more Tcl/Tk-ish approach would be to use Tcl_CreateExitHandler to register an exit handler:

Tcl_CreateExitHandler arranges for proc to be invoked by Tcl_Exit before it terminates the application. This provides a hook for cleanup operations such as flushing buffers and freeing global memory.

Upvotes: 1

Related Questions