Получить физический адрес файла на диске - PullRequest
0 голосов
/ 28 ноября 2018

Используя Windows API, я пытаюсь написать программу для чтения данных с диска.Мне удалось получить доступ к содержимому диска с помощью CreateFile , и я могу выполнить поиск по нему.Допустим, на этом диске есть несколько файлов, и я знаю их пути, но на самом деле меня интересует их физическое местоположение.

Мой вопрос: возможно ли получить физическое местоположение или адрес файлов (или сектор, в котором они находятся) и где они хранятся на диске без поиска всего диска?Если так, какие функции я должен использовать?Использование SetFilePointer или FindFirstFile , похоже, также не решает проблему.

1 Ответ

0 голосов
/ 28 ноября 2018

Смысл любой файловой системы в том, чтобы абстрагировать секторы физического диска и предоставить вам абстракцию более высокого уровня (называемые файлами).Таким образом, ответ на вопрос «Можно ли получить физическое местоположение» должен быть нет! (в общем);некоторый код может даже перемещать секторы файла (например, дефрагментатор диска , и вы можете представить, что он работает одновременно с вашей программой, даже если это не рекомендуется ..)

Для получения дополнительной информации прочитайте вики-страницы по файловым системам и файлам , а затем прочитайте хорошую книгу, такую ​​как Операционные системы: Three Easy Pieces

Обратите внимание, что при использовании файлов вы ожидаете, что ваша программа будет вести себя аналогично после перемещения файловой системы на другой диск при условии, что пути к файлам, их содержимое и метаданные останутся прежними.В частности, у вас может быть два внешних USB дисковых корпуса с разной геометрией или емкостью, имеющие одинаковое содержимое файла (возможно, даже в разных файловых системах, например, VFAT в одной и NTFS в другой), а затем вы ожидаете, что ваша программа будет вести себя одинаково при доступе к таким файлам (в первом или втором окне).Независимо от того, какой блок подключен, ваша программа (например) получит доступ к тому же файлу F:\MyDir\MyFile.dat.Что касается файловых систем, оба поля будут выглядеть одинаково.На уровне физического сектора данные будут организованы совсем по-другому.

Кстати, физическая организация файлов внутри файловой системы сильно варьируется от одной файловой системы к другой.Вы можете использовать некоторую файловую систему Ext3 на своем компьютере (поскольку * Windows 1030 * Ext3 для Windows) - и это действительно полезно для обмена некоторыми данными между Linux и Windows на ПК с двойной загрузкой- и файловая организация отличается от FAT one или NTFS one.

Вы можете найти способ запросить ядро, чтобы получить реальный физический секторместо нахождения.Но я не уверен, что это работает для всех файловых систем (что означало бы расположение сектора для некоторой удаленной NFS).И эта информация может быть устаревшей до того, как ваша программа ее получит (например, если какой-то дефрагментатор работает параллельно).Кроме того, другие процессы могут одновременно обращаться к одной и той же файловой системе и изменять ее (так что метаданные - например, местоположение сектора - будут устаревшими к тому времени, когда запланирован запуск вашего процесса).

В Windowsи в Unix-подобных системах код файловой системы выполняется в ядре.И другие процессы могут использовать этот же код (и ту же файловую систему), пока ваш процесс не запущен.И Windows, и Unix имеют упреждающее планирование, поэтому у вас нет гарантии, что ваш процесс снова запустится в пользовательском режиме, прежде чем какой-то другой процесс будет использовать ту же файловую систему.

Помните, что на практике ваши файловые данные часто остаются в кеш страниц .И именно поэтому вы можете не слышать, как работает ваш диск - если у вас все еще есть вращающийся жесткий диск - при доступе к одному и тому же файлу несколько раз подряд (например, запуск одной и той же программы для одного и того же файла дважды, с интервалом в несколько секунд; обычноВторой запуск - сохранение диска в режиме молчания, поскольку данные файла уже находятся в ОЗУ.)

В комментарии вы упоминаете, что хотите

Чтобы просмотреть данные файла иНапример, посмотрите, что происходит с данными, когда они удаляются или изменяются.

но это должно работать на уровне файловой системы.В Linux для этого есть inotify (7) (они работают на большинстве локальных файловых систем, например Ext4 или BTRFS, но не на удаленных файловых системах а-ля nfs (5) , и ни в псевдофайловых системах à la proc (5) ).Я не знаю, есть ли в Windows что-то похожее на Linux inotify (но, вероятно, да , по крайней мере, в некоторых случаях).

Вам, вероятно, следует рассмотреть возможность использования некоторой базы данных (может быть, столь же простой, как sqlite ), и, возможно, вы хотите ACID свойств (затем использовать некоторые реальные RDBMS как PostGreSQL).С PostGreSQL вы можете использовать TRIGGER s, чтобы знать, что некоторые данные изменились, даже если некоторые другие программы изменят ту же базу данных.

Вы также можете сделать некоторые блокировка файла и принятие соглашения о том, что каждая программа, обращающаяся к вашему конкретному файлу, должна блокировать его соответствующим образом.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...