生活随笔
收集整理的這篇文章主要介紹了
父子进程共享文件
小編覺得挺不錯的,現在分享給大家,幫大家做個參考.
父子進程共享文件
1、父進程和子進程可以共享打開的文件描述符。
2、父子進程共享文件描述符的條件:在fork之前打開文件。
3、對于兩個完全不相關的進程,文件描述符不能共享。
4、父子進程文件描述符是共享的,但是關閉的時候可以分別關閉,也可以同時在公有代碼中關閉。
Fork函數創建子進程后,子進程將復制父進程的數據段、BSS段、代碼段、堆空間、棧空間和文件描述符,而對文件描述符關聯的內核文件表項(struct file結構),則采用共享的方式。
父進程和子進程可以共享打開的文件描述符
#include
<stdio
.h
>
#include
<fcntl
.h
>
#include
<unistd
.h
>
#include
<wait
.h
>
#include
<stdlib
.h
>
#include
<string
.h
>
#include
<sys
/types
.h
>
#include
<sys
/stat
.h
>
int
main(int argc
,char
*argv
[])
{int fd
,fd2
=-1;int i
;pid_t pid
,pid_wait
=-1;int status
;char
*buf
="hello linux";char
BUF[128]={0};if((fd
=open("myfile",O_RDWR | O_TRUNC ))==-1){perror("open");exit(EXIT_FAILURE);}if((pid
=fork())==-1){perror("fork");exit(EXIT_SUCCESS);}if(pid
==0){if(write(fd
,buf
,strlen(buf
))==-1){perror("write");exit(EXIT_FAILURE);}exit(EXIT_SUCCESS);}else {pid_wait
=wait(&status
);if((i
=WIFEXITED(status
))){printf("child pid %d %d, normal exit,return value :%d\n",pid
,pid_wait
,i
);}lseek(fd
,-strlen(buf
),SEEK_CUR);if(read(fd
,BUF,128)==-1){perror("read");exit(EXIT_FAILURE);}printf("%s\n",BUF);close(fd
);exit(0);}
}
運行結果
如果將上述代碼稍微改動一下 將打開文件位于fork之后,并且不使用lseek對文件讀寫指針重新定位
#include
<stdio
.h
>
#include
<fcntl
.h
>
#include
<unistd
.h
>
#include
<wait
.h
>
#include
<stdlib
.h
>
#include
<string
.h
>
#include
<sys
/types
.h
>
#include
<sys
/stat
.h
>
int
main(int argc
,char
*argv
[])
{int fd
,fd2
=-1;int i
;pid_t pid
,pid_wait
=-1;int status
;char
*buf
="hello linux";char
BUF[128]={0};if((pid
=fork())==-1){perror("fork");exit(EXIT_SUCCESS);}if((fd
=open("myfile",O_RDWR | O_TRUNC ))==-1){perror("open");exit(EXIT_FAILURE);}if(pid
==0){if(write(fd
,buf
,strlen(buf
))==-1){perror("write");exit(EXIT_FAILURE);}exit(EXIT_SUCCESS);}else {pid_wait
=wait(&status
);if((i
=WIFEXITED(status
))){printf("child pid %d %d, normal exit,return value :%d\n",pid
,pid_wait
,i
);}if(read(fd
,BUF,128)==-1){perror("read");exit(EXIT_FAILURE);}printf("%s\n",BUF);close(fd
);exit(0);}
}
運行結果
依舊會讀取出文件中的內容
原因分析:子進程的執行位置為fork返回處此時子進程打開”myfile”文件然后對其進行寫入數據操作,當子進程執行完畢,父進程由fork處返回,獲取子進程的PID,然后父進程又一次打開了”myfile”文件,那么父子進程對文件表的操作便是這樣
如果在子進程中打開文件,父子進程是否會共享文件呢?
由于fork 創建的子進程相當于父進程的一個副本,所以在子進程中打開一個文件并不會影響到父進程,而vfork與父進程共享內存那么在使用vfork創建的子進程中打開文件,父子進程能夠文件共享嗎
錯誤原因:一個錯誤的文件描述符
子進程打開文件返回一個文件描述符 使得fd=3,由于父子進程共享內存,父進程在使用這個文件描述符時,由于父進程中這個文件描述符并沒有打開任何文件,所以出現錯誤
文件描述符,文件表,inode節點表
第一種情況,一個進程中多次打開同一個文件,實現文件共享
第二種情況 兩個進程打開同一個文件,實現文件共享
第三種情況,使用dup復制文件描述符,實現文件共享
同時這種方式也是實現重定向編程的方法,在這里寫一個簡單的程序,將輸出內容寫入到文件中去
#include
<stdio
.h
>
#include
<fcntl
.h
>
#include
<unistd
.h
>
int
main(int argc
,char
*argv
[])
{int fd1
,fd2
=-1;fd1
=open(argv
[1],O_RDWR | O_CREAT,0777);if(fd1
==-1){perror("open");return -1;}close(1);fd2
=dup(fd1
);printf("fd2=%d\n",fd2
);printf("---------------\n");close(fd1
);return 0;
}
運行結果
第四種,父子進程共享文件
總結
以上是生活随笔為你收集整理的父子进程共享文件的全部內容,希望文章能夠幫你解決所遇到的問題。
如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。