When evaluating a VarDecl as a constant or determining whether it is
an integral constant expression, maintain a cache of the value and the
is-an-ICE flag within the VarDecl itself. This eliminates
exponential-time behavior of the Fibonacci template metaprogram.

llvm-svn: 72428
diff --git a/clang/lib/AST/ExprConstant.cpp b/clang/lib/AST/ExprConstant.cpp
index 34b0187..7651884 100644
--- a/clang/lib/AST/ExprConstant.cpp
+++ b/clang/lib/AST/ExprConstant.cpp
@@ -700,8 +700,17 @@
   // In C, they can also be folded, although they are not ICEs.
   if (E->getType().getCVRQualifiers() == QualType::Const) {
     if (const VarDecl *D = dyn_cast<VarDecl>(E->getDecl())) {
-      if (const Expr *Init = D->getInit())
-        return Visit(const_cast<Expr*>(Init));
+      if (APValue *V = D->getEvaluatedValue())
+        return Success(V->getInt(), E);
+      if (const Expr *Init = D->getInit()) {
+        if (Visit(const_cast<Expr*>(Init))) {
+          // Cache the evaluated value in the variable declaration.
+          D->setEvaluatedValue(Info.Ctx, Result);
+          return true;
+        }
+
+        return false;
+      }
     }
   }