From 678839297204002df215e0be12bcd10b20a9a4a4 Mon Sep 17 00:00:00 2001 From: Richard Smith <richard-llvm@metafoo.co.uk> Date: Wed, 5 Dec 2012 03:18:16 +0000 Subject: [PATCH] Simplify diagnostic emission. No functionality change intended. git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@169351 91177308-0d34-0410-b5e6-96231b3b80d8 --- include/clang/Basic/SourceManager.h | 36 ++------------------------ lib/Frontend/DiagnosticRenderer.cpp | 39 ++++++++++++++--------------- 2 files changed, 21 insertions(+), 54 deletions(-) diff --git a/include/clang/Basic/SourceManager.h b/include/clang/Basic/SourceManager.h index 506947cbd64..a69ffad2907 100644 --- a/include/clang/Basic/SourceManager.h +++ b/include/clang/Basic/SourceManager.h @@ -1479,35 +1479,19 @@ public: bool UseLineDirectives = true) const{ // This is a condensed form of the algorithm used by emitCaretDiagnostic to // walk to the top of the macro call stack. - while (Loc.isMacroID()) { - Loc = skipToMacroArgExpansion(Loc); + while (Loc.isMacroID()) Loc = getImmediateMacroCallerLoc(Loc); - } return getPresumedLoc(Loc, UseLineDirectives); } - /// Look through spelling locations for a macro argument expansion, and if - /// found skip to it so that we can trace the argument rather than the macros - /// in which that argument is used. If no macro argument expansion is found, - /// don't skip anything and return the starting location. - SourceLocation skipToMacroArgExpansion(SourceLocation StartLoc) const { - for (SourceLocation L = StartLoc; L.isMacroID(); - L = getImmediateSpellingLoc(L)) { - if (isMacroArgExpansion(L)) - return L; - } - // Otherwise just return initial location, there's nothing to skip. - return StartLoc; - } - /// Gets the location of the immediate macro caller, one level up the stack /// toward the initial macro typed into the source. SourceLocation getImmediateMacroCallerLoc(SourceLocation Loc) const { if (!Loc.isMacroID()) return Loc; // When we have the location of (part of) an expanded parameter, its - // spelling location points to the argument as typed into the macro call, + // spelling location points to the argument as expanded in the macro call, // and therefore is used to locate the macro caller. if (isMacroArgExpansion(Loc)) return getImmediateSpellingLoc(Loc); @@ -1517,22 +1501,6 @@ public: return getImmediateExpansionRange(Loc).first; } - /// Gets the location of the immediate macro callee, one level down the stack - /// toward the leaf macro. - SourceLocation getImmediateMacroCalleeLoc(SourceLocation Loc) const { - if (!Loc.isMacroID()) return Loc; - - // When we have the location of (part of) an expanded parameter, its - // expansion location points to the unexpanded parameter reference within - // the macro definition (or callee). - if (isMacroArgExpansion(Loc)) - return getImmediateExpansionRange(Loc).first; - - // Otherwise, the callee of the macro is located where this location was - // spelled inside the macro definition. - return getImmediateSpellingLoc(Loc); - } - private: const llvm::MemoryBuffer *getFakeBufferForRecovery() const; const SrcMgr::ContentCache *getFakeContentCacheForRecovery() const; diff --git a/lib/Frontend/DiagnosticRenderer.cpp b/lib/Frontend/DiagnosticRenderer.cpp index 930a975dbad..084c5cb2883 100644 --- a/lib/Frontend/DiagnosticRenderer.cpp +++ b/lib/Frontend/DiagnosticRenderer.cpp @@ -380,7 +380,7 @@ void DiagnosticRenderer::emitMacroExpansionsAndCarets( unsigned OnMacroInst) { assert(!Loc.isInvalid() && "must have a valid source location here"); - + // If this is a file source location, directly emit the source snippet and // caret line. Also record the macro depth reached. if (Loc.isFileID()) { @@ -394,22 +394,12 @@ void DiagnosticRenderer::emitMacroExpansionsAndCarets( return; } // Otherwise recurse through each macro expansion layer. - - // When processing macros, skip over the expansions leading up to - // a macro argument, and trace the argument's expansion stack instead. - Loc = SM.skipToMacroArgExpansion(Loc); - - SourceLocation OneLevelUp = SM.getImmediateMacroCallerLoc(Loc); + // Walk up to the caller of this macro, and produce a backtrace down to there. + SourceLocation OneLevelUp = SM.getImmediateMacroCallerLoc(Loc); emitMacroExpansionsAndCarets(OneLevelUp, Level, Ranges, Hints, SM, MacroDepth, OnMacroInst + 1); - - // Save the original location so we can find the spelling of the macro call. - SourceLocation MacroLoc = Loc; - - // Map the location. - Loc = SM.getImmediateMacroCalleeLoc(Loc); - + unsigned MacroSkipStart = 0, MacroSkipEnd = 0; if (MacroDepth > DiagOpts->MacroBacktraceLimit && DiagOpts->MacroBacktraceLimit != 0) { @@ -417,11 +407,11 @@ void DiagnosticRenderer::emitMacroExpansionsAndCarets( DiagOpts->MacroBacktraceLimit % 2; MacroSkipEnd = MacroDepth - DiagOpts->MacroBacktraceLimit / 2; } - + // Whether to suppress printing this macro expansion. bool Suppressed = (OnMacroInst >= MacroSkipStart && OnMacroInst < MacroSkipEnd); - + if (Suppressed) { // Tell the user that we've skipped contexts. if (OnMacroInst == MacroSkipStart) { @@ -435,15 +425,24 @@ void DiagnosticRenderer::emitMacroExpansionsAndCarets( return; } - // Map the ranges. + // Find the spelling location for the macro definition. We must use the + // spelling location here to avoid emitting a macro bactrace 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); + + // Map the ranges into the FileID of the diagnostic location. SmallVector<CharSourceRange, 4> SpellingRanges; - mapDiagnosticRanges(MacroLoc, Ranges, SpellingRanges, &SM); + mapDiagnosticRanges(Loc, Ranges, SpellingRanges, &SM); SmallString<100> MessageStorage; llvm::raw_svector_ostream Message(MessageStorage); Message << "expanded from macro '" - << getImmediateMacroName(MacroLoc, SM, LangOpts) << "'"; - emitDiagnostic(SM.getSpellingLoc(Loc), DiagnosticsEngine::Note, + << getImmediateMacroName(Loc, SM, LangOpts) << "'"; + emitDiagnostic(SpellingLoc, DiagnosticsEngine::Note, Message.str(), SpellingRanges, ArrayRef<FixItHint>(), &SM); } -- GitLab