为什么main函数与堆栈的其他功能不同

时间:2015-06-03 11:32:48

标签: c assembly operating-system stack-trace

我正在学习使用gdb,我有点困惑。这是我的代码:

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
void g(char *password) {
}

int main(int argc, char *argv[]) {
if(argc > 1)
    {
        g(argv[1]);
    } 
}

所以使用常规函数(本例中为g())如果我想检查函数参数,那就是ebp + 8 , ebp+12.. etc. But in main function when I'm trying to examine command line arguments (for example argv [1]`)看来,在这种情况下,先前检查参数的方法并不成功。所以我的问题是:

  1. 动态分配argv的内存(类似malloc)?
  2. 为什么不同大小的参数会改变argv本身的地址?(使用&#34; A&#34;它是0xbffff084但是使用&#34; A&#34; x10它是{ {1}})
  3. 为什么0xbffff074离ebp这么远?(在我的情况下,当我提供argv作为命令行参数时,ebp出现在0xbfffefe8argv 0xbffff084中)
  4. 命令行参数和ebp寄存器之间是什么?
  5. 最后一个问题(不是关于这个问题,而是...) 如何查看文件的实际内容?我的意思是当程序在程序集开始之前运行时,有一些正在运行的指令。例如,检查文件是否与您的操作系统等兼容...
    对不起,如果问题听起来很愚蠢我是gdb的新手。谢谢。

3 个答案:

答案 0 :(得分:2)

也许这澄清了。在使用GCC和GAS组装相同的代码时发现了这一点:

# GCC
# Stack is:
#ESP -> ret addr
#       argc
#       argv -> argv[0] -> "program name"
#               argv[1] -> "Key"
#               argv[2] -> "Infile"
#               argv[3] -> "Outfile"

# GAS
# Stack is:
#ESP -> argc
#       argv[0] -> "program name"
#       argv[1] -> "Key"
#       argv[2] -> "Infile"
#       argv[3] -> "Outfile"

我记得&#34; argv-list&#34;由操作系统构建。

答案 1 :(得分:1)

  1. 不,内存不是动态分配的。在main_start)之前的函数中,argvargc被推入堆栈以供main使用

  2. 地址的变化与参数的数量无关。它可能是另一个过程中蝴蝶翅膀的击球导致了这个

  3. 这是依赖于实现的。这很难说。但是你可以在GDB中运行这个命令来亲眼看看:

    disass _start
    
  4. ^^^

答案 2 :(得分:1)

函数参数是argv,是一个普通参数,与任何其他类型为char**的参数一样。 argv[1]不是函数参数,它是argv的偏移和解引用,您会在预期的位置找到 (这取决于目标ABI)。