在使用fork/exec在创建系统进程时,一个问题就是性能,fork会复制调用进程的大部分内容,之后才会调用exec去执行我们需要的进程文件。我好奇的一点是,究竟会有多慢呢?
于是有了下面的代码,用来测试父进程拥有不同内存大小时,fork的性能。
#include <unistd.h> #include <stdlib.h> #include <string.h> #include <sys/wait.h> int main(int argc, char *argv[]) { long c = atoi(argv[1]) * 1024 * 1024; int n = atoi(argv[2]); int i = 0; if (n) { char *ptr = malloc(c); memset(ptr, 0, c); } for (; i < n; i++) { pid_t child = fork(); if (child) { waitpid(child, NULL, 0); } else { exit(0); } } }
在使用malloc的情况下,本机的结果如下:
malloc(1MB) 3235 ms 0.161750 ms/iter malloc(100MB) 390 ms 3.900000 ms/iter malloc(500MB) 1663 ms 16.630000 ms/iter malloc(1024MB) 3329 ms 33.290000 ms/iter
调用进程在1G的情况下,执行100次,平均每次的时间长达33ms,如果系统的内存分配使用malloc,调用fork后子进程会从调用进程复制大量内容,所以这种情况下大量的fork来进程,性能会相当的被催。
将上面代码中的malloc换成mmap(MAP_ANON|MAP_SHARED),执行后结果如下:
mmap(1MB) 1204 ms 0.120400 ms/iter mmap(100MB) 1201 ms 0.120100 ms/iter mmap(500MB) 1231 ms 0.123100 ms/iter mmap(1024MB) 1229 ms 0.122900 ms/iter
可以看出来使用share模式的mmap,会与所有指向这个内存空间的对象共享,相当于输出文件,所以fork出来的进程并没有将全部内容拷贝出来。这样就是为什么性能比malloc好的原因。
博客随笔IT之内容均由作者:Ritchie E在加班过度状态下,手抖随机敲键盘生成
内容均属原创,转载请以链接形式注明:
The post 不同内存分配方式下fork()的性能 appeared first on 随笔IT.