亚洲欧美第一页_禁久久精品乱码_粉嫩av一区二区三区免费野_久草精品视频

? 歡迎來到蟲蟲下載站! | ?? 資源下載 ?? 資源專輯 ?? 關于我們
? 蟲蟲下載站

?? driver.cpp

?? 《Windows驅動開發技術詳解》隨書源碼
?? CPP
字號:
/************************************************************************
* 文件名稱:Driver.cpp                                                 
* 作    者:張帆
* 完成日期:2007-11-1
*************************************************************************/

#include "Driver.h"

/************************************************************************
* 函數名稱:DriverEntry
* 功能描述:初始化驅動程序,定位和申請硬件資源,創建內核對象
* 參數列表:
      pDriverObject:從I/O管理器中傳進來的驅動對象
      pRegistryPath:驅動程序在注冊表的中的路徑
* 返回 值:返回初始化驅動狀態
*************************************************************************/
#pragma INITCODE
extern "C" NTSTATUS DriverEntry (
			IN PDRIVER_OBJECT pDriverObject,
			IN PUNICODE_STRING pRegistryPath	) 
{
	NTSTATUS ntStatus;
	KdPrint(("DriverB:Enter B DriverEntry\n"));

	//注冊其他驅動調用函數入口
	pDriverObject->DriverUnload = HelloDDKUnload;
	pDriverObject->MajorFunction[IRP_MJ_CREATE] = HelloDDKCreate;
	pDriverObject->MajorFunction[IRP_MJ_CLOSE] = HelloDDKClose;
	pDriverObject->MajorFunction[IRP_MJ_WRITE] = HelloDDKDispatchRoutine;
	pDriverObject->MajorFunction[IRP_MJ_READ] = HelloDDKRead;
	
	UNICODE_STRING DeviceName;
	RtlInitUnicodeString( &DeviceName, L"\\Device\\MyDDKDeviceA" );

	PDEVICE_OBJECT DeviceObject = NULL;
	PFILE_OBJECT FileObject = NULL;
	//尋找DriverA創建的設備對象
	ntStatus = IoGetDeviceObjectPointer(&DeviceName,FILE_ALL_ACCESS,&FileObject,&DeviceObject);

	if (!NT_SUCCESS(ntStatus))
	{
		KdPrint(("DriverB:IoGetDeviceObjectPointer() 0x%x\n", ntStatus ));
		return ntStatus;
	}

	//創建自己的驅動設備對象
	ntStatus = CreateDevice(pDriverObject);

	if ( !NT_SUCCESS( ntStatus ) )
	{
		ObDereferenceObject( FileObject );
		DbgPrint( "IoCreateDevice() 0x%x!\n", ntStatus );
		return ntStatus;
	}

	PDEVICE_EXTENSION pdx = (PDEVICE_EXTENSION) pDriverObject->DeviceObject->DeviceExtension;

	PDEVICE_OBJECT FilterDeviceObject = pdx->pDevice;

	//將自己的設備對象掛載在DriverA的設備對象上
	PDEVICE_OBJECT TargetDevice = IoAttachDeviceToDeviceStack( FilterDeviceObject,
										  DeviceObject );
	//將底層設備對象記錄下來
	pdx->TargetDevice = TargetDevice;
	
	if ( !TargetDevice )
	{
		ObDereferenceObject( FileObject );
		IoDeleteDevice( FilterDeviceObject );
		DbgPrint( "IoAttachDeviceToDeviceStack() 0x%x!\n", ntStatus );
		return STATUS_INSUFFICIENT_RESOURCES;
	}

	FilterDeviceObject->DeviceType = TargetDevice->DeviceType;
	FilterDeviceObject->Characteristics = TargetDevice->Characteristics;
	FilterDeviceObject->Flags &= ~DO_DEVICE_INITIALIZING;
	FilterDeviceObject->Flags |= ( TargetDevice->Flags & ( DO_DIRECT_IO |
														 DO_BUFFERED_IO ) );
	ObDereferenceObject( FileObject );

	KdPrint(("DriverB:B attached A successfully!\n"));
	
	KdPrint(("DriverB:Leave B DriverEntry\n"));
	return ntStatus;
}

/************************************************************************
* 函數名稱:CreateDevice
* 功能描述:初始化設備對象
* 參數列表:
      pDriverObject:從I/O管理器中傳進來的驅動對象
* 返回 值:返回初始化狀態
*************************************************************************/
#pragma INITCODE
NTSTATUS CreateDevice (
		IN PDRIVER_OBJECT	pDriverObject) 
{
	NTSTATUS ntStatus;
	PDEVICE_OBJECT pDevObj;
	PDEVICE_EXTENSION pDevExt;
	
	//創建設備名稱
	UNICODE_STRING devName;
	RtlInitUnicodeString(&devName,L"\\Device\\MyDDKDeviceB");
	
	//創建設備
	ntStatus = IoCreateDevice( pDriverObject,
						sizeof(DEVICE_EXTENSION),
						&(UNICODE_STRING)devName,
						FILE_DEVICE_UNKNOWN,
						0, TRUE,
						&pDevObj );
	if (!NT_SUCCESS(ntStatus))
		return ntStatus;

	pDevObj->Flags |= DO_DIRECT_IO;
	pDevExt = (PDEVICE_EXTENSION)pDevObj->DeviceExtension;
	pDevExt->pDevice = pDevObj;
	pDevExt->ustrDeviceName = devName;
	return STATUS_SUCCESS;
}

/************************************************************************
* 函數名稱:HelloDDKUnload
* 功能描述:負責驅動程序的卸載操作
* 參數列表:
      pDriverObject:驅動對象
* 返回 值:返回狀態
*************************************************************************/
#pragma PAGEDCODE
VOID HelloDDKUnload (IN PDRIVER_OBJECT pDriverObject) 
{
	PDEVICE_OBJECT	pNextObj;
	KdPrint(("DriverB:Enter B DriverUnload\n"));
	pNextObj = pDriverObject->DeviceObject;

	while (pNextObj != NULL) 
	{
		PDEVICE_EXTENSION pDevExt = (PDEVICE_EXTENSION)
			pNextObj->DeviceExtension;
		pNextObj = pNextObj->NextDevice;
		//從設備棧中彈出
		IoDetachDevice( pDevExt->TargetDevice);
		//刪除該設備對象
		IoDeleteDevice( pDevExt->pDevice );
	}
	KdPrint(("DriverB:Enter B DriverUnload\n"));
}

/************************************************************************
* 函數名稱:HelloDDKDispatchRoutine
* 功能描述:對讀IRP進行處理
* 參數列表:
      pDevObj:功能設備對象
      pIrp:從IO請求包
* 返回 值:返回狀態
*************************************************************************/
#pragma PAGEDCODE
NTSTATUS HelloDDKDispatchRoutine(IN PDEVICE_OBJECT pDevObj,
								 IN PIRP pIrp) 
{
	KdPrint(("DriverB:Enter B HelloDDKDispatchRoutine\n"));
	NTSTATUS ntStatus = STATUS_SUCCESS;
	// 完成IRP
	pIrp->IoStatus.Status = ntStatus;
	pIrp->IoStatus.Information = 0;	// bytes xfered
	IoCompleteRequest( pIrp, IO_NO_INCREMENT );
	KdPrint(("DriverB:Leave B HelloDDKDispatchRoutine\n"));
	return ntStatus;
}

#pragma PAGEDCODE
NTSTATUS HelloDDKCreate(IN PDEVICE_OBJECT pDevObj,
								 IN PIRP pIrp) 
{
	KdPrint(("DriverB:Enter B HelloDDKCreate\n"));
	NTSTATUS ntStatus = STATUS_SUCCESS;
	//
// 	// 完成IRP
// 	pIrp->IoStatus.Status = ntStatus;
// 	pIrp->IoStatus.Information = 0;	// bytes xfered
// 	IoCompleteRequest( pIrp, IO_NO_INCREMENT );

	PDEVICE_EXTENSION pdx = (PDEVICE_EXTENSION)pDevObj->DeviceExtension;

    IoSkipCurrentIrpStackLocation (pIrp);

    ntStatus = IoCallDriver(pdx->TargetDevice, pIrp);

	KdPrint(("DriverB:Leave B HelloDDKCreate\n"));

	return ntStatus;
}

const int MAX_PACKAGE_SIZE=1024;

#pragma PAGEDCODE
NTSTATUS
HelloDDKReadCompletion(
    IN PDEVICE_OBJECT DeviceObject,
    IN PIRP           Irp,
    IN PVOID          Context
    )
{
	KdPrint(("DriverB:Enter B HelloDDKReadCompletion\n"));

	PMYDRIVER_RW_CONTEXT rwContext = (PMYDRIVER_RW_CONTEXT) Context;
    NTSTATUS ntStatus = Irp->IoStatus.Status;

	ULONG stageLength;

	if(rwContext && NT_SUCCESS(ntStatus)) 
	{
		//已經傳送了多少字節
		rwContext->Numxfer += Irp->IoStatus.Information;

       if(rwContext->Length) 
	   {
		   //設定下一階段讀取字節數
            if(rwContext->Length > MAX_PACKAGE_SIZE) 
			{
				stageLength = MAX_PACKAGE_SIZE;
            }
            else 
			{
                stageLength = rwContext->Length;
            }
			//重新利用MDL
            MmPrepareMdlForReuse(rwContext->NewMdl);

            IoBuildPartialMdl(Irp->MdlAddress,
                              rwContext->NewMdl,
                              (PVOID) rwContext->VirtualAddress,
                              stageLength);
        
            rwContext->VirtualAddress += stageLength;
            rwContext->Length -= stageLength;

			IoCopyCurrentIrpStackLocationToNext(Irp);
            PIO_STACK_LOCATION nextStack = IoGetNextIrpStackLocation(Irp);

			nextStack->Parameters.Read.Length = stageLength;

            IoSetCompletionRoutine(Irp,
                                   HelloDDKReadCompletion,
                                   rwContext,
                                   TRUE,
                                   TRUE,
                                   TRUE);

            IoCallDriver(rwContext->DeviceExtension->TargetDevice, 
                         Irp);

            return STATUS_MORE_PROCESSING_REQUIRED;
        }
        else 
		{
			//最后一次傳輸
            Irp->IoStatus.Information = rwContext->Numxfer;
        }
	}

	KdPrint(("DriverB:Leave B HelloDDKReadCompletion\n"));
	return STATUS_MORE_PROCESSING_REQUIRED;  
}

#pragma PAGEDCODE
NTSTATUS HelloDDKRead(IN PDEVICE_OBJECT pDevObj,
								 IN PIRP pIrp) 
{
	KdPrint(("DriverB:Enter B HelloDDKRead\n"));
	NTSTATUS status = STATUS_SUCCESS;

	PDEVICE_EXTENSION pDevExt = (PDEVICE_EXTENSION)
		pDevObj->DeviceExtension;

	PIO_STACK_LOCATION stack = IoGetCurrentIrpStackLocation(pIrp);
	
	ULONG totalLength;
	ULONG stageLength;
	PMDL mdl;
	PVOID virtualAddress;
	PMYDRIVER_RW_CONTEXT rwContext = NULL;
	PIO_STACK_LOCATION nextStack;

	if (!pIrp->MdlAddress)
	{
		status = STATUS_UNSUCCESSFUL;
		totalLength = 0;
		goto HelloDDKRead_EXIT;
	}

	//獲取MDL的虛擬地址
	virtualAddress = MmGetMdlVirtualAddress(pIrp->MdlAddress);
	//獲取MDL的長度
	totalLength = MmGetMdlByteCount(pIrp->MdlAddress);

	KdPrint(("DriverB:(pIrp->MdlAddress)MmGetMdlVirtualAddress:%08X\n",MmGetMdlVirtualAddress(pIrp->MdlAddress)));
	KdPrint(("DriverB:(pIrp->MdlAddress)MmGetMdlByteCount:%d\n",MmGetMdlByteCount(pIrp->MdlAddress)));

	//將總的傳輸,分成幾個階段,這里設定每次階段的長度
    if(totalLength > MAX_PACKAGE_SIZE) 
	{
        stageLength = MAX_PACKAGE_SIZE;
    }else 
	{
        stageLength = totalLength;
    }

	//創建新的MDL
    mdl = IoAllocateMdl((PVOID) virtualAddress,
                        totalLength,
                        FALSE,
                        FALSE,
                        NULL);

	KdPrint(("DriverB:(new mdl)MmGetMdlVirtualAddress:%08X\n",MmGetMdlVirtualAddress(mdl)));
	KdPrint(("DriverB:(new mdl)MmGetMdlByteCount:%d\n",MmGetMdlByteCount(mdl)));

    if(mdl == NULL) 
	{
		KdPrint(("DriverB:Failed to alloc mem for mdl\n"));
		status = STATUS_INSUFFICIENT_RESOURCES;
		goto HelloDDKRead_EXIT;
    }

	//將IRP的MDL做重新映射
    IoBuildPartialMdl(pIrp->MdlAddress,
                      mdl,
                      (PVOID) virtualAddress,
                      stageLength);
	KdPrint(("DriverB:(new mdl)MmGetMdlVirtualAddress:%08X\n",MmGetMdlVirtualAddress(mdl)));
	KdPrint(("DriverB:(new mdl)MmGetMdlByteCount:%d\n",MmGetMdlByteCount(mdl)));

	rwContext = (PMYDRIVER_RW_CONTEXT)
                ExAllocatePool(NonPagedPool,sizeof(MYDRIVER_RW_CONTEXT));

    rwContext->NewMdl			= mdl;
	rwContext->PreviousMdl		= pIrp->MdlAddress;
    rwContext->Length			= totalLength - stageLength;//還剩下多少沒讀取
    rwContext->Numxfer			= 0;						//讀了多少字節
    rwContext->VirtualAddress	= ((ULONG_PTR)virtualAddress + stageLength);//下一階段開始讀取的地址
	rwContext->DeviceExtension	= pDevExt;

	//拷貝到底層堆棧
	IoCopyCurrentIrpStackLocationToNext(pIrp);

	nextStack = IoGetNextIrpStackLocation(pIrp);
	//根據底層驅動的實現,底層驅動有可能讀取這個數值,也有可能讀取mdl的length。
	nextStack->Parameters.Read.Length = stageLength;

	pIrp->MdlAddress = mdl;
	
	//設定完成例程
    IoSetCompletionRoutine(pIrp, 
                           (PIO_COMPLETION_ROUTINE)HelloDDKReadCompletion,
                           rwContext,
                           TRUE,
                           TRUE,
                           TRUE);

    IoCallDriver(pDevExt->TargetDevice,pIrp);
	
	pIrp->MdlAddress = rwContext->PreviousMdl;
	IoFreeMdl(rwContext->NewMdl);

HelloDDKRead_EXIT:
	// 完成IRP
	pIrp->IoStatus.Status = status;
	pIrp->IoStatus.Information = totalLength;	// bytes xfered
	IoCompleteRequest( pIrp, IO_NO_INCREMENT );
	KdPrint(("DriverB:Leave B HelloDDKRead\n"));
	return status;
}

#pragma PAGEDCODE
NTSTATUS HelloDDKClose(IN PDEVICE_OBJECT pDevObj,
								 IN PIRP pIrp) 
{
	KdPrint(("DriverB:Enter B HelloDDKClose\n"));
	NTSTATUS ntStatus = STATUS_SUCCESS;

	PDEVICE_EXTENSION pdx = (PDEVICE_EXTENSION)pDevObj->DeviceExtension;

    IoSkipCurrentIrpStackLocation (pIrp);

    ntStatus = IoCallDriver(pdx->TargetDevice, pIrp);	
	
	KdPrint(("DriverB:Leave B HelloDDKClose\n"));

	return ntStatus;
}

?? 快捷鍵說明

復制代碼 Ctrl + C
搜索代碼 Ctrl + F
全屏模式 F11
切換主題 Ctrl + Shift + D
顯示快捷鍵 ?
增大字號 Ctrl + =
減小字號 Ctrl + -
亚洲欧美第一页_禁久久精品乱码_粉嫩av一区二区三区免费野_久草精品视频
精品人伦一区二区色婷婷| 91视视频在线观看入口直接观看www | 中文字幕一区二| 99r国产精品| 一区二区三区四区在线播放| 91成人在线精品| 亚洲一区二区三区在线播放| 4438亚洲最大| 国产精品资源在线| 中文字幕一区二区三区在线观看| 91亚洲精品久久久蜜桃| 亚洲国产一区视频| 欧美一区午夜视频在线观看| 激情综合五月天| 欧美国产精品一区二区三区| 在线一区二区视频| 喷白浆一区二区| 久久免费精品国产久精品久久久久| 福利电影一区二区| 亚洲码国产岛国毛片在线| 欧美日韩一级二级三级| 精品一区二区三区视频在线观看| 国产精品人妖ts系列视频| 色婷婷久久久亚洲一区二区三区| 污片在线观看一区二区| 久久伊99综合婷婷久久伊| 9人人澡人人爽人人精品| 午夜av一区二区| 精品av久久707| 91麻豆.com| 九色|91porny| 亚洲国产视频在线| 久久久久久久综合狠狠综合| 色婷婷av一区二区三区gif| 麻豆成人在线观看| 一区二区三区在线观看动漫| 日韩精品一区二区三区视频播放| av毛片久久久久**hd| 免费高清不卡av| 一区二区视频在线看| 26uuu精品一区二区三区四区在线 26uuu精品一区二区在线观看 | 亚洲va欧美va国产va天堂影院| 日韩一区二区电影网| 91亚洲永久精品| 国模套图日韩精品一区二区| 亚洲一卡二卡三卡四卡五卡| 国产亚洲欧美日韩俺去了| 欧美日韩国产高清一区二区| 9色porny自拍视频一区二区| 国产精品77777| 麻豆精品国产传媒mv男同| 亚洲靠逼com| 国产精品亲子乱子伦xxxx裸| 欧美成人a∨高清免费观看| 欧美日韩亚洲国产综合| 91日韩在线专区| 国产盗摄一区二区| 精品制服美女丁香| 亚洲va欧美va人人爽午夜| 亚洲视频免费看| 欧美国产视频在线| 国产午夜精品在线观看| 精品国产乱码久久久久久影片| 欧美疯狂做受xxxx富婆| 91福利国产精品| 91久久线看在观草草青青| 国产mv日韩mv欧美| 国产福利精品导航| 国产盗摄视频一区二区三区| 国产一区二区伦理| 国产一二精品视频| 久久av资源网| 久久国内精品自在自线400部| 午夜欧美在线一二页| 亚洲蜜桃精久久久久久久| 亚洲色图19p| 一区二区三区日韩精品视频| 亚洲免费观看高清完整版在线观看| 国产精品久久久久久久久免费樱桃| 国产欧美日韩精品a在线观看| 久久久久国产免费免费| 国产欧美一区二区三区在线看蜜臀 | 久久蜜臀精品av| 久久中文娱乐网| 国产欧美综合在线观看第十页| 国产片一区二区| 日韩久久一区二区| 国产在线精品一区二区| 激情五月激情综合网| 国产高清不卡一区| 91在线视频免费91| 欧美在线不卡视频| 91麻豆精品国产91久久久使用方法| 欧美精品一级二级| 日韩精品一区二区三区蜜臀| 久久精品网站免费观看| 亚洲欧美在线观看| 亚洲成va人在线观看| 经典三级一区二区| aaa欧美日韩| 欧美疯狂做受xxxx富婆| 久久综合给合久久狠狠狠97色69| 日本一区二区三级电影在线观看| 国产精品久久久久久久蜜臀 | 欧美乱熟臀69xxxxxx| 日韩欧美123| 中文字幕一区二区三区不卡在线 | 亚洲男人天堂av网| 日本特黄久久久高潮| 国产精品自产自拍| 在线观看av一区| 久久久久久99精品| 午夜久久电影网| 国产成人精品免费视频网站| 欧美性猛交xxxx乱大交退制版 | 中文字幕日本乱码精品影院| 亚洲国产精品一区二区尤物区| 美女免费视频一区| 97精品电影院| 精品99久久久久久| 亚洲一区二区三区中文字幕在线| 精品一二三四在线| 日本久久一区二区| 久久人人爽爽爽人久久久| 亚洲精品五月天| 国内外成人在线| 欧美日韩免费一区二区三区视频| 久久先锋影音av鲁色资源 | 三级一区在线视频先锋| 国产精品77777| 欧美一级理论片| 亚洲美女少妇撒尿| 福利电影一区二区三区| 91精品视频网| 亚洲一区二区高清| 91在线视频网址| 国产香蕉久久精品综合网| 日韩avvvv在线播放| 色哟哟一区二区在线观看 | 日韩欧美国产系列| 亚洲一区欧美一区| 成人福利电影精品一区二区在线观看| 日韩视频一区二区三区在线播放| 亚洲美女区一区| 不卡一区中文字幕| 久久精品人人做人人综合| 免费成人性网站| 91精品国产欧美日韩| 亚洲影院免费观看| 色综合久久99| 亚洲欧美日韩国产综合在线| 成人高清免费在线播放| 久久精品在这里| 九色综合国产一区二区三区| 51精品国自产在线| 日韩电影一区二区三区四区| 欧美专区日韩专区| 夜夜精品视频一区二区| 91在线你懂得| 一区二区三区美女| 色婷婷综合激情| 亚洲午夜羞羞片| 在线观看日韩一区| 亚洲一二三四在线| 色88888久久久久久影院野外| 亚洲三级视频在线观看| 色网站国产精品| 夜夜嗨av一区二区三区网页| 欧美在线观看视频在线| 午夜欧美在线一二页| 欧美嫩在线观看| 免费日韩伦理电影| 久久久综合精品| 成人高清免费观看| 一区二区欧美国产| 在线电影国产精品| 蜜桃av一区二区在线观看| 久久毛片高清国产| 99久久99久久精品国产片果冻| 中文字幕一区二区三区在线观看| 色婷婷激情久久| 欧美a级理论片| 久久久亚洲精品一区二区三区| 国产大陆精品国产| 一区二区三区国产精品| 欧美三日本三级三级在线播放| 日韩高清一区在线| 久久先锋影音av鲁色资源网| 99久久精品国产麻豆演员表| 亚洲午夜精品久久久久久久久| 91精品国产美女浴室洗澡无遮挡| 精品在线视频一区| 亚洲三级在线看| 欧美一区二区私人影院日本| 国产一区二区三区免费在线观看 | 亚洲五码中文字幕| 精品成人一区二区三区| 99久久精品久久久久久清纯| 亚洲va欧美va人人爽午夜| 国产性色一区二区|