首页
论坛
课程
招聘
对[FCG]KeyGen2.0按钮特效的分析[1].txt
2006-10-25 15:23 5889

对[FCG]KeyGen2.0按钮特效的分析[1].txt

2006-10-25 15:23
5889
  首先,注意一个比较特别的现象。原始版本在某些Windows上会崩溃,而崩溃后的Runtime Error对话框的OK按钮居然也是特效。说明什么?一定是钩子。
  用IDA反汇编正常的KG2,注意到和KG1的不同点,可以发现多了一个WM_SHOWWINDOW。其处理程序如下:

CODE:00408482 loc_408482:
CODE:00408482                 push    0
CODE:00408484                 call    sub_406984
CODE:00408489                 jmp     loc_4088E0

  可以看到,这是个stdcall/pascal类型的过程。至于到底是哪种,无关紧要。这里的参数只有一个,所以不必担心顺序。

CODE:00406984 sub_406984      proc near
CODE:00406984
CODE:00406984 arg_0           = dword ptr  8
CODE:00406984
CODE:00406984                 push    ebp
CODE:00406985                 mov     ebp, esp
//这里是典型的pascal/stdcall调用的开头。但是因为只有1个参数,无法肯定是哪个类型。
//值得注意的是,这是个VC的obj。所以不能因为是VC编译的obj就一概使用cdecl。
CODE:00406987                 push    ebx
CODE:00406988                 mov     ebx, [ebp+arg_0]
CODE:0040698B                 xor     eax, eax
CODE:0040698D                 test    ebx, ebx
CODE:0040698F                 jnz     short loc_4069CC
CODE:00406991                 cmp     ds:hhk, 0
CODE:00406998                 jnz     short loc_4069D2
CODE:0040699A                 push    1               ; lParam
CODE:0040699C                 push    offset fn       ; lpfn
CODE:004069A1                 call    GetCurrentThreadId_0
CODE:004069A6                 push    eax             ; dwThreadId
CODE:004069A7                 call    EnumThreadWindows
CODE:004069AC                 call    GetCurrentThreadId_0
CODE:004069B1                 push    eax             ; dwThreadId
CODE:004069B2                 push    0               ; hmod
CODE:004069B4                 push    offset sub_406D4A ; lpfn
CODE:004069B9                 push    4               ; idHook
CODE:004069BB                 call    SetWindowsHookExA
CODE:004069C0                 mov     ds:hhk, eax
CODE:004069C5                 mov     eax, ds:hhk
CODE:004069CA                 jmp     short loc_4069D2
CODE:004069CC
CODE:004069CC loc_4069CC:
CODE:004069CC                 push    ebx
CODE:004069CD                 call    sub_406A1F
CODE:004069D2
CODE:004069D2 loc_4069D2:
CODE:004069D2                 pop     ebx
CODE:004069D3                 pop     ebp
CODE:004069D4                 retn    4
CODE:004069D4 sub_406984      endp

  这个初始化过程(实际是个函数)的流程还是非常清楚的。但是这个参数到底是什么?从上面来看,如果参数为0,那么就枚举当前线程的窗口。看来应该是某窗口的句柄。通过查看sub_406A1F,发现00406A53处有对GetWindowLong的调用,而且传过去的ebx作为首个参数。这样,可以判断它是个窗口句柄。这里给出该过程的Pascal形式
Var
  CurrentHook:HHOOK;

Function Init(Window:HWND):HHOOK;
Begin
  Result:=0;
  If Window=0 Then
    Begin
      If CurrentHook=0 Then
        Begin
          EnumThreadWindows(GetCurrentThreadId,,1);
          CurrentHook:=SetWindowsHookEx(WH_CALLWNDPROC,sub_406D4A,0,GetCurrentThreadId);
          Result:=CurrentHook;
        End;
    End
  Else
    Begin
      sub_406A1F(Window);
    End;
End;

  CurrentHook又是什么呢?从上面看,应该是起类似于标志的作用。初始值为0,Hook过以后就是
Hook函数的句柄。所以修改一下定义
Const
  CurrentHook:HHOOK=0;

    首先看看sub_406D4A,这是一个CallWndProc函数。MSDN中有关定义如下:
LRESULT CALLBACK CallWndProc(
    int nCode,
    WPARAM wParam,
    LPARAM lParam
);

    再看看函数体:

seg000:00406D4A ; LRESULT __stdcall sub_406D4A(int,WPARAM,LPARAM)
seg000:00406D4A sub_406D4A      proc near               ; DATA XREF: sub_406984+30
seg000:00406D4A
seg000:00406D4A arg_0           = dword ptr  8
seg000:00406D4A wParam          = dword ptr  0Ch
seg000:00406D4A arg_8           = dword ptr  10h
seg000:00406D4A
seg000:00406D4A                 push    ebp
seg000:00406D4B                 mov     ebp, esp
seg000:00406D4D                 push    ebx
seg000:00406D4E                 push    esi
seg000:00406D4F                 mov     ebx, [ebp+arg_8]
//ebx:=LPARAM
//注意这里是一个地址,指向一个CWPSTRUCT结构
seg000:00406D52                 mov     esi, [ebp+arg_0]
//esi:=nCode
seg000:00406D55                 cmp     dword ptr [ebx+8], 1
//判断CWPSTRUCT.Message
//由于BN_PAINT=WM_CREATE=1,所以
//具体1是哪个message,需要根据进一步的分析来判断
seg000:00406D59                 jnz     short loc_406D67
seg000:00406D5B                 test    esi, esi
seg000:00406D5D                 jl      short loc_406D67
seg000:00406D5F                 push    dword ptr [ebx+0Ch]
//CWPSTRUCT.hwnd
seg000:00406D62                 call    sub_406A1F
seg000:00406D67
seg000:00406D67 loc_406D67:                             ; CODE XREF: sub_406D4A+F
seg000:00406D67                                         ; sub_406D4A+13
seg000:00406D67                 push    ebx             ; lParam
seg000:00406D68                 push    [ebp+wParam]    ; wParam
seg000:00406D6B                 push    esi             ; nCode
seg000:00406D6C                 push    ds:hhk          ; hhk
seg000:00406D72                 call    CallNextHookEx
seg000:00406D77                 pop     esi
seg000:00406D78                 pop     ebx
seg000:00406D79                 pop     ebp
seg000:00406D7A                 retn    0Ch
seg000:00406D7A sub_406D4A      endp

    其中的CWPSTRUCT结构:
typedef struct {
    LPARAM lParam;
    WPARAM wParam;
    UINT message;
    HWND hwnd;
} CWPSTRUCT, *PCWPSTRUCT;

    这个函数也不复杂:
Procedure CallBackWndProc(nCode:Integer;wParam:Cardinal;var lParam:CWPSTRUCT);stdcall;
Begin
  If (lParam.message=1) AND (nCode<0) Then
    Begin
      sub_406A1F(lParam.hwnd);
    End;
  CallNextHookEx(CurrentHook,nCode,wParam,lParam);

End;

[2023春季班]《安卓高级研修班(网课)》月薪两万班招生中~

上传的附件:
收藏
点赞0
打赏
分享
最新回复 (4)
雪    币: 10169
活跃值: 活跃值 (13001)
能力值: (RANK:350 )
在线值:
发帖
回帖
粉丝
kanxue 活跃值 8 2006-10-25 16:12
2
0
文章不错。
不知firstrose周末到苏州的旅游路线定好了没有。;)
雪    币: 484
活跃值: 活跃值 (18)
能力值: ( LV9,RANK:1060 )
在线值:
发帖
回帖
粉丝
wenglingok 活跃值 26 2006-10-25 18:56
3
0
学习下 HOOK.txt

旅游线路 苏州-杭州-上海-马来西亚-泰国-新加坡-柏林-温哥华-巴西 一日游
雪    币: 244
活跃值: 活跃值 (42)
能力值: ( LV12,RANK:650 )
在线值:
发帖
回帖
粉丝
firstrose 活跃值 16 2006-10-25 20:18
4
0
第1篇是去年2月份写的。第2篇开始写的时间是今年3月,今天刚刚写完,打算明天写完第3篇。
跟索耶学学,写完3再发2,手里总归要握一篇。
顺便打个广告,第2篇比第一篇好不少。

最初由 kanxue 发布
不知firstrose周末到苏州的旅游路线定好了没有。;)


路线已经定了,上午拙政园,中午观前街,下午虎丘。时间充裕的话再去寒山寺。
雪    币: 308
活跃值: 活跃值 (77)
能力值: ( LV12,RANK:470 )
在线值:
发帖
回帖
粉丝
zhuwg 活跃值 11 2006-10-28 11:39
5
0
旅游路线不错啊,哈哈
游客
登录 | 注册 方可回帖
返回