首页
社区
课程
招聘
[求助]寒江独钓TDI过滤StackLocation问题求助
发表于: 2014-11-26 11:39 4994

[求助]寒江独钓TDI过滤StackLocation问题求助

2014-11-26 11:39
4994
TDI过滤驱动 创建了自己的设备附加到 tcp udp rawip上面。
过滤后调用原来的IoCallDriver发送给下层驱动

NTSTATUS FilterDeviceDispatch(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp)
{
	PIO_STACK_LOCATION irps;
	irps = IoGetCurrentIrpStackLocation(Irp);

//问题在这里 
	if (Irp->CurrentLocation <= 1)
	{
		DbgPrint("DeviceObject->stacksize=%d currentLocation=%d----%d\n", DeviceObject->StackSize, Irp->CurrentLocation\
			,Irp->StackCount);
		IoSkipCurrentIrpStackLocation(Irp);
		DbgBreakPoint();
		return IoCallDriver(GETORGDEVOBJ(DeviceObject), Irp);
	}


	IoCopyCurrentIrpStackLocationToNext(Irp);
	return IoCallDriver(GETORGDEVOBJ(DeviceObject), Irp);
}


之前我并没有这个判断。
if (Irp->CurrentLocation <= 1)

直接调用
IoCopyCurrentIrpStackLocationToNext(Irp);
return IoCallDriver(GETORGDEVOBJ(DeviceObject), Irp);
(这里我没有设置完成例程,假设我有完成例程要设置 ,因此调用iocopy而不是ioskip)
在XP系统上浏览网页偶尔蓝屏 ,点击网络邻居查看网络连接之类的就会蓝屏几率更大。
蓝屏代码为NO_MORE_IRP_STACK_LOCATIONS
没有更多的IO栈

按理说,我的设备是附加上去的。 进入我的dispatch例程后。Irp->CurrentLocation至少为2为何会出现Irp->CurrentLocation==1的情况呢??

加上这个判断后的确也出现了Irp->CurrentLocation=1的情况。
查看寒江独钓tdifw源码
tdi_fw.c line 755

if (cr == NULL || irp->CurrentLocation <= 1)
		{
			/*
			 * we use _THIS_ way of sending IRP to old driver
			 * a) to avoid NO_MORE_STACK_LOCATIONS
			 * b) and if we haven't our completions - no need to copy stack locations!
			 */

			// stay on this location after IoCallDriver
			IoSkipCurrentIrpStackLocation(irp);
	
		} 

这里也只是说明了
a避免 NO_MORE_STACK_LOCATIONS的错误
b没有完成例程,没必要copystacklocation 只需要skip就行。(假如我需要完成例程,是不是这个就漏过了)
并没有解释为何出现这个问题。

我自己跟踪了一下,发现流程是这样的

netbt.sys 创建的设备\Device\NetBt_tcpip_{xxxxxxxxxxxxx},stacksize为2

rdbss!RxTdiQueryInformation创建了一个IRP 发送到这个\Device\NetBt_tcpip_{xxxxxxxxxxxxx}
currentstacklocation值为stacksize+1=3;
随后调用IocallDriver currentstacklocation--变成2
进入netbt!NbtDispatchInternalCtrl
继续调用 netbt!NTQueryInformation
获取IoGetCurrentStackLocation获取irpsp
irpsp->fileobject
fileobject->fscontext
由于fscontext没法了解,总之再取了几次值以后
用IoGetRelatedDeviceObject获取到了我的过滤设备,FilterDevice。
然后IoCallDriver(FilterDevice,Irp)
currentstacklocation--变成1
就到了上面的情况。
源码很简单,希望哪位帮忙解释一下
希望高人指点一下为何会出现这个问题。

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

上传的附件:
收藏
免费 0
支持
分享
最新回复 (4)
雪    币: 219
活跃值: (788)
能力值: (RANK:290 )
在线值:
发帖
回帖
粉丝
2
switch( irpStack->MajorFunction )
        {
        case IRP_MJ_CREATE:
                return Filter_create( dev, Irp );
                break;
        case IRP_MJ_CLEANUP:
                return Filter_cleanup( dev, Irp );
                break;
        case IRP_MJ_DEVICE_CONTROL:
                if( KeGetCurrentIrql()==PASSIVE_LEVEL ){
                        status = TdiMapUserRequest( dev, Irp, irpStack );
                }else{
                        status = STATUS_NOT_IMPLEMENTED;
                }
                if( !NT_SUCCESS(status)) break; //没映射成功,直接下发
                //如果成功则进入 IRP_MJ_INTERNAL_DEVICE_CONTROL
        case IRP_MJ_INTERNAL_DEVICE_CONTROL:
                {
                       
                }
                break;
        }
        ///
        ///
       
        IoSkipCurrentIrpStackLocation( Irp );
        return IoCallDriver( _device , Irp );
2014-11-26 12:48
0
雪    币: 1392
活跃值: (5207)
能力值: ( LV13,RANK:240 )
在线值:
发帖
回帖
粉丝
3
要是想能成功运行 按照他的代码如果<=1直接下发好了。并没有解决我的疑问。。为什么当前我的设备stacksize为2.某个IRP进入我的例程之后currentlocation只剩下1了。
2014-11-26 12:58
0
雪    币: 1392
活跃值: (5207)
能力值: ( LV13,RANK:240 )
在线值:
发帖
回帖
粉丝
4
不想只按照人家的做,而不问为什么。求甚解,望大神们帮忙

查看了一下tdi_fw 发现这一段寒江独钓是照着抄的。
2014-11-26 12:59
0
雪    币: 293
活跃值: (239)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
5
学习一下
2014-12-1 21:54
0
游客
登录 | 注册 方可回帖
返回
//