此部分測試涉及到APUE V3中,第三章的圖3-12到圖3-14。git
經過fcntl.h提供的功能,修改fd的文件屬性,本處增長O_SYNC功能,並測試其效果。github
本文涉及代碼:ubuntu
tree ch3 ch3 ├── makefile.sync ├── mycat.c ├── set_fl.c ├── set_fl.h ├── sync.c └── test
mycat.c 代碼:函數
1 #include "../apue.h" 2 3 #define BUFFSIZE 4096 4 5 int main(void) 6 { 7 int n; 8 char buf[BUFFSIZE]; 9 // set_fl(STDOUT_FILENO, O_SYNC); for O_SYNC 10 while ((n = read(STDIN_FILENO, buf, BUFFSIZE)) > 0) 11 if (write(STDOUT_FILENO, buf, n) != n) 12 err_sys("write error"); 13 14 if (n < 0) 15 err_sys("read error"); 16 17 exit(0); 18 }
2 使用O_SYNC功能的代碼測試
set_fl.h頭文件:spa
#ifndef SET_FL #define SET_FL void set_fl(int fd, int flags); /* flags are file status flags to turn on */ void clr_fl(int fd, int flags); /* flags are file status flags to turn off */ #endif
set_fl.c代碼:code
#include <fcntl.h> #include "set_fl.h" void set_fl(int fd, int flags) /* flags are file status flags to turn on */ { int val; if ((val = fcntl(fd, F_GETFL, 0)) < 0) err_sys("fcntl F_GETFL error"); val |= flags; /* turn on flags */ if (fcntl(fd, F_SETFL, val) < 0) err_sys("fcntl F_SETFL error"); }
sync.c代碼,即前面mycat.c中,取消set_fl函數 的註釋。blog
makefile.sync文件:get
sync: sync.o set_fl.o gcc -o sync sync.o set_fl.o set_fl.o: set_fl.c gcc -c set_fl.c
準備:分別在mac及ubuntu環境下生成一個1GB的文件,並編譯文件。it
dd if=/dev/zero of=./test bs=512 count=2048000 2048000+0 records in 2048000+0 records out 1048576000 bytes (1.0 GB) copied, 11.1418 s, 94.1 MB/s make -f makefile.sync gcc mycat.c
Ubuntu14.04效果以下:
time ./a.out < test >./dup.buf real 0m9.965s user 0m0.014s sys 0m1.453s time ./sync < test >./dup.sync real 0m10.355s user 0m0.025s sys 0m1.350s
mac10.11效果:
time ./a.out < test >/dev/null ./a.out < test > /dev/null 0.10s user 1.17s system 60% cpu 2.079 total time ./sync < test >/dev/null ./sync < test > /dev/null 0.10s user 1.20s system 62% cpu 2.070 total time ./sync < test >./dup.sync ./sync < test > ./dup.sync 0.27s user 23.79s system 45% cpu 53.369 total time ./a.out < test >./dup.buf ./a.out < test > ./dup.buf 0.11s user 3.06s system 53% cpu 5.955 total
可見,每一次buf數據都直接O_SYNC到磁盤,會影響寫磁盤的效果,在mac上幾乎近10倍的差別。
而在Ubuntu上,卻沒有特別明顯的差別,如書上所述。經過fcntl對O_SYNC的控制是失效的。
#over