3

阅读关于不支持 FENV_ACCESS pragma的 clang 错误报告我遇到了一条评论

在不使用的情况下设置舍入模式会#pragma STDC FENV_ACCESS ON调用未定义的行为。见 C11 7.6.1/2。(C++ 中不存在此编译指示,因此 <cfenv> 无法使用,但这不是我们的错...)

C++ 中真的不存在这个编译指示,导致<cfenv>无法使用吗?我试图在 C++11 标准中搜索它,但实际上根本没有提到它。编译指示是否与函数原型一起从 C 继承?或者他们实际上不需要避免 UB,因为 C++ 标准没有说明当不使用编译指示时行为未定义(由于根本没有提到编译指示)?

4

1 回答 1

1

我搜索了 2015 年标准草案文本,没有发现 FENV_ACCESS 的出现。http://cppreference.com也一无所有。

但是,http://cplusplus.com确实提到了它(因为它不在标准中,我认为我们必须假设这是最好的咨询信息):

http://www.cplusplus.com/reference/cfenv/FENV_ACCESS/

引自 cplusplus.com:(强调我的)

如果设置为 on,程序会通知编译器它可能会访问浮点环境以测试其状态标志(异常)或在默认情况下以外的控制模式下运行。

如果设置为 off,编译器可能会执行某些可以破坏这些测试和模式更改的优化,因此在上述情况下访问浮点环境会导致未定义的行为

默认情况下,此 pragma 的状态是打开还是关闭取决于编译器设置和库实现。

鉴于令人不安的缺乏清晰度,我希望尽可能避免使用它。

与以往一样,如果使用是不可避免的,我想将它封装到一个类中,我可以专门针对每种架构进行测试。

然后记录这个类的存在以及如果编译器、环境或库实现升级可能引起的问题。

更新:

在 c++ 标准中有一个非常简短的标题:

§ 26.3 浮点环境 [cfenv]

...

2 标头定义了与 C 标准第 7.6 条相同的所有函数、类型和宏。

更新:

更多信息在这里:http ://en.cppreference.com/w/cpp/preprocessor/impl

我对此的解读是编译指示是由 C11 标准定义的,而不是 C++11 标准。因此,在 c++ 程序中的使用是严格实现/未定义的。

于 2016-03-25T12:12:59.870 回答