Unix Programming - Communicate siginfo_t of SIGCHLD to parent

This is Interesting: Free IT Magazines  
Home > Archive > Unix Programming > January 2004 > Communicate siginfo_t of SIGCHLD to parent





You are viewing an archived Text-only version of the thread. To view this thread in it's original format and/or if you want to reply to this thread please [click here]

Author Communicate siginfo_t of SIGCHLD to parent
Michael B Allen

2004-01-23, 5:36 pm

I have a fork server that creates worker processes. When a worker exits
I would like to lookup the worker context object and save information
about it's exit status, information from siginfo_t, etc. I've never felt
comfortable about signals. What is the correct way to do this without
creating the possability of concurrency issues? The linkedlist code is
reentant. I want to do something like the following:

struct linkedlist *workers;

void
sig_action(int s, siginfo_t *si, void *ctx)
{
if (s == SIGCLHD) {
ucontext_t *uc = ctx; /* what is this? */
iter_t iter;
struct worker *worker;

linkedlist_iterate(workers, &iter);
while ((worker = linkedlist_next(workers, &iter))) {
if (worker->pid == si->si_pid) { /* is si_pid the child pid? */
waitpid(worker->pid, &worker->status, WNOHANG);
worker->si_code = si->si_code;
break;
}
}
}
}
Valentin Nechayev

2004-01-23, 5:36 pm

>>> Michael B Allen wrote:

MBA> I have a fork server that creates worker processes. When a worker exits
MBA> I would like to lookup the worker context object and save information
MBA> about it's exit status, information from siginfo_t, etc. I've never felt
MBA> comfortable about signals. What is the correct way to do this without
MBA> creating the possability of concurrency issues? The linkedlist code is
MBA> reentant. I want to do something like the following:

MBA> struct linkedlist *workers;

Your code seems to be working, but, if there are too many child processes,
cycle around waitpid() and hashed lookups will be more efficient.

OTOH, any async-signal-unsafe function in asynchronous signal handler
is danger. It's safer to set flag in this function and check it in
main cycle. If main cycle is event-driven, you can also write something
to signal pipe.


-netch-
Michael B Allen

2004-01-23, 5:36 pm

On Sat, 17 Jan 2004 08:29:09 -0500, Valentin Nechayev wrote:
quote:

>
> OTOH, any async-signal-unsafe function in asynchronous signal handler is
> danger. It's safer to set flag in this function and check it in main
> cycle. If main cycle is event-driven, you can also write something to
> signal pipe.



Ok, so I write the pid of the process that exited to a pipe and then
read that in the main loop, call wait and collect the information? Mmm,
that sounds reasonable.

Mike
James Antill

2004-01-23, 5:36 pm

On Sun, 18 Jan 2004 00:44:32 -0500, Michael B Allen wrote:
quote:

> On Sat, 17 Jan 2004 08:29:09 -0500, Valentin Nechayev wrote:
>
> Ok, so I write the pid of the process that exited to a pipe and then read
> that in the main loop, call wait and collect the information? Mmm, that
> sounds reasonable.



No, don't do that as you'll have big problems if you get a lot of signals
at once (Ie. the pipe will become full and block -- which will be a
deadlock). There are also nasty problems lurking with PIPE_BUF and
pid separation.

The way it's "commonly" done is to write a single byte down the pipe
(non-blocking). Then when the select comes back, you just call...

int status = 0;
while ((pid = waitpid(-1, &status, WNOHANG)) > 0)
{ /* pid is now the pid of a proc. */

}

....and lookup the process from the pid. For more selection you can use
process groups etc. ... see man waitpid.

--
James Antill -- james@and.org
Need an efficient and powerful string library for C?
http://www.and.org/vstr/

Michael B Allen

2004-01-23, 5:36 pm

On Sun, 18 Jan 2004 03:11:34 -0500, James Antill wrote:
quote:

>
> No, don't do that as you'll have big problems if you get a lot of
> signals
> at once (Ie. the pipe will become full and block -- which will be a
> deadlock). There are also nasty problems lurking with PIPE_BUF and pid
> separation.
>
> The way it's "commonly" done is to write a single byte down the pipe
> (non-blocking). Then when the select comes back, you just call...
>
> int status = 0;
> while ((pid = waitpid(-1, &status, WNOHANG)) > 0) { /* pid is now the
> pid of a proc. */
>
> }
>
> ...and lookup the process from the pid. For more selection you can use
> process groups etc. ... see man waitpid.



Good points. Now we're talkn'. So even if the pipe buffer overflows I
don't care because I can call waitpid repeatedly and be certain that I
will get all worker's exit status.

Although, this still doesn't let me get the siginfo_t

Mike
Sponsored Links






Free braindumps | Software forum | Database administration forum

Copyright 2003 - 2008 webservertalk.com