[CFG] Keep speculatively working around an MSVC compiler crash.
authorArtem Dergachev <artem.dergachev@gmail.com>
Sat, 24 Feb 2018 03:54:22 +0000 (03:54 +0000)
committerArtem Dergachev <artem.dergachev@gmail.com>
Sat, 24 Feb 2018 03:54:22 +0000 (03:54 +0000)
Replace if() with a switch(). Because random changes in the code seem to
suppress the crash.

Story so far:
r325966 - Crash introduced.
r325969 - Speculative fix had no effect.
r325978 - Tried to bisect the offending function, crash suddenly disappeared.
r326016 - After another random change in the code, bug appeared again.

llvm-svn: 326021

clang/lib/Analysis/CFG.cpp

index 7ad6fbb..1cf7063 100644 (file)
@@ -1171,25 +1171,47 @@ void CFGBuilder::findConstructionContexts(
     const ConstructionContext *ContextSoFar, Stmt *Child) {
   if (!BuildOpts.AddRichCXXConstructors)
     return;
+
   if (!Child)
     return;
-  if (auto *CE = dyn_cast<CXXConstructExpr>(Child)) {
-    consumeConstructionContext(ContextSoFar, CE);
-  } else if (auto *Cleanups = dyn_cast<ExprWithCleanups>(Child)) {
+
+  switch(Child->getStmtClass()) {
+  case Stmt::CXXConstructExprClass:
+  case Stmt::CXXTemporaryObjectExprClass: {
+    consumeConstructionContext(ContextSoFar, cast<CXXConstructExpr>(Child));
+    break;
+  }
+  case Stmt::ExprWithCleanupsClass: {
+    auto *Cleanups = cast<ExprWithCleanups>(Child);
     findConstructionContexts(ContextSoFar, Cleanups->getSubExpr());
-  } else if (auto *Cast = dyn_cast<CXXFunctionalCastExpr>(Child)) {
+    break;
+  }
+  case Stmt::CXXFunctionalCastExprClass: {
+    auto *Cast = cast<CXXFunctionalCastExpr>(Child);
+    findConstructionContexts(ContextSoFar, Cast->getSubExpr());
+    break;
+  }
+  case Stmt::ImplicitCastExprClass: {
+    auto *Cast = cast<ImplicitCastExpr>(Child);
     findConstructionContexts(ContextSoFar, Cast->getSubExpr());
-  } else if (auto *ImplicitCast = dyn_cast<ImplicitCastExpr>(Child)) {
-    if (ImplicitCast->getCastKind() == CK_NoOp)
-      findConstructionContexts(ContextSoFar, ImplicitCast->getSubExpr());
-  } else if (auto *BTE = dyn_cast<CXXBindTemporaryExpr>(Child)) {
+    break;
+  }
+  case Stmt::CXXBindTemporaryExprClass: {
+    auto *BTE = cast<CXXBindTemporaryExpr>(Child);
     findConstructionContexts(
         ConstructionContext::create(cfg->getBumpVectorContext(), BTE,
                                     ContextSoFar),
         BTE->getSubExpr());
-  } else if (auto *CO = dyn_cast<ConditionalOperator>(Child)) {
+    break;
+  }
+  case Stmt::ConditionalOperatorClass: {
+    auto *CO = cast<ConditionalOperator>(Child);
     findConstructionContexts(ContextSoFar, CO->getLHS());
     findConstructionContexts(ContextSoFar, CO->getRHS());
+    break;
+  }
+  default:
+    break;
   }
 }