【问题标题】:Why same variable got different virtual addresses at different runs?为什么同一个变量在不同的运行中得到不同的虚拟地址?
【发布时间】:2011-06-24 22:13:38
【问题描述】:

我需要知道我项目中变量(尤其是堆变量)的虚拟地址。变量的指针值实际上就是它的虚拟地址。我的理解是同一变量的虚拟地址在不同的运行中应该相同。我写了以下简单的代码来证明我的想法,但结果证明是错误的,

#include <stdio.h>
#include <stdlib.h>
int main(int argc, char **argv)
{
    int node=0;
    char* buffer;
    int i;
    printf("Hello World from Node %d the vm of i is %p and %ld \n",node, &i,&i);
    buffer = (char*)malloc(sizeof(char)*1024*1024*300); 
    for(i = 0; i < 1024*1024*300; i++){
    buffer[i] = (char)1;
}   
printf("I  am in %d and the vm of buffer is %p:%ld \n",node, buffer,buffer);
return 0;
}

但是对于不同的运行,我得到了不同的指针值,如下所示,

-bash-4.0$ gcc singletest.c
-bash-4.0$ ./a.out 
Hello World from Node 0 the vm of i is 0x7fffb87a8e00 and 140736288427520 
I  am in 0 and the vm of buffer is 0x7fb05dfcf010:140395467829264 
-bash-4.0$ ./a.out 
Hello World from Node 0 the vm of i is 0x7fffec2856f0 and 140737155454704 
I  am in 0 and the vm of buffer is 0x7f5888c54010:140018228477968 
-bash-4.0$ ./a.out 
Hello World from Node 0 the vm of i is 0x7fff1f44a780 and 140733717981056 
I  am in 0 and the vm of buffer is 0x7fbea3b91010:140456767328272 

我还编写了一个简单的 MPI 代码,每个进程只生成完全相同的变量。而且不同进程的同一个变量指针值不同,这和我想象的不一样。

谁能给我解释一下? 谢谢,

【问题讨论】:

    标签: pointers virtual memory-address


    【解决方案1】:

    无法保证变量的地址在两次运行之间保持不变。现代操作系统试图改变程序加载的地址以及堆和堆栈的地址,正是为了防止这种情况发生。他们这样做是因为它使攻击者更难利用某些类别的错误。

    具体来说,在您的情况下,您正在查看的变量是在堆上分配的指针。绝对没有理由期望在堆上分配两次内存会产生两次相同的地址。

    【讨论】:

    • 谢谢!如果地址随机化被禁用,你认为我有可能两次运行有相同的指针值吗?即使是堆变量?谢谢,
    • 我严重怀疑您是否可以依赖它。我不会推荐它。
    • 我只是按照stackoverflow.com/questions/1921485/… 的说明禁用随机化。堆变量具有不同运行的固定虚拟地址。
    • 我问的原因是你真的不能依赖这种行为。
    【解决方案2】:

    这个问题和我的一个类似:Pseudo-random stack pointer under Linux?

    正如 awser 中的链接所描述的,这一切都是出于安全原因而完成的。

    【讨论】:

    • 是的,地址空间随机化解决了我的担忧。谢谢!
    猜你喜欢
    • 2021-12-18
    • 1970-01-01
    • 2011-03-27
    • 2012-03-22
    • 2017-05-06
    • 1970-01-01
    • 2019-08-07
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多