首页
社区
课程
招聘
[原创]Windows驱动程序框架
发表于: 2013-8-9 22:43 20834

[原创]Windows驱动程序框架

2013-8-9 22:43
20834

windows驱动程序入门比较坑爹一点,本文旨在降低入门的门槛。注:下面的主要以NT式驱动为例,部分涉及到WDM驱动的差别会有特别说明。

首先,肯定是配置好对应的开发环境啦,不懂的就百度下吧,这里不再次描述了。

在Console控制台下,我们的有一个入口函数main;在Windows图形界面平台下,有另外一个入口函数Winmain。我们只要在这入口函数里面调用其他相关的函数,程序就会按照我们的意愿跑起来了。在我们用IDE开发的时候,也许你不会发现这些细微之处是如何配置出来的,一般来说我们也不用理会,因为在新建工程的时候,IDE已经帮我们把编译器(Compiler)以及连接器(Linker)的相关参数设置好,在正式编程的时候,我们只要按照规定的框架编程就行了。

同样,在驱动程序也有一个入口函数DriverEntry,这并不是一定的,但这是微软默认的、推荐使用的。在我们配置开发环境的时候我们有机会指定入口函数,这是链接器的参数/entry:"DriverEntry"。

入口函数的声明

NTSTATUS DriverEntry(PDRIVER_OBJECT pDriverObject,PUNICODE_STRING pRegistryPath)  
#define NT_SUCCESS(Status) (((NTSTATUS)(Status)) >= 0)  
#define NT_INFORMATION(Status) ((((ULONG)(Status)) >> 30) == 1)  
#define NT_WARNING(Status) ((((ULONG)(Status)) >> 30) == 2)  
#define NT_ERROR(Status) ((((ULONG)(Status)) >> 30) == 3)  
typedef struct _UNICODE_STRING {  
  USHORT  Length;  
  USHORT  MaximumLength;  
  PWSTR  Buffer;  
} UNICODE_STRING, *PUNICODE_STRING;  
typedef struct _DRIVER_OBJECT {  
    CSHORT Type;  
    CSHORT Size;  
    PDEVICE_OBJECT DeviceObject;  
    ULONG Flags;  
    PVOID DriverStart;  
    ULONG DriverSize;  
    PVOID DriverSection;  
    PDRIVER_EXTENSION DriverExtension;  
    UNICODE_STRING DriverName;  
    PUNICODE_STRING HardwareDatabase;  
    PFAST_IO_DISPATCH FastIoDispatch;  
    PDRIVER_INITIALIZE DriverInit;  
    PDRIVER_STARTIO DriverStartIo;  
    PDRIVER_UNLOAD DriverUnload;  
    PDRIVER_DISPATCH MajorFunction[IRP_MJ_MAXIMUM_FUNCTION + 1];  
} DRIVER_OBJECT;  
typedef struct _DEVICE_OBJECT {  
  CSHORT                      Type;  
  USHORT                      Size;  
  LONG                        ReferenceCount;  
  struct _DRIVER_OBJECT  *DriverObject;  
  struct _DEVICE_OBJECT  *NextDevice;  
  struct _DEVICE_OBJECT  *AttachedDevice;  
  struct _IRP  *CurrentIrp;  
  PIO_TIMER                   Timer;  
  ULONG                       Flags;  
  ULONG                       Characteristics;  
  __volatile PVPB             Vpb;  
  PVOID                       DeviceExtension;  
  DEVICE_TYPE                 DeviceType;  
  CCHAR                       StackSize;  
  union {  
    LIST_ENTRY         ListEntry;  
    WAIT_CONTEXT_BLOCK Wcb;  
  } Queue;  
  ULONG                       AlignmentRequirement;  
  KDEVICE_QUEUE               DeviceQueue;  
  KDPC                        Dpc;  
  ULONG                       ActiveThreadCount;  
  PSECURITY_DESCRIPTOR        SecurityDescriptor;  
  KEVENT                      DeviceLock;  
  USHORT                      SectorSize;  
  USHORT                      Spare1;  
  struct _DEVOBJ_EXTENSION  *  DeviceObjectExtension;  
  PVOID                       Reserved;  
} DEVICE_OBJECT, *PDEVICE_OBJECT;  
#ifdef __cplusplus
extern "C"
{
#endif

#include <NTDDK.h>

#ifdef __cplusplus
};
#endif

#define PAGECODE code_seg("PAGE")
#define LOCKEDCODE code_seg()
#define INITCODE code_seg("INIT")

#define PAGEDATA data_seg("PAGE")
#define LOCKEDDATA data_seg()
#define INITDATA data_seg("INIT")


typedef struct _DEVICE_EXTENSION
{
	PDEVICE_OBJECT pDevice;
	UNICODE_STRING ustrDeviceName;
	UNICODE_STRING ustrSymLinkName;
} DEVICE_EXTENSION , *PDEVICE_EXTENSION;

//函数声明
NTSTATUS DispatchRoutine(__in struct _DEVICE_OBJECT  *DeviceObject, __in struct _IRP  *Irp);
VOID UnloadRoutine(__in struct _DRIVER_OBJECT  *DriverObject);

///////////////////////
#pragma INITCODE
extern "C" NTSTATUS DriverEntry(PDRIVER_OBJECT pDriverObject,
								PUNICODE_STRING pRegistryPath)
{
	NTSTATUS status;
	PDEVICE_EXTENSION pDevExt;
	PDEVICE_OBJECT pDevObj;
	KdPrint(("\n--------------------------------------!\n"));
	KdPrint(("Enter DriverEntry!\n"));
	//注册相关例程
	pDriverObject->DriverUnload = UnloadRoutine;
	pDriverObject->MajorFunction[IRP_MJ_CREATE]	=	DispatchRoutine;
	pDriverObject->MajorFunction[IRP_MJ_READ]	=	DispatchRoutine;
	pDriverObject->MajorFunction[IRP_MJ_WRITE]	=	DispatchRoutine;
	pDriverObject->MajorFunction[IRP_MJ_CLOSE]	=	DispatchRoutine;

	//初始化相关字符串
	UNICODE_STRING ustrDeviceName;	//设备名
	UNICODE_STRING ustrSymLinkName; //符号链接名

	RtlInitUnicodeString(&ustrDeviceName,L"\\Device\\MyDDKDevice1");
	RtlInitUnicodeString(&ustrSymLinkName,L"\\??\\MyDDKDriver1");

	//创建设备对象
	
	status = IoCreateDevice(pDriverObject,sizeof(DEVICE_EXTENSION),&ustrDeviceName,FILE_DEVICE_UNKNOWN,0,TRUE,&pDevObj);
	if (!NT_SUCCESS(status))
	{
		KdPrint(("Create Device Failure!\n"));
		return status;	
	}
	pDevObj->Flags |= DO_BUFFERED_IO;
	pDevExt = (PDEVICE_EXTENSION)pDevObj->DeviceExtension;
	pDevExt->ustrDeviceName = ustrDeviceName;
	pDevExt->pDevice = pDevObj;

	//创建符号链接
	pDevExt->ustrSymLinkName = ustrSymLinkName;
	status = IoCreateSymbolicLink(&ustrSymLinkName,&ustrDeviceName);
	if (!NT_SUCCESS(status))
	{
		IoDeleteDevice(pDevObj);
		return status;
	}
	KdPrint(("Leave DriverEntry! stauts=%d",status));
	return status;
}

[注意]传递专业知识、拓宽行业人脉——看雪讲师团队等你加入!

上传的附件:
收藏
免费 5
支持
分享
最新回复 (18)
雪    币: 5199
活跃值: (3437)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
2
谢谢,好人一生平安。
2013-8-9 23:51
0
雪    币: 245
活跃值: (13)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
3
学习了谢谢分享
2013-8-9 23:51
0
雪    币: 1088
活跃值: (30)
能力值: ( LV3,RANK:20 )
在线值:
发帖
回帖
粉丝
4
收藏了..最近正在入门驱动
2013-8-10 01:17
0
雪    币: 81
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
5
谢谢分享
2013-8-10 08:43
0
雪    币: 11
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
6
mark
2013-8-12 17:55
0
雪    币: 53
活跃值: (42)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
7
卧槽,太详细了,可以当教材了
2013-12-21 10:43
0
雪    币: 154
活跃值: (91)
能力值: ( LV6,RANK:80 )
在线值:
发帖
回帖
粉丝
8
支持。。。mark
2013-12-21 13:45
0
雪    币: 134
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
9
入门……好心人
2013-12-21 23:08
0
雪    币: 3944
活跃值: (2380)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
10
浅显易懂,谢谢!
2013-12-21 23:32
0
雪    币: 217
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
11
做个记号正在学习驱动
2013-12-26 07:23
0
雪    币: 209
活跃值: (143)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
12
这个讲得比较细,而且注意了循序渐进,希望继续发文,整理成一个系列。
2013-12-26 09:02
0
雪    币: 209
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
13
mark~~~
2013-12-26 11:13
0
雪    币: 22
活跃值: (21)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
14
这篇文章对我们这些菜鸟来说作用实在是太大了,非常感谢楼主,希望楼主能够继续出这些浅显易懂的驱动入门帖子,拜谢!
2013-12-26 11:24
0
雪    币: 3366
活跃值: (1353)
能力值: ( LV4,RANK:40 )
在线值:
发帖
回帖
粉丝
15
妙文,果断收藏,弥补了书上一部分没有讲到,
2013-12-26 11:32
0
雪    币: 49
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
16
楼主,请教个问题,code_seg这个必须要添加么?为什么不加上这个驱动也能运行,我用的WDK 7
2014-5-13 20:03
0
雪    币: 201
活跃值: (183)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
17
谢谢楼主分享。
2014-12-10 14:10
0
雪    币: 5
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
18
讲的非常仔细,谢谢分享...
2014-12-30 17:26
0
雪    币: 123
活跃值: (27)
能力值: ( LV5,RANK:60 )
在线值:
发帖
回帖
粉丝
19
这个我之前都看过,竟然挂的是【原创】,是别人抄袭你的?
2014-12-30 17:34
0
游客
登录 | 注册 方可回帖
返回
//