Случилось так, что пришлось мне писать с нуля драйвер для usb дисплея под windows. Имея возможность — расскажу о деталях столь занимательного процесса.
![image](https://habrastorage.org/r/w780q1/getpro/habr/post_images/0b4/f04/8da/0b4f048da74aeb691b6042ad38eb7455.jpg)
Итак, почему же шина usb так удобна, и что скрывает за собой слово Universal в расшифровке аббревиатуры.
Раньше, когда программист был вынужден писать драйвер для общения с устройством – он работал непосредственно на уровне шины, грубо говоря — если устройство подключалось 9-жильным проводом, т.к. две из них обычно отводятся под питание — то программист вручную был вынужден контролировать до 7 жил. У каждого устройства было своё представление, как использовать предоставленный ему порт. Например, одно устройство могло передавать данные на компьютер через 1,2 и 5 проводники, использовать 3 и 7 для управления, а 4 и 6 использовались бы для записи данных в устройство, другое устройство могло иметь 2 проводника для передачи данных в обе стороны и 5 для управляющих сигналов.
Всё это необходимо было контролировать во времени, ожидая реакции или готовности устройства. Если же устройство выполняло более чем один вид деятельности – необходимо было знать с каким функционалом мы работаем в данный момент и, исходя из этого, изменять методы работы. В таких условиях отладка была тяжелой, и программисту нужно было учить свой протокол общения по этому порту для каждого устройства. Всё это не могло продолжаться бесконечно, и была изобретена шина usb.
![image](https://habrastorage.org/r/w1560/getpro/habr/post_images/bfd/d86/176/bfdd86176b881f37516d3b2955fe6371.png)
На первой линии обороны нас ждёт уровень интерфейсов, это логическое разделение устройства по выполняемым им задачам, например, если у нас есть внешний дисплей, оборудованный в добавок системой звукового оповещения – наше устройство вполне может иметь пару интерфейсов, один для работы с дисплеем, другой для работы со звуком, и, например, третий – для перепрошивки самого устройства.
Если мы будем рассматривать написание драйвера под windows с использованием последнего драйвер-фреймворка (WDF), то узнать количество интерфейсов и получить доступ к ним можно при помощи пары строк кода.
Интерфейс – не единственный уровень разделения, существующий в USB, каждый интерфейс подразделяется на набор так называемых конечных(концевых) точек (endpoint).
Предположим что мы можем как записывать картинку на дисплей – так и читать текущую картинку с дисплея, в таком случае одна концевая точка будет использоваться для чтения, другая – для записи. Помимо направления передачи данных (In/Out) концевая точка имеет ещё одно достаточно полезное свойство, это тип передачи, который имеет одно из следующих значений:
• управляющие передачи – используются хостом для конфигурирования устройства во время подключения, для управления устройством и получения статусной информации в процессе работы. Протокол обеспечивает гарантированную доставку таких посылок;
• передачи массивов данных (Bulk Data Transfers) – применяются при необходимости обеспечения гарантированной доставки данных от хоста к функции или от функции к хосту, но время доставки не ограничено;
• передачи по прерываниям – используются в том случае, когда требуется передавать одиночные пакеты данных небольшого размера. Каждый пакет требуется передать за ограниченное время. Операции передачи носят спонтанный характер и должны обслуживаться не медленнее, чем того требует устройство;
• изохронные передачи – применяются для обмена данными в «реальном времени», когда на каждом временном интервале требуется передавать строго определенное количество данных, но доставка информации не гарантирована (передача данных ведется без повторения при сбоях, допускается потеря пакетов).
Помимо концевых точек, определяемых непосредственно логикой устройства, одна (нулевая) концевая точка определяется непосредственно протоколом, любое usb устройство обязано иметь нулевую концевую точку. Именно благодаря этому как только вы подключаете устройство к компьютеру – операционная система сразу распознаёт название этого устройства, и пытается найти к нему драйвер, без этой стандартной концевой точки получение информации об устройстве при отсутствии драйвера было бы невозможным.
![image](https://habrastorage.org/r/w1560/getpro/habr/post_images/478/160/cfc/478160cfc87b8afa2ecd28272022f627.png)
Это – всё что необходимо знать о шине для того, чтобы написать свой первый драйвер, чем мы и займёмся в следующей статье.
Комплект для разработки драйверов для операционных системы Windows XP, Vista, 7 – можно скачать по ссылке: комплект разработчика.
В следующей части: обработка событий, связанных с устройством, работа с подсветкой из прикладного приложения, и немного реверс-инжиниринга.
Фотография будущего пациента:
![image](https://habrastorage.org/r/w780q1/getpro/habr/post_images/18c/a2a/caa/18ca2acaad99d4202289abaf7c01550b.jpg)
![image](https://habrastorage.org/getpro/habr/post_images/0b4/f04/8da/0b4f048da74aeb691b6042ad38eb7455.jpg)
USB – это simple
Несмотря на то, что написание драйверов считается достаточно трудным, в сравнении с прикладным программированием – и в этом низкоуровневом мире программисты не были обделены вниманием, большим шагом в упрощении создания драйверов стала разработка шины usb.Итак, почему же шина usb так удобна, и что скрывает за собой слово Universal в расшифровке аббревиатуры.
Раньше, когда программист был вынужден писать драйвер для общения с устройством – он работал непосредственно на уровне шины, грубо говоря — если устройство подключалось 9-жильным проводом, т.к. две из них обычно отводятся под питание — то программист вручную был вынужден контролировать до 7 жил. У каждого устройства было своё представление, как использовать предоставленный ему порт. Например, одно устройство могло передавать данные на компьютер через 1,2 и 5 проводники, использовать 3 и 7 для управления, а 4 и 6 использовались бы для записи данных в устройство, другое устройство могло иметь 2 проводника для передачи данных в обе стороны и 5 для управляющих сигналов.
Всё это необходимо было контролировать во времени, ожидая реакции или готовности устройства. Если же устройство выполняло более чем один вид деятельности – необходимо было знать с каким функционалом мы работаем в данный момент и, исходя из этого, изменять методы работы. В таких условиях отладка была тяжелой, и программисту нужно было учить свой протокол общения по этому порту для каждого устройства. Всё это не могло продолжаться бесконечно, и была изобретена шина usb.
Структура шины
Первое, что можно увидеть при работе с usb устройствами в современных ОС – вам больше не нужно работать физически с портом передачи данных. Итак – давайте посмотрим что же представляет из себя произвольное usb устройство в первом приближении:![image](https://habrastorage.org/getpro/habr/post_images/bfd/d86/176/bfdd86176b881f37516d3b2955fe6371.png)
На первой линии обороны нас ждёт уровень интерфейсов, это логическое разделение устройства по выполняемым им задачам, например, если у нас есть внешний дисплей, оборудованный в добавок системой звукового оповещения – наше устройство вполне может иметь пару интерфейсов, один для работы с дисплеем, другой для работы со звуком, и, например, третий – для перепрошивки самого устройства.
Если мы будем рассматривать написание драйвера под windows с использованием последнего драйвер-фреймворка (WDF), то узнать количество интерфейсов и получить доступ к ним можно при помощи пары строк кода.
Интерфейс – не единственный уровень разделения, существующий в USB, каждый интерфейс подразделяется на набор так называемых конечных(концевых) точек (endpoint).
Предположим что мы можем как записывать картинку на дисплей – так и читать текущую картинку с дисплея, в таком случае одна концевая точка будет использоваться для чтения, другая – для записи. Помимо направления передачи данных (In/Out) концевая точка имеет ещё одно достаточно полезное свойство, это тип передачи, который имеет одно из следующих значений:
• управляющие передачи – используются хостом для конфигурирования устройства во время подключения, для управления устройством и получения статусной информации в процессе работы. Протокол обеспечивает гарантированную доставку таких посылок;
• передачи массивов данных (Bulk Data Transfers) – применяются при необходимости обеспечения гарантированной доставки данных от хоста к функции или от функции к хосту, но время доставки не ограничено;
• передачи по прерываниям – используются в том случае, когда требуется передавать одиночные пакеты данных небольшого размера. Каждый пакет требуется передать за ограниченное время. Операции передачи носят спонтанный характер и должны обслуживаться не медленнее, чем того требует устройство;
• изохронные передачи – применяются для обмена данными в «реальном времени», когда на каждом временном интервале требуется передавать строго определенное количество данных, но доставка информации не гарантирована (передача данных ведется без повторения при сбоях, допускается потеря пакетов).
Помимо концевых точек, определяемых непосредственно логикой устройства, одна (нулевая) концевая точка определяется непосредственно протоколом, любое usb устройство обязано иметь нулевую концевую точку. Именно благодаря этому как только вы подключаете устройство к компьютеру – операционная система сразу распознаёт название этого устройства, и пытается найти к нему драйвер, без этой стандартной концевой точки получение информации об устройстве при отсутствии драйвера было бы невозможным.
![image](https://habrastorage.org/getpro/habr/post_images/478/160/cfc/478160cfc87b8afa2ecd28272022f627.png)
Заключение
Все данные передаются по двум проводникам внутри usb кабеля (ещё 2 отводятся под питание), это позволяет использовать единый разъём для всех usb устройств.Это – всё что необходимо знать о шине для того, чтобы написать свой первый драйвер, чем мы и займёмся в следующей статье.
Комплект для разработки драйверов для операционных системы Windows XP, Vista, 7 – можно скачать по ссылке: комплект разработчика.
В следующей части: обработка событий, связанных с устройством, работа с подсветкой из прикладного приложения, и немного реверс-инжиниринга.
Фотография будущего пациента:
![image](https://habrastorage.org/getpro/habr/post_images/18c/a2a/caa/18ca2acaad99d4202289abaf7c01550b.jpg)