Pufferüberlauf mit fgets

Ich experimentiere mit Pufferüberläufen und versuche, die Rücksprungadresse des Stacks mit einer bestimmten Eingabe von fgets zu überschreiben

Dies ist der Code:

void foo()
{
    fprintf(stderr, "You did it.\n");
}

void bar()
{
    char buf[20];
    puts("Input:");
    fgets(buf, 24, stdin);
    printf("Your input:.\n", strlen(buf));
}


int main(int argc, char **argv)
{
    bar();
    return 0;
}

Bei einer normalen Ausführung gibt das Programm nur Ihre Eingabe zurück. Ich möchte, dass es foo () ausgibt, ohne den Code zu ändern.

Meine Idee war, den Puffer von überzulaufenbuf durch Eingabe von 20'A's. Dies funktioniert und verursacht einen Segmentierungsfehler. Meine nächste Idee war es, die Adresse von herauszufindenfoo() welches ist\x4006cd und füge dies an die 20 an'A's.

Nach meinem Verständnis sollte dies die Rücksprungadresse des Stapels überschreiben und ihn zum Springen bringenfoo. Aber es verursacht nur einen Segfehler.

Was mache ich falsch?

Update: Assembler legt main ab

    Dump of assembler code for function main:
   0x000000000040073b <+0>: push   %rbp
   0x000000000040073c <+1>: mov    %rsp,%rbp
   0x000000000040073f <+4>: sub    $0x10,%rsp
   0x0000000000400743 <+8>: mov    %edi,-0x4(%rbp)
   0x0000000000400746 <+11>:    mov    %rsi,-0x10(%rbp)
   0x000000000040074a <+15>:    mov    $0x0,%eax
   0x000000000040074f <+20>:    callq  0x4006f1 <bar>
   0x0000000000400754 <+25>:    mov    $0x0,%eax
   0x0000000000400759 <+30>:    leaveq 
   0x000000000040075a <+31>:    retq   
   End of assembler dump.

foo

Dump of assembler code for function foo:
   0x00000000004006cd <+0>: push   %rbp
   0x00000000004006ce <+1>: mov    %rsp,%rbp
   0x00000000004006d1 <+4>: mov    0x200990(%rip),%rax        # 0x601068 <stderr@@GLIBC_2.2.5>
   0x00000000004006d8 <+11>:    mov    %rax,%rcx
   0x00000000004006db <+14>:    mov    $0x15,%edx
   0x00000000004006e0 <+19>:    mov    $0x1,%esi
   0x00000000004006e5 <+24>:    mov    $0x400804,%edi
   0x00000000004006ea <+29>:    callq  0x4005d0 <fwrite@plt>
   0x00000000004006ef <+34>:    pop    %rbp
   0x00000000004006f0 <+35>:    retq   
End of assembler dump.

Bar:

Dump of assembler code for function bar:
   0x00000000004006f1 <+0>: push   %rbp
   0x00000000004006f2 <+1>: mov    %rsp,%rbp
   0x00000000004006f5 <+4>: sub    $0x20,%rsp
   0x00000000004006f9 <+8>: mov    $0x40081a,%edi
   0x00000000004006fe <+13>:    callq  0x400570 <puts@plt>
   0x0000000000400703 <+18>:    mov    0x200956(%rip),%rdx        # 0x601060 <stdin@@GLIBC_2.2.5>
   0x000000000040070a <+25>:    lea    -0x20(%rbp),%rax
   0x000000000040070e <+29>:    mov    $0x18,%esi
   0x0000000000400713 <+34>:    mov    %rax,%rdi
   0x0000000000400716 <+37>:    callq  0x4005b0 <fgets@plt>
   0x000000000040071b <+42>:    lea    -0x20(%rbp),%rax
   0x000000000040071f <+46>:    mov    %rax,%rdi
   0x0000000000400722 <+49>:    callq  0x400580 <strlen@plt>
   0x0000000000400727 <+54>:    mov    %rax,%rsi
   0x000000000040072a <+57>:    mov    $0x400821,%edi
   0x000000000040072f <+62>:    mov    $0x0,%eax
   0x0000000000400734 <+67>:    callq  0x400590 <printf@plt>
   0x0000000000400739 <+72>:    leaveq 
   0x000000000040073a <+73>:    retq   
End of assembler dump.

Antworten auf die Frage(2)

Ihre Antwort auf die Frage