Notesearch利用异常(黑客:剥削艺术)

时间:2014-01-12 11:57:49

标签: c

这个问题是关于“黑客:剥削艺术”第二版第121页上的节目笔记研究的利用。

在漏洞利用中有一些我不理解的东西:

  

当系统执行./notesearch'xyz ....'参数时   'xyz ...'溢出了子程序中的字符串缓冲区   覆盖返回地址......很清楚。

这里的假设是,notesearch程序的堆栈帧位于调用exploit的Stack帧的顶部。当编译版本存在于同一系统上时,这是成立的。

我的第一个问题是1.这是否会作为远程黑客工作?

我的第二个问题是 2.由于缓冲区已用于覆盖包括返回地址在内的所有变量,因此notesearch程序如何按预期工作? 像“打印”等变量位于这个堆栈框架中并决定是否打印消息似乎都能正常工作。 即使调用函数位于相关堆栈帧的顶部,其中正在被泛洪的字符串缓冲区位于其中,也存在某些将被覆盖的关键变量。

问题编号。 3。 鉴于String缓冲区是在执行notesearch开始后推入的新堆栈帧的一部分,缓冲区将覆盖该notesearch程序中的所有给定变量。缓冲区也是搜索字符串的值。由于程序逻辑由于搜索字符串与消息不匹配,因此程序不应输出用户消息的详细信息。在这种情况下,会显示消息。我想知道为什么?

3 个答案:

答案 0 :(得分:2)

(供参考:本书为http://www.tinker.tv/download/hacking2_sample.pdf,代码可从http://www.nostarch.com/hacking2.htm免费下载。)

继续读这本书;另一个例子在第122页给出,然后有大量的解释性文本告诉所有有关漏洞的内容。

以下是notesearch代码的相关部分:

int main(int argc, char *argv[]) {
    int userid, printing=1, fd; // file descriptor
    char searchstring[100];

    if(argc > 1)                        // If there is an arg
        strcpy(searchstring, argv[1]);   //   that is the search string
    else                                // otherwise
        searchstring[0] = 0;             //   search string is empty

    userid = getuid();
    fd = open(FILENAME, O_RDONLY);   // open the file for read-only access

您写道:

  

这里的假设是notesearch程序的堆栈帧位于调用exploit的Stack帧的顶部。

不,那是错的。这里只有一个相关的堆栈帧:main()notesearch函数的堆栈帧。我们通过./notesearch xyz...内的system()调用调用exploit_notesearch这一事实无关紧要;我们也可以直接在bash命令行上调用./notesearch xyz...,或者欺骗其他一些进程(例如,你知道, bash )代表我们执行它。

  
      
  1. 这项工作即使是远程黑客工作吗?
  2.   

当然。

  
      
  1. 由于缓冲区已被用于覆盖包括返回地址在内的所有变量,因此notesearch程序如何按预期工作?
  2.   

嗯, 再看一下输出:

reader@hacking:~/booksrc $ gcc exploit_notesearch.c
reader@hacking:~/booksrc $ ./a.out
[DEBUG] found a 34 byte note for user id 999
[DEBUG] found a 41 byte note for user id 999
-------[ end of note data ]-------
sh-3.2#

明确给你一个壳不算“按预期工作”。但即便在此之前,该程序声称在/var/notes中找到了用户ID 999的注释,这可能表明它有点混乱。在我们作为恶意黑客的角色中,我们不关心关于来自notesearch程序的垃圾输出;我们所关心的是最终到达main()的末尾并返回我们的shellcode,让我们可以访问shell。

但是,如果您想知道我们如何设法覆盖返回地址而不覆盖局部变量useridprintingfd,那么至少有三种明显的可能性:< / p>

A。也许这些变量分配在堆栈的searchstring下面。

B。也许这些变量是在寄存器中而不是在堆栈中分配的。

C。绝大多数情况下,这些变量 被覆盖,但它们的初始值与程序无关。例如,userid可以获得任何值,因为该垃圾值将立即被下一行getuid()覆盖。唯一一个初始值很重要的变量是printing。甚至printing只有在恰好获得值0时才更改程序的行为 - 并且不能获取值0,因为根据设计,我们复制的数据完全由非零字节组成。

答案 1 :(得分:0)

我认为你真的不明白什么是缓冲区溢出。该searchstring变量最初位于堆栈上100个字节。现在,您将一大块缓冲区复制到searchstring中,而不检查它的长度。因此缓冲区溢出到notesearch主要功能的堆栈帧的其他部分。返回地址也会被覆盖。这就是它的工作原理。

答案 2 :(得分:0)

我认为这里最重要的假设是 notesearch 堆栈与 exploit_notesearch 类似。这就是他使用 exploit_notesearch 局部变量(unsigned int i)来计算 ret 的原因。他假设(当然,知道notesearch的源代码),当两个程序都加载到内存中时,它们将具有相似的帧地址(大约为0xffff7 ..) 当然,2个程序不共享内存,它们是不同的过程。