• 标 题:不知道我理解的对否,关于SuperBpm...的 (10千字)
  • 作 者:hume
  • 时 间:2002-3-23 20:47:08
  • 链 接:http://bbs.pediy.com

comment /*
    你知道SuperBpm的erase和monitor的区别吗?如果不知道,可以往下看.
    最近看了一点老掉牙的VxD,才看明白superBpm的工作原理,我用masm改写了一下,未经充分测试,只是比EliCZ这win32 ASM Pioneer更烦琐了写可能好理解点,有兴趣的看看.Loader部分十分简单,主要是根据用户选择用deviceIoControl向驱动VxD发出命令,VxD则执行相应动作.

    对于VxD部分,则是通过拦截_VWIN32_Set_Thread_Context服务(即所谓的hook)来实现对程序擦除或改变Drx寄存器的监视和恢复,Erase模式仅仅是禁止应用程序用context改写Drx寄存器,这样Seh或者用SetThreadContext等把戏就不好用了,因为VxD工作在最地层,这种拦截是有效的.Monitor模式是为了阻止那些比如直接修改中断等进入ring0修改寄存器的把戏的(我想是这样的...可能错误).
    但是这个版本明显对Cr4没有进行处理,因为BPIO指令是否有效与CR4的DE位有关,如果你聪明应该知道如何利用这一点.而且在monitor模式下对Dr7为0才恢复这一判断也是有问题的,等你的改进了.EliCZ源程序中用到的从VWIN32服务函数表来直接查找_VWIN32_Set_Thread_Context地址的方法我也没有找到详细资料,反正VxD快死了,我想知道也就足够了.

    VxD部分我改写了一下,没有处理TERMINATE_THREAD消息,但有问题,如果不怕死机,可以试试.仅供理解关键点参考.
   
    错误难免,如有发现,请指出:QQ:8709369(经常在线)

*/
;===============================Rc文件
#include <d:\masm32\include\resource.h>

100 DIALOG DISCARDABLE  0, 0, 113, 17
STYLE DS_MODALFRAME | WS_POPUP | WS_CAPTION | WS_SYSMENU |DS_CENTER
CAPTION "SuperBPM,Rewrite in Masm32,hume"
FONT 9, "System"
BEGIN
    CONTROL        "擦除恢复",101,"Button",BS_AUTORADIOBUTTON | WS_GROUP,
                    2,3,45,10
    CONTROL        "监视恢复",102,"Button",BS_AUTORADIOBUTTON,58,3,50,10
END


;===============================superBpm.exe.asm
.586
.model flat, stdcall
option casemap :none  ; case sensitive
include c:\hd\hd.h
include c:\hd\mac.h
DlgP            proto :DWORD,:DWORD,:DWORD,:DWORD
CallDriver              proto :DWORD
;;--------------
    .DATA
DrxUnHook  equ    800h
DrxHook    equ    801h
DrxMonitor equ    802h

SuperbpmDevice  db "\\.\superbpm.vxd",0
Traceflg        dd 0
        .DATA?
hVxD    dd ?
hResume dd ?
hStop  dd ?
;;-----------------------------------------
    .CODE
__Start:
        hTemplate      EQU 0
    invoke    CreateFile,addr SuperbpmDevice,GENERIC_READ+GENERIC_WRITE,\
                                FILE_SHARE_READ+FILE_SHARE_WRITE,\
                                0,\
                                OPEN_EXISTING,FILE_FLAG_DELETE_ON_CLOSE,\
                                hTemplate
        inc    eax
        jne    CrSuccess
                                                            ;打开驱动(.vxd)失败,出错         
        invoke    MessageBox,0,CTEXT("Can't Load superbpm.vxd"),CTEXT("Err report:"),30h+1000h       
        jmp    __Quit
    ;-----------------------------------------
    
CrSuccess:
        dec    eax
        mov    hVxD,eax                ;保存句柄
        invoke    GetModuleHandle,0
        invoke    DialogBoxParam,eax,100,0,offset DlgP,0
        invoke    CloseHandle,hVxD        ;要关闭


        ;-----------------------------------------       
__Quit:
        invoke    ExitProcess,0
;################################################################################
DlgP    proc uses esi edi ebx hWnd:DWORD,wMsg:DWORD,wParam:DWORD,lParam:DWORD
        mov    eax,wMsg
        .IF eax==WM_INITDIALOG
                invoke    GetDlgItem,hWnd,101
                mov    hResume,eax
                invoke    SendMessage,eax,BM_SETCHECK,BST_CHECKED,0
                invoke    SendMessage,hResume,WM_COMMAND,101,0
                invoke    GetDlgItem,hWnd,102
                mov    hStop,eax               
         
                invoke    SetWindowPos,hWnd,HWND_TOPMOST,0,0,0,0,SWP_NOMOVE or SWP_NOSIZE
                                                ;以上是初始化

        .ELSEIF eax==WM_CLOSE
                invoke    EndDialog,hWnd,0
                invoke    CallDriver,DrxUnHook
               

        .ELSEIF eax==WM_COMMAND
                mov    edx,wParam
                .if    dx==101
                  test Traceflg,1
                  jnz  @f
                  mov  Traceflg,1
                  invoke    CallDriver,DrxHook        ;擦除及恢复drx功能打开
                 
              @@:   
                .elseif dx==102
                  cmp  Traceflg,0
                  je  @f
                  mov  Traceflg,0                       
                  invoke    CallDriver,DrxMonitor    ;监视及恢复Drx 功能                         
              @@:       
                .endif

        .ELSE
                sub    eax,eax
                ret
        .ENDIF
        mov    eax,1
    ret
DlgP    endp
;;------------------------------------------------_
CallDriver PROC DrvFunc:DWORD                ;DeviceIoControl包装
        mov    edx,DrvFunc
        sub    eax,eax
        invoke    DeviceIoControl, hVxD, edx, eax, eax, eax,eax,eax,eax
        ret
CallDriver ENDP
END    __Start
;==========================superbpm.vxd.asm仅供参考,运行死机别找我
.586p
include C:\98DDK\inc\win98\vmm.inc
include C:\98DDK\inc\win98\vwin32.inc

DrxUnHook  equ    800h
DrxErase  equ    801h
DrxMonitor equ    802h

CmdUnhook EQU 0
CmdErase  EQU 1
CmdMonit  EQU 2

;------------------------------------
VxD_LOCKED_DATA_SEG
          orgEntry      dd 0
          orgSTC        dd 0
          TheThread    DWORD 0
          SavedDRx    DWORD 6 DUP (?)
          PreserveMode BYTE CmdErase
          Saved        BYTE 0
          installed      db 0
VxD_LOCKED_DATA_ENDS


VxD_LOCKED_CODE_SEG

DECLARE_VIRTUAL_DEVICE SUPERBPM,1,0, MESSAGE_Control, UNDEFINED_DEVICE_ID, UNDEFINED_INIT_ORDER

Begin_Control_Dispatch MESSAGE
    Control_Dispatch W32_DEVICEIOCONTROL , OnDeviceIoControl    ;处理相应发来的消息
End_Control_Dispatch MESSAGE
        ;-----------------------------------------DeviceIoControl       
        BeginProc      OnDeviceIoControl
                Assume esi:ptr DIOCParams             
                        .IF [esi].dwIoControlCode==DIOC_OPEN
                          sub  eax,eax
                          clc
                        .ELSEIF [esi].dwIoControlCode==DrxUnHook      ;退出卸载恢复原来的入口
                            mov ecx,orgEntry                           
                            mov dword ptr [ecx],OFFSET32 HookedSTC
                        @@:
                            and  TheThread,0
                            and  Saved,0
                            sub  eax,eax
                            clc

                        .ELSEIF [esi].dwIoControlCode==DrxErase
                       
                            cmp installed,1
                            je  @f                           
                            mov  eax, VWIN32_DEVICE_ID
                            VMMCall  Get_DDB            ;VWIn32的DDB
                                 
                            mov ecx, [ecx+38H]          ;得到引出服务表的地址
                            add ecx, 8+8*15H            ;第16项?我没找到详细资料,但确实是
                            cmp byte  ptr [ecx+4],2    ;后面存储的参数个数为2?
                            jnz @f
                            mov eax,[ecx]
                            mov orgSTC,eax
                            mov dword ptr [ecx],OFFSET32 HookedSTC
                            mov orgEntry,ecx            ;替换入口,实现hook功能
                            mov installed,1
                        @@:
                          mov PreserveMode, CmdErase  ;模式是CmdErase
                        ;-----------------------------------------
                          xor  eax,eax
                          clc
                        .ELSEIF [esi].dwIoControlCode==DrxMonitor
                          mov  PreserveMode, CmdMonit   
                          @@:
                          xor  eax,eax
                          clc
                        .ENDIF
                       
                        ret
        EndProc        OnDeviceIoControl

        HookedSTC  PROC
          PUSHFD
          PUSH    EAX
          PUSH    ECX
          PUSH    ESI
          PUSH    EDI
          MOV    ECX, [ESP+5*4 +4 +3*4]  ;ecx->CONTEXT
          CMP    PreserveMode, CmdErase 
          JE      HackContext


          @@:
            VMMCall Get_Cur_Thread_Handle  ;如果是Monitor模式就得到当前有非法企图的Thread句柄
                                            ;看看dr7,dr7是第7项
          CMP    BYTE PTR [ECX+4*5+4], 0  ;dr7=0?看看Seh资料的Context结构
          JE      Restore                  ;就恢复?

          CMP    Saved, 1
          JE      Done   

          MOV    TheThread, EDI          ;保存句柄

          CLD
          MOV    EDI, OFFSET SavedDRx    ;保存Drx 
          MOV    EAX, DR0
          STOSD
          MOV    EAX, DR1
          STOSD
          MOV    EAX, DR2
          STOSD
          MOV    EAX, DR3
          STOSD
          MOV    EAX, DR6
          STOSD
          MOV    EAX, DR7
          STOSD
          MOV    Saved, 1
          JMP    Done

          Restore:
          CMP    EDI, TheThread
          JNE    Done


          CMP    Saved, 1
          JE    HackContext
         
          CLD
          MOV    ESI, OFFSET SavedDRx    ;恢复Drx....
          LODSD
          MOV    DR0, EAX
          LODSD
          MOV    DR1, EAX
          LODSD
          MOV    DR2, EAX
          LODSD
          MOV    DR3, EAX
          LODSD
          MOV    DR6, EAX
          LODSD
          MOV    DR7, EAX
          MOV    Saved, 1

          HackContext:
          AND    BYTE PTR [ECX], NOT 10H    ;这个标志是不更新除Drx系列寄存器外
                                              ;恢复所有的寄存器,以此有些Seh把戏就无效了
          Done:
          POP    EDI
          POP    ESI
          POP    ECX
          POP    EAX
          POPFD
          JMP    orgSTC 
        HookedSTC  ENDP
VxD_LOCKED_CODE_ENDS

end
;-----------------Over-------------------
                                                    ; Hume 2002.3