跨DLL边界抛出C ++异常

时间:2011-02-24 17:06:03

标签: c++ dll exception-handling

我已经阅读了有关如何不在一个DLL中分配堆内存并从该DLL外部解除分配的各种内容。但是抛出一个只是临时的异常对象(如大多数异常对象)呢? E.g:

throw my_exception( args ); // temporary: no heap allocation

当异常对象被捕获到DLL外部时,最终将执行该对象的析构函数,并且将回收该对象的非堆内存。这样可以,因为它不是堆内存吗?

2 个答案:

答案 0 :(得分:24)

只有当所有模块使用相同的C ++运行时,才能跨DLL边界抛出C ++异常,在这种情况下,它们也共享一个堆。但这可能是一种维护负担,尤其是涉及多个供应商的库时,所以不鼓励这样做。

如果您想要在多个编译器/编译器版本/编译器设置中可移植的错误处理,请使用返回代码或操作系统提供的异常(例如Windows上的SEH)/

答案 1 :(得分:1)

这取决于内存的分配方式以及执行此操作的机制(“运行时”或“内存管理器”)是否在特定DLL和应用程序的其他部分之间共享。例如。根据细节,throw new my_exception( args );也可以按顺序排列。

您可以对您的异常引用进行计数,以便它具有如何销毁自己的实例(以及拥有的内存)的内在知识。

使用IMalloc(请参阅MSDN)进行实例分配和展示位置new将是另一种方式(之前请致电OleInitialize)...

实际上,内存分配是一个问题,具体取决于所使用的内容。例如,在应用程序的不同部分混合使用静态链接的CRT和动态链接的CRT将导致问题与混合调试和释放代码相同。这里的问题是应该释放内存的代码使用不同的“内存管理器”。但是如果抛出的对象知道它自己的破坏,它应该没问题,因为dtor代码将与分配它的代码驻留在相同的编译单元中。