Як однаковий fd у різних процесах може вказувати на один і той же файл?


25

Скажіть, у мене є процес 1 і процес 2 . Обидва мають дескриптор файлу, відповідний цілому числу 4.

Однак у кожному процесі дескриптор файлу 4 вказує на зовсім інший файл у таблиці відкритих файлів ядра:

введіть тут опис зображення

Як це можливо? Чи не повинен дескриптор файлу бути індексом запису в таблиці відкритих файлів?


1
Гарне питання! Я гадаю, що дескриптори файлів перекладені так, що fd 4в обох процесах є відносним до його власного числа відкритих fd. Fd 0-2(stdin, stdout, sdterr) завжди відкриваються для нового процесу, і номери не зарезервовані лише для цього процесу.


@ jw013 Я вважав, що це звучить знайомо. \ @Pithikos Як це не дублікат?
Майкл Мрозек

1
Це погана діаграма - вона повинна показувати, що дескриптор файлу 4 означає четвертий запис [ну, п’ятий, він рахується з нуля] таблиці дескрипторів файлів зліва, а не запис, який містить "4". Фактична «4» живе у змінній вашому просторі користувачів, що містить число. Діаграма в іншому питанні набагато краща.
Випадково832

2
@ Random832 Добре, якби я знав, яка діаграма була правильною, я, мабуть, ніколи не ставив цього питання.
Пітікос

Відповіді:


35

Дескриптор файлу, тобто 4у вашому прикладі, є індексом у таблиці дескрипторів файлу, специфічної для процесу , а не у відкритій таблиці файлів. Сам запис дескриптора файлу містить індекс до запису в глобальній таблиці відкритих файлів ядра, а також прапори дескриптора файлу.


2
Для запису в більшості систем є лише один "прапор дескриптора файлів", прапор близького до виконання. Усі інші стану "per-fd" (включаючи зміщення та режим доступу) є частиною запису відкритої таблиці файлів.
Випадково832

24

Кожен процес має власну таблицю дескрипторів файлів. Дескриптор файлу 4 в процесі 1234 балів всередині таблиці 1234 процесу. Дескриптор файлу 4 в процесі 5678 вказує всередині таблиці 5678 процесу. Випадок, з яким ви повинні бути знайомі, - це дескриптори файлів 0, 1 і 2, які для кожного процесу - це стандартний вхід, стандартний вихід і стандартна помилка, вказуючи туди, куди вони були перенаправлені.

Процес може відкривати один і той же файл не один раз. Це може статися випадково, наприклад, коли стандартний висновок і стандартна помилка перенаправляються на той же термінал або в один і той же файл. Записи в базовій таблиці файлів (наприклад, Linuxstruct file ) містять більше ніж інформацію про файл; вони також містять режими відкриття (наприклад, читання або запис) та інший стан (наприклад, прапори, наприклад, close-on-exec). Наприклад, у процесу може бути відкритий термінал для читання лише в дескрипторі файлів 0, а той самий термінал відкритий для запису лише в дескрипторі файлів 2. Записи таблиць файлів також містять положення процесу у файлі; процес може захотіти до lseekдвох різних позицій в одному файлі, і тому він буде використовувати dupдля отримання двох ручок до цього файлу.


2
Це не зовсім правильно. Згідно з довідковою сторінкою / специфікаціями, dupробить саме те, що написано на тині: обидва результуючі дескриптори вказують на один і той же запис файлової таблиці і, таким чином, мають однакове зміщення. Для того, щоб отримати 2 різні записи файлових таблиць, я впевнений, що вам потрібно ввести openфайл двічі.
jw013

@Gilles "Дескриптор файлу 4 в процесі 1234 балів всередині таблиці 1234 процесу". Яку таблицю ви маєте на увазі? З того, що я знаю, єдина таблиця в процесі - це таблиця дескрипторів файлів, де кожна запис вказує на єдину таблицю відкритих файлів ядра .
Пітікос

Дивіться unix.stackexchange.com/questions/195057/… для більш точного опису.
Жил "ТАК - перестань бути злим"

8

Кожен процес має власну таблицю дескрипторів файлів. Це все.

Це все дуже добре описано в мережевому програмуванні UNIX Річарда Стівенса, якщо ви хочете глибоко вивчити це.


На яку таблицю ви звертаєтесь?
Пітікос

1
Таблиця дескрипторів файлів
Michał Šrajer

7

Чи не зайвий рівень непрямості вирішить вашу проблему? ("Усі проблеми в комп'ютерному програмуванні можна вирішити додатковим рівнем непрямості" - деяка мудра сіра борода). Тобто, мале ціле число у кожному процесі закінчується як індекс у масиві індексів простору ядра в «процес відкритих таблиць файлів».


2
Джерело мудрий старий , ймовірно , Девід Уілер. Схоже, він також сказав: " Але це зазвичай створить іншу проблему ". :)
jw013
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.