【问题标题】:Am I understanding the stack? please correct me我了解堆栈吗?请纠正我
【发布时间】:2014-03-18 08:32:08
【问题描述】:

我有这段代码是用c写的:

int main(){
  double x, y;
  int a, b, c;
  int *p;

我有:

sizeof(int)=4
sizeof(double)=8

内存结构是这样的吗? 更详细的图形模式:

IN MEMORY:(whole memory)
  LE = Little Endian  (INTEL)
  BE = Big Endian     (MIPS)

                                                  ------------------
                                    0x00000000   |                  | ?
                                                  ------------------
                                         .                 .
                                         .                 .
                                         .                 .
                                                  ------------------
                                    0x0012ff60   |  64(LE)  00(BE)  | 
                                                  ------------------
                                                  ------------------
                                    0x0012ff61   |  ff(LE)  12(BE)  | 
                                                  ------------------
                                                  ------------------
                                    0x0012ff62   |  12(LE)  ff(BE)  | 
                                                  ------------------
                                                  ------------------
                                    0x0012ff63   |  00(LE)  64(BE)  | 
                                                  ------------------

                                                  ------------------
                                    0x0012ff64   | 00(LE)   00(BE)  |  c         if c = 256        (base10)
                                                  ------------------                c = 0x00000100 (base16)
                                                  ------------------
                                    0x0012ff65   | 01(LE)   00(BE)  |  c   0x0012ff64 points to c variable
                                                  ------------------       0x0012ff64 is a pointer
                                                  ------------------
                                    0x0012ff66   | 00(LE)   01(BE)  |  c
                                                  ------------------
                                                  ------------------
                                    0x0012ff67   | 00(LE)   00(BE)  |  c 
                                                  ------------------
                                                  ------------------
                                    0x0012ff68   |                  |  b
                                                  ------------------
                                                           .
                                                           .
                                                           .
                                                  ------------------
                                    0x0012ff6c   |                  |  a
                                                  ------------------
                                                           .
                                                           .
                                                           .
                                                  ------------------
                                    0x0012ff70   |                  |  y
                                                  ------------------
                                                  ------------------
                                    0x0012ff71   |                  |  y
                                                  ------------------  
                                                  ------------------
                                    0x0012ff72   |                  |  y
                                                  ------------------
                                                  ------------------
                                    0x0012ff73   |                  |  y
                                                  ------------------
                                                  ------------------
                                    0x0012ff74   |                  |  y
                                                  ------------------
                                                  ------------------
                                    0x0012ff75   |                  |  y
                                                  ------------------
                                                  ------------------
                                    0x0012ff76   |                  |  y
                                                  ------------------
                                                  ------------------
                                    0x0012ff77   |                  |  y
                                                  ------------------
                                                          .
                                                          .
                                                          .
                                                  ------------------
                                    0x0012ff78   |                  |  x
                                                  ------------------
                                                          .
                                                          .
                                                          .
                                                  ------------------
                                    0xfffffffff  |                  |  ?
                                                  ------------------

我的问题: 当我们将某物压入堆栈时,我们会这样做吗?

1) 我的意思是我们将数据压入堆栈的末尾,地址值更高?

2) 或者我们将数据压入栈顶,地址值较低?

3)每个栈占用多少内存地址?这取决于什么?

谢谢

【问题讨论】:

  • ebb寄存器不指向返回指令指针,而是指向前一个函数的ebp
  • 不要忘记编译器可以(并且可能会)将局部变量存储在寄存器中 - 其中一些或全部可能根本不在堆栈上。
  • 请注意,即使 EBP 寄存器的含义也可能取决于编译器:使用优化时,甚至可能根本不使用 EBP。然而,在大多数情况下,x86 机器上的堆栈就像您理解的那样工作。但是在 x86 上,所有数据都是小端的!

标签: variables memory assembly x86 stack


【解决方案1】:

在 x86 机器上,如果编译器没有做任何特别的事情,堆栈将向下增长。在 push 上,堆栈指针将按 push 的大小递减,pushed 的数据将进入堆栈的较低地址。

pop 上,堆栈指针将按弹出的大小递增。

即使您在问题中提到了 MIPS,我也不会评论它,因为:

  1. 我对 MIPS 架构一无所知
  2. 您的问题已标记为x86

关于堆栈中每个变量的大小,这 100% 取决于编译器,所以我无法对此发表评论。

【讨论】:

  • 好吧,我真的不在乎MIPS,我为INTEL 写的内存结构正确吗?我的帖子中有 3 个问题,如果您能更详细地回答,我将不胜感激:)
  • 他还询问了(总)尺寸(我认为)。这是由编译器选择的(通常受操作系统限制)。在gcc 中,您可以使用--stack 选项对其进行更改。现代机器的典型值是 1 MB;现代 Linux 通常有 10 MB 的限制 (ulimit -s)。
  • @MortezaLSC:看起来还不错。另外,请注意您问了 两个 问题,因为 (1) 和 (2) 是相反的。
  • @Nathan Fellman 所以这在堆栈的顶部或末尾并不重要......重点是the pushed data will go onto the lower addresses of the stack。对吗?
  • 在我对内存的理解中,我显示了从顶部的0x00000000 到底部的0xfffffffff 的地址..但是图像是别的东西......是吗? :(
猜你喜欢
  • 1970-01-01
  • 2015-11-15
  • 1970-01-01
  • 1970-01-01
  • 2016-04-02
  • 2021-10-28
  • 2018-07-18
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多