5.11.2. Блочные устройства
Блочными устройствами называются такие устройства, на которых DOS может организовать файловую систему. DOS не работает напрямую с дисками через BIOS, а только с драйверами блочных устройств, каждое из которых представляется системе как линейный массив секторов определенной длины (обычно 512 байт) с произвольным доступом (для BIOS, к примеру, диск - это четырехмерный массив секторов, дорожек, цилиндров и головок). Каждому загруженному устройству DOS присваивает один или несколько номеров логических дисков, которые соответствуют буквам, используемым для обращения к ним. Так, стандартный драйвер дисков получает буквы А, В, С и так далее, по числу видимых разделов на диске.
Рассмотрим атрибуты и команды, передающиеся блочным устройствам^
Атрибуты:
бит 15: 0 (признак блочного устройства)
бит 14: поддерживаются IOCTL-чтение и запись
бит 13: не требует копию первого сектора FAT, чтобы построить ВРВ
бит 12: сетевой диск
бит 11: поддерживает команды открыть/закрыть устройство и проверить, является ли устройство сменным биты 10-8: 000
бит 7: поддерживается проверка поддержки IOCTL
бит 6: поддерживается обобщенный IOCTL и команды установить и определить номер логического диска биты 5-2: 0000
бит поддерживаются номера секторов
бит 0: О
Команды и структура переменной части буфера запроса для них (только то, что отличается от аналогичных структур для символьных устройств):
ООЬ: инициализация +ОВЪ: - байт количество устройств, которые поддерживает драйвер +12Ь: 4 - байта дальний адрес массива ВРВ-структур (по одной для каждого устройства)
ВРВ - это 25-байтная структура (53 для БАТ32), которая описывает блочное устройство. Ее можно найти по смещению ОВЬ от начала нулевого сектора на любом диске:
+Q: 2 байта +2: байт
+3: 2 байта
+5: байт
+6: +8:
2 байта 2 байта
+OAh: байт
+OBh: 2 байта +0Dh:2 байта ■ +OFh: 2 байта +llh: 4 байта ■ +15h: 4 байта ■
число байтов в секторе (обычно 512)
число секторов в кластере (DOS выделяет пространство на диске для файлов не секторами, а обычно более крупными единицами - кластерами. Даже самый маленький файл занимает один
кластер)
число секторов до начала FAT (обычно один - загрузочный) число копий FAT (обычно 2) (FAT - это список кластеров, в которых расположен каждый файл. DOS делает вторую копию, чтобы можно было восстановить диск, если произошел сбой во время модификации FAT)
максимальное число файлов в корневой директории ■ число секторов на устройстве (если их больше 65 536 - здесь записан 0)
- описатель носителя (OF8h - для жестких дисков, OFOh - для дискет на 1,2 и 1,44 Мб, а также других устройств)
- число секторов в одной копии FAT (0, если больше 65 535)
число секторов на дорожке (для доступа средствами BIOS)
число головок (для доступа средствами BIOS) число скрытых секторов 32-битное число секторов на диске
(следующие поля действительны только для дисков, использующих FAT32) +16h: 4 байта - 32-битное число секторов в FAT + ШЬ:байт -флаги
бит 7: не обновлять резервные копии FAT
биты 3-0: номер активной FAT, если бит 7 = 1 +lFh: 2 байта - версия файловой системы (ООООЬдля Windows 95 OSR2) +21h: 4 байта - номер кластера корневой директории
+25h: 2 байта - номер сектора с информацией о файловой системе (OFFFFh, если он отсутствует)
+27h: 2 байта - номер сектора запасной копии загрузочного сектора (OFFFFh,
если отсутствует) +29h: 12 байт - зарезервировано
Для всех остальных команд в поле буфера запроса со смещением + 1 размещается номер логического устройства из числа обслуживаемых драйвером, к которому относится команда:
Olh; проверка носителя +0Dh: байт - на входе - описатель носителя
на выходе - OFFh, если диск был сменен Olh, если диск не был сменен 00h, если это нельзя определить +OFh: 4 байта - адрес ASCIZ-строки с меткой диска (если установлен бит 11 в атрибуте) 02h: построить ВРВ +0Dh: описатель носителя
+0Eh: 4 байта - на входе - дальний адрес копии первого сектора FAT на выходе - дальний адрес ВРВ 03h: IOCTL-чтение (если установлен бит 14 атрибута) Q4h: чтение из устройства
+ODh: байт - описатель носителя
+12h: 2 байта - на входе - число секторов, которые надо прочитать
на выходе - число прочитанных секторов +16h: 2 байта - первый сектор (если больше 65 535 - здесь OFFFFh) +18h: 4 байта — на выходе - адрес метки диска, если произошла ошибка OFh +1СЬ:4байта- первый сектор Q8h: запись в устройство
структура буфера аналогична Q4h с точностью до замены чтения на запись Q9h: запись в устройство с проверкой
аналогично Q8h ОСЬ: IOCTL-запись (если установлен бит 14 атрибута) ODh: открыть устройство (если установлен бит 11 атрибута) OEh: закрыть устройство (если установлен бит 11 атрибута) OFh: проверка наличия сменного диска (если установлен бит 11 атрибута):
драйвер должен установить бит 9 слова состояния, если диск сменный, и сбросить, если нет 13h: обобщенный IOCTL (если установлен бит б атрибута) +ODh: байт - категория устройства: 08h: дисковое устройство 48h: дисковое устройство с FAT32 +0Eh: код - подфункции:
4Qh: установить параметры 6Qh: прочитать параметры 41h: записать дорожку 42h: отформатировать и проверить дорожку 62h: проверить дорожку 46h: установить номер тома 66h: считать номер тома 47h: установить флаг доступа " 67h: прочитать флаг доступа 68h: определить тип носителя (DOS 5.Q+)
4Ah: заблокировать логический диск (Windows 95) 6Ah: разблокировать логический диск (Windows 95) 4Bh: заблокировать физический диск (Windows 95) 6Bh: разблокировать физический диск (Windows 95) 6Ch: ' определить флаг блокировки (Windows 95)
6Dh: перечислить открытые файлы (Windows 95)
6Eh: найти файл подкачки (Windows 95)
6Fh: получить соотношение логических и физических дисков (Windows 95) 70h: получить текущее состояние блокировки (Windows 95) получить адрес первого кластера (Windows 95) + 13h: адрес структуры (аналогично INT 21h АХ = 440Dh) 17h: определить логический диск (если установлен бит 6 атрибута) +0Ш: байт - на входе - номер устройства на выходе - его номер диска 18h: установить логический диск (если установлен бит 6 атрибута) +0Ш: байт - номер устройства
(команды 17пи 18h позволяют DOS обращаться к одному и тому же дисководу как к устройству А: и как к устройству В)
19h: поддержка функций IOCTL (если установлены биты 6 и 7 атрибута)
Для написания своего драйвера блочного устройства можно пользоваться схемой, аналогичной символьному драйверу из предыдущей главы. Единственное важное отличие - процедура инициализации должна будет подготовить и заполнить ВРВ, а также сообщить DOS число устройств, для которых действует этот
драйвер.