我在模块间内存分配/释放方面遇到了一些问题。 好像this帖子描述了同样的错误。
这是一段代码:
我的主要申请:
#pragma comment(lib, "mydll.lib")
__declspec(dllimport) std::shared_ptr<VOID> GetMemory(size_t size);
int wmain(int argc, wchar_t* argv[])
{
std::shared_ptr<VOID> lpMem = GetMemory(100);
return 0;
}
Dll代码:
__declspec(dllexport) std::shared_ptr<VOID> GetMemory(size_t size);
BOOL WINAPI DllMain(HINSTANCE, DWORD dwReason, LPVOID)
{
return TRUE;
}
std::shared_ptr<VOID> GetMemory(size_t size)
{
return std::shared_ptr<VOID>(new (std::nothrow) char[size]);
}
正确处理/MT
或/MD
编译器标志。并且执行不会失败。
我的问题是:为什么std::shared_ptr
的解决方案能够正常运行?它有什么变化?什么是那些&#34;内存管理器&#34; (在线程linked above中提到),在单个进程中是不同的?那只是一个CRT抽象吗?或者,CRT可能提供了一些特定的内存分配实现吗?
我认为,new
/ malloc
/ LocalAlloc
的任何来电都会导致HeapAlloc
。我对吗?如果是这样,为什么new
/ delete
- 在一个进程中的不同模块中调用(不包含std::shared_ptr
)会导致崩溃?
答案 0 :(得分:3)
RE
“为什么std :: shared_ptr的解决方案能够正常运行?
因为您有未定义的行为,并且UB包含您希望会发生的事情,所以会发生。它是UB,因为使用new[]
表达式创建的对象需要使用delete[]
表达式进行销毁。默认情况下,shared_ptr
会通过delete
表达式销毁。
这与DLL是否涉及无关。
RE
“ [使用
shared_ptr
]会有什么变化?
在DLL场景中,它可以捆绑一个调用特定于DLL的释放函数的删除函数。
但是,由于分配了shared_ptr
的控制块,您仍然可能会遇到问题。这是否表现为实际问题取决于您的构建设置(例如共享运行时库?)以及您正在使用的工具链。
RE
“那些”内存管理器“(在上面链接的线程中提到)是什么,它们在一个进程中是不同的
大概是每个DLL中的运行时。
如果所有DLL和主程序都链接到单个公共DLL运行时,而不是静态库运行时,那么所有DLL都使用相同的共享内存管理,那部分就可以了。