Re: I disabled more compiler warnings..

From: Linus Torvalds
Date: Mon May 11 2020 - 15:34:22 EST


On Mon, May 11, 2020 at 10:59 AM Paul Smith <psmith@xxxxxxx> wrote:
>
> As with all single-threaded applications, though, the problem is the
> difficulty (in a portable way) of handling both signals and wait*(2)
> reliably...

I do wonder if GNU make isn't making it worse for itself by blocking SIGCHLD.

I wonder if you could just have three different file descriptors:

- the "current token file descriptor"

- a /dev/null file descriptor

- the jobserver pipe file descriptor. This is left blocking.

and then make the rule be that

- the SIGCHLD handler just does

dup2(nullfd, jobserverfd);

This guarantees that any read() that was interrupted by a SIGCHLD
will now reliably return immediately. But it also guarantees that if
we raced, and the SIGCHLD happened just *before* we did the read(),
the read() will also exit immediately.

- the waiting code does

check_child_status();
for (;;) {
ret = read(jobserverfd, buffer, 1);
if (ret == 1) {
.. we got the token successfully, do whatever ..
return;
}
/* The read might fail because of SIGCHLD - either we got
interrupted, or the fd was replaced with /dev/null */
/* First, re-instate the pipe binding */
dup2(pipefd, jobserverfd);
/* Then do the child status stuff again */
check_child_status();
/* Ok, we can restart, there's no races with SIGCHLD */
}

which fundamentally doesn't have any races. Look, ma, no need for
nonblocking reads, or pselect().

I don't know. Maybe I missed something.

Linus