return to libc - problem

浪尽此生 提交于 2019-12-03 13:52:17
osgx

Let's do some asm before:

Code

$ cat gets.c
int main(int argc, char **argv) {
  char array[512];
  gets(array);
}

Asm

$ gcc gets.c -o getsA.s -S -fverbose-asm
$ cat gets.s
    ....
.globl main
        .type   main, @function
main:
        leal    4(%esp), %ecx   #,
        andl    $-16, %esp      #,
        pushl   -4(%ecx)        #  (1)
        pushl   %ebp            #  2
        movl    %esp, %ebp      #,
        pushl   %ecx            #  3
        subl    $516, %esp      #,
        leal    -516(%ebp), %eax        #, tmp60
        movl    %eax, (%esp)    # tmp60,
        call    gets            #  << break here  
        addl    $516, %esp      #,  << or here to see the stack picture
        popl    %ecx            #  (3')
        popl    %ebp            #  (2')
        leal    -4(%ecx), %esp  #  (1')
        ret
        .size   main, .-main

The prologue and epilogue (these are with alignment code) is described in detail here Understanding the purpose of some assembly statements

Stack layout:

(char)  array[0]
...
(char)  array[511]
(32bit) $ecx - pushed by 3 - it was the address on the stack of the eip which main will return to
(32bit) $ebp - pushed by 2
(32bit) $esp - pushed by 1 - change the $esp to the original value

So, if you want to change a return address of main, you should not to change address in stack which will be used by ret, but also to repeat the values saved in stack by (1),(2),(3) pushes. Or you can embed a new return address in the array itself and overwrite only (3) by the your new stack address+4. (use 516 byte string)

I suggest you use this source code to hack it:

$ cat getss.c
f()
{
  char array[512];
  gets(array);
}
int main(int argc, char **argv) {
    f();
}

because f have no problems with stack realignement

.globl f
        .type   f, @function
f:
        pushl   %ebp    #
        movl    %esp, %ebp      #,
        subl    $520, %esp      #,
        leal    -512(%ebp), %eax        #, tmp59
        movl    %eax, (%esp)    # tmp59,
        call    gets    #
        leave
        ret
        .size   f, .-f

Stack layout for f():

(char)  array[0]
...
(char)  array[511]
(32bit) old ebp
(32bit) return address

Breakpoint at ret instruction in f() with 520 bytes of "A"

(gdb) x/w $sp
0xXXXXXa3c:     0x41414141
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!