Разница между клоном и форком +unshare
Как-то проще позвонить fork
а потом unshare
потому что многие аргументы копируются через fork
который в противном случае был бы вручную упакован в clone
, Мой вопрос, в чем разница между (1) вызовом clone
который создает новый процесс в отдельных пространствах имен и (2) fork+unshare
который разветвляется на новый процесс, а затем покидает пространства имен родителя. Предположим, что все флаги пространства имен переданы clone
а также unshare
подобные.
auto flag = CLONE_NEWUSER | CLONE_NEWUTS | CLONE_NEWIPC | CLONE_NEWPID | CLONE_NEWNS | CLONE_NEWNET | SIGCHLD;
Таким образом, с помощью fork очень легко повторно использовать данные, унаследованные от родителей.
int mydata; // this could be even more complicated, class, struct, etc.
auto pid = fork();
if(pid == 0) {
// reuse inherited data in a copy-on-write manner
unshare(flag);
}
Для клона нам иногда приходится переносить данные в другую структуру и передавать их как void*
к clone
системный вызов.
int mydata;
clone(func, stack+stack_size, flag, &wrapper_of_data);
Мне кажется, что в приведенном выше примере единственная разница заключается в снижении производительности, когда fork может быть немного дороже. Тем не менее, характер fork
избавляет меня от многих усилий, связанных с тем, что оба могут создать процесс в новых пространствах имен.
1 ответ
Каким-то образом проще вызвать fork, а затем отказаться от совместного использования, поскольку многие аргументы копируются с помощью fork, которые в противном случае были бы вручную упакованы для клонирования.
Это верно только для функции-оболочки libc.
Базовый системный вызов больше похож на fork() и, вероятно, будет работать лучше в этом случае:
long flags = CLONE_NEWUSER | ... | SIGCHLD;
long pid = syscall(__NR_clone, flags, 0, 0, 0, 0);
if(pid == 0) {
/* child with unshared namespaces */
}
Примерно в то время, когда был введен системный вызов клонирования, fork() - это просто особый случай клонирования с флагами =SIGCHLD и 0 для всех остальных аргументов.
Вероятно, нет оснований предпочитать пару fork/unshare вместо простой передачи тех же флагов для клонирования.