我有一个简单的单成员结构,删除了复制结构/赋值,以及默认的移动构造/赋值.我试图通过值将这些结构中的一个传递给函数并返回该成员 - 非常简单.
struct NoCopy {
explicit NoCopy(int x) : x{x} {}
NoCopy(const NoCopy&) = delete;
NoCopy& operator=(const NoCopy&) = delete;
NoCopy(NoCopy&&) = default;
NoCopy& operator=(NoCopy&&) = default;
int x;
};
// noinline to ensure the crash is reproducible in release
// not required to reproduce the problem code
__declspec(noinline) int problem_function(NoCopy x) {
return x.x;
}
int main() {
return problem_function(NoCopy{ 1 });
}
Run Code Online (Sandbox Code Playgroud)
问题是当使用MSVC编译时,此函数崩溃.
查看反汇编,看起来当删除复制构造函数时,MSVC会尝试将其解释x为a NoCopy*,并且后续成员读取会导致分段错误.
这是一个godbolt的例子,用gcc和clang作为参考:https://godbolt.org/z/jG7kIw
请注意,gcc和clang都按预期运行.另请注意,这在优化和未优化的构建中都会发生,并且似乎会影响MSVC 2015和2017.
作为参考,我正在使用Visual Studio Professional 2015(14.0.25431.01 …