Я пытаюсь реализовать драйвер фильтра мыши, прикрепив «\ Device \ PointerClass0». Присоединение устройства к стеку с помощью IoAttachDevice прошло успешно.
Процедура диспетчеризации для IRP_MJ_READ устанавливает процедуру завершения, а затем передает IRP нижним драйверам.
IoCopyCurrentIrpStackLocationToNext(Irp);
IoSetCompletionRoutine(Irp,CompletionRoutine,DeviceObject,TRUE,TRUE,TRUE);
return IoCallDriver(TopMostDriver,Irp);
И затем, когда вызывается подпрограмма завершения, она инвертирует Y ax:
NTSTATUS CompletionRoutine(PDEVICE_OBJECT DeviceObject,PIRP Irp,PVOID Context){
PMOUSE_INPUT_DATA MouseData;
if(Irp->IoStatus.Status == STATUS_SUCCESS){
MouseData = (PMOUSE_INPUT_DATA)Irp->AssociatedIrp.SystemBuffer;
MouseData->LastY *= -1;
}
if(Irp->PendingReturned){
IoMarkIrpPending(Irp);
}
return STATUS_SUCCESS;
}
Процедура отправки по умолчанию для других основных функций просто передает IRP нижним драйверам.
Проблема заключается в том, что при загрузке моего драйвера процедура отправки по умолчанию вызывается 1 раз только после подключения драйвера, после этого она не вызывается и процедура отправки для IRP_MJ_READ. Я проверил с помощью DeviceTree, что мое устройство подключено, отправка рутина не будет вызвана, если это не так или иначе.
РЕДАКТИРОВАТЬ: Я на самом деле нашел это утверждение в osronline:
the mouse input stacks are pnp and there is no way for you to put yourself
into the stack after it has started running (you could install yourself as a filter and then restart the stack)
Как я могу на самом деле перезапустить стек драйверов?
На самом деле, вы можете ввести себя, не перезагружая устройство, но это довольно неприятно. Вы можете найти драйвер, который находится в стеке устройства, а затем скопировать все (или некоторые) из его MajorFunction Обработчики IRP к имеющемуся у вас массиву, а затем замените все (или некоторые) из этих обработчиков на свои собственные, убедившись, что «прозрачно» передаст IRP обработчикам, которые у вас «средние». Это означает, что у вас не будет своего IO_STACK_LOCATION работать с, однако. Эта стратегия довольно неприятная, поэтому я не рекомендую ее, если вам не нужно. (Читайте как «никогда не делай этого».)
Лучше установить драйвер фильтра, как обычно устанавливаются драйверы фильтра, а затем перезагрузить устройство. Вы можете использовать функции управления устройством PnP в пользовательском режиме, чтобы выполнить это, с помощью какой-либо утилиты установки, которую вы напишите, или просто задокументировать процесс установки для пользователей и позволить им это сделать.