zoukankan      html  css  js  c++  java
  • 派遣函数学习3)其他方式读写设备

    首先    既不设置 DO_DIRECT_IO /  DO_BUFFER_IO

    派遣函数直接读写应用程序提供的缓冲区地址。  直接操应用程序的缓冲区地址是很危险的

    只有驱动程序与应用程序运行再相同线程上下文的时候,才能用这种方式


    探测可读可写用: ProbeForWrite   +   try 块

    NTSTATUS HelloDDKRead(IN PDEVICE_OBJECT pDevObj,
    								 IN PIRP pIrp) 
    {
    	KdPrint(("Enter HelloDDKRead
    "));
    
    	PDEVICE_EXTENSION pDevExt = (PDEVICE_EXTENSION)pDevObj->DeviceExtension;
    	NTSTATUS status = STATUS_SUCCESS;
    
    	//得到当前堆栈
    	PIO_STACK_LOCATION stack = IoGetCurrentIrpStackLocation(pIrp);
    	//得到读的长度
    	ULONG ulReadLength = stack->Parameters.Read.Length;
    	//得到读的偏移量
    	ULONG ulReadOffset = (ULONG)stack->Parameters.Read.ByteOffset.QuadPart;
    	//得到用户模式地址
    	PVOID user_address = pIrp->UserBuffer;
    
    	KdPrint(("user_address:0X%0X
    ",user_address));
    
    	__try
    	{
    		KdPrint(("Enter __try block
    "));
    		//判断空指针是否可写,显然会导致异常
    		ProbeForWrite(user_address,ulReadLength,4);
    
    		memset(user_address,0xAA,ulReadLength);
    
    		//由于在上面引发异常,所以以后语句不会被执行!
    		KdPrint(("Leave __try block
    "));
    	}
    	__except(EXCEPTION_EXECUTE_HANDLER)
    	{
    		KdPrint(("Catch the exception
    "));
    		KdPrint(("The program will keep going
    "));
    		status = STATUS_UNSUCCESSFUL;
    	}
    
    	pIrp->IoStatus.Status = status;
    	pIrp->IoStatus.Information = ulReadLength;	// bytes xfered
    	IoCompleteRequest( pIrp, IO_NO_INCREMENT );
    	KdPrint(("Leave HelloDDKRead
    "));
    
    	return status;
    }


  • 相关阅读:
    DataTable的一些使用技巧
    Linux下使用Mysql
    【Cocos2d-X开发学习笔记】第28期:游戏中音乐和音效的使用
    HDU 4669 Mutiples on a circle (DP , 统计)
    面试经典-设计包含min函数的栈
    最大熵模型
    这篇文章关于两阶段提交和Paxos讲的很好
    【读书笔记】神经网络与深度学习
    这个对协程的分析不错
    sendfile学习
  • 原文地址:https://www.cnblogs.com/zcc1414/p/3982510.html
Copyright © 2011-2022 走看看