首页
社区
课程
招聘
[求助]如何取消kbdclass中正在等待的IRP
发表于: 2015-8-13 18:58 8798

[求助]如何取消kbdclass中正在等待的IRP

2015-8-13 18:58
8798
做一个传统的键盘过滤,但是键盘输入总有一个在等待的irp,也就导致过滤键盘的按键总会漏掉第一个按键。
如何找到这个IRP并把它取消掉?望大大们指点!!!
我尝试在KbdClass->DeviceObject->DeviceExtension里面去获取,但是不知道是不是我的DeviceExtension结构定义跟我测试的系统(xpsp3)有出入(获取到ReadQueue不对)

DeviceExtension定义是我从ddk中的kbdclass.h拷贝的,是不是哪里错了
//
// Class device extension.
//
typedef struct _DEVICE_EXTENSION {

    //
    // Back pointer to the Device Object created for this port.
    //
    PDEVICE_OBJECT  Self;

    //
    // Pointer to the active Class DeviceObject;
    // If the AFOAOFA (all for one and one for all) switch is on then this
    // points to the device object named as the first keyboard.
    //
    PDEVICE_OBJECT  TrueClassDevice;

    //
    // The Target port device Object to which all IRPs are sent.
    //
    PDEVICE_OBJECT  TopPort;

    //
    // The PDO if applicable.
    //
    PDEVICE_OBJECT  PDO;

    //
    // A remove lock to keep track of outstanding I/Os to prevent the device
    // object from leaving before such time as all I/O has been completed.
    //
    IO_REMOVE_LOCK  RemoveLock;

    //
    // If this port a Plug and Play port
    //
    BOOLEAN         PnP;
    BOOLEAN         Started;
    BOOLEAN         AllowDisable;

    KSPIN_LOCK WaitWakeSpinLock;

    //
    // Is the Trusted Subsystem Connected
    //
    ULONG TrustedSubsystemCount;

    //
    // Number of input data items currently in the InputData queue.
    //
    ULONG InputCount;

    //
    // A Unicode string pointing to the symbolic link for the Device Interface
    // of this device object.
    //
    UNICODE_STRING  SymbolicLinkName;

    //
    // Start of the class input data queue (really a circular buffer).
    //
    PKEYBOARD_INPUT_DATA InputData;

    //
    // Insertion pointer for InputData.
    //
    PKEYBOARD_INPUT_DATA DataIn;

    //
    // Removal pointer for InputData.
    //
    PKEYBOARD_INPUT_DATA DataOut;

    //
    // Keyboard attributes.
    //
    KEYBOARD_ATTRIBUTES  KeyboardAttributes;

    //
    // A saved state of indicator lights
    //
    KEYBOARD_INDICATOR_PARAMETERS   IndicatorParameters;

    //
    // Spinlock used to synchronize access to the input data queue and its
    // insertion/removal pointers.
    //
    KSPIN_LOCK SpinLock;

    //
    // Queue of pended read requests sent to this port.  Access to this queue is
    // guarded by SpinLock
    //
    LIST_ENTRY ReadQueue;

    //
    // Request sequence number (used for error logging).
    //
    ULONG SequenceNumber;

    //
    // The "D" and "S" states of the current device
    //
    DEVICE_POWER_STATE DeviceState;
    SYSTEM_POWER_STATE SystemState;

    ULONG UnitId;

    //
    // WMI Information
    //
    WMILIB_CONTEXT WmiLibInfo;

    //
    // Mapping of system to device states when a wait wake irp is active
    //
    DEVICE_POWER_STATE SystemToDeviceState[PowerSystemHibernate];

    //
    // Minimum amount of power needed to wake the device
    //
    DEVICE_POWER_STATE MinDeviceWakeState;

    //
    // Lowest system state that the machine can be in and have the device wake it up
    //
    SYSTEM_POWER_STATE MinSystemWakeState;

    //
    // Actual wait wake irp
    //
    PIRP WaitWakeIrp;

    //
    // Duplicate wait wake irp getting completed because another was queued.
    //
    PIRP ExtraWaitWakeIrp;

    //
    // Target Device Notification Handle
    //
    PVOID TargetNotifyHandle;

    //
    // Only used for a legacy port device
    //
    LIST_ENTRY Link;

    //
    // Used only for a legacy port device when grand master mode is off
    //
    PFILE_OBJECT File;

    //
    // Used for a legacy port device
    //
    BOOLEAN Enabled;

    //
    // Indicates whether it is okay to log overflow errors.
    //
    BOOLEAN OkayToLogOverflow;

    //
    // Indicates whether it is okay to send wait wake irps down the stack
    // (does NOT reflect if the bus can implement or not)
    //
    BOOLEAN WaitWakeEnabled;

    //
    // Indicates whether we have received a surprise removed irp
    //
    BOOLEAN SurpriseRemoved;

} DEVICE_EXTENSION, *PDEVICE_EXTENSION;

[培训]内核驱动高级班,冲击BAT一流互联网大厂工作,每周日13:00-18:00直播授课

收藏
免费 0
支持
分享
最新回复 (9)
雪    币: 34
活跃值: (734)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
2
没有人解答一下吗?
2015-8-13 20:15
0
雪    币: 1392
活跃值: (5177)
能力值: ( LV13,RANK:240 )
在线值:
发帖
回帖
粉丝
3
思路麻烦
取消后如何保证再投递,你直接取消很可能以后的按键就再也没有作用了。

最好是找到这个irp然后 完成这个irp。 也许要去线程的Irp列队里面找,不然还真没什么好办法,或者直接写键盘的IO端口,不知道是否可行。
2015-8-14 08:23
0
雪    币: 34
活跃值: (734)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
4
不用投递,直接取消就好了,关键是怎么找到这个IRP,请指点。
写一个模拟数据的话,来消耗这个IRP的话,需要考虑P/S和USB两种情况,所以暂时不用这个方法。
2015-8-14 08:42
0
雪    币: 1392
活跃值: (5177)
能力值: ( LV13,RANK:240 )
在线值:
发帖
回帖
粉丝
5
我不确定 你取消后系统是否会帮你再投递一个Read IRP ,这点你要确定。我感觉消耗是最靠谱的办法。
实在要找这个IRP,可能需要到RawInputThread线程ETHREAD结构的irp队列里面找。
2015-8-14 08:53
0
雪    币: 34
活跃值: (734)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
6
http://bbs.pediy.com/showthread.php?t=85883

这个贴里面,qihoocom大神有稍微讲一下方向,也就是开头我说那个方法,可是为什么在我这里行不通呢,不知道哪里有问题
2015-8-14 10:19
0
雪    币: 1392
活跃值: (5177)
能力值: ( LV13,RANK:240 )
在线值:
发帖
回帖
粉丝
7
帖子里不是已经解决了吗?照着抄啊。他后面又开了一贴 解决了
2015-8-14 13:00
0
雪    币: 34
活跃值: (734)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
8
他的问题跟我不一样啊,我是获取的设备扩展数据后半段对不上
2015-8-14 13:28
0
雪    币: 210
活跃值: (36)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
9
请问楼主有解决这个问题吗?我也遇到类似问题。如果可以的话,我想学习一下楼主的实现方法,多谢楼主。
2020-10-26 09:47
0
雪    币: 34
活跃值: (734)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
10
这么久了,我也忘记了,后面我是用替换键盘的类驱动回调实现的,寒江独钓这本书里有简单提过这个方法
2021-1-27 16:07
0
游客
登录 | 注册 方可回帖
返回
//