• 攻防世界 reverse evil


    这是2017 ddctf的一道逆向题,

    挑战:《恶意软件分析》

    赛题背景: 员工小A收到了一封邮件,带一个文档附件,小A随手打开了附件。随后IT部门发现小A的电脑发出了异常网络访问请求,进一步调查发现小A当时所打开的附件其实是一个伪装成word文档的恶意可执行文件。

    赛题描述: 请在试着分析evil.exe和其所下载的x.jpg, 从中找出key.

    评分标准: 密钥正确则可进入下一题。

    攻防世界只给了exe文件,没有给x.jpg文件,(每个人的x.jpg文件是不同的,解得的flag也是不一样的。)

    查壳: UPX(3.91)[NRV,best]

    脱壳:

    工具脱壳失败,手动脱壳。

    两次esp脱壳法,dump。

    (第一次脱没脱干净,但发现可以静态分析,0.0)

    具体分析可参考:

    【CTF习题】恶意软件分析
    https://www.52pojie.cn/thread-679122-1-1.html
    (出处: 吾爱破解论坛)

     1 int __stdcall WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nShowCmd)
     2 {
     3   char *new_data; // ST10_4
     4   int key[67]; // [esp+4h] [ebp-118h]
     5   size_t dwSize; // [esp+114h] [ebp-8h]
     6   void *jpg_data; // [esp+118h] [ebp-4h]
     7 
     8   if ( sub_401370(hInstance) == 6 )
     9     return 0;
    10   sub_401620();
    11   jpg_data = download_xjpg_4018F0(&dwSize);
    12   if ( jpg_data )
    13   {
    14     if ( dwSize )
    15     {
    16       new_data = malloc(dwSize);
    17       init_key_401740(key, 0x4A8754F5745174ui64);
    18       decrypt_401800(key, jpg_data, new_data, dwSize);
    19       exec_shellcode_401220(new_data, dwSize);
    20     }
    21     free(jpg_data);
    22   }
    23   return 0;
    24 }

    在decrypt_401800函数中,我把参数一定义成了个结构体,两个int型成员,一个byte[256]数组

    00000000 key_struct      struc ; (sizeof=0x108, mappedto_22)
    00000000 x               dd ?
    00000004 y               dd ?
    00000008 key_data        db 256 dup(?)
    00000108 key_struct      ends

    这样再看清晰了一些

     1 void __cdecl decrypt_401800(key_struct *key, char *jpg_data, char *new_data, unsigned int dwsize)
     2 {
     3   unsigned __int8 v4; // ST02_1
     4   unsigned __int8 v5; // ST03_1
     5   unsigned int i; // [esp+4h] [ebp-4h]
     6 
     7   for ( i = 0; i < dwsize; ++i )
     8   {
     9     key->x = (key->x + 1) % 256;
    10     key->y = (key->key_data[key->x] + key->y) % 256;
    11     v4 = key->key_data[key->x];
    12     v5 = key->key_data[key->y];
    13     key->key_data[key->x] = v5;
    14     key->key_data[key->y] = v4;
    15     new_data[i] = key->key_data[(v5 + v4) % 256] ^ jpg_data[i];
    16   }
    17 }

    wp:

     1 key=[]
     2 a=0x4A8754F5745174
     3 temp=[0 for i in range(8)]
     4 for i in range(8):
     5     temp[i]=a
     6     a=a>>8
     7 for i in range(256):
     8     key.append((i+temp[i%8])&0xff)
     9 
    10 
    11 f=open('x.jpg','rb')
    12 jpg_data=f.read()
    13 new_data=[]
    14 f.close()
    15 x=0
    16 y=0
    17 for i in range(len(jpg_data)):
    18     x=(x+1)%256
    19     y=(key[x]+y)%256
    20     key[x],key[y]=key[y],key[x]
    21     new_data.append(((key[(key[x]+key[y])%256]^jpg_data[i])^i)&0xff)
    22 # print(new_data)
    23 mf=open('mydecrypt','wb')
    24 mf.write(bytes(new_data))
    25 mf.close()
    26 
    27 new_data=bytes(new_data)
    28 flag = []
    29 i = 0
    30 while(i<len(new_data)):
    31     if(new_data[i]==0x68):#这里是解析push指令,保存压栈数据
    32         flag.append(new_data[i+1:i+5])
    33         i += 3
    34     i += 1
    35 
    36 for i in flag[::-1]:    #输出压栈数据
    37     print(str(i)[2:-1], end='')
    38 print()

    输出:

    Key: DDCTF-cc49badacb1c4d69bd4ae7173d9e9ade@didichuxing.comXCongratsX   user32.dll Ax8eNx0exec

    这题做的话最简单的方法就是搭本地服务,然后动态调试,省时省力。

    整体上程序流程清晰,算法还原也不复杂。

    脱壳请参考:https://www.cnblogs.com/dliv3/p/6909066.html

    攻防世界 key来源:https://blog.csdn.net/qq_38025365/article/details/89389311

    DDCTF-01c981e4d5ea4da6b38b2990abbaf411@didichuxing.com


    (滴滴的题还是蛮有趣的)

  • 相关阅读:
    【noip2011】选择客栈
    【noip2013】货车运输
    【bzoj3732】Network
    Codeforces 111C Petya and Spiders (状压dp)
    线段树优化 dijkstra (CF787D Legacy)
    Codeforces 908G Yet Another Maxflow Problem (最小割定理,线段树)
    IOI 2007 Sail (线段树+贪心)
    Codeforces 474E Pillars (树状数组+dp)
    Bzoj 3688 折线统计(dp+树状数组)
    Gorgeous Sequence (线段树)
  • 原文地址:https://www.cnblogs.com/DirWang/p/11551743.html
Copyright © 2020-2023  润新知