如何使用MSVC使malloc每次都返回相同的地址?

问题描述 投票:1回答:1

为了调试的目的,我想 malloc 每次执行程序时都返回相同的地址,但在MSVC中却不是这样的。

#include <stdlib.h>
#include <stdio.h>

int main() {
    int test = 5;
    printf("Stack: %p\n", &test);
    printf("Heap: %p\n", malloc(4));
    return 0;
}

用cygwin的gcc编译,每次都得到相同的Stack地址和Heap地址,而用msvc编译时aslr关闭... ...

cl t.c /link /DYNAMICBASE:NO /NXCOMPAT:NO

...我每次都得到相同的堆栈地址,但堆栈地址会改变。

我已经试过在注册表中加入 HKLM\SYSTEM\CurrentControlSet\Control\Session Manager\Memory Management\MoveImages 但却无法工作。

c visual-c++ malloc
1个回答
2
投票

返回的栈地址和指针都是由 malloc() 可能每次都不同。事实上,当程序被编译并在MacOS上多次运行时,两者都有所不同。

编译器或操作系统可能会导致这种行为,以尝试并使其更难以利用软件缺陷。在某些情况下,可能有一种方法可以防止这种情况,但如果你的目标是重播相同的一系列的 malloc() 地址,其他因素可能会改变地址,例如时间敏感行为、文件系统的副作用,更不用说非决定性的线程行为。你应该尽量避免依赖这个来进行测试。

还需要注意的是 &test 当作 (void *) 作为 %p 期待 void 指针,它不能保证与 int *.


2
投票

事实证明,你可能无法从MSVC运行时库中获得确定性行为。 无论是调试版还是生产版的CC++运行库,最终都会调用一个名为------的函数。 _malloc_base(),进而调用Win32 API函数 HeapAlloc(). 遗憾的是,这两种情况都没有发生。HeapAlloc() 也不是提供其堆的函数。HeapCreate(),记录一个标志或其他方式来获得确定性行为。

你可以在你自己的分配方案的基础上,在 VirtualAlloc()如同@Enosh_Cohen所建议的那样,但这样一来,你就会松开了 调试功能 MSVC分配函数提供的。


0
投票

堆的性质是这样的,它给你下一个可用的段,它可能位于任何地方。理论上,堆可以通过malloc完成的底层API调用与计算机上的其他一切共享。

此外,托管的操作系统利用 地址空间布局随机化 (ASLR)来防止漏洞。意味着无论是堆栈还是堆地址都不能保证在执行之间保持不变。

© www.soinside.com 2019 - 2024. All rights reserved.