我正在学习c程序的内存管理。我已经怀疑了。 (Ubuntu OS)
我怀疑:
我想知道堆栈内和堆内的数据的地址。但是当我尝试打印这些地址时,我发现地址长度不同! 问题是为什么它显示的堆栈地址长度超过堆地址?
我所知道的:
我把我的演示代码放在这里,以便你能很好地回答我的疑问。
#include <stdio.h>
#include <stdlib.h>
int main()
{
int *ptr; // goes on stack
ptr = (int *)malloc(sizeof(int));
*ptr = 10; // 10 is stored on heap
printf("%p : heap address\n",ptr);
printf("%p: stack address\n",&ptr);
return 0;
}
输出: 我在终端
中得到了以下输出0x1ea2010 : heap address
0x7ffda62cb3c0: stack address
所以现在你可能会明白我在问什么。为什么堆栈地址的长度比堆长?堆是大量的内存,所以显然它应该有更长的长度。
如果堆栈和堆分配在相同的内存块中完成(根据现代OS ..我已经在某处读过),那么它也应该具有相同的长度。
好。请帮我把记忆概念弄清楚。
注意:如果我的疑问非常简单或愚蠢,那么至少请告诉我如何在我的演示代码中完成内存分配以及在不同长度的地址背后的魔力。
感谢阅读这样的帖子。快乐回答!
答案 0 :(得分:3)
鉴于您正在运行Ubuntu,我假设您在x86或x86-64平台上运行。假设这是真的,你的程序布局看起来像这样:
.delay
堆栈从高地址开始并向下“增长”(朝向递减地址),而堆从相当低的地址开始并且“向上”增长(朝向增加的地址)。 +-----------------------------+
High Address: | Command-line arguments |
| and environment variables |
+-----------------------------+
| Stack |
| | |
| V |
| |
| ^ |
| | |
| Heap |
+-----------------------------+
| Uninitialized Data |
+-----------------------------+
| Initialized Data |
+-----------------------------+
| Program Text |
Low Address: | (machine code) |
+-----------------------------+
转换说明符不会在地址值中打印前导零;如果是这样,你的地址就像
%p
两个地址的长度确实相同,只是前导零没有显示。
答案 1 :(得分:2)
您似乎正在使用64位地址,这意味着它们打印为最多 16个十六进制字符。你应该在左侧用零填充所有地址,以达到16个字符。
0x0000000001ea2010: heap address
0x00007ffda62cb3c0: stack address
堆和堆栈都位于相同的虚拟2 ^ 64字节空间中。
答案 2 :(得分:2)
printf中的格式字符串指定跳过前导零,这是默认值。您需要在%016p,%016x或%016X中添加所需的打印地址长度(如果需要大写十六进制字符)。
正确假设,所有指针的长度必须相同。
答案 3 :(得分:0)
没有标准。
但是,通常情况下,当堆栈向下增长时,堆会增长。因此,从逻辑上讲,在起始点,Heap的大小会更小,而Stack的大小会更大。
存在这样的实现的原因是因为它给程序提供了静态与动态内存重叠的可能性较小。
上面提到的虚拟地址和物理地址。从上下文来讲,一个进程中的每一块内存都是一个虚拟地址,因此,试图解释BUDDY算法是最好的冗余,最坏的情况是不相关的。
答案 4 :(得分:-1)
想象一下,你住在一条长街上。你住在街道的南端,房子的地址是1,2,3。
想象一下,这条街向北延伸一英里。想象一下,在街道的北端,地址是998,999,1000。
想象一下,到目前为止,只开发了街道的南北两端。从地址20到地址990只是未开发的空地。
但是在你街的尽头还有很多活动。新买家在20到30之间买入并开始在他们身上建造房屋。
与此同时,在街道的北端,没有那么多活动。看起来很多989和990已经售出,而且还有一些东西在那里建造。
那么,哪里有更大的游泳池&#34;未开发的地段?在街道的北端或南端?
到目前为止,街道南端(1-20,并且还在增长)的房屋数量比街道北端(990-1000)还多。到目前为止,街道南端的增长也更快。 (南端正在建设10个,北部为2个。)
然而,街道北端的地址比南方(2位数)更大(3位数字,从9位开始,或4位数字)。这是什么意思? (答案:它并不意味着什么。)