Процессы обычно создаются с fork
, потоки (облегченные процессы) обычно создаются с clone
в настоящее время.Однако, как это ни странно, существуют также модели потоков 1: N, которые тоже этого не делают.
Обе fork
и clone
отображаются на одну и ту же функцию ядра do_fork
внутри.Эта функция может создать облегченный процесс, который разделяет адресное пространство со старым или отдельный процесс (и многие другие параметры), в зависимости от того, какие флаги вы ему подаете.Системный вызов clone
является более или менее прямой передачей этой функции ядра (и используется библиотеками потоков более высокого уровня), тогда как fork
включает do_fork
в функциональность 50-летней традиционной функции Unix.
Важное отличие состоит в том, что fork
гарантирует, что будет сделана полная, отдельная копия адресного пространства.Это, как правильно указывает Василий, в настоящее время выполняется с копированием при записи и, следовательно, не так дорого, как можно подумать.
Когда вы создаете поток, он просто повторно использует исходное адресное пространство и ту же память.
Однако, не следует предполагать, что создание процессов, как правило, «облегчено» в unix-подобных системах из-за копирования при записи.Он несколько менее тяжелый, чем, например, в Windows, но его далеко не бесплатно.
Одна из причин заключается в том, что, хотя реальные страницы не копируются, новому процессу все равно требуется копия таблицы страниц.Это может быть от нескольких килобайт до мегабайт памяти для процессов, которые используют большие объемы памяти.Другая причина заключается в том, что хотя копирование при записи невидимо и является разумной оптимизацией, оно не является бесплатным и не может творить чудеса.Когда данные модифицируются любым из процессов, что неизбежно происходит, происходит сбой затронутых страниц.
Redis является хорошим примером, где вы можете видеть, что fork
совсем не легок (он использует fork
для сохранения в фоновом режиме.).