The OpenNET Project / Index page

[ новости /+++ | форум | wiki | теги | ]

Интерактивная система просмотра системных руководств (man-ов)

 ТемаНаборКатегория 
 
 [Cписок руководств | Печать]

vfork (2)
  • vfork (2) ( Solaris man: Системные вызовы )
  • vfork (2) ( FreeBSD man: Системные вызовы )
  • >> vfork (2) ( Русские man: Системные вызовы )
  • vfork (2) ( Linux man: Системные вызовы )
  • vfork (3) ( POSIX man: Библиотечные вызовы )
  •  

    НАЗВАНИЕ

    vfork - создает дочерний процесс и блокирует родительский  

    СИНТАКСИС

    #include <sys/types.h>
    #include <unistd.h>

    pid_t vfork(void);  

    ОПИСАНИЕ СТАНДАРТА

    (Из черновика XPG4 / SUSv2 / POSIX) Функция vfork() аналогична fork() за тем исключением, что поведение процесса, созданного vfork(), неопределено, если он модифицирует любые данные, кроме переменной типа pid_t, используемой в качестве значения, возвращаемого vfork(), или возвращается из функции, в которой была вызвана функция vfork(), или вызывает любую функцию до удачного исполнения _exit() или одной из функций семейства exec.  

    НАЙДЕННЫЕ ОШИБКИ

    EAGAIN
    В системе слишком много процессов - попробуйте еще раз.
    ENOMEM
    Не хватает памяти для создания нового процесса.
     

    ОПИСАНИЕ LINUX

    vfork, так же, как и fork(2), создает дочерний процесс для вызывающего. Подробности, возвращаемые значения и ошибки смотрите в fork(2).

    vfork() это специальный вариант clone(2). Он используется для создания новых процессов без копирования таблиц страниц родительского процесса. Это может использоваться в приложениях, критичных к производительности, для создания дочерних процессов, сразу же запускающих execve().

    vfork() отличается от fork тем, что родительский процесс блокируется до тех пор, пока дочерний процесс не вызовет execve(2) или _exit(2). Дочерний процесс разделяет всю память с родительским, включая стек, до тех пор, пока не вызовет execve(). Дочерний процесс не должен выходить из текущей функции или вызывать exit(), но может вызвать _exit().

    Обработчики прерываний наследуются, но не разделяются. Сигналы передаются родительскому процессу после того, как дочерний процесс разблокирует его работу.  

    ПРИМЕЧАНИЯ ПО ИСТОРИИ

    В Linux функция fork() реализована при помощи страниц "копирования при записи" (copy-on-write), поэтому единственная задержка, возникающая при вызове fork(), - это время, необходимое для создания копии таблиц страниц родительского процесса и структуры задания дочернего процесса. Однако, в прошлом fork() мог требовать создания полной копии пространства данных вызывающего процесса, что обычно не требовалось, так как сразу за fork() следовало exec(). Поэтому для большей эффективности BSD предложило системный вызов vfork, который не копировал адресное пространство процесса, а использовал то же самое пространство, блокируя родительский процесс до вызова execve() или до прекращения своей работы. Использование vfork было похоже на трюк: например, сохранность данных родительсокго процесса зависела от того, какие переменные содержатся в регистрах.  

    НАЙДЕННЫЕ ОШИБКИ

    Скажем прямо, не очень хорошо, что в Linux существует столь тяжелый пережиток прошлого. В man-странице BSD написано следующее: "Этот системный вызов будет устранен после того, как будут реализованы соответствующие механизмы разделения ресурсов системы. Пользователи не должны опираться на существующую семантику разделения памяти vfork, то есть программа должна быть аналогична программе с fork." Говоря проще, стандартное описание не позволяет использовать vfork(), потому что, если последующий за ним exec может не исполниться, что произойдет дальше - не определено. Обработка сигналов еще более сложна и различается от системы к системе. В man-странице BSD написано следующее: "Для исключения возможности остановки системы процессы, являющиеся дочерними после исполнения vfork, никогда не получают сигналов SIGTTOU или SIGTTIN; вместо этого вывод или ioctl всегда разрешены, а попытки ввода приводят к ситуации "EOF". На текущий момент (Linux 2.3.25) strace(1) не может следовать за vfork() и требует изменений в коде ядра.  

    ПРИМЕЧАНИЯ ПО ИСТОРИИ

    Системный вызов vfork() впервые появился в 3.0BSD. В BSD 4.4 он стал синонимом fork(), но NetBSD ввела его снова: http://www.netbsd.org/Documentation/kernel/vfork.html . В Linux этот системный вызов был эквивалентом fork() примерно до ядра 2.2.0-pre6. Начиная с 2.2.0-pre9 (на i386 и немного позже на других архитектурах), он стал независимым системным вызовом. Его поддержка быда добавлена в glibc 2.0.112.  

    СООТВЕТСТВИЕ СТАНДАРТАМ

    Системный вызов vfork может быть похожим на системные вызовы с тем же именем в других ОС. Требования, предъявляемые стандартами к vfork не такие жесткие, как те, которые предъявляются к fork, поэтому будет достаточно тех реализаций, в которых эти два вызова являются синонимами. В частности, программист не может полагаться на действия родительского процесса до вызова execve() или _exit() и не может полагаться на специфичесоке поведение т.н. "возникшей разделяемой памяти".  

    СМ. ТАКЖЕ

    clone(2), execve(2), fork(2), wait(2)


     

    Index

    НАЗВАНИЕ
    СИНТАКСИС
    ОПИСАНИЕ СТАНДАРТА
    НАЙДЕННЫЕ ОШИБКИ
    ОПИСАНИЕ LINUX
    ПРИМЕЧАНИЯ ПО ИСТОРИИ
    НАЙДЕННЫЕ ОШИБКИ
    ПРИМЕЧАНИЯ ПО ИСТОРИИ
    СООТВЕТСТВИЕ СТАНДАРТАМ
    СМ. ТАКЖЕ


    Поиск по тексту MAN-ов: 




    Спонсоры:
    Inferno Solutions
    Hosting by Hoster.ru
    Хостинг:

    Закладки на сайте
    Проследить за страницей
    Created 1996-2021 by Maxim Chirkov
    Добавить, Поддержать, Вебмастеру