我在使用 Visual Studio 15 编译某些东西时遇到了问题。这段代码说明了这一点:
const char* getx() { return "foo"; }
void __declspec(naked) nf()
{
static const char* x = getx();
}
失败并出现以下错误:错误 C3068“nf”:“裸”函数不能包含在发生 C++ 异常时需要展开的对象
。不过,我真的不明白为什么会失败;静态对象不是自动的,就存储而言,它们的行为或多或少像全局对象,并且在执行入口点之前被初始化(据我所知)。如果是这样,那么这条消息指的是什么展开?此时堆栈上没有任何内容,所以没有什么可以放松的。此外,如果我删除函数调用,则 static
变量声明就可以了(没有赋值的函数调用也可以,或者为 x
变量分配常量值,例如static const char* x = 0;
).
我是不是漏掉了什么?
最佳答案
在 C++11 中引入的 noexcept
函数属性正式声明该函数不会抛出异常。
即使 getx() 可能不会抛出任何异常,编译器也不会自动添加 noexcept
属性,因为这会更改函数签名。
因此,当编译器解析 nf()
函数时,它会看到对另一个可能引发异常的函数的调用,这显然在特定于平台的“裸”中是被禁止的功能。
显式声明getx
为noexcept
显式声明此函数不会抛出异常,因此编译器将知道此函数调用不会抛出异常,并允许要编译的“裸”函数。
关于c++ - "Naked function cannot contain objects that would require unwinding..."静态初始化变量,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/34552828/