Page 20 of 46

Re: Тестируем поддержку USB

Posted: Mon Aug 29, 2011 7:00 pm
by CleverMouse
Serge, а мне не нравится создание потока для каждого элементарного действия.
Запускать таймер должен драйвер по одному ему известным условиям. Добавлять драйверное API для таймеров специально для USBшных драйверов только чтобы их обрабатывал поток USB, а не главный, на том основании, что это же USBшный драйвер, - бред.

Re: Тестируем поддержку USB

Posted: Mon Aug 29, 2011 7:32 pm
by Serge
CleverMouse
А причем здесь драйверное API ? И разве нынешнее решение не сделано специально для USB ?

У тебя ведь драйвер уже работает в своём потоке ? Что мешает ему обработать в этом потоке событие таймера ? Почему это должен делать поток OS/IDLE ? Потому что так проще ? На эти грабли уже наступали.

Re: Тестируем поддержку USB

Posted: Mon Aug 29, 2011 7:41 pm
by CleverMouse
Функции TimerHS/CancelTimerHS? Нет, в них нет вообще ничего специфичного для USB. Одним из планов использования, между прочим, является замена check_fdd_motor_status и check_ATAPI_device_event при выносе соответствующего кода в драйвера. Соответственно, я не понимаю, почему ты предлагаешь заняться этим потоку USB, и где ты видишь грабли.

Re: Тестируем поддержку USB

Posted: Mon Aug 29, 2011 8:20 pm
by Serge
CleverMouse
Ага, значит мы друг друга не понимаем. Совсем ничего не имею против TimerHS/CancelTimerHS. Наоборот таймеры нужны, вопрос в реализации. Моя идея:

Code: Select all

usb_thread()
{
    while(1)
    {
        kevent_t event;

        get_event_ex(&event);
        switch(event.code)
        {
            case EV_IRQ:
            ;постобработка irq.
            break;
            case EV_TIMER:
            ;обрабатываем таймеры
            break;
        };
    };
};

Re: Тестируем поддержку USB

Posted: Mon Aug 29, 2011 8:57 pm
by CleverMouse
В реализации чего именно?
На что, по-твоему, нужно заменить вот эти два фрагмента из usbhid.asm, который на данный момент является единственным пользователем TimerHS/CancelTimerHS?

Code: Select all

; 5h. Start the auto-repeat timer.
        pop     ecx     ; restore keycode
        mov     [ebx+keyboard_data.repeatkey], cl
        stdcall TimerHS, 25, 5, autorepeat_timer, ebx
        mov     [ebx+keyboard_data.timer], eax

Code: Select all

; Timer function for auto-repeat.
autorepeat_timer:
        mov     eax, [esp+4]
        movzx   ecx, [eax+keyboard_data.repeatkey]
        test    cl, cl
        jns     @f
        push    ecx
        mov     ecx, 0xE0
        call    SetKeyboardData
        pop     ecx
        and     cl, not 0x80
@@:
        call    SetKeyboardData
        ret     4

Re: Тестируем поддержку USB

Posted: Mon Aug 29, 2011 10:38 pm
by Serge
Не надо ничего менять. autorepeat_timer надо вызывать из потока usb (в обработчике EV_TIMER), а не из osloop.
Может я и не прав. Просто мне нравится идея Minix, где каждый сервис работает в своём потоке.

Re: Тестируем поддержку USB

Posted: Mon Aug 29, 2011 11:10 pm
by CleverMouse
Хорошо. Теперь предположим, что завтра появляется драйвер PS/2-клавиатуры, автор которого посчитал механизм автоповтора в PS/2 недостаточно гибким и тоже использует программную эмуляцию. Естественно, в этом драйвере тоже будут два вышеприведённых фрагмента кода, причём дословно те же самые. Если мы против копипаста, предположим заодно, что загрузчик PE-драйверов умеет обрабатывать импорт не только из ядра, тогда можно считать, что два драйвера просто вызывают одну функцию общей библиотеки. Должен ли поток USB захватывать autorepeat_timer и для этого драйвера? Если да, то что будет, если подсистема USB не загружена, поскольку USB-устройств нет? Если нет, то почему два логически абсолютно идентичных фрагмента кода должны исполняться в двух логически совершенно разных местах?

Я определённо предпочитаю Windows, а не Minix. Там KeSetTimerEx/KeCancelTimer позволяют поставить процедуру на выполнение и не думать, какой именно поток её будет выполнять.

Re: Тестируем поддержку USB

Posted: Tue Aug 30, 2011 12:55 am
by Serge
Отлично. А теперь предположим, что у нас есть общий сервис (процесс), который принимает от драйверов устройств события (нажатие клавиш, перемещение мыши и джойстика) обрабатывает, сам генерирует автоповтор для клавиатуры, и пересылает приложениям. И этот сервис является частью оконной системы, как и должно быть. Очень похоже на osloop. Должен ли этот процесс обрабатывать таймеры для совершенно посторонних устройств, как флоппи ?
Ответ на твой вопрос зависит от того, создаст ли автор драйвера для PS/2 отдельный процесс. Если нет, он не сможет обработать событие таймера и TimerHS() ему не поможет. Если да, то он будет выполнять autorepeat_timer независимо от usb. Это вопрос принципов устройства драйверной модели.
Я определённо предпочитаю Windows, а не Minix. Там KeSetTimerEx/KeCancelTimer позволяют поставить процедуру на выполнение и не думать, какой именно поток её будет выполнять.
И действительно, зачем нам всякие KeWaitForSingleObject и KeWaitForMultipleObjects если есть замечательные DPC которые блокируют остальные потоки
Spoiler:
Note The CustomTimerDpc routine, like all DPC routines, is called at IRQL = DISPATCH_LEVEL. While a DPC routine runs, all threads are prevented from running on the same processor. Driver developers should carefully design their CustomTimerDpc routines to run for as brief a time as possible.
Есть ещё Threaded DPC но это же Vista :(
Я кстати именно эту схему предлагаю, только название у KeWaitForMultipleObjects другое.

Re: Тестируем поддержку USB

Posted: Tue Aug 30, 2011 4:28 pm
by CleverMouse
Ага. Значит, в ситуации "как и должно быть" всё-таки автоповтор обрабатывается не потоком, который, как сложилось, породил драйвер клавиатуры, а потоком-частью оконной системы, который имеет непосредственное отношение к содержимому autorepeat_timer. С этим я соглашусь. Разумеется, в этой ситуации поток-часть оконной системы не должен обрабатывать посторонние таймеры. Я даже соглашусь, что идеологически osloop не должен обрабатывать посторонние таймеры. Тем не менее, сейчас он их по факту обрабатывает, и я считаю, что сейчас это правильно.

Для реализации второго способа работы с KeSetTimerEx - через объекты ядра, на которых могут ждать потоки, - как в винде, нужен планировщик, как в винде. Сейчас каждый новый поток - это заметная нагрузка на систему: планировщик просматривает этот поток, даже если он просто спит, на каждом тике - в предположении ненагруженности системы, когда за тик успевает прокрутиться вся карусель потоков; в CPU этот поток даёт ещё один невнятный вход; если он создан не при загрузке системы и попал в середину карусели с пользовательскими потоками, то получаем плюс одну перезагрузку CR3; каждый новый поток приближает предел в 255 потоков. Мне кажется, что ты это понимаешь и поэтому настаиваешь на включении таймеров в поток usb вместо создания отдельных потоков, хотя идеологически там они столь же неуместны, сколь и в osloop.

Если планировщик не будет вообще обращаться к спящим потокам, будет отдавать предпочтение потокам текущего процесса и система будет чётко осознавать разницу между процессами и потоками - хотя бы для CPU, чтобы он давал внятные показания, - я только за выделение различных сущностей в различные потоки. Но поскольку этого нет, я настаиваю на включении всех мелких задач в osloop, который по факту уже и есть обработчик кучи мелких задач; это экономит время планировщика, ограниченное число потоков, перезагрузки CR3, а в качестве минусов задерживает на миллисекунды отрисовку курсора - с моей точки зрения в текущей ситуации плюсы явно существеннее.

Re: Тестируем поддержку USB

Posted: Tue Aug 30, 2011 5:25 pm
by Serge
Планировщик не переключается на блокированные потоки. Поиск по всем TASKDATA и проверка событий для ожидающих потоков занимает незначительное время. Хотя разбирать события в планировщике не лучшее решение.

Re: Тестируем поддержку USB

Posted: Fri Mar 02, 2012 11:43 am
by SoUrcerer
Приношу извинения за поднятие такой старой темы, но я только сейчас добрался до ковыряния кода usbhid.asm. Я так понимаю, что этот драйвер вызывается только тогда, когда ядро уже определило, что устройство - это HID? Потому что я добавляю в драйвер отладочную строчку, и не вижу ее:

Code: Select all

AddDevice:

        mov     edx, [esp+12]

        push    ebx     ; save used register to be stdcall

        mov     cx, word [edx+interface_descr.bInterfaceSubClass]

        DEBUGF 1,'K : unknown device: %x\n',cx
Впрочем, я вообще никаких строчек не вижу, получаю сообщение ядра о том, что что-то не так с SET_ADDRESS, и USB-устройство будет отключено. Использовал ядро и исходник драйвера с ftp. Как сделать так, чтобы ядро и с другими Class/Subclass/Protocol работало? Нашел наконец исходники драйвера, через который работает мой 3G-модем, хочу попробовать для начала хотя бы совершать звонки.

Re: Тестируем поддержку USB

Posted: Fri Mar 02, 2012 12:13 pm
by dunkaist
SoUrcerer,
CleverMouse в usbapi.txt wrote:For every interface the kernel looks for class code of this interface and loads the corresponding COFF driver. Currently the correspondence is hardcoded into the kernel code and looks as follows: 3 = usbhid.obj.
CleverMouse,
мне тоже интересно попробовать свои силы в драйверописании. Исходники ядра с usb были бы как нельзя кстати, пусть и не на svn.

Re: Тестируем поддержку USB

Posted: Fri Mar 02, 2012 12:14 pm
by SoUrcerer
Да, я именно об этом и подумал. Спасибо за уточнение. Все равно, поэкспериментировать желание имеется.

Re: Тестируем поддержку USB

Posted: Tue Apr 24, 2012 12:48 pm
by CleverMouse
Ядро http://ftp.kolibrios.org/users/CleverMo ... kernel.mnt синхронизировано с транком. Драйвера usbhid.obj и usbstor.obj не пострадали. В процессе синхронизации произошло выпиливание старых мьютексов и замена их новыми, так что могли появиться глюки.

Я напоминаю, что ядро умеет работать с существующими и вновь подключаемыми usb1-устройствами, определяя их class/subclass/protocol и выводя информацию на доску отладки, а также - при существовании usbhid.obj и usbstor.obj в папке drivers - поддерживать мышки и клавиатуры и распечатывать первые несколько байт первого сектора флешки для проверки работы с аппаратной частью. USB2-устройства в зависимости от настроек BIOSа и конкретного порта, к которому они подключены, могут либо работать на скорости usb1, либо захватываться BIOSом, в последнем случае ядро либо не увидит их совсем, либо произойдёт ошибка на первой стадии конфигурации aka SET_ADDRESS. При динамическом переподключении USB2-устройства могут в зависимости от тех же условий либо быть, либо не быть захваченными BIOSом.

Re: Тестируем поддержку USB

Posted: Tue Apr 24, 2012 7:03 pm
by Artyom
Мышка, я разницы при байтовом сравнение trunk'ов не увидел. Сможешь покакать где проблемная часть возникла?
Или могла возникнуть, случаем :)