]> granicus.if.org Git - clang/commitdiff
Do not perform the analysis based warning if the warnings are ignored
authorOlivier Goffart <ogoffart@woboq.com>
Thu, 23 Nov 2017 08:15:22 +0000 (08:15 +0000)
committerOlivier Goffart <ogoffart@woboq.com>
Thu, 23 Nov 2017 08:15:22 +0000 (08:15 +0000)
This saves some cycles when compiling with "-w".

(Also fix a potential crash on invalid code for tools that tries to recover from some
errors, because analysis might compute the CFG which crashes if the code contains
invalid declaration. This does not happen normally with because we also don't perform
these analysis if there was an error.)

Differential Revision: https://reviews.llvm.org/D40242

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

lib/Sema/AnalysisBasedWarnings.cpp
unittests/Tooling/ToolingTest.cpp

index f004a990a4285e09e65c1e7d54d71a5d83adc493..c5b4eb27f90a8426cb786f719589cdccca94312f 100644 (file)
@@ -2080,10 +2080,10 @@ AnalysisBasedWarnings::IssueWarnings(sema::AnalysisBasedWarnings::Policy P,
   //     time.
   DiagnosticsEngine &Diags = S.getDiagnostics();
 
-  // Do not do any analysis for declarations in system headers if we are
-  // going to just ignore them.
-  if (Diags.getSuppressSystemWarnings() &&
-      S.SourceMgr.isInSystemHeader(D->getLocation()))
+  // Do not do any analysis if we are going to just ignore them.
+  if (Diags.getIgnoreAllWarnings() ||
+      (Diags.getSuppressSystemWarnings() &&
+       S.SourceMgr.isInSystemHeader(D->getLocation())))
     return;
 
   // For code in dependent contexts, we'll do this at instantiation time.
index 430dcaa831f663131b6fe85065289dd890fd3fac..891907a4d081acc37ca627dff1edeedcb84149b0 100644 (file)
@@ -564,5 +564,31 @@ TEST(ClangToolTest, InjectDiagnosticConsumerInBuildASTs) {
 }
 #endif
 
+TEST(runToolOnCode, TestResetDiagnostics) {
+  // This is a tool that resets the diagnostic during the compilation.
+  struct ResetDiagnosticAction : public clang::ASTFrontendAction {
+    std::unique_ptr<ASTConsumer> CreateASTConsumer(CompilerInstance &Compiler,
+                                                   StringRef) override {
+      struct Consumer : public clang::ASTConsumer {
+        bool HandleTopLevelDecl(clang::DeclGroupRef D) override {
+          auto &Diags = (*D.begin())->getASTContext().getDiagnostics();
+          // Ignore any error
+          Diags.Reset();
+          // Disable warnings because computing the CFG might crash.
+          Diags.setIgnoreAllWarnings(true);
+          return true;
+        }
+      };
+      return llvm::make_unique<Consumer>();
+    }
+  };
+
+  // Should not crash
+  EXPECT_FALSE(
+      runToolOnCode(new ResetDiagnosticAction,
+                    "struct Foo { Foo(int); ~Foo(); struct Fwd _fwd; };"
+                    "void func() { long x; Foo f(x); }"));
+}
+
 } // end namespace tooling
 } // end namespace clang