Подсистема ввода / вывода задумывалась как абстрактный интерфейс для связи приложений к аппаратным и программным (виртуальным) устройствам.
Компоненты подсистемы ввода / вывода
Как вы помните, подсистема ввода / вывода работает в режиме ядра. В этой подсистеме работают три диспетчера, которые я опишу ниже.
Во-первых, это диспетчер ввода / вывода. Он обеспечивает связь приложений с устройствами. То есть приложения напрямую с оборудованием не работают. Они лишь могут отправлять запросы этому диспетчеру. А уже он, в свою очередь, передает эти запросы драйверам. Такие запросы называются IRP и они могут помещаться в специальный буфер запросов.
В свою очередь драйверы через этот диспетчер могут общаться друг с другом. Например при записи файла на диск, будут вместе работать драйвер файловой системы и драйвер диска.
Во-вторых, это диспетчер PnP. Он работает вместе с диспетчером ввода / вывода и с драйвером шины. Именно он обеспечивают загрузку необходимого драйвера при обнаружении нового устройства.
В-третьих, это диспетчер электропитания. Он тоже тесно связан с диспетчером ввода / вывода. Он управляет переходами оборудования в различные состояния энергосбережения через драйвера устройств.
Помимо всего прочего такая подсистема ввода / вывода обрабатывает асинхронные запросы от оборудования, которые называются прерываниями. Для этого используется процедура обслуживания прерываний (ISR).
Прерывания
Каждое устройство в системе получает свой номер IRQ. Посмотреть список таких номеров IRQ, вы можете в программе «Сведения о системе«. Запустите её и перейдите в меню «Аппаратные ресурсы» / «Прерывания (IRQ)«:
На самом деле IRQ (Interrupt request) — это номер прерывания. А устройства просто используют разные номера.
Суть прерываний в следующем. Процессор обрабатывает какой-то код в обычном режиме. В это время с оборудованием происходит какое-то событие, например вы передвинули мышку. Процессор получает сигнал о том что нужно прервать свою текущую работу и обработать запрос от оборудования. Этот запрос вызывает функцию, которая называется обработчиком прерывания (ISR). И процессор начинает обрабатывать этот ISR. И только после обработки ISR, он возвращается к обработки той задачи, на которой был прерван.
Прерывания могут быть:
- Асинхронные — это прерывания исходящие от внешних устройств. Они могут произойти в любой момент.
- Синхронные — это события в самом процессоре, которые могут произойти при различных условиях. Например, при делении на ноль, при переполнение стека, при обращении к недопустимым адресам памяти.
Прерывания позволяют операционной системе использовать процессор максимально эффективно, совмещая основную работу с операциями ввода / вывода.
При всем этом разное оборудование имеет разные приоритеты прерываний, которые называются IRQL (Interrupt Request Level). Суть в том чтобы более приоритетные прерывания могли прервать менее приоритетные, но не наоборот.
Для разных архитектур используются разные IRQL. Архитектура x64 для оборудования выделяет уровни от 3 до 12. Выше находятся, например IPI прерывания, когда один процессор может прервать работу другого. А ниже программные прерывания.
А когда процессор не обслуживает прерывания, то он работает на нулевом уровне.