我正在做一些實驗來了解命名管道。這是我的理解,操作系統將阻止寫入命名管道的程序,直到另一個程序從命名管道讀取。所以我寫了兩個程序,startloop
和readbyte
。 startloop
創建一個FIFO,並不斷寫入它與客戶的每個讀取(readbyte
):運行時爲什麼在沒有人閱讀之後繼續寫入命名管道?
#include <stdio.h>
#include <stdlib.h>
#include <fcntl.h>
#include <unistd.h>
#include <sys/stat.h>
int main(int argc, char *argv[]) {
const char num = 123;
mkfifo("fifo", S_IRUSR | S_IWUSR | S_IRGRP | S_IWGRP);
int fd = open("fifo", O_WRONLY | O_CREAT | O_TRUNC, S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH);
while (1) {
printf("loop_start\n");
write(fd, &num, sizeof(num));
}
close(fd);
return 0;
}
readbyte
從FIFO中讀取一個字節:
#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#include <fcntl.h>
int main(int argc, char *argv[]) {
char num;
int fd;
if ((fd = open(argv[1], O_RDONLY, S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH)) == -1) {
perror("Cannot open input file\n"); exit(1);
}
read(fd, &num, sizeof(num));
printf("%d\n", num);
close(fd);
return 0;
}
readbyte
打印數量按預期時在「先進先出」運行:
hostname:dir username$ ./readbyte fifo
65
如我所料,loopstart
直到我讀不打印任何東西從與fifo readbyte
。但是,當它變爲暢通時,它會多次寫入「fifo」,而不是立即暫停。爲什麼是這樣?
hostname:dir username$ ./startloop
loop_start
loop_start
loop_start
loop_start
loop_start
loop_start
loop_start
loop_start
loop_start
loop_start
loop_start
loop_start
loop_start
loop_start
loop_start
loop_start
loop_start
loop_start
loop_start
loop_start
你怎麼知道'write()'調用成功?你沒有檢查它的返回值。 –
@Andrew Henle - 我知道它至少能以某種方式成功,因爲'readbyte'能夠打印出寫入的內容。我確實有一個錯誤檢查的版本 - 儘管如此,我刪除了所有這些使帖子更短的文章。如果您認爲這是問題,我可以將其添加回來。 – watkipet
您的循環繼續的事實意味着'write()'不*阻止*,不是*成功*。有很大的差異。如果您不知道發生了什麼並希望獲得幫助,則發佈的數據越多,獲得的幫助就越好。在這種情況下,發出一個循環計數器以及來自'write()'的返回值會比簡單的「loop_start」好很多。這是一個容易解決的問題 - 解決更難的問題將需要額外的信息。 –