Функция R mcfork
является только оболочкой для системного вызова fork
(Кстати, на странице руководства сказано, что этот вызов сам по себе является оболочкой для clone
)
Я создал простую программу на C ++ для проверки поведения fork
:
#include <stdio.h>
#include <unistd.h>
#include<vector>
int main(int argc, char **argv)
{
printf("--beginning of program\n");
std::vector<std::vector<int> > l(50000, std::vector<int>(50000, 0));
// while (true) {}
int counter = 0;
pid_t pid = fork();
pid = fork();
pid = fork();
if (pid == 0)
{
// child process
int i = 0;
for (; i < 5; ++i)
{
printf("child process: counter=%d\n", ++counter);
}
}
else if (pid > 0)
{
// parent process
int j = 0;
for (; j < 5; ++j)
{
printf("parent process: counter=%d\n", ++counter);
}
}
else
{
// fork failed
printf("fork() failed!\n");
return 1;
}
printf("--end of program--\n");
while (true) {}
return 0;
}
Во-первых, программа выделяет в куче около 8 ГБ данных. Затем он порождает 2 ^ 2 ^ 2 = 8 дочерних элементов через вызов fork и ждет, пока пользователь их не убьет, и входит в бесконечный цикл, чтобы его было легко обнаружить в диспетчере задач.
Вот мои наблюдения:
- Для успешного выполнения форка в моей системе должно быть не менее 51% свободной памяти, но это включает в себя своп. Вы можете изменить это, отредактировав
/proc/sys/vm/overcommit_*
файлы proc.
- Как и ожидалось, ни один из дочерних элементов не занимает больше памяти, поэтому эта свободная память 51% остается свободной на протяжении всей программы, и все последующие вилки также не дают сбоев.
- Память распределяется между вилками, поэтому она восстанавливается только после того, как вы убили последнего ребенка.
Проблема фрагментации памяти
Вы не должны беспокоиться о каком-либо уровне фрагментации памяти по отношению к fork. Фрагментация памяти R здесь не применяется, потому что fork работает с виртуальной памятью. Вам не следует беспокоиться о фрагментации физической памяти, потому что практически все современные операционные системы используют виртуальную память (что, следовательно, позволяет им использовать подкачку). Единственная фрагментация памяти, которая может быть проблемой, - это фрагментация пространства виртуальной памяти, но AFAIK в пространстве виртуальной памяти Linux составляет 2 ^ 47, что более чем огромно, и в течение многих десятилетий у вас не должно возникнуть проблем с поиском непрерывных областей любой практичный размер.
Резюме:
Убедитесь, что у вас больше подкачки, чем физической памяти, и, пока вашим вычислениям не требуется больше памяти, чем у вас есть в ОЗУ, вы можете mcfork
их сколько угодно.
Или, если вы готовы рискнуть стабильностью (нехваткой памяти) всей системы, попробуйте echo 1 >/proc/sys/vm/overcommit_memory
как root в Linux.
Или еще лучше: (безопаснее)
echo 2 >/proc/sys/vm/overcommit_memory
echo 100 >/proc/sys/vm/overcommit_ratio
Вы можете узнать больше о чрезмерных обязательствах здесь: https://www.win.tue.nl/~aeb/linux/lk/lk-9.html
person
Adam Ryczkowski
schedule
20.05.2016