我正在检查Visual C++ 10优化功能,发现了一件很奇怪的事情。本文中的所有代码均使用/O2进行编译。
在下面的代码中:
int _tmain(int argc, _TCHAR* argv[])
{
char buffer[1024] = {};
MessageBoxA( 0, buffer, buffer, 0 );
memset( buffer, 0, sizeof( buffer ) );
return 0;
}
从机器代码中删除
memset()
之前对return
的调用(我检查了反汇编)。这是完全合理的-如果此后没有读取buffer
,则memset()
没用,如果开发人员真的想覆盖缓冲区,则可以使用 SecureZeroMemory()
代替。但是在以下代码中:
int _tmain(int argc, _TCHAR* argv[])
{
char buffer[1024] = {};
MessageBoxA( 0, buffer, buffer, 0 );
memset( buffer, 0, sizeof( buffer ) );
Sleep( 0 ); //<<<<<<<<<<<<<<<<<<<<<<<<<<< Extra code
return 0;
}
没有消除对
memset()
的调用。该调用对观察到的行为没有影响,可以像在第一个代码段中一样被消除。这可能是编译器缺陷,也可能是有用的-我无法决定。
为什么在第二个代码段发出的机器代码中留下
memset()
调用会有用吗? 最佳答案
编译器可能无法说出MessageBoxA
并未为buffer
创建别名,该别名随后会被Sleep
使用。因此,它无法通过“假设”检查。