p align="left">Поскольку для драйвера важны только адреса рабочих процедур, то все рабочие процедуры могут иметь совершенно произвольные имена. Стандартный прототип таких функций обработки: NTSTATUS IRPControl( IN PDEVICE_OBJECT DeviceObject, // указатель на объект устройства IN PIRP Irp) // указатель на пакет IRP Функции обработки пакетов IRP Функции, адреса которых записаны в массиве MajorFunctions, вызываются диспетчером ввода/вывода для обработки соответствующих запросов от клиентского драйвера (пользовательских приложений или модулей уровня ядра). Эти запросы оформляются в виде специальных структур - IRP пакетов. При любом запросе Диспетчер формирует IRP. Память для структуры IRP выделяется в нестраничной памяти. В IRP записывается код операции ввода вывода. Пакет IRP состоит из заголовка (рис. 2.3), который имеет постоянный размер и стека IRP (рис. 2.4). Стек имеет переменную длину. Заголовок IRP пакета: Поле IoStatus типа IO_STATUS_BLOCK содержит два подполя Status - значение, которое устанавливает драйвер после обработки пакета. В Information - чаще всего число переданных или полученных байт. Поле AssociatedIrp.SystemBuffer типа void* содержит указатель на системный буфер для случая если устройство поддерживает буферизованный ввод/вывод. Поле MdlAddress типа PMDL содержит указатель на MDL список, если устройство поддерживает прямой ввод вывод. Поле UserBuffer типа void* содержит адрес пользовательского буфера для ввода/вывода. Поле Cancel типа BOOLEAN - это индикатор того, что пакет IRP должен быть аннулирован. Рис. 2.3. Заголовок IRP-пакета Стек IRP пакета Основное значение ячеек стека IRP пакета состоит в том, чтобы хранить функциональный код и параметры запроса на ввод/вывод. Для запроса, который адресован драйверу самого нижнего уровня, соответствующий IRP пакет имеет только одну ячейку стека. Для запроса, который послан драйверу верхнего уровня, Диспетчер ввода/вывода создает пакет IRP с несколькими стековыми ячейками - по одной для каждого FDO. Каждая ячейка стека IRP содержит: MajorFunction типа UCHAR - это код, описывающий назначение операции MinorFunction типа UCHAR - это код, описывающий суб-код операции DeviceObject типа PDEVICE_OBJECT - это указатель на объект устройства, которому был адресован данный запрос IRP FileObject типа PFILE_OBJECT - файловый объект для данного запроса Диспетчер ввода/вывода использует поле MajorFunction для того, чтобы извлечь из массива MajorFunction нужную для обработки запроса процедуру. Рис. 2.4 Стек IRP-пакета Функция обработки пакетов IRP_MJ_DEVICE_CONTROL Эта функция позволяет обрабатывать расширенные запросы от клиентов пользовательского режима. Такой запрос может быть сформирован посредством вызова функции DeviceIoControl. Каждый IOCTL запрос имеет свой код. Этот код передается как параметр функции DeviceIoControl. Код IOCTL - это 32-битное число. Запросы IOCTL служат чаще всего для обмена данными между драйвером и приложением. Для передачи данных в Windows предусмотрены 4 способа: METHOD_BUFFERED Входной пользовательский буфер копируется в системный, а по окончании обработки системный копируется в в выходной пользовательский буфер. METHOD_IN_DIRECT и METHOD_OUT_DIRECT Необходимые страницы пользовательского буфера загружаются с диска в оперативную память и блокируются. Используются MDL-списки для доступа к буферу пользователя. METHOD_NEITHER При данном методе передачи не производится проверка доступности памяти, не выделяются промежуточные буфера и не создаются MDL. В пакете IRP передаются виртуальные адреса буферов в пространстве памяти инициатора запроса ввода/вывода. Функция обработки пакетов IRP_MJ_READ Данная функция должна обрабатывать запросы на чтение информации из устройства. Функция обработки пакетов IRP_MJ_PNP Данная функция должна обрабатывать запросы от менеджера PnP. Функция обработки пакетов IRP_MJ_POWER Данная функция должна обрабатывать запросы от менеджера питания. ISR Данная точка входа вызовется когда произойдет прерывание, на которое зарегистрирована эта ISR функция. Вызов может произойти в любом контексте: как ядра, так и пользовательского процесса. Здесь драйвер может либо дожидаться следующего прерывания либо запросить отложенный вызов процедуры DPC (Deferred Procedure Call). 2.4 Приоритеты выполнения программного кода Прерывание требует обработки, поэтому выполнение текущего кода прекращается и управление передается обработчику прерывания. Существуют как аппаратные, так и программные прерывания. Прерывания обслуживаются в соответствии с их приоритетом. Windows NT 5 использует схему приоритетов прерываний, известную под названием «уровни запросов прерываний» (interrupt request levels, IRQL). Всего существует 32 уровня, с 0 (passive), имеющего самый низкий приоритет, по 31 (high), имеющего соответственно самый высокий. Причем, прерывания с IRQL=0 (PASSIVE_LEVEL, уровень нормального исполнения потоков) по IRQL=2 (DISPATCH_LEVEL, планирование потоков и выполнение отложенных процедур) являются программными, а прерывания с IRQL=3 (device 1) по IRQL=31 (HIGH_LEVEL, проверка компьютера и шинные ошибки) являются аппаратными. В любой конкретный момент времени каждая инструкция выполняется на одном определенном уровне IRQL. Прерывание с уровнем IRQL=0, строго говоря, прерыванием не является, так как оно не может прервать работу никакого кода (для этого этот код должен выполняться на еще более низком уровне прерывания, а такого уровня нет). Потоки, работающие на уровне PASSIVE_LEVEL, попадают под управление планировщика заданий (scheduler). Приоритеты, которые различает планировщик заданий для потоков с уровнем PASSIVE_LEVEL, принимают значения от 0 до 31 (MAXIMUM_PRIORITY) и называются приоритетами планирования. Различают Real-Time и Normal приоритеты планирования. Первые продолжают свою работу до тех пор, пока не появится поток с большим приоритетом, так что потоки низких приоритетов должны дожидаться, пока текущий поток Real-Time не завершит работу естественным путем. Потоки с приоритетами Normal планируются по другим правилам. Для работы им выделяется определенный квант процессорного времени, после чего управление передается другим потокам такого же приоритета. Время от времени планировщик может повышать приоритет отложенного потока в пределах диапазона Normal, в результате чего все программные потоки среди потоков этой группы, даже имеющие самые низкие приоритеты, рано или поздно получают управление. 2.5 Стек клавиатуры Физическую связь клавиатуры с шиной осуществляет микроконтроллер клавиатуры Intel 8042. На современных компьютерах он интегрирован в чипсет материнской платы. Этот контроллер может работать в двух режимах: AT-совместимом и PS/2-совместимом. Почти все клавиатуры уже давно являются PS/2-совместимыми. В PS/2-совместимом режиме микроконтроллер клавиатуры также связывает с шиной и PS/2-совместимую мышь. Данным микроконтроллером управляет функциональный драйвер i8042prt. Драйвер i8042prt создает два безымянных объекта «устройство» и подключает один к стеку клавиатуры, а другой к стеку мыши. Поверх драйвера i8042prt, точнее, поверх его устройств, располагаются именованные объекты «устройство» драйверов Kbdclass и Mouclass. Драйверы Kbdclass и Mouclass являются так называемыми драйверами класса и реализуют общую функциональность для всех типов клавиатур и мышей, т.е. для всего класса этих устройств. Оба эти драйвера устанавливаются как высокоуровневые драйверы. Стек клавиатуры обрабатывает несколько типов запросов. В данной курсовой работе необходимо рассмотреть только IRP типа IRP_MJ_READ, которые несут с собой коды клавиш. Генератором этих IRP является поток необработанного ввода RawInputThread системного процесса csrcc.exe. Этот поток открывает объект «устройство» драйвера класса клавиатуры для эксклюзивного использования и направляет ему IRP типа IRP_MJ_READ. Получив IRP, драйвер Kbdclass отмечает его как ожидающий завершения (pending), ставит в очередь и возвращает STATUS_PENDING. Потоку необработанного ввода придется ждать завершения IRP. Подключаясь к стеку, драйвер Kbdclass регистрирует у драйвера i8042prt процедуру обратного вызова KeyboardClassServiceCallback, направляя ему IRP IOCTL_INTERNAL_KEYBOARD_CONNECT. Драйвер i8042prt тоже регистрирует у системы свою процедуру обработки прерывания (ISR) I8042KeyboardInterruptService, вызовом функции IoConnectInterrupt. Когда будет нажата или отпущена клавиша, контроллер клавиатуры выработает аппаратное прерывание. Его обработчик вызовет I8042KeyboardInterruptService, которая прочитает из внутренней очереди контроллера клавиатуры необходимые данные. Т.к. обработка аппаратного прерывания происходит на повышенном IRQL, ISR делает только самую неотложную работу и ставит в очередь вызов отложенной процедуры I8042KeyboardIsrDpc (DPC). DPC работает при IRQL = DISPATCH_LEVEL. Когда IRQL понизится до DISPATCH_LEVEL, система вызовет процедуру I8042KeyboardIsrDpc, которая вызовет зарегистрированную драйвером Kbdclass процедуру обратного вызова KeyboardClassServiceCallback (также выполняется на IRQL = DISPATCH_LEVEL). KeyboardClassServiceCallback извлечет из своей очереди ожидающий завершения IRP, заполнит структуру KEYBOARD_INPUT_DATA, несущую всю необходимую информацию о нажатиях/отпусканиях клавиш, и завершит IRP. Поток необработанного ввода пробуждается, обрабатывает полученную информацию и вновь посылает IRP типа IRP_MJ_READ драйверу класса, который опять ставится в очередь до следующего нажатия/отпускания клавиши. Таким образом, у стека клавиатуры всегда есть, по крайней мере, один, ожидающий завершения IRP, и находится он в очереди драйвера Kbdclass. Стек клавиатуры представлен на рис.2.5. Рис. 2.5. Стек клавиатуры 2.6 Kernel Streaming Kernel streaming (KS) - это совокупность функций Windows NT 5, которые обрабатывают в режиме ядра потоковые данные, такие как аудио и видео-данные. WDM аудио-драйвер предоставляет системе свои музыкальные функции, как набор фильтров KS. Объект KS фильтра может расширить функции аудиоадаптера, если требуется дополнительная цифровая обработка аудио-потоков, которые идут через этот фильтр. Например, фильтр может преобразовывать форматы потоков, синтезировать или смешивать потоки. Фильтр может содержать несколько пинов. Пин является точкой входа или выхода, через которую аудио-поток входит или покидает фильтр. У каждого пина есть определённый формат данных, и данные только этого формата могут проходить через пин. Пины могут быть подсоединены к пинам других фильтров, что позволяет создавать графы фильтров. Для того чтобы быть частью графа аудио-фильтров, фильтр должен содержать не менее одного пина. KS-фильтр - это объект ядра и к нему можно получить доступ используя HANDLE. Обращение к объекту пина производится также с использованием HANDLE. Данные входят во входные пины, проходят соответствующую обработку в узлах фильтра и выходят из выходящих пинов, как показано на рис. 2.6. Рис.2.6. Схема аудио-фильтра 2.7 Описание формата MIDI-данных Формат МИДИ - Musical Instrument Digital Interface. Существует 16 миди каналов (0..15). На каждом из них в одно и то же время может находиться один инструмент. Всего существует 128 разных инструментов (0..127). Каждый инструмент занимает определенную позицию в общей структуре тембровой схемы - таблица 2.1. Каждый инструмент имеет 128 нот (0..127). Простейшая MIDI-команда состоит из 3 байт, которые отправляются MIDI-устройству. MIDI-команды, которые используются в данной курсовой работе: Утановить инструмент Instrument в канале Channel InstrumentByte[0] = 0xC0 | Channel; InstrumentByte[1] = Instrument; InstrumentByte[2] = 0; Воспроизвести ноту Note в канале Channel на максимальной громкости NoteOnByte[0] = 0x90 | Channel; NoteOnByte[1] = Note; NoteOnByte[2] = 0x7F; Выключить воспроизведение ноты Note в канале Channel NoteOffByte[0] = 0x80 | Channel; NoteOffByte[1] = Note; NoteOffByte[2] = 0x00; Таблица 2.1 Инструменты MIDI |
Acoustic Grand Piano Bright acoustic piano Electric grand piano Honky-tonk piano Electric piano 1 Electric piano 2 Harpsichord Clavi Celesta Glockenspiel Music box Vibraphone Marimba Xylophone Tubular bells Dulcimer Drawbar organ Percussive organ Rock organ Church organ Reed organ Accordian Harmonica Tango accordian Acoustic guitar (nylon) Acoustic guitar (steel) Jazz guitar Clean electric guitar Muted electric guitar Overdrive guitar Distortion guitar Guitar harmonics Accoustic bass Fingered bass Picked bass Fretless bass Slap bass 1 Slap bass 2 Synth bass 1 Synth bass 2 Violin Viola Cello | Contrabass Tremolo strings Pizzicato strings Orchestral harp Timpani String ensemble 1 String ensemble 2 Synth. strings 1 Synth strings 2 Choir ahh Choir oohh Synth voice Orchestral hit Trumpet Trombone Tuba Muted trumpet French horn Brass section Synth brass 1 Synth brass 2 Soprano sax Alto sax Tenor sax Baritone sax Oboe English horn Bassoon Clarinet Piccolo Flute Recorder Pan flute Blown bottle Shakuhachi Whistle Ocarina Square wave Sawtooth wave Caliope Chiff Charang Voice | Fifth's Bass & lead New age Warm Polysynth Choir Bowed Metallic Halo Sweep FX rain FX soundtrack FX crystal FX atmosphere FX brightness FX goblins FX echo drops FX star theme Sitar Banjo Shamisen Koto Kalimba Bagpipe Fiddle Shanai Tinkle bell Agogo Steel drums Woodblock Taiko drum Melodic tom Synth drum Reverse cymbal Guit.fret noise Breath noise Seashore Bird tweet Telephone ring Helicopter Applause Gunshot | | |
Страницы: 1, 2, 3, 4, 5, 6, 7
|