Meh*_*dad 8 c++ x86-64 atomic visual-c++ no-op
如果您编译如下代码
#include <atomic>
int load(std::atomic<int> *p) {
return p->load(std::memory_order_acquire) + p->load(std::memory_order_acquire);
}
Run Code Online (Sandbox Code Playgroud)
int load(std::atomic<int> *) PROC
mov edx, DWORD PTR [rcx]
npad 1
mov eax, DWORD PTR [rcx]
npad 1
add eax, edx
ret 0
Run Code Online (Sandbox Code Playgroud)
为什么是这样?有什么办法可以避免它而不放松内存顺序(这会影响代码的正确性)?
p->load()最终可能会使用_ReadWriteBarrier编译器内部函数。
据此: https: //developercommunity.visualstudio.com/t/-readwritebarrier-intrinsic-eits-unnecessary-code/1538997
\n\n\nnops 被插入是因为现在默认情况下启用了/volatileMetadata 标志。您可以通过添加 /volatileMetadata- 返回到旧的行为,但如果您的代码曾经被模拟运行,这样做会导致性能更差。它\xe2\x80\x99仍将被正确模拟,但模拟器将不得不悲观地假设每个加载/存储都需要一个屏障。
\n
编译/volatileMetadata-确实删除了npad.