我可以将Visual C++运行时切换到另一个堆吗?

sha*_*oth 6 c++ memory-management visual-c++

我的程序使用第三方动态链接库,里面有巨大的内存泄漏.我的程序和库都是Visual C++本机代码.两者都动态链接到Visual C++运行时.

我想强制该库进入另一个堆,以便在库代码运行时通过Visual C++运行时完成的所有分配都在该堆上完成.我可以打电话HeapCreate(),稍后HeapDestroy().如果我以某种方式确保所有分配都在新堆中完成,我不再关心泄漏 - 当我销毁第二个堆时它们都会消失.

是否可以强制Visual C++运行时在指定的堆上进行所有分配?

rep*_*vsd 3

抱歉,我的最后一个答案发布得半生不熟,我按了选项卡并输入,但不记得这是一个文本框而不是编辑器......

无论如何,这是完整的:

您可以使用 detours 库来挂钩分配和释放函数,并将它们替换为您自己的:

隐约是这样的:

//declare a global 
HANDLE g_currentHeap;

LPVOID WINAPI HeapAlloc(HANDLE hHeap, DWORD dwFlags, SIZE_T dwBytes) 
{ 
    return OriginalHeapAlloc(g_currentHeap, dwFlags, dwBytes);
}


BOOL WINAPI HeapFree(HANDLE hHeap, DWORD dwFlags, LPVOID lpMem)
{
    return OriginalHeapFree(g_currentHeap, dwFlags, lpMem);
}
Run Code Online (Sandbox Code Playgroud)

在应用程序负载中

HANDLE g_Heaps[2];

int main()
{
    // Two heaps
    g_Heaps[0] = HeapCreate(...);
    g_Heaps[1] = HeapCreate(...);


    // Do whatevers needed to hook HeapAlloc and HeapFree and any other heap functions 
    // and redirect them to the versions above
    // Save the old function pointers so we can call them
}
Run Code Online (Sandbox Code Playgroud)

然后每次你从第 3 方 DLL 调用 API 时,你都可以这样做

void someFn()
{
    g_currentHeap = g_Heaps[1];
    Some3rdPartyAPI();
    g_currentHeap = g_Heaps[0];

    SomeOtherFunction();

}
Run Code Online (Sandbox Code Playgroud)

这应该可以解决你的问题

@peterchen:C++ 运行时为 new 和 malloc() 调用 HeapAlloc,因此这种方法可以工作。事实上,我相信几乎所有语言运行时都会使用 win32 堆函数,除非有特殊原因不这样做。