20211028gfsj_re_key

打开运行,闪退。拿去查壳,无壳,C++编译32位。

C++看着就烦,拿去OD调试。

F9运行一下,直接到达程序结束处,但总算看得到黑窗口有什么了。

?W?h?a?t h?a?p?p?e?n?

还有种方法可以不让它闪退。就是在cmd运行程序,而不是直接打开程序。这样就可以看到它的返回字符串且不闪退。

重新载入,右键->中文搜索引擎->智能搜索,看到很多有意义的字符串。

地址       反汇编                                    文本字符串
000F1043   mov eax,key.000F526C                      Unknown exception
000F115F   mov eax,dword ptr ds:[0xF529C]            emida
000F1164   movups xmm0,dqword ptr ds:[0xF528C]       themidathemidathemida
000F116E   movzx eax,word ptr ds:[0xF52A0]           a
000F1179   movzx eax,word ptr ds:[0xF52B4]           <.
000F1188   movups xmm0,dqword ptr ds:[0xF52A4]       >----++++....<<<<.
000F1246   mov edx,key.000F52E4                      ?W?h?a?t h?a?p?p?e?n?
000F133E   mov edx,key.000F52FC                      |------------------------------|
000F1356   mov edx,key.000F5320                      |==============================|
000F1373   mov edx,key.000F5320                      |==============================|
000F1390   mov edx,key.000F5320                      |==============================|
000F13AD   mov edx,key.000F5344                      \  /\  /\  /\  /\==============|
000F13CA   mov edx,key.000F5368                       \/  \/  \/  \/  \=============|
000F13E7   mov edx,key.000F538C                                       |-------------|
000F1415   mov edx,key.000F53B0                      Congrats You got it!
000F1421   mov edx,key.000F53C8                      =W=r=o=n=g=K=e=y=
000F21F6   push key.000F53DC                         string too long
000F2587   push key.000F52B8                         C:\Users\CSAW2016\haha\flag_dir\flag.txt
000F269C   push key.000F53DC                         string too long
000F29A8   mov [local.8],key.000F5280                bad cast
000F2D38   mov [local.8],key.000F5280                bad cast
000F3415   call key.000F389D                         (Initial CPU selection)
000F37DE   mov dword ptr ds:[ecx+0x4],key.000F5238   bad allocation
000F3817   mov dword ptr ds:[ecx+0x4],key.000F5254   bad array new length

因为有flag.txt路径,猜测这个程序是拿到key后读取flag.txt文件。一个一个看字符串。

先看Whathappen,上面有个跳转指令刚好跳过Whathappen,在跳转指令下断点,运行,改一下ZF的值使跳转实现,再运行,终端显示=W=r=o=n=g=K=e=y=

000F123E  |. /74 25         je short key.000F1265
000F1240  |. |8B0D C8500F00 mov ecx,dword ptr ds:[<&MSVCP140.std::cerr>]                ;  msvcp140.std::cerr
000F1246  |.  BA E4520F00   mov edx,key.000F52E4                     ;  ?W?h?a?t h?a?p?p?e?n?
000F124B  |.  68 502C0F00   push key.000F2C50
000F1250  |.  E8 AB170000   call key.000F2A00
000F1255  |.  8BC8          mov ecx,eax
000F1257  |.  FF15 98500F00 call dword ptr ds:[<&MSVCP140.std::basic>;  msvcp140.std::basic_ostream<wchar_t,std::char_traits<wchar_t> >::operator<<
000F125D  |.  6A FF         push -0x1                                ; /status = FFFFFFFF (-1.)
000F125F  |.  FF15 68510F00 call dword ptr ds:[<&api-ms-win-crt-runt>; \exit
000F1265  |> \8D55 AC       lea edx,[local.21]

再看Congrats You got it!,往上全都是call指令,直到遇到第一个跳转指令,下断点,运行。发现程序停在了123E地址,也就是我们下的第一个断点处,改一下ZF值再运行,发现断在了第二个断点处,改ZF,运行,终端显示Congrats You got it!。如果是爆破的话,那这样改就可以达到破解程序的目的了。可惜我们是要得到flag,那就需要逆向算法。

可知如果要到达Congrats You got it!,先要经过Whathappen那一个跳转指令。在那条跳转指令往上看看有什么东西。

000F11A0  |> /8A4435 DC               /mov al,byte ptr ss:[ebp+esi-0x24]
000F11A4  |. |8D4D 94                 |lea ecx,[local.27]
000F11A7  |. |324435 C4               |xor al,byte ptr ss:[ebp+esi-0x3C]
000F11AB  |. |04 16                   |add al,0x16
000F11AD  |. |8885 D8FEFFFF           |mov byte ptr ss:[ebp-0x128],al
000F11B3  |. |FFB5 D8FEFFFF           |push [local.74]
000F11B9  |. |6A 01                   |push 0x1
000F11BB  |. |E8 20100000             |call key.000F21E0
000F11C0  |. |46                      |inc esi
000F11C1  |. |83FE 12                 |cmp esi,0x12
000F11C4  |.^\7C DA                   \jl short key.000F11A0
000F11C6  |.  33F6                    xor esi,esi
000F11C8  |.  C745 D8 0F000000        mov [local.10],0xF
000F11CF  |.  8975 D4                 mov [local.11],esi
000F11D2  |.  C645 C4 00              mov byte ptr ss:[ebp-0x3C],0x0
000F11D6  |.  C645 FC 02              mov byte ptr ss:[ebp-0x4],0x2
000F11DA  |.  8B7D A8                 mov edi,[local.22]
000F11DD  |.  8B5D 94                 mov ebx,[local.27]
000F11E0  |>  83FF 10                 /cmp edi,0x10
000F11E3  |.  8D45 94                 |lea eax,[local.27]
000F11E6  |.  8D4D C4                 |lea ecx,[local.15]
000F11E9  |.  0F43C3                  |cmovnb eax,ebx
000F11EC  |.  8A0430                  |mov al,byte ptr ds:[eax+esi]
000F11EF  |.  04 09                   |add al,0x9
000F11F1  |.  8885 D8FEFFFF           |mov byte ptr ss:[ebp-0x128],al
000F11F7  |.  FFB5 D8FEFFFF           |push [local.74]
000F11FD  |.  6A 01                   |push 0x1
000F11FF  |.  E8 DC0F0000             |call key.000F21E0
000F1204  |.  46                      |inc esi
000F1205  |.  83FE 12                 |cmp esi,0x12
000F1208  |.^ 7C D6                   \jl short key.000F11E0
000F120A  |.  68 B8000000   push 0xB8                                                   ; /n = B8 (184.)
000F120F  |.  8D85 DCFEFFFF lea eax,[local.73]                                          ; |
000F1215  |.  6A 00         push 0x0                                                    ; |c = 00
000F1217  |.  50            push eax                                                    ; |s = 00000070
000F1218  |.  E8 ED2B0000   call <jmp.&VCRUNTIME140.memset>                             ; \memset
000F121D  |.  51            push ecx
000F121E  |.  8D8D DCFEFFFF lea ecx,[local.73]
000F1224  |.  E8 F7030000   call key.000F1620
000F1229  |.  C645 FC 03    mov byte ptr ss:[ebp-0x4],0x3
000F122D  |.  8B85 DCFEFFFF mov eax,[local.73]                                          ;  key.000F542C
000F1233  |.  8B40 04       mov eax,dword ptr ds:[eax+0x4]
000F1236  |.  F68405 E8FEFF>test byte ptr ss:[ebp+eax-0x118],0x6
000F123E  |.  74 25         je short key.000F1265

有两个循环,一个设置缓存函数,两个call指令。在第一个循环内某条指令下断点,跑一下发现它会跑出一些字符串,存在ecx中。在跳出循环的下一条指令下断点,F9运行,可以看到ecx存着循环跑完的字符串 `[^VZe`uYaY]`s^joY

第二个循环同样操作,发现它需要用到第一个循环跑出来的字符串,直至循环跑完,字符串为idg_cni~bjbfi|gsxb

设置缓存空间函数没什么可利用的,跳过。两个call指令执行完后的eax都是某个地址,不是返回值,也没什么好看的。所以关键就是那两个循环。

没想到吧,flag就是idg_cni~bjbfi|gsxb

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值