wxProcess

From WxWiki
Jump to: navigation, search
Official Classes SmallBlocks.png Archive Containers Controls Data Structures Database Date & Time Debug Device Contexts Dialogs Document & Views Drag & Drop Events Filesystem Frames Graphics Grid Cell Help HTML Logging Miscellaneous Networking Printing Sizers Streams Threading Windows

The objects of this class are used in conjunction with the wxExecute() function.

When a wxProcess object is passed to wxExecute(), its OnTerminate() virtual method is called when the process terminates. This allows the program to be (asynchronously) notified about the process termination and also retrieve its exit status which is unavailable from wxExecute() in the case of asynchronous execution.

Note: If the wxEVT_END_PROCESS event sent after termination is processed by the parent, then it is responsible for deleting the wxProcess object which sent it. However, if it is not processed, the object will delete itself and so the library users should only delete those objects whose notifications have been processed (and call wxProcess::Detach for others). This also means that unless you're going to process the wxEVT_END_PROCESS event, you must allocate the wxProcess class on the heap.

wxProcess also supports IO redirection of the child process. For this, you have to call its Redirect() method before passing it to wxExecute(). If the child process was launched successfully, GetInputStream(), GetOutputStream() and GetErrorStream() can then be used to retrieve the streams corresponding to the child process standard output, input and error output respectively.

Issues

SIGTERM signal on wxMSW only works on windowed applications

As of wx2.3.3, if you call wxKill() function or the equivalent wxProcess::Kill() function on MSW with a wxSIGTERM function, it will only do anything if the process you are trying to kill has a window. If it is a commandline-only, then you need to kill it with wxSIGKILL for it to have any effect at all. This still holds in 2.6.0, however, wxSIGNONE appears to function.

Never-ending input streams during piped input

If you are looking at adapting the /samples/exec to your project, you will see that it catches both stderr and stdout streams from the process. For your own application, if you want the dialog to refresh every so often while the redirected output is displayed, only use the stream that you expect to be generating some output. Otherwise the Eof() of the stream with no input will cause a holdup until the process is terminated, and you won't get a refresh until the end.

BCC asserts on wxProcess::Exists()

wxProcess::Exists(int pid) asserts on Borland C++ 5.5. But shouldn't be using this in a dialog anyways, since you should be keeping track of whether your own process is still running. Otherwise another program could start a process with that id and thus the process id would end up existing and it would be killed.

Threading

wxProcess/wxExecute are NOT thread safe. In wx2.6.0, the unix/msw ports (others unknown?) will still only allow wxExecute from the main thread (see src/msw/utilsexc.cpp:540 (rcs rev 1.79) and src/unix/utilsunx:251 (rcs rev 1.123)). This is only when WXDEBUG has been set. *DO NOT* ignore this or comment it out: under Unix (GNU/Linux2.4 specifically but this is probably mostly the case) a fork (wxExecute is, as expected, a well-protected invocation of fork/exec) will inherit the entire memory space of the parent, including locking bodies (mutexes etc). Forking and attempting to manipulate thread operations of the parent process will result in unknown behaviour - at best a segmentation fault (this could be nontrivially solved with clever use of pthread_atfork). This is also reported to be a "problem" in earlier versions of wx (2.4.x).

Console

Unix ports (wx2.6.0) will allow asynchronous (wxEXEC_ASYNC) wxExecute functions to fork but will fail with an ASSERT while (or rather, before) waiting for the child pid leaving the child active while the parent traps. This only occurs in console mode WXDEBUG when wxApp has not been properly invoked. See src/unix/baseunix.cpp:73 (rcs rev 1.12).

See Also