The analyzer can sometimes output the error "Some diagnostic messages may contain incorrect line number". This occurs in two cases:
- Use of multiline #define-macros on Microsoft Visual Studio 2005 system without Service Pack 1.
- Use of multiline #pragma directives on all supported versions of Microsoft Visual Studio.
Any code analyzer works only with preprocessed files, i.e. with those files in which all macros (#define) are substituted, and all include files are substituted (#include). With this, in the pre-processed file, information is contained about which files were substituted in which positions. That means, in the preprocessed files, information about line numbers is contained.
Preprocessing is carried out in any case. For the user, this procedure looks quite transparent. Sometimes, the preprocessor is a part of the code analyzer, and sometimes (like in the case with PVS-Studio) external preprocessor is used. In PVS-Studio, preprocessor by Microsoft Visual Studio is used. The analyzer starts the command line compiler cl.exe for each C/C++ file being processed and with its help, generates preprocessed file with "i" extension.
There exists an error in the preprocessor by Microsoft Visual Studio 2005. If preprocessing is done from the command line (the way it is done in PVS-Studio), then in case multiline macros are present in the program, information about line numbers becomes confused. This can lead to incorrect positioning of the code analyzer in the file. It means that the code analyzer will find the real problem, but it will show incorrectly the line in which this error was detected.
Let us explain it on an example. In a simple code, assert is used, with this, the expression in parentheses is divided into several lines. E.g., this way:
int _tmain(int argc, _TCHAR* argv[])
{
int a = 0;
int b = 1;
size_t c = 2;
assert(a ==
b);
a++; // the analyzer will show an error in this harmless line.
c = a; // actually, however, this diagnostic message should
// point at the line "c = a;".
return 0;
}
As we can see it from the remarks, because multiline assert is present, the analyzer will show that there exists an error (this is correct), but as the line that contains this error the above one will be shown. Of course, this can mislead the user.
If the same code is written with assert in one line, there will be no problem:
int _tmain(int argc, _TCHAR* argv[])
{
int a = 0;
int b = 1;
size_t c = 2;
assert (a == b);
a++;
c = a; // Diagnostic message refers to
// the correct line.
return 0;
}
This error shows itself only during PVS-Studio work on Microsoft Visual Studio 2005 without Visual Studio Service Pack 1. On Visual Studio 2005 Service Pack1, as well as on higher program versions (Visual Studio 2008 and higher) this problem does not exist. We recommend the following solution of the problem: install Visual Studio 2005 Service Pack 1 on Visual Studio 2005. Then the code with multiline macros will be processed by PVS-Studio analyzer correctly.
Here is one more situation at which the message "Some diagnostic messages may contain incorrect line number" is output, and a failure in positioning diagnostic messages occurs. It is referred to multiline directives #pragma of a special type. Here is an example of correct code:
#pragma warning(push)
void test()
{
int a = 0;
size_t b = a; // PVS-Studio will inform about the error here
}
If #pragma directive is written in two lines, the analyzer PVS-Studio will show an error in an incorrect place (there will be a one-line shift):
#pragma \
warning(push)
void test()
{
int a = 0; // PVS-Studio will show the error here,
size_t b = a; // actually, however, the error should be here.
}
In another case, however, with multiline #pragma directive there will be no error:
#pragma warning \
(push)
void test()
{
int a = 0;
size_t b = a; // PVS-Studio will inform about the error in this line
}
This error is corrected by installing Service Pack 1 on Visual Studio 2005 or upgrade to Visual Studio 2008. The only recommendation is either not to use multiline #pragma directives or to use them, but in the way they are correctly processed.
The code analyzer tries to detect a failure in lines numbering in the processed file. This mechanism is an heuristic one, and it cannot guarantee correct determination of positioning diagnostic messages in the program code. However, if it is possible to realize that a particular file contains multiline macros, and there exists a positioning error, then the message "Some diagnostic messages may contain incorrect line number" is given out.
This mechanism operates the following way.
The analyzer opens the source C/C++ file and searches for the very last token. Tokens not shorter than three symbols are selected only in order to ignore closing parentheses, etc. E.g., for the following code, operator "return" will be considered the last token:
01 #include "stdafx.h"
02
03 int foo(int a)
04 {
05 assert(a >= 0 &&
06 a <= 1000);
07 int b = a + 1;
08 return b;
09 }
Having found the last token, the analyzer will determine the number of line which contains it. In this very case, it is line 8. Further on, the analyzer searches for the last token in the file which has already been preprocessed. If the last tokens do not coincide, the macro in the end of file has been likely to substitute; the analyzer is unable to understand whether the lines are arranged correctly, and ignores the given situation. However, such situations occur very rarely, and last tokens almost always coincide in the source and preprocessed files. If it is so, the number of line, in which the token in the preprocessed file is situated, is determined.
Thus, we have the line numbers in which the last token is situated in the source file and in the preprocessed file. If these line numbers do not coincide, then there has been a failure in lines numbering. In this case, the analyzer will notify the user about it with the message "Some diagnostic messages may contain incorrect line number".
Please consider that if a multiline macro or a multiline #pragma-directive are situated in the file after all the dangerous code areas found, then all the line numbers for the found errors will be correct. Even though the analyzer outputs the message "Some diagnostic messages may contain incorrect line number for file", this will not prevent you from analyzing the diagnostic messages given out by it.
Please pay attention that though this is not an error purely of PVS-Studio code analyzer, it anyway leads to incorrect work of the code analyzer.