diff options
author | Julian Elischer <julian@FreeBSD.org> | 1996-08-20 08:22:01 +0000 |
---|---|---|
committer | Julian Elischer <julian@FreeBSD.org> | 1996-08-20 08:22:01 +0000 |
commit | 0f7d684755aefbcfd70b45d24efc2d39bc505c4c (patch) | |
tree | b14348030d1048f8628b798374a8a061a990aae3 /lib/libpthread/thread/thr_sig.c | |
parent | 1bbb22c82e47dbc805e523be5e2fe3d4436761e0 (diff) |
Notes
Diffstat (limited to 'lib/libpthread/thread/thr_sig.c')
-rw-r--r-- | lib/libpthread/thread/thr_sig.c | 49 |
1 files changed, 44 insertions, 5 deletions
diff --git a/lib/libpthread/thread/thr_sig.c b/lib/libpthread/thread/thr_sig.c index 77ec713b63d98..c3ec1919077e9 100644 --- a/lib/libpthread/thread/thr_sig.c +++ b/lib/libpthread/thread/thr_sig.c @@ -31,6 +31,8 @@ * */ #include <signal.h> +#include <fcntl.h> +#include <unistd.h> #include <errno.h> #ifdef _THREAD_SAFE #include <pthread.h> @@ -40,6 +42,7 @@ void _thread_sig_handler(int sig, int code, struct sigcontext * scp) { char c; + int i; pthread_t pthread; /* @@ -67,16 +70,52 @@ _thread_sig_handler(int sig, int code, struct sigcontext * scp) } else { /* Handle depending on signal type: */ switch (sig) { - /* Interval timer used for timeslicing: */ + /* Interval timer used for timeslicing: */ case SIGVTALRM: /* * Don't add the signal to any thread. Just want to - * call + * call the scheduler: */ - /* the scheduler: */ break; - /* Signals specific to the running thread: */ + /* Child termination: */ + case SIGCHLD: + /* + * Enter a loop to process each thread in the linked + * list: + */ + for (pthread = _thread_link_list; pthread != NULL; + pthread = pthread->nxt) { + /* + * Add the signal to the set of pending + * signals: + */ + pthread->sigpend[sig] += 1; + if (pthread->state == PS_WAIT_WAIT) { + /* Reset the error: */ + /* There should be another flag so that this is not required! ### */ + _thread_seterrno(pthread, 0); + + /* Change the state of the thread to run: */ + pthread->state = PS_RUNNING; + } + } + + /* + * Go through the file list and set all files + * to non-blocking again in case the child + * set some of them to block. Sigh. + */ + for (i = 0; i < _thread_dtablesize; i++) { + /* Check if this file is used: */ + if (_thread_fd_table[i] != NULL) { + /* Set the file descriptor to non-blocking: */ + _thread_sys_fcntl(i, F_SETFL, _thread_fd_table[i]->flags | O_NONBLOCK); + } + } + break; + + /* Signals specific to the running thread: */ case SIGBUS: case SIGEMT: case SIGFPE: @@ -88,7 +127,7 @@ _thread_sig_handler(int sig, int code, struct sigcontext * scp) _thread_run->sigpend[sig] += 1; break; - /* Signals to send to all threads: */ + /* Signals to send to all threads: */ default: /* * Enter a loop to process each thread in the linked |