我在这里走过房子,我以为我找到了解决办法。它当然似乎正确地识别了我所知道的问题,但也导致了大约一半系统测试用例中无法解释的崩溃。
问题是我们的代码需要将客户端代码作为dll调用。我们可以控制我们的代码,但不能控制客户的代码,而且经验表明他们的代码并不总是完美无缺。我已经通过退出程序并保留了可能出错的明确信息来防止分段错误,但我也有一些来自客户端代码的除零异常,我想要识别和然后退出。
我一直想做的是:
理论上有很多方法可以做到这一点,但许多方法似乎不适用于VS2010。
我一直在尝试使用floating_point编译指示:
#pragma float_control(except, on, push)
// run client code
#pragma float_control(pop)
__asm fwait; // This forces the floating point unit to synchronise
if (_statusfp() & _SW_ZERODIVIDE)
{
// abort the program
}
这在理论上应该没问题,而且在实践中它在50%的情况下运作良好。
我认为问题可能是float_point控件仍然存在,并导致代码中的其他地方出现问题。
根据microsoft.com:
“/ fp:exact,/ fp:fast,/ fp:strict和/ fp:除了开关控制 逐个文件的浮点语义。 float_control pragma在逐个函数的基础上提供这种控制。“
但是,在编译期间我收到警告:
警告C4177:#pragma'float_control'应该只在全局使用 范围或命名空间范围
从表面上讲,这是一个直接的矛盾。
所以我的问题是:
答案 0 :(得分:2)
你试过
#pragma float_control(except, on, push)
// run client code
#pragma float_control(pop)
这不是它的工作原理。它是一个编译器指令,它意味着
#pragma float_control(except, on, push)
// This entire function is compiled with float_control exceptions on.
// Therefore, the pragma has to appear outside the function, at global scope.
#pragma float_control(pop)
当然,此设置仅影响正在编译的功能,不会影响他们可能调用的任何功能 - 例如您的客户端。 #pragma无法改变已编译的代码。
所以,答案是:
_controlfp_s