5433|8

70

帖子

0

TA的资源

一粒金砂(初级)

楼主
 

如何在U盘过滤驱动的SCSI派遣函数里读取U盘扇区? [复制链接]

最近在研究U盘过滤驱动,想在SCSI派遣函数里读取U盘扇区,如果没有我们写入的标识,则禁用U盘。

现在禁用实现了,但是不知道怎么读取U盘扇区,请大家指点

最新回复

重路问题可以利用Irp->Tail.Overlay.Thread=PsGetCurrentThread();判断这个线程是否重路。 你可以直接HOOK驱动对象:Driver\USBSTOR的IRP_MJ_SCSI例程啊!我就怎么干的。  详情 回复 发表于 2010-6-16 16:21
点赞 关注

回复
举报

87

帖子

0

TA的资源

一粒金砂(初级)

沙发
 
大家帮帮忙 急用
 
 

回复

72

帖子

0

TA的资源

一粒金砂(初级)

板凳
 
没人做过吗?
有相关经验的请指点一二
 
 
 

回复

72

帖子

0

TA的资源

一粒金砂(初级)

4
 
过滤驱动过载在注册表HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control\Class\{36FC9E60-C465-11CF-8056-444553540000}下,
我想知道在SCSI派遣函数里构造IRP能读取U盘扇区吗?

或者是在PNP派遣函数的IRP_MN_START_DEVICE里能读取到吗?
 
 
 

回复

83

帖子

0

TA的资源

一粒金砂(初级)

5
 
幫你頂了。最近也是在做u盤方面的,但是禁用沒有實現
請問樓主你是如何實現u盤自動禁用的
能否給我些參考呢····多謝了··
 
 
 

回复

84

帖子

0

TA的资源

一粒金砂(初级)

6
 
参照别人的读写硬盘的代码,我写了一段代码,但是没有读取到U盘扇区,大家给看看
#pragma LOCKEDCODE
NTSTATUS DispatchForSCSI(IN PDEVICE_OBJECT fido, IN PIRP Irp)
{
    KdPrint((DRIVERNAME " - Enter DispatchForSCSI \n"));
    //获得设备扩展
        PDEVICE_EXTENSION pdx = (PDEVICE_EXTENSION) fido->DeviceExtension;
        //获得I/O堆栈
        PIO_STACK_LOCATION irpStack = IoGetCurrentIrpStackLocation(Irp);
        PDEVICE_OBJECT DeviceObject = pdx->DeviceObject;
        NTSTATUS status;

        if (_wcsnicmp(DeviceObject->AttachedDevice->DriverObject->DriverName.Buffer,L"\\Driver\\USBSTOR",15)==0)
        {
                CHAR buf[512];
        RtlZeroMemory(buf,sizeof(buf));
                //RtlCopyMemory(buf,"HT",2);

                status = AtapiReadWriteDisk(fido,IRP_MJ_READ,buf,1,1,Irp);
                if (NT_SUCCESS(status))
                {
                        Irp->IoStatus.Status = STATUS_ACCESS_DENIED;
                        Irp->IoStatus.Information = 0;
                        IoCompleteRequest( Irp, IO_NO_INCREMENT );
            return STATUS_ACCESS_DENIED;
                }
               
                //获取自旋锁
                status = IoAcquireRemoveLock(&pdx->RemoveLock, Irp);
                //判断是否成功获取自旋锁
                if (!NT_SUCCESS(status))
                        //结束IRP请求
                        return CompleteRequest(Irp, status, 0);
                //略过当前I/O堆栈
                IoSkipCurrentIrpStackLocation(Irp);
                //调用底层驱动程序
                status = IoCallDriver(pdx->LowerDeviceObject, Irp);
                //释放自旋锁
                IoReleaseRemoveLock(&pdx->RemoveLock, Irp);

                ExFreePool(buf);
       
        return status;
    }
}

ULONG  AtapiReadWriteDisk(PDEVICE_OBJECT dev_object,ULONG MajorFunction, PVOID buffer,ULONG DiskPos, int BlockCount,PIRP Irp)
{
        NTSTATUS status;
        PSCSI_REQUEST_BLOCK srb;
        PSENSE_DATA sense;
        KEVENT Event;
        //PIRP irp;
        PMDL mdl;
        IO_STATUS_BLOCK isb;
        PIO_STACK_LOCATION isl;
        PVOID psense;
        PDEVICE_EXTENSION pdx = (PDEVICE_EXTENSION) dev_object->DeviceExtension;
        int count=8;

        while(1)
        {
                srb = (PSCSI_REQUEST_BLOCK)ExAllocatePool(NonPagedPool,sizeof(SCSI_REQUEST_BLOCK));
                if(!srb)
                        break;
                sense = (PSENSE_DATA)ExAllocatePool(NonPagedPool,sizeof(SENSE_DATA));
                psense=sense;
                if(!sense)
                        break;
                memset(srb,0,sizeof(SCSI_REQUEST_BLOCK));
                memset(sense,0,sizeof(SENSE_DATA));

        //更多关于srb,请看《SCSI 总线和IDE接口:协议、应用和编程》和《SCSI程序员指南》
                srb->Length=sizeof(SCSI_REQUEST_BLOCK);
                srb->Function=0;
                srb->DataBuffer=buffer;
                srb->DataTransferLength=BlockCount<<9;//sector size*number of sector
                srb->QueueAction=SRB_FLAGS_DISABLE_AUTOSENSE;
                srb->SrbStatus=0;
                srb->ScsiStatus=0;
                srb->NextSrb=0;
                srb->SenseInfoBuffer=sense;
                srb->SenseInfoBufferLength=sizeof(SENSE_DATA);
                if(MajorFunction==IRP_MJ_READ)
                        srb->SrbFlags=SRB_FLAGS_DATA_IN;
                else
                        srb->SrbFlags=SRB_FLAGS_DATA_OUT;
               
                if(MajorFunction==IRP_MJ_READ)
                        srb->SrbFlags|=SRB_FLAGS_ADAPTER_CACHE_ENABLE;
               
                srb->SrbFlags|=SRB_FLAGS_DISABLE_AUTOSENSE;
                srb->TimeOutValue=(srb->DataTransferLength>>10)+1;
                srb->QueueSortKey=DiskPos;
                srb->CdbLength=10;
                srb->Cdb[0]=2*((UCHAR)MajorFunction+ 17);
                srb->Cdb[1]=srb->Cdb[1] & 0x1F | 0x80;
                srb->Cdb[2]=(unsigned char)(DiskPos>>0x18)&0xFF;    //
                srb->Cdb[3]=(unsigned char)(DiskPos>>0x10)&0xFF;    //
                srb->Cdb[4]=(unsigned char)(DiskPos>>0x08)&0xFF;    //
                srb->Cdb[5]=(UCHAR)DiskPos;          //填写sector位置
                srb->Cdb[7]=(UCHAR)BlockCount>>0x08;
                srb->Cdb[8]=(UCHAR)BlockCount;
                //By:Eros412
                //KeInitializeEvent(&Event, 0, 0);
                KeInitializeEvent(&Event, NotificationEvent, FALSE);
                //irp=IoAllocateIrp(dev_object->StackSize,0);
                mdl=IoAllocateMdl(buffer, BlockCount<<9, 0, 0, Irp);
                Irp->MdlAddress=mdl;
                if(!mdl)
                {
                        ExFreePool(srb);
                        ExFreePool(psense);
                        IoFreeIrp(Irp);
                        return STATUS_INSUFFICIENT_RESOURCES;
                }
                //MmProbeAndLockPages(mdl,0,(MajorFunction==IRP_MJ_READ?0:1));
                MmProbeAndLockPages(mdl,0,IoReadAccess);
                srb->OriginalRequest=Irp;
                Irp->UserIosb=&isb;
                Irp->UserEvent=&Event;
                Irp->IoStatus.Status=0;
                Irp->IoStatus.Information=0;
                Irp->Flags=IRP_SYNCHRONOUS_API|IRP_NOCACHE;
                Irp->AssociatedIrp.SystemBuffer=0;
                Irp->Cancel=0;
                Irp->RequestorMode=0;
                Irp->CancelRoutine=0;
                Irp->Tail.Overlay.Thread=PsGetCurrentThread();

                isl=IoGetNextIrpStackLocation(Irp);
                //isl->DeviceObject=dev_object;
                //isl->MajorFunction=IRP_MJ_SCSI;
                isl->Parameters.Scsi.Srb=srb;
                isl->CompletionRoutine=IrpCompletionRoutine_0;
                //isl->Context=srb;
                //isl->Control=SL_INVOKE_ON_CANCEL|SL_INVOKE_ON_SUCCESS|SL_INVOKE_ON_ERROR;

//                 //获取自旋锁
//                 status = IoAcquireRemoveLock(&pdx->RemoveLock, Irp);
//                 //判断是否成功获取自旋锁
//                 if (!NT_SUCCESS(status))
//                         //结束IRP请求
//                         return CompleteRequest(irp, status, 0);
//                 //略过当前I/O堆栈
//                 IoSkipCurrentIrpStackLocation(irp);
//                 //调用底层驱动程序
//                 status = IoCallDriver(pdx->LowerDeviceObject, Irp);
//                 //释放自旋锁
//         IoReleaseRemoveLock(&pdx->RemoveLock, Irp);

                status=IoCallDriver(pdx->LowerDeviceObject,Irp);
                //KeWaitForSingleObject(&Event, 0, 0, 0, 0);
                KeWaitForSingleObject(&Event, Executive, KernelMode, FALSE, 0);
       
                if(srb->SenseInfoBuffer!=psense&&srb->SenseInfoBuffer)
                        ExFreePool(srb->SenseInfoBuffer);
               
                ExFreePool(srb);
                ExFreePool(psense);
               
                if ( status >= 0 || !count )
                        return status;
               
                DbgPrint("Send XXX Failed..%08x\r\n", status);
                KeStallExecutionProcessor(1u);
                --count;
        }
        return STATUS_INSUFFICIENT_RESOURCES;
}       
 
 
 

回复

68

帖子

0

TA的资源

一粒金砂(初级)

7
 
我是想自己创建一个SCSI_REQUEST_BLOCK,替换原来的,然后传递下去,但是没有读取到U盘扇区
 
 
 

回复

59

帖子

0

TA的资源

一粒金砂(初级)

8
 
在网上找了一段机器狗的读取扇区的代码,
加到我的代码里试了试,发现反复的进入读扇区的代码,但是扇区却始终没有读到,后来系统崩溃了。
我意识到好像是所谓的“重路”了。
有段代码如下:
isl=IoGetNextIrpStackLocation(irp);
                isl->DeviceObject=dev_object;
                isl->MajorFunction=IRP_MJ_SCSI;
                isl->Parameters.Scsi.Srb=srb;
                isl->CompletionRoutine=IrpCompletionRoutine_0;
                isl->Context=srb;
                isl->Control=SL_INVOKE_ON_CANCEL|SL_INVOKE_ON_SUCCESS|SL_INVOKE_ON_ERROR;
                status=MyIoCallDriver(dev_object,irp);

我是在SCSI的派遣函数里调用读取扇区的代码的,但是代码中isl->MajorFunction=IRP_MJ_SCSI;又是进入SCSI派遣函数,所以重路了。不能读取U盘扇区。

我想我需要在SCSI派遣函数里自己写一个IRP,是读取扇区代码在经过SCSI派遣函数进入下层设备站的IRP以及其他的参数,在网上没找到相关的资料,有人知道怎么做吗?

过滤驱动过载在注册表HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control\Class\{36FC9E60-C465-11CF-8056-444553540000}下,
 
 
 

回复

73

帖子

0

TA的资源

一粒金砂(初级)

9
 
重路问题可以利用Irp->Tail.Overlay.Thread=PsGetCurrentThread();判断这个线程是否重路。
你可以直接HOOK驱动对象:Driver\USBSTOR的IRP_MJ_SCSI例程啊!我就怎么干的。
 
 
 

回复
您需要登录后才可以回帖 登录 | 注册

随便看看
查找数据手册?

EEWorld Datasheet 技术支持

相关文章 更多>>
关闭
站长推荐上一条 1/7 下一条

 
EEWorld订阅号

 
EEWorld服务号

 
汽车开发圈

About Us 关于我们 客户服务 联系方式 器件索引 网站地图 最新更新 手机版

站点相关: 国产芯 安防电子 汽车电子 手机便携 工业控制 家用电子 医疗电子 测试测量 网络通信 物联网

北京市海淀区中关村大街18号B座15层1530室 电话:(010)82350740 邮编:100190

电子工程世界版权所有 京B2-20211791 京ICP备10001474号-1 电信业务审批[2006]字第258号函 京公网安备 11010802033920号 Copyright © 2005-2025 EEWORLD.com.cn, Inc. All rights reserved
快速回复 返回顶部 返回列表