Despite the complications, you can fork a child that continues running and even continues to use Pthreads. You must use fork handlers carefully to protect your mutexes and the shared data that the mutexes are protecting. Fork handlers are described in Section 6.1.1.
Because thread-specific data destructors and cleanup handlers are not called, you may need to worry about memory leaks. One possible solution would be to cancel threads created by your subsystem in the
POSIX specifies a small set of functions that may be called safely from within signal-catching functions ("async-signal safe" functions), and fork is one ofthem. However, none of the POSIX threads functions is async-signal safe (and there are good reasons for this, because being async-signal safe generally makes a function substantially more expensive). With the introduction offork handlers, however, a call to fork is also a call to some set of fork handlers.
The purpose of a fork handler is to allow threaded code to protect synchronization state and data invariants across a fork, and in most cases that requires locking mutexes. But you cannot lock mutexes from a signal-catching function. So while it is legal to call fork from within a signal-catching function, doing so may fbeyond the control or knowledge of the caller) require performing other operations that cannot be performed within a signal-catching function.
This is an inconsistency in the POSIX standard that will need to be fixed. Nobody yet knows what the eventual solution will be. My advice is to avoid using fork in a signal-catching function.
6.1.1 Fork handlers
int pthread_atfork (void (*prepare)(void),
void (*parent)(void), void (*child)(void));
Pthreads added the pthread_atfork "fork handler" mechanism to allow your code to protect data invariants across fork. This is somewhat analogous to atexit, which allows a program to perform cleanup when a process terminates. With pthread_atfork you supply three separate handler addresses. The
|If you write a subsystem that uses mutexes and does not establish fork handlers,then that subsystem will not function correctly in a child process after a fork.
Normally a
The
Your fork handlers are only as good as everyone else's fork handlers.
The system will run all
If you use an ANSI C library that doesn't supply fork handlers to prepare those mutexes properly for a fork, for example, then, sometimes, you may find that
your child process hangs when it calls printf, because another thread in the parent process had the mutex locked when your thread called fork. There's often nothing you can do about this type of problem except to file a problem report against the system. These mutexes are usually private to the library, and aren't visible to your code — you can't lock them in your