Ответы:
Любой ввод-вывод обрабатывается системным вызовом, вызываемым процессом. В конце концов, такой системный вызов перейдет к некоторой подходящей низкоуровневой функции драйвера устройства для выполнения фактической операции ввода-вывода.
Ввод / вывод может быть сложным - для фактического ввода данных в устройство и из него могут потребоваться различные этапы, в порядке и, возможно, с учетом требований к времени. Если эти шаги не выполняются атомарно, то при следующей попытке устройство может не отвечать, плохо себя вести или даже вызывать зависание системы. Эти шаги могут быть различными и уникальными для каждого устройства, поэтому существует так много драйверов устройств.
Хорошо написанный драйвер устройства должен знать, как обращаться с устройством, которое он пытается обслуживать, поэтому у него обычно не должно возникать проблем, если нет ошибки драйвера, вы используете неправильный драйвер для устройства или физическое устройство выходит из строя.
Теперь, когда я прочитал книгу Мориса Баха «Дизайн операционных систем Unix», позвольте мне самому ответить на этот вопрос.
Короче говоря, обеспечение бесперебойного ввода-вывода имеет целью завершить задачу ввода-вывода КАК МОЖНО СКОРЕЕ, без помех для сигналов.
Некоторые связанные знания, которые я получил из книги:
Некоторые пути кода в ядре помечены как бесперебойные, в основном потому, что код должен соответствовать строгой синхронизации (для ответа на устройство) или потому, что он делает что-то, что не допускает помех. В случае с Linux, большинство из них были вытеснены на независимые шаги в ядре, а вторые были в основном уничтожены (я подозреваю, что в основном под давлением современных многопроцессорных машин). Т.е. прошло уже некоторое время, когда я не видел процесса в непрерывном сне.
write(2)
разрешено возвращать рано, возвращая фактическое записанное количество байтов, которое может быть меньше, чем длина буфера, переданного в качестве 3-го аргумента.