ctdb-common: Avoid race between fd and signal events
authorAmitay Isaacs <amitay@samba.org>
Tue, 9 Apr 2019 04:44:04 +0000 (14:44 +1000)
committerAmitay Isaacs <amitay@samba.org>
Fri, 12 Apr 2019 08:19:29 +0000 (08:19 +0000)
BUG: https://bugzilla.samba.org/show_bug.cgi?id=13895

In run_proc, there was an implicit assumption that when a process exits,
fd event (pipe between parent and child) would be processed first and
signal event (SIGCHLD for the child) would be processed later.

However, that is not the case.  SIGCHLD can be received asynchronously
any time even when the pipe data has not fully been read.  This causes
run_proc to miss some of the output from child process in tests.

When SIGCHLD is being processed, if the pipe between parent and child is
still open, then do an explict read from the pipe to ensure we read any
data still in the pipe before closing the pipe.

Signed-off-by: Amitay Isaacs <amitay@gmail.com>
Reviewed-by: Martin Schwenke <martin@meltin.net>
Autobuild-User(master): Amitay Isaacs <amitay@samba.org>
Autobuild-Date(master): Fri Apr 12 08:19:29 UTC 2019 on sn-devel-144

ctdb/common/run_proc.c

index 97895b383b9485aa5358df88c14dfaed51f9827c..037b6d9651de358035a6dbc04494e99549420f7e 100644 (file)
@@ -295,6 +295,13 @@ again:
                proc->result.sig = WTERMSIG(status);
        }
 
+       /* Confirm that all data has been read from the pipe */
+       if (proc->fd != -1) {
+               proc_read_handler(ev, proc->fde, 0, proc);
+               TALLOC_FREE(proc->fde);
+               proc->fd = -1;
+       }
+
        /* Active run_proc request */
        if (proc->req != NULL) {
                run_proc_done(proc->req);