+ All Categories
Home > Documents > Windows98/2000 驱动程序编写方法

Windows98/2000 驱动程序编写方法

Date post: 04-Jan-2016
Category:
Upload: rosalyn-morrow
View: 117 times
Download: 2 times
Share this document with a friend
Description:
Windows98/2000 驱动程序编写方法. (上). 杨全胜. 1. 驱动程序的开发环境. 对于 VxD 的开发,需要的开发环境是 : Visual C++ 5.0/6.0 Windosw 95DDK 如果想加快开发步骤,建议使用第三方的 VToolsD 开发工具,它将 DDK 的东西全部封装成 C++ 的类,可以直接用 Visual C++ 编写程序,而无须使用汇编。而且它提供的  QuickVxd 能够方便快速地建立 VxD 程序的框架。. 对于 WDM 的开发,又分几种情况 : 对于 Windows 98 系统 Visual C++ 5.0 - PowerPoint PPT Presentation
61
1 http://qsyang.yeah.n http://qsyang.yeah.n 现现现现现现现现现现现 现现现现现现现现现现现 ( ( 2 2 ) ) Windows98/2000 现现现现现现现现 现现 () 现现现
Transcript
Page 1: Windows98/2000 驱动程序编写方法

1 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))

Windows98/2000 驱动程序编写方法

(上)

杨全胜

Page 2: Windows98/2000 驱动程序编写方法

2 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))

1. 驱动程序的开发环境

对于对于 VxDVxD 的开发,需要的开发环境是的开发,需要的开发环境是::• Visual C++ 5.0/6.0• Windosw 95DDK 如果想加快开发步骤,建议使用第三方的 VToolsD

开发工具,它将 DDK 的东西全部封装成 C++ 的类,可以直接用 Visual C++ 编写程序,而无须使用汇编。而且它提供的 QuickVxd 能够方便快速地建立 VxD 程序的框架。

Page 3: Windows98/2000 驱动程序编写方法

3 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 )) 对于对于 WDMWDM 的开发,又分几种情况的开发,又分几种情况 :1)对于 Windows 98 系统• Visual C++ 5.0Visual C++ 5.0• Windows 98DDKWindows 98DDK2) 对于 Windows Me/2000• Visual C++ 6.0Visual C++ 6.0• Windows 2000DDKWindows 2000DDK3) 对于 Windows XP• Visual C++6.0/.netVisual C++6.0/.net• Windows XPDDKWindows XPDDK 同样,为了方便起见,也可以使用第三方的开发

工具 Driver Works ,它也是将 DDK 的内容封装成类,而且提供一个快速方便地生成驱动框架的工具。

Page 4: Windows98/2000 驱动程序编写方法

4 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))2. 驱动程序开发工具包 DriverStudio2.1 DriverStudio 2.7 所包含的工具• VToolsDVToolsD    VToolsD 是一个用来开发针对 Win9X (Windows 95 和 Windows 98) 操作系统下设备驱动程序 (VxD) 的工具。 VToolsD 中包括生成驱动程序源代码的工具, run-time 和 interface 库,以及一些驱动程序样本,可以用来作为各种类型的设备驱动程序的基础部分。 • DriverWorksDriverWorks    DriverWorks 对于 Windows NT 下和 Windows 98 与 Windows 2000 共同支持的 Win32 驱动模型 (WDM) 设备驱动程序的开发提供完全的支持。 DriverWorks 中包含一个非常完善的源代码生成工具 (DriverWizard) 以及相应的类库和驱动程序样本,它提供了在 C++ 下进行设备驱动程序开发的支持。

Page 5: Windows98/2000 驱动程序编写方法

5 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))• DriverNetworksDriverNetworks

    DriverNetworks 是针对 Windows 网络驱动开发人员的一个模块。在它的核心部分, DriverNetworks 是一个针对 NDIS drivers 和 TDI clients (DriverSockets) 的 C++ 的类库。 DriverNetworks 中也有 Quick Miniport Wizard 用来直接开始一个 NDIS Miniport 或 Intermediate Driver 工程。它可以让你快速的生成所有采用 DriverNetworks C++ 类库编写的 NDIS 驱动程序的编译,安装和调试所需要的文件 。• SoftICESoftICE

    SoftICE 是一个功能极其强大的内核模式调试器,它支持在配置一台单独的计算机或两台计算机下进行设备驱动程序的调试。

Page 6: Windows98/2000 驱动程序编写方法

6 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))• DriverMonitorDriverMonitor

    DriverMonitor 不仅可以显示 WDM 和 VxD 在操作系统核心层次输出的调试语句,还可以装载和卸载 VxD 驱动和 NT4 系统的驱动程序。

• EZDriverInstallerEZDriverInstaller    EZDriverInstaller 是一个无需经过设备管理器或“添加新硬件”功能就能为 Windows 2000/XP 动态加载和卸载 WDM 驱动程序的小实用程序。

• SetDDKGoSetDDKGo    SetDDKGo 用来设置设备驱动程序创建的环境。当我们用 Visual Studio ( VC++ )编译驱动程序源程序的时候,需要用 SetDDKGo 来设置环境变量,之后 SetDDKGo 会自动启动 Visual Studio ( VC++ )编译环境。

Page 7: Windows98/2000 驱动程序编写方法

7 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))2.2 DriverStudio 2.7 的安装安装需要的软硬件环境安装需要的软硬件环境• PC-compatible Intel x86 系统•Windows 2000, (Optional: 其中一些工具也支持 Wind

ows 98 和 Windows 95.)•内存 : 最少 32 MB, 推荐使用 64 MB•硬盘 : 完全安装需要 72 MB•针对 SoftICE 的远程调试 : NE2000- 兼容网卡或 3Co

m 网卡•针对 DriverWorks: Microsoft DDK,MS Visual C++

Page 8: Windows98/2000 驱动程序编写方法

8 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))

安装步骤安装步骤: 在安装 DriverWorks 之前,首先要保证你的计算机上已经安装了 Microsoft Visual C++ 以及相应针对 Windows NT 或 WDM 的 DDK 的正确版本。 所有这些包所有这些包括括 DriverStudioDriverStudio 的安装都必须以系统管理员身份启动的安装都必须以系统管理员身份启动系统。并且要按照下面的顺序安装。系统。并且要按照下面的顺序安装。

第一步: 安装 Microsoft Visual Studio C++ 6.0 (注意 Windows 2000DDK 暂时对 Visual Studio.NET 不支持)

Page 9: Windows98/2000 驱动程序编写方法

9 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))

第二步: 安装 2000DDK ( Driver Development Kits )。注意:注意:1 )如果本地机的操作系统为 Windows2000 请确认已经安装了 Windows SevicePack1 或 Windows SevicePack2 在安装 DDK 的时候请选择完全安装。 2 )安装中,不需要安装 64BIT IA64Binaries 3 )安装好后,对于 2000DDK 不需要手动配置环境变量,只需在开始菜单中点击 Checked Build Envirment 则 DDK 会自动调用 setenv 配置环境变量,并监测相应的 SDK 以及 Visual Studio IDE

Page 10: Windows98/2000 驱动程序编写方法

10 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))第三步: 安装 DriverStudio 2.7 (按照安装提示安装)。注意, 注意, DriverStudio 2.7DriverStudio 2.7 ,包,包括最新的括最新的 DriverStudio 3.0DriverStudio 3.0 不不能在能在 Windows 2000Windows 2000 的的 SP4SP4 和和WindowsXPWindowsXP 上使用,会引起上使用,会引起蓝屏。遇到这种情况,请在安蓝屏。遇到这种情况,请在安装好后不要重新启动机器,而装好后不要重新启动机器,而是立即打上补丁。打补丁的方是立即打上补丁。打补丁的方法是用新的法是用新的 siwvid.sys(siwvid.sys( 补丁的补丁的内容)替换掉内容)替换掉 \%system%\sys\%system%\system32\drivers\tem32\drivers\ 下的老的下的老的 siwvisiwvid.sysd.sys

Page 11: Windows98/2000 驱动程序编写方法

11 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))

DriverStudioDriverStudio 安装后的设置安装后的设置:1 )使用 SetDDKGo 工具定义 BASEDIR 环境变量并启动 MSVC 5.0 或 6.0 ,

Page 12: Windows98/2000 驱动程序编写方法

12 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))

Page 13: Windows98/2000 驱动程序编写方法

13 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))

Page 14: Windows98/2000 驱动程序编写方法

14 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))2 )打开下列地址上的建立库文件工程

Page 15: Windows98/2000 驱动程序编写方法

15 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))

3 )选择 Build|Batch Build (编译 |批构件),打开下面的窗口,从中选则需要编译的配置。

注意不要选择 IA64 的各项, Checked 是调试版本, Free 是发布版本

Page 16: Windows98/2000 驱动程序编写方法

16 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))

4 )点击 Build 编译所选择的库文件。

注意:库文件只需在安装完成后第一次使用前编译一次注意:库文件只需在安装完成后第一次使用前编译一次即可。即可。以后要使用以后要使用 DriverWorksDriverWorks ,只需通过,只需通过 SetDDKGSetDDKGoo 进入进入MSVCMSVC即可。即可。

Page 17: Windows98/2000 驱动程序编写方法

17 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))3. VtoolsD 开发 VxD简介生成简单框架

Page 18: Windows98/2000 驱动程序编写方法

18 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))

动态装载

设备名

编程语言

生成调试用目标代码

Page 19: Windows98/2000 驱动程序编写方法

19 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))

Page 20: Windows98/2000 驱动程序编写方法

20 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))

Page 21: Windows98/2000 驱动程序编写方法

21 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))

与应用程序通信的控制消息

Page 22: Windows98/2000 驱动程序编写方法

22 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))

Page 23: Windows98/2000 驱动程序编写方法

23 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))

虚拟机类名

设备类名

线程类名

Page 24: Windows98/2000 驱动程序编写方法

24 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))

Page 25: Windows98/2000 驱动程序编写方法

25 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))

Page 26: Windows98/2000 驱动程序编写方法

26 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))

Page 27: Windows98/2000 驱动程序编写方法

27 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))

Page 28: Windows98/2000 驱动程序编写方法

28 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))

Page 29: Windows98/2000 驱动程序编写方法

29 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))

Page 30: Windows98/2000 驱动程序编写方法

30 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))

Page 31: Windows98/2000 驱动程序编写方法

31 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))

// MYFIRST.h - include file for VxD MYFIRST// MYFIRST.h - include file for VxD MYFIRST#include <vtoolscp.h>#define DEVICE_CLASS MyfirstDevice#define MYFIRST_DeviceID UNDEFINED_DEVICE_ID#define MYFIRST_Init_Order UNDEFINED_INIT_ORDER#define MYFIRST_Major 1#define MYFIRST_Minor 0#define DIOC_MY_IO CTL_CODE#define DIOC_MY_IO CTL_CODE (( FILE_DEVICE_UNKNOWN, FILE_DEVICE_UNKNOWN, 1, METHOD_NEITHER, FILE_ANY_ACCESS1, METHOD_NEITHER, FILE_ANY_ACCESS ))

// // 定义一个句柄用于应用程序与定义一个句柄用于应用程序与 VxDVxD通信通信

头文件

Page 32: Windows98/2000 驱动程序编写方法

32 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))

class MyfirstDevice : public VDevice{public : virtual DWORD OnW32DeviceIoControl ( PIOCTLPARAMS

pDIOCParams );};class MyfirstVM : public VVirtualMachine{public :

MyfirstVM ( VMHANDLE hVM );};class MyfirstThread : public VThread{public :

MyfirstThread ( THREADHANDLE hThread );};

Page 33: Windows98/2000 驱动程序编写方法

33 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))

// MYFIRST.cpp - main module for VxD MYFIRST#define DEVICE_MAIN#include "myfirst.h"Declare_Virtual_Device ( MYFIRST )#undef DEVICE_MAINMyfirstVM::MyfirstVM(VMHANDLE hVM):VVirtualMachine

( hVM ) {}MyfirstThread::MyfirstThread(THREADHANDLE hThread):

VThread ( hThread ) {}DWORD MyfirstDevice::OnW32DeviceIoControl

( PIOCTLPARAMS pDIOCParams ){ char* msg="欢迎进入虚拟机世界 !"; char* caption="Hello World!";

.cpp 文件

Page 34: Windows98/2000 驱动程序编写方法

34 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))

switch ( pDIOCParams->dioc_IOCtlCode ) {case DIOC_OPEN:dout<<"I am Opening!"; break;

// 调用 CreateFile函数时响应该分支代码case DIOC_MY_IO:dout<<"I am working!"<<endl;

SHELL_Message ( pDIOCParams->dioc_hvm, MB_OK, msg, caption,0,0,0 );

break;// 调用 DeviceIoControl函数时响应该分支下的代码

case DIOC_CLOSEHANDLE : dout<<"I am Closing!"; break;// 调用 CloseHandle函数时响应该分支代码

} return 0;}

Page 35: Windows98/2000 驱动程序编写方法

35 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))

# MYFIRST.mak - makefile for VxD MYFIRSTDEVICENAME = MYFIRSTDYNAMIC = 1FRAMEWORK = CPPDEBUG = 1OBJECTS = myfirst.OBJ!include $ ( VTOOLSD ) \include\vtoolsd.mak!include $ ( VTOOLSD ) \include\vxdtarg.makmyfirst.OBJ : myfirst.cpp myfirst.h

.mak 文件

Page 36: Windows98/2000 驱动程序编写方法

36 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))

Page 37: Windows98/2000 驱动程序编写方法

37 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))

Page 38: Windows98/2000 驱动程序编写方法

38 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))

#include <iostream.h>#include <windows.h>#include <winioctl.h>#define DIOC_MY_IO CTL_CODE ( FILE_DEVICE_UNKNOWN,

1, METHOD_NEITHER, FILE_ANY_ACCESS ) //定义一个句柄用于应用程序与 VxD通信

void main (){

HANDLE hDevice;hDevice=CreateFile ( "\\\\.\\myfirst.vxd", 0

, 0,0,OPEN_EXISTING,

FILE_FLAG_DELETE_ON_CLOSE, 0 );// 文件名的路径一定是以 \\\\.\\打头 ,默认的 VXD 的

文件的目录是 C:\Windows\system, 如果 VXD 在 d:\myvxd目录下,则这里应该写成 "\\\\.\\d : \\myvxd\\myfirst.vxd"

Win32 环境下的控制台程序

Page 39: Windows98/2000 驱动程序编写方法

39 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))

if ( hDevice==INVALID_HANDLE_VALUE ){

cout<<"Open VxD error"<<GetLastError () <<endl;

exit ( 1 );}DeviceIoControl ( hDevice,DIOC_MY_IO,NULL,0,NULL,0,

NULL,NULL ); // 使用句柄 DIOC_MY_IO 与 VxD交互

CloseHandle ( hDevice ); //关闭设备句柄}

Page 40: Windows98/2000 驱动程序编写方法

40 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))VToolsD 的类库

Page 41: Windows98/2000 驱动程序编写方法

41 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))I/O 类

class VIOPort{public : VIOPort ( DWORD port ); //构造函数 ~VIOPort (); //析构函数 BOOL hook (); //挂钩一个端口处理程序 BOOL unhook (); //摘钩一个端口处理程序 VOID localEnable ( VMHANDLE ); //允许监控指定虚拟机端口的 I/O 操作 VOID localDisable ( VMHANDLE ); //禁止监控指定虚拟机端口的 I/O操作 VOID globalEnable (); //允许监控所有虚拟机端口的 I/O 操作 VOID globalDisable (); //禁止监控所有虚拟机端口的 I/O 操作 virtual DWORD handler ( VMHANDLE, DWORD port,CLIENT_STRUCT* pRegs, DWORD iotype, DWORD outdata ); //端口处理程序protected : DWORD m_port; BYTE m_thunk[IOPORTTHUNKSIZE];};

Page 42: Windows98/2000 驱动程序编写方法

42 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 )) 下面我们给出一个例子,该例子捕获端口 0xf0 ,当应用程序要读该端口时,它将上次写入该端口的资料返回给应用程序。用 VToolsD 生成的时候,基本上和生成 Myfirst 的方法一样,只是在 Windows95控制消息中只选择 SYS_DYNAMIC_DEVICE_EXIT 和 SYS_DYNAMIC_DEVICE_INIT 两个消息而不选择 W32_DEVICEIOCONTROL 。// IOPORT.h - include file for VxD IOPORT#include <vtoolscp.h>#define DEVICE_CLASS IoportDevice#define IOPORT_DeviceID UNDEFINED_DEVICE_ID#define IOPORT_Init_Order UNDEFINED_INIT_ORDER#define IOPORT_Major 1#define IOPORT_Minor 0#define PORT_NUM 0xf0 // 要捕获的端口地址 ……

Page 43: Windows98/2000 驱动程序编写方法

43 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))

……………………class IoportPort class IoportPort : : public VIOPortpublic VIOPort{{publicpublic :: IoportPortIoportPort ():(): VIOPortVIOPort (( PORT_NUMPORT_NUM )) {}{} ;; DWORD handlerDWORD handler (( VMHANDLE hVM, DWORDVMHANDLE hVM, DWORD port,CLIENT_STRUCT* pRegs,DWORD iotype, port,CLIENT_STRUCT* pRegs,DWORD iotype, DWORD outdataDWORD outdata ););}};; ……………………

Page 44: Windows98/2000 驱动程序编写方法

44 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))

// IOPORT.cpp - main module for VxD IOPORT#define DEVICE_MAIN#include "ioport.h"Declare_Virtual_Device ( IOPORT )#undef DEVICE_MAINIoportPort* pio;IoportVM :: IoportVM ( VMHANDLE hVM ) : VVirtualMachine ( hVM ) {}IoportThread :: IoportThread ( THREADHANDLE hThread) : VThread ( hThread ) {}

Page 45: Windows98/2000 驱动程序编写方法

45 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))

BOOL IoportDevice :: OnSysDynamicDeviceInit (){ // 动态装载初始化的时候调用 pio=new ( IoportPort ); if ( pio ) { if ( pio->hook ()) // 挂上端口映射 { dout<<"hook success"<<endl; } else return FALSE; } else return FALSE; return TRUE;}

Page 46: Windows98/2000 驱动程序编写方法

46 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))BOOL IoportDevice :: OnSysDynamicDeviceExit (){ // 驱动程序被卸下时调用 if ( pio ) { if ( pio->unhook ()) // 将 I/O映射卸载下来 { dout<<"unhook success"<<endl; } delete pio; } return TRUE;} DWORD IoportPort :: handler ( VMHANDLE hVM, DWORD port,CLIENT_STRUCT* pRegs,DWORD iotype, DWORD outdata ){ static WORD count=0; static DWORD buffer[20]; static BYTE inppt=0; count++; dout<<"entering handler"<<endl; dout<<"entered count"<<count<<endl;

Page 47: Windows98/2000 驱动程序编写方法

47 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))switch ( iotype ) { case BYTE_INPUT : dout<<"buffer byte"<< ( BYTE ) buffer[inppt]<<endl

; inppt++; return ( BYTE ) buffer[inppt-1]; case WORD_INPUT : dout<<"buffer word"<< ( WORD ) buffer[inppt]<<endl

; inppt++; return ( WORD ) buffer[inppt-1]; case DWORD_INPUT : dout<< "buffer dword"<< ( WORD ) buffer[inppt]<<en

dl; inppt++; return ( WORD ) buffer[inppt-1];case BYTE_OUTPUT : buffer[count-1]=outdata; dout<<"byte output data : "

<< ( BYTE ) outdata<<endl; break; case WORD_OUTPUT : buffer[count-1]=outdata; dout<<"word output data :

"<< ( WORD )outdata<<endl; break; case DWORD_OUTPUT : buffer[count-1]=outdata; dout<<"dword output data

: "<<( DWORD ) outdata<< endl;break; default : break; } // 对于输入,处理程序将数据输入到端口的缓冲,对于输出,处理程序将缓冲中的资料输出

到端口 return 0;}

Page 48: Windows98/2000 驱动程序编写方法

48 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))下面给出调用端口 0xf0 的 Win32控制台程序。 #include "conio.h"

#include <iostream.h>#include <windows.h>#include <winioctl.h>#define PORT_NUM 0xf0void main (){ char* srcdata="This is IO Sample!!"; char* desdata=new char ( 20 ); HANDLE hDevice; char ch; _cprintf ( "1=load IOPORT VXD, x=exit, Others=Do not load IO

PORT VXD\n" ); ch=_getch ();while ( ch!='x' ) { if ( ch=='1' ) { hDevice=CreateFile ( "\\\\.\\Ioport.vxd",0,0,0,OPEN_EXISTING,FILE_FLAG_DELETE_O

N_CLOSE,0 );

Page 49: Windows98/2000 驱动程序编写方法

49 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))if ( hDevice==INVALID_HANDLE_VALUE ) { cout<<"Open VXD error"<<GetLastError () <<endl; exit ( 1 ); } }desdata[0]='\0'; _asm {

mov dx,PORT_NUMmov edi,srcdatamov ecx,20

byteoutput : mov al,[edi]out dx,alinc ediloop byteoutputmov esi,desdatamov ecx,20

byteinput : in al,dxmov [esi],alinc esiloop byteinput

}

Page 50: Windows98/2000 驱动程序编写方法

50 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))

if ( ch=='1' ) {CloseHandle ( hDevice ); //关闭设备句柄_cprintf ( "scrdata and desdata should be the same!\n" ); } _cprintf ( "srcdata : %s\n",srcdata ); _cprintf ( "desdata : %s\n",desdata ); _cprintf ( "1=load IOPORT VXD, x=exit, Others=Do not load IOPORT VXD\n" ); ch=_getch (); }}

Page 51: Windows98/2000 驱动程序编写方法

51 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))中断类class VHardwareInt{public :VHardwareInt ( int irq, DWORD flags, DWORD tout, PVOID refdata ); //构造函数~VHardwareInt (); //析构函数virtual BOOL hook (); //挂钩虚拟 IRQ 的处理程序virtual BOOL unhook (); //摘钩虚拟 IRQ 的处理程序virtual VOID OnHardwareInt ( VMHANDLE ); // 硬件中断信号处理程序virtual VOID OnVirtualInt ( VMHANDLE );

//虚拟中断信号处理程序 VPICD给 VxD 的)virtual VOID OnVirtualEOI ( VMHANDLE );

// 当虚拟机发出 EOI命令时被调用virtual VOID OnVirtualMask ( VMHANDLE, BOOL bMask );

//虚拟机改变屏蔽位的时候被调用virtual VOID OnVirtualIRET ( VMHANDLE ); // 当虚拟机中中断处理程序返回控制给 VPICD 时被调用VOID assert ( VMHANDLE ); // 在指定虚拟机中请求虚拟中断VOID deassert ( VMHANDLE ); //撤消指定虚拟机中的虚拟中断DWORD getStatus ( VMHANDLE hVM ); //返回虚拟 IRQ 的部分状态信息

Page 52: Windows98/2000 驱动程序编写方法

52 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))DWORD getCompleteStatus ( VMHANDLE hVM );

//返回虚拟 IRQ 的全部状态信号BOOL testPhysicalRequest (); // 测试物理 IRQ 的状态信息VOID sendPhysicalEOI (); //向物理 PIC 发出中断结束 EOI信号VOID physicalMask (); //物理屏蔽 IRQVOID physicalUnmask (); //物理允许 IRQVOID setAutoMask (); //指示可编程中断控制器执行智能的 IRQ 屏蔽static LONG convertIntToIRQ ( int vecno, VMHANDLE hVM); // 将中断号转换成 IRQ号static LONG convertIRQToInt ( int irq, VMHANDLE hVM );

// 将 IRQ号转换成中断号static BOOL forceDefaultOwner ( int irq, VMHANDLE hVM );

//控制 IRQ 的默认处理protected :WORD m_irq;WORD m_flags;DWORD m_timeout;PVOID m_refdata;IRQHANDLE m_handle;BYTE m_thunk[HWITHUNKSIZE];private :VHardwareInt ();};

Page 53: Windows98/2000 驱动程序编写方法

53 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))

class VSharedHardwareInt : public VHardwareInt{public :VSharedHardwareInt ( int irq, DWORD flags,

DWORD timeout,PVOID refdata );virtual BOOL hook ();virtual BOOL OnSharedHardwareInt ( VMHANDLE );

// 中断处理程序protected :BYTE m_sthunk[SHWINTTHUNKSIZE];private :VSharedHardwareInt ( void );};

Page 54: Windows98/2000 驱动程序编写方法

54 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 )) 下面我们使用 VsharedHardwareInt给一个 VxD 的例子,该例子捕获鼠标中断。该例子也是用 VtoolsD 生成的可动态加载的 VxD 框架,然后在 VC6 中修改的,我们只给出修改的部分。 // HARDINT.h - include file for VxD HARDINT…#define IRQ_NUM 12 //根据你的鼠标情况指定, COM1 为 4 , COM2 为 3 ,PS/2 为 12class HardintDevice : public VDevice{public : virtual BOOL OnSysDynamicDeviceInit (); virtual BOOL OnSysDynamicDeviceExit ();};…class HardintInt : public VSharedHardwareInt{public : HardintInt () : VSharedHardwareInt ( IRQ_NUM,0,0,0 ) {}; BOOL OnSharedHardwareInt ( VMHANDLE hVM );};

Page 55: Windows98/2000 驱动程序编写方法

55 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))// HARDINT.cpp - main module for VxD HARDINT…HardintInt* pshint;…BOOL HardintDevice :: OnSysDynamicDeviceInit (){ VMHANDLE hVM; hVM=VMD_Get_Mouse_Owner (); dout<<"Mouse's VMHANDLE"<< ( DWORD ) hVM<<endl; pshint=new ( HardintInt ); if ( pshint ) { if ( pshint->hook ()) {dout<<"shared interruppt hooked"<<endl; } else {dout<<"shared interruppt hook failed!"<<endl;return FALSE; } }

Page 56: Windows98/2000 驱动程序编写方法

56 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 )) else return FALSE; return TRUE;}BOOL HardintDevice :: OnSysDynamicDeviceExit (){ if ( pshint ) { if ( pshint->unhook ()) {dout<<"shared interrupt unhooked"<<endl; } delete pshint; } return TRUE;}BOOL HardintInt :: OnSharedHardwareInt ( VMHANDLE hVM ){ static WORD count=0; count++; dout<<"hardware ( Mouse ) int count : "<<count<<endl; return FALSE;}

Page 57: Windows98/2000 驱动程序编写方法

57 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))热键类 class VHotKey{public : VHotKey ( BYTE scan, scanType_t st,

DWORD shift, DWORD flags, PVOID refData=0,DWORD delay=0 ); //构造函数

~VHotKey () {unhook (); }; //析构函数 virtual VOID handler ( BYTE scan,

keyAction_t ka, DWORD shift,PVOID refData, DWORD elapased ); //热键处理程序 BOOL hook (); //挂钩热键处理程序 BOOL unhook (); //摘钩热键处理程序 VOID localEnable ( BOOL enable, VMHANDLE hVM );

// 在指定的虚拟机中允许或禁止热键事件 VOID reflectToVM ( VMHANDLE hVM, DWORD shift );

//指示 VxD把热键事件传到指定虚拟机中 static VOID cancelState (); //取消热键

Page 58: Windows98/2000 驱动程序编写方法

58 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))

protected : DWORD m_handle; BYTE m_scanCode; scanType_t m_scanType; DWORD m_shiftState; BYTE m_flags; PVOID m_refData; DWORD m_timeout; BYTE m_thunk[HKTHUNKSIZE];}

Page 59: Windows98/2000 驱动程序编写方法

59 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 )) 下面这个例子截获 Ctrl+P键,当按下这两个键时,将弹出一个窗口,说明已经捕获。该例子也是用 VtoolsD 生成的可动态加载的 VxD 框架,然后在 VC6 中修改的,我们只给出修改的部分。 // HOTKEY.h - include file for VxD HOTKEY…#define C_SCAN 0X19 //P键的扫描码class HotkeyDevice : public VDevice{public : virtual BOOL OnSysDynamicDeviceInit (); virtual BOOL OnSysDynamicDeviceExit ();};…class HotkeyHot : public VHotKey{public : HotkeyHot (): VHotKey ( C_SCAN, SCAN_NORMAL, HKSS_Ctrl, CallO

nPress,"热键被按下! ",0 ) { }; void handler ( BYTE scan, keyAction_t keyEvent, DWORD shift,

PVOID refData, DWORD elapased );};

Page 60: Windows98/2000 驱动程序编写方法

60 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))

// HOTKEY.cpp - main module for VxD HOTKEY…HotkeyHot* pkey;…BOOL HotkeyDevice :: OnSysDynamicDeviceInit (){ pkey=new ( HotkeyHot ); if ( pkey ) { if ( pkey->hook ()) {dout<<"hot key hooked"<<endl; } else return FALSE; } else return FALSE; return TRUE;}

Page 61: Windows98/2000 驱动程序编写方法

61 http://qsyang.yeah.nethttp://qsyang.yeah.net

现代微机原理与接口技术现代微机原理与接口技术 (( 第第 22 版版 ))BOOL HotkeyDevice :: OnSysDynamicDeviceExit (){ if ( pkey ) { if ( pkey->unhook ()) { dout<<"hot key unhooked"<<endl; } delete pkey; } return TRUE;}void HotkeyHot :: handler ( BYTE scan, keyAction_t keyEvent, DWORD shift, PVOID refData, DWORD elapased ){ dout<<"entering handler"<<endl; SHELL_Message ( Get_Cur_VM_Handle () ,MB_OK, ( char* ) refData,"CTRL+P Pressed",0,0,0 ); // 显示一个消息框 pkey->reflectToVM ( Get_Cur_VM_Handle () ,shift );

// 将按键信息传送到当前虚拟机中}


Recommended