看起来 is_nothrow_constructible_v() 在 MSVC 中被破坏了,我错了吗?
Posted
技术标签:
【中文标题】看起来 is_nothrow_constructible_v() 在 MSVC 中被破坏了,我错了吗?【英文标题】:Looks like is_nothrow_constructible_v() is broken in MSVC, am I wrong? 【发布时间】:2020-07-10 19:52:38 【问题描述】:编辑: Here is 更好的代码重现。所有低于 19.20 的 MSVC 版本都无法编译测试。
此问题与this SO post 有关。我注意到当inplacer
下的逻辑引发异常时,我的应用程序会终止。
这里是重现的代码:
#include <optional>
struct S;
S foo() throw "oh, noes...";
template<class F>
struct inplacer
F f_;
operator std::invoke_result_t<F&>() return f_();
;
template<class F> inplacer(F) -> inplacer<F>;
int main()
try
std::optional<S> v;
v.emplace( inplacer [] return foo(); );
return 0;
catch(...) return 1;
如果我使用 MSVC v15.9.20 构建它并运行它——进程会得到std::terminate()
d。看来问题出在_Construct_in_place()
:
template<class _Ty,
class... _Types> inline
void _Construct_in_place(_Ty& _Obj, _Types&&... _Args)
_NOEXCEPT_COND(is_nothrow_constructible_v<_Ty, _Types...>) <----- HERE???
// invoke True Placement New to initialize the referenced object with _Args...
::new (const_cast<void *>(static_cast<const volatile void *>(_STD addressof(_Obj))))
_Ty(_STD forward<_Types>(_Args)...);
// std::_Construct_in_place<S,inplacer<S <lambda>(void) > >(S & _Obj, inplacer<S <lambda>(void) > && <_Args_0>)
看起来is_nothrow_constructible_v<S, inplacer<...>>
产生误报,导致noexcept
声明,当底层代码抛出时,这反过来会杀死我的应用程序。
附: GCC 和 Clang 似乎工作正常。
【问题讨论】:
【参考方案1】:这是一个known bug。在 msvc v19.16 中修复。
【讨论】:
以上是关于看起来 is_nothrow_constructible_v() 在 MSVC 中被破坏了,我错了吗?的主要内容,如果未能解决你的问题,请参考以下文章