A few days ago I was trying to write an exploit for a buffer overflow with GDB. This was a console application and pasting shellcode would mess with it.
There are a few options:
- Writing shellcode to a file and then using it as input for GDB.
# you can also include GDB commands like setting up breakpoints (e.g. b * 0xDEADBEEF) # remember to include a new line after each command $ python -c 'print "b * 0xDEADBEEF" + "\n" + "\x41"*1000 + "\n"' > input # $ perl -e for perl # start debugging with GDB # -q (quiet mode): no text at startup $ gdb executable1 -q (gdb) run < input
After this you can manually debug in GDB.
- Writing a Python script for interactive debugging When I wrote this, I thought it was a clever idea but then someone told me I could have written a GDB script. However, I have already written this snippet so here it goes.
#!/usr/bin/python from subprocess import Popen , PIPE from time import sleep # shellcode shellcode = "\x41" * 1000 + "\n" # opens gdb with parameter executable # you can also manage stdout and stderr here proc = Popen( ['gdb' , 'executable'] , bufsize=1 ,stdin=PIPE ) # sample breakpoint # notice the new line after each command proc.stdin.write('b *DEADBEEF\n') # half a second of sleep after each command sleep(0.5) # r or run to start debugging the program with GDB proc.stdin.write('r\n') sleep(0.5) # any other commands go here # this is a loop, will get every command and pass it to GDB # "leave" == quit GDB and terminate process # "dump" == paste shellcode while True: mycommand = raw_input() if (mycommand == "leave"): # quit gdb proc.stdin.write("quit\n") break # paste shellcode if (mycommand == "dump"): proc.stdin.write(shellcode) # more custom commands go here # not a custom command? send it as-is else: mycommand = mycommand + '\n' proc.stdin.write(mycommand) sleep(0.5) # close our pipe proc.stdin.close()
I think that this code can be modified and become a very simple fuzzer. We have control over stdin and can read stdout and stderr. Change input, record output, rinse and repeat.
subprocess is a very powerful module. For example to normally run an application with an argument we can write
but let's say we want to run executable with input (containing shellcode):
import subprocess shellcode = "\x41" * 100 subprocess.call( ['gdb' , 'executable'] , shellcode)