std :: uncaught_exception不能跨DLL边界工作

时间:2016-07-13 09:47:05

标签: c++ visual-c++ visual-studio-2013 visual-studio-2015

我在DLL中有一个带有析构函数的类,用于检查std :: uncaught_exception()。如果在可执行文件中使用try / catch-block,则如果抛出异常则不会返回true。

以下是一些示例代码: lib.h:

#pragma once

class __declspec(dllexport) C final
{
  public:
    ~C();
};

lib.cpp:

#include "lib.h"
#include <iostream>
#include <exception>

C::~C()
{
  std::cout << "C says: Uncaught: " << (std::uncaught_exception() ? "yes" : "no") << std::endl;
}

main.cpp中:

#include "lib.h"
#include <iostream>
#include <exception>

class D final
{
  public:
    ~D()
    {
      std::cout << "D says: Uncaught: " << (std::uncaught_exception() ? "yes" : "no") << std::endl;
    }
};


int main(int argc, char **argv)
{
  try
  {
    C c;
    D d;
    throw 88;
  }
  catch (int a)
  {
    std::cout << "Code: " << a << std::endl;
  }
  {
    C c;
    D d;
  }
  return 0;
}

使用以下方式构建所有内容:

cl.exe lib.cpp /EHsc /LD /c /Fo:lib.obj
link.exe lib.obj /incremental:no /fixed:no /DLL
cl.exe main.cpp /EHsc /LD /c /Fo:main.obj
link.exe main.obj /incremental:no /fixed:no lib.lib

在Visual Studio 2015和Visual Studio 2013 x64和x86上,我得到结果:

D says: Uncaught: yes
C says: Uncaught: no
Code: 88
D says: Uncaught: no
C says: Uncaught: no

我希望第二行是

C says: Uncaught: yes

因此,DLL中的类没有看到导致堆栈展开的异常导致它被调用析构函数。但是直接位于内部类中的类看到它。

是否有任何链接器/编译器标志可以按预期工作?

1 个答案:

答案 0 :(得分:4)

使用/MD动态运行时编译器选项。

如果没有一个,主可执行文件和每个DLL都有自己的运行时副本,并为每个模块复制其所有内部状态。