Hi Bruno,
On Sun, 11 Apr 2010, Bruno Haible wrote:
> > pid = create_pipe_bidi ("m4", m4, (char **)(void*)argv, false, true,
> > true, filter_fd);
> > I thought that create_pipe_bidi is supposed to make sure
> > that the m4 subprocess is killed when Bison invokes exit
>
> No, there's no feature in Unix or in create_pipe_bidi that does such a
> cleanup.
> You need to do this cleanup yourself. For example, through an atexit
> call that registers a function that does
>
> pid_t pid = pid_of_running_child_process;
> if (pid != (pid_t)(-1))
> kill (pid, SIGTERM);
In the create_pipe_bidi invocation above, I set the slave_process argument
to true. create_pipe_bidi passes that argument to create_pipe, which then
invokes register_slave_subprocess, which uses atexit to register a
function that invokes kill.
Moreover the documentation in pipe.h, which contains create_pipe_bidi,
says:
If slave_process is true, the child process will be terminated when
its creator receives a catchable fatal signal or exits normally. If
slave_process is false, the child process will continue running in
this case, until it is lucky enough to attempt to communicate with
its creator and thus get a SIGPIPE signal.
> The tricky thing here is to make sure that you don't accidentally kill
> an unrelated process that got assigned the same PID after your child
> process exited.
When the child process exits, it becomes a zombie so that the parent can
safely reap it, so I didn't think the pid could possibly be reused before
the parent exits.
> > I might try the simple fix of draining the m4 output pipe before invoking
> > exit
>
> What would be the point of letting 'm4' consume CPU time once you know that
> you want to throw away its input anyway? Instead, I would just kill it.
Right, but I figured that killing it wasn't working properly on the
reported platform.