Linux学习笔记-管道的读写特性
生活随笔
收集整理的這篇文章主要介紹了
Linux学习笔记-管道的读写特性
小編覺得挺不錯的,現在分享給大家,幫大家做個參考.
目錄
?
理論
栗子
理論
管道的讀寫特性
1.通過打開兩個管道來創建一個雙向的管道;
2.管道默認是阻塞性的,當進程從管道中讀取數據,若沒有數據進程會阻塞;
3.當一個進程往管道中不斷地寫入數據但是沒有進程去讀取數據,此時只要管道沒有滿是可以寫的,但若管道放滿數據的則會報錯;
?
下面舉兩個例子!
不完整管道:
1.當讀一個寫端已被關閉的管道時,在所有數據被讀取后,read返回0,易表示到達了文件尾部;
2.如果寫一個讀端已被關閉的管道,則產生信號SIGPIPE,如果忽略該信號或捕捉該信號并從處理程序的返回,而write返回-1,同時erno設置為EPIPE;
?
栗子
例子一:當讀一個寫端已被關閉的管道時,在所有數據被讀取后,read返回0,易表示到達了文件尾部;
程序運行截圖如下:
源碼如下:
#include <unistd.h> #include <stdlib.h> #include <stdio.h> #include <string.h>/** 不完整管道:* 讀取一個寫端已經關閉的管道*/int main(void){int fd[2];if(pipe(fd) < 0){perror("pipe error");exit(1);}pid_t pid;if((pid = fork()) < 0){perror("fork error");exit(1);}else if(pid > 0){ //parent process//父進程不完整(寫端關閉)中讀取數據sleep(5);close(fd[1]);while(1){char c;if(read(fd[0], &c, 1) == 0){printf("\n write-end of pipe closed\n");break;}else{printf("%c", c);}}close(fd[0]);wait(0);}else{ //child process//子進程負責將數據寫入管道close(fd[0]);char *s = "12345";write(fd[1], s, sizeof(s));//寫入數據后關閉管道的寫端close(fd[1]);}exit(0); }例子二:如果寫一個讀端已被關閉的管道,則產生信號SIGPIPE,如果忽略該信號或捕捉該信號并從處理程序的返回,而write返回-1,同時erno設置為EPIPE;
程序運行截圖如下:
源碼如下:
#include <unistd.h> #include <stdlib.h> #include <stdio.h> #include <signal.h> #include <string.h> #include <errno.h>/** 不完整管道:寫一個讀端已經被關閉的管道*/void sig_handler(int signo){if(signo == SIGPIPE){printf("SIGPIPE occured\n");} }int main(void){int fd[2];if(pipe(fd) < 0){perror("pipe error");exit(1);} pid_t pid;if((pid == fork()) < 0){perror("fork error");exit(1);}else if(pid > 0){ //parent process//父進程負責將數據寫到不完整的管道(讀端關閉)中sleep(5);close(fd[0]);if(signal(SIGPIPE, sig_handler) == SIG_ERR){perror("signal sigpipe error");exit(1);}char *s = "1234";if(write(fd[1], s, sizeof(s)) != sizeof(s)){fprintf(stderr, "%s, %s\n", strerror(errno), (errno == EPIPE) ? "EPIPE" : ",unknow");}close(fd[1]);wait(0);}else{ //child processclose(fd[0]); //子進程關閉管道讀端close(fd[1]); }exit(0); }?
總結
以上是生活随笔為你收集整理的Linux学习笔记-管道的读写特性的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: Linux学习笔记-增量编译(Makef
- 下一篇: Linux学习笔记-对父子进程直接通信基