This information made possible by a generous grant from the Jonas Holderman Foundation. Jonas did the initial research on this and provided his findings.
Having the compiler find potential problems in your source code is a Good Thing™. To get the maximum benefit from the compiler, we want to set the warning level at the highest level (Level 4). Unfortunately, the Standard Template Library (STL) that ships with Microsoft's VC++ compiler has a lot of code that generates superfluous warnings at that level. Literally hundreds of warnings can be emitted from the compiler on a simple "Hello, World!" program. Compiling with warnings set at this level makes it virtually impossible to find the meaningful warnings that are scattered among the plethora of messages.The technique shown here isn't fool-proof, and some warnings may still leak out. But, this is a good starting point to allow you to get the maximum benefit from the compiler's warning messages.
Quick Example
The technique is to surround the STL header files at the top of your source file with #pragmas that temporarily reduce the warnings and then restore them:#pragma warning(disable: 4710) // Suppress 'function ... not inlined' for Release builds #pragma warning(disable: 4514) // Suppress '... unreferenced inline function has been removed' #pragma warning(push, 3) // Set warning levels to a quieter level for the STL // Place your #include directives for STL classes here #pragma warning(pop) // Restore warning levels for our code // The rest of your source file here ...
Details
This example below emits 24 warnings at level 4:#include <iostream>
int main(void)
{
std::cout << "Hello" << std::endl;
return 0;
}
The warnings look like this:
--------------------Configuration: Level4W - Win32 Debug-------------------- Compiling... main.cpp d:\program files\microsoft visual studio\vc98\include\xmemory(39) : warning C4100: '_P' : unreferenced formal parameter d:\program files\microsoft visual studio\vc98\include\xmemory(41) : warning C4100: '_P' : unreferenced formal parameter d:\program files\microsoft visual studio\vc98\include\xlocale(242) : warning C4511: 'codecvt_base' : copy constructor could not be generated d:\program files\microsoft visual studio\vc98\include\xlocale(223) : see declaration of 'codecvt_base' d:\program files\microsoft visual studio\vc98\include\xlocale(242) : warning C4512: 'codecvt_base' : assignment operator could not be generated d:\program files\microsoft visual studio\vc98\include\xlocale(223) : see declaration of 'codecvt_base' d:\program files\microsoft visual studio\vc98\include\xlocale(296) : warning C4663: C++ language change: to explicitly specialize class template 'codecvt' use the following syntax: template<> class codecvt... [ other warnings deleted ] Linking... Level4W.exe - 0 error(s), 24 warning(s)
Fortunately, (as we learned in CS220), there is a technique we can use to adjust the warning levels for specific files. We just need to wrap the STL #include lines in a #pragma.
Now, we will direct the compiler (using compiler directives, of course!) to set the warnings to Level 3 just prior to compiling the STL header files, and then restore the warnings to its previous setting (usually Level 4) immediately after processing the STL header files:
#pragma warning(push, 3) // Set warning levels to a quieter level for the STL
#include <iostream>
#pragma warning(pop) // Restore warning levels for our code
int main(void)
{
std::cout << "Hello" << std::endl;
return 0;
}
This doesn't quite solve the problem. Actually, it looks like it makes it worse because now our program
generates 140 warnings instead of a mere 24! Fortunately, all 140 warnings are of the form:
where XXXX is the name of a function. These warnings can safely be ignored by adding another #pragma to the code:warning C4514: 'XXXX' : unreferenced inline function has been removed
#pragma warning(disable: 4514) // Suppress 'unreferenced inline function has been removed'
#pragma warning(push, 3) // Set warning levels to a quieter level for the STL
#include <iostream>
#pragma warning(pop) // Restore warning levels for our code
int main(void)
{
std::cout << "Hello" << std::endl;
return 0;
}
Now, the code will compile quietly with the compiler warning level set to Level 4. Actually, it will only
compile quietly in a Debug build. Building in Release mode will cause one other warning to be emitted:
where XXXX is the name of a function. These warnings also can safely be ignored by adding another #pragma to the code. The final work-around should look something like this:warning C4710: function 'XXXX' not inlined
#pragma warning(disable: 4710) // Suppress 'function ... not inlined' for Release builds
#pragma warning(disable: 4514) // Suppress '... unreferenced inline function has been removed'
#pragma warning(push, 3) // Set warning levels to a quieter level for the STL
#include <iostream>
#pragma warning(pop) // Restore warning levels for our code
int main(void)
{
std::cout << "Hello" << std::endl;
return 0;
}
The technique shown here isn't fool-proof, and some warnings may still leak out. But, this is a good starting point
to allow you to get the maximum benefit from the compiler's warning messages.
My standard pragma template prevents non-Microsoft compilers (e.g. Borland and GNU) from complaining about the unknown pragmas by guarding them with ifdef specific to MS:
#ifdef _MSC_VER
#pragma warning(disable: 4290) // Suppress 'C++ Exception Specification ignored'
#pragma warning(disable: 4710) // Suppress 'function ... not inlined' for Release builds
#pragma warning(disable: 4514) // Suppress '... unreferenced inline function has been removed'
#pragma warning(disable: 4786) // Suppress '... truncated to 255 chars in debug'
#pragma warning(push, 3) // Set warning levels to a quieter level for the STL
#endif
/* System header files included here (e.g. iostream, string, etc. */
#ifdef _MSC_VER
#pragma warning(pop) // Restore warning levels for our code
#endif
/* My includes here... */
Additional Information