ELF64手脱UPX壳实战

最近在做CTF逆向习题时,遇到一个带有UPX壳的ELF CrackMe,题目的目标是找到flag。
由于此前只对PE做过UPX脱壳,本来使用UPX的脱壳工具,用命令就能脱壳,但是出于研究的目的,看看ELF文件的UPX如何手动脱壳,话不多说,进入正题~

0x1 工具和环境

  • IDA
  • Ubuntu18.04

0x2 寻找OEP

  • 首先在Ubuntu上运行程序,观察程序的运行情况

  • Ubuntu上打开终端使用命令查看当前IP
  • 将IDA文件夹内的linux_server64拷贝到Ubuntu系统中,给与运行权限并运行

  • 将ELF文件拖入Win上的IDA内,选择Linux远程调试器,填入Ubuntu的IP地址启动调试,弹框点击确定


  • 开始单步调试,单步调试遵循两个原则:1.除非F8跑飞,否则不用F7。2.循环直接跳过。




  • 0x3 Dump内存文件

  • 顺利找到OEP,准备dump内存
  • dump文件执行结束,在对应目录生成dump文件

  • 将dump文件拖入Ubuntu系统给与权限,并运行查看结果

    0x4 Dump文件代码

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26

27

28

29

30

31

32

33

34

35

36

37

38

39

40

41

42

43

44

45

46

47

48

49

50

51

52

53

54

55

56

57

58

59

60

61

62

63

64

65

#include <idc.idc>

#define PT_LOAD              1

#define PT_DYNAMIC           2

static main(void)

{

         auto ImageBase,StartImg,EndImg;

         auto e_phoff;

         auto e_phnum,p_offset;

         auto i,dumpfile;

         ImageBase=0x400000;

         StartImg=0x400000;

         EndImg=0x0;

         if (Dword(ImageBase)==0x7f454c46 || Dword(ImageBase)==0x464c457f )

  {

    if(dumpfile=fopen("G:\\dumpfile","wb"))

    {

      e_phoff=ImageBase+Qword(ImageBase+0x20);

      Message("e_phoff = 0x%x\n", e_phoff);

      e_phnum=Word(ImageBase+0x38);

      Message("e_phnum = 0x%x\n", e_phnum);

      for(i=0;i<e_phnum;i++)

      {

         if (Dword(e_phoff)==PT_LOAD || Dword(e_phoff)==PT_DYNAMIC)

                         {

                                 p_offset=Qword(e_phoff+0x8);

                                 StartImg=Qword(e_phoff+0x10);

                                 EndImg=StartImg+Qword(e_phoff+0x28);

                                 Message("start = 0x%x, end = 0x%x, offset = 0x%x\n", StartImg, EndImg, p_offset);

                                 dump(dumpfile,StartImg,EndImg,p_offset);

                                 Message("dump segment %d ok.\n",i);

                         }   

         e_phoff=e_phoff+0x38;

      }

 

      fseek(dumpfile,0x3c,0);

      fputc(0x00,dumpfile);

      fputc(0x00,dumpfile);

      fputc(0x00,dumpfile);

      fputc(0x00,dumpfile);

 

      fseek(dumpfile,0x28,0);

      fputc(0x00,dumpfile);

      fputc(0x00,dumpfile);

      fputc(0x00,dumpfile);

      fputc(0x00,dumpfile);

      fputc(0x00,dumpfile);

      fputc(0x00,dumpfile);

      fputc(0x00,dumpfile);

      fputc(0x00,dumpfile);

 

      fclose(dumpfile);

        }else Message("dump err.");

 }

}

static dump(dumpfile,startimg,endimg,offset)

{

        auto i;

        auto size;

        size=endimg-startimg;

        fseek(dumpfile,offset,0);

        for ( i=0; i < size; i=i+1 )

        {

        fputc(Byte(startimg+i),dumpfile);

        }

}

0x4 总结

  • 样本来源于CTF的逆向题,各位可放心下载练习,如果有兴趣,可以继续找出目标flag。
  • 链接: https://pan.baidu.com/s/1YzHb9zTPxUcRDcDnr2VZ6Q 提取码: 8ihv
  • 密码:bbs.pediy.com
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值