LoginSignup
2
0

なぜmallocしている量が多くなるとforkが遅くなるのか?

Last updated at Posted at 2023-06-13

TL;DR

It seems that even though the data of the allocated/used memory itself is not being copied, thanks to the copy-on-write feature, the internal virtual memory structures in the kernel, which hold the information about how much and what memory the parent process has allocated, are being copied in an inefficient way while the child process is being created by fork().
forkしたときコピー・オン・ライトによりmallocされたメモリそのものはコピーされないが、カーネル内部での仮想メモリの構造が非効率な方法でコピーされている。
https://blog.famzah.net/2009/11/20/fork-gets-slower-as-parent-process-use-more-memory/

実験用プログラム

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <sys/time.h>
#include <sys/wait.h>

int main(int argc, char *argv[])
{
    int count = 3000;   // forkする回数
    int mb = 10;        // mallocするサイズ(MiB)
    struct timeval tv1;
    struct timeval tv2;

    if (argc >= 2)
        mb = atoi(argv[1]);
    if (argc >= 3)
        count = atoi(argv[2]);

    printf("count = %d\n", count);
    printf("mb    = %d\n", mb);

    int len = 1024 * 1024 * mb;
    int size = sizeof(int) * len;
    int* p = malloc(size);
    // mallocしただけではカーネルはメモリを確保しないので書き込んでおく
    for (int i = 0; i < len; i++) {
        p[i] = i;
    }

    gettimeofday(&tv1, NULL);

    // fork
    for (int i = 0; i < count; i++) {
        if (fork() == 0) {
            exit(0);
        }
    }
    // 全子プロセスが終了するまで待つ
    while (wait(NULL) != -1) {
    }

    gettimeofday(&tv2, NULL);

    double elapsed = tv2.tv_sec - tv1.tv_sec + (tv2.tv_usec - tv1.tv_usec) / (1000.0 * 1000.0);

    printf("elapsed = %f\n", elapsed);
    return 0;
}

実行例

(10の部分を1から40まで変えて実行してみた)

./a.out 10

実験結果

FreeBSD
1   0.645625
10  1.102455
20  1.150587
30  4.327679
40  6.803514

Linux
1   0.445254
10  1.767612
20  3.032894
30  4.407658
40  5.822945
2
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
2
0