標準ユーティリティを使用した信号のロック解除

標準ユーティリティを使用した信号のロック解除

標準ユーティリティを使用してbashから信号をロック解除するには?

過去数週間で、Macosのシェルがハングすることがわかりました(例:yes | head終了しません)。もっと深く掘り下げて、私が作ったすべての新しいシェルがかなり多くの信号セットをブロックしていることを発見しました。 (そのため、前の例ではSIGPIPEがブロックされています。ツール作成者の注意事項などの yes戻り値を確認してくださいwrite。)printf

この動作は少し迷惑ですが、今問題がわかったので、簡単に解決できます。しかし、それは簡単ではありません。 trap目的に合わないようです(私はbashを使用しています)。標準ユーティリティを使用してブロックされた信号セットを消去するには、bashの起動に何を追加できますか?以下を追加しましたが、非常に混乱しているようです。

if { ! show-mask && which unblock; } > /dev/null 2>&1; then
        exec unblock bash
fi

show-mask と unblock は以下からビルドされます。

$ cat show-mask.c 
/* Show the current set of blocked signals */    
#include <signal.h>
#include <stdlib.h>
#include <stdio.h>

int
main(int argc, char **argv)
{
        struct sigaction act = {{0}};
        sigset_t old;

        if(sigprocmask(SIG_SETMASK, NULL, &old)) {
                perror("sigprocmask");
                return EXIT_FAILURE;
        }
        printf("mask: %x\n", old);

        return !!old;
}
$ cat unblock.c
#include <signal.h>
#include <string.h>
#include <unistd.h>
#include <stdlib.h>
#include <stdio.h>

void
set_default(struct sigaction *act, int s)
{
        if(sigaction(s, act, NULL)) {
                perror("sigaction");
                exit(EXIT_FAILURE);
        }
}

int
main(int argc, char **argv)
{
        struct sigaction act = {{0}};
        sigset_t new;

        sigemptyset(&new);

        if(sigprocmask(SIG_SETMASK, &new, NULL)) {
                perror("sigprocmask");
                return EXIT_FAILURE;
        }

        act.sa_handler = SIG_DFL;
        set_default(&act, SIGPIPE);
        set_default(&act, SIGINT);
        set_default(&act, SIGTERM);

        execvp(argv[1], argv+1);

        perror("execlp");
        return EXIT_FAILURE;
}

関連情報