
- •Лекция №7-8. Подсистема в/в. Пакеты запросов ввода/вывода (irp). [7.1] Подсистема в/в и её характеристики.
- •[7.2] Структура irp
- •[7.2.1] Поля в Фиксированной части irp.
- •[7.2.2.] Поля в Стеке размещения Ввода - вывода irp.
- •[7.3] Описание Буфера Данных
- •[7.4] Коды Функции Ввода - вывода
- •[8.1] Передача данных посредством irp и диспетчерские точки входа драйвера
- •[8.1.1] Запросы чтения и записи irp_mj_read и irp_mj_write [8.1.1.1] Определение метода передачи буфера для запросов чтения-записи
- •[8.1.1.2] Получение буфера
- •[8.1.1.3] Завершение запроса в/в
- •[8.1.1.4] Пример обработки запросов чтения/записи
- •[8.1.2.1] Пояснения по использованию
- •[8.1.2.2] Задание кода управления вводом/выводом (ioctl)
- •[8.1.2.3] Получение буфера
- •[8.1.2.4] Завершение запроса в/в
- •[8.1.2.5] Пример обработки
[7.2.2.] Поля в Стеке размещения Ввода - вывода irp.
Каждый Стек размещения Ввода - вывода в IRP содержит информацию для конкретного драйвера относительно запроса Ввода - вывода. Стек размещения Ввода - вывода определяется структурой IO_STACK_LOCATION. Для определения местонахождения текущего Стека Размещения Ввода - вывода внутри данного IRP, драйвер должен использовать функцию IoGetCurrentIrpStackLocation(). Единственным параметром при вызове является указатель на IRP. Возвращаемым значением будет указатель на текущий Стек размещения Ввода - вывода.
Когда Диспетчер Ввода - вывода создает IRP и инициализирует его фиксированную часть, он также инициализирует в IRP первый Стек размещения Ввода - вывода. В него помещается информация, которую нужно передать первому драйверу в стеке драйверов, которые будут обрабатывать этот запрос. Поля в Стеке размещения Ввода - вывода включают следующее:
MajorFunction. Это поле указывает главный код функции в/в, связанный запросом в/в. Тем самым указывается тип операции в/в, которая должна быть выполнена.
MinorFunction. Это поле указывает второстепенный код функции в/в, связанный с запросом. При использовании, это поле переопределяет главный функциональный код. Второстепенные функции используются почти исключительно сетевыми транспортными драйверами и файловыми системами и игнорируются большинством драйверов устройств.
Flags. Это поле содержит флаги обработки, определенные для выполняемой функции в/в. Это поле представляет интерес главным образом для драйверов файловых систем.
Control. Это поле является набором флагов, которые устанавливаются и читаются Диспетчером Ввода - вывода, указывая, как надо обработать данный пакет IRP. Например, в этом поле (обращением драйвера к функции IoMarkIrpPending()) может быть установлен бит SL_PENDING, указывающий Диспетчеру Ввода - вывода, что завершение обработки пакета IRP отложено на неопределенное время. Точно так же флажки sl_invoke_on_cancel, sl_invoke_on_error и sl_invoke_on_success указывают, когда для этого IRP должна быть вызвана Подпрограмма Завершения Ввода - вывода драйвера.
Parameters. Это поле включает несколько подполей, каждое из которых зависит от главной функции Ввода – вывода, которая будет выполняться.
DeviceObject. Это поле содержит указатель на объект-устройство, который является получателем запроса Ввода - вывода.
FileObject. Это поле содержит указатель на объект-файл, связанный с запросом Ввода - вывода.
После того, как фиксированная часть IRP и первый Стек размещения Ввода - вывода в IRP инициализированы, Диспетчер Ввода - вывода вызывает верхний драйвер в стеке драйверов в его точке входа dispatch, которая соответствует главному функциональному коду для запроса. Таким образом, если Диспетчер Ввода - вывода сформировал IRP для описания запроса чтения, он вызовет первый драйвер в стеке драйверов в его диспетчерской точке входа для чтения (IRP_MJ_READ). При этом Диспетчер Ввода - вывода передает следующие параметры:
указатель на IRP, который был только что сформирован;
указатель на обьект-устройство, который соответствует устройству, для которого драйвер должен обработать запрос.