共有ファイルマッピングは MAP_SHARED を使ったファイルマッピングです。
ファイルマッピングは複数のプロセスで共有されるため、他のプロセスはマッピングしたリソースに対しての変更を見ることができます。
main.c.
1 #include <stdio.h>
2 #include <stdlib.h>
3 #include <string.h>
4 #include <sys/mman.h>
5 #include <sys/stat.h>
6 #include <sys/types.h>
7 #include <unistd.h>
8 #include <fcntl.h>
9
10 #define BUF_SIZE 8
11
12 int main()
13 {
14 int fd,i;
15 struct stat sb;
16 char buf[BUF_SIZE];
17 char *mm;
18
19 memset(buf,0,BUF_SIZE);
20
21 fd = open("abc.txt",O_CREAT|O_RDWR|O_TRUNC,0644);
22 if(fd < 0) {
23 perror("ファイルを開けません");
24 exit(1);
25 }
26 write(fd,buf,BUF_SIZE);
27 if(fstat(fd,&sb) == -1) {
28 perror("stat");
29 exit(1);
30 }
31
32 mm = mmap(NULL,sb.st_size,PROT_WRITE|PROT_READ,MAP_SHARED,fd,0);
33 if(mm == MAP_FAILED){
34 perror("mmap");
35 exit(1);
36 }
37
38 pid_t id = fork();
39
40 if(id == 0) {
41 for(i = 0; i < sb.st_size-2; i++)
42 mm[i] = 'a'+i;
43 mm[sb.st_size-2] = '\n';
44 mm[sb.st_size-1] = '\0';
45
46 } else {
47 for(i = 0; i < sb.st_size-2; i++)
48 mm[i] = 'a';
49 mm[sb.st_size-2] = '\n';
50 mm[sb.st_size-1] = '\0';
51 }
52
53 msync(mm,sb.st_size,MS_SYNC);
54 for(i = 0; i < 10; i++)
55 printf("mm[%d] => %c\n",i,mm[i]);
56
57 if(munmap(mm,sb.st_size) == -1) {
58 perror("munmap");
59 exit(1);
60 }
61 close(fd);
62
63 return 0;
64 }
ビルドと実行結果.
$ gcc main.c $ ./a.out mm[0] => a mm[1] => b mm[2] => c mm[3] => d mm[4] => e mm[5] => f mm[6] => mm[7] => mm[8] => mm[0] => a mm[9] => mm[1] => b mm[2] => c mm[3] => d mm[4] => e mm[5] => f mm[6] => mm[7] => mm[8] => mm[9] =>
実行結果を見て分かるとおり、親プロセスと子プロセスは同じ値になっていますね。
この場合は子プロセスの書き込みが後に来ているようなので、子プロセスの配列結果が共有されてます。
msync() は単にファイルに書き込みするだけなので、この場合は書き込み順序に影響は与えないと思います。
ソースを解析したりデバッグすれば、順序の解析もできるかもしれませんが、そこまでの気力が筆者に無いです。
(´・ω・`)
Copyright 2018-2019, by Masaki Komatsu