This isn’t one of my areas, but I wonder about a few things in your example:
-
What if there are multiple events passed to the filter function? Isn’t
setting ‘consumed’ going to eat all of them? But you are really only
processing the first event.
-
If a real user is pressing that ‘z’ key, you are probably going to get a
single event which is the keydown, which you consume and replace. But you
don’t seem to do anything with the now mis-matched keyup that will come
along later. Perhaps getting a keyup without a keydown can confuse things
in a state machine someplace?
-
You have set input data consumed to some value other than what it had,
and now you pass this UP the stack as well as having returned the value down
the stack. Possibly having the data marked consumed by a lower filter is
confusing the upper layers?
I think if I were inserting data I might do something like making a specific
call up the stack with my inserted data, then, if there was unconsumed data
in the original packet, pass this unconsumed data up the stack in a second
call. On the first call I would probably pass a pointer to a dummy
‘consumed’ local rather than the value passed into the filter. Also, if I
consumed a keydown, I’d probably also set some state that would live long
enough to tell me that I have to consume the keyup also (and any key
repeats, if they have already been generated at this level).
Loren
-----Original Message-----
From: xxxxx@lists.osr.com
[mailto:xxxxx@lists.osr.com] On Behalf Of Phil Falck
Sent: Monday, December 08, 2003 2:34 PM
To: Windows System Software Devs Interest List
Subject: [ntdev] RE: Inserting keystrokes using kbfiltr
Doron,
Sorry to bother you, but I must be doing something stupid. Here is a
simplified KbFilter_ServiceCallback() from kbfiltr.c.
In the example I am simply just trying to change a ‘z’ into a ‘d’ ‘i’.
(I.e. trying to replace a single character with a sequence of
characters).
If you could point out the error of my ways I would greatly appreciate
it.
TIA, phil
VOID
KbFilter_ServiceCallback(
IN PDEVICE_OBJECT DeviceObject,
IN PKEYBOARD_INPUT_DATA InputDataStart,
IN PKEYBOARD_INPUT_DATA InputDataEnd,
IN OUT PULONG InputDataConsumed
)
{
PDEVICE_EXTENSION devExt;
ULONG i;
KEYBOARD_INPUT_DATA kid[16];
BOOLEAN bInsert = FALSE;
devExt = (PDEVICE_EXTENSION) DeviceObject->DeviceExtension;
// print out what keys came in
for (i = 0; i < (ULONG)(InputDataEnd-InputDataStart); i++)
KdPrint((“%d-MC:%02x; F:%02x; SP:%08x; EP:%08x;
Consumed:%d\r\n”,
i,
(InputDataStart+i)->MakeCode,
(InputDataStart+i)->Flags,
InputDataStart,
InputDataEnd,
*InputDataConsumed));
// look for a ‘z’ pressed, then turn it into a ‘d’ ‘i’
if ((InputDataStart->MakeCode == 0x2c)&&(InputDataStart->Flags ==
0))
{
bInsert = TRUE;
RtlZeroMemory(kid, 16*sizeof(KEYBOARD_INPUT_DATA));
kid[0].MakeCode = 0x20; // simulate a ‘d’ press
kid[0].Flags = 0x00;
kid[1].MakeCode = 0x20; // simulate a ‘d’ release
kid[1].Flags = 0x01;
kid[2].MakeCode = 0x17; // simulate a ‘i’ press
kid[2].Flags = 0x00;
kid[3].MakeCode = 0x17; // simulate a ‘i’ release
kid[3].Flags = 0x01;
*InputDataConsumed = 1; // none of 0, 1, 4 works
}
(*(PSERVICE_CALLBACK_ROUTINE)
devExt->UpperConnectData.ClassService)(
devExt->UpperConnectData.ClassDeviceObject,
bInsert ? &kid[0] : InputDataStart,
bInsert ? &kid[4] : InputDataEnd,
InputDataConsumed);
}
Questions? First check the Kernel Driver FAQ at
http://www.osronline.com/article.cfm?id=256
You are currently subscribed to ntdev as: xxxxx@windows.microsoft.com
To unsubscribe send a blank email to xxxxx@lists.osr.com
Questions? First check the Kernel Driver FAQ at
http://www.osronline.com/article.cfm?id=256
You are currently subscribed to ntdev as: xxxxx@earthlink.net
To unsubscribe send a blank email to xxxxx@lists.osr.com