これはちょっと長いです...私はLinux 2.6.33、gcc 4.4.4です。O_ASYNCの生成が停止するSIGIO
名前付きパイプを作成し、それを読み取って特定の文字列を見ると、FIFOを取り除き、それ自体を再実行する小さなプログラムを作成しました。コンパイルされ、バックグラウンドで実行すると
#include<unistd.h>
#include<fcntl.h>
#include<signal.h>
#include<sys/types.h>
#include<sys/stat.h>
int fifo;
#define put(x) write(1, x, (sizeof x)-1)
void reader(int a)
{
char buf[26];
int n;
while((n=read(fifo, buf, 25))>0){
buf[25] = '\0';
if(!strncmp(buf, "moo", 3)){
put("exec()-ing\n");
close(fifo);
unlink("lefifo");
execl("/home/dave/a.out", "a.out", 0);
}
write(1, buf, n);
}
}
main()
{
signal(SIGIO, reader);
mknod("lefifo", 0600|S_IFIFO,0);
fifo = open("lefifo", O_RDONLY|O_NONBLOCK);
fcntl(fifo, F_SETOWN, getpid());
fcntl(fifo, F_SETFL, O_ASYNC);
for(;;)
pause();
}
は、私がlefifo
にエコーすることができ、私は「MOO」で始まる文字列を入力するまでは、期待通りに動作します。次の例セッション:FIFOを作る支障がない、
execve("./a.out", ["./a.out"], [/* 36 vars */]) = 0
mknod("lefifo", S_IFIFO|0600) = 0
open("lefifo", O_RDONLY|O_NONBLOCK) = 3
getpid() = 3945
fcntl(3, F_SETOWN, 3945) = 0
fcntl(3, F_SETFL, O_RDONLY|O_ASYNC) = 0
pause() = ? ERESTARTNOHAND (To be restarted)
--- SIGIO (I/O possible) @ 0 (0) ---
read(3, "klar\n"..., 25) = 5
write(1, "klar\n"..., 5) = 5
read(3, ""..., 25) = 0
sigreturn() = ? (mask now [])
pause() = ? ERESTARTNOHAND (To be restarted)
--- SIGIO (I/O possible) @ 0 (0) ---
read(3, "moo\n"..., 25) = 4
write(1, "exec()-ing\n"..., 13) = 13
close(3) = 0
unlink("lefifo") = 0
execve("/home/dave/a.out", ["a.out"], [/* 36 vars */]) = 0
mknod("lefifo", S_IFIFO|0600) = 0
open("lefifo", O_RDONLY|O_NONBLOCK) = 3
getpid() = 3945
fcntl(3, F_SETOWN, 3945) = 0
fcntl(3, F_SETFL, O_RDONLY|O_ASYNC) = 0
pause() = ? ERESTARTNOHAND (To be restarted)
--- SIGTERM (Terminated) @ 0 (0) ---
は、あなたが見ることができるように、最初の頃、およびSIGIOが生成されます。
$ gcc fifo.c
$ ./a.out&
$ echo klar > lefifo
klar
$ echo moo > lefifo
exec()-ing
$ echo klar2 > lefifo
$ echo where did you go > lefifo
$ echo moo > lefifo
$ pkill a.out
は、このトレースを(いくつかの脂肪をトリミング)を生成しますうまくいく。 exec()
の後に新しいFIFOは信号を生成しません。古いものは正常終了を示し、正常に削除されたようです。
なぜこのように振舞うのか、私は非常に困惑しています。何か案は?
一般に、 'sigaction'の使用を検討する必要があります。より複雑なAPIですが、これらのセマンティクスのすべてが明確に定義されており、ドキュメンテーションで話をしています。 – Omnifarious