欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页

Direct3D FPS

程序员文章站 2022-07-13 10:10:51
...

打开是个3d游戏,有枪有带笑脸的蛋有照片,使劲撞蛋上会死,开很多枪能打死蛋,然而有什么用!??很迷
用ida打开,shift+F12,比较关键的两个点,game over,game clear。
Direct3D FPS
找到主函数vinmain还有判断成功的函数sub_4039C0
Direct3D FPS
很明显dword_407020是血量,血量小于0就game over。否则就判断是否成功。
再看判断的函数

int *sub_4039C0()
{
  int *result; // eax@1

  result = dword_409194;地址
  while ( *result != 1 )
  {
    result += 132;
    if ( (signed int)result >= (signed int)&unk_40F8B4 )
    {
      MessageBoxA(hWnd, &byte_407028, "Game Clear!", 0x40u);
      return (int *)SendMessageA(hWnd, 2u, 0, 0);
    }
  }
  return result;
}

也很好理解,只要result>=unk_40F8B4就game clear。那再看dword_409194

.data:00409184 ; char byte_409184[]
.data:00409184 byte_409184     db ?                    ; DATA XREF: sub_403400+27r
.data:00409185                 align 10h
.data:00409190 ; int dword_409190[]
.data:00409190 dword_409190    dd ?                    ; DATA XREF: sub_403400+13r
.data:00409190                                         ; sub_403400+38w
.data:00409194 ; int dword_409194[]
.data:00409194 dword_409194    dd ?                    ; DATA XREF: sub_403400+1Dw
.data:00409194                                         ; sub_4039C0o

再看函数sub_403400

int __thiscall sub_403400(void *this)
{
  int result; // aaa@qq.com
  int v2; // aaa@qq.com
  int v3; // aaa@qq.com

  result = sub_403440(this);
  if ( result != -1 )
  {
    v2 = 132 * result;
    v3 = dword_409190[132 * result];//100
    if ( v3 > 0 )
    {
      dword_409190[v2] = v3 - 2;//每单位时间-2
    }
    else
    {
      dword_409194[v2] = 0;
      *((_BYTE *)&byte_407028 + result) ^= byte_409184[v2 * 4];
    }
  }
  return result;
}
 if ( dword_407BD4 )
          {
            sub_403400(v13);
            if ( dword_407BD8 < 5 )
              sub_401880(&v22);
            else
              dword_407BD8 = 0;
            ++dword_407BD8;
            if ( dword_407BDC >= 10 )
            {
              dword_407BDC = 0;
              PlaySoundA("data\\Shoot.wav", 0, 1u);每十秒播放一次
            }
            ++dword_407BDC;
          }

看到有个wp讲的是用idc,打印出来。
先看看idc是什么。。

看见IDA 在调试时,有一个默认python 的交换调试窗口.
点击它,可以改为IDC 脚本对话窗口.
然后可以在这个窗口中输入命令:

就是脚本,而且语言和c相似

IDC>auto i;for(i=0;i<50;i++)Message(“%d “, Byte(0x409184 + i*132*4)); 
0 4 8 12 16 20 24 28 32 36 40 44 48 52 56 60 64 68 72 76 80 84 88 92 96 100 104 108 112 116 120 124 128 132 136 140 144 148 152 156 160 164 168 172 176 180 184 188 192 196 

就是i*4,再看看

IDC>auto i;for(i=0;i<50;i++)Message(“%d, “, Byte(0x407028 + i)); 
67, 107, 102, 107, 98, 117, 108, 105, 76, 69, 92, 69, 95, 90, 70, 28, 7, 37, 37, 41, 112, 23, 52, 57, 1, 22, 73, 76, 32, 21, 11, 15, 247, 235, 250, 232, 176, 253, 235, 188, 244, 204, 218, 159, 245, 240, 232, 206, 240, 169,

然后用c进行处理

#include <stdio.h>
int main ()
{
    int i,s[50]={67, 107, 102, 107, 98, 117, 108, 105, 76, 69, 92, 69, 95, 90, 70, 28, 7, 37, 37, 41, 112, 23, 52, 57, 1, 22, 73, 76, 32, 21, 11, 15, 247, 235, 250, 232, 176, 253, 235, 188, 244, 204, 218, 159, 245, 240, 232, 206, 240, 169};
    for(i=0;i<50;i++)
        printf("%c",s[i] ^ (i*4));
}

运行出来是Congratulation~ Game Clear! Password is Thr3EDPr0m