`
wujianjun12315
  • 浏览: 111880 次
  • 性别: Icon_minigender_1
  • 来自: 北京
社区版块
存档分类
最新评论

VxD编程入门教程(驱动开发)

 
阅读更多

原文出处:http://www.vckbase.com/document/viewdoc/?id=227

一、Windows 95 DDK的安装

  安装Windows 95 DDK一般需要先安装Win32 SDK,原因是Windows 95 DDK需要Win32 SDK的16位资源编译器,但是Win32 SDK很大(一整张光盘的容量),而且国内难以买到,ftp站上也较少见,即使有,下载也很困难。笔者经过一段时间的摸索,找到了安装Windows 95 DDK的几种简单方法,现将方法介绍如下:

方法之一:使用第三方资源编译器

1、修改注册表,仿真Win32 SDK已经安装的情况。建立一个名为WIN32SDK.REG的注册表文件,内容为:

REGEDIT4

[HKEY_USERS\.Default\Software\Microsoft\Win32SDK]

[HKEY_USERS\.Default\Software\Microsoft\Win32SDK\Directories]
"Install Dir"="C:\\MSTOOLS"

  在资源管理器中双击此文件,将此文件中的内容添加到注册表。就可以安装Windows 95 DDK了。

2、运行Windows 95 DDK中的SETUP.EXE文件,安装Windows 95 DDK到C:\DDK。

3、安装MASM 6.11到C:\MASM611,安装完成后将未安装的Windows 95 DDK中的MASM611C目录下的文件覆盖到C:\MASM611\BIN。

4、安装Visual C++ 5.0(4.0也可以,但不宜使用6.0)到C:\Program Files\DevStudio\VC。

5、建立C:\MSTOOLS\BINW16目录,拷贝资源编译器。Windows 95 DDK需要一个能将Win32资源源文件编译成16位资源的资源编译器。如果有Win32 SDK,可以将BINW16目录下的文件直接拷贝到C:\MSTOOLS\BINW16,如果没有Win32 SDK,则可以使用第三方的资源编译器,这里以使用Borland的资源编译器为例:准备Turbo MASM 5.0一套,用UNPAK工具解压缩CMDLINE.PAK文件,找到下面三个文件:

BRC.EXE
BRCC32.EXE
RW32CORE.DLL

将这三个文件拷贝到C:\MSTOOLS\BINW16,并将BRC.EXE改名为RC.EXE即可。

6、修改CONFIG.SYS增大环境变量空间。在CONFIG.SYS文件最后加入一行:

SHELL=C:\WINDOWS\COMMAND.COM /E:8192 /P

7、进入Windows 95 MS-DOS方式,初始化编译环境(最好建立一个批处理文件):

 
C:\MASM611\BINR\NEW-VARS.BAT
C:\DDK\DDKINIT.BAT 32 BASE
(编译的设备驱动程序不同,参数也不同)
C:\Program Files\DevStudio\VC\bin\VCVARS32.BAT

  就可以使用Windows 95 DDK了,连接时出现的警告可以不理会。方法之二:使用Windows 98 DDK完整版的Windows 98 DDK(约30M)包括Windows 95 DDK、全套SDK编译器和MASM 6.11C汇编器,安装方法非常简单:安装Windows 98 DDK和Visual C++ 5.0,然后直接运行“Check Build Environment”(编译带调试信息的设备驱动程序)或者“Free Build Environment”(编译正式发布版本的设备驱动程序)程序项即可。

二、一个拦截Windows 95/98文件操作的VxD

  VxD——虚拟设备驱动程序,顾名思义,VxD是用来控制硬件设备的,那么这里为什么要讲一个拦截Windows 95/98文件操作的VxD呢?其实,VxD不仅仅可以用来控制硬件设备,因为VxD工作在80386保护模式Ring 0特权级(最高特权级)上,而一般的应用程序工作在Ring 3特权级(最低特权级)上,所以VxD可以完成许多API不能完成的功能,例如端口读写、物理内存读写、中断调用、API拦截等。正因为如此,VxD在Windows系统编程中有广泛用途,其实大家一般都是碰到Windows API不能解决或者难以解决的问题才考虑编写VxD解决问题。这里介绍的拦截Windows 95/98文件操作的VxD可以用来拦截Windows 95/98(Windows NT不支持VxD)的所有文件操作,那么这个VxD有什么用途呢?最大的用途可能是——病毒防火墙,用来对文件操作进行过滤,可以进行动态病毒检测和动态杀毒。这个VxD使用的原理和目前流行的CIH病毒传染的原理是基本相同的。(其实大家如果要问我为什么要写这么一个VxD,那是因为——我是Virus版的版主啦)

该VxD的文件名是FILEHOOK.VXD,源程序(FILEHOOK.ASM)如下: ;FILEHOOK.VXD--拦截Windows 95/98文件操作的VxD

.386p

.XLIST

INCLUDE VMM.Inc
INCLUDE VWin32.Inc
INCLUDE Shell.Inc

MASM=1

INCLUDE IFS.Inc
INCLUDE IFSMgr.Inc

.LIST

;VxD声明

Declare_Virtual_Device 
FILEHOOK,1,0,VxD_Control,Undefined_Device_ID,,,

;保护模式数据段

VxD_DATA_SEG
Prev_File_System_Api_Hook dd 0
In_File_System_Api_Hook db 0
Message1 db ''Open file !'',0
Caption1 db ''FILEHOOK'',0
VxD_DATA_ENDS

;保护模式代码段

VxD_CODE_SEG

;系统控制过程

BeginProc VxD_Control
Control_Dispatch SYS_DYNAMIC_DEVICE_INIT,VxD_Device_Init
Control_Dispatch SYS_DYNAMIC_DEVICE_EXIT,VxD_Device_Exit
Control_Dispatch W32_DEVICEIOCONTROL,VxD_IOCTL
clc
ret
EndProc VxD_Control

;IOCTL 控制(设备I/O控制)过程

BeginProc VxD_IOCTL

;获取DeviceIoControl控制代码

mov ecx,[esi.dwIoControlCode]
cmp ecx,1
jz Install_File_System_Api_Hook
cmp ecx,2
jz Uninstall_File_System_Api_Hook
jmp VxD_IOCTL_Exit

;安装文件系统API 钩子

Install_File_System_Api_Hook:
mov eax,OFFSET32 File_System_Api_Hook
VxDCall IFSMgr_InstallFileSystemApiHook 
or eax,eax
jz Error_Handler

;保存上一个文件系统API 钩子地址

mov Prev_File_System_Api_Hook,eax
jmp VxD_IOCTL_Exit

;移去文件系统API 钩子

Uninstall_File_System_Api_Hook:
mov eax,OFFSET32 File_System_Api_Hook
VxDCall IFSMgr_RemoveFileSystemApiHook 
cmp eax,0FFFFFFFFH
jz Error_Handler
jmp VxD_IOCTL_Exit

;IOCTL 控制过程结束

VxD_IOCTL_Exit:
xor eax,eax
clc
ret

;错误处理

Error_Handler:
mov eax,0FFFFFFFFH
stc
ret
EndProc VxD_IOCTL

;VxD_Device_Exit过程

BeginProc VxD_Device_Exit
clc
ret
EndProc VxD_Device_Exit

;文件系统API 钩子过程(C语言调用方式)

BeginProc File_System_Api_Hook,CCALL
ArgVar FSDFnAddr,DWORD
ArgVar FunctionNum,DWORD
ArgVar Drive,DWORD
ArgVar ResourceFlags,DWORD
ArgVar CodePage,DWORD
ArgVar pir,DWORD
EnterProc
pushad

;防止重入

cmp byte ptr In_File_System_Api_Hook,00h
jnz Prev_Hook

;比较是打开文件操作吗?

cmp dword ptr FunctionNum,IFSFN_OPEN
jnz Prev_Hook

;设置重入标志

inc byte ptr In_File_System_Api_Hook

;取当前VM句柄

VMMCall Get_Cur_VM_Handle

;显示消息框

mov eax,MB_ICONASTERISK+MB_OK
mov ecx,OFFSET32 Message1
mov edi,OFFSET32 Caption1
mov esi,0
mov edx,0
VxDCall Shell_Message

;取消重入标志

dec byte ptr In_File_System_Api_Hook

;转到上一个文件系统API 钩子地址

Prev_Hook:
popad
LeaveProc
mov eax,Prev_File_System_Api_Hook
jmp [eax]
Return
EndProc File_System_Api_Hook

VxD_CODE_ENDS

;保护模式初始化代码段

VxD_ICODE_SEG

;VxD_Device_Init过程

BeginProc VxD_Device_Init
clc
ret
EndProc VxD_Device_Init

VxD_ICODE_ENDS

end

  该VxD在设备控制过程(VxD_Control过程)中处理了3个系统控制消息,分别是SYS_DYNAMIC_DEVICE_INIT(动态VxD初始化)、SYS_DYNAMIC_DEVICE_EXIT(动态VxD退出)和W32_DEVICEIOCONTROL(设备I/O控制),对应的消息处理过程分别是VxD_Device_Init、VxD_Device_Exit和VxD_IOCTL。其中VxD_Device_Init过程和VxD_Device_Exit过程只清除进位标志返回(表示成功),VxD_IOCTL过程是Windows 95/98应用程序与VxD通信的接口,完成文件系统API钩子的安装和移去工作,[esi.dwIOControlCode]中是设备I/O控制代码,该控制代码为1时安装文件系统API钩子,为2时移去文件系统API钩子。File_System_Api_Hook是文件系统API钩子过程,这里作为一个简单的实例,钩子过程判断是否是打开文件操作,如果是则显示一个简单的消息框,然后跳转到上一个文件钩子(相当于旧的文件系统API入口)。如果需要扩充功能,可以在该过程中增加代码。汇编连接VxD需要一个模块定义文件和一个NMAKE文件(手工汇编连接当然也可以)。这两个文件都可以直接用DDK中的GENERIC实例中的模块定义文件和NMAKE文件修改而成,模块定义文件(FILEHOOK.DEF)如下:

VXD FILEHOOK DYNAMIC

DESCRIPTION ''File System API Hook Program''

SEGMENTS
    _LPTEXT     CLASS ''LCODE''   PRELOAD NONDISCARDABLE
    _LTEXT      CLASS ''LCODE''   PRELOAD NONDISCARDABLE
    _LDATA      CLASS ''LCODE''   PRELOAD NONDISCARDABLE
    _TEXT       CLASS ''LCODE''   PRELOAD NONDISCARDABLE
    _DATA       CLASS ''LCODE''   PRELOAD NONDISCARDABLE
    CONST       CLASS ''LCODE''   PRELOAD NONDISCARDABLE
    _TLS        CLASS ''LCODE''   PRELOAD NONDISCARDABLE
    _BSS        CLASS ''LCODE''   PRELOAD NONDISCARDABLE
    _LMSGTABLE  CLASS ''MCODE''   PRELOAD NONDISCARDABLE IOPL
    _LMSGDATA   CLASS ''MCODE''   PRELOAD NONDISCARDABLE IOPL
    _IMSGTABLE  CLASS ''MCODE''   PRELOAD DISCARDABLE IOPL
    _IMSGDATA   CLASS ''MCODE''   PRELOAD DISCARDABLE IOPL
    _ITEXT      CLASS ''ICODE''   DISCARDABLE
    _IDATA      CLASS ''ICODE''   DISCARDABLE
    _PTEXT      CLASS ''PCODE''   NONDISCARDABLE
    _PMSGTABLE  CLASS ''MCODE''   NONDISCARDABLE IOPL
    _PMSGDATA   CLASS ''MCODE''   NONDISCARDABLE IOPL
    _PDATA      CLASS ''PDATA''   NONDISCARDABLE SHARED
    _STEXT      CLASS ''SCODE''   RESIDENT
    _SDATA      CLASS ''SCODE''   RESIDENT
    _DBOSTART   CLASS ''DBOCODE'' PRELOAD NONDISCARDABLE CONFORMING
    _DBOCODE    CLASS ''DBOCODE'' PRELOAD NONDISCARDABLE CONFORMING
    _DBODATA    CLASS ''DBOCODE'' PRELOAD NONDISCARDABLE CONFORMING
    _16ICODE    CLASS ''16ICODE'' PRELOAD DISCARDABLE
    _RCODE      CLASS ''RCODE''

EXPORTS
FILEHOOK_DDB @1

NMAKE文件(MAKEFILE)如下:

!ifdef MASTER_MAKE
BUILD_BITS=32
BUILD_TYPE=base
!INCLUDE $(DDKROOT)\master.mk
!endif

NAME = filehook

# supply the location of a 16-bit linker

LINK =

#Definitions for the debug level 

!ifdef DEBUG
DDEBUG=-DDEBLEVEL=1 -DDEBUG
!else
DDEBUG=-DDEBLEVEL=0
!endif

#Definitions for MASM 6 Assembler

ASM= ml
AFLAGS = -coff -DBLD_COFF -DIS_32 -W2 -c -Cx -Zm -DMASM6 $(DDEBUG)
ASMENV = ML
LFLAGS = /VXD /NOD

#MASM 6 only inference rules

.asm.obj:
set $(ASMENV)=$(AFLAGS)
$(ASM) -Fo$*.obj $< 

all : $(NAME).VXD

OBJS = filehook.obj

filehook.obj: filehook.asm

$(NAME).vxd: $(NAME).def $(OBJS)
link @<<$(NAME).lnk
$(LFLAGS) 
/OUT:$(NAME).vxd
/MAP:$(NAME).map
/DEF:$(NAME).def
$(OBJS)
<<
mapsym -s -o $(NAME).sym $(NAME).map

clean:
-@del *.obj
-@del *.vxd
-@del *.exp
-@del *.lib
-@del *.map
-@del *.sym

  有了这两个文件,运行NMAKE即可汇编连接VxD。

三、Windows 95/98应用程序与VxD的通信

Windows 95/98应用程序与VxD的通信一般使用DeviceIoControl函数,这里给出一个实例源程序(FHTEST.C)如下:

//拦截Windows 95/98文件操作测试程序

#include "tchar.h"

#define INSTALL_FILE_SYSTEM_API_HOOK 1
#define UNINSTALL_FILE_SYSTEM_API_HOOK 2

static TCHAR szAppName[]=_T("FHTEST");
static TCHAR szAppTitle[]=_T("拦截Windows 95/98文件操作测试程序");
static HANDLE hDevice;

LRESULT CALLBACK WndProc(HWND hWnd,UINT Message,WPARAM 
						 wParam,LPARAM lParam);

int WINAPI WinMain(HINSTANCE hInstance,HINSTANCE 
				   hPrevInstance,LPSTR lpCmdLine,int nCmdShow)
{
	HWND hWnd;
	WNDCLASSEX wcex;
	MSG Msg;
	//本程序不能在Windows NT中运行
	if(GetVersion()<0x80000000)
	{
		MessageBox(NULL,_T("本程序不能在Windows NT中运行!
			"),szAppTitle,MB_ICONINFORMATION|MB_OK);
			return FALSE;
	}
	if(!hPrevInstance)
	{
		wcex.cbSize=sizeof(WNDCLASSEX);
		wcex.style=CS_HREDRAW|CS_VREDRAW;
		wcex.lpfnWndProc=WndProc;
		wcex.cbClsExtra=0;
		wcex.cbWndExtra=0;
		wcex.hInstance=hInstance;
		wcex.hIcon=LoadIcon(hInstance,IDI_APPLICATION);
		wcex.hCursor=LoadCursor(NULL,IDC_ARROW);
		wcex.hbrBackground=(HBRUSH)(COLOR_WINDOW+1);
		wcex.lpszMenuName=NULL;
		wcex.lpszClassName=szAppName;
		wcex.hIconSm=LoadIcon(hInstance,IDI_APPLICATION);
		if(!RegisterClassEx(&wcex)) return FALSE;
	}
	hWnd=CreateWindow(szAppName,szAppTitle,WS_OVERLAPPEDWINDOW,CW_USEDEFAULT,CW_USEDEFAULT,CW_USEDEFAULT,CW_USEDEFAULT,
		0,0,hInstance,NULL);
	if(!hWnd) return FALSE;
	ShowWindow(hWnd,nCmdShow);
	UpdateWindow(hWnd);
	while(GetMessage(&Msg,0,0,0))
	{
		TranslateMessage(&Msg);
		DispatchMessage(&Msg);
	}
	return Msg.wParam;
}

LRESULT CALLBACK WndProc(HWND hWnd,UINT Message,WPARAM wParam,LPARAM lParam)
{
	HDC hDC;
	PAINTSTRUCT ps;
	DWORD cb;
	BOOL bResult;
	switch(Message)
	{
	case WM_CREATE:
		
		hDevice=CreateFile("\\\\.\\FILEHOOK.VXD",0,0,NULL,0,FILE_FLAG_DELETE_ON_CLOSE,NULL);
		if(hDevice!=INVALID_HANDLE_VALUE)
		{
			
			bResult=DeviceIoControl(hDevice,INSTALL_FILE_SYSTEM_API_HOOK,NULL,0,NULL,0,&cb,0);
			if(bResult) MessageBox(hWnd,_T("文件系统API 钩子安装成功!"),szAppTitle,MB_ICONINFORMATION|MB_OK);
			else MessageBox(hWnd,_T("不能安装文件系统API 钩子!"),szAppTitle,MB_ICONINFORMATION|MB_OK);
		}
		else
		{
			MessageBox(hWnd,_T("不能打开FILEHOOK.VXD!
				"),szAppTitle,MB_ICONINFORMATION|MB_OK);
		}
		break;
	case WM_PAINT:
		hDC=BeginPaint(hWnd,&ps);
		EndPaint(hWnd,&ps);
		break;
	case WM_DESTROY:
		if(hDevice!=INVALID_HANDLE_VALUE)
		{
			
			bResult=DeviceIoControl(hDevice,UNINSTALL_FILE_SYSTEM_API_HOOK,NULL,0,NULL,0,&cb,0);
			if(bResult) MessageBox(hWnd,_T("文件系统API 钩子移去
				成功!"),szAppTitle,MB_ICONINFORMATION|MB_OK);
				else MessageBox(hWnd,_T("不能移去文件系统API 钩子!
				"),szAppTitle,MB_ICONINFORMATION|MB_OK);
				CloseHandle(hDevice);
		}
		else
		{
			MessageBox(hWnd,_T("不能打开FILEHOOK.VXD!"),szAppTitle,MB_ICONINFORMATION|MB_OK);
		}
		PostQuitMessage(0);
		break;
	default:
		return DefWindowProc(hWnd,Message,wParam,lParam);
	}
	return 0;
}

  本程序使用CreateFile函数动态装载VxD,然后用DeviceIoControl函数向VxD发送设备I/O控制代码,安装和移去文件系统API钩子,最后用CloseHandle函数动态移去VxD。运行该程序时,如果文件系统API钩子安装成功,会显示出“文件系统API钩子安装成功!”的消息框,然后只要进行打开文件操作,就会显示出“Open File !”的消息框。退出该程序时,如果文件API钩子移去成功,会显示出“文件API钩子移去成功!”的消息框,以后进行打开文件操作时不再显示消息框。

四、小结

  上述实例演示了一个完整的拦截Windows 95/98文件系统API的VxD和Windows 95/98应用程序与该VxD通信的方法。该VxD可以作为一个基本框架,稍作修改即可用于病毒防火墙等软件。其实VxD的功能远不止这些,充分利用VxD的功能可以编写出许多用API不能编写出的高级应用程序。本教程只是一个简单的VxD编程例子,因为笔者水平所限,加之时间较少,写得较为简单,还请大家见谅,同时也欢迎大家讨论。本教程中使用的VMM功能、VxD功能和API函数请查阅相关手册或者帮助。

分享到:
评论

相关推荐

    驱动开发入门:Win7 SP1 x64 驱动开发环境搭建

    这些建议和解决方案是为了帮助新手开发者避免常见的错误,快速入门驱动开发。同时,本文也提到了驱动程序开发的一些基本原则,比如驱动程序不具有兼容性,即x86和x64架构下的驱动程序不能相互替换使用。由于x86架构...

    windows内核安全与驱动开发(pdf+源码).zip

    《Windows内核安全与驱动开发》是一本深入探讨Windows操作系统内核安全机制和驱动程序开发的专业书籍。在Windows操作系统中,内核是系统的基石,它管理着系统资源、硬件抽象层以及进程调度等核心功能。驱动程序则是...

    Windows驱动编程基础教程

    总的来说,“Windows驱动编程基础教程”是一份全面的资源,覆盖了从驱动开发基础知识到高级主题的各个方面。通过这个教程,新手可以逐步掌握Windows驱动程序的开发流程,为今后的硬件适配和系统优化打下坚实的基础。...

    驱动学习笔记新手入门

    总的来说,“驱动学习笔记新手入门”是一个很好的起点,通过学习这个资料,你可以逐步了解驱动开发的基本概念、技术和流程,为以后的深入学习打下坚实的基础。记住,实践出真知,理论知识结合实际操作是成为驱动开发...

    windows 2000 驱动程序开发入门_Win2k驱动程序开发(ppt).zip

    虽然标题中提到的是"Win2k驱动程序开发",但WDK的概念依然重要,因为它代表了驱动开发技术的发展趋势。WDK包含了开发、调试和测试所有类型Windows驱动程序所需的工具、库和文档。在Windows 2000之后的系统中,如XP、...

    使用vc6.0编写编译驱动超简单的方法,极力推荐使用,不看你会失望的

    需要注意的是,虽然vc6.0和DriverWizard简化了驱动开发过程,但深入学习驱动开发还需要掌握更多的知识,例如Windows内核编程、硬件中断处理、I/O操作等。此外,由于vc6.0已不再更新,对于现代的Windows操作系统和...

    驱动开发学习笔记

    对于初学者来说,了解驱动开发的基本概念和入门知识是非常必要的。本篇学习笔记将深入浅出地探讨驱动开发,尤其是针对Windows环境下的WDM(Windows Driver Model)。 首先,驱动程序是操作系统与硬件设备之间的桥梁...

    驱动入门资料【win98/2000】

    压缩包中的"接口驱动程序开发(上).ppt"和"接口驱动程序开发(下).ppt"很可能是关于接口驱动开发的详细教程,涵盖了驱动的结构、API使用、调试技巧等内容,对于初学者来说是非常宝贵的资源。 总结,驱动程序开发是...

    驱动程序开发

    1. **《C程序设计》** - 强化C语言基础,为驱动开发奠定编程技能。 2. **《Windows2000内部揭密》** - 深入理解Windows操作系统架构,利于驱动设计。 3. **《Microsoft Windows驱动程序模型设计》** - 专注WDM模型,...

    易语言驱动操作模块源码

    易语言是一种国产的编程语言,它的设计理念是“易学易用”,旨在降低编程入门的门槛。在易语言中,驱动操作模块是实现底层硬件交互的关键部分,它允许程序员通过编写代码来控制硬件设备,比如硬盘、网络卡、打印机等...

    VxD.docx

    VxD编程涉及到深入的系统级知识,包括中断处理、内存管理以及与VMM的交互。开发者需要熟悉汇编语言和Windows 9x的内部机制,才能有效地编写和调试这类驱动程序。虽然现在VxD已经较少使用,但理解其工作原理对于系统...

    转 WDM开发上路笔记

    ”是编程初学者的第一个程序,因此这个文档可能包含了一个WDM驱动的基本构建和运行过程,让读者能够快速体验到驱动开发的乐趣和挑战。 在这个教程中,学习者可以期待了解以下知识点: 1. **WDM驱动概述**:理解WDM...

    WIN32ASM教程

    而“PE格式和VxD”则是Windows环境下执行文件的两种重要形式,PE(Portable Executable)是现代Windows系统的标准可执行文件格式,VxD(Virtual Device Driver)则是在Windows 9x系统中用于驱动程序开发的机制。...

    DDK Wizard

    DDK Wizard是一个专为开发人员设计的工具...然而,需要注意的是,随着Windows驱动开发的发展,Microsoft已推出了更新的工具,如WDK(Windows Driver Kit),它集成了DDK Wizard的功能并提供了更多的现代驱动开发支持。

Global site tag (gtag.js) - Google Analytics