#c #windows #file-descriptor
#c #Windows #файловый дескриптор
Вопрос:
Похож ли ДЕСКРИПТОР на дескриптор файла в Linux? Насколько я знаю, ДЕСКРИПТОР используется для обработки всех ресурсов в Windows, таких как шрифт, значки, файлы, устройства …, что по сути является просто указателем void, указывающим на блок памяти, содержащий данные определенного ресурса
Комментарии:
1. Да, то же самое. Кстати, это не указатель.
2. ДЕСКРИПТОР Windows — это своего рода токен для объекта ядра (всегда ссылающийся на объекты, которые были загружены в память). ОС создает сопоставление с объектами ядра, а дескриптор (передаваемый в пространство пользователя) является «ключом» к этому сопоставлению. Обратите внимание, что для одного и того же объекта ядра могут быть разные дескрипторы (даже в одном и том же процессе), и ОС не уничтожит объект, пока вы не закроете все дескрипторы.
3. Распечатайте значения ДЕСКРИПТОРА … вы увидите, что они не являются указателями. Дело в том, что не имеет значения, что представляют значения, вам должно быть все равно. Так что да, они оба обеспечивают одинаковую функциональность, но используют разные методы.
4. Но вы должны различать настоящие дескрипторы ядра, которые, проще говоря, закрыты
CloseHandle()
, и другие объекты, которые синтаксически похожи, но не являются объектами ядра, такие как дескрипторы окон (HWND), объекты GDI (HICON, HGC, HBITMAP), HMENU и т. Д.5. Вы спрашиваете, похожи ли они концептуально или они реализованы аналогично?
Ответ №1:
Да, дескрипторы Windows очень похожи на файловые дескрипторы Unix (FD).
Обратите внимание, что a HANDLE
не является указателем на блок памяти. Хотя HANDLE
это typedef
‘d as void *
, это просто для того, чтобы сделать его более непрозрачным. На практике a HANDLE
— это индекс, который просматривается в таблице, так же, как и номер FD.
В этом сообщении в блоге рассматриваются некоторые сходства и различия: http://lackingrhoticity .blogspot.com/2015/05/passing-fds-handles-between-processes.html
Ответ №2:
Да, они концептуально похожи. Файловые дескрипторы в unix отображают целые числа в таблицу указателей на другие объекты для каждого процесса (которые также могут быть не только файлами). Хотя файловые дескрипторы не так унифицированы — некоторые вещи существуют в отдельном «пространстве имен» (например, таймеры процессов). В этом отношении Windows более ортогональна — CloseHandle всегда освобождает ресурс, независимо от того, что это такое.
Ответ №3:
Помимо того факта, что дескрипторы относятся к гораздо более широкому понятию в Windows. Даже если мы ограничим обсуждение только дескрипторами файлов, есть существенные различия. Существует функция с именем _open_osfhandle() как часть библиотеки времени выполнения C в Windows. Его цель состоит в том, чтобы, цитирую «Связать дескриптор файла C во время выполнения с дескриптором существующего файла операционной системы». То есть функция склеивания между областью ядра и областью времени выполнения C. Сигнатура функции выглядит следующим образом:
int _open_osfhandle (
intptr_t osfhandle,
int flags
);
Дескрипторы файлов Windows на самом деле более многофункциональны, чем дескрипторы файлов в C, которые можно настроить, когда дескриптор файла создается с помощью CreateFileA (версия ANSI) или CreateFile (версия UTF16), что отражает разницу в дизайне между * Nix и Windows. И полученный дескриптор переносит всю эту информацию со всеми вытекающими последствиями.
Ответ №4:
Комментарии:
1. Будьте осторожны, делая выводы из этого. Неполный тип указателя — хороший тип для непрозрачного дескриптора, потому что он запрещает арифметику — вы не можете случайно добавить два дескриптора вместе, как вы можете с файловыми дескрипторами unix, хранящимися в
int
переменных. Но aHANDLE
не является адресом памяти. Иtypedef PVOID HANDLE;
даже неверно. (НайдитеSTRICT
макрос и его эффект)2. (Проверьте комментарий yic81 «Утверждение
typedef HANDLE HINSTANCE;
абсолютно неверно, как и многие другие дескрипторы typedef. Подавляющее большинство из них теперьDECLARE_HANDLE()
являются структурами «. на странице, на которую вы ссылались. Он прав, страница MSDN неверна.)