2.3重要的数据结构 - 驱动对象和设备对象

Windows内核中把驱动,设备,文件等都称为"对象",在系统启动后,这些对象都在内存中.

一个驱动对象(DRIVER_OBJECT)代表了一个驱动程序,或者是内核模块.

设备对象(DEVICE_OBJECT)是在内核中唯一接收请求的实体.大部分消息都是以请求(IRP)方式传递的,而任何一个请求都是发送被某个设备对象的.设备对象是驱动对象结构的第三个参数对象.

内核程序是以一个驱动对象表示的,所以一个设备对象总是属于一个驱动对象.

驱动对象结构:

typedef struct _DRIVER_OBJECT{

CSHORT Type;

CSHORT Size;

//设备对象,是一个设备对象链表的开始.

PDEVICE_OBJECT DeviceObject;

ULONG Flags;

//驱动在内核空间的开始地址和大小

PVOID DriverStart;

ULONG DriverSize;

PVOID DriverSection;

PDRIVER_EXTENSION DriverExtension;

//驱动的名字,确定一个I/O请求被绑定的驱动程序的名称

UNICODE_STRING DriverName;

//指向注册表中的硬件信息的路径

PUNICODE_STRING HardwareDatabase;

//快速IO分发函数的入口,数组的可选指针,通过参数单独调用驱动程序执行,而不是使用IRP(操作系统内核的一个数据结构,应用程序与驱动程序进行通信需要通过IRP包)调用机制,这些功能只能被用户同步IO或者文件缓存

PFAST_IO_DISPATCH FastIoDispatch;

//驱动程序初始化

PDRIVER_INITIALIZE DriverInit;

//特定入口,

PDRIVER_STARTIO DriverStartIo;

//驱动卸载函数

PDRIVER_UNLOAD DriverUnload;

//普通分发函数(IRP)

PDRIVER_DISPATCH MajorFunction[IRP_MJ_MAXIMUM_FUNCTION + 1];

} DRIVER_OBJECT;

设备对象结构:

typedef struct DECLSPEC_ALIGN(MEMORY_ALLOCATION_ALIGNMENT) _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;

//IRP栈的大小

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;

IRP向设备对象发送请求时会被驱动对象的分发函数捕获,被其中一个调用

分发函数原型

NTSTATUS MyDispatch(PDEVICE_OBJECT device, PIRP irp);

参数1是请求的目标设备,参数2是IRP请求的指针

IRP的结构

IRP是一个内核数据结构,结构非常复杂,因为要表示无数中实际请求.

typedef struct DECLSPEC_ALIGN(MEMORY_ALLOCATION_ALIGNMENT) _IRP 共300多行代码,位于 wdm.h 24795行

其中

PMDL MdlAddress; 内存描述符表链表指针,是一个缓冲区,内核请求都需要一个缓冲区,用来保存数据

union {

struct _IRP *MasterIrp;

__volatile LONG IrpCount;

PVOID SystemBuffer;

} AssociatedIrp; 该共用体也是一个系统缓冲,比 MdlAddress 稍简单表示缓冲的方式,IRP会根据IO的请求方式选择其中的某一个.

IO_STATUS_BLOCK IoStatus; IO状态,请求完成之后的返回情况放在这里.

CHAR StackCount; IRP栈空间大小

CHAR CurrentLocation; IRP当前栈空间

__volatile PDRIVER_CANCEL CancelRoutine; 用来取消一个未决(没有执行完成?)请求的函数

PVOID UserBuffer; 与上面两个一样可以表示缓冲区,但特性稍有不同

union {

struct {

union {

KDEVICE_QUEUE_ENTRY DeviceQueueEntry;

struct {

PVOID DriverContext[4];

} ;

} ;

//发出这个请求的线程

PETHREAD Thread;

PCHAR AuxiliaryBuffer;

struct {

LIST_ENTRY ListEntry;

union {

//IRP栈空间元素

struct _IO_STACK_LOCATION *CurrentStackLocation;

ULONG PacketType;

};

};

PFILE_OBJECT OriginalFileObject;

} Overlay;

KAPC Apc;

PVOID CompletionKey;

} Tail;

因为IRP请求会传递许多个设备才能完成,所以每次中转都会留一个栈空间,用于保存中间参数.

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 158,736评论 4 362
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 67,167评论 1 291
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 108,442评论 0 243
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 43,902评论 0 204
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 52,302评论 3 287
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 40,573评论 1 216
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 31,847评论 2 312
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 30,562评论 0 197
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 34,260评论 1 241
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 30,531评论 2 245
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 32,021评论 1 258
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 28,367评论 2 253
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 33,016评论 3 235
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 26,068评论 0 8
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 26,827评论 0 194
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 35,610评论 2 274
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 35,514评论 2 269

推荐阅读更多精彩内容

  • 技术原理 何为符号链接?符号链接是一个别名,可以指向任意一个有名字的对象. ZwCreateFile 不但可以打开...
    f675b1a02698阅读 540评论 0 0
  • 设备绑定的内核API之一 驱动 --> 生成多个 --> 设备对象 --> 对应 --> 真实的一个设备 wind...
    f675b1a02698阅读 622评论 0 0
  • 原文链接1、驱动对象:一个驱动对象代表了一个驱动程序。或者说一个内核模块。驱动对象的结构如下(这个结构的定义取自 ...
    Quinton_Lau阅读 1,514评论 0 0
  • 引言 总结一下最近设备驱动的学习成果,记录一下心得。文章里穿插记录字符设备驱动的相关知识。 硬件相关 一 ...
    three_eyelid阅读 1,135评论 1 1
  • 如果驱动程序要和应用程序通信,那么要生成一个设备对象. 设备对象和分发函数构成了整个内核体系的基本框架. 设备对象...
    f675b1a02698阅读 1,187评论 0 0