Вопрос или проблема
Системный вызов mmap
требует файловый дескриптор (fd) в качестве параметра, но когда вы закрываете этот дескриптор, mmap все равно остаётся в адресном пространстве памяти процесса.
Следовательно, для удержания mmap не требуется открытый дескриптор, так почему же Linux поддерживает создание mmap только для файла с использованием дескриптора, а не с помощью пути к файлу? Не было бы замечательно, если бы у нас был системный вызов mmapat
, как openat
и execveat
?
Если mmap
создаёт дополнительную ссылку на этот файл, почему мы не можем иметь mmapat
, который атомарно создаёт такую ссылку в первый раз без необходимости получения дескриптора процесса, а затем освобождения его позже?
Существует ли какая-либо историческая или Sicherheitsgrund для отсутствия такого системного вызова в ядре Linux?
mmap(2) фактически работает как read(2) для буфера, в который ядро будет записывать напрямую, вместо чтения в буфер ядра и затем копирования в предоставленный буфер.
Нет mmapat(2) по той же причине, по которой нет readat(2).
Файловый дескриптор больше не нужен, потому что…
Функция mmap() добавляет дополнительную ссылку на файл, связанный с файловым дескриптором fildes, которая не удаляется последующим вызовом close() для этого файлового дескриптора. Эта ссылка уничтожается, когда больше нет отображений файла.
Это согласно сайту OpenGroup. Они управляют стандартом POSIX, если я не ошибаюсь, так что они должны знать.
Ответ или решение
Почему в Linux не поддерживается mmap по пути?
Вопрос о том, почему в Linux не существует системного вызова mmap
, принимающего путь к файлу вместо дескриптора файла (fd), имеет множество аспектов, включая архитектурные, исторические и безопасность.
Основные причины отсутствия mmap по пути
-
Парадигма работы с дескрипторами файлов:
Система вызоваmmap
в Linux требует наличия дескриптора файла по нескольким причинам. Во-первых, дескрипторы файлов предоставляют абстракцию, которая позволяет управлять доступом к ресурсам в операционной системе. При открытии файла с помощьюopen()
создается дескриптор, который затем используется для различных операций, таких какread()
,write()
иmmap()
. Использование дескрипторов делает управление ресурсами более безопасным и эффективным. -
Избежание гонок условий:
Если быmmap
принимал путь, то могли бы возникнуть ситуации гонки — например, файл мог бы быть удален или изменен до момента, когдаmmap
будет успешно вызван. При использовании дескрипторов, особенно с поддержкой системных вызовов, таких какopenat()
, можно сохранить целостность данных и избежать таких ситуаций. -
Ссылочная верификация:
Когда вызываетсяmmap(fd)
, система в большинстве случаев добавляет дополнительную ссылку на файл, связанный с дескриптором. Закрытие дескриптора черезclose(fd)
не освобождает эту ссылку, пока не будут удалены все маппинги, что позволяет избежать преждевременного удаления данных и тем самым сохранить их в памяти процесса. -
Исторические причины:
Архитектура Linux и её системные вызовы развивались в контексте POSIX-стандарта, который изначально был спроектирован с использованием дескрипторов для управления файлами. К тому же, многие Unix-подобные системы придерживаются этой моделью, и внедрение системного вызова, подобногоmmapat
, потребовало бы серьезной переработки существующих подходов к управлению файлами. -
Проблемы безопасности:
Использование дескрипторов подразумевает наличие средств контроля доступа и управления безопасностью, чего нельзя достичь, если работать исключительно с именами файлов. С помощью дескрипторов можно настроить права доступа, а также реализовать другие механизмы безопасности, которые защищают данные от несанкционированного доступа.
Заключение
Подводя итог, можно сказать, что отсутствие системного вызова mmap
по пути связано как с историческими, так и с техническими аспектами, которые больше способствуют управлению ресурсами и безопасности в операционной системе. Хотя звучит привлекательно иметь mmapat
, работающий аналогично openat
и execveat
, текущая архитектура, основанная на дескрипторах файлов, обеспечивает более надёжное и безопасное взаимодействие с файлами.