Диалог для просмотра метаданных FAT32

Тип работы:
Курсовая
Предмет:
Программирование


Узнать стоимость

Детальная информация о работе

Выдержка из работы

БЕЛОРУССКИЙ НАЦИОНАЛЬНЫЙ ТЕХНИЧЕСКИЙ УНИВЕРСИТЕТ

Факультет информационных технологий и робототехники (ФИТР)

Кафедра «Программное обеспечение вычислительной техники и автоматизированных систем»

КУРСОВАЯ РАБОТА

по дисциплине:

«Операционные системы и системное программирование»

Тема:

«Диалог для просмотра метаданных Fat 32»

Выполнил: студент 4 курса ФИТР

группы 307 218

Жуковский И.И.

Руководитель проекта:

доцент, к.т. н

Разоренов Н.А.

Минск 2011

Белорусский национальный технический университет

Факультет информационных технологий и робототехники

Кафедра «Программное обеспечение вычислительной техники и
автоматизированных систем»

ПОЯСНИТЕЛЬНАЯ ЗАПИСКА

к курсовой работе по дисциплине

«Операционные системы и системное программирование»

Тема:

«Диалог для просмотра метаданных Fat 32»

Выполнил:

студент 4 курса ФИТР, гр. 307 218 _________________ Жуковский И. И.

Руководитель: _________________ Разоренов Н. А.

Минск 2011

СОДЕРЖАНИЕ

ВВЕДЕНИЕ

1. АНАЛИЗ СОСТОЯНИЯ ВОПРОСА

1.1 Структура системы FAT

1.2 Анализ области BOOT

1.2.1 Загрузочная запись

1.2.2 FSInfo

1.2.3 Определение типа FAT тома

1.3 Таблица FAT

1.3.1 Цепочки кластеров

1.3.2 Файловые записи

1.4 Корневой каталог ROOT

1.5 Структура файловой записи

1.6 Имя файла в FAT

1.7 Файловые атрибуты

2. ПОСТАНОВКА ЗАДАЧИ

3. РАЗРАБОТКА ПРОГРАММЫ

3.1 Структура построения проекта

3.2 Функции и переменные DLL-модуля

3.3 Функции и переменные управляющего приложения

4. ТЕСТИРОВАНИЕ ПРОГРАММЫ

4.1 Ошибки, выявленные при тестировании

4.1.1 Ошибка вызванная отсутствием выравнивания полей fat_boot_sector

4.1.2 Ошибка, вызванная некорректным ID контроля диалогового окна

4.2 Конечное тестирование приложения

ВЫВОДЫ

СПИСОК ИСТОЧНИКОВ

Приложение, А — Графическая часть

Приложение Б — Листинг алгоритма

Приложение В — Листинг управляющего приложения USBDrvReader. exe

ВВЕДЕНИЕ

Файловая система (англ. file system) — порядок, определяющий способ организации, хранения и именования данных на носителях информации в компьютерах, а также в другом электронном оборудовании: цифровых фотоаппаратах, мобильных телефонах и т. п. Файловая система определяет формат содержимого и физического хранения информации, которую принято группировать в виде файлов. Конкретная файловая система определяет размер имени файла (папки), максимальный возможный размер файла и раздела, набор атрибутов файла. Некоторые файловые системы предоставляют сервисные возможности, например, разграничение доступа или шифрование файлов.

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

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

FAT (англ. File Allocation Table «таблица размещения файлов») — классическая архитектура файловой системы.

Существует три версии FAT — FAT12, FAT16 и FAT32. Они отличаются разрядностью записей в дисковой структуре, т. е. количеством бит, отведённых для хранения номера кластера. FAT12 применяется в основном для дискет, FAT16 — для дисков малого объёма.

FAT32 — последняя версия файловой системы FAT и улучшение предыдущей версии, известной как FAT16. FAT32 была создана, чтобы преодолеть ограничения на размер тома в FAT16, позволяя при этом использовать старый код программ MS-DOS и сохранив формат. FAT32 использует 32-разрядную адресацию кластеров. FAT32 появилась вместе с Windows 95 OSR2. По принципу построения FAT похожа на оглавление книги, т. к. операционная система использует ее для поиска файла и определения кластеров, которые этот файл занимает на жестком диске. Изначально компания Microsoft разработала FAT для управления файлами на дискетах, и только затем приняла ее в качестве стандарта для управления дисками в MS-DOS. Сначала для дискет и небольших жестких дисков (менее 16 Мбайт) использовалась 12-разрядная версия FAT (так называемая FAT12). В MS-DOS v. 3.0 была введена 16-разрядная версия PAT для более крупных дисков. К настоящему моменту FAT 12 применяется на носителях очень малого объема (или на очень старых дисках). Например, все 3,5-дюймовые дискеты емкостью 1,44 Мбайт форматируются для FAT16, а все 5,25-дюймовые? для FAT12.

Максимально возможное число кластеров в FAT32 равно 268 435 445, что позволяет использовать тома (логические диски) объёмом до 8 ТБ. При использовании размера сектора, равного 32 768 байт, максимальный размер тома составит чуть менее 1024 ТБ. Хотя размер сектора может быть любым, традиционно он считается равным 1 сектору диска и равен 512 байт и т.к. эта величина не менялась с момента создания -- она может считаться некоторым ПО как константа.

На основе FAT была разработана новая файловая система exFAT (extended FAT), используемая преимущественно для флеш-накопителей.

Препятствием на пути отказа от FAT32 и перехода на другие файловые системы на USB флеш-накопителях является производительность. Помимо описанных ограничений у FAT32 есть ряд преимуществ (по крайней мере над NTFS) как в скорости записи на флеш-накопитель, так и в скорости чтения/копирования данных с него.

Новейшие FAT 32 имеют атрибуты (архивный, системный, скрытый, временный, только для чтения). [1]

Эта файловая система предусматривает ряд специальных областей на диске, выделенных для организации пространства диска в процессе его форматирования — головную запись загрузки, таблицу разбиения диска, запись загрузки, таблицу размещения файлов (от которой система FAT и получила свое название) и корневой каталог. На физическом уровне пространство диска разбивается на 512-байт области, называемые секторами. В системе FAT место для файлов выделяется блоками, которые состоят из целого числа секторов и именуютс кластерами. Число секторов в кластере должно быть кратно степени двойки

В данной работе будет рассмотрен принцип получения и расшифровки данных основных областей FAT32.

1. АНАЛИЗ СОСТОЯНИЯ ВОПРОСА

1.1 Структура системы FAT

В файловой системе FAT смежные секторы диска объединяются в единицы, называемые кластерами. Количество секторов в кластере может быть равно 1 или степени двойки (см. далее). Для хранения данных файла отводится целое число кластеров (минимум один), так что, например, если размер файла составляет 40 байт, а размер кластера 4 кбайт, реально занят информацией файла будет лишь 1% отведенного для него места. Для избежания подобных ситуаций целесообразно уменьшать размер кластеров, а для сокращения объема адресной информации и повышения скорости файловых операций — наоборот. На практике выбирают некоторый компромисс. Так как емкость диска вполне может и не выражаться целым числом кластеров, обычно в конце тома присутствуют т.н. surplus sectors — «остаток» размером менее кластера, который не может отводиться ОС для хранения информации.

Пространство тома FAT32 логически разделено на три смежные области:

— Зарезервированная область BOOT. Содержит служебные структуры, которые принадлежат загрузочной записи раздела (Partition Boot Record — PBR, для отличия от Master Boot Record — главной загрузочной записи диска; также PBR часто некорректно называется загрузочным сектором) и используются при инициализации тома;

— Область таблицы FAT, содержащая массив индексных указателей («ячеек»), соответствующих кластерам области данных. Обычно на диске представлено две копии таблицы FAT в целях надежности;

— Корневой каталог ROOT, где записано собственно содержимое файлов — т. е. текст текстовых файлов, кодированное изображение для файлов рисунков, оцифрованный звук для аудиофайлов и т. д. — а также т.н. метаданные — информация относительно имен файлов и папок, их атрибутов, времени создания и изменения, размеров и размещения на диске.

В FAT12 и FAT16 также специально выделяется область корневого каталога. Она имеет фиксированное положение (непосредственно после последнего элемента таблицы FAT) и фиксированный размер в секторах.

Если кластер принадлежит файлу, то соответствующая ему ячейка содержит номер следующего кластера этого же файла. Если ячейка соответствует последнему кластеру файла, то она содержит специальное значение (FFFF16 для FAT16). Таким образом выстраивается цепочка кластеров файла. Неиспользуемым кластерам в таблице соответствуют нули. «Плохим» кластерам (которые исключаются из обработки, например, по причине нечитаемости соответствующей области устройства) также соответствует специальный код.

При удалении файла первый знак имени заменяется специальным кодом E516 и цепочка кластеров файла в таблице размещения обнуляется. Поскольку информация о размере файла (которая располагается в каталоге рядом с именем файла) при этом остаётся нетронутой, в случае, если кластеры файла располагались на диске последовательно и они не были перезаписаны новой информацией, возможно восстановление удалённого файла.

1.2 Анализ области BOOT

1.2.1 Загрузочная запись

Первая важная структура тома FAT называется BPB (BIOS Parameter Block) и расположена в зарезервированной области, в нулевом секторе.

BPB в принципе отсутствовал в FAT, обслуживавшей MS-DOS 1. x, так как в то время предполагалось лишь два различных типа тома — одно- и двусторонние пятидюймовые дискеты на 360 кб, причем формат тома определялся по первому байту области FAT. BPB был введен в MS-DOS 2. x в начале 1983 г. как обязательная структура загрузочного сектора, по которой впредь следовало определять формат тома; старая схема определения по первому байту FAT лишилась поддержки. Также в MS-DOS 2.0 была введена иерархия файлов и папок (до этого все файлы хранились в корневом каталоге).

Структура BPB в MS-DOS 2. x содержала 16-битное поле «общего количества секторов», что означало принципиальную неприменимость этой версии FAT для томов объемом более 216 = 65 536 секторов, т. е. более 32 Мб при стандартном размере сектора 512 байт. В MS-DOS 4.0 (1988) вышеназванное поле BPB было расширено до 32 бит, что означало увеличение максимального размера тома до 232 = 4 294 967 296 секторов, т. е. до 2 Гб при 512-байтном секторе.

Следующая модификация BPB появилась вместе с Windows 95 OSR2, в которой была введена FAT32 (в августе 1996 г.). Было снято двухгигабайтное ограничение на размер тома, том FAT32 теоретически может иметь размер до 8 Тб. Впрочем, размер каждого отдельного файла при этом не может превышать 4 Гб. BIOS Parameter Block FAT32 в целях совместимости с ранними версиями FAT повторяет BPB FAT16 вплоть до поля BPB_TotSec32 включительно, далее следуют различия.

«Загрузочный сектор» FAT32 в действительности представляет собой три 512-байтных сектора — сектора 0, 1 и 2. Каждый из них содержит сигнатуру 0xAA55 по адресу 0x1FE, т. е. в последних двух байтах при том, что сектор = 512 байт. В экзотическом случае, когда размер сектора больше, эта подпись повторяется в последних двух байтах нулевого сектора.

1.2.2 FSInfo

Загрузочная запись раздела FAT32 содержит структуру под названием FSInfo, используемую для хранения значения числа свободных кластеров тома. FSInfo, как правило, занимает сектор 1 (см. поле BPB_FSInfo) и имеет следующую структуру (адреса относительно начала сектора):

— FSI_LeadSig. 4-байтовая подпись 0×41 615 252, свидетельствует, что сектор используется для структуры FSInfo.

— FSI_Reserved1. Промежуток с 4-го по 483-й байт сектора включительно, обнуляется.

— FSI_StrucSig. Ещё одна подпись, расположена по адресу 0x1E4 и содержит значение 0×61 417 272.

— FSI_Free_Count. Четырехбайтовое поле по адресу 0x1E8, содержит последнее известное системе значение числа свободных кластеров тома. Значение 0xFFFFFFFF означает, что число свободных кластеров неизвестно и должно вычисляться.

— FSI_Nxt_Free. Четырехбайтовое поле по адресу 0x1EC, содержит номер кластера, от которого должен начинаться поиск свободных кластеров по таблице индексных указателей. Обычно это поле содержит номер последнего кластера FAT, отведенного для хранения файла. Значение 0xFFFFFFFF означает, что поиск свободного кластера должен проводиться с самого начала таблицы FAT, т. е. со второго кластера.

— FSI_Reserved2. Зарезервированное 12-байтное поле по адресу 0x1F0.

— FSI_TrailSig. Подпись 0xAA550000 — последние 4 байта сектора FSInfo.

Смысл введения FSInfo в оптимизации работы системы, так как в FAT32 таблица индексных указателей может иметь значительные размеры и ее побайтовый просмотр может занять значительное время. Однако значения полей FSI_Free_Count и FSI_Nxt_Free могут не соответствовать действительности и должны проверяться на адекватность. Кроме того, они даже не обновляются в резервной копии FSInfo, расположенной, как правило, в секторе 7.

1.2.3 Определение типа FAT тома

Определение типа FAT тома (т.е. выбор между FAT12, FAT16 и FAT32) производится ОС по количеству кластеров в томе, которое в свою очередь определяется из полей BPB. Прежде всего вычисляется количество секторов корневого каталога:

RootDirSectors = (BPB_RootEntCnt * 32) / BPB_BytsPerSec

Далее определяется, какие из полей BPB_FATSz16/32 и BPB_TotSec16/32 не равны нулю, и они используются при определении количества секторов области данных тома:

DataSec = TotSec —

— (

BPB_ResvdSecCnt +

(BPB_NumFATs * FATSz) +

RootDirSectors

) (1)

Наконец, определяется количество кластеров области данных:

CountofClusters = DataSec / BPB_SecPerClus (2)

По количеству кластеров проводится однозначное соответствие с файловой системой:

— CountofClusters < 4085 — FAT12

— CountofClusters = 4085 ч 65 524 — FAT16

— CountofClusters > 65 524 — FAT32

Согласно официальной спецификации, это единственный допустимый способ определения типа FAT. Искусственное создание тома, нарушающего указанные правила соответствия, приведет к его некорректной обработке Windows. Тем не менее, рекомендуется избегать значений CountofClusters, близких к критическим (4085 и 65 525), для верного определения типа файловой системы любыми, часто некорректно написанными драйверами. На дискете при форматировании всегда создается FAT12. Что касается жестких и флэш-дисков, то при размере диска до 512 Мб (при 512-байтном секторе) по умолчанию создается FAT16, свыше 512 Мб — FAT32. Размер кластера определяется при форматировании исходя из файловой системы и размера тома.

1.3 Таблица FAT

1.3.1 Цепочки кластеров

Следующая важная структура тома FAT — это сама таблица FAT, занимающая отдельную логическую область. Она определяет список (цепочку) кластеров, в которых размещаются файлы и папки тома. Между кластерами и индексными указателями таблицы имеется взаимно однозначное соответствие — N-й указатель соответствует кластеру с тем же номером. Первому кластеру области данных присваивается номер 2. Значение индексного указателя соответствует состоянию соответствующего кластера. Возможны следующие состояния:

— кластер свободен — указатель обнулен;

— кластер занят файлом и не является последним кластером файла — значение указателя — это номер следующего кластера файла;

— кластер является последним кластером файла — указатель содержит метку EOC (End Of Clusterchain), значение которой зависит от версии FAT: для FAT12 меткой EOC считается любое значение, большее или равное 0x0FF8 (по умолчанию 0x0FFF); для FAT16 — большее или равное 0xFFF8 (по умолчанию 0xFFFF); для FAT32 — любое значение, большее или равное 0x0FFFFFF8 (по умолчанию 0x0FFFFFFF);

— кластер поврежден — указатель содержит специальную метку, значение которой для FAT12 0x0FF7, для FAT16 0xFFF7 и для FAT32 0x0FFFFFF7. Поврежденный кластер не может использоваться файловой системой для хранения данных; соответствующие указатели не затрагиваются при форматировании тома, когда все остальные указатели обнуляются;

— кластер зарезервирован «для будущей стандартизации» — указатель содержит значение, превышающее CountofClusters, но меньшее метки поврежденного кластера (т.е. до 0xFFF6 включительно для FAT16). В этом случае кластер, не соответствуя никаким реальным данным, считается занятым и пропускается при поиске свободного, но никакой другой информации о нем не предоставляется.

Кластеры 0 и 1 отражаются FAT особо. Индексный указатель, соответствующий нулевому кластеру (самый первый указатель таблицы FAT), содержит значение BPB_Media в нижних 8 битах; остальные биты устанавливаются в 1. Например, если BPB_Media = 0xF8 (жесткий диск), FAT[0] = 0x0FFFFFF8 для FAT32. Таким образом, формально FAT[0] = EOC, что используется при обработке файлов нулевого размера (см. далее).

Второй зарезервированный указатель, FAT[1], при форматировании устанавливается в значение метки EOC. В FAT12 он не используется больше никак, а в FAT16 и FAT32 верхние два бита этого указателя могут содержать отметку о необходимости проверки тома (т.н. «грязный бит»), при чем все остальные биты выставлены в 1. Наличие грязного бита проверяется в процессе загрузки Windows программой autochk. exe. Грязный бит формируется при некорректном отключении тома или при аппаратной ошибке носителя и соответственно принимает два возможных значения.

Индексный указатель FAT32 по определению является 32-битным, однако верхние 4 бита в действительности игнорируются, так что значение указателя по сути является 28-битным. Единственной операцией, оперирующей с верхними 4 битами указателя, является форматирование тома, когда обнуляется весь указатель. Это означает, что, например, значения указателя 0×10 000 000, 0xF0000000 и 0×0 все соответствуют свободному кластеру, так как они отличаются лишь в верхних 4 битах.

Значение размера таблицы FAT по BPB, т. е. BPB_FATSz16/32, может превышать реальное, так что в конце каждой таблицы FAT могут находиться сектора, не соответствующие никаким реальным кластерам данных. При форматировании эти сектора обнуляются, а в процессе функционирования тома никак не используются. Поэтому действительный адрес последнего сектора таблицы FAT, содержащего указатели на реальные кластеры тома, всегда должен рассчитываться из общего количества кластеров области данных, а не из поля BPB_FATSz16/32. Кроме того, последний сектор, занятый таблицей FAT, вовсе не обязательно весь занят ею — в этом случае избыточное пространство сектора так же не используется и забивается нулями при форматировании тома.

1.3.2 Файловые записи

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

1.4 Корневой каталог ROOT

Единственным обязательно присутствующим каталогом является корневой каталог. В FAT12/FAT16 корневой каталог имеет фиксированный размер в секторах, который вычисляется из значения BPB_RootEntCnt, и следует на диске непосредственно после таблицы FAT.

В FAT32 корневой каталог, как любой другой, имеет переменный размер и является цепочкой кластеров. Номер первого кластера корневого каталога отражается BPB_RootClus. Корневой каталог имеет следующие отличия от других каталогов тома FAT:

— он не метится штампами даты-времени;

— не имеет собственного имени (кроме ««);

— не содержит файлов «.» и «.» (см. далее);

— является единственной директорией, в которой может штатно располагаться файл метки тома (см. далее).

1.5 Структура файловой записи

Файловая запись FAT32 состоит из следующих структур:

— DIR_Name. 11-байтное поле по относительному адресу 0, содержит короткое имя файла (в рамках стандарта 8. 3). По поводу имен файлов см. далее.

— DIR_Attr. Байт по адресу 0x0B, отвечающий за атрибуты файла.

— DIR_NTRes. Байт по адресу 0x0C, используется в Windows NT.

— DIR_CrtTimeTenth. Байт по адресу 0x0D. Счетчик десятков миллисекунд времени создания файла, допустимы значения 0−199. Поле часто неоправданно игнорируется.

— DIR_CrtTime. 2 байта по адресу 0x0E. Время создания файла с точностью до 2 секунд.

— DIR_CrtDate. 2 байта по адресу 0×10. Дата создания файла.

— DIR_LstAccDate. 2 байта по адресу 0×12. Дата последнего доступа к файлу (т.е. последнего чтения или записи — в последнем случае приравнивается DIR_WrtDate). Аналогичное поле для времени не предусмотрено.

— DIR_FstClusHI. 2 байта по адресу 0×14. Номер первого кластера файла (старшее слово, на томе FAT12/FAT16 равен нулю).

— DIR_WrtTime. 2 байта по адресу 0×16. Время последней записи (модификации) файла, например его создания.

— DIR_WrtDate. 2 байта по адресу 0×18. Дата последней записи (модификации) файла, в том числе создания.

— DIR_FstClusLO. 2 байта по адресу 0x1A. Номер первого кластера файла (младшее слово).

— DIR_FileSize. DWORD, содержащий значение размера файла в байтах. Фундаментальное ограничение FAT32 — максимально допустимое значение размера файла составляет 0xFFFFFFFF, т. е. 4 294 967 295 байт (4 Гб минус 1 байт). Уже к 2005 г. это вызывало массу неудобств.

Если первый байт записи FAT (т.е. DIR_Name[0]) суть 0xE5 или 0×05, это значит, что запись свободна (соответствующий файл был удален). Если DIR_Name[0] = 0×00, это значит, что свободна не только эта запись, но и все записи директории после нее; Windows не анализирует остаток каталога после обнуленной записи.

1.6 Имя файла в FAT

Поле DIR_Name логически разбивается на первые 8 символов, образующие имя файла, и последние 3, образующие расширение. Точка-разделитель добавляется на уровне файловой системы и не включается в поле имени. Если имя и расширение файла не заполняют отведенное для них место, остальные байты поля DIR_Name забиваются пробелами (0×20). Имя и расширение файла могут содержать любую комбинацию букв, цифр или символов с ASCII-кодами свыше 127; специальные символы распределяются на три группы:

Разрешенные: ! # $ % & () — @ ^ _ ` { } ~ '

Запрещенные: + ,.; = [ ]

Служебные: *? <: > / | «

Служебные символы имеют специальное значение в Windows и не могут входить в состав имени файла, в то время как символы из числа запрещенных все же можно включить в имя файла ценой возникновения LFN-записи (см. ниже). Например, каталог с именем, начинающимся точкой, можно создать в режиме командной строки (mkdir. directory) или в оболочках FAR, Total Commander, WinRAR. Имя файла не может начинаться или заканчиваться пробелом; ни в каком байте поля имени недопустимы служебные символы ASCII, предшествующие пробелу, т. е. 0×00−0х1 °F (за исключением вышеоговоренного случая 0×05). Имена сохраняются по кодовой странице OEM/DOS в конфигурации, имевшей место на момент создания файла. Полный путь к файлу не может превышать 80 символов (3 — буква диска; 64 — путь; 12 — имя файла, включая точку-разделитель; 1 — разделитель NUL).

Все буквенные символы 8.3 имени всегда переводятся и сохраняются в поле DIR_Name в верхнем регистре. Для сохранения исходного регистра имени Windows NT используется байт DIR_NTRes: его биты 3 и 4 при значении 1 свидетельствуют, что соответственно имя и/или расширение файла следует отображать в нижнем регистре. Если имя или расширение содержат символы обоих регистров, для такого файла создается LFN-запись (см. ниже). Windows 9x для сохранения нетривиального регистра имени всегда создает LFN-запись и игнорирует поле DIR_NTRes. Как следствие, имя одного и того же файла, лишенного ассоциированной LFN-записи, может отображаться Windows 9x целиком в верхнем регистре, а Windows NT — (частично) в нижнем.

1.7 Файловые атрибуты

В байте атрибутов верхние два бита являются резервными и всегда должны быть обнулены. Остальные биты распределяются таким образом, что значение 0×01 соответствует атрибуту «только для чтения», 0×02 — «скрытый», 0×04 — «системный», 0×20 — «архивный». Набор нескольких атрибутов составляется суммированием основных значений. Кроме этих стандартных атрибутов, используются ещё следующие: 0×10 — свидетельствует, что файл является каталогом (контейнером для других файлов); 0×08 — ATTR_VOLUME_ID, специальный атрибут уникального файла нулевого размера в корневом каталоге, имя которого считается меткой тома. Ограничение длины метки тома FAT в 11 символов связано с размером поля DIR_Name. Если файл имеет набор атрибутов READ_ONLY | HIDDEN | SYSTEM | VOLUME_ID (значение 0х0F), это свидетельствует, что запись не соответствет отдельному файлу, а содержит часть длинного имени другого файла, не вписывающегося в рамки 8.3 (см. далее).

Искусственное присвоение ненулевого значения верхним двум битам DIR_Attr используется для формирования файлов, которые невозможно удалить или переименовать штатными средствами файловой системы без форматирования. Это полезно, например, при борьбе с вирусами Autorun. inf (программа Panda USB and AutoRun Vaccine). С другой стороны, это же средство могут использовать сами вирусы. Значение DIR_Attr = 0×40 резервировано для внутреннего использования (устройство). 2]

2. ПОСТАНОВКА ЗАДАЧИ

Целью данной работы является разработка динамической библиотеки DLL и управляющего приложения позволяющих получать информацию о загрузочной области BOOT, таблице расположения файлов FAT и структуры корневого каталога ROOT для файловой системы FAT32.

В качестве объекта исследования в данной работе рассматривается файловая система съёмного носителя данных (флеш-накопителя).

В качестве метода исследования избрано пошаговое получение информации основных разделов FAT посредством чтения секторов съёмного носителя. Организация доступа к носителю была осуществлена с помощью CreateFile. Чтение секторов носителя осуществлялась посредством CreateFile.

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

Результатом работы являются управляющее-приложение USBDrvReader. exe и DLL модуль Fat32Info. dll реализующее все поставленные задачи. Написание приложения осуществлялась в VisualStudio 9.0 API.

файловый запись кластер приложение

3. РАЗРАБОТКА ПРОГРАММЫ

3.1 Структура построения проекта

Для реализации считывания и расшировки данных FAT проект был разделён на DLL-модуль Fat32Info. dll и управляющее приложение USBDrvReader. exe.

В функции DLL-модуля входит:

1. организация доступа;

2. считывание и расшифровка информации FAT;

3. последующей передачей информации FAT в управляющее приложение.

Функциями управляющего приложения являются:

1. загрузка DLL-модуля в адресное пространство ОС;

2. управление работой DLL-модуля;

3. организация графического интерфейса пользователя;.

Список функций проекта и их параметров приведен ниже.

3.2 Функции и переменные DLL-модуля

Таблица 3.2.1 — Функции использующееся в DLL-модуле

Метод

Назначение

BOOL APIENTRY DllMain

(

HANDLE hModule,

DWORD ul_reason_for_call,

LPVOID lpReserved

)

DllMain — дополнительная точка входа в динамически-подключаемую библиотеку (DLL). Если функция используется, то она вызывается системой тогда, когда процессы и потоки инициализированы и завершили работу или при вызове функции LoadLibrary и FreeLibrary.

Параметры

hInstance — дескриптор модуля DLL. Это значение — базовый адрес DLLв адресном пространстве ОС.

ul_reason_for_call — указывает, почему DLL вызывает функцию точки входа. Этим параметром может быть одно из ниже перечисленных значений:

DLL_PROCESS_ATTACH — DLL загружается в виртуальное адресное пространство текущего процесса в результате операции запуска или в результате вызова LoadLibrary.

DLL_THREAD_ATTACH — текущий процесс создает новый поток. Когда это происходит, система вызывает функцию

точки входа всех DLLs, в текущий момент связанных с процессом.

DLL_THREAD_DETACH-поток выходит чисто. Если DLL сохранила указатель на распределенную память в слоте TLS, она должна использовать эту возможность, чтобы освободить память.

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

lpvReserved — NULL для динамических загрузок и не ПУСТО (NULL) для статических загрузок.

Возвращаемые значения

Когда система вызывает функцию DllMain созначением DLL_PROCESS_ATTACH, функция возвращает значение ИСТИНА (TRUE), если она завершается успешно.

Когда система вызывает функцию DllMain с каким-либо значением, а не DLL_PROCESS_ATTACH, возвращаемое значение игнорируется.

void ReadBoot

(

HWND hDlg,

UINT IDC_DAMP,

UINT IDC_DATA,

LPCTSTR path

)

ReadBoot — функция по чтению и расшифровке данных загрузочной области BOOT FAT.

Параметры

hDlg — дескриптор главного окна управляющего приложения

IDC_DAMP — определяет ID элемента диалогового окна управляющего приложения для отображения дампа BOOT.

IDC_DATA — определяет ID элемента диалогового окна управляющего приложения для отображения расшифрованной информации дампа BOOT.

path — содержит путь к тому FAT, для котрого получаем расшифровку BOOT.

Возвращаемые значения

Функцыя не возвращает значений.

void ReadTable

(

HWND hDlg,

UINT IDC_DAMP,

UINT IDC_DATA,

LPCTSTR path

)

ReadTable — функция по чтению и расшифровке данных таблицы FAT.

Параметры

hDlg — дескриптор главного окна управляющего приложения

IDC_DAMP — определяет ID элемента диалогового окна управляющего приложения для отображения дампа FAT.

IDC_DATA — определяет ID элемента диалогового окна управляющего приложения для отображения расшифрованной информации дампа FAT.

path — содержит путь к тому FAT, для котрого получаем расшифровку таблицы FAT.

Возвращаемые значения

Функция не возвращает значений.

void ReadRoot

(

HWND hDlg,

UINT IDC_DAMP,

UINT IDC_DATA,

LPCTSTR path,

UINT IDC_N,

UINT IDC_CHAIN,

int pos

)

ReadRoot — функция по чтению и расшифровке данных корневого каталога ROOT FAT.

Параметры

hDlg — дескриптор главного окна управляющего приложения

IDC_DAMP — определяет ID элемента диалогового окна управляющего приложения для отображения дампа ROOT.

IDC_DATA — определяет ID элемента диалогового окна управляющего приложения для отображения расшифрованной информации дампа ROOT.

path — содержит путь к тому FAT, для котрого получаем расшифровку BOOT.

IDC_N — определяет ID элемента диалогового окна управляющего приложения для отображения номера текущего кластера в цепочке.

pos — требуемый номер кластера в цепочке к котрому не обходимо осуществить переход

Возвращаемые значения

Функцыя не возвращает значений.

3.3 Функции и переменные управляющего приложения

Таблица 3.2.1 — Функции использующееся в управляющем приложении

Метод

Назначение

int WINAPI WinMain

(

HINSTANCE hInstance,

HINSTANCE hPrevInstance,

PSTR szCmdLine,

int iCmdShow

)

WinMain — вызывается системой как начальная точка входа, прикладной программы.

Параметры

hInstance — дескриптор текущего экземпляра прикладной программы.

hPrevInstance- дескриптор предыдущего экземпляра приложения. Этот параметр всегда имеет значение ПУСТО (NULL).

lpCmdLine — указатель на строку с символом нуля в конце, устанавливающую командную строку для приложения, исключая имя программы.

nCmdShow — определяет, как окно должно быть показано.

Возвращаемые значения

Если функция достигла цели, то завершается тогда, когда примет сообщение WM_QUIT, при этом она должна возвратить значение выхода, содержащееся в параметре wParam этого сообщения. Если функция завершается перед вводом цикла сообщений, она должна возвратить 0.

INT_PTR DialogBox

(

HINSTANCE hInstance,

LPCTSTR lpTemplate,

HWND hWndParent,

DLGPROC lpDialogFunc

);

Макрокоманда DialogBox создает модальное диалоговое окно из ресурса шаблона блока диалога. DialogBox не возвращает управления до тех пор, пока заданная функция обратного вызова не завершит работу модального диалогового окна путем вызова функции EndDialog.

Параметры

hInstance — дескриптор модуля, исполняемый файл которого содержит шаблон диалогового окна.

lpTemplate — Определяет шаблон диалогового окна. Этот параметр является или указателем на строку символов с нулем в конце, которая устанавливает имя шаблона блока диалога, или целочисленным значением, которое определяет идентификатор ресурса шаблона диалогового окна.

hWndParent — дескриптор окна, которое владеет диалоговым окном.

lpDialogFunc — Указатель на процедуру диалогового окна DialogProc.

Возвращаемые значения

Если функция завершается успешно, возвращаемое значение — параметр nResult при вызове функции EndDialog, используемой, чтобы завершить работу диалогового окна.

BOOL CALLBACK DlgProc

(

HWND hWnd,

UINT message,

WPARAM wParam,

LPARAM lParam

)

DlgProc — процедура диалогового окна вызываемая DialogBox.

Параметры

hWnd — дескриптор диалогового окна

uMsg — устанавливает сообщение.

wParam — определяет дополнительную конкретную для сообщения информацию.

lParam — определяет дополнительную конкретную для сообщения информацию.

Возвращаемые значения

Обычно, процедура диалогового окна должна возвратить значение ИСТИНА (TRUE), если она обработала сообщение, и ЛОЖЬ (FALSE), если она этого не сделала. Если процедура диалогового окна возвращает ЛОЖЬ (FALSE), диспетчер диалогового окна, в ответ на это сообщение, выполняет заданную по умолчанию операцию блока диалога.

void ResizeWnd

(

HWND hDlg,

RECT pWndRect

)

ResizeWnd — отвечает за синхронное изменение размеров контролов окна в зависимости от его размеров.

Параметры

hDlg — дескриптор главного окна управляющего приложения

pWndRect — определяет размеры области для которой идёт отрисовка.

Возвращаемые значения

Функцыя не возвращает значений.

4. ТЕСТИРОВАНИЕ ПРОГРАММЫ

4.1 Ошибки выявленные при тестировании

С целью тестирования приложения был осуществлён запуск USBDrvReader. exe. После запуска приложение успешно загружало Fat32Info. dll.

4.1.1 Ошибка вызванная отсутствием выравнивания полей fat_boot_sector

В ходе разработки и тестирования проекта было установлено, что программа некорректно отображает поля некоторые поля BOOT. Тестирование показала что ошибка проиходила в функции ReadBoot Fat32Info. dll. Пошаговое прохождение алгоритма показало некорректное считывание полей в ReadFile — при считывании происходил здвиг данных в пределах структуры fat_boot_sector. Ппоблемма была устранена выравниванием полей структуры посредством дурективы #pragma pack (1).

4.1.2 Ошибка вызванная некорректным ID контрола диалогового окна

В ходе тестирования приложения в режме динамического изменения размеров окна было обнаружено, что элемент StaticText IDC_SHOW_GETDRV не изменяет своих размеров, в то время как остальные элементы окна изменяли свои размеры синхронно с размерами окна. Детальный анализ показал, что GetDlgItem (hDlg, IDC_SHOW_GETDRV) не возвращает HWND элемента. Анализ resource. h показал что IDC_SHOW_GETDRV по какой-то причине имел ID -1. После присваивания IDC_SHOW_GETDRV ID 32 775 GetDlgItem начал возвращать дескриптор элемента. Посредством MoveWindow начало происходить коректное изменение размеров контрола синхронно с размерами окна.

4.2 Конечное тестирование приложения

После устранения ошибки п 4.1.1. — 4.1.2 работа приложения начала происходить корректно. Результаты работы приложения для съёмного носителя Transcend 8Gb приведены ниже

Рисунок 4.1 — Дамп и расшифровка BOOT FAT32

Рисунок 4.2 — Дамп и расшифровка таблицы FAT

Рисунок 4.3 — Дамп и расшифровка ROOT

Как видно из рисунков USBDrvReader. exe и DLL-модуль Fat32Info. dll полностью решают поставленную задачу получения и расшифровки основных структурных элементов FAT32.

ВЫВОДЫ

В процессе работы были созданы DLL-модуль Fat32Info. dll и приложение-тетер USBDrvReader. exe с целью получения информации основных разделов FAT32. В качестве исследуемой модели применялась файловая система съёмного накопителя Transcend 8Gb.

В результате тестирования были получены и расшифрованы дампы BOOT, FAT и ROOT/

Для программирования использовалась среда «Microsoft Visual C++ 2008 Full Editional». Разработан алгоритм программы, наиболее оптимально отражаю-щий основную идею проекта.

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

СПИСОК ИСТОЧНИКОВ

1) Гордеев А. В. Операционные системы. 2-е издание. — СПб: Питер, 2005;

2) Молчанов А. Ю. Системное программное обеспечение. — СПб.: Питер, 2003;

3) MSDN Library Visual Studio 6. 0;

4) Ганеев Р. М. Проектирование интерфейса пользователя средствами Win32API;

5) Круглинский Д., Уингоу С., Шеферд Дж. Программирование на Visuale C++6.0 для профессионалов, СПб: Питер, 2001;

6) Майкл Дж. Янг Visual C++. Полное руководство;

7) http: //support. microsoft. com/kb/140 418/ru.

ПРИЛОЖЕНИЕ, А — Графическая часть

КП--- -PО-2012

Изм.

Лист

№ документа

Подпись

Дата

Разраб.

Структура FAT32

Лит

Лист

Листов

Руковод.

Д

1

3

Консульт.

1 40 01 02 БНТУ

г. Минск

Н. контр.

Зав. каф.

Приложение Б — Листинг DLL-модуля Fat32Info. dll

Листинг Fat32Def. h

#include «stdafx. h»

#pragma pack (1)

struct TExtFlags

{

USHORT Rezerv8: 8; //зарезервировано

USHORT ActivFat: 1; //0 или 1

USHORT Reserv3: 3; //зарезервировано

USHORT ActivNumbFat: 4; //номер активной Fat

};

#pragma pack (1)

struct TFSVer

{

BYTE NumbVers; //номер версии

BYTE NumbPromVers; //номер промежуточной версии

};

#pragma pack (1)

struct fat_boot_sector

{

BYTE JmpBoot[3]; //команда JMP — ближний переход на програм-му начальной загрузки

char OEMName[8]; //имя OEM в кодировке ASCII

//расширенный блок параметров BIOS (BPB)

USHORT KolvoByteSect; //количество байтов в одном секторе

BYTE KolvoSectKlast; //количество секторов в одном кластере

USHORT KolvoRezSect; //количество зарезервированных секторов

BYTE KolvoFat; //количсетво FAT

USHORT MaxKolvohFileRoot; //max кол-во дескрипторов файлов в корневом ката-логе диска

USHORT GeneralKolvoSect; //общее количество секторов на носителе данных

BYTE Media; //байт-описатель среды носителя дан-ных (media)

USHORT KolvoFatSect16; //16-разрядный размер (в секторах) каждой копии FAT в FAT12 и FAT16. В FAT32 поле равно 0

USHORT KolvoSectTrack; //кол-во секторов на дорожке

USHORT KolvoHead; //кол-во магнитных головок

UINT KolvoHiddenSect; //кол-во скрытых секторов, для носителя размером < 32 Мб

UINT KolvoHiddenSect32; //кол-во скрытых секторов, для носителя размером — 32 Мб

UINT KolvoFatSect32; //32-разрядный размер одной копии FAT (в секторах)

TExtFlags ExtFlags; //только для FAT32

TFSVer FSVer; //только для FAT32

UINT RootClas; //номер первого кластера корневой директо-рии

USHORT FSInfo; //номер сектора со структурой FSINFO в зарезервированной части FAT32. Обычно 1.

USHORT BkBootSee; //номер сектора в резервной области диска, где хранится копия boot сектора

BYTE Rezerved[12]; //зарезервировано

BYTE DrvNumb; //номер диска BIOS INT13h

BYTE Rezerved1; //не используется

BYTE BootSig; //расширенная сигнатура, которая показыва-ет, действительны ли следующие три значения

UINT VolID; //серийный номер тома

char VolLab[11]; //метка тома в кодировке ASCII

char FilSysType[8]; //метка типа файловой системы в кодировке ASCII.

BYTE RezervedFat[420]; //не используется

USHORT Signatura; //сигнатура (0xAA55)

};

#pragma pack (1)

struct TFileAttributes

{

BYTE ReadOnly: 1; //файл предназначен только для чтения, его нельзя стирать

BYTE Hidden: 1; //скрытый файл

BYTE System: 1; //системный файл

BYTE MarkDisk: 1; //метка диска

BYTE SubDirectory: 1; //описывает файл, являющейся подкаталогом данного катало-га

BYTE FlagArchiv: 1; //флаг архивации

BYTE Rezerv1: 1; //зарезервирован

BYTE Rezerv2: 1; //зарезервирован

};

//время создания файла

#pragma pack (1)

struct TFTime

{

USHORT Seconds: 5; //секунды

USHORT Minutes: 6; //минуты

USHORT Hours: 5; //часы

};

//дата создания файла

#pragma pack (1)

struct TFDate

{

USHORT Day: 5; //день

USHORT Month: 4; //месяц

USHORT Year: 7; //год

};

//структура корневого каталога

#pragma pack (1)

struct TROOT

{

char Name[8]; //имя файла

char Expansion[3]; //расширение файла

TFileAttributes FAtr; //атрибуты файла

BYTE Reserved; //зарезервировано

BYTE Ms; //десятые доли секунды

TFTime FTime; //время создания файла

TFDate FDate; //дата создания файла

TFDate DateLast; //дата последнего доступа

USHORT HighByte; //старшие 2 байта номера первого кластера в FAT32

TFTime ModifiedTime; //время последнего изменения

TFDate ModifiedDate; //дата последнего изменения

USHORT LowByte; //младшие два байта номера первого кластера

UINT SizeFile; //размер файла

};

Листинг Fat32Info. срр

// Fat32Info. cpp: Defines the entry point for the DLL application.

//

#include «stdafx. h»

#include «Fat32Def. h»

#include < stdio. h>

#ifdef __cplusplus

#define EXPORT extern «C» __declspec (dllexport)

#else

#define EXPORT __declspec (dllexport)

#endif

EXPORT void ReadBoot (HWND hDlg, UINT IDC_DAMP, UINT IDC_DATA, LPCTSTR path);

EXPORT void ReadTable (HWND hDlg, UINT IDC_DAMP, UINT IDC_DATA, LPCTSTR path);

EXPORT void ReadRoot (HWND hDlg, UINT IDC_DAMP, UINT IDC_DATA, LPCTSTR path, UINT IDC_N, UINT IDC_CHAIN, int pos);

BOOL APIENTRY DllMain (HANDLE hModule,

DWORD ul_reason_for_call,

LPVOID lpReserved

)

{

return TRUE;

}

void ReadBoot (HWND hDlg, UINT IDC_DAMP, UINT IDC_DATA, LPCTSTR path)

{

int i;

DWORD vLength;

fat_boot_sector sB;

char buffer[16*1024] = {0};

ZeroMemory (& sB, sizeof (sB));

HANDLE hBoot = CreateFile (path,

GENERIC_READ,

FILE_SHARE_READ,

NULL,

OPEN_EXISTING,

FILE_ATTRIBUTE_NORMAL,

NULL);

if (hBoot ≠INVALID_HANDLE_VALUE)

{

SetFilePointer (hBoot, 0, NULL, FILE_BEGIN);

ReadFile (hBoot,& sB, 512,&vLength, NULL);

BYTE tFile[512];

SetFilePointer (hBoot, 0, NULL, FILE_BEGIN);

ReadFile (hBoot, & tFile, 512, & vLength, NULL);

for (i=0; i< 512; i++)

sprintf (& buffer[i*3],"%02X «, tFile[i]);

SetDlgItemText (hDlg, IDC_DAMP, buffer);

VirtualFree (tFile, 0, MEM_RELEASE);

i = sprintf (buffer, «Загрузочный сектор: rn»);

i += sprintf (buffer+i, «Команда JMP: %X %X %Xrn», sB. JmpBoot[0], sB. JmpBoot[1], sB. JmpBoot[2]);

i += sprintf (buffer+i, «Фирма-изготовителя ОС и версия: %srn», sB. OEMName);

i += sprintf (buffer+i, «Количество байтов в одном секторе: %urn», sB. KolvoByteSect);

i += sprintf (buffer+i, «Количество секторов в одном кластере: %urn», sB. KolvoSectKlast);

i += sprintf (buffer+i, «Количество зарезервированных секторов: %urn», sB. KolvoRezSect);

i += sprintf (buffer+i, «Количсетво FAT: %urn», sB. KolvoFat);

i += sprintf (buffer+i, «Макс. кол-во дескрипторов корневом каталоге: %urn», sB. MaxKolvohFileRoot);

i += sprintf (buffer+i, «Общее количество секторов на носителе данных: %urn», sB. GeneralKolvoSect);

i += sprintf (buffer+i, «Описатель среды носителя данных (media): %Xrn», sB. Media);

i += sprintf (buffer+i, «16-разрядный размер (в секторах): %urn», sB. KolvoFatSect16);

i += sprintf (buffer+i, «Кол-во секторов на дорожке: %urn», sB. KolvoSectTrack);

i += sprintf (buffer+i, «Кол-во магнитных головок: %urn», sB. KolvoHead);

i += sprintf (buffer+i, «Кол-во скрытых секторов (если < 32 Мб): %urn», sB. KolvoHiddenSect);

i += sprintf (buffer+i, «Кол-во скрытых секторов (если 32 Мб): %urn», sB. KolvoHiddenSect32);

i += sprintf (buffer+i, «32-разрядный размер FAT (в секторах): %urn», sB. KolvoFatSect32);

i += sprintf (buffer+i, «Номер активной FAT: %urn», sB. ExtFlags. ActivNumbFat);

i += sprintf (buffer+i, «Зарезервировано: %urn», sB. ExtFlags. Reserv3);

i += sprintf (buffer+i, «0-FAT зерк-ся, 1-активна только одна FAT: %urn», sB. ExtFlags. ActivFat);

i += sprintf (buffer+i, «Зарезервировано: %urn», sB. ExtFlags. Rezerv8);

i += sprintf (buffer+i, «Номер версии: %urn», sB. FSVer. NumbVers);

i += sprintf (buffer+i, «Номер промежуточной версии: %urn», sB. FSVer. NumbPromVers);

i += sprintf (buffer+i, «Номер первого кластера корневой директории: %urn», sB. RootClas);

i += sprintf (buffer+i, «Номер сектора с FSINFO в FAT32: %urn», sB. FSInfo);

i += sprintf (buffer+i, «Ном. сектора с копией boot сектора: %urn», sB. BkBootSee);

i += sprintf (buffer+i, «Зарезервировано: %u bytesrn», sizeof (sB. Rezerved));

i += sprintf (buffer+i, «Номер диска BIOS INT13h: %urn», sB. DrvNumb);

i += sprintf (buffer+i, «Не используется: %u bytesrn», sizeof (sB. Rezerved1));

i += sprintf (buffer+i, «Действ-ны ли след. три значения: %urn», sB. BootSig);

i += sprintf (buffer+i, «-Серийный номер тома: %Xrn», sB. VolID);

i += sprintf (buffer+i, «-Метка тома в кодировке ASCII: %. 11srn», sB. VolLab);

i += sprintf (buffer+i, «-Метка типа файловой системы в кодировке ASCII: %. 8srn», sB. FilSysType);

i += sprintf (buffer+i, «Не используется: %u bytesrn», sizeof (sB. RezervedFat));

i += sprintf (buffer+i, «Сигнатура (0xAA55): 0x%X», sB. Signatura);

SetDlgItemTextA (hDlg, IDC_DATA, buffer);

CloseHandle (hBoot);

}

else

MessageBox

(

hDlg,

«Не могу прочитать загрузочный сектор!»,

NULL,

MB_ICONERROR | MB_OK | MB_SYSTEMMODAL

);

}

void ReadTable (HWND hDlg, UINT IDC_DAMP, UINT IDC_DATA, LPCTSTR path)

{

int i, j, offset;

DWORD vLength;

UINT Fat[128] = {0};

fat_boot_sector sB;

ZeroMemory (& sB, sizeof (sB));

char buffer[16*1024] = {0};

HANDLE hFleshka = CreateFile

(

path,

GENERIC_READ,

FILE_SHARE_READ,

NULL,

OPEN_EXISTING,

FILE_ATTRIBUTE_NORMAL,

NULL

);

if (hFleshka ≠INVALID_HANDLE_VALUE)

{

SetFilePointer (hFleshka, 0, NULL, FILE_BEGIN);

ReadFile (hFleshka,& sB, 512,&vLength, NULL);

offset = sB. KolvoRezSect*sB. KolvoByteSect; //смещение Fat

BYTE tFile[512];

SetFilePointer (hFleshka, offset, NULL, FILE_BEGIN);

ReadFile (hFleshka, & tFile, 512, & vLength, NULL);

for (i=0; i< 512; i++)

{

sprintf (& buffer[i*3],"%02X «, tFile[i]);

}

SetDlgItemText (hDlg, IDC_DAMP, buffer);

SetFilePointer (hFleshka, offset, NULL, FILE_BEGIN);

ReadFile (hFleshka, & Fat, 512, & vLength, NULL);

j = sprintf (buffer, «Расшифровка таблицы FAT: rn»);

for (i=0; i< 128; i++)

{

if (Fat[i] == 0×0)

j += sprintf (buffer+j, «0x%08X: свободный кластерrn», Fat[i]);

if (Fat[i] == 0×1)

j += sprintf (buffer+j, «0x%08X: зарезервированный кластерrn», Fat[i]);

if ((Fat[i] > 0×1) & & (Fat[i] < (0x0FFFFFEF+1)))

j += sprintf (buffer+j, «0x%08X: указатель на следующий кла-стерrn», Fat[i]);

if ((Fat[i] > 0x0FFFFFEF) & & (Fat[i] < 0x0FFFFFF7))

j += sprintf (buffer+j, «0x%08X: зарезервированный кластерrn», Fat[i]);

if ((Fat[i] == 0x0FFFFFF7))

j += sprintf (buffer+j, «0x%08X: повреждённый кластерrn», Fat[i]);

if ((Fat[i] > 0x0FFFFFF7) & & (Fat[i] < 0×10 000 000))

j += sprintf (buffer+j, «0x%08X: последний кластер в файлеrn», Fat[i]);

if (Fat[i] == 0xFFFFFFFF)

j += sprintf (buffer+j, «0x%08X: последний кластер в файлеrn», Fat[i]);

}

SetDlgItemText (hDlg, IDC_DATA, buffer);

CloseHandle (hFleshka);

VirtualFree (buffer, 0, MEM_RELEASE);

VirtualFree (Fat, 0, MEM_RELEASE);

}

else

MessageBox

(

hDlg,

«Не могу прочитать таблицы FAT!»,

NULL,

MB_ICONERROR | MB_OK | MB_SYSTEMMODAL

);

}

void ReadRoot (HWND hDlg, UINT IDC_DAMP, UINT IDC_DATA, LPCTSTR path, UINT IDC_N, UINT IDC_CHAIN, int pos)

{

int i, offset;

UINT Fat[256] = {0};

DWORD vLength, allLength;

char temp[256]= {0};

fat_boot_sector sB;

ZeroMemory (& sB, sizeof (sB));

unsigned long currentCell;

char buffer[16*1024] = {0};

TROOT sR[32];

ZeroMemory (& sR, sizeof (sR));

int nzap=0;

HANDLE hFleshka = CreateFile

(

path,

GENERIC_READ,

FILE_SHARE_READ,

NULL,

OPEN_EXISTING,

FILE_ATTRIBUTE_NORMAL,

NULL

);

if (hFleshka ≠INVALID_HANDLE_VALUE)

{

SetFilePointer (hFleshka, 0, NULL, FILE_BEGIN);

ReadFile (hFleshka,& sB, sizeof (sB),&vLength, NULL);

offset = sB. KolvoRezSect*sB. KolvoByteSect+sB. KolvoByteSect*sB. KolvoFatSect32*sB. KolvoFat;

SetFilePointer (hFleshka, offset, NULL, FILE_BEGIN);

ReadFile (hFleshka, & sR, 1024, & allLength, NULL);

nzap=0;

while ((sR[nzap]. Name[0])&&(pos<32))

{

nzap++;

}

if (pos> =nzap)

pos=nzap-1;

if (pos<0)

pos=0;

SetDlgItemInt (hDlg, IDC_N, pos+1, false);

BYTE tFile[512];

SetFilePointer (hFleshka, offset, NULL, FILE_BEGIN);

ReadFile (hFleshka, & tFile, 512, & vLength, NULL);

for (i=0; i< 512; i++)

{

sprintf (& buffer[i*3],"%02X «, tFile[i]);

}

SetDlgItemText (hDlg, IDC_DAMP, buffer);

VirtualFree (tFile, 0, MEM_RELEASE);

i= sprintf (buffer, «---Cтруктура одного файла корневой директории: rn»);

OemToChar (sR[pos]. Name, sR[pos]. Name);

i += sprintf (buffer+i, «Имя файла: %. 8srn», sR[pos]. Name);

i += sprintf (buffer+i, «Расширение файла: %. 3srn», sR[pos]. Expansion);

i += sprintf (buffer+i, «Файл предназначен только для чтения, его нельзя сти-рать: %srn», sR[pos]. FAtr. ReadOnly? «да»: «нет»);

i += sprintf (buffer+i, «Скрытый файл: %srn», sR[pos]. FAtr. Hidden? «да»: «нет»);

i += sprintf (buffer+i, «Системный файл: %srn», sR[pos]. FAtr. System? «да»: «нет»);

i += sprintf (buffer+i, «Метка диска: %srn», sR[pos]. FAtr. MarkDisk? «да»: «нет»);

i += sprintf (buffer+i, «Подкаталог данного каталога: %srn», sR[pos]. FAtr. SubDirectory? «да»: «нет»);

i += sprintf (buffer+i, «Флаг архивации: %srn», sR[pos]. FAtr. FlagArchiv? «да»: «нет»);

i += sprintf (buffer+i, «Зарезервирован: %srn», sR[pos]. FAtr. Rezerv1? «да»: «нет»);

i += sprintf (buffer+i, «Зарезервирован: %srn», sR[pos]. FAtr. Rezerv2? «да»: «нет»);

i += sprintf (buffer+i, «Зарезервировано: %urn», sR[pos]. Reserved);

i += sprintf (buffer+i, «Время создания файла: %02u: %02u:%02urn», sR[pos]. FTime. Hours, sR[pos]. FTime. Minutes, sR[pos]. FTime. Seconds);

i += sprintf (buffer+i, «Дата создания файла: %u: %u:%urn», sR[pos]. FDate. Day, sR[pos]. FDate. Month, sR[pos]. FDate. Year+1980);

i += sprintf (buffer+i, «Дата последнего доступа: %u: %u:%urn», sR[pos]. DateLast. Day, sR[pos]. DateLast. Month, sR[pos]. DateLast. Year+1980);

i += sprintf (buffer+i, «Старшие 2 байта номера первого кластера в FAT32: 0x%04Xrn», sR[pos]. HighByte);

i += sprintf (buffer+i, «Время последнего изменения: %02u: %02u:%02urn», sR[pos]. ModifiedTime. Hours, sR[pos]. ModifiedTime. Minutes, sR[pos]. ModifiedTime. Seconds);

i += sprintf (buffer+i, «Дата последнего изменения: %u: %u:%urn», sR[pos]. ModifiedDate. Day, sR[pos]. ModifiedDate. Month, sR[pos]. ModifiedDate. Year+1980);

i += sprintf (buffer+i, «Младшие два байта номера первого кластера: 0x%04Xrn», sR[pos]. LowByte);

i += sprintf (buffer+i, «Размер файла: %u», sR[pos]. SizeFile);

SetDlgItemText (hDlg, IDC_DATA, buffer);

SetFilePointer (hFleshka, offset, NULL, FILE_BEGIN);

ReadFile (hFleshka, & Fat, 512, & vLength, NULL);

CloseHandle (hFleshka);

VirtualFree (buffer, 0, MEM_RELEASE);

if (sR[pos]. Name[0]==-27)

SetDlgItemText (hDlg, IDC_CHAIN, «Файл удален!»);

else

{

currentCell=sR[pos]. HighByte;

currentCell*=65 536;

currentCell+=sR[pos]. LowByte;

sprintf (buffer, «0x%08X», currentCell);

ПоказатьСвернуть
Заполнить форму текущей работой