В системах Unix идиома создания процесса fork () и fork () / exec () требует итерации по всем потенциальным дескрипторам файла процесса, пытающимся закрыть каждый, обычно оставляя только несколько файловых дескрипторов, таких как stdin, stdout,stderr не тронут или перенаправлен куда-либо еще.
Так как является API Unix для запуска процесса, его необходимо выполнять каждый раз, когда создается новый процесс, включая выполнение каждого и не встроенного-in команда вызывается в сценариях оболочки.
Другие факторы, которые следует учитывать, - это то, что, хотя некоторые программы могут использовать sysconf(OPEN_MAX)
для динамического определения количества файлов, которые могут быть открыты процессом, много программного обеспечения.по-прежнему использует библиотеку C по умолчанию FD_SETSIZE
, которая обычно составляет 1024 дескриптора, и поэтому никогда не может иметь больше, чем столько открытых файлов, независимо от какого-либо административно определенного верхнего предела.
Unix имеет устаревший асинхронный IМеханизм ввода / вывода на основе наборов файловых дескрипторов, которые используют смещения битовпредставлять файлы для ожидания и файлы, которые готовы или находятся в состоянии исключения.Он не очень хорошо масштабируется для тысяч файлов, так как эти наборы дескрипторов необходимо настраивать и очищать каждый раз вокруг цикла выполнения.Более новые нестандартные API-интерфейсы появились в основных вариантах Unix, включая kqueue()
на * BSD и epoll()
на Linux для устранения недостатков производительности при работе с большим количеством дескрипторов.
Важно отметить, что select()/poll()
все еще используется ОЧЕНЬ большим количеством программного обеспечения, поскольку долгое время он был API POSIX для асинхронного ввода-вывода.Современный подход асинхронного ввода-вывода POSIX теперь API aio_*
, но он, вероятно, не конкурирует с API kqueue()
или epoll()
.Я не использовал aio в гневе, и у него, конечно, не было бы производительности и семантики, предлагаемых нативными подходами, так как они могут объединять несколько событий для повышения производительности.kqueue () в * BSD имеет действительно хорошую семантику, инициируемую фронтами для уведомления о событиях, что позволяет ему заменять select () / poll (), не вызывая больших структурных изменений в вашем приложении.Linux epoll () следует примеру * BSD kqueue () и улучшает его, что, в свою очередь, следует примеру Sun / Solaris evports.
В результате увеличение количества разрешенных открытых файлов в системе добавляетзатраты времени и пространства для каждого процесса в системе, даже если они не могут использовать эти дескрипторы в зависимости от используемых ими API.Существуют также общие ограничения системы для количества разрешенных открытых файлов.Этот более старый, но интересный сводный список настроек для одновременных соединений 100–200 тыс., Использующих nginx во FreeBSD , дает некоторое представление о накладных расходах на поддержание открытых соединений и , другой охватывает более широкий диапазон систем , но «только»"видя соединения 10K как Mt Everest.
Вероятно, лучшим справочным материалом для программирования в Unix-системах является W. Richard Stevens Расширенное программирование в среде Unix