forked from OSchip/llvm-project
Fix macro backtrace printing.
Sometimes, a macro that expands to another macro name will not be printed in the macro backtrace. This patch finds the missed macro expansions and prints them. Fixes PR16799 llvm-svn: 246237
This commit is contained in:
parent
c269ed5115
commit
a1d7ece05c
|
@ -399,13 +399,7 @@ void DiagnosticRenderer::emitSingleMacroExpansion(
|
|||
const SourceManager &SM) {
|
||||
// Find the spelling location for the macro definition. We must use the
|
||||
// spelling location here to avoid emitting a macro backtrace for the note.
|
||||
SourceLocation SpellingLoc = Loc;
|
||||
|
||||
// If this is the expansion of a macro argument, point the caret at the
|
||||
// use of the argument in the definition of the macro, not the expansion.
|
||||
if (SM.isMacroArgExpansion(Loc))
|
||||
SpellingLoc = SM.getImmediateExpansionRange(Loc).first;
|
||||
SpellingLoc = SM.getSpellingLoc(SpellingLoc);
|
||||
SourceLocation SpellingLoc = SM.getSpellingLoc(Loc);
|
||||
|
||||
// Map the ranges into the FileID of the diagnostic location.
|
||||
SmallVector<CharSourceRange, 4> SpellingRanges;
|
||||
|
@ -477,11 +471,23 @@ void DiagnosticRenderer::emitMacroExpansions(SourceLocation Loc,
|
|||
SmallVector<SourceLocation, 8> LocationStack;
|
||||
unsigned IgnoredEnd = 0;
|
||||
while (Loc.isMacroID()) {
|
||||
LocationStack.push_back(Loc);
|
||||
// If this is the expansion of a macro argument, point the caret at the
|
||||
// use of the argument in the definition of the macro, not the expansion.
|
||||
if (SM.isMacroArgExpansion(Loc))
|
||||
LocationStack.push_back(SM.getImmediateExpansionRange(Loc).first);
|
||||
else
|
||||
LocationStack.push_back(Loc);
|
||||
|
||||
if (checkRangesForMacroArgExpansion(Loc, Ranges, SM))
|
||||
IgnoredEnd = LocationStack.size();
|
||||
|
||||
Loc = SM.getImmediateMacroCallerLoc(Loc);
|
||||
|
||||
// Once the location no longer points into a macro, try stepping through
|
||||
// the last found location. This sometimes produces additional useful
|
||||
// backtraces.
|
||||
if (Loc.isFileID())
|
||||
Loc = SM.getImmediateMacroCallerLoc(LocationStack.back());
|
||||
assert(!Loc.isInvalid() && "must have a valid source location here");
|
||||
}
|
||||
|
||||
|
|
|
@ -0,0 +1,50 @@
|
|||
// RUN: not %clang -cc1 -fsyntax-only %s 2>&1 | FileCheck %s
|
||||
|
||||
#define a b
|
||||
#define b c
|
||||
#define c(x) d(x)
|
||||
#define d(x) x*1
|
||||
|
||||
#define e f
|
||||
#define f g
|
||||
#define g(x) h(x)
|
||||
#define h(x) x
|
||||
|
||||
void PR16799() {
|
||||
const char str[] = "string";
|
||||
a(str);
|
||||
// CHECK: :15:3: error: invalid operands to binary expression
|
||||
// CHECK: ('const char *' and 'int')
|
||||
// CHECK: a(str);
|
||||
// CHECK: ^ ~~~
|
||||
// CHECK: :3:11: note: expanded from macro 'a'
|
||||
// CHECK: #define a b
|
||||
// CHECK: ^
|
||||
// CHECK: :4:11: note: expanded from macro 'b'
|
||||
// CHECK: #define b c
|
||||
// CHECK: ^
|
||||
// CHECK: :5:14: note: expanded from macro 'c'
|
||||
// CHECK: #define c(x) d(x)
|
||||
// CHECK: ^~~~
|
||||
// CHECK: :6:15: note: expanded from macro 'd'
|
||||
// CHECK: #define d(x) x*1
|
||||
// CHECK: ^~
|
||||
|
||||
e(str);
|
||||
// CHECK: :33:5: warning: expression result unused
|
||||
// CHECK: e(str);
|
||||
// CHECK: ^~~
|
||||
// CHECK: :8:11: note: expanded from macro 'e'
|
||||
// CHECK: #define e f
|
||||
// CHECK: ^
|
||||
// CHECK: :9:11: note: expanded from macro 'f'
|
||||
// CHECK: #define f g
|
||||
// CHECK: ^
|
||||
// CHECK: :10:16: note: expanded from macro 'g'
|
||||
// CHECK: #define g(x) h(x)
|
||||
// CHECK: ^
|
||||
// CHECK: :11:14: note: expanded from macro 'h'
|
||||
// CHECK: #define h(x) x
|
||||
// CHECK: ^
|
||||
}
|
||||
// CHECK: 1 warning and 1 error generated.
|
Loading…
Reference in New Issue