]> granicus.if.org Git - clang/commitdiff
Make sure to always check the result of
authorDouglas Gregor <dgregor@apple.com>
Fri, 12 Nov 2010 07:15:47 +0000 (07:15 +0000)
committerDouglas Gregor <dgregor@apple.com>
Fri, 12 Nov 2010 07:15:47 +0000 (07:15 +0000)
SourceManager::getPresumedLoc(), so that we don't try to make use of
an invalid presumed location. Doing so can cause crashes.

git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@118885 91177308-0d34-0410-b5e6-96231b3b80d8

13 files changed:
include/clang/Basic/SourceManager.h
lib/AST/StmtDumper.cpp
lib/AST/TypePrinter.cpp
lib/Basic/SourceLocation.cpp
lib/Checker/AnalysisConsumer.cpp
lib/Checker/AnalyzerStatsChecker.cpp
lib/Frontend/DocumentXML.cpp
lib/Frontend/PrintPreprocessedOutput.cpp
lib/Frontend/TextDiagnosticPrinter.cpp
lib/Lex/PPDirectives.cpp
lib/Lex/PPMacroExpansion.cpp
lib/Lex/Pragma.cpp
tools/libclang/CIndexInclusionStack.cpp

index 4f5c17344d1d687052ca8d49dffbebfe6b340548..d5e41de25f0ac3448cb15ec627c69b0b735e8a0b 100644 (file)
@@ -724,6 +724,11 @@ public:
   ///
   /// Note that a presumed location is always given as the instantiation point
   /// of an instantiation location, not at the spelling location.
+  ///
+  /// \returns The presumed location of the specified SourceLocation. If the
+  /// presumed location cannot be calculate (e.g., because \p Loc is invalid
+  /// or the file containing \p Loc has changed on disk), returns an invalid
+  /// presumed location.
   PresumedLoc getPresumedLoc(SourceLocation Loc) const;
 
   /// isFromSameFile - Returns true if both SourceLocations correspond to
index 8b3ad5a61fd302f14e0322ce5bfc103205d257d5..afc9b509e7be0c3f34cefa2fcbb46ee58e60c395 100644 (file)
@@ -169,15 +169,15 @@ namespace  {
 void StmtDumper::DumpLocation(SourceLocation Loc) {
   SourceLocation SpellingLoc = SM->getSpellingLoc(Loc);
 
-  if (SpellingLoc.isInvalid()) {
-    OS << "<invalid sloc>";
-    return;
-  }
-
   // The general format we print out is filename:line:col, but we drop pieces
   // that haven't changed since the last loc printed.
   PresumedLoc PLoc = SM->getPresumedLoc(SpellingLoc);
 
+  if (PLoc.isInvalid()) {
+    OS << "<invalid sloc>";
+    return;
+  }
+
   if (strcmp(PLoc.getFilename(), LastLocFilename) != 0) {
     OS << PLoc.getFilename() << ':' << PLoc.getLine()
        << ':' << PLoc.getColumn();
index 2e7e06fef78e2d5115b5d8ceeb5bd698e08c1b00..b405db4bcedd43f755efa7ba314e4394edeb8b0e 100644 (file)
@@ -481,9 +481,9 @@ void TypePrinter::PrintTag(TagDecl *D, std::string &InnerString) {
       if (!HasKindDecoration)
         OS << " " << D->getKindName();
 
-      if (D->getLocation().isValid()) {
-        PresumedLoc PLoc = D->getASTContext().getSourceManager().getPresumedLoc(
+      PresumedLoc PLoc = D->getASTContext().getSourceManager().getPresumedLoc(
           D->getLocation());
+      if (PLoc.isValid()) {
         OS << " at " << PLoc.getFilename()
            << ':' << PLoc.getLine()
            << ':' << PLoc.getColumn();
index 7412b955606ab8863171d09b232548b8ba3dde3a..1571e2205f8cb29958173007cb20f6132c05f87d 100644 (file)
@@ -43,6 +43,11 @@ void SourceLocation::print(llvm::raw_ostream &OS, const SourceManager &SM)const{
 
   if (isFileID()) {
     PresumedLoc PLoc = SM.getPresumedLoc(*this);
+    
+    if (PLoc.isInvalid()) {
+      OS << "<invalid>";
+      return;
+    }
     // The instantiation and spelling pos is identical for file locs.
     OS << PLoc.getFilename() << ':' << PLoc.getLine()
        << ':' << PLoc.getColumn();
index e1591a6a649d7e1c82dc530add4300c8915357ed..16ad5a7ef1967a11b4cecd7f648d1d5e0177bbef 100644 (file)
@@ -143,19 +143,21 @@ public:
 
     SourceManager &SM = Mgr->getASTContext().getSourceManager();
     PresumedLoc Loc = SM.getPresumedLoc(D->getLocation());
-    llvm::errs() << "ANALYZE: " << Loc.getFilename();
+    if (Loc.isValid()) {
+      llvm::errs() << "ANALYZE: " << Loc.getFilename();
 
-    if (isa<FunctionDecl>(D) || isa<ObjCMethodDecl>(D)) {
-      const NamedDecl *ND = cast<NamedDecl>(D);
-      llvm::errs() << ' ' << ND << '\n';
-    }
-    else if (isa<BlockDecl>(D)) {
-      llvm::errs() << ' ' << "block(line:" << Loc.getLine() << ",col:"
-                   << Loc.getColumn() << '\n';
-    }
-    else if (const ObjCMethodDecl *MD = dyn_cast<ObjCMethodDecl>(D)) {
-      Selector S = MD->getSelector();
-      llvm::errs() << ' ' << S.getAsString();
+      if (isa<FunctionDecl>(D) || isa<ObjCMethodDecl>(D)) {
+        const NamedDecl *ND = cast<NamedDecl>(D);
+        llvm::errs() << ' ' << ND << '\n';
+      }
+      else if (isa<BlockDecl>(D)) {
+        llvm::errs() << ' ' << "block(line:" << Loc.getLine() << ",col:"
+                     << Loc.getColumn() << '\n';
+      }
+      else if (const ObjCMethodDecl *MD = dyn_cast<ObjCMethodDecl>(D)) {
+        Selector S = MD->getSelector();
+        llvm::errs() << ' ' << S.getAsString();
+      }
     }
   }
 
index 9badb79625d3c75026c95581c379f0995bdec2b2..c484537e957aacc22d7e8a58d7e9bfdf6a904470 100644 (file)
@@ -83,16 +83,18 @@ void AnalyzerStatsChecker::VisitEndAnalysis(ExplodedGraph &G,
   llvm::SmallString<128> buf;
   llvm::raw_svector_ostream output(buf);
   PresumedLoc Loc = SM.getPresumedLoc(D->getLocation());
-  output << Loc.getFilename() << " : ";
+  if (Loc.isValid()) {
+    output << Loc.getFilename() << " : ";
 
-  if (isa<FunctionDecl>(D) || isa<ObjCMethodDecl>(D)) {
-    const NamedDecl *ND = cast<NamedDecl>(D);
-    output << ND;
-  }
-  else if (isa<BlockDecl>(D)) {
-    output << "block(line:" << Loc.getLine() << ":col:" << Loc.getColumn();
+    if (isa<FunctionDecl>(D) || isa<ObjCMethodDecl>(D)) {
+      const NamedDecl *ND = cast<NamedDecl>(D);
+      output << ND;
+    }
+    else if (isa<BlockDecl>(D)) {
+      output << "block(line:" << Loc.getLine() << ":col:" << Loc.getColumn();
+    }
   }
-
+  
   output << " -> Total CFGBlocks: " << total << " | Unreachable CFGBlocks: "
       << unreachable << " | Aborted Block: "
       << (Eng.wasBlockAborted() ? "yes" : "no")
index 2f7e995b208f900ec338fbcb0682f540315d5857..b24ece5119d691d1dc61a884de0f0ec1f61fad8b 100644 (file)
@@ -327,9 +327,11 @@ PresumedLoc DocumentXML::addLocation(const SourceLocation& Loc)
   if (!SpellingLoc.isInvalid())
   {
     PLoc = SM.getPresumedLoc(SpellingLoc);
-    addSourceFileAttribute(PLoc.getFilename());
-    addAttribute("line", PLoc.getLine());
-    addAttribute("col", PLoc.getColumn());
+    if (PLoc.isValid()) {
+      addSourceFileAttribute(PLoc.getFilename());
+      addAttribute("line", PLoc.getLine());
+      addAttribute("col", PLoc.getColumn());
+    }
   }
   // else there is no error in some cases (eg. CXXThisExpr)
   return PLoc;
@@ -346,8 +348,9 @@ void DocumentXML::addLocationRange(const SourceRange& R)
     if (!SpellingLoc.isInvalid())
     {
       PresumedLoc PLoc = SM.getPresumedLoc(SpellingLoc);
-      if (PStartLoc.isInvalid() ||
-          strcmp(PLoc.getFilename(), PStartLoc.getFilename()) != 0) {
+      if (PLoc.isInvalid()) {
+      } else if (PStartLoc.isInvalid() ||
+                 strcmp(PLoc.getFilename(), PStartLoc.getFilename()) != 0) {
         addToMap(SourceFiles, PLoc.getFilename(), ID_FILE);
         addAttribute("endfile", PLoc.getFilename());
         addAttribute("endline", PLoc.getLine());
index 6019b30833864cf72dac91109650a92267840799..429999cd5e3c31033582dd2ed6e7a5524ae24fcf 100644 (file)
@@ -131,7 +131,10 @@ public:
 
   bool HandleFirstTokOnLine(Token &Tok);
   bool MoveToLine(SourceLocation Loc) {
-    return MoveToLine(SM.getPresumedLoc(Loc).getLine());
+    PresumedLoc PLoc = SM.getPresumedLoc(Loc);
+    if (PLoc.isInvalid())
+      return false;
+    return MoveToLine(PLoc.getLine());
   }
   bool MoveToLine(unsigned LineNo);
 
@@ -238,10 +241,13 @@ void PrintPPOutputPPCallbacks::FileChanged(SourceLocation Loc,
   SourceManager &SourceMgr = SM;
   
   PresumedLoc UserLoc = SourceMgr.getPresumedLoc(Loc);
+  if (UserLoc.isInvalid())
+    return;
+  
   unsigned NewLine = UserLoc.getLine();
 
   if (Reason == PPCallbacks::EnterFile) {
-    SourceLocation IncludeLoc = SourceMgr.getPresumedLoc(Loc).getIncludeLoc();
+    SourceLocation IncludeLoc = UserLoc.getIncludeLoc();
     if (IncludeLoc.isValid())
       MoveToLine(IncludeLoc);
   } else if (Reason == PPCallbacks::SystemHeaderPragma) {
@@ -593,10 +599,18 @@ void clang::DoPrintPreprocessedInput(Preprocessor &PP, llvm::raw_ostream *OS,
   // start.
   const SourceManager &SourceMgr = PP.getSourceManager();
   Token Tok;
-  do PP.Lex(Tok);
-  while (Tok.isNot(tok::eof) && Tok.getLocation().isFileID() &&
-         !strcmp(SourceMgr.getPresumedLoc(Tok.getLocation()).getFilename(),
-                 "<built-in>"));
+  do {
+    PP.Lex(Tok);
+    if (Tok.is(tok::eof) || !Tok.getLocation().isFileID())
+      break;
+
+    PresumedLoc PLoc = SourceMgr.getPresumedLoc(Tok.getLocation());
+    if (PLoc.isInvalid())
+      break;
+
+    if (strcmp(PLoc.getFilename(), "<built-in>"))
+      break;
+  } while (true);
 
   // Read all the preprocessed tokens, printing them out to the stream.
   PrintPreprocessedTokens(PP, Tok, Callbacks, *OS);
index 9e450d25c3d17fe71cda4a6e3930fe60ae605368..4fd0552bacff5bce388403b836fd299aaaa75a10 100644 (file)
@@ -57,7 +57,9 @@ PrintIncludeStack(SourceLocation Loc, const SourceManager &SM) {
   if (Loc.isInvalid()) return;
 
   PresumedLoc PLoc = SM.getPresumedLoc(Loc);
-
+  if (PLoc.isInvalid())
+    return;
+  
   // Print out the other include frames first.
   PrintIncludeStack(PLoc.getIncludeLoc(), SM);
 
@@ -328,7 +330,9 @@ void TextDiagnosticPrinter::EmitCaretDiagnostic(SourceLocation Loc,
     if (!Suppressed) {
       // Get the pretty name, according to #line directives etc.
       PresumedLoc PLoc = SM.getPresumedLoc(Loc);
-
+      if (PLoc.isInvalid())
+        return;
+      
       // If this diagnostic is not in the main file, print out the
       // "included from" lines.
       if (LastWarningLoc != PLoc.getIncludeLoc()) {
@@ -567,6 +571,10 @@ void TextDiagnosticPrinter::EmitCaretDiagnostic(SourceLocation Loc,
 
         // We specifically do not do word-wrapping or tab-expansion here,
         // because this is supposed to be easy to parse.
+        PresumedLoc PLoc = SM.getPresumedLoc(B);
+        if (PLoc.isInvalid())
+          break;
+        
         OS << "fix-it:\"";
         OS.write_escaped(SM.getPresumedLoc(B).getFilename());
         OS << "\":{" << SM.getLineNumber(BInfo.first, BInfo.second)
@@ -770,6 +778,9 @@ void TextDiagnosticPrinter::HandleDiagnostic(Diagnostic::Level Level,
   if (Info.getLocation().isValid()) {
     const SourceManager &SM = Info.getLocation().getManager();
     PresumedLoc PLoc = SM.getPresumedLoc(Info.getLocation());
+    if (PLoc.isInvalid())
+      return;
+    
     unsigned LineNo = PLoc.getLine();
 
     // First, if this diagnostic is not in the main file, print out the
index 7d428402db48a58256f4a8d548a03f218d0ef876..7aa3b31bc73775a437284cb3ab501fae01773469 100644 (file)
@@ -804,7 +804,9 @@ static bool ReadLineMarkerFlags(bool &IsFileEntry, bool &IsFileExit,
     FileID CurFileID =
       SM.getDecomposedInstantiationLoc(FlagTok.getLocation()).first;
     PresumedLoc PLoc = SM.getPresumedLoc(FlagTok.getLocation());
-
+    if (PLoc.isInvalid())
+      return true;
+    
     // If there is no include loc (main file) or if the include loc is in a
     // different physical file, then we aren't in a "1" line marker flag region.
     SourceLocation IncLoc = PLoc.getIncludeLoc();
index b779dd5654320b110f213b0b0667fdf71a892fd2..2428f9af4504db0a33236ec214fa49ec67bebd33 100644 (file)
@@ -723,7 +723,7 @@ void Preprocessor::ExpandBuiltinMacro(Token &Tok) {
     PresumedLoc PLoc = SourceMgr.getPresumedLoc(Loc);
 
     // __LINE__ expands to a simple numeric value.
-    OS << PLoc.getLine();
+    OS << (PLoc.isValid()? PLoc.getLine() : 1);
     Tok.setKind(tok::numeric_constant);
   } else if (II == Ident__FILE__ || II == Ident__BASE_FILE__) {
     // C99 6.10.8: "__FILE__: The presumed name of the current source file (a
@@ -732,19 +732,24 @@ void Preprocessor::ExpandBuiltinMacro(Token &Tok) {
 
     // __BASE_FILE__ is a GNU extension that returns the top of the presumed
     // #include stack instead of the current file.
-    if (II == Ident__BASE_FILE__) {
+    if (II == Ident__BASE_FILE__ && PLoc.isValid()) {
       SourceLocation NextLoc = PLoc.getIncludeLoc();
       while (NextLoc.isValid()) {
         PLoc = SourceMgr.getPresumedLoc(NextLoc);
+        if (PLoc.isInvalid())
+          break;
+        
         NextLoc = PLoc.getIncludeLoc();
       }
     }
 
     // Escape this filename.  Turn '\' -> '\\' '"' -> '\"'
     llvm::SmallString<128> FN;
-    FN += PLoc.getFilename();
-    Lexer::Stringify(FN);
-    OS << '"' << FN.str() << '"';
+    if (PLoc.isValid()) {
+      FN += PLoc.getFilename();
+      Lexer::Stringify(FN);
+      OS << '"' << FN.str() << '"';
+    }
     Tok.setKind(tok::string_literal);
   } else if (II == Ident__DATE__) {
     if (!DATELoc.isValid())
@@ -770,9 +775,11 @@ void Preprocessor::ExpandBuiltinMacro(Token &Tok) {
     unsigned Depth = 0;
 
     PresumedLoc PLoc = SourceMgr.getPresumedLoc(Tok.getLocation());
-    PLoc = SourceMgr.getPresumedLoc(PLoc.getIncludeLoc());
-    for (; PLoc.isValid(); ++Depth)
+    if (PLoc.isValid()) {
       PLoc = SourceMgr.getPresumedLoc(PLoc.getIncludeLoc());
+      for (; PLoc.isValid(); ++Depth)
+        PLoc = SourceMgr.getPresumedLoc(PLoc.getIncludeLoc());
+    }
 
     // __INCLUDE_LEVEL__ expands to a simple numeric value.
     OS << Depth;
index 8d469f609decedd0f385bd3df5d6a71a25b4a4d0..58625520a99175f70bbfec78c9e2e461b51e6c04 100644 (file)
@@ -329,6 +329,9 @@ void Preprocessor::HandlePragmaSystemHeader(Token &SysHeaderTok) {
 
 
   PresumedLoc PLoc = SourceMgr.getPresumedLoc(SysHeaderTok.getLocation());
+  if (PLoc.isInvalid())
+    return;
+  
   unsigned FilenameLen = strlen(PLoc.getFilename());
   unsigned FilenameID = SourceMgr.getLineTableFilenameID(PLoc.getFilename(),
                                                          FilenameLen);
index e86323956f91db85f6bc82198729766566f36e04..55edc1e3f3ec15ab724c29eb7eaede15f3009646 100644 (file)
@@ -55,7 +55,7 @@ void clang_getInclusions(CXTranslationUnit TU, CXInclusionVisitor CB,
     while (L.isValid()) {
       PresumedLoc PLoc = SM.getPresumedLoc(L);
       InclusionStack.push_back(cxloc::translateSourceLocation(Ctx, L));
-      L = PLoc.getIncludeLoc();
+      L = PLoc.isValid()? PLoc.getIncludeLoc() : SourceLocation();
     }
             
     // Callback to the client.