ExprConstant.cpp revision 8327fad71da34492d82c532f42a58cb4baff81a3
1b542afe02d317411d53b3541946f9f2a8f509a11Chris Lattner//===--- ExprConstant.cpp - Expression Constant Evaluator -----------------===//
2c44eec6dd29ee9415cbd38a35deff4c8b67abb6aAnders Carlsson//
3c44eec6dd29ee9415cbd38a35deff4c8b67abb6aAnders Carlsson//                     The LLVM Compiler Infrastructure
4c44eec6dd29ee9415cbd38a35deff4c8b67abb6aAnders Carlsson//
5c44eec6dd29ee9415cbd38a35deff4c8b67abb6aAnders Carlsson// This file is distributed under the University of Illinois Open Source
6c44eec6dd29ee9415cbd38a35deff4c8b67abb6aAnders Carlsson// License. See LICENSE.TXT for details.
7c44eec6dd29ee9415cbd38a35deff4c8b67abb6aAnders Carlsson//
8c44eec6dd29ee9415cbd38a35deff4c8b67abb6aAnders Carlsson//===----------------------------------------------------------------------===//
9c44eec6dd29ee9415cbd38a35deff4c8b67abb6aAnders Carlsson//
10c44eec6dd29ee9415cbd38a35deff4c8b67abb6aAnders Carlsson// This file implements the Expr constant evaluator.
11c44eec6dd29ee9415cbd38a35deff4c8b67abb6aAnders Carlsson//
12c44eec6dd29ee9415cbd38a35deff4c8b67abb6aAnders Carlsson//===----------------------------------------------------------------------===//
13c44eec6dd29ee9415cbd38a35deff4c8b67abb6aAnders Carlsson
14c44eec6dd29ee9415cbd38a35deff4c8b67abb6aAnders Carlsson#include "clang/AST/APValue.h"
15c44eec6dd29ee9415cbd38a35deff4c8b67abb6aAnders Carlsson#include "clang/AST/ASTContext.h"
16199c3d6cd16aebbb9c7f0d42af9d922c9628bf70Ken Dyck#include "clang/AST/CharUnits.h"
1719cc4abea06a9b49e0e16a50d335c064cd723572Anders Carlsson#include "clang/AST/RecordLayout.h"
180fe52e1bcaa69ba127f1bda036f057fec1f478deSeo Sanghyeon#include "clang/AST/StmtVisitor.h"
198ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor#include "clang/AST/TypeLoc.h"
20500d3297d2a21edeac4d46cbcbe21bc2352c2a28Chris Lattner#include "clang/AST/ASTDiagnostic.h"
218ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor#include "clang/AST/Expr.h"
221b63e4f732dbc73d90abf886b4d21f8e3a165f6dChris Lattner#include "clang/Basic/Builtins.h"
2306a3675627e3b3c47b49c689c8e404a33144194aAnders Carlsson#include "clang/Basic/TargetInfo.h"
247462b39a9bccaf4392687831036713f09f9c0681Mike Stump#include "llvm/ADT/SmallString.h"
254572baba9d18c275968ac113fd73b0e3c77cccb8Mike Stump#include <cstring>
264572baba9d18c275968ac113fd73b0e3c77cccb8Mike Stump
27c44eec6dd29ee9415cbd38a35deff4c8b67abb6aAnders Carlssonusing namespace clang;
28f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattnerusing llvm::APSInt;
29d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedmanusing llvm::APFloat;
30c44eec6dd29ee9415cbd38a35deff4c8b67abb6aAnders Carlsson
3187eae5ecf94e38baa20d9a327b8f73f8bdc72436Chris Lattner/// EvalInfo - This is a private struct used by the evaluator to capture
3287eae5ecf94e38baa20d9a327b8f73f8bdc72436Chris Lattner/// information about a subexpression as it is folded.  It retains information
3387eae5ecf94e38baa20d9a327b8f73f8bdc72436Chris Lattner/// about the AST context, but also maintains information about the folded
3487eae5ecf94e38baa20d9a327b8f73f8bdc72436Chris Lattner/// expression.
3587eae5ecf94e38baa20d9a327b8f73f8bdc72436Chris Lattner///
3687eae5ecf94e38baa20d9a327b8f73f8bdc72436Chris Lattner/// If an expression could be evaluated, it is still possible it is not a C
3787eae5ecf94e38baa20d9a327b8f73f8bdc72436Chris Lattner/// "integer constant expression" or constant expression.  If not, this struct
3887eae5ecf94e38baa20d9a327b8f73f8bdc72436Chris Lattner/// captures information about how and why not.
3987eae5ecf94e38baa20d9a327b8f73f8bdc72436Chris Lattner///
4087eae5ecf94e38baa20d9a327b8f73f8bdc72436Chris Lattner/// One bit of information passed *into* the request for constant folding
4187eae5ecf94e38baa20d9a327b8f73f8bdc72436Chris Lattner/// indicates whether the subexpression is "evaluated" or not according to C
4287eae5ecf94e38baa20d9a327b8f73f8bdc72436Chris Lattner/// rules.  For example, the RHS of (0 && foo()) is not evaluated.  We can
4387eae5ecf94e38baa20d9a327b8f73f8bdc72436Chris Lattner/// evaluate the expression regardless of what the RHS is, but C only allows
4487eae5ecf94e38baa20d9a327b8f73f8bdc72436Chris Lattner/// certain things in certain situations.
45c54061a679d8db4169438b2f97f81e3f443c6a25Benjamin Kramernamespace {
46c54061a679d8db4169438b2f97f81e3f443c6a25Benjamin Kramer  struct EvalInfo {
47c54061a679d8db4169438b2f97f81e3f443c6a25Benjamin Kramer    const ASTContext &Ctx;
481eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
491e12c59e8f9bb76c23628c4e0d0a1dfced0b1fa0Richard Smith    /// EvalStatus - Contains information about the evaluation.
501e12c59e8f9bb76c23628c4e0d0a1dfced0b1fa0Richard Smith    Expr::EvalStatus &EvalStatus;
51f0c1e4b679e15c26bffb5892e35985bf3c52f77aAnders Carlsson
52c54061a679d8db4169438b2f97f81e3f443c6a25Benjamin Kramer    typedef llvm::DenseMap<const OpaqueValueExpr*, APValue> MapTy;
53c54061a679d8db4169438b2f97f81e3f443c6a25Benjamin Kramer    MapTy OpaqueValues;
54c54061a679d8db4169438b2f97f81e3f443c6a25Benjamin Kramer    const APValue *getOpaqueValue(const OpaqueValueExpr *e) const {
55c54061a679d8db4169438b2f97f81e3f443c6a25Benjamin Kramer      MapTy::const_iterator i = OpaqueValues.find(e);
56c54061a679d8db4169438b2f97f81e3f443c6a25Benjamin Kramer      if (i == OpaqueValues.end()) return 0;
57c54061a679d8db4169438b2f97f81e3f443c6a25Benjamin Kramer      return &i->second;
58c54061a679d8db4169438b2f97f81e3f443c6a25Benjamin Kramer    }
5956ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall
601e12c59e8f9bb76c23628c4e0d0a1dfced0b1fa0Richard Smith    EvalInfo(const ASTContext &C, Expr::EvalStatus &S)
611e12c59e8f9bb76c23628c4e0d0a1dfced0b1fa0Richard Smith      : Ctx(C), EvalStatus(S) {}
62f10d9171ac24380ca94c71847a9270a05b791cefRichard Smith
63f10d9171ac24380ca94c71847a9270a05b791cefRichard Smith    const LangOptions &getLangOpts() { return Ctx.getLangOptions(); }
64c54061a679d8db4169438b2f97f81e3f443c6a25Benjamin Kramer  };
6587eae5ecf94e38baa20d9a327b8f73f8bdc72436Chris Lattner
66f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall  struct ComplexValue {
67f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall  private:
68f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall    bool IsInt;
69f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall
70f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall  public:
71f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall    APSInt IntReal, IntImag;
72f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall    APFloat FloatReal, FloatImag;
73f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall
74f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall    ComplexValue() : FloatReal(APFloat::Bogus), FloatImag(APFloat::Bogus) {}
75f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall
76f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall    void makeComplexFloat() { IsInt = false; }
77f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall    bool isComplexFloat() const { return !IsInt; }
78f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall    APFloat &getComplexFloatReal() { return FloatReal; }
79f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall    APFloat &getComplexFloatImag() { return FloatImag; }
80f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall
81f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall    void makeComplexInt() { IsInt = true; }
82f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall    bool isComplexInt() const { return IsInt; }
83f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall    APSInt &getComplexIntReal() { return IntReal; }
84f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall    APSInt &getComplexIntImag() { return IntImag; }
85f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall
8656ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall    void moveInto(APValue &v) const {
87f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall      if (isComplexFloat())
88f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall        v = APValue(FloatReal, FloatImag);
89f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall      else
90f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall        v = APValue(IntReal, IntImag);
91f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall    }
9256ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall    void setFrom(const APValue &v) {
9356ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall      assert(v.isComplexFloat() || v.isComplexInt());
9456ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall      if (v.isComplexFloat()) {
9556ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall        makeComplexFloat();
9656ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall        FloatReal = v.getComplexFloatReal();
9756ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall        FloatImag = v.getComplexFloatImag();
9856ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall      } else {
9956ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall        makeComplexInt();
10056ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall        IntReal = v.getComplexIntReal();
10156ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall        IntImag = v.getComplexIntImag();
10256ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall      }
10356ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall    }
104f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall  };
105efdb83e26f9a1fd2566afe54461216cd84814d42John McCall
106efdb83e26f9a1fd2566afe54461216cd84814d42John McCall  struct LValue {
1078cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    const Expr *Base;
108efdb83e26f9a1fd2566afe54461216cd84814d42John McCall    CharUnits Offset;
109efdb83e26f9a1fd2566afe54461216cd84814d42John McCall
1108cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    const Expr *getLValueBase() { return Base; }
111efdb83e26f9a1fd2566afe54461216cd84814d42John McCall    CharUnits getLValueOffset() { return Offset; }
112efdb83e26f9a1fd2566afe54461216cd84814d42John McCall
11356ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall    void moveInto(APValue &v) const {
114efdb83e26f9a1fd2566afe54461216cd84814d42John McCall      v = APValue(Base, Offset);
115efdb83e26f9a1fd2566afe54461216cd84814d42John McCall    }
11656ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall    void setFrom(const APValue &v) {
11756ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall      assert(v.isLValue());
11856ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall      Base = v.getLValueBase();
11956ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall      Offset = v.getLValueOffset();
12056ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall    }
121efdb83e26f9a1fd2566afe54461216cd84814d42John McCall  };
122f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall}
12387eae5ecf94e38baa20d9a327b8f73f8bdc72436Chris Lattner
1241e12c59e8f9bb76c23628c4e0d0a1dfced0b1fa0Richard Smithstatic bool Evaluate(APValue &Result, EvalInfo &Info, const Expr *E);
125efdb83e26f9a1fd2566afe54461216cd84814d42John McCallstatic bool EvaluateLValue(const Expr *E, LValue &Result, EvalInfo &Info);
126efdb83e26f9a1fd2566afe54461216cd84814d42John McCallstatic bool EvaluatePointer(const Expr *E, LValue &Result, EvalInfo &Info);
12787eae5ecf94e38baa20d9a327b8f73f8bdc72436Chris Lattnerstatic bool EvaluateInteger(const Expr *E, APSInt  &Result, EvalInfo &Info);
128d9becd1846e2c72bf6ad283faa1b048f33dd3afeChris Lattnerstatic bool EvaluateIntegerOrLValue(const Expr *E, APValue  &Result,
129d9becd1846e2c72bf6ad283faa1b048f33dd3afeChris Lattner                                    EvalInfo &Info);
130d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedmanstatic bool EvaluateFloat(const Expr *E, APFloat &Result, EvalInfo &Info);
131f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCallstatic bool EvaluateComplex(const Expr *E, ComplexValue &Res, EvalInfo &Info);
132f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner
133f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner//===----------------------------------------------------------------------===//
1344efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman// Misc utilities
1354efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman//===----------------------------------------------------------------------===//
1364efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman
137e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnarastatic bool IsGlobalLValue(const Expr* E) {
13842c8f87eb60958170c46767273bf93e6c96125bfJohn McCall  if (!E) return true;
13942c8f87eb60958170c46767273bf93e6c96125bfJohn McCall
14042c8f87eb60958170c46767273bf93e6c96125bfJohn McCall  if (const DeclRefExpr *DRE = dyn_cast<DeclRefExpr>(E)) {
14142c8f87eb60958170c46767273bf93e6c96125bfJohn McCall    if (isa<FunctionDecl>(DRE->getDecl()))
14242c8f87eb60958170c46767273bf93e6c96125bfJohn McCall      return true;
14342c8f87eb60958170c46767273bf93e6c96125bfJohn McCall    if (const VarDecl *VD = dyn_cast<VarDecl>(DRE->getDecl()))
14442c8f87eb60958170c46767273bf93e6c96125bfJohn McCall      return VD->hasGlobalStorage();
14542c8f87eb60958170c46767273bf93e6c96125bfJohn McCall    return false;
14642c8f87eb60958170c46767273bf93e6c96125bfJohn McCall  }
14742c8f87eb60958170c46767273bf93e6c96125bfJohn McCall
14842c8f87eb60958170c46767273bf93e6c96125bfJohn McCall  if (const CompoundLiteralExpr *CLE = dyn_cast<CompoundLiteralExpr>(E))
14942c8f87eb60958170c46767273bf93e6c96125bfJohn McCall    return CLE->isFileScope();
15042c8f87eb60958170c46767273bf93e6c96125bfJohn McCall
15142c8f87eb60958170c46767273bf93e6c96125bfJohn McCall  return true;
15242c8f87eb60958170c46767273bf93e6c96125bfJohn McCall}
15342c8f87eb60958170c46767273bf93e6c96125bfJohn McCall
154efdb83e26f9a1fd2566afe54461216cd84814d42John McCallstatic bool EvalPointerValueAsBool(LValue& Value, bool& Result) {
155efdb83e26f9a1fd2566afe54461216cd84814d42John McCall  const Expr* Base = Value.Base;
156a7d3c04fcfe9d4af2f7758f46aef26b1a8f8ac09Rafael Espindola
1573554283157190e67918fad4221a5e6faf9317362John McCall  // A null base expression indicates a null pointer.  These are always
1583554283157190e67918fad4221a5e6faf9317362John McCall  // evaluatable, and they are false unless the offset is zero.
1593554283157190e67918fad4221a5e6faf9317362John McCall  if (!Base) {
1603554283157190e67918fad4221a5e6faf9317362John McCall    Result = !Value.Offset.isZero();
1613554283157190e67918fad4221a5e6faf9317362John McCall    return true;
1623554283157190e67918fad4221a5e6faf9317362John McCall  }
1633554283157190e67918fad4221a5e6faf9317362John McCall
16442c8f87eb60958170c46767273bf93e6c96125bfJohn McCall  // Require the base expression to be a global l-value.
165e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara  if (!IsGlobalLValue(Base)) return false;
16642c8f87eb60958170c46767273bf93e6c96125bfJohn McCall
1673554283157190e67918fad4221a5e6faf9317362John McCall  // We have a non-null base expression.  These are generally known to
1683554283157190e67918fad4221a5e6faf9317362John McCall  // be true, but if it'a decl-ref to a weak symbol it can be null at
1693554283157190e67918fad4221a5e6faf9317362John McCall  // runtime.
1703554283157190e67918fad4221a5e6faf9317362John McCall  Result = true;
171a7d3c04fcfe9d4af2f7758f46aef26b1a8f8ac09Rafael Espindola
1723554283157190e67918fad4221a5e6faf9317362John McCall  const DeclRefExpr* DeclRef = dyn_cast<DeclRefExpr>(Base);
173a7d3c04fcfe9d4af2f7758f46aef26b1a8f8ac09Rafael Espindola  if (!DeclRef)
174a7d3c04fcfe9d4af2f7758f46aef26b1a8f8ac09Rafael Espindola    return true;
175a7d3c04fcfe9d4af2f7758f46aef26b1a8f8ac09Rafael Espindola
1763554283157190e67918fad4221a5e6faf9317362John McCall  // If it's a weak symbol, it isn't constant-evaluable.
177a7d3c04fcfe9d4af2f7758f46aef26b1a8f8ac09Rafael Espindola  const ValueDecl* Decl = DeclRef->getDecl();
178a7d3c04fcfe9d4af2f7758f46aef26b1a8f8ac09Rafael Espindola  if (Decl->hasAttr<WeakAttr>() ||
179a7d3c04fcfe9d4af2f7758f46aef26b1a8f8ac09Rafael Espindola      Decl->hasAttr<WeakRefAttr>() ||
1800a0d2b179085a52c10402feebeb6db8b4d96a140Douglas Gregor      Decl->isWeakImported())
181a7d3c04fcfe9d4af2f7758f46aef26b1a8f8ac09Rafael Espindola    return false;
182a7d3c04fcfe9d4af2f7758f46aef26b1a8f8ac09Rafael Espindola
1835bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman  return true;
1845bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman}
1855bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman
186cd7a445c6b46c5585580dfb652300c8483c0cb6bJohn McCallstatic bool HandleConversionToBool(const Expr* E, bool& Result,
187cd7a445c6b46c5585580dfb652300c8483c0cb6bJohn McCall                                   EvalInfo &Info) {
1882ade35e2cfd554e49d35a52047cea98a82787af9Douglas Gregor  if (E->getType()->isIntegralOrEnumerationType()) {
1894efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman    APSInt IntResult;
1904efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman    if (!EvaluateInteger(E, IntResult, Info))
1914efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman      return false;
1924efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman    Result = IntResult != 0;
1934efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman    return true;
1944efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman  } else if (E->getType()->isRealFloatingType()) {
1954efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman    APFloat FloatResult(0.0);
1964efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman    if (!EvaluateFloat(E, FloatResult, Info))
1974efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman      return false;
1984efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman    Result = !FloatResult.isZero();
1994efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman    return true;
200a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman  } else if (E->getType()->hasPointerRepresentation()) {
201efdb83e26f9a1fd2566afe54461216cd84814d42John McCall    LValue PointerResult;
2024efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman    if (!EvaluatePointer(E, PointerResult, Info))
2034efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman      return false;
2045bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman    return EvalPointerValueAsBool(PointerResult, Result);
205a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman  } else if (E->getType()->isAnyComplexType()) {
206f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall    ComplexValue ComplexResult;
207a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman    if (!EvaluateComplex(E, ComplexResult, Info))
208a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman      return false;
209a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman    if (ComplexResult.isComplexFloat()) {
210a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman      Result = !ComplexResult.getComplexFloatReal().isZero() ||
211a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman               !ComplexResult.getComplexFloatImag().isZero();
212a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman    } else {
213a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman      Result = ComplexResult.getComplexIntReal().getBoolValue() ||
214a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman               ComplexResult.getComplexIntImag().getBoolValue();
215a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman    }
216a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman    return true;
2174efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman  }
2184efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman
2194efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman  return false;
2204efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman}
2214efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman
2221eb4433ac451dc16f4133a88af2d002ac26c58efMike Stumpstatic APSInt HandleFloatToIntCast(QualType DestType, QualType SrcType,
2234ba2a17694148e16eaa8d3917f657ffcd3667be4Jay Foad                                   APFloat &Value, const ASTContext &Ctx) {
224a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar  unsigned DestWidth = Ctx.getIntWidth(DestType);
225a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar  // Determine whether we are converting to unsigned or signed.
226575a1c9dc8dc5b4977194993e289f9eda7295c39Douglas Gregor  bool DestSigned = DestType->isSignedIntegerOrEnumerationType();
2271eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
228a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar  // FIXME: Warning for overflow.
2293e1ef7849845a9e7bf79156bbb8a2c26d77a1d2eJeffrey Yasskin  APSInt Result(DestWidth, !DestSigned);
230a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar  bool ignored;
2313e1ef7849845a9e7bf79156bbb8a2c26d77a1d2eJeffrey Yasskin  (void)Value.convertToInteger(Result, llvm::APFloat::rmTowardZero, &ignored);
2323e1ef7849845a9e7bf79156bbb8a2c26d77a1d2eJeffrey Yasskin  return Result;
233a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar}
234a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar
2351eb4433ac451dc16f4133a88af2d002ac26c58efMike Stumpstatic APFloat HandleFloatToFloatCast(QualType DestType, QualType SrcType,
2364ba2a17694148e16eaa8d3917f657ffcd3667be4Jay Foad                                      APFloat &Value, const ASTContext &Ctx) {
237a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar  bool ignored;
238a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar  APFloat Result = Value;
2391eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump  Result.convert(Ctx.getFloatTypeSemantics(DestType),
240a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar                 APFloat::rmNearestTiesToEven, &ignored);
241a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar  return Result;
242a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar}
243a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar
2441eb4433ac451dc16f4133a88af2d002ac26c58efMike Stumpstatic APSInt HandleIntToIntCast(QualType DestType, QualType SrcType,
2454ba2a17694148e16eaa8d3917f657ffcd3667be4Jay Foad                                 APSInt &Value, const ASTContext &Ctx) {
246a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar  unsigned DestWidth = Ctx.getIntWidth(DestType);
247a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar  APSInt Result = Value;
248a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar  // Figure out if this is a truncate, extend or noop cast.
249a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar  // If the input is signed, do a sign extend, noop, or truncate.
2509f71a8f4c7a182a5236da9e747d57cc1d1bd24c2Jay Foad  Result = Result.extOrTrunc(DestWidth);
251575a1c9dc8dc5b4977194993e289f9eda7295c39Douglas Gregor  Result.setIsUnsigned(DestType->isUnsignedIntegerOrEnumerationType());
252a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar  return Result;
253a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar}
254a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar
2551eb4433ac451dc16f4133a88af2d002ac26c58efMike Stumpstatic APFloat HandleIntToFloatCast(QualType DestType, QualType SrcType,
2564ba2a17694148e16eaa8d3917f657ffcd3667be4Jay Foad                                    APSInt &Value, const ASTContext &Ctx) {
257a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar
258a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar  APFloat Result(Ctx.getFloatTypeSemantics(DestType), 1);
259a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar  Result.convertFromAPInt(Value, Value.isSigned(),
260a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar                          APFloat::rmNearestTiesToEven);
261a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar  return Result;
262a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar}
263a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar
26403f96110bc2c2c773e06a42982b17a03dd2e5379Richard Smith/// Try to evaluate the initializer for a variable declaration.
26503f96110bc2c2c773e06a42982b17a03dd2e5379Richard Smithstatic APValue *EvaluateVarDeclInit(EvalInfo &Info, const VarDecl *VD) {
26603f96110bc2c2c773e06a42982b17a03dd2e5379Richard Smith  if (isa<ParmVarDecl>(VD))
26703f96110bc2c2c773e06a42982b17a03dd2e5379Richard Smith    return 0;
26803f96110bc2c2c773e06a42982b17a03dd2e5379Richard Smith
26903f96110bc2c2c773e06a42982b17a03dd2e5379Richard Smith  const Expr *Init = VD->getAnyInitializer();
27003f96110bc2c2c773e06a42982b17a03dd2e5379Richard Smith  if (!Init)
27103f96110bc2c2c773e06a42982b17a03dd2e5379Richard Smith    return 0;
27203f96110bc2c2c773e06a42982b17a03dd2e5379Richard Smith
27303f96110bc2c2c773e06a42982b17a03dd2e5379Richard Smith  if (APValue *V = VD->getEvaluatedValue())
27403f96110bc2c2c773e06a42982b17a03dd2e5379Richard Smith    return V;
27503f96110bc2c2c773e06a42982b17a03dd2e5379Richard Smith
27603f96110bc2c2c773e06a42982b17a03dd2e5379Richard Smith  if (VD->isEvaluatingValue())
27703f96110bc2c2c773e06a42982b17a03dd2e5379Richard Smith    return 0;
27803f96110bc2c2c773e06a42982b17a03dd2e5379Richard Smith
27903f96110bc2c2c773e06a42982b17a03dd2e5379Richard Smith  VD->setEvaluatingValue();
28003f96110bc2c2c773e06a42982b17a03dd2e5379Richard Smith
28103f96110bc2c2c773e06a42982b17a03dd2e5379Richard Smith  // FIXME: If the initializer isn't a constant expression, propagate up any
28203f96110bc2c2c773e06a42982b17a03dd2e5379Richard Smith  // diagnostic explaining why not.
28303f96110bc2c2c773e06a42982b17a03dd2e5379Richard Smith  Expr::EvalResult EResult;
28403f96110bc2c2c773e06a42982b17a03dd2e5379Richard Smith  if (Init->Evaluate(EResult, Info.Ctx) && !EResult.HasSideEffects)
28503f96110bc2c2c773e06a42982b17a03dd2e5379Richard Smith    VD->setEvaluatedValue(EResult.Val);
28603f96110bc2c2c773e06a42982b17a03dd2e5379Richard Smith  else
28703f96110bc2c2c773e06a42982b17a03dd2e5379Richard Smith    VD->setEvaluatedValue(APValue());
28803f96110bc2c2c773e06a42982b17a03dd2e5379Richard Smith
28903f96110bc2c2c773e06a42982b17a03dd2e5379Richard Smith  return VD->getEvaluatedValue();
29003f96110bc2c2c773e06a42982b17a03dd2e5379Richard Smith}
29103f96110bc2c2c773e06a42982b17a03dd2e5379Richard Smith
29203f96110bc2c2c773e06a42982b17a03dd2e5379Richard Smithbool IsConstNonVolatile(QualType T) {
29303f96110bc2c2c773e06a42982b17a03dd2e5379Richard Smith  Qualifiers Quals = T.getQualifiers();
29403f96110bc2c2c773e06a42982b17a03dd2e5379Richard Smith  return Quals.hasConst() && !Quals.hasVolatile();
29503f96110bc2c2c773e06a42982b17a03dd2e5379Richard Smith}
29603f96110bc2c2c773e06a42982b17a03dd2e5379Richard Smith
297c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stumpnamespace {
298770b4a8834670e9427d3ce5a1a8472eb86f45fd2Benjamin Kramerclass HasSideEffect
2998cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  : public ConstStmtVisitor<HasSideEffect, bool> {
3001e12c59e8f9bb76c23628c4e0d0a1dfced0b1fa0Richard Smith  const ASTContext &Ctx;
301c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stumppublic:
302c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump
3031e12c59e8f9bb76c23628c4e0d0a1dfced0b1fa0Richard Smith  HasSideEffect(const ASTContext &C) : Ctx(C) {}
304c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump
305c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump  // Unhandled nodes conservatively default to having side effects.
3068cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitStmt(const Stmt *S) {
307c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump    return true;
308c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump  }
309c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump
3108cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitParenExpr(const ParenExpr *E) { return Visit(E->getSubExpr()); }
3118cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitGenericSelectionExpr(const GenericSelectionExpr *E) {
312f111d935722ed488144600cea5ed03a6b5069e8fPeter Collingbourne    return Visit(E->getResultExpr());
313f111d935722ed488144600cea5ed03a6b5069e8fPeter Collingbourne  }
3148cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitDeclRefExpr(const DeclRefExpr *E) {
3151e12c59e8f9bb76c23628c4e0d0a1dfced0b1fa0Richard Smith    if (Ctx.getCanonicalType(E->getType()).isVolatileQualified())
316c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump      return true;
317c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump    return false;
318c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump  }
319f85e193739c953358c865005855253af4f68a497John McCall  bool VisitObjCIvarRefExpr(const ObjCIvarRefExpr *E) {
3201e12c59e8f9bb76c23628c4e0d0a1dfced0b1fa0Richard Smith    if (Ctx.getCanonicalType(E->getType()).isVolatileQualified())
321f85e193739c953358c865005855253af4f68a497John McCall      return true;
322f85e193739c953358c865005855253af4f68a497John McCall    return false;
323f85e193739c953358c865005855253af4f68a497John McCall  }
324f85e193739c953358c865005855253af4f68a497John McCall  bool VisitBlockDeclRefExpr (const BlockDeclRefExpr *E) {
3251e12c59e8f9bb76c23628c4e0d0a1dfced0b1fa0Richard Smith    if (Ctx.getCanonicalType(E->getType()).isVolatileQualified())
326f85e193739c953358c865005855253af4f68a497John McCall      return true;
327f85e193739c953358c865005855253af4f68a497John McCall    return false;
328f85e193739c953358c865005855253af4f68a497John McCall  }
329f85e193739c953358c865005855253af4f68a497John McCall
330c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump  // We don't want to evaluate BlockExprs multiple times, as they generate
331c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump  // a ton of code.
3328cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitBlockExpr(const BlockExpr *E) { return true; }
3338cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitPredefinedExpr(const PredefinedExpr *E) { return false; }
3348cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitCompoundLiteralExpr(const CompoundLiteralExpr *E)
335c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump    { return Visit(E->getInitializer()); }
3368cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitMemberExpr(const MemberExpr *E) { return Visit(E->getBase()); }
3378cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitIntegerLiteral(const IntegerLiteral *E) { return false; }
3388cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitFloatingLiteral(const FloatingLiteral *E) { return false; }
3398cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitStringLiteral(const StringLiteral *E) { return false; }
3408cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitCharacterLiteral(const CharacterLiteral *E) { return false; }
3418cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitUnaryExprOrTypeTraitExpr(const UnaryExprOrTypeTraitExpr *E)
342f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne    { return false; }
3438cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitArraySubscriptExpr(const ArraySubscriptExpr *E)
344980ca220848d27ef55ef4c2d37423461a8ed0da3Mike Stump    { return Visit(E->getLHS()) || Visit(E->getRHS()); }
3458cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitChooseExpr(const ChooseExpr *E)
3461e12c59e8f9bb76c23628c4e0d0a1dfced0b1fa0Richard Smith    { return Visit(E->getChosenSubExpr(Ctx)); }
3478cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitCastExpr(const CastExpr *E) { return Visit(E->getSubExpr()); }
3488cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitBinAssign(const BinaryOperator *E) { return true; }
3498cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitCompoundAssignOperator(const BinaryOperator *E) { return true; }
3508cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitBinaryOperator(const BinaryOperator *E)
351980ca220848d27ef55ef4c2d37423461a8ed0da3Mike Stump  { return Visit(E->getLHS()) || Visit(E->getRHS()); }
3528cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitUnaryPreInc(const UnaryOperator *E) { return true; }
3538cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitUnaryPostInc(const UnaryOperator *E) { return true; }
3548cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitUnaryPreDec(const UnaryOperator *E) { return true; }
3558cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitUnaryPostDec(const UnaryOperator *E) { return true; }
3568cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitUnaryDeref(const UnaryOperator *E) {
3571e12c59e8f9bb76c23628c4e0d0a1dfced0b1fa0Richard Smith    if (Ctx.getCanonicalType(E->getType()).isVolatileQualified())
358c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump      return true;
359980ca220848d27ef55ef4c2d37423461a8ed0da3Mike Stump    return Visit(E->getSubExpr());
360c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump  }
3618cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitUnaryOperator(const UnaryOperator *E) { return Visit(E->getSubExpr()); }
362363ff23cfddb51abe4ee4212a6dd3c9b534fcc8bChris Lattner
363363ff23cfddb51abe4ee4212a6dd3c9b534fcc8bChris Lattner  // Has side effects if any element does.
3648cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitInitListExpr(const InitListExpr *E) {
365363ff23cfddb51abe4ee4212a6dd3c9b534fcc8bChris Lattner    for (unsigned i = 0, e = E->getNumInits(); i != e; ++i)
366363ff23cfddb51abe4ee4212a6dd3c9b534fcc8bChris Lattner      if (Visit(E->getInit(i))) return true;
3678cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    if (const Expr *filler = E->getArrayFiller())
3684423ac0282acb8ba801eb05b38712438dc0c1e3eArgyrios Kyrtzidis      return Visit(filler);
369363ff23cfddb51abe4ee4212a6dd3c9b534fcc8bChris Lattner    return false;
370363ff23cfddb51abe4ee4212a6dd3c9b534fcc8bChris Lattner  }
371ee8aff06f6a96214731de17b2cb6df407c6c1820Douglas Gregor
3728cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitSizeOfPackExpr(const SizeOfPackExpr *) { return false; }
373c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump};
374c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump
37556ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCallclass OpaqueValueEvaluation {
37656ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall  EvalInfo &info;
37756ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall  OpaqueValueExpr *opaqueValue;
37856ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall
37956ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCallpublic:
38056ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall  OpaqueValueEvaluation(EvalInfo &info, OpaqueValueExpr *opaqueValue,
38156ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall                        Expr *value)
38256ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall    : info(info), opaqueValue(opaqueValue) {
38356ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall
38456ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall    // If evaluation fails, fail immediately.
3851e12c59e8f9bb76c23628c4e0d0a1dfced0b1fa0Richard Smith    if (!Evaluate(info.OpaqueValues[opaqueValue], info, value)) {
38656ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall      this->opaqueValue = 0;
38756ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall      return;
38856ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall    }
38956ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall  }
39056ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall
39156ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall  bool hasError() const { return opaqueValue == 0; }
39256ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall
39356ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall  ~OpaqueValueEvaluation() {
3941e12c59e8f9bb76c23628c4e0d0a1dfced0b1fa0Richard Smith    // FIXME: This will not work for recursive constexpr functions using opaque
3951e12c59e8f9bb76c23628c4e0d0a1dfced0b1fa0Richard Smith    // values. Restore the former value.
39656ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall    if (opaqueValue) info.OpaqueValues.erase(opaqueValue);
39756ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall  }
39856ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall};
39956ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall
400c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump} // end anonymous namespace
401c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump
4024efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman//===----------------------------------------------------------------------===//
4038cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne// Generic Evaluation
4048cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne//===----------------------------------------------------------------------===//
4058cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbournenamespace {
4068cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne
4078cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbournetemplate <class Derived, typename RetTy=void>
4088cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourneclass ExprEvaluatorBase
4098cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  : public ConstStmtVisitor<Derived, RetTy> {
4108cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourneprivate:
4118cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  RetTy DerivedSuccess(const APValue &V, const Expr *E) {
4128cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    return static_cast<Derived*>(this)->Success(V, E);
4138cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  }
4148cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  RetTy DerivedError(const Expr *E) {
4158cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    return static_cast<Derived*>(this)->Error(E);
4168cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  }
417f10d9171ac24380ca94c71847a9270a05b791cefRichard Smith  RetTy DerivedValueInitialization(const Expr *E) {
418f10d9171ac24380ca94c71847a9270a05b791cefRichard Smith    return static_cast<Derived*>(this)->ValueInitialization(E);
419f10d9171ac24380ca94c71847a9270a05b791cefRichard Smith  }
4208cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne
4218cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourneprotected:
4228cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  EvalInfo &Info;
4238cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  typedef ConstStmtVisitor<Derived, RetTy> StmtVisitorTy;
4248cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  typedef ExprEvaluatorBase ExprEvaluatorBaseTy;
4258cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne
426f10d9171ac24380ca94c71847a9270a05b791cefRichard Smith  RetTy ValueInitialization(const Expr *E) { return DerivedError(E); }
427f10d9171ac24380ca94c71847a9270a05b791cefRichard Smith
4288cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbournepublic:
4298cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  ExprEvaluatorBase(EvalInfo &Info) : Info(Info) {}
4308cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne
4318cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  RetTy VisitStmt(const Stmt *) {
432b219cfc4d75f0a03630b7c4509ef791b7e97b2c8David Blaikie    llvm_unreachable("Expression evaluator should not be called on stmts");
4338cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  }
4348cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  RetTy VisitExpr(const Expr *E) {
4358cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    return DerivedError(E);
4368cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  }
4378cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne
4388cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  RetTy VisitParenExpr(const ParenExpr *E)
4398cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    { return StmtVisitorTy::Visit(E->getSubExpr()); }
4408cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  RetTy VisitUnaryExtension(const UnaryOperator *E)
4418cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    { return StmtVisitorTy::Visit(E->getSubExpr()); }
4428cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  RetTy VisitUnaryPlus(const UnaryOperator *E)
4438cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    { return StmtVisitorTy::Visit(E->getSubExpr()); }
4448cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  RetTy VisitChooseExpr(const ChooseExpr *E)
4458cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    { return StmtVisitorTy::Visit(E->getChosenSubExpr(Info.Ctx)); }
4468cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  RetTy VisitGenericSelectionExpr(const GenericSelectionExpr *E)
4478cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    { return StmtVisitorTy::Visit(E->getResultExpr()); }
44891a5755ad73c5dc1dfb167e448fdd74e75a6df56John McCall  RetTy VisitSubstNonTypeTemplateParmExpr(const SubstNonTypeTemplateParmExpr *E)
44991a5755ad73c5dc1dfb167e448fdd74e75a6df56John McCall    { return StmtVisitorTy::Visit(E->getReplacement()); }
4508cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne
4518cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  RetTy VisitBinaryConditionalOperator(const BinaryConditionalOperator *E) {
4528cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    OpaqueValueEvaluation opaque(Info, E->getOpaqueValue(), E->getCommon());
4538cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    if (opaque.hasError())
4548cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne      return DerivedError(E);
4558cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne
4568cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    bool cond;
4578cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    if (!HandleConversionToBool(E->getCond(), cond, Info))
4588cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne      return DerivedError(E);
4598cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne
4608cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    return StmtVisitorTy::Visit(cond ? E->getTrueExpr() : E->getFalseExpr());
4618cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  }
4628cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne
4638cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  RetTy VisitConditionalOperator(const ConditionalOperator *E) {
4648cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    bool BoolResult;
4658cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    if (!HandleConversionToBool(E->getCond(), BoolResult, Info))
4668cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne      return DerivedError(E);
4678cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne
4688cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    Expr* EvalExpr = BoolResult ? E->getTrueExpr() : E->getFalseExpr();
4698cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    return StmtVisitorTy::Visit(EvalExpr);
4708cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  }
4718cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne
4728cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  RetTy VisitOpaqueValueExpr(const OpaqueValueExpr *E) {
4738cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    const APValue *value = Info.getOpaqueValue(E);
4748cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    if (!value)
4758cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne      return (E->getSourceExpr() ? StmtVisitorTy::Visit(E->getSourceExpr())
4768cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne                                 : DerivedError(E));
4778cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    return DerivedSuccess(*value, E);
4788cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  }
479f10d9171ac24380ca94c71847a9270a05b791cefRichard Smith
480f10d9171ac24380ca94c71847a9270a05b791cefRichard Smith  RetTy VisitInitListExpr(const InitListExpr *E) {
481f10d9171ac24380ca94c71847a9270a05b791cefRichard Smith    if (Info.getLangOpts().CPlusPlus0x) {
482f10d9171ac24380ca94c71847a9270a05b791cefRichard Smith      if (E->getNumInits() == 0)
483f10d9171ac24380ca94c71847a9270a05b791cefRichard Smith        return DerivedValueInitialization(E);
484f10d9171ac24380ca94c71847a9270a05b791cefRichard Smith      if (E->getNumInits() == 1)
485f10d9171ac24380ca94c71847a9270a05b791cefRichard Smith        return StmtVisitorTy::Visit(E->getInit(0));
486f10d9171ac24380ca94c71847a9270a05b791cefRichard Smith    }
487f10d9171ac24380ca94c71847a9270a05b791cefRichard Smith    return DerivedError(E);
488f10d9171ac24380ca94c71847a9270a05b791cefRichard Smith  }
489f10d9171ac24380ca94c71847a9270a05b791cefRichard Smith  RetTy VisitImplicitValueInitExpr(const ImplicitValueInitExpr *E) {
490f10d9171ac24380ca94c71847a9270a05b791cefRichard Smith    return DerivedValueInitialization(E);
491f10d9171ac24380ca94c71847a9270a05b791cefRichard Smith  }
492f10d9171ac24380ca94c71847a9270a05b791cefRichard Smith  RetTy VisitCXXScalarValueInitExpr(const CXXScalarValueInitExpr *E) {
493f10d9171ac24380ca94c71847a9270a05b791cefRichard Smith    return DerivedValueInitialization(E);
494f10d9171ac24380ca94c71847a9270a05b791cefRichard Smith  }
495f10d9171ac24380ca94c71847a9270a05b791cefRichard Smith
4968327fad71da34492d82c532f42a58cb4baff81a3Richard Smith  /// Visit a value which is evaluated, but whose value is ignored.
4978327fad71da34492d82c532f42a58cb4baff81a3Richard Smith  void VisitIgnoredValue(const Expr *E) {
4988327fad71da34492d82c532f42a58cb4baff81a3Richard Smith    APValue Scratch;
4998327fad71da34492d82c532f42a58cb4baff81a3Richard Smith    if (!Evaluate(Scratch, Info, E))
5008327fad71da34492d82c532f42a58cb4baff81a3Richard Smith      Info.EvalStatus.HasSideEffects = true;
5018327fad71da34492d82c532f42a58cb4baff81a3Richard Smith  }
5028cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne};
5038cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne
5048cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne}
5058cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne
5068cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne//===----------------------------------------------------------------------===//
5074efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman// LValue Evaluation
5084efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman//===----------------------------------------------------------------------===//
5094efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedmannamespace {
510770b4a8834670e9427d3ce5a1a8472eb86f45fd2Benjamin Kramerclass LValueExprEvaluator
5118cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  : public ExprEvaluatorBase<LValueExprEvaluator, bool> {
512efdb83e26f9a1fd2566afe54461216cd84814d42John McCall  LValue &Result;
5130124839d7fb3d846795190ba2ccf3951f27784feChandler Carruth  const Decl *PrevDecl;
514efdb83e26f9a1fd2566afe54461216cd84814d42John McCall
5158cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool Success(const Expr *E) {
516efdb83e26f9a1fd2566afe54461216cd84814d42John McCall    Result.Base = E;
517efdb83e26f9a1fd2566afe54461216cd84814d42John McCall    Result.Offset = CharUnits::Zero();
518efdb83e26f9a1fd2566afe54461216cd84814d42John McCall    return true;
519efdb83e26f9a1fd2566afe54461216cd84814d42John McCall  }
5204efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedmanpublic:
5211eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
522efdb83e26f9a1fd2566afe54461216cd84814d42John McCall  LValueExprEvaluator(EvalInfo &info, LValue &Result) :
5230124839d7fb3d846795190ba2ccf3951f27784feChandler Carruth    ExprEvaluatorBaseTy(info), Result(Result), PrevDecl(0) {}
5244efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman
5258cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool Success(const APValue &V, const Expr *E) {
5268cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    Result.setFrom(V);
5278cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    return true;
5288cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  }
5298cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool Error(const Expr *E) {
530efdb83e26f9a1fd2566afe54461216cd84814d42John McCall    return false;
5314efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman  }
5328ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor
5338cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitDeclRefExpr(const DeclRefExpr *E);
5348cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitPredefinedExpr(const PredefinedExpr *E) { return Success(E); }
5358cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitCompoundLiteralExpr(const CompoundLiteralExpr *E);
5368cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitMemberExpr(const MemberExpr *E);
5378cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitStringLiteral(const StringLiteral *E) { return Success(E); }
5388cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitObjCEncodeExpr(const ObjCEncodeExpr *E) { return Success(E); }
5398cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitArraySubscriptExpr(const ArraySubscriptExpr *E);
5408cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitUnaryDeref(const UnaryOperator *E);
5418cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne
5428cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitCastExpr(const CastExpr *E) {
54326bc220377705292a0519a71d3ea3aef68fcfec6Anders Carlsson    switch (E->getCastKind()) {
54426bc220377705292a0519a71d3ea3aef68fcfec6Anders Carlsson    default:
545efdb83e26f9a1fd2566afe54461216cd84814d42John McCall      return false;
54626bc220377705292a0519a71d3ea3aef68fcfec6Anders Carlsson
5472de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case CK_NoOp:
548db924224b51b153f24fbe492102d4edebcbbb7f4Eli Friedman    case CK_LValueBitCast:
54926bc220377705292a0519a71d3ea3aef68fcfec6Anders Carlsson      return Visit(E->getSubExpr());
550db924224b51b153f24fbe492102d4edebcbbb7f4Eli Friedman
551db924224b51b153f24fbe492102d4edebcbbb7f4Eli Friedman    // FIXME: Support CK_DerivedToBase and friends.
55226bc220377705292a0519a71d3ea3aef68fcfec6Anders Carlsson    }
55326bc220377705292a0519a71d3ea3aef68fcfec6Anders Carlsson  }
554cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl
555ba98d6bb414861965a1f22628494ea046785ecd4Eli Friedman  // FIXME: Missing: __real__, __imag__
5568cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne
5574efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman};
5584efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman} // end anonymous namespace
5594efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman
560efdb83e26f9a1fd2566afe54461216cd84814d42John McCallstatic bool EvaluateLValue(const Expr* E, LValue& Result, EvalInfo &Info) {
5618cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  return LValueExprEvaluator(Info, Result).Visit(E);
5624efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman}
5634efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman
5648cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbournebool LValueExprEvaluator::VisitDeclRefExpr(const DeclRefExpr *E) {
56550c39ea4858265f3f5f42a0c624557ce2281936bEli Friedman  if (isa<FunctionDecl>(E->getDecl())) {
566efdb83e26f9a1fd2566afe54461216cd84814d42John McCall    return Success(E);
5678cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  } else if (const VarDecl* VD = dyn_cast<VarDecl>(E->getDecl())) {
56850c39ea4858265f3f5f42a0c624557ce2281936bEli Friedman    if (!VD->getType()->isReferenceType())
569efdb83e26f9a1fd2566afe54461216cd84814d42John McCall      return Success(E);
570761c94e3bffef0fcb8b4bbf202fd5ee73db134f3Chandler Carruth    // Reference parameters can refer to anything even if they have an
571761c94e3bffef0fcb8b4bbf202fd5ee73db134f3Chandler Carruth    // "initializer" in the form of a default argument.
5720124839d7fb3d846795190ba2ccf3951f27784feChandler Carruth    if (!isa<ParmVarDecl>(VD)) {
5738cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne      // FIXME: Check whether VD might be overridden!
5740124839d7fb3d846795190ba2ccf3951f27784feChandler Carruth
5750124839d7fb3d846795190ba2ccf3951f27784feChandler Carruth      // Check for recursive initializers of references.
5760124839d7fb3d846795190ba2ccf3951f27784feChandler Carruth      if (PrevDecl == VD)
5770124839d7fb3d846795190ba2ccf3951f27784feChandler Carruth        return Error(E);
5780124839d7fb3d846795190ba2ccf3951f27784feChandler Carruth      PrevDecl = VD;
5798cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne      if (const Expr *Init = VD->getAnyInitializer())
5808cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne        return Visit(Init);
5810124839d7fb3d846795190ba2ccf3951f27784feChandler Carruth    }
58250c39ea4858265f3f5f42a0c624557ce2281936bEli Friedman  }
58350c39ea4858265f3f5f42a0c624557ce2281936bEli Friedman
5848cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  return ExprEvaluatorBaseTy::VisitDeclRefExpr(E);
58535873c49adad211ff466e34342a52665742794f5Anders Carlsson}
58635873c49adad211ff466e34342a52665742794f5Anders Carlsson
5878cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbournebool
5888cad3046be06ea73ff8892d947697a21d7a440d3Peter CollingbourneLValueExprEvaluator::VisitCompoundLiteralExpr(const CompoundLiteralExpr *E) {
589efdb83e26f9a1fd2566afe54461216cd84814d42John McCall  return Success(E);
5904efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman}
5914efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman
5928cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbournebool LValueExprEvaluator::VisitMemberExpr(const MemberExpr *E) {
5934efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman  QualType Ty;
5944efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman  if (E->isArrow()) {
595efdb83e26f9a1fd2566afe54461216cd84814d42John McCall    if (!EvaluatePointer(E->getBase(), Result, Info))
596efdb83e26f9a1fd2566afe54461216cd84814d42John McCall      return false;
5976217b80b7a1379b74cced1c076338262c3c980b3Ted Kremenek    Ty = E->getBase()->getType()->getAs<PointerType>()->getPointeeType();
5984efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman  } else {
599efdb83e26f9a1fd2566afe54461216cd84814d42John McCall    if (!Visit(E->getBase()))
600efdb83e26f9a1fd2566afe54461216cd84814d42John McCall      return false;
6014efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman    Ty = E->getBase()->getType();
6024efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman  }
6034efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman
6048cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  const RecordDecl *RD = Ty->getAs<RecordType>()->getDecl();
6054efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman  const ASTRecordLayout &RL = Info.Ctx.getASTRecordLayout(RD);
60686f194083504938df72135b5b66bf0c5cafd9498Douglas Gregor
6078cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  const FieldDecl *FD = dyn_cast<FieldDecl>(E->getMemberDecl());
60886f194083504938df72135b5b66bf0c5cafd9498Douglas Gregor  if (!FD) // FIXME: deal with other kinds of member expressions
609efdb83e26f9a1fd2566afe54461216cd84814d42John McCall    return false;
6102be586108bb401019647791feca19ea03fd477ceEli Friedman
6112be586108bb401019647791feca19ea03fd477ceEli Friedman  if (FD->getType()->isReferenceType())
612efdb83e26f9a1fd2566afe54461216cd84814d42John McCall    return false;
6132be586108bb401019647791feca19ea03fd477ceEli Friedman
61482905749d5c8d8b4edec11de754a73349cb96603Eli Friedman  unsigned i = FD->getFieldIndex();
615fb1e3bc29b667f4275e1d5a43d64ec173f4f9a7dKen Dyck  Result.Offset += Info.Ctx.toCharUnitsFromBits(RL.getFieldOffset(i));
616efdb83e26f9a1fd2566afe54461216cd84814d42John McCall  return true;
6174efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman}
6184efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman
6198cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbournebool LValueExprEvaluator::VisitArraySubscriptExpr(const ArraySubscriptExpr *E) {
6203068d117951a8df54bae9db039b56201ab10962bAnders Carlsson  if (!EvaluatePointer(E->getBase(), Result, Info))
621efdb83e26f9a1fd2566afe54461216cd84814d42John McCall    return false;
6221eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
6233068d117951a8df54bae9db039b56201ab10962bAnders Carlsson  APSInt Index;
6243068d117951a8df54bae9db039b56201ab10962bAnders Carlsson  if (!EvaluateInteger(E->getIdx(), Index, Info))
625efdb83e26f9a1fd2566afe54461216cd84814d42John McCall    return false;
6263068d117951a8df54bae9db039b56201ab10962bAnders Carlsson
627199c3d6cd16aebbb9c7f0d42af9d922c9628bf70Ken Dyck  CharUnits ElementSize = Info.Ctx.getTypeSizeInChars(E->getType());
628efdb83e26f9a1fd2566afe54461216cd84814d42John McCall  Result.Offset += Index.getSExtValue() * ElementSize;
629efdb83e26f9a1fd2566afe54461216cd84814d42John McCall  return true;
6303068d117951a8df54bae9db039b56201ab10962bAnders Carlsson}
6314efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman
6328cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbournebool LValueExprEvaluator::VisitUnaryDeref(const UnaryOperator *E) {
633efdb83e26f9a1fd2566afe54461216cd84814d42John McCall  return EvaluatePointer(E->getSubExpr(), Result, Info);
634e8761c8fe2ee6b628104a0885f49fd3c21c08a4fEli Friedman}
635e8761c8fe2ee6b628104a0885f49fd3c21c08a4fEli Friedman
6364efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman//===----------------------------------------------------------------------===//
637f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner// Pointer Evaluation
638f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner//===----------------------------------------------------------------------===//
639f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner
640c754aa62643e66ab967ca32ae8b0b3fc419bba25Anders Carlssonnamespace {
641770b4a8834670e9427d3ce5a1a8472eb86f45fd2Benjamin Kramerclass PointerExprEvaluator
6428cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  : public ExprEvaluatorBase<PointerExprEvaluator, bool> {
643efdb83e26f9a1fd2566afe54461216cd84814d42John McCall  LValue &Result;
644efdb83e26f9a1fd2566afe54461216cd84814d42John McCall
6458cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool Success(const Expr *E) {
646efdb83e26f9a1fd2566afe54461216cd84814d42John McCall    Result.Base = E;
647efdb83e26f9a1fd2566afe54461216cd84814d42John McCall    Result.Offset = CharUnits::Zero();
648efdb83e26f9a1fd2566afe54461216cd84814d42John McCall    return true;
649efdb83e26f9a1fd2566afe54461216cd84814d42John McCall  }
6502bad1687fe6f00e10767a691a33b070b151902b6Anders Carlssonpublic:
6511eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
652efdb83e26f9a1fd2566afe54461216cd84814d42John McCall  PointerExprEvaluator(EvalInfo &info, LValue &Result)
6538cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    : ExprEvaluatorBaseTy(info), Result(Result) {}
654f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner
6558cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool Success(const APValue &V, const Expr *E) {
6568cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    Result.setFrom(V);
6578cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    return true;
6582bad1687fe6f00e10767a691a33b070b151902b6Anders Carlsson  }
6598cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool Error(const Stmt *S) {
6608cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    return false;
661f111d935722ed488144600cea5ed03a6b5069e8fPeter Collingbourne  }
662f10d9171ac24380ca94c71847a9270a05b791cefRichard Smith  bool ValueInitialization(const Expr *E) {
663f10d9171ac24380ca94c71847a9270a05b791cefRichard Smith    return Success((Expr*)0);
664f10d9171ac24380ca94c71847a9270a05b791cefRichard Smith  }
6652bad1687fe6f00e10767a691a33b070b151902b6Anders Carlsson
666efdb83e26f9a1fd2566afe54461216cd84814d42John McCall  bool VisitBinaryOperator(const BinaryOperator *E);
6678cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitCastExpr(const CastExpr* E);
668efdb83e26f9a1fd2566afe54461216cd84814d42John McCall  bool VisitUnaryAddrOf(const UnaryOperator *E);
6698cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitObjCStringLiteral(const ObjCStringLiteral *E)
670efdb83e26f9a1fd2566afe54461216cd84814d42John McCall      { return Success(E); }
6718cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitAddrLabelExpr(const AddrLabelExpr *E)
672efdb83e26f9a1fd2566afe54461216cd84814d42John McCall      { return Success(E); }
6738cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitCallExpr(const CallExpr *E);
6748cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitBlockExpr(const BlockExpr *E) {
675469a1eb996e1cb0be54f9b210f836afbddcbb2ccJohn McCall    if (!E->getBlockDecl()->hasCaptures())
676efdb83e26f9a1fd2566afe54461216cd84814d42John McCall      return Success(E);
677efdb83e26f9a1fd2566afe54461216cd84814d42John McCall    return false;
678b83d287bc7f47d36fb0751a481e2ef9308b37252Mike Stump  }
6798cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitCXXNullPtrLiteralExpr(const CXXNullPtrLiteralExpr *E)
680f10d9171ac24380ca94c71847a9270a05b791cefRichard Smith      { return ValueInitialization(E); }
68156ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall
682ba98d6bb414861965a1f22628494ea046785ecd4Eli Friedman  // FIXME: Missing: @protocol, @selector
6832bad1687fe6f00e10767a691a33b070b151902b6Anders Carlsson};
684f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner} // end anonymous namespace
6852bad1687fe6f00e10767a691a33b070b151902b6Anders Carlsson
686efdb83e26f9a1fd2566afe54461216cd84814d42John McCallstatic bool EvaluatePointer(const Expr* E, LValue& Result, EvalInfo &Info) {
6877db7acbbb84b82d0522266a50ebabc3a52a9e5d1John McCall  assert(E->getType()->hasPointerRepresentation());
6888cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  return PointerExprEvaluator(Info, Result).Visit(E);
689f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner}
690650c92fdcc27a950a8a848ecab6a74e6f5e80788Anders Carlsson
691efdb83e26f9a1fd2566afe54461216cd84814d42John McCallbool PointerExprEvaluator::VisitBinaryOperator(const BinaryOperator *E) {
6922de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall  if (E->getOpcode() != BO_Add &&
6932de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall      E->getOpcode() != BO_Sub)
694efdb83e26f9a1fd2566afe54461216cd84814d42John McCall    return false;
6951eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
696650c92fdcc27a950a8a848ecab6a74e6f5e80788Anders Carlsson  const Expr *PExp = E->getLHS();
697650c92fdcc27a950a8a848ecab6a74e6f5e80788Anders Carlsson  const Expr *IExp = E->getRHS();
698650c92fdcc27a950a8a848ecab6a74e6f5e80788Anders Carlsson  if (IExp->getType()->isPointerType())
699f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner    std::swap(PExp, IExp);
7001eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
701efdb83e26f9a1fd2566afe54461216cd84814d42John McCall  if (!EvaluatePointer(PExp, Result, Info))
702efdb83e26f9a1fd2566afe54461216cd84814d42John McCall    return false;
7031eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
704efdb83e26f9a1fd2566afe54461216cd84814d42John McCall  llvm::APSInt Offset;
705efdb83e26f9a1fd2566afe54461216cd84814d42John McCall  if (!EvaluateInteger(IExp, Offset, Info))
706efdb83e26f9a1fd2566afe54461216cd84814d42John McCall    return false;
707efdb83e26f9a1fd2566afe54461216cd84814d42John McCall  int64_t AdditionalOffset
708efdb83e26f9a1fd2566afe54461216cd84814d42John McCall    = Offset.isSigned() ? Offset.getSExtValue()
709efdb83e26f9a1fd2566afe54461216cd84814d42John McCall                        : static_cast<int64_t>(Offset.getZExtValue());
710650c92fdcc27a950a8a848ecab6a74e6f5e80788Anders Carlsson
711e0cdb4edd8f265d0fd22d178d03c597dd201cda2Daniel Dunbar  // Compute the new offset in the appropriate width.
712e0cdb4edd8f265d0fd22d178d03c597dd201cda2Daniel Dunbar
713e0cdb4edd8f265d0fd22d178d03c597dd201cda2Daniel Dunbar  QualType PointeeType =
714e0cdb4edd8f265d0fd22d178d03c597dd201cda2Daniel Dunbar    PExp->getType()->getAs<PointerType>()->getPointeeType();
715efdb83e26f9a1fd2566afe54461216cd84814d42John McCall  CharUnits SizeOfPointee;
7161eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
7174d4c50dd8b4db191c38782414665fb7608315a36Anders Carlsson  // Explicitly handle GNU void* and function pointer arithmetic extensions.
7184d4c50dd8b4db191c38782414665fb7608315a36Anders Carlsson  if (PointeeType->isVoidType() || PointeeType->isFunctionType())
719efdb83e26f9a1fd2566afe54461216cd84814d42John McCall    SizeOfPointee = CharUnits::One();
7204d4c50dd8b4db191c38782414665fb7608315a36Anders Carlsson  else
721efdb83e26f9a1fd2566afe54461216cd84814d42John McCall    SizeOfPointee = Info.Ctx.getTypeSizeInChars(PointeeType);
7224efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman
7232de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall  if (E->getOpcode() == BO_Add)
724efdb83e26f9a1fd2566afe54461216cd84814d42John McCall    Result.Offset += AdditionalOffset * SizeOfPointee;
725650c92fdcc27a950a8a848ecab6a74e6f5e80788Anders Carlsson  else
726efdb83e26f9a1fd2566afe54461216cd84814d42John McCall    Result.Offset -= AdditionalOffset * SizeOfPointee;
7274efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman
728efdb83e26f9a1fd2566afe54461216cd84814d42John McCall  return true;
729650c92fdcc27a950a8a848ecab6a74e6f5e80788Anders Carlsson}
7304efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman
731efdb83e26f9a1fd2566afe54461216cd84814d42John McCallbool PointerExprEvaluator::VisitUnaryAddrOf(const UnaryOperator *E) {
732efdb83e26f9a1fd2566afe54461216cd84814d42John McCall  return EvaluateLValue(E->getSubExpr(), Result, Info);
7334efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman}
7341eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
735650c92fdcc27a950a8a848ecab6a74e6f5e80788Anders Carlsson
7368cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbournebool PointerExprEvaluator::VisitCastExpr(const CastExpr* E) {
7378cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  const Expr* SubExpr = E->getSubExpr();
738650c92fdcc27a950a8a848ecab6a74e6f5e80788Anders Carlsson
73909a8a0e6ec1252cad52666e9dbb21002b9c80f38Eli Friedman  switch (E->getCastKind()) {
74009a8a0e6ec1252cad52666e9dbb21002b9c80f38Eli Friedman  default:
74109a8a0e6ec1252cad52666e9dbb21002b9c80f38Eli Friedman    break;
74209a8a0e6ec1252cad52666e9dbb21002b9c80f38Eli Friedman
7432de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall  case CK_NoOp:
7442de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall  case CK_BitCast:
7451d9b3b25f7ac0d0195bba6b507a684fe5e7943eeJohn McCall  case CK_CPointerToObjCPointerCast:
7461d9b3b25f7ac0d0195bba6b507a684fe5e7943eeJohn McCall  case CK_BlockPointerToObjCPointerCast:
7472de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall  case CK_AnyPointerToBlockPointerCast:
74809a8a0e6ec1252cad52666e9dbb21002b9c80f38Eli Friedman    return Visit(SubExpr);
74909a8a0e6ec1252cad52666e9dbb21002b9c80f38Eli Friedman
7505c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson  case CK_DerivedToBase:
7515c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson  case CK_UncheckedDerivedToBase: {
7525c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson    LValue BaseLV;
7535c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson    if (!EvaluatePointer(E->getSubExpr(), BaseLV, Info))
7545c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson      return false;
7555c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson
7565c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson    // Now figure out the necessary offset to add to the baseLV to get from
7575c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson    // the derived class to the base class.
7587c7f820d70c925b29290a8563b59615816a827fcKen Dyck    CharUnits Offset = CharUnits::Zero();
7595c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson
7605c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson    QualType Ty = E->getSubExpr()->getType();
7615c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson    const CXXRecordDecl *DerivedDecl =
7625c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson      Ty->getAs<PointerType>()->getPointeeType()->getAsCXXRecordDecl();
7635c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson
7645c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson    for (CastExpr::path_const_iterator PathI = E->path_begin(),
7655c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson         PathE = E->path_end(); PathI != PathE; ++PathI) {
7665c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson      const CXXBaseSpecifier *Base = *PathI;
7675c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson
7685c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson      // FIXME: If the base is virtual, we'd need to determine the type of the
7695c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson      // most derived class and we don't support that right now.
7705c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson      if (Base->isVirtual())
7715c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson        return false;
7725c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson
7735c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson      const CXXRecordDecl *BaseDecl = Base->getType()->getAsCXXRecordDecl();
7745c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson      const ASTRecordLayout &Layout = Info.Ctx.getASTRecordLayout(DerivedDecl);
7755c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson
7767c7f820d70c925b29290a8563b59615816a827fcKen Dyck      Offset += Layout.getBaseClassOffset(BaseDecl);
7775c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson      DerivedDecl = BaseDecl;
7785c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson    }
7795c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson
7805c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson    Result.Base = BaseLV.getLValueBase();
7817c7f820d70c925b29290a8563b59615816a827fcKen Dyck    Result.Offset = BaseLV.getLValueOffset() + Offset;
7825c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson    return true;
7835c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson  }
7845c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson
785404cd1669c3ba138a9ae0a619bd689cce5aae271John McCall  case CK_NullToPointer: {
786404cd1669c3ba138a9ae0a619bd689cce5aae271John McCall    Result.Base = 0;
787404cd1669c3ba138a9ae0a619bd689cce5aae271John McCall    Result.Offset = CharUnits::Zero();
788404cd1669c3ba138a9ae0a619bd689cce5aae271John McCall    return true;
789404cd1669c3ba138a9ae0a619bd689cce5aae271John McCall  }
790404cd1669c3ba138a9ae0a619bd689cce5aae271John McCall
7912de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall  case CK_IntegralToPointer: {
792efdb83e26f9a1fd2566afe54461216cd84814d42John McCall    APValue Value;
793efdb83e26f9a1fd2566afe54461216cd84814d42John McCall    if (!EvaluateIntegerOrLValue(SubExpr, Value, Info))
79409a8a0e6ec1252cad52666e9dbb21002b9c80f38Eli Friedman      break;
79569ab26a8623141f35e86817cfc6e0fbe7639a40fDaniel Dunbar
796efdb83e26f9a1fd2566afe54461216cd84814d42John McCall    if (Value.isInt()) {
7979f71a8f4c7a182a5236da9e747d57cc1d1bd24c2Jay Foad      Value.getInt() = Value.getInt().extOrTrunc((unsigned)Info.Ctx.getTypeSize(E->getType()));
798efdb83e26f9a1fd2566afe54461216cd84814d42John McCall      Result.Base = 0;
799efdb83e26f9a1fd2566afe54461216cd84814d42John McCall      Result.Offset = CharUnits::fromQuantity(Value.getInt().getZExtValue());
800efdb83e26f9a1fd2566afe54461216cd84814d42John McCall      return true;
801efdb83e26f9a1fd2566afe54461216cd84814d42John McCall    } else {
802efdb83e26f9a1fd2566afe54461216cd84814d42John McCall      // Cast is of an lvalue, no need to change value.
803efdb83e26f9a1fd2566afe54461216cd84814d42John McCall      Result.Base = Value.getLValueBase();
804efdb83e26f9a1fd2566afe54461216cd84814d42John McCall      Result.Offset = Value.getLValueOffset();
805efdb83e26f9a1fd2566afe54461216cd84814d42John McCall      return true;
806650c92fdcc27a950a8a848ecab6a74e6f5e80788Anders Carlsson    }
807650c92fdcc27a950a8a848ecab6a74e6f5e80788Anders Carlsson  }
8082de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall  case CK_ArrayToPointerDecay:
8092de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall  case CK_FunctionToPointerDecay:
810efdb83e26f9a1fd2566afe54461216cd84814d42John McCall    return EvaluateLValue(SubExpr, Result, Info);
8114efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman  }
8124efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman
813efdb83e26f9a1fd2566afe54461216cd84814d42John McCall  return false;
8141eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump}
815650c92fdcc27a950a8a848ecab6a74e6f5e80788Anders Carlsson
8168cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbournebool PointerExprEvaluator::VisitCallExpr(const CallExpr *E) {
8171eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump  if (E->isBuiltinCall(Info.Ctx) ==
8180d13f6fdbdd6f06e2449b8834dda53334abd399aDavid Chisnall        Builtin::BI__builtin___CFStringMakeConstantString ||
8190d13f6fdbdd6f06e2449b8834dda53334abd399aDavid Chisnall      E->isBuiltinCall(Info.Ctx) ==
8200d13f6fdbdd6f06e2449b8834dda53334abd399aDavid Chisnall        Builtin::BI__builtin___NSStringMakeConstantString)
821efdb83e26f9a1fd2566afe54461216cd84814d42John McCall    return Success(E);
82256ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall
8238cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  return ExprEvaluatorBaseTy::VisitCallExpr(E);
8244efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman}
825f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner
826f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner//===----------------------------------------------------------------------===//
82759b5da6d853b4368b984700315adf7b37de05764Nate Begeman// Vector Evaluation
82859b5da6d853b4368b984700315adf7b37de05764Nate Begeman//===----------------------------------------------------------------------===//
82959b5da6d853b4368b984700315adf7b37de05764Nate Begeman
83059b5da6d853b4368b984700315adf7b37de05764Nate Begemannamespace {
831770b4a8834670e9427d3ce5a1a8472eb86f45fd2Benjamin Kramer  class VectorExprEvaluator
83207fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith  : public ExprEvaluatorBase<VectorExprEvaluator, bool> {
83307fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith    APValue &Result;
83459b5da6d853b4368b984700315adf7b37de05764Nate Begeman  public:
8351eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
83607fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith    VectorExprEvaluator(EvalInfo &info, APValue &Result)
83707fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith      : ExprEvaluatorBaseTy(info), Result(Result) {}
8381eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
83907fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith    bool Success(const ArrayRef<APValue> &V, const Expr *E) {
84007fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith      assert(V.size() == E->getType()->castAs<VectorType>()->getNumElements());
84107fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith      // FIXME: remove this APValue copy.
84207fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith      Result = APValue(V.data(), V.size());
84307fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith      return true;
84407fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith    }
84507fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith    bool Success(const APValue &V, const Expr *E) {
84607fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith      Result = V;
84707fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith      return true;
84807fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith    }
84907fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith    bool Error(const Expr *E) { return false; }
85007fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith    bool ValueInitialization(const Expr *E);
8511eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
85207fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith    bool VisitUnaryReal(const UnaryOperator *E)
85391110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman      { return Visit(E->getSubExpr()); }
85407fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith    bool VisitCastExpr(const CastExpr* E);
85507fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith    bool VisitCompoundLiteralExpr(const CompoundLiteralExpr *E);
85607fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith    bool VisitInitListExpr(const InitListExpr *E);
85707fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith    bool VisitUnaryImag(const UnaryOperator *E);
85891110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman    // FIXME: Missing: unary -, unary ~, binary add/sub/mul/div,
8592217c87bdc5ab357046a5453bdb06f469c41024eEli Friedman    //                 binary comparisons, binary and/or/xor,
86091110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman    //                 shufflevector, ExtVectorElementExpr
86191110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman    //        (Note that these require implementing conversions
86291110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman    //         between vector types.)
86359b5da6d853b4368b984700315adf7b37de05764Nate Begeman  };
86459b5da6d853b4368b984700315adf7b37de05764Nate Begeman} // end anonymous namespace
86559b5da6d853b4368b984700315adf7b37de05764Nate Begeman
86659b5da6d853b4368b984700315adf7b37de05764Nate Begemanstatic bool EvaluateVector(const Expr* E, APValue& Result, EvalInfo &Info) {
86759b5da6d853b4368b984700315adf7b37de05764Nate Begeman  if (!E->getType()->isVectorType())
86859b5da6d853b4368b984700315adf7b37de05764Nate Begeman    return false;
86907fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith  return VectorExprEvaluator(Info, Result).Visit(E);
87059b5da6d853b4368b984700315adf7b37de05764Nate Begeman}
87159b5da6d853b4368b984700315adf7b37de05764Nate Begeman
87207fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smithbool VectorExprEvaluator::VisitCastExpr(const CastExpr* E) {
87307fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith  const VectorType *VTy = E->getType()->castAs<VectorType>();
874c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman  QualType EltTy = VTy->getElementType();
875c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman  unsigned NElts = VTy->getNumElements();
876c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman  unsigned EltWidth = Info.Ctx.getTypeSize(EltTy);
8771eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
87859b5da6d853b4368b984700315adf7b37de05764Nate Begeman  const Expr* SE = E->getSubExpr();
879e8c9e9218f215ec6089f12b076c7b9d310fd5194Nate Begeman  QualType SETy = SE->getType();
88059b5da6d853b4368b984700315adf7b37de05764Nate Begeman
88146a523285928aa07bf14803178dc04616ac85994Eli Friedman  switch (E->getCastKind()) {
88246a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_VectorSplat: {
88307fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith    APValue Val = APValue();
88446a523285928aa07bf14803178dc04616ac85994Eli Friedman    if (SETy->isIntegerType()) {
88546a523285928aa07bf14803178dc04616ac85994Eli Friedman      APSInt IntResult;
88646a523285928aa07bf14803178dc04616ac85994Eli Friedman      if (!EvaluateInteger(SE, IntResult, Info))
88707fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith         return Error(E);
88807fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith      Val = APValue(IntResult);
88946a523285928aa07bf14803178dc04616ac85994Eli Friedman    } else if (SETy->isRealFloatingType()) {
89046a523285928aa07bf14803178dc04616ac85994Eli Friedman       APFloat F(0.0);
89146a523285928aa07bf14803178dc04616ac85994Eli Friedman       if (!EvaluateFloat(SE, F, Info))
89207fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith         return Error(E);
89307fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith       Val = APValue(F);
89446a523285928aa07bf14803178dc04616ac85994Eli Friedman    } else {
89507fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith      return Error(E);
89646a523285928aa07bf14803178dc04616ac85994Eli Friedman    }
897c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman
898c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman    // Splat and create vector APValue.
89907fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith    SmallVector<APValue, 4> Elts(NElts, Val);
90007fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith    return Success(Elts, E);
901e8c9e9218f215ec6089f12b076c7b9d310fd5194Nate Begeman  }
90246a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_BitCast: {
90307fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith    // FIXME: this is wrong for any cast other than a no-op cast.
90446a523285928aa07bf14803178dc04616ac85994Eli Friedman    if (SETy->isVectorType())
9058cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne      return Visit(SE);
906c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman
90746a523285928aa07bf14803178dc04616ac85994Eli Friedman    if (!SETy->isIntegerType())
90807fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith      return Error(E);
9091eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
91046a523285928aa07bf14803178dc04616ac85994Eli Friedman    APSInt Init;
91146a523285928aa07bf14803178dc04616ac85994Eli Friedman    if (!EvaluateInteger(SE, Init, Info))
91207fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith      return Error(E);
913c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman
91446a523285928aa07bf14803178dc04616ac85994Eli Friedman    assert((EltTy->isIntegerType() || EltTy->isRealFloatingType()) &&
91546a523285928aa07bf14803178dc04616ac85994Eli Friedman           "Vectors must be composed of ints or floats");
91646a523285928aa07bf14803178dc04616ac85994Eli Friedman
9175f9e272e632e951b1efe824cd16acb4d96077930Chris Lattner    SmallVector<APValue, 4> Elts;
91846a523285928aa07bf14803178dc04616ac85994Eli Friedman    for (unsigned i = 0; i != NElts; ++i) {
91946a523285928aa07bf14803178dc04616ac85994Eli Friedman      APSInt Tmp = Init.extOrTrunc(EltWidth);
92046a523285928aa07bf14803178dc04616ac85994Eli Friedman
92146a523285928aa07bf14803178dc04616ac85994Eli Friedman      if (EltTy->isIntegerType())
92246a523285928aa07bf14803178dc04616ac85994Eli Friedman        Elts.push_back(APValue(Tmp));
92346a523285928aa07bf14803178dc04616ac85994Eli Friedman      else
92446a523285928aa07bf14803178dc04616ac85994Eli Friedman        Elts.push_back(APValue(APFloat(Tmp)));
92546a523285928aa07bf14803178dc04616ac85994Eli Friedman
92646a523285928aa07bf14803178dc04616ac85994Eli Friedman      Init >>= EltWidth;
92746a523285928aa07bf14803178dc04616ac85994Eli Friedman    }
92807fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith    return Success(Elts, E);
92946a523285928aa07bf14803178dc04616ac85994Eli Friedman  }
93046a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_LValueToRValue:
93146a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_NoOp:
9328cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    return Visit(SE);
93346a523285928aa07bf14803178dc04616ac85994Eli Friedman  default:
93407fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith    return Error(E);
935c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman  }
93659b5da6d853b4368b984700315adf7b37de05764Nate Begeman}
93759b5da6d853b4368b984700315adf7b37de05764Nate Begeman
93807fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smithbool
93959b5da6d853b4368b984700315adf7b37de05764Nate BegemanVectorExprEvaluator::VisitCompoundLiteralExpr(const CompoundLiteralExpr *E) {
94007fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith  return Visit(E->getInitializer());
94159b5da6d853b4368b984700315adf7b37de05764Nate Begeman}
94259b5da6d853b4368b984700315adf7b37de05764Nate Begeman
94307fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smithbool
94459b5da6d853b4368b984700315adf7b37de05764Nate BegemanVectorExprEvaluator::VisitInitListExpr(const InitListExpr *E) {
94507fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith  const VectorType *VT = E->getType()->castAs<VectorType>();
94659b5da6d853b4368b984700315adf7b37de05764Nate Begeman  unsigned NumInits = E->getNumInits();
94791110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman  unsigned NumElements = VT->getNumElements();
9481eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
94959b5da6d853b4368b984700315adf7b37de05764Nate Begeman  QualType EltTy = VT->getElementType();
9505f9e272e632e951b1efe824cd16acb4d96077930Chris Lattner  SmallVector<APValue, 4> Elements;
95159b5da6d853b4368b984700315adf7b37de05764Nate Begeman
952a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall  // If a vector is initialized with a single element, that value
953a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall  // becomes every element of the vector, not just the first.
954a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall  // This is the behavior described in the IBM AltiVec documentation.
955a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall  if (NumInits == 1) {
95607fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith
95707fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith    // Handle the case where the vector is initialized by another
958b92ae0e31126e5630d7022f2d6abe7eed2e17746Tanya Lattner    // vector (OpenCL 6.1.6).
959b92ae0e31126e5630d7022f2d6abe7eed2e17746Tanya Lattner    if (E->getInit(0)->getType()->isVectorType())
96007fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith      return Visit(E->getInit(0));
96107fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith
962a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall    APValue InitValue;
96359b5da6d853b4368b984700315adf7b37de05764Nate Begeman    if (EltTy->isIntegerType()) {
96459b5da6d853b4368b984700315adf7b37de05764Nate Begeman      llvm::APSInt sInt(32);
965a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall      if (!EvaluateInteger(E->getInit(0), sInt, Info))
96607fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith        return Error(E);
967a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall      InitValue = APValue(sInt);
96859b5da6d853b4368b984700315adf7b37de05764Nate Begeman    } else {
96959b5da6d853b4368b984700315adf7b37de05764Nate Begeman      llvm::APFloat f(0.0);
970a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall      if (!EvaluateFloat(E->getInit(0), f, Info))
97107fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith        return Error(E);
972a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall      InitValue = APValue(f);
973a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall    }
974a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall    for (unsigned i = 0; i < NumElements; i++) {
975a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall      Elements.push_back(InitValue);
976a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall    }
977a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall  } else {
978a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall    for (unsigned i = 0; i < NumElements; i++) {
979a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall      if (EltTy->isIntegerType()) {
980a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall        llvm::APSInt sInt(32);
981a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall        if (i < NumInits) {
982a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall          if (!EvaluateInteger(E->getInit(i), sInt, Info))
98307fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith            return Error(E);
984a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall        } else {
985a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall          sInt = Info.Ctx.MakeIntValue(0, EltTy);
986a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall        }
987a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall        Elements.push_back(APValue(sInt));
98891110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman      } else {
989a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall        llvm::APFloat f(0.0);
990a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall        if (i < NumInits) {
991a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall          if (!EvaluateFloat(E->getInit(i), f, Info))
99207fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith            return Error(E);
993a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall        } else {
994a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall          f = APFloat::getZero(Info.Ctx.getFloatTypeSemantics(EltTy));
995a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall        }
996a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall        Elements.push_back(APValue(f));
99791110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman      }
99859b5da6d853b4368b984700315adf7b37de05764Nate Begeman    }
99959b5da6d853b4368b984700315adf7b37de05764Nate Begeman  }
100007fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith  return Success(Elements, E);
100159b5da6d853b4368b984700315adf7b37de05764Nate Begeman}
100259b5da6d853b4368b984700315adf7b37de05764Nate Begeman
100307fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smithbool
100407fc657e3077531805b0e2dbf8f8964d48daa38bRichard SmithVectorExprEvaluator::ValueInitialization(const Expr *E) {
100507fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith  const VectorType *VT = E->getType()->getAs<VectorType>();
100691110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman  QualType EltTy = VT->getElementType();
100791110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman  APValue ZeroElement;
100891110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman  if (EltTy->isIntegerType())
100991110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman    ZeroElement = APValue(Info.Ctx.MakeIntValue(0, EltTy));
101091110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman  else
101191110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman    ZeroElement =
101291110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman        APValue(APFloat::getZero(Info.Ctx.getFloatTypeSemantics(EltTy)));
101391110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman
10145f9e272e632e951b1efe824cd16acb4d96077930Chris Lattner  SmallVector<APValue, 4> Elements(VT->getNumElements(), ZeroElement);
101507fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith  return Success(Elements, E);
101691110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman}
101791110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman
101807fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smithbool VectorExprEvaluator::VisitUnaryImag(const UnaryOperator *E) {
10198327fad71da34492d82c532f42a58cb4baff81a3Richard Smith  VisitIgnoredValue(E->getSubExpr());
102007fc657e3077531805b0e2dbf8f8964d48daa38bRichard Smith  return ValueInitialization(E);
102191110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman}
102291110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman
102359b5da6d853b4368b984700315adf7b37de05764Nate Begeman//===----------------------------------------------------------------------===//
1024f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner// Integer Evaluation
1025f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner//===----------------------------------------------------------------------===//
1026f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner
1027f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattnernamespace {
1028770b4a8834670e9427d3ce5a1a8472eb86f45fd2Benjamin Kramerclass IntExprEvaluator
10298cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  : public ExprEvaluatorBase<IntExprEvaluator, bool> {
103030c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar  APValue &Result;
1031f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattnerpublic:
103230c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar  IntExprEvaluator(EvalInfo &info, APValue &result)
10338cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    : ExprEvaluatorBaseTy(info), Result(result) {}
1034f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner
1035973c4fc0b0a88f9cea273b16f2082788a6e57d74Abramo Bagnara  bool Success(const llvm::APSInt &SI, const Expr *E) {
1036973c4fc0b0a88f9cea273b16f2082788a6e57d74Abramo Bagnara    assert(E->getType()->isIntegralOrEnumerationType() &&
10372ade35e2cfd554e49d35a52047cea98a82787af9Douglas Gregor           "Invalid evaluation result.");
1038973c4fc0b0a88f9cea273b16f2082788a6e57d74Abramo Bagnara    assert(SI.isSigned() == E->getType()->isSignedIntegerOrEnumerationType() &&
10393f7d995390009fede92b333a040da80e1ce90997Daniel Dunbar           "Invalid evaluation result.");
1040973c4fc0b0a88f9cea273b16f2082788a6e57d74Abramo Bagnara    assert(SI.getBitWidth() == Info.Ctx.getIntWidth(E->getType()) &&
10413f7d995390009fede92b333a040da80e1ce90997Daniel Dunbar           "Invalid evaluation result.");
104230c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar    Result = APValue(SI);
10433f7d995390009fede92b333a040da80e1ce90997Daniel Dunbar    return true;
10443f7d995390009fede92b333a040da80e1ce90997Daniel Dunbar  }
10453f7d995390009fede92b333a040da80e1ce90997Daniel Dunbar
1046131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar  bool Success(const llvm::APInt &I, const Expr *E) {
10472ade35e2cfd554e49d35a52047cea98a82787af9Douglas Gregor    assert(E->getType()->isIntegralOrEnumerationType() &&
10482ade35e2cfd554e49d35a52047cea98a82787af9Douglas Gregor           "Invalid evaluation result.");
104930c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar    assert(I.getBitWidth() == Info.Ctx.getIntWidth(E->getType()) &&
10503f7d995390009fede92b333a040da80e1ce90997Daniel Dunbar           "Invalid evaluation result.");
105130c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar    Result = APValue(APSInt(I));
1052575a1c9dc8dc5b4977194993e289f9eda7295c39Douglas Gregor    Result.getInt().setIsUnsigned(
1053575a1c9dc8dc5b4977194993e289f9eda7295c39Douglas Gregor                            E->getType()->isUnsignedIntegerOrEnumerationType());
1054131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar    return true;
1055131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar  }
1056131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar
1057131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar  bool Success(uint64_t Value, const Expr *E) {
10582ade35e2cfd554e49d35a52047cea98a82787af9Douglas Gregor    assert(E->getType()->isIntegralOrEnumerationType() &&
10592ade35e2cfd554e49d35a52047cea98a82787af9Douglas Gregor           "Invalid evaluation result.");
106030c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar    Result = APValue(Info.Ctx.MakeIntValue(Value, E->getType()));
1061131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar    return true;
1062131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar  }
1063131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar
10644f3bc8f7aa90b72832b03bee9201c98f4bb6b4d1Ken Dyck  bool Success(CharUnits Size, const Expr *E) {
10654f3bc8f7aa90b72832b03bee9201c98f4bb6b4d1Ken Dyck    return Success(Size.getQuantity(), E);
10664f3bc8f7aa90b72832b03bee9201c98f4bb6b4d1Ken Dyck  }
10674f3bc8f7aa90b72832b03bee9201c98f4bb6b4d1Ken Dyck
10684f3bc8f7aa90b72832b03bee9201c98f4bb6b4d1Ken Dyck
106982206e267ce6cc709797127616f64672d255b310Anders Carlsson  bool Error(SourceLocation L, diag::kind D, const Expr *E) {
107032fea9d18cc3658a1b01df5ca6f2ac302625c61dChris Lattner    // Take the first error.
10711e12c59e8f9bb76c23628c4e0d0a1dfced0b1fa0Richard Smith    if (Info.EvalStatus.Diag == 0) {
10721e12c59e8f9bb76c23628c4e0d0a1dfced0b1fa0Richard Smith      Info.EvalStatus.DiagLoc = L;
10731e12c59e8f9bb76c23628c4e0d0a1dfced0b1fa0Richard Smith      Info.EvalStatus.Diag = D;
10741e12c59e8f9bb76c23628c4e0d0a1dfced0b1fa0Richard Smith      Info.EvalStatus.DiagExpr = E;
107532fea9d18cc3658a1b01df5ca6f2ac302625c61dChris Lattner    }
107654176fdb044312b4b77c3da6682d3575b3728d30Chris Lattner    return false;
10777a76778e218da57a3b10c80066a0a938f28987b6Chris Lattner  }
10781eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
10798cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool Success(const APValue &V, const Expr *E) {
10808cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    return Success(V.getInt(), E);
108132fea9d18cc3658a1b01df5ca6f2ac302625c61dChris Lattner  }
10828cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool Error(const Expr *E) {
10830e8acbbba71ec6acd5dceb4fcbce63e463e1b755Anders Carlsson    return Error(E->getLocStart(), diag::note_invalid_subexpr_in_ice, E);
1084f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner  }
10851eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
1086f10d9171ac24380ca94c71847a9270a05b791cefRichard Smith  bool ValueInitialization(const Expr *E) { return Success(0, E); }
1087f10d9171ac24380ca94c71847a9270a05b791cefRichard Smith
10888cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  //===--------------------------------------------------------------------===//
10898cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  //                            Visitor Methods
10908cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  //===--------------------------------------------------------------------===//
1091f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner
10924c4867e140327fa3b56306fa03c64c8e6a7c95efChris Lattner  bool VisitIntegerLiteral(const IntegerLiteral *E) {
1093131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar    return Success(E->getValue(), E);
10944c4867e140327fa3b56306fa03c64c8e6a7c95efChris Lattner  }
10954c4867e140327fa3b56306fa03c64c8e6a7c95efChris Lattner  bool VisitCharacterLiteral(const CharacterLiteral *E) {
1096131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar    return Success(E->getValue(), E);
10974c4867e140327fa3b56306fa03c64c8e6a7c95efChris Lattner  }
1098043097507f99b1156bfd8bad41e7d5166ae4b9b6Eli Friedman
1099043097507f99b1156bfd8bad41e7d5166ae4b9b6Eli Friedman  bool CheckReferencedDecl(const Expr *E, const Decl *D);
1100043097507f99b1156bfd8bad41e7d5166ae4b9b6Eli Friedman  bool VisitDeclRefExpr(const DeclRefExpr *E) {
11018cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    if (CheckReferencedDecl(E, E->getDecl()))
11028cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne      return true;
11038cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne
11048cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    return ExprEvaluatorBaseTy::VisitDeclRefExpr(E);
1105043097507f99b1156bfd8bad41e7d5166ae4b9b6Eli Friedman  }
1106043097507f99b1156bfd8bad41e7d5166ae4b9b6Eli Friedman  bool VisitMemberExpr(const MemberExpr *E) {
1107043097507f99b1156bfd8bad41e7d5166ae4b9b6Eli Friedman    if (CheckReferencedDecl(E, E->getMemberDecl())) {
1108043097507f99b1156bfd8bad41e7d5166ae4b9b6Eli Friedman      // Conservatively assume a MemberExpr will have side-effects
11091e12c59e8f9bb76c23628c4e0d0a1dfced0b1fa0Richard Smith      Info.EvalStatus.HasSideEffects = true;
1110043097507f99b1156bfd8bad41e7d5166ae4b9b6Eli Friedman      return true;
1111043097507f99b1156bfd8bad41e7d5166ae4b9b6Eli Friedman    }
11128cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne
11138cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    return ExprEvaluatorBaseTy::VisitMemberExpr(E);
1114043097507f99b1156bfd8bad41e7d5166ae4b9b6Eli Friedman  }
1115043097507f99b1156bfd8bad41e7d5166ae4b9b6Eli Friedman
11168cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitCallExpr(const CallExpr *E);
1117b542afe02d317411d53b3541946f9f2a8f509a11Chris Lattner  bool VisitBinaryOperator(const BinaryOperator *E);
11188ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor  bool VisitOffsetOfExpr(const OffsetOfExpr *E);
1119b542afe02d317411d53b3541946f9f2a8f509a11Chris Lattner  bool VisitUnaryOperator(const UnaryOperator *E);
1120f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner
11218cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitCastExpr(const CastExpr* E);
1122f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne  bool VisitUnaryExprOrTypeTraitExpr(const UnaryExprOrTypeTraitExpr *E);
11230518999d3adcc289997bd974dce90cc97f5c1c44Sebastian Redl
11243068d117951a8df54bae9db039b56201ab10962bAnders Carlsson  bool VisitCXXBoolLiteralExpr(const CXXBoolLiteralExpr *E) {
1125131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar    return Success(E->getValue(), E);
11263068d117951a8df54bae9db039b56201ab10962bAnders Carlsson  }
11271eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
1128f10d9171ac24380ca94c71847a9270a05b791cefRichard Smith  // Note, GNU defines __null as an integer, not a pointer.
11293f70456b8adb0405ef2a47d51f9fc2d5937ae8aeAnders Carlsson  bool VisitGNUNullExpr(const GNUNullExpr *E) {
1130f10d9171ac24380ca94c71847a9270a05b791cefRichard Smith    return ValueInitialization(E);
1131664a104ba0b8f47b8908ec6af694d9646adba1fcEli Friedman  }
1132664a104ba0b8f47b8908ec6af694d9646adba1fcEli Friedman
113364b45f7e0d3167f040841ac2920aead7f080730dSebastian Redl  bool VisitUnaryTypeTraitExpr(const UnaryTypeTraitExpr *E) {
11340dfd848fa4c9664852ba8c929a8bd3fce93ddca2Sebastian Redl    return Success(E->getValue(), E);
113564b45f7e0d3167f040841ac2920aead7f080730dSebastian Redl  }
113664b45f7e0d3167f040841ac2920aead7f080730dSebastian Redl
11376ad6f2848d7652ab2991286eb48be440d3493b28Francois Pichet  bool VisitBinaryTypeTraitExpr(const BinaryTypeTraitExpr *E) {
11386ad6f2848d7652ab2991286eb48be440d3493b28Francois Pichet    return Success(E->getValue(), E);
11396ad6f2848d7652ab2991286eb48be440d3493b28Francois Pichet  }
11406ad6f2848d7652ab2991286eb48be440d3493b28Francois Pichet
114121ff2e516b0e0bc8c1dbf965cb3d44bac3c64330John Wiegley  bool VisitArrayTypeTraitExpr(const ArrayTypeTraitExpr *E) {
114221ff2e516b0e0bc8c1dbf965cb3d44bac3c64330John Wiegley    return Success(E->getValue(), E);
114321ff2e516b0e0bc8c1dbf965cb3d44bac3c64330John Wiegley  }
114421ff2e516b0e0bc8c1dbf965cb3d44bac3c64330John Wiegley
1145552622067dc45013d240f73952fece703f5e63bdJohn Wiegley  bool VisitExpressionTraitExpr(const ExpressionTraitExpr *E) {
1146552622067dc45013d240f73952fece703f5e63bdJohn Wiegley    return Success(E->getValue(), E);
1147552622067dc45013d240f73952fece703f5e63bdJohn Wiegley  }
1148552622067dc45013d240f73952fece703f5e63bdJohn Wiegley
1149722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman  bool VisitUnaryReal(const UnaryOperator *E);
1150664a104ba0b8f47b8908ec6af694d9646adba1fcEli Friedman  bool VisitUnaryImag(const UnaryOperator *E);
1151664a104ba0b8f47b8908ec6af694d9646adba1fcEli Friedman
1152295995c9c3196416372c9cd35d9cedb6da37bd3dSebastian Redl  bool VisitCXXNoexceptExpr(const CXXNoexceptExpr *E);
1153ee8aff06f6a96214731de17b2cb6df407c6c1820Douglas Gregor  bool VisitSizeOfPackExpr(const SizeOfPackExpr *E);
1154cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl
1155fcee0019b76f9f368f2b3d6d4048a98232593f29Chris Lattnerprivate:
11568b752f10c394b140f9ef89e049cbad1a7676fc25Ken Dyck  CharUnits GetAlignOfExpr(const Expr *E);
11578b752f10c394b140f9ef89e049cbad1a7676fc25Ken Dyck  CharUnits GetAlignOfType(QualType T);
115842c8f87eb60958170c46767273bf93e6c96125bfJohn McCall  static QualType GetObjectType(const Expr *E);
11598cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool TryEvaluateBuiltinObjectSize(const CallExpr *E);
1160664a104ba0b8f47b8908ec6af694d9646adba1fcEli Friedman  // FIXME: Missing: array subscript of vector, member of vector
1161f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner};
1162f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner} // end anonymous namespace
1163f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner
116469ab26a8623141f35e86817cfc6e0fbe7639a40fDaniel Dunbarstatic bool EvaluateIntegerOrLValue(const Expr* E, APValue &Result, EvalInfo &Info) {
11652ade35e2cfd554e49d35a52047cea98a82787af9Douglas Gregor  assert(E->getType()->isIntegralOrEnumerationType());
11668cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  return IntExprEvaluator(Info, Result).Visit(E);
116769ab26a8623141f35e86817cfc6e0fbe7639a40fDaniel Dunbar}
116869ab26a8623141f35e86817cfc6e0fbe7639a40fDaniel Dunbar
116969ab26a8623141f35e86817cfc6e0fbe7639a40fDaniel Dunbarstatic bool EvaluateInteger(const Expr* E, APSInt &Result, EvalInfo &Info) {
11702ade35e2cfd554e49d35a52047cea98a82787af9Douglas Gregor  assert(E->getType()->isIntegralOrEnumerationType());
11717db7acbbb84b82d0522266a50ebabc3a52a9e5d1John McCall
117230c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar  APValue Val;
117369ab26a8623141f35e86817cfc6e0fbe7639a40fDaniel Dunbar  if (!EvaluateIntegerOrLValue(E, Val, Info) || !Val.isInt())
117430c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar    return false;
117530c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar  Result = Val.getInt();
117630c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar  return true;
1177f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner}
1178f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner
1179043097507f99b1156bfd8bad41e7d5166ae4b9b6Eli Friedmanbool IntExprEvaluator::CheckReferencedDecl(const Expr* E, const Decl* D) {
11804c4867e140327fa3b56306fa03c64c8e6a7c95efChris Lattner  // Enums are integer constant exprs.
1181bfbdcd861a4364bfc21a9e5047bdbd56812d6693Abramo Bagnara  if (const EnumConstantDecl *ECD = dyn_cast<EnumConstantDecl>(D)) {
1182973c4fc0b0a88f9cea273b16f2082788a6e57d74Abramo Bagnara    // Check for signedness/width mismatches between E type and ECD value.
1183973c4fc0b0a88f9cea273b16f2082788a6e57d74Abramo Bagnara    bool SameSign = (ECD->getInitVal().isSigned()
1184973c4fc0b0a88f9cea273b16f2082788a6e57d74Abramo Bagnara                     == E->getType()->isSignedIntegerOrEnumerationType());
1185973c4fc0b0a88f9cea273b16f2082788a6e57d74Abramo Bagnara    bool SameWidth = (ECD->getInitVal().getBitWidth()
1186973c4fc0b0a88f9cea273b16f2082788a6e57d74Abramo Bagnara                      == Info.Ctx.getIntWidth(E->getType()));
1187973c4fc0b0a88f9cea273b16f2082788a6e57d74Abramo Bagnara    if (SameSign && SameWidth)
1188973c4fc0b0a88f9cea273b16f2082788a6e57d74Abramo Bagnara      return Success(ECD->getInitVal(), E);
1189973c4fc0b0a88f9cea273b16f2082788a6e57d74Abramo Bagnara    else {
1190973c4fc0b0a88f9cea273b16f2082788a6e57d74Abramo Bagnara      // Get rid of mismatch (otherwise Success assertions will fail)
1191973c4fc0b0a88f9cea273b16f2082788a6e57d74Abramo Bagnara      // by computing a new value matching the type of E.
1192973c4fc0b0a88f9cea273b16f2082788a6e57d74Abramo Bagnara      llvm::APSInt Val = ECD->getInitVal();
1193973c4fc0b0a88f9cea273b16f2082788a6e57d74Abramo Bagnara      if (!SameSign)
1194973c4fc0b0a88f9cea273b16f2082788a6e57d74Abramo Bagnara        Val.setIsSigned(!ECD->getInitVal().isSigned());
1195973c4fc0b0a88f9cea273b16f2082788a6e57d74Abramo Bagnara      if (!SameWidth)
1196973c4fc0b0a88f9cea273b16f2082788a6e57d74Abramo Bagnara        Val = Val.extOrTrunc(Info.Ctx.getIntWidth(E->getType()));
1197973c4fc0b0a88f9cea273b16f2082788a6e57d74Abramo Bagnara      return Success(Val, E);
1198973c4fc0b0a88f9cea273b16f2082788a6e57d74Abramo Bagnara    }
1199bfbdcd861a4364bfc21a9e5047bdbd56812d6693Abramo Bagnara  }
1200b2bc62bd35129f09d0746ef6a5ef4dc392b6d6e1Sebastian Redl
1201b2bc62bd35129f09d0746ef6a5ef4dc392b6d6e1Sebastian Redl  // In C++, const, non-volatile integers initialized with ICEs are ICEs.
1202e1646da3bb0fe97b372e5fe8cefc537b22048fc4Eli Friedman  // In C, they can also be folded, although they are not ICEs.
120303f96110bc2c2c773e06a42982b17a03dd2e5379Richard Smith  if (IsConstNonVolatile(E->getType())) {
1204043097507f99b1156bfd8bad41e7d5166ae4b9b6Eli Friedman    if (const VarDecl *VD = dyn_cast<VarDecl>(D)) {
120503f96110bc2c2c773e06a42982b17a03dd2e5379Richard Smith      APValue *V = EvaluateVarDeclInit(Info, VD);
120603f96110bc2c2c773e06a42982b17a03dd2e5379Richard Smith      if (V && V->isInt())
120703f96110bc2c2c773e06a42982b17a03dd2e5379Richard Smith        return Success(V->getInt(), E);
1208b2bc62bd35129f09d0746ef6a5ef4dc392b6d6e1Sebastian Redl    }
1209b2bc62bd35129f09d0746ef6a5ef4dc392b6d6e1Sebastian Redl  }
1210b2bc62bd35129f09d0746ef6a5ef4dc392b6d6e1Sebastian Redl
12114c4867e140327fa3b56306fa03c64c8e6a7c95efChris Lattner  // Otherwise, random variable references are not constants.
12128cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  return false;
12134c4867e140327fa3b56306fa03c64c8e6a7c95efChris Lattner}
12144c4867e140327fa3b56306fa03c64c8e6a7c95efChris Lattner
1215a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner/// EvaluateBuiltinClassifyType - Evaluate __builtin_classify_type the same way
1216a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner/// as GCC.
1217a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattnerstatic int EvaluateBuiltinClassifyType(const CallExpr *E) {
1218a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner  // The following enum mimics the values returned by GCC.
12197c80bd64032e610c0dbd74fc0ef6ea334447f2fdSebastian Redl  // FIXME: Does GCC differ between lvalue and rvalue references here?
1220a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner  enum gcc_type_class {
1221a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner    no_type_class = -1,
1222a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner    void_type_class, integer_type_class, char_type_class,
1223a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner    enumeral_type_class, boolean_type_class,
1224a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner    pointer_type_class, reference_type_class, offset_type_class,
1225a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner    real_type_class, complex_type_class,
1226a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner    function_type_class, method_type_class,
1227a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner    record_type_class, union_type_class,
1228a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner    array_type_class, string_type_class,
1229a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner    lang_type_class
1230a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner  };
12311eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
12321eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump  // If no argument was supplied, default to "no_type_class". This isn't
1233a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner  // ideal, however it is what gcc does.
1234a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner  if (E->getNumArgs() == 0)
1235a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner    return no_type_class;
12361eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
1237a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner  QualType ArgTy = E->getArg(0)->getType();
1238a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner  if (ArgTy->isVoidType())
1239a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner    return void_type_class;
1240a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner  else if (ArgTy->isEnumeralType())
1241a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner    return enumeral_type_class;
1242a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner  else if (ArgTy->isBooleanType())
1243a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner    return boolean_type_class;
1244a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner  else if (ArgTy->isCharType())
1245a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner    return string_type_class; // gcc doesn't appear to use char_type_class
1246a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner  else if (ArgTy->isIntegerType())
1247a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner    return integer_type_class;
1248a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner  else if (ArgTy->isPointerType())
1249a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner    return pointer_type_class;
1250a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner  else if (ArgTy->isReferenceType())
1251a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner    return reference_type_class;
1252a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner  else if (ArgTy->isRealType())
1253a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner    return real_type_class;
1254a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner  else if (ArgTy->isComplexType())
1255a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner    return complex_type_class;
1256a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner  else if (ArgTy->isFunctionType())
1257a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner    return function_type_class;
1258fb87b89fc9eb103e19fb8e4b925c23f0bd091b99Douglas Gregor  else if (ArgTy->isStructureOrClassType())
1259a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner    return record_type_class;
1260a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner  else if (ArgTy->isUnionType())
1261a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner    return union_type_class;
1262a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner  else if (ArgTy->isArrayType())
1263a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner    return array_type_class;
1264a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner  else if (ArgTy->isUnionType())
1265a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner    return union_type_class;
1266a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner  else  // FIXME: offset_type_class, method_type_class, & lang_type_class?
1267b219cfc4d75f0a03630b7c4509ef791b7e97b2c8David Blaikie    llvm_unreachable("CallExpr::isBuiltinClassifyType(): unimplemented type");
1268a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner  return -1;
1269a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner}
1270a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner
127142c8f87eb60958170c46767273bf93e6c96125bfJohn McCall/// Retrieves the "underlying object type" of the given expression,
127242c8f87eb60958170c46767273bf93e6c96125bfJohn McCall/// as used by __builtin_object_size.
127342c8f87eb60958170c46767273bf93e6c96125bfJohn McCallQualType IntExprEvaluator::GetObjectType(const Expr *E) {
127442c8f87eb60958170c46767273bf93e6c96125bfJohn McCall  if (const DeclRefExpr *DRE = dyn_cast<DeclRefExpr>(E)) {
127542c8f87eb60958170c46767273bf93e6c96125bfJohn McCall    if (const VarDecl *VD = dyn_cast<VarDecl>(DRE->getDecl()))
127642c8f87eb60958170c46767273bf93e6c96125bfJohn McCall      return VD->getType();
127742c8f87eb60958170c46767273bf93e6c96125bfJohn McCall  } else if (isa<CompoundLiteralExpr>(E)) {
127842c8f87eb60958170c46767273bf93e6c96125bfJohn McCall    return E->getType();
127942c8f87eb60958170c46767273bf93e6c96125bfJohn McCall  }
128042c8f87eb60958170c46767273bf93e6c96125bfJohn McCall
128142c8f87eb60958170c46767273bf93e6c96125bfJohn McCall  return QualType();
128242c8f87eb60958170c46767273bf93e6c96125bfJohn McCall}
128342c8f87eb60958170c46767273bf93e6c96125bfJohn McCall
12848cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbournebool IntExprEvaluator::TryEvaluateBuiltinObjectSize(const CallExpr *E) {
128542c8f87eb60958170c46767273bf93e6c96125bfJohn McCall  // TODO: Perhaps we should let LLVM lower this?
128642c8f87eb60958170c46767273bf93e6c96125bfJohn McCall  LValue Base;
128742c8f87eb60958170c46767273bf93e6c96125bfJohn McCall  if (!EvaluatePointer(E->getArg(0), Base, Info))
128842c8f87eb60958170c46767273bf93e6c96125bfJohn McCall    return false;
128942c8f87eb60958170c46767273bf93e6c96125bfJohn McCall
129042c8f87eb60958170c46767273bf93e6c96125bfJohn McCall  // If we can prove the base is null, lower to zero now.
129142c8f87eb60958170c46767273bf93e6c96125bfJohn McCall  const Expr *LVBase = Base.getLValueBase();
129242c8f87eb60958170c46767273bf93e6c96125bfJohn McCall  if (!LVBase) return Success(0, E);
129342c8f87eb60958170c46767273bf93e6c96125bfJohn McCall
129442c8f87eb60958170c46767273bf93e6c96125bfJohn McCall  QualType T = GetObjectType(LVBase);
129542c8f87eb60958170c46767273bf93e6c96125bfJohn McCall  if (T.isNull() ||
129642c8f87eb60958170c46767273bf93e6c96125bfJohn McCall      T->isIncompleteType() ||
12971357869bc5983cdfbc986db1f3d18265bb34cb0eEli Friedman      T->isFunctionType() ||
129842c8f87eb60958170c46767273bf93e6c96125bfJohn McCall      T->isVariablyModifiedType() ||
129942c8f87eb60958170c46767273bf93e6c96125bfJohn McCall      T->isDependentType())
130042c8f87eb60958170c46767273bf93e6c96125bfJohn McCall    return false;
130142c8f87eb60958170c46767273bf93e6c96125bfJohn McCall
130242c8f87eb60958170c46767273bf93e6c96125bfJohn McCall  CharUnits Size = Info.Ctx.getTypeSizeInChars(T);
130342c8f87eb60958170c46767273bf93e6c96125bfJohn McCall  CharUnits Offset = Base.getLValueOffset();
130442c8f87eb60958170c46767273bf93e6c96125bfJohn McCall
130542c8f87eb60958170c46767273bf93e6c96125bfJohn McCall  if (!Offset.isNegative() && Offset <= Size)
130642c8f87eb60958170c46767273bf93e6c96125bfJohn McCall    Size -= Offset;
130742c8f87eb60958170c46767273bf93e6c96125bfJohn McCall  else
130842c8f87eb60958170c46767273bf93e6c96125bfJohn McCall    Size = CharUnits::Zero();
13094f3bc8f7aa90b72832b03bee9201c98f4bb6b4d1Ken Dyck  return Success(Size, E);
131042c8f87eb60958170c46767273bf93e6c96125bfJohn McCall}
131142c8f87eb60958170c46767273bf93e6c96125bfJohn McCall
13128cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbournebool IntExprEvaluator::VisitCallExpr(const CallExpr *E) {
13133c385e5f8d9008fff18597ca302be19fa86e51f6Douglas Gregor  switch (E->isBuiltinCall(Info.Ctx)) {
1314019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner  default:
13158cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    return ExprEvaluatorBaseTy::VisitCallExpr(E);
131664eda9e50b593f935c95bd1edc98c4bfda03f601Mike Stump
131764eda9e50b593f935c95bd1edc98c4bfda03f601Mike Stump  case Builtin::BI__builtin_object_size: {
131842c8f87eb60958170c46767273bf93e6c96125bfJohn McCall    if (TryEvaluateBuiltinObjectSize(E))
131942c8f87eb60958170c46767273bf93e6c96125bfJohn McCall      return true;
132064eda9e50b593f935c95bd1edc98c4bfda03f601Mike Stump
1321b2aaf51ed73a4774322a39a0dd59d0fe7e3258c0Eric Christopher    // If evaluating the argument has side-effects we can't determine
1322b2aaf51ed73a4774322a39a0dd59d0fe7e3258c0Eric Christopher    // the size of the object and lower it to unknown now.
1323393c247fe025ccb5f914e37e948192ea86faef8cFariborz Jahanian    if (E->getArg(0)->HasSideEffects(Info.Ctx)) {
1324a6b8b2c09610b8bc4330e948ece8b940c2386406Richard Smith      if (E->getArg(1)->EvaluateKnownConstInt(Info.Ctx).getZExtValue() <= 1)
1325cf184655319cf7a5b811067cff9d26a5741fd161Chris Lattner        return Success(-1ULL, E);
132664eda9e50b593f935c95bd1edc98c4bfda03f601Mike Stump      return Success(0, E);
132764eda9e50b593f935c95bd1edc98c4bfda03f601Mike Stump    }
1328c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump
132964eda9e50b593f935c95bd1edc98c4bfda03f601Mike Stump    return Error(E->getLocStart(), diag::note_invalid_subexpr_in_ice, E);
133064eda9e50b593f935c95bd1edc98c4bfda03f601Mike Stump  }
133164eda9e50b593f935c95bd1edc98c4bfda03f601Mike Stump
1332019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner  case Builtin::BI__builtin_classify_type:
1333131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar    return Success(EvaluateBuiltinClassifyType(E), E);
13341eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
13354bbc0e05a714d4ee4918a92a4a7049dd6ef33ad0Anders Carlsson  case Builtin::BI__builtin_constant_p:
1336019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner    // __builtin_constant_p always has one operand: it returns true if that
1337019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner    // operand can be folded, false otherwise.
1338131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar    return Success(E->getArg(0)->isEvaluatable(Info.Ctx), E);
133921fb98ee003e992b0c4e204d98a19e0ef544cae3Chris Lattner
134021fb98ee003e992b0c4e204d98a19e0ef544cae3Chris Lattner  case Builtin::BI__builtin_eh_return_data_regno: {
1341a6b8b2c09610b8bc4330e948ece8b940c2386406Richard Smith    int Operand = E->getArg(0)->EvaluateKnownConstInt(Info.Ctx).getZExtValue();
1342bcfd1f55bfbb3e5944cd5e03d07b343e280838c4Douglas Gregor    Operand = Info.Ctx.getTargetInfo().getEHDataRegisterNumber(Operand);
134321fb98ee003e992b0c4e204d98a19e0ef544cae3Chris Lattner    return Success(Operand, E);
134421fb98ee003e992b0c4e204d98a19e0ef544cae3Chris Lattner  }
1345c4a2638b5ef3e2d35d872614ceb655a7a22c58beEli Friedman
1346c4a2638b5ef3e2d35d872614ceb655a7a22c58beEli Friedman  case Builtin::BI__builtin_expect:
1347c4a2638b5ef3e2d35d872614ceb655a7a22c58beEli Friedman    return Visit(E->getArg(0));
13485726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor
13495726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor  case Builtin::BIstrlen:
13505726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor  case Builtin::BI__builtin_strlen:
13515726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor    // As an extension, we support strlen() and __builtin_strlen() as constant
13525726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor    // expressions when the argument is a string literal.
13538cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    if (const StringLiteral *S
13545726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor               = dyn_cast<StringLiteral>(E->getArg(0)->IgnoreParenImpCasts())) {
13555726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor      // The string literal may have embedded null characters. Find the first
13565726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor      // one and truncate there.
13575f9e272e632e951b1efe824cd16acb4d96077930Chris Lattner      StringRef Str = S->getString();
13585f9e272e632e951b1efe824cd16acb4d96077930Chris Lattner      StringRef::size_type Pos = Str.find(0);
13595f9e272e632e951b1efe824cd16acb4d96077930Chris Lattner      if (Pos != StringRef::npos)
13605726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor        Str = Str.substr(0, Pos);
13615726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor
13625726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor      return Success(Str.size(), E);
13635726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor    }
13645726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor
13655726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor    return Error(E->getLocStart(), diag::note_invalid_subexpr_in_ice, E);
1366454b57ac42c9ce0bed9b7a99c2ed5a18fbcd286bEli Friedman
1367454b57ac42c9ce0bed9b7a99c2ed5a18fbcd286bEli Friedman  case Builtin::BI__atomic_is_lock_free: {
1368454b57ac42c9ce0bed9b7a99c2ed5a18fbcd286bEli Friedman    APSInt SizeVal;
1369454b57ac42c9ce0bed9b7a99c2ed5a18fbcd286bEli Friedman    if (!EvaluateInteger(E->getArg(0), SizeVal, Info))
1370454b57ac42c9ce0bed9b7a99c2ed5a18fbcd286bEli Friedman      return false;
1371454b57ac42c9ce0bed9b7a99c2ed5a18fbcd286bEli Friedman
1372454b57ac42c9ce0bed9b7a99c2ed5a18fbcd286bEli Friedman    // For __atomic_is_lock_free(sizeof(_Atomic(T))), if the size is a power
1373454b57ac42c9ce0bed9b7a99c2ed5a18fbcd286bEli Friedman    // of two less than the maximum inline atomic width, we know it is
1374454b57ac42c9ce0bed9b7a99c2ed5a18fbcd286bEli Friedman    // lock-free.  If the size isn't a power of two, or greater than the
1375454b57ac42c9ce0bed9b7a99c2ed5a18fbcd286bEli Friedman    // maximum alignment where we promote atomics, we know it is not lock-free
1376454b57ac42c9ce0bed9b7a99c2ed5a18fbcd286bEli Friedman    // (at least not in the sense of atomic_is_lock_free).  Otherwise,
1377454b57ac42c9ce0bed9b7a99c2ed5a18fbcd286bEli Friedman    // the answer can only be determined at runtime; for example, 16-byte
1378454b57ac42c9ce0bed9b7a99c2ed5a18fbcd286bEli Friedman    // atomics have lock-free implementations on some, but not all,
1379454b57ac42c9ce0bed9b7a99c2ed5a18fbcd286bEli Friedman    // x86-64 processors.
1380454b57ac42c9ce0bed9b7a99c2ed5a18fbcd286bEli Friedman
1381454b57ac42c9ce0bed9b7a99c2ed5a18fbcd286bEli Friedman    // Check power-of-two.
1382454b57ac42c9ce0bed9b7a99c2ed5a18fbcd286bEli Friedman    CharUnits Size = CharUnits::fromQuantity(SizeVal.getZExtValue());
1383454b57ac42c9ce0bed9b7a99c2ed5a18fbcd286bEli Friedman    if (!Size.isPowerOfTwo())
1384454b57ac42c9ce0bed9b7a99c2ed5a18fbcd286bEli Friedman#if 0
1385454b57ac42c9ce0bed9b7a99c2ed5a18fbcd286bEli Friedman      // FIXME: Suppress this folding until the ABI for the promotion width
1386454b57ac42c9ce0bed9b7a99c2ed5a18fbcd286bEli Friedman      // settles.
1387454b57ac42c9ce0bed9b7a99c2ed5a18fbcd286bEli Friedman      return Success(0, E);
1388454b57ac42c9ce0bed9b7a99c2ed5a18fbcd286bEli Friedman#else
1389454b57ac42c9ce0bed9b7a99c2ed5a18fbcd286bEli Friedman      return Error(E->getLocStart(), diag::note_invalid_subexpr_in_ice, E);
1390454b57ac42c9ce0bed9b7a99c2ed5a18fbcd286bEli Friedman#endif
1391454b57ac42c9ce0bed9b7a99c2ed5a18fbcd286bEli Friedman
1392454b57ac42c9ce0bed9b7a99c2ed5a18fbcd286bEli Friedman#if 0
1393454b57ac42c9ce0bed9b7a99c2ed5a18fbcd286bEli Friedman    // Check against promotion width.
1394454b57ac42c9ce0bed9b7a99c2ed5a18fbcd286bEli Friedman    // FIXME: Suppress this folding until the ABI for the promotion width
1395454b57ac42c9ce0bed9b7a99c2ed5a18fbcd286bEli Friedman    // settles.
1396454b57ac42c9ce0bed9b7a99c2ed5a18fbcd286bEli Friedman    unsigned PromoteWidthBits =
1397454b57ac42c9ce0bed9b7a99c2ed5a18fbcd286bEli Friedman        Info.Ctx.getTargetInfo().getMaxAtomicPromoteWidth();
1398454b57ac42c9ce0bed9b7a99c2ed5a18fbcd286bEli Friedman    if (Size > Info.Ctx.toCharUnitsFromBits(PromoteWidthBits))
1399454b57ac42c9ce0bed9b7a99c2ed5a18fbcd286bEli Friedman      return Success(0, E);
1400454b57ac42c9ce0bed9b7a99c2ed5a18fbcd286bEli Friedman#endif
1401454b57ac42c9ce0bed9b7a99c2ed5a18fbcd286bEli Friedman
1402454b57ac42c9ce0bed9b7a99c2ed5a18fbcd286bEli Friedman    // Check against inlining width.
1403454b57ac42c9ce0bed9b7a99c2ed5a18fbcd286bEli Friedman    unsigned InlineWidthBits =
1404454b57ac42c9ce0bed9b7a99c2ed5a18fbcd286bEli Friedman        Info.Ctx.getTargetInfo().getMaxAtomicInlineWidth();
1405454b57ac42c9ce0bed9b7a99c2ed5a18fbcd286bEli Friedman    if (Size <= Info.Ctx.toCharUnitsFromBits(InlineWidthBits))
1406454b57ac42c9ce0bed9b7a99c2ed5a18fbcd286bEli Friedman      return Success(1, E);
1407454b57ac42c9ce0bed9b7a99c2ed5a18fbcd286bEli Friedman
1408454b57ac42c9ce0bed9b7a99c2ed5a18fbcd286bEli Friedman    return Error(E->getLocStart(), diag::note_invalid_subexpr_in_ice, E);
1409454b57ac42c9ce0bed9b7a99c2ed5a18fbcd286bEli Friedman  }
1410019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner  }
14114c4867e140327fa3b56306fa03c64c8e6a7c95efChris Lattner}
1412f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner
1413b542afe02d317411d53b3541946f9f2a8f509a11Chris Lattnerbool IntExprEvaluator::VisitBinaryOperator(const BinaryOperator *E) {
14142de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall  if (E->getOpcode() == BO_Comma) {
14158327fad71da34492d82c532f42a58cb4baff81a3Richard Smith    VisitIgnoredValue(E->getLHS());
14168327fad71da34492d82c532f42a58cb4baff81a3Richard Smith    return Visit(E->getRHS());
1417a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman  }
1418a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman
1419a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman  if (E->isLogicalOp()) {
1420a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman    // These need to be handled specially because the operands aren't
1421a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman    // necessarily integral
1422fcb4d09531abbf2a5cf398c2f946fb3bc2875f64Anders Carlsson    bool lhsResult, rhsResult;
14231eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
1424fcb4d09531abbf2a5cf398c2f946fb3bc2875f64Anders Carlsson    if (HandleConversionToBool(E->getLHS(), lhsResult, Info)) {
142551fe996231b1d7199f76e4005ff4c943d5deeecdAnders Carlsson      // We were able to evaluate the LHS, see if we can get away with not
142651fe996231b1d7199f76e4005ff4c943d5deeecdAnders Carlsson      // evaluating the RHS: 0 && X -> 0, 1 || X -> 1
14272de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall      if (lhsResult == (E->getOpcode() == BO_LOr))
14283f7d995390009fede92b333a040da80e1ce90997Daniel Dunbar        return Success(lhsResult, E);
1429a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman
1430fcb4d09531abbf2a5cf398c2f946fb3bc2875f64Anders Carlsson      if (HandleConversionToBool(E->getRHS(), rhsResult, Info)) {
14312de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall        if (E->getOpcode() == BO_LOr)
1432131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar          return Success(lhsResult || rhsResult, E);
14334bbc0e05a714d4ee4918a92a4a7049dd6ef33ad0Anders Carlsson        else
1434131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar          return Success(lhsResult && rhsResult, E);
14354bbc0e05a714d4ee4918a92a4a7049dd6ef33ad0Anders Carlsson      }
14364bbc0e05a714d4ee4918a92a4a7049dd6ef33ad0Anders Carlsson    } else {
1437fcb4d09531abbf2a5cf398c2f946fb3bc2875f64Anders Carlsson      if (HandleConversionToBool(E->getRHS(), rhsResult, Info)) {
14384bbc0e05a714d4ee4918a92a4a7049dd6ef33ad0Anders Carlsson        // We can't evaluate the LHS; however, sometimes the result
14394bbc0e05a714d4ee4918a92a4a7049dd6ef33ad0Anders Carlsson        // is determined by the RHS: X && 0 -> 0, X || 1 -> 1.
14402de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall        if (rhsResult == (E->getOpcode() == BO_LOr) ||
14412de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall            !rhsResult == (E->getOpcode() == BO_LAnd)) {
1442131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar          // Since we weren't able to evaluate the left hand side, it
1443fcb4d09531abbf2a5cf398c2f946fb3bc2875f64Anders Carlsson          // must have had side effects.
14441e12c59e8f9bb76c23628c4e0d0a1dfced0b1fa0Richard Smith          Info.EvalStatus.HasSideEffects = true;
1445131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar
1446131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar          return Success(rhsResult, E);
14474bbc0e05a714d4ee4918a92a4a7049dd6ef33ad0Anders Carlsson        }
14484bbc0e05a714d4ee4918a92a4a7049dd6ef33ad0Anders Carlsson      }
1449a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman    }
1450a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman
1451a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman    return false;
1452c8cc9ccc7b87a7ed1749b074f6b670bcec49abc1Chris Lattner  }
145354176fdb044312b4b77c3da6682d3575b3728d30Chris Lattner
1454286f85e791dda3634fee7f6c67f0ed92296c028fAnders Carlsson  QualType LHSTy = E->getLHS()->getType();
1455286f85e791dda3634fee7f6c67f0ed92296c028fAnders Carlsson  QualType RHSTy = E->getRHS()->getType();
14564087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar
14574087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar  if (LHSTy->isAnyComplexType()) {
14584087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar    assert(RHSTy->isAnyComplexType() && "Invalid comparison");
1459f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall    ComplexValue LHS, RHS;
14604087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar
14614087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar    if (!EvaluateComplex(E->getLHS(), LHS, Info))
14624087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar      return false;
14634087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar
14644087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar    if (!EvaluateComplex(E->getRHS(), RHS, Info))
14654087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar      return false;
14664087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar
14674087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar    if (LHS.isComplexFloat()) {
14681eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump      APFloat::cmpResult CR_r =
14694087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar        LHS.getComplexFloatReal().compare(RHS.getComplexFloatReal());
14701eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump      APFloat::cmpResult CR_i =
14714087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar        LHS.getComplexFloatImag().compare(RHS.getComplexFloatImag());
14724087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar
14732de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall      if (E->getOpcode() == BO_EQ)
1474131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar        return Success((CR_r == APFloat::cmpEqual &&
1475131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar                        CR_i == APFloat::cmpEqual), E);
1476131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar      else {
14772de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall        assert(E->getOpcode() == BO_NE &&
1478131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar               "Invalid complex comparison.");
14791eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump        return Success(((CR_r == APFloat::cmpGreaterThan ||
1480fc39dc4c7886723310419b1869cf651ca55b7af4Mon P Wang                         CR_r == APFloat::cmpLessThan ||
1481fc39dc4c7886723310419b1869cf651ca55b7af4Mon P Wang                         CR_r == APFloat::cmpUnordered) ||
14821eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump                        (CR_i == APFloat::cmpGreaterThan ||
1483fc39dc4c7886723310419b1869cf651ca55b7af4Mon P Wang                         CR_i == APFloat::cmpLessThan ||
1484fc39dc4c7886723310419b1869cf651ca55b7af4Mon P Wang                         CR_i == APFloat::cmpUnordered)), E);
1485131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar      }
14864087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar    } else {
14872de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall      if (E->getOpcode() == BO_EQ)
1488131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar        return Success((LHS.getComplexIntReal() == RHS.getComplexIntReal() &&
1489131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar                        LHS.getComplexIntImag() == RHS.getComplexIntImag()), E);
1490131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar      else {
14912de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall        assert(E->getOpcode() == BO_NE &&
1492131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar               "Invalid compex comparison.");
1493131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar        return Success((LHS.getComplexIntReal() != RHS.getComplexIntReal() ||
1494131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar                        LHS.getComplexIntImag() != RHS.getComplexIntImag()), E);
1495131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar      }
14964087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar    }
14974087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar  }
14981eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
1499286f85e791dda3634fee7f6c67f0ed92296c028fAnders Carlsson  if (LHSTy->isRealFloatingType() &&
1500286f85e791dda3634fee7f6c67f0ed92296c028fAnders Carlsson      RHSTy->isRealFloatingType()) {
1501286f85e791dda3634fee7f6c67f0ed92296c028fAnders Carlsson    APFloat RHS(0.0), LHS(0.0);
15021eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
1503286f85e791dda3634fee7f6c67f0ed92296c028fAnders Carlsson    if (!EvaluateFloat(E->getRHS(), RHS, Info))
1504286f85e791dda3634fee7f6c67f0ed92296c028fAnders Carlsson      return false;
15051eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
1506286f85e791dda3634fee7f6c67f0ed92296c028fAnders Carlsson    if (!EvaluateFloat(E->getLHS(), LHS, Info))
1507286f85e791dda3634fee7f6c67f0ed92296c028fAnders Carlsson      return false;
15081eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
1509286f85e791dda3634fee7f6c67f0ed92296c028fAnders Carlsson    APFloat::cmpResult CR = LHS.compare(RHS);
1510529569e68d10b0fd3750fd2124faf742249b846bAnders Carlsson
1511286f85e791dda3634fee7f6c67f0ed92296c028fAnders Carlsson    switch (E->getOpcode()) {
1512286f85e791dda3634fee7f6c67f0ed92296c028fAnders Carlsson    default:
1513b219cfc4d75f0a03630b7c4509ef791b7e97b2c8David Blaikie      llvm_unreachable("Invalid binary operator!");
15142de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case BO_LT:
1515131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar      return Success(CR == APFloat::cmpLessThan, E);
15162de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case BO_GT:
1517131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar      return Success(CR == APFloat::cmpGreaterThan, E);
15182de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case BO_LE:
1519131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar      return Success(CR == APFloat::cmpLessThan || CR == APFloat::cmpEqual, E);
15202de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case BO_GE:
15211eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump      return Success(CR == APFloat::cmpGreaterThan || CR == APFloat::cmpEqual,
1522131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar                     E);
15232de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case BO_EQ:
1524131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar      return Success(CR == APFloat::cmpEqual, E);
15252de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case BO_NE:
15261eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump      return Success(CR == APFloat::cmpGreaterThan
1527fc39dc4c7886723310419b1869cf651ca55b7af4Mon P Wang                     || CR == APFloat::cmpLessThan
1528fc39dc4c7886723310419b1869cf651ca55b7af4Mon P Wang                     || CR == APFloat::cmpUnordered, E);
1529286f85e791dda3634fee7f6c67f0ed92296c028fAnders Carlsson    }
1530286f85e791dda3634fee7f6c67f0ed92296c028fAnders Carlsson  }
15311eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
1532ad02d7debd03ff275ac8ea27891a4ecccdb78068Eli Friedman  if (LHSTy->isPointerType() && RHSTy->isPointerType()) {
15332de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    if (E->getOpcode() == BO_Sub || E->isEqualityOp()) {
1534efdb83e26f9a1fd2566afe54461216cd84814d42John McCall      LValue LHSValue;
15353068d117951a8df54bae9db039b56201ab10962bAnders Carlsson      if (!EvaluatePointer(E->getLHS(), LHSValue, Info))
15363068d117951a8df54bae9db039b56201ab10962bAnders Carlsson        return false;
1537a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman
1538efdb83e26f9a1fd2566afe54461216cd84814d42John McCall      LValue RHSValue;
15393068d117951a8df54bae9db039b56201ab10962bAnders Carlsson      if (!EvaluatePointer(E->getRHS(), RHSValue, Info))
15403068d117951a8df54bae9db039b56201ab10962bAnders Carlsson        return false;
1541a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman
15425bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman      // Reject any bases from the normal codepath; we special-case comparisons
15435bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman      // to null.
15445bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman      if (LHSValue.getLValueBase()) {
15455bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman        if (!E->isEqualityOp())
15465bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman          return false;
1547a73058324197b7bdfd19307965954f626e26199dKen Dyck        if (RHSValue.getLValueBase() || !RHSValue.getLValueOffset().isZero())
15485bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman          return false;
15495bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman        bool bres;
15505bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman        if (!EvalPointerValueAsBool(LHSValue, bres))
15515bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman          return false;
15522de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall        return Success(bres ^ (E->getOpcode() == BO_EQ), E);
15535bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman      } else if (RHSValue.getLValueBase()) {
15545bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman        if (!E->isEqualityOp())
15555bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman          return false;
1556a73058324197b7bdfd19307965954f626e26199dKen Dyck        if (LHSValue.getLValueBase() || !LHSValue.getLValueOffset().isZero())
15575bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman          return false;
15585bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman        bool bres;
15595bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman        if (!EvalPointerValueAsBool(RHSValue, bres))
15605bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman          return false;
15612de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall        return Success(bres ^ (E->getOpcode() == BO_EQ), E);
15625bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman      }
1563a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman
15642de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall      if (E->getOpcode() == BO_Sub) {
15654992bdde387c5f033bb450a716eaabc0fda52688Chris Lattner        QualType Type = E->getLHS()->getType();
15664992bdde387c5f033bb450a716eaabc0fda52688Chris Lattner        QualType ElementType = Type->getAs<PointerType>()->getPointeeType();
15673068d117951a8df54bae9db039b56201ab10962bAnders Carlsson
1568a73058324197b7bdfd19307965954f626e26199dKen Dyck        CharUnits ElementSize = CharUnits::One();
1569ce1bca73aef9bbf6359ab8420278203dda81a054Eli Friedman        if (!ElementType->isVoidType() && !ElementType->isFunctionType())
1570a73058324197b7bdfd19307965954f626e26199dKen Dyck          ElementSize = Info.Ctx.getTypeSizeInChars(ElementType);
1571a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman
1572a73058324197b7bdfd19307965954f626e26199dKen Dyck        CharUnits Diff = LHSValue.getLValueOffset() -
1573a73058324197b7bdfd19307965954f626e26199dKen Dyck                             RHSValue.getLValueOffset();
1574a73058324197b7bdfd19307965954f626e26199dKen Dyck        return Success(Diff / ElementSize, E);
1575ad02d7debd03ff275ac8ea27891a4ecccdb78068Eli Friedman      }
1576ad02d7debd03ff275ac8ea27891a4ecccdb78068Eli Friedman      bool Result;
15772de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall      if (E->getOpcode() == BO_EQ) {
1578ad02d7debd03ff275ac8ea27891a4ecccdb78068Eli Friedman        Result = LHSValue.getLValueOffset() == RHSValue.getLValueOffset();
1579267c0ab1b9a15768f3f15abbfc40ce344751c78bEli Friedman      } else {
1580ad02d7debd03ff275ac8ea27891a4ecccdb78068Eli Friedman        Result = LHSValue.getLValueOffset() != RHSValue.getLValueOffset();
1581ad02d7debd03ff275ac8ea27891a4ecccdb78068Eli Friedman      }
1582ad02d7debd03ff275ac8ea27891a4ecccdb78068Eli Friedman      return Success(Result, E);
15833068d117951a8df54bae9db039b56201ab10962bAnders Carlsson    }
15843068d117951a8df54bae9db039b56201ab10962bAnders Carlsson  }
15852ade35e2cfd554e49d35a52047cea98a82787af9Douglas Gregor  if (!LHSTy->isIntegralOrEnumerationType() ||
15862ade35e2cfd554e49d35a52047cea98a82787af9Douglas Gregor      !RHSTy->isIntegralOrEnumerationType()) {
1587a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman    // We can't continue from here for non-integral types, and they
1588a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman    // could potentially confuse the following operations.
1589a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman    return false;
1590a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman  }
1591a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman
1592a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman  // The LHS of a constant expr is always evaluated and needed.
159330c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar  if (!Visit(E->getLHS()))
1594a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman    return false; // error in subexpression.
1595d9f4bcda18bfbf79341edd9d381d4b6a3cffe655Eli Friedman
159642edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman  APValue RHSVal;
159742edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman  if (!EvaluateIntegerOrLValue(E->getRHS(), RHSVal, Info))
159830c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar    return false;
159942edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman
160042edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman  // Handle cases like (unsigned long)&a + 4.
160142edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman  if (E->isAdditiveOp() && Result.isLValue() && RHSVal.isInt()) {
1602a73058324197b7bdfd19307965954f626e26199dKen Dyck    CharUnits Offset = Result.getLValueOffset();
1603a73058324197b7bdfd19307965954f626e26199dKen Dyck    CharUnits AdditionalOffset = CharUnits::fromQuantity(
1604a73058324197b7bdfd19307965954f626e26199dKen Dyck                                     RHSVal.getInt().getZExtValue());
16052de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    if (E->getOpcode() == BO_Add)
1606a73058324197b7bdfd19307965954f626e26199dKen Dyck      Offset += AdditionalOffset;
160742edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman    else
1608a73058324197b7bdfd19307965954f626e26199dKen Dyck      Offset -= AdditionalOffset;
1609a73058324197b7bdfd19307965954f626e26199dKen Dyck    Result = APValue(Result.getLValueBase(), Offset);
161042edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman    return true;
161142edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman  }
161242edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman
161342edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman  // Handle cases like 4 + (unsigned long)&a
16142de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall  if (E->getOpcode() == BO_Add &&
161542edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman        RHSVal.isLValue() && Result.isInt()) {
1616a73058324197b7bdfd19307965954f626e26199dKen Dyck    CharUnits Offset = RHSVal.getLValueOffset();
1617a73058324197b7bdfd19307965954f626e26199dKen Dyck    Offset += CharUnits::fromQuantity(Result.getInt().getZExtValue());
1618a73058324197b7bdfd19307965954f626e26199dKen Dyck    Result = APValue(RHSVal.getLValueBase(), Offset);
161942edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman    return true;
162042edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman  }
162142edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman
162242edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman  // All the following cases expect both operands to be an integer
162342edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman  if (!Result.isInt() || !RHSVal.isInt())
1624b542afe02d317411d53b3541946f9f2a8f509a11Chris Lattner    return false;
1625a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman
162642edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman  APSInt& RHS = RHSVal.getInt();
162742edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman
1628a25ae3d68d84d2b89907f998df6a396549589da5Anders Carlsson  switch (E->getOpcode()) {
162932fea9d18cc3658a1b01df5ca6f2ac302625c61dChris Lattner  default:
16300e8acbbba71ec6acd5dceb4fcbce63e463e1b755Anders Carlsson    return Error(E->getOperatorLoc(), diag::note_invalid_subexpr_in_ice, E);
16312de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall  case BO_Mul: return Success(Result.getInt() * RHS, E);
16322de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall  case BO_Add: return Success(Result.getInt() + RHS, E);
16332de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall  case BO_Sub: return Success(Result.getInt() - RHS, E);
16342de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall  case BO_And: return Success(Result.getInt() & RHS, E);
16352de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall  case BO_Xor: return Success(Result.getInt() ^ RHS, E);
16362de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall  case BO_Or:  return Success(Result.getInt() | RHS, E);
16372de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall  case BO_Div:
163854176fdb044312b4b77c3da6682d3575b3728d30Chris Lattner    if (RHS == 0)
16390e8acbbba71ec6acd5dceb4fcbce63e463e1b755Anders Carlsson      return Error(E->getOperatorLoc(), diag::note_expr_divide_by_zero, E);
164030c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar    return Success(Result.getInt() / RHS, E);
16412de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall  case BO_Rem:
164254176fdb044312b4b77c3da6682d3575b3728d30Chris Lattner    if (RHS == 0)
16430e8acbbba71ec6acd5dceb4fcbce63e463e1b755Anders Carlsson      return Error(E->getOperatorLoc(), diag::note_expr_divide_by_zero, E);
164430c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar    return Success(Result.getInt() % RHS, E);
16452de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall  case BO_Shl: {
1646091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall    // During constant-folding, a negative shift is an opposite shift.
1647091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall    if (RHS.isSigned() && RHS.isNegative()) {
1648091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall      RHS = -RHS;
1649091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall      goto shift_right;
1650091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall    }
1651091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall
1652091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall  shift_left:
1653091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall    unsigned SA
1654091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall      = (unsigned) RHS.getLimitedValue(Result.getInt().getBitWidth()-1);
165530c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar    return Success(Result.getInt() << SA, E);
16563f7d995390009fede92b333a040da80e1ce90997Daniel Dunbar  }
16572de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall  case BO_Shr: {
1658091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall    // During constant-folding, a negative shift is an opposite shift.
1659091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall    if (RHS.isSigned() && RHS.isNegative()) {
1660091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall      RHS = -RHS;
1661091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall      goto shift_left;
1662091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall    }
1663091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall
1664091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall  shift_right:
16651eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump    unsigned SA =
166630c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar      (unsigned) RHS.getLimitedValue(Result.getInt().getBitWidth()-1);
166730c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar    return Success(Result.getInt() >> SA, E);
16683f7d995390009fede92b333a040da80e1ce90997Daniel Dunbar  }
16691eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
16702de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall  case BO_LT: return Success(Result.getInt() < RHS, E);
16712de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall  case BO_GT: return Success(Result.getInt() > RHS, E);
16722de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall  case BO_LE: return Success(Result.getInt() <= RHS, E);
16732de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall  case BO_GE: return Success(Result.getInt() >= RHS, E);
16742de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall  case BO_EQ: return Success(Result.getInt() == RHS, E);
16752de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall  case BO_NE: return Success(Result.getInt() != RHS, E);
1676b11e77836dd0867955c5abf32baf1c3e6c7f81e1Eli Friedman  }
1677a25ae3d68d84d2b89907f998df6a396549589da5Anders Carlsson}
1678a25ae3d68d84d2b89907f998df6a396549589da5Anders Carlsson
16798b752f10c394b140f9ef89e049cbad1a7676fc25Ken DyckCharUnits IntExprEvaluator::GetAlignOfType(QualType T) {
16805d484e8cf710207010720589d89602233de61d01Sebastian Redl  // C++ [expr.sizeof]p2: "When applied to a reference or a reference type,
16815d484e8cf710207010720589d89602233de61d01Sebastian Redl  //   the result is the size of the referenced type."
16825d484e8cf710207010720589d89602233de61d01Sebastian Redl  // C++ [expr.alignof]p3: "When alignof is applied to a reference type, the
16835d484e8cf710207010720589d89602233de61d01Sebastian Redl  //   result shall be the alignment of the referenced type."
16845d484e8cf710207010720589d89602233de61d01Sebastian Redl  if (const ReferenceType *Ref = T->getAs<ReferenceType>())
16855d484e8cf710207010720589d89602233de61d01Sebastian Redl    T = Ref->getPointeeType();
16869f1210c3280104417a4ad30f0a00825ac8fa718aChad Rosier
16879f1210c3280104417a4ad30f0a00825ac8fa718aChad Rosier  // __alignof is defined to return the preferred alignment.
16889f1210c3280104417a4ad30f0a00825ac8fa718aChad Rosier  return Info.Ctx.toCharUnitsFromBits(
16899f1210c3280104417a4ad30f0a00825ac8fa718aChad Rosier    Info.Ctx.getPreferredTypeAlign(T.getTypePtr()));
1690e9feb475d72ba50dc29cec62a8c47cae721065ebChris Lattner}
1691e9feb475d72ba50dc29cec62a8c47cae721065ebChris Lattner
16928b752f10c394b140f9ef89e049cbad1a7676fc25Ken DyckCharUnits IntExprEvaluator::GetAlignOfExpr(const Expr *E) {
1693af707ab8fbb9451e8febb8d766f6c043628125c4Chris Lattner  E = E->IgnoreParens();
1694af707ab8fbb9451e8febb8d766f6c043628125c4Chris Lattner
1695af707ab8fbb9451e8febb8d766f6c043628125c4Chris Lattner  // alignof decl is always accepted, even if it doesn't make sense: we default
16961eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump  // to 1 in those cases.
1697af707ab8fbb9451e8febb8d766f6c043628125c4Chris Lattner  if (const DeclRefExpr *DRE = dyn_cast<DeclRefExpr>(E))
16988b752f10c394b140f9ef89e049cbad1a7676fc25Ken Dyck    return Info.Ctx.getDeclAlign(DRE->getDecl(),
16998b752f10c394b140f9ef89e049cbad1a7676fc25Ken Dyck                                 /*RefAsPointee*/true);
1700a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman
1701af707ab8fbb9451e8febb8d766f6c043628125c4Chris Lattner  if (const MemberExpr *ME = dyn_cast<MemberExpr>(E))
17028b752f10c394b140f9ef89e049cbad1a7676fc25Ken Dyck    return Info.Ctx.getDeclAlign(ME->getMemberDecl(),
17038b752f10c394b140f9ef89e049cbad1a7676fc25Ken Dyck                                 /*RefAsPointee*/true);
1704af707ab8fbb9451e8febb8d766f6c043628125c4Chris Lattner
1705e9feb475d72ba50dc29cec62a8c47cae721065ebChris Lattner  return GetAlignOfType(E->getType());
1706e9feb475d72ba50dc29cec62a8c47cae721065ebChris Lattner}
1707e9feb475d72ba50dc29cec62a8c47cae721065ebChris Lattner
1708e9feb475d72ba50dc29cec62a8c47cae721065ebChris Lattner
1709f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne/// VisitUnaryExprOrTypeTraitExpr - Evaluate a sizeof, alignof or vec_step with
1710f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne/// a result as the expression's type.
1711f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbournebool IntExprEvaluator::VisitUnaryExprOrTypeTraitExpr(
1712f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne                                    const UnaryExprOrTypeTraitExpr *E) {
1713f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne  switch(E->getKind()) {
1714f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne  case UETT_AlignOf: {
1715e9feb475d72ba50dc29cec62a8c47cae721065ebChris Lattner    if (E->isArgumentType())
17164f3bc8f7aa90b72832b03bee9201c98f4bb6b4d1Ken Dyck      return Success(GetAlignOfType(E->getArgumentType()), E);
1717e9feb475d72ba50dc29cec62a8c47cae721065ebChris Lattner    else
17184f3bc8f7aa90b72832b03bee9201c98f4bb6b4d1Ken Dyck      return Success(GetAlignOfExpr(E->getArgumentExpr()), E);
1719e9feb475d72ba50dc29cec62a8c47cae721065ebChris Lattner  }
1720a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman
1721f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne  case UETT_VecStep: {
1722f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne    QualType Ty = E->getTypeOfArgument();
17230518999d3adcc289997bd974dce90cc97f5c1c44Sebastian Redl
1724f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne    if (Ty->isVectorType()) {
1725f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne      unsigned n = Ty->getAs<VectorType>()->getNumElements();
1726a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman
1727f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne      // The vec_step built-in functions that take a 3-component
1728f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne      // vector return 4. (OpenCL 1.1 spec 6.11.12)
1729f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne      if (n == 3)
1730f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne        n = 4;
1731f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne
1732f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne      return Success(n, E);
1733f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne    } else
1734f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne      return Success(1, E);
1735f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne  }
1736f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne
1737f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne  case UETT_SizeOf: {
1738f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne    QualType SrcTy = E->getTypeOfArgument();
1739f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne    // C++ [expr.sizeof]p2: "When applied to a reference or a reference type,
1740f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne    //   the result is the size of the referenced type."
1741f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne    // C++ [expr.alignof]p3: "When alignof is applied to a reference type, the
1742f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne    //   result shall be the alignment of the referenced type."
1743f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne    if (const ReferenceType *Ref = SrcTy->getAs<ReferenceType>())
1744f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne      SrcTy = Ref->getPointeeType();
1745f2da9dfef96dc11b7b5effb1d02cb427b2d71599Eli Friedman
1746f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne    // sizeof(void), __alignof__(void), sizeof(function) = 1 as a gcc
1747f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne    // extension.
1748f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne    if (SrcTy->isVoidType() || SrcTy->isFunctionType())
1749f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne      return Success(1, E);
1750f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne
1751f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne    // sizeof(vla) is not a constantexpr: C99 6.5.3.4p2.
1752f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne    if (!SrcTy->isConstantSizeType())
1753f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne      return false;
1754f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne
1755f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne    // Get information about the size.
1756f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne    return Success(Info.Ctx.getTypeSizeInChars(SrcTy), E);
1757f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne  }
1758f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne  }
1759f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne
1760f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne  llvm_unreachable("unknown expr/type trait");
1761f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne  return false;
1762fcee0019b76f9f368f2b3d6d4048a98232593f29Chris Lattner}
1763fcee0019b76f9f368f2b3d6d4048a98232593f29Chris Lattner
17648cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbournebool IntExprEvaluator::VisitOffsetOfExpr(const OffsetOfExpr *OOE) {
17658ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor  CharUnits Result;
17668cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  unsigned n = OOE->getNumComponents();
17678ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor  if (n == 0)
17688ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor    return false;
17698cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  QualType CurrentType = OOE->getTypeSourceInfo()->getType();
17708ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor  for (unsigned i = 0; i != n; ++i) {
17718ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor    OffsetOfExpr::OffsetOfNode ON = OOE->getComponent(i);
17728ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor    switch (ON.getKind()) {
17738ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor    case OffsetOfExpr::OffsetOfNode::Array: {
17748cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne      const Expr *Idx = OOE->getIndexExpr(ON.getArrayExprIndex());
17758ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor      APSInt IdxResult;
17768ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor      if (!EvaluateInteger(Idx, IdxResult, Info))
17778ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor        return false;
17788ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor      const ArrayType *AT = Info.Ctx.getAsArrayType(CurrentType);
17798ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor      if (!AT)
17808ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor        return false;
17818ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor      CurrentType = AT->getElementType();
17828ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor      CharUnits ElementSize = Info.Ctx.getTypeSizeInChars(CurrentType);
17838ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor      Result += IdxResult.getSExtValue() * ElementSize;
17848ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor        break;
17858ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor    }
17868ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor
17878ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor    case OffsetOfExpr::OffsetOfNode::Field: {
17888ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor      FieldDecl *MemberDecl = ON.getField();
17898ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor      const RecordType *RT = CurrentType->getAs<RecordType>();
17908ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor      if (!RT)
17918ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor        return false;
17928ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor      RecordDecl *RD = RT->getDecl();
17938ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor      const ASTRecordLayout &RL = Info.Ctx.getASTRecordLayout(RD);
1794ba4f5d5754c8291690d01ca9581926673d69b24cJohn McCall      unsigned i = MemberDecl->getFieldIndex();
1795cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor      assert(i < RL.getFieldCount() && "offsetof field in wrong type");
1796fb1e3bc29b667f4275e1d5a43d64ec173f4f9a7dKen Dyck      Result += Info.Ctx.toCharUnitsFromBits(RL.getFieldOffset(i));
17978ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor      CurrentType = MemberDecl->getType().getNonReferenceType();
17988ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor      break;
17998ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor    }
18008ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor
18018ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor    case OffsetOfExpr::OffsetOfNode::Identifier:
18028ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor      llvm_unreachable("dependent __builtin_offsetof");
1803cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor      return false;
1804cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor
1805cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor    case OffsetOfExpr::OffsetOfNode::Base: {
1806cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor      CXXBaseSpecifier *BaseSpec = ON.getBase();
1807cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor      if (BaseSpec->isVirtual())
1808cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor        return false;
1809cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor
1810cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor      // Find the layout of the class whose base we are looking into.
1811cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor      const RecordType *RT = CurrentType->getAs<RecordType>();
1812cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor      if (!RT)
1813cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor        return false;
1814cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor      RecordDecl *RD = RT->getDecl();
1815cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor      const ASTRecordLayout &RL = Info.Ctx.getASTRecordLayout(RD);
1816cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor
1817cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor      // Find the base class itself.
1818cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor      CurrentType = BaseSpec->getType();
1819cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor      const RecordType *BaseRT = CurrentType->getAs<RecordType>();
1820cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor      if (!BaseRT)
1821cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor        return false;
1822cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor
1823cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor      // Add the offset to the base.
18247c7f820d70c925b29290a8563b59615816a827fcKen Dyck      Result += RL.getBaseClassOffset(cast<CXXRecordDecl>(BaseRT->getDecl()));
1825cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor      break;
1826cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor    }
18278ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor    }
18288ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor  }
18298cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  return Success(Result, OOE);
18308ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor}
18318ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor
1832b542afe02d317411d53b3541946f9f2a8f509a11Chris Lattnerbool IntExprEvaluator::VisitUnaryOperator(const UnaryOperator *E) {
18332de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall  if (E->getOpcode() == UO_LNot) {
1834a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman    // LNot's operand isn't necessarily an integer, so we handle it specially.
1835a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman    bool bres;
1836a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman    if (!HandleConversionToBool(E->getSubExpr(), bres, Info))
1837a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman      return false;
1838131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar    return Success(!bres, E);
1839a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman  }
1840a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman
18414fff4819a913c65ae23cfd389bc47c61919e4e1fDaniel Dunbar  // Only handle integral operations...
18422ade35e2cfd554e49d35a52047cea98a82787af9Douglas Gregor  if (!E->getSubExpr()->getType()->isIntegralOrEnumerationType())
18434fff4819a913c65ae23cfd389bc47c61919e4e1fDaniel Dunbar    return false;
18444fff4819a913c65ae23cfd389bc47c61919e4e1fDaniel Dunbar
184587eae5ecf94e38baa20d9a327b8f73f8bdc72436Chris Lattner  // Get the operand value into 'Result'.
184687eae5ecf94e38baa20d9a327b8f73f8bdc72436Chris Lattner  if (!Visit(E->getSubExpr()))
184775a4881047deeb3a300ff9293dc6ba8570048bb5Chris Lattner    return false;
1848a25ae3d68d84d2b89907f998df6a396549589da5Anders Carlsson
184975a4881047deeb3a300ff9293dc6ba8570048bb5Chris Lattner  switch (E->getOpcode()) {
18504c4867e140327fa3b56306fa03c64c8e6a7c95efChris Lattner  default:
185175a4881047deeb3a300ff9293dc6ba8570048bb5Chris Lattner    // Address, indirect, pre/post inc/dec, etc are not valid constant exprs.
185275a4881047deeb3a300ff9293dc6ba8570048bb5Chris Lattner    // See C99 6.6p3.
18530e8acbbba71ec6acd5dceb4fcbce63e463e1b755Anders Carlsson    return Error(E->getOperatorLoc(), diag::note_invalid_subexpr_in_ice, E);
18542de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall  case UO_Extension:
18554c4867e140327fa3b56306fa03c64c8e6a7c95efChris Lattner    // FIXME: Should extension allow i-c-e extension expressions in its scope?
18564c4867e140327fa3b56306fa03c64c8e6a7c95efChris Lattner    // If so, we could clear the diagnostic ID.
18573f7d995390009fede92b333a040da80e1ce90997Daniel Dunbar    return true;
18582de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall  case UO_Plus:
18591eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump    // The result is always just the subexpr.
18603f7d995390009fede92b333a040da80e1ce90997Daniel Dunbar    return true;
18612de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall  case UO_Minus:
186230c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar    if (!Result.isInt()) return false;
186330c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar    return Success(-Result.getInt(), E);
18642de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall  case UO_Not:
186530c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar    if (!Result.isInt()) return false;
186630c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar    return Success(~Result.getInt(), E);
186706a3675627e3b3c47b49c689c8e404a33144194aAnders Carlsson  }
1868a25ae3d68d84d2b89907f998df6a396549589da5Anders Carlsson}
18691eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
1870732b2236ae4a4f11e7642677cebbd169c07ea877Chris Lattner/// HandleCast - This is used to evaluate implicit or explicit casts where the
1871732b2236ae4a4f11e7642677cebbd169c07ea877Chris Lattner/// result type is integer.
18728cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbournebool IntExprEvaluator::VisitCastExpr(const CastExpr *E) {
18738cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  const Expr *SubExpr = E->getSubExpr();
187482206e267ce6cc709797127616f64672d255b310Anders Carlsson  QualType DestType = E->getType();
1875b92dac8bc2f6f73919825f9af693a8a7e89ae1d4Daniel Dunbar  QualType SrcType = SubExpr->getType();
187682206e267ce6cc709797127616f64672d255b310Anders Carlsson
187746a523285928aa07bf14803178dc04616ac85994Eli Friedman  switch (E->getCastKind()) {
187846a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_BaseToDerived:
187946a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_DerivedToBase:
188046a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_UncheckedDerivedToBase:
188146a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_Dynamic:
188246a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_ToUnion:
188346a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_ArrayToPointerDecay:
188446a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_FunctionToPointerDecay:
188546a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_NullToPointer:
188646a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_NullToMemberPointer:
188746a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_BaseToDerivedMemberPointer:
188846a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_DerivedToBaseMemberPointer:
188946a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_ConstructorConversion:
189046a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_IntegralToPointer:
189146a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_ToVoid:
189246a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_VectorSplat:
189346a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_IntegralToFloating:
189446a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_FloatingCast:
18951d9b3b25f7ac0d0195bba6b507a684fe5e7943eeJohn McCall  case CK_CPointerToObjCPointerCast:
18961d9b3b25f7ac0d0195bba6b507a684fe5e7943eeJohn McCall  case CK_BlockPointerToObjCPointerCast:
189746a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_AnyPointerToBlockPointerCast:
189846a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_ObjCObjectLValueCast:
189946a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_FloatingRealToComplex:
190046a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_FloatingComplexToReal:
190146a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_FloatingComplexCast:
190246a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_FloatingComplexToIntegralComplex:
190346a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_IntegralRealToComplex:
190446a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_IntegralComplexCast:
190546a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_IntegralComplexToFloatingComplex:
190646a523285928aa07bf14803178dc04616ac85994Eli Friedman    llvm_unreachable("invalid cast kind for integral value");
190746a523285928aa07bf14803178dc04616ac85994Eli Friedman
1908e50c297f92914ca996deb8b597624193273b62e4Eli Friedman  case CK_BitCast:
190946a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_Dependent:
191046a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_GetObjCProperty:
191146a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_LValueBitCast:
191246a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_UserDefinedConversion:
191333e56f3273457bfa22c7c50bc46cf5a18216863dJohn McCall  case CK_ARCProduceObject:
191433e56f3273457bfa22c7c50bc46cf5a18216863dJohn McCall  case CK_ARCConsumeObject:
191533e56f3273457bfa22c7c50bc46cf5a18216863dJohn McCall  case CK_ARCReclaimReturnedObject:
191633e56f3273457bfa22c7c50bc46cf5a18216863dJohn McCall  case CK_ARCExtendBlockObject:
191746a523285928aa07bf14803178dc04616ac85994Eli Friedman    return false;
191846a523285928aa07bf14803178dc04616ac85994Eli Friedman
191946a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_LValueToRValue:
192046a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_NoOp:
192146a523285928aa07bf14803178dc04616ac85994Eli Friedman    return Visit(E->getSubExpr());
192246a523285928aa07bf14803178dc04616ac85994Eli Friedman
192346a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_MemberPointerToBoolean:
192446a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_PointerToBoolean:
192546a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_IntegralToBoolean:
192646a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_FloatingToBoolean:
192746a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_FloatingComplexToBoolean:
192846a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_IntegralComplexToBoolean: {
19294efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman    bool BoolResult;
19304efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman    if (!HandleConversionToBool(SubExpr, BoolResult, Info))
19314efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman      return false;
1932131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar    return Success(BoolResult, E);
19334efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman  }
19344efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman
193546a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_IntegralCast: {
1936732b2236ae4a4f11e7642677cebbd169c07ea877Chris Lattner    if (!Visit(SubExpr))
1937b542afe02d317411d53b3541946f9f2a8f509a11Chris Lattner      return false;
1938a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar
1939be26570e3faa009bdcefedfaf04473e518940520Eli Friedman    if (!Result.isInt()) {
1940be26570e3faa009bdcefedfaf04473e518940520Eli Friedman      // Only allow casts of lvalues if they are lossless.
1941be26570e3faa009bdcefedfaf04473e518940520Eli Friedman      return Info.Ctx.getTypeSize(DestType) == Info.Ctx.getTypeSize(SrcType);
1942be26570e3faa009bdcefedfaf04473e518940520Eli Friedman    }
194330c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar
1944dd2116462ae311043986ae8b7fba27e68c1b2e66Daniel Dunbar    return Success(HandleIntToIntCast(DestType, SrcType,
194530c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar                                      Result.getInt(), Info.Ctx), E);
1946732b2236ae4a4f11e7642677cebbd169c07ea877Chris Lattner  }
19471eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
194846a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_PointerToIntegral: {
1949efdb83e26f9a1fd2566afe54461216cd84814d42John McCall    LValue LV;
195087eae5ecf94e38baa20d9a327b8f73f8bdc72436Chris Lattner    if (!EvaluatePointer(SubExpr, LV, Info))
1951b542afe02d317411d53b3541946f9f2a8f509a11Chris Lattner      return false;
19524efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman
1953dd2116462ae311043986ae8b7fba27e68c1b2e66Daniel Dunbar    if (LV.getLValueBase()) {
1954dd2116462ae311043986ae8b7fba27e68c1b2e66Daniel Dunbar      // Only allow based lvalue casts if they are lossless.
1955dd2116462ae311043986ae8b7fba27e68c1b2e66Daniel Dunbar      if (Info.Ctx.getTypeSize(DestType) != Info.Ctx.getTypeSize(SrcType))
1956dd2116462ae311043986ae8b7fba27e68c1b2e66Daniel Dunbar        return false;
1957dd2116462ae311043986ae8b7fba27e68c1b2e66Daniel Dunbar
1958efdb83e26f9a1fd2566afe54461216cd84814d42John McCall      LV.moveInto(Result);
1959dd2116462ae311043986ae8b7fba27e68c1b2e66Daniel Dunbar      return true;
1960dd2116462ae311043986ae8b7fba27e68c1b2e66Daniel Dunbar    }
19614efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman
1962a73058324197b7bdfd19307965954f626e26199dKen Dyck    APSInt AsInt = Info.Ctx.MakeIntValue(LV.getLValueOffset().getQuantity(),
1963a73058324197b7bdfd19307965954f626e26199dKen Dyck                                         SrcType);
1964dd2116462ae311043986ae8b7fba27e68c1b2e66Daniel Dunbar    return Success(HandleIntToIntCast(DestType, SrcType, AsInt, Info.Ctx), E);
19652bad1687fe6f00e10767a691a33b070b151902b6Anders Carlsson  }
19664efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman
196746a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_IntegralComplexToReal: {
1968f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall    ComplexValue C;
19691725f683432715e5afe34d476024bd6f16eac3fcEli Friedman    if (!EvaluateComplex(SubExpr, C, Info))
19701725f683432715e5afe34d476024bd6f16eac3fcEli Friedman      return false;
197146a523285928aa07bf14803178dc04616ac85994Eli Friedman    return Success(C.getComplexIntReal(), E);
19721725f683432715e5afe34d476024bd6f16eac3fcEli Friedman  }
19732217c87bdc5ab357046a5453bdb06f469c41024eEli Friedman
197446a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_FloatingToIntegral: {
197546a523285928aa07bf14803178dc04616ac85994Eli Friedman    APFloat F(0.0);
197646a523285928aa07bf14803178dc04616ac85994Eli Friedman    if (!EvaluateFloat(SubExpr, F, Info))
197746a523285928aa07bf14803178dc04616ac85994Eli Friedman      return false;
1978732b2236ae4a4f11e7642677cebbd169c07ea877Chris Lattner
197946a523285928aa07bf14803178dc04616ac85994Eli Friedman    return Success(HandleFloatToIntCast(DestType, SrcType, F, Info.Ctx), E);
198046a523285928aa07bf14803178dc04616ac85994Eli Friedman  }
198146a523285928aa07bf14803178dc04616ac85994Eli Friedman  }
19821eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
198346a523285928aa07bf14803178dc04616ac85994Eli Friedman  llvm_unreachable("unknown cast resulting in integral value");
198446a523285928aa07bf14803178dc04616ac85994Eli Friedman  return false;
1985a25ae3d68d84d2b89907f998df6a396549589da5Anders Carlsson}
19862bad1687fe6f00e10767a691a33b070b151902b6Anders Carlsson
1987722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedmanbool IntExprEvaluator::VisitUnaryReal(const UnaryOperator *E) {
1988722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman  if (E->getSubExpr()->getType()->isAnyComplexType()) {
1989f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall    ComplexValue LV;
1990722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman    if (!EvaluateComplex(E->getSubExpr(), LV, Info) || !LV.isComplexInt())
1991722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman      return Error(E->getExprLoc(), diag::note_invalid_subexpr_in_ice, E);
1992722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman    return Success(LV.getComplexIntReal(), E);
1993722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman  }
1994722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman
1995722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman  return Visit(E->getSubExpr());
1996722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman}
1997722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman
1998664a104ba0b8f47b8908ec6af694d9646adba1fcEli Friedmanbool IntExprEvaluator::VisitUnaryImag(const UnaryOperator *E) {
1999722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman  if (E->getSubExpr()->getType()->isComplexIntegerType()) {
2000f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall    ComplexValue LV;
2001722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman    if (!EvaluateComplex(E->getSubExpr(), LV, Info) || !LV.isComplexInt())
2002722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman      return Error(E->getExprLoc(), diag::note_invalid_subexpr_in_ice, E);
2003722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman    return Success(LV.getComplexIntImag(), E);
2004722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman  }
2005722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman
20068327fad71da34492d82c532f42a58cb4baff81a3Richard Smith  VisitIgnoredValue(E->getSubExpr());
2007664a104ba0b8f47b8908ec6af694d9646adba1fcEli Friedman  return Success(0, E);
2008664a104ba0b8f47b8908ec6af694d9646adba1fcEli Friedman}
2009664a104ba0b8f47b8908ec6af694d9646adba1fcEli Friedman
2010ee8aff06f6a96214731de17b2cb6df407c6c1820Douglas Gregorbool IntExprEvaluator::VisitSizeOfPackExpr(const SizeOfPackExpr *E) {
2011ee8aff06f6a96214731de17b2cb6df407c6c1820Douglas Gregor  return Success(E->getPackLength(), E);
2012ee8aff06f6a96214731de17b2cb6df407c6c1820Douglas Gregor}
2013ee8aff06f6a96214731de17b2cb6df407c6c1820Douglas Gregor
2014295995c9c3196416372c9cd35d9cedb6da37bd3dSebastian Redlbool IntExprEvaluator::VisitCXXNoexceptExpr(const CXXNoexceptExpr *E) {
2015295995c9c3196416372c9cd35d9cedb6da37bd3dSebastian Redl  return Success(E->getValue(), E);
2016295995c9c3196416372c9cd35d9cedb6da37bd3dSebastian Redl}
2017295995c9c3196416372c9cd35d9cedb6da37bd3dSebastian Redl
2018f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner//===----------------------------------------------------------------------===//
2019d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman// Float Evaluation
2020d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman//===----------------------------------------------------------------------===//
2021d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman
2022d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedmannamespace {
2023770b4a8834670e9427d3ce5a1a8472eb86f45fd2Benjamin Kramerclass FloatExprEvaluator
20248cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  : public ExprEvaluatorBase<FloatExprEvaluator, bool> {
2025d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman  APFloat &Result;
2026d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedmanpublic:
2027d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman  FloatExprEvaluator(EvalInfo &info, APFloat &result)
20288cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    : ExprEvaluatorBaseTy(info), Result(result) {}
2029d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman
20308cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool Success(const APValue &V, const Expr *e) {
20318cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    Result = V.getFloat();
20328cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    return true;
20338cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  }
20348cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool Error(const Stmt *S) {
2035d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman    return false;
2036d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman  }
2037d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman
2038f10d9171ac24380ca94c71847a9270a05b791cefRichard Smith  bool ValueInitialization(const Expr *E) {
2039f10d9171ac24380ca94c71847a9270a05b791cefRichard Smith    Result = APFloat::getZero(Info.Ctx.getFloatTypeSemantics(E->getType()));
2040f10d9171ac24380ca94c71847a9270a05b791cefRichard Smith    return true;
2041f10d9171ac24380ca94c71847a9270a05b791cefRichard Smith  }
2042f10d9171ac24380ca94c71847a9270a05b791cefRichard Smith
2043019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner  bool VisitCallExpr(const CallExpr *E);
2044d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman
20455db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar  bool VisitUnaryOperator(const UnaryOperator *E);
2046d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman  bool VisitBinaryOperator(const BinaryOperator *E);
2047d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman  bool VisitFloatingLiteral(const FloatingLiteral *E);
20488cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitCastExpr(const CastExpr *E);
20492217c87bdc5ab357046a5453bdb06f469c41024eEli Friedman
2050abd3a857ace59100305790545d1baae5877b8945John McCall  bool VisitUnaryReal(const UnaryOperator *E);
2051abd3a857ace59100305790545d1baae5877b8945John McCall  bool VisitUnaryImag(const UnaryOperator *E);
2052ba98d6bb414861965a1f22628494ea046785ecd4Eli Friedman
2053189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall  bool VisitDeclRefExpr(const DeclRefExpr *E);
2054189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall
2055abd3a857ace59100305790545d1baae5877b8945John McCall  // FIXME: Missing: array subscript of vector, member of vector,
2056abd3a857ace59100305790545d1baae5877b8945John McCall  //                 ImplicitValueInitExpr
2057d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman};
2058d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman} // end anonymous namespace
2059d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman
2060d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedmanstatic bool EvaluateFloat(const Expr* E, APFloat& Result, EvalInfo &Info) {
20617db7acbbb84b82d0522266a50ebabc3a52a9e5d1John McCall  assert(E->getType()->isRealFloatingType());
20628cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  return FloatExprEvaluator(Info, Result).Visit(E);
2063d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman}
2064d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman
20654ba2a17694148e16eaa8d3917f657ffcd3667be4Jay Foadstatic bool TryEvaluateBuiltinNaN(const ASTContext &Context,
2066db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall                                  QualType ResultTy,
2067db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall                                  const Expr *Arg,
2068db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall                                  bool SNaN,
2069db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall                                  llvm::APFloat &Result) {
2070db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall  const StringLiteral *S = dyn_cast<StringLiteral>(Arg->IgnoreParenCasts());
2071db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall  if (!S) return false;
2072db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall
2073db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall  const llvm::fltSemantics &Sem = Context.getFloatTypeSemantics(ResultTy);
2074db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall
2075db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall  llvm::APInt fill;
2076db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall
2077db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall  // Treat empty strings as if they were zero.
2078db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall  if (S->getString().empty())
2079db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall    fill = llvm::APInt(32, 0);
2080db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall  else if (S->getString().getAsInteger(0, fill))
2081db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall    return false;
2082db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall
2083db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall  if (SNaN)
2084db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall    Result = llvm::APFloat::getSNaN(Sem, false, &fill);
2085db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall  else
2086db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall    Result = llvm::APFloat::getQNaN(Sem, false, &fill);
2087db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall  return true;
2088db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall}
2089db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall
2090019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattnerbool FloatExprEvaluator::VisitCallExpr(const CallExpr *E) {
20913c385e5f8d9008fff18597ca302be19fa86e51f6Douglas Gregor  switch (E->isBuiltinCall(Info.Ctx)) {
20928cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  default:
20938cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    return ExprEvaluatorBaseTy::VisitCallExpr(E);
20948cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne
2095019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner  case Builtin::BI__builtin_huge_val:
2096019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner  case Builtin::BI__builtin_huge_valf:
2097019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner  case Builtin::BI__builtin_huge_vall:
2098019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner  case Builtin::BI__builtin_inf:
2099019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner  case Builtin::BI__builtin_inff:
21007cbed03c00e246682e5292785d01e1c120ce54bdDaniel Dunbar  case Builtin::BI__builtin_infl: {
21017cbed03c00e246682e5292785d01e1c120ce54bdDaniel Dunbar    const llvm::fltSemantics &Sem =
21027cbed03c00e246682e5292785d01e1c120ce54bdDaniel Dunbar      Info.Ctx.getFloatTypeSemantics(E->getType());
210334a74ab81600a40c6324fd76adb724b803dfaf91Chris Lattner    Result = llvm::APFloat::getInf(Sem);
210434a74ab81600a40c6324fd76adb724b803dfaf91Chris Lattner    return true;
21057cbed03c00e246682e5292785d01e1c120ce54bdDaniel Dunbar  }
21061eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
2107db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall  case Builtin::BI__builtin_nans:
2108db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall  case Builtin::BI__builtin_nansf:
2109db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall  case Builtin::BI__builtin_nansl:
2110db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall    return TryEvaluateBuiltinNaN(Info.Ctx, E->getType(), E->getArg(0),
2111db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall                                 true, Result);
2112db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall
21139e62171a25e3a08fb5c49fb370f83faf5ae786f5Chris Lattner  case Builtin::BI__builtin_nan:
21149e62171a25e3a08fb5c49fb370f83faf5ae786f5Chris Lattner  case Builtin::BI__builtin_nanf:
21159e62171a25e3a08fb5c49fb370f83faf5ae786f5Chris Lattner  case Builtin::BI__builtin_nanl:
21164572baba9d18c275968ac113fd73b0e3c77cccb8Mike Stump    // If this is __builtin_nan() turn this into a nan, otherwise we
21179e62171a25e3a08fb5c49fb370f83faf5ae786f5Chris Lattner    // can't constant fold it.
2118db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall    return TryEvaluateBuiltinNaN(Info.Ctx, E->getType(), E->getArg(0),
2119db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall                                 false, Result);
21205db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar
21215db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar  case Builtin::BI__builtin_fabs:
21225db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar  case Builtin::BI__builtin_fabsf:
21235db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar  case Builtin::BI__builtin_fabsl:
21245db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar    if (!EvaluateFloat(E->getArg(0), Result, Info))
21255db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar      return false;
21261eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
21275db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar    if (Result.isNegative())
21285db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar      Result.changeSign();
21295db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar    return true;
21305db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar
21311eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump  case Builtin::BI__builtin_copysign:
21321eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump  case Builtin::BI__builtin_copysignf:
21335db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar  case Builtin::BI__builtin_copysignl: {
21345db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar    APFloat RHS(0.);
21355db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar    if (!EvaluateFloat(E->getArg(0), Result, Info) ||
21365db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar        !EvaluateFloat(E->getArg(1), RHS, Info))
21375db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar      return false;
21385db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar    Result.copySign(RHS);
21395db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar    return true;
21405db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar  }
2141019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner  }
2142019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner}
2143019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner
2144189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCallbool FloatExprEvaluator::VisitDeclRefExpr(const DeclRefExpr *E) {
21458cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  if (ExprEvaluatorBaseTy::VisitDeclRefExpr(E))
21468cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    return true;
21478cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne
214803f96110bc2c2c773e06a42982b17a03dd2e5379Richard Smith  const VarDecl *VD = dyn_cast<VarDecl>(E->getDecl());
214903f96110bc2c2c773e06a42982b17a03dd2e5379Richard Smith  if (VD && IsConstNonVolatile(VD->getType())) {
215003f96110bc2c2c773e06a42982b17a03dd2e5379Richard Smith    APValue *V = EvaluateVarDeclInit(Info, VD);
215103f96110bc2c2c773e06a42982b17a03dd2e5379Richard Smith    if (V && V->isFloat()) {
2152189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall      Result = V->getFloat();
2153189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall      return true;
2154189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall    }
2155189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall  }
2156189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall  return false;
2157189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall}
2158189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall
2159abd3a857ace59100305790545d1baae5877b8945John McCallbool FloatExprEvaluator::VisitUnaryReal(const UnaryOperator *E) {
216043efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman  if (E->getSubExpr()->getType()->isAnyComplexType()) {
216143efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman    ComplexValue CV;
216243efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman    if (!EvaluateComplex(E->getSubExpr(), CV, Info))
216343efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman      return false;
216443efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman    Result = CV.FloatReal;
216543efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman    return true;
216643efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman  }
216743efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman
216843efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman  return Visit(E->getSubExpr());
2169abd3a857ace59100305790545d1baae5877b8945John McCall}
2170abd3a857ace59100305790545d1baae5877b8945John McCall
2171abd3a857ace59100305790545d1baae5877b8945John McCallbool FloatExprEvaluator::VisitUnaryImag(const UnaryOperator *E) {
217243efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman  if (E->getSubExpr()->getType()->isAnyComplexType()) {
217343efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman    ComplexValue CV;
217443efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman    if (!EvaluateComplex(E->getSubExpr(), CV, Info))
217543efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman      return false;
217643efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman    Result = CV.FloatImag;
217743efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman    return true;
217843efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman  }
217943efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman
21808327fad71da34492d82c532f42a58cb4baff81a3Richard Smith  VisitIgnoredValue(E->getSubExpr());
218143efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman  const llvm::fltSemantics &Sem = Info.Ctx.getFloatTypeSemantics(E->getType());
218243efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman  Result = llvm::APFloat::getZero(Sem);
2183abd3a857ace59100305790545d1baae5877b8945John McCall  return true;
2184abd3a857ace59100305790545d1baae5877b8945John McCall}
2185abd3a857ace59100305790545d1baae5877b8945John McCall
21865db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbarbool FloatExprEvaluator::VisitUnaryOperator(const UnaryOperator *E) {
21872de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall  if (E->getOpcode() == UO_Deref)
2188a468d34bed16861f25aff6c8354f4e75d3358c1aNuno Lopes    return false;
2189a468d34bed16861f25aff6c8354f4e75d3358c1aNuno Lopes
21905db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar  if (!EvaluateFloat(E->getSubExpr(), Result, Info))
21915db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar    return false;
21925db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar
21935db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar  switch (E->getOpcode()) {
21945db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar  default: return false;
21952de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall  case UO_Plus:
21965db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar    return true;
21972de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall  case UO_Minus:
21985db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar    Result.changeSign();
21995db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar    return true;
22005db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar  }
22015db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar}
2202019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner
2203d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedmanbool FloatExprEvaluator::VisitBinaryOperator(const BinaryOperator *E) {
22042de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall  if (E->getOpcode() == BO_Comma) {
22058327fad71da34492d82c532f42a58cb4baff81a3Richard Smith    VisitIgnoredValue(E->getLHS());
22068327fad71da34492d82c532f42a58cb4baff81a3Richard Smith    return Visit(E->getRHS());
22077f92f0362ef2cf218bc19bb83e1a97dd254b5527Eli Friedman  }
22087f92f0362ef2cf218bc19bb83e1a97dd254b5527Eli Friedman
220996e93660124c8028a4c3bcc038ab0cdd18cd7ab2Anders Carlsson  // We can't evaluate pointer-to-member operations.
221096e93660124c8028a4c3bcc038ab0cdd18cd7ab2Anders Carlsson  if (E->isPtrMemOp())
221196e93660124c8028a4c3bcc038ab0cdd18cd7ab2Anders Carlsson    return false;
221296e93660124c8028a4c3bcc038ab0cdd18cd7ab2Anders Carlsson
2213d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman  // FIXME: Diagnostics?  I really don't understand how the warnings
2214d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman  // and errors are supposed to work.
22155db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar  APFloat RHS(0.0);
2216d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman  if (!EvaluateFloat(E->getLHS(), Result, Info))
2217d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman    return false;
2218d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman  if (!EvaluateFloat(E->getRHS(), RHS, Info))
2219d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman    return false;
2220d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman
2221d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman  switch (E->getOpcode()) {
2222d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman  default: return false;
22232de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall  case BO_Mul:
2224d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman    Result.multiply(RHS, APFloat::rmNearestTiesToEven);
2225d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman    return true;
22262de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall  case BO_Add:
2227d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman    Result.add(RHS, APFloat::rmNearestTiesToEven);
2228d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman    return true;
22292de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall  case BO_Sub:
2230d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman    Result.subtract(RHS, APFloat::rmNearestTiesToEven);
2231d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman    return true;
22322de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall  case BO_Div:
2233d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman    Result.divide(RHS, APFloat::rmNearestTiesToEven);
2234d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman    return true;
2235d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman  }
2236d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman}
2237d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman
2238d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedmanbool FloatExprEvaluator::VisitFloatingLiteral(const FloatingLiteral *E) {
2239d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman  Result = E->getValue();
2240d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman  return true;
2241d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman}
2242d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman
22438cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbournebool FloatExprEvaluator::VisitCastExpr(const CastExpr *E) {
22448cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  const Expr* SubExpr = E->getSubExpr();
22451eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
22462a523eec6a31955be876625819b89e8dc5def707Eli Friedman  switch (E->getCastKind()) {
22472a523eec6a31955be876625819b89e8dc5def707Eli Friedman  default:
22482a523eec6a31955be876625819b89e8dc5def707Eli Friedman    return false;
22492a523eec6a31955be876625819b89e8dc5def707Eli Friedman
22502a523eec6a31955be876625819b89e8dc5def707Eli Friedman  case CK_LValueToRValue:
22512a523eec6a31955be876625819b89e8dc5def707Eli Friedman  case CK_NoOp:
22522a523eec6a31955be876625819b89e8dc5def707Eli Friedman    return Visit(SubExpr);
22532a523eec6a31955be876625819b89e8dc5def707Eli Friedman
22542a523eec6a31955be876625819b89e8dc5def707Eli Friedman  case CK_IntegralToFloating: {
22554efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman    APSInt IntResult;
22563f7d995390009fede92b333a040da80e1ce90997Daniel Dunbar    if (!EvaluateInteger(SubExpr, IntResult, Info))
22574efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman      return false;
22581eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump    Result = HandleIntToFloatCast(E->getType(), SubExpr->getType(),
2259a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar                                  IntResult, Info.Ctx);
22604efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman    return true;
22614efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman  }
22622a523eec6a31955be876625819b89e8dc5def707Eli Friedman
22632a523eec6a31955be876625819b89e8dc5def707Eli Friedman  case CK_FloatingCast: {
22644efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman    if (!Visit(SubExpr))
22654efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman      return false;
2266a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar    Result = HandleFloatToFloatCast(E->getType(), SubExpr->getType(),
2267a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar                                    Result, Info.Ctx);
22684efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman    return true;
22694efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman  }
2270f3ea8cfe6b1c2ef0702efe130561e9e66708d799John McCall
22712a523eec6a31955be876625819b89e8dc5def707Eli Friedman  case CK_FloatingComplexToReal: {
2272f3ea8cfe6b1c2ef0702efe130561e9e66708d799John McCall    ComplexValue V;
2273f3ea8cfe6b1c2ef0702efe130561e9e66708d799John McCall    if (!EvaluateComplex(SubExpr, V, Info))
2274f3ea8cfe6b1c2ef0702efe130561e9e66708d799John McCall      return false;
2275f3ea8cfe6b1c2ef0702efe130561e9e66708d799John McCall    Result = V.getComplexFloatReal();
2276f3ea8cfe6b1c2ef0702efe130561e9e66708d799John McCall    return true;
2277f3ea8cfe6b1c2ef0702efe130561e9e66708d799John McCall  }
22782a523eec6a31955be876625819b89e8dc5def707Eli Friedman  }
22794efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman
22804efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman  return false;
22814efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman}
22824efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman
2283d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman//===----------------------------------------------------------------------===//
2284a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar// Complex Evaluation (for float and integer)
22859ad16aebc0e840a5e7d425da72eb6cbe25e4b58cAnders Carlsson//===----------------------------------------------------------------------===//
22869ad16aebc0e840a5e7d425da72eb6cbe25e4b58cAnders Carlsson
22879ad16aebc0e840a5e7d425da72eb6cbe25e4b58cAnders Carlssonnamespace {
2288770b4a8834670e9427d3ce5a1a8472eb86f45fd2Benjamin Kramerclass ComplexExprEvaluator
22898cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  : public ExprEvaluatorBase<ComplexExprEvaluator, bool> {
2290f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall  ComplexValue &Result;
22911eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
22929ad16aebc0e840a5e7d425da72eb6cbe25e4b58cAnders Carlssonpublic:
2293f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall  ComplexExprEvaluator(EvalInfo &info, ComplexValue &Result)
22948cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    : ExprEvaluatorBaseTy(info), Result(Result) {}
22951eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
22968cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool Success(const APValue &V, const Expr *e) {
22978cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    Result.setFrom(V);
22988cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne    return true;
22998cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  }
23008cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool Error(const Expr *E) {
2301f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall    return false;
23029ad16aebc0e840a5e7d425da72eb6cbe25e4b58cAnders Carlsson  }
23031eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
23048cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  //===--------------------------------------------------------------------===//
23058cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  //                            Visitor Methods
23068cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  //===--------------------------------------------------------------------===//
23079ad16aebc0e840a5e7d425da72eb6cbe25e4b58cAnders Carlsson
23088cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitImaginaryLiteral(const ImaginaryLiteral *E);
2309a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar
23108cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  bool VisitCastExpr(const CastExpr *E);
2311b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman
2312b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman  bool VisitBinaryOperator(const BinaryOperator *E);
231396fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara  bool VisitUnaryOperator(const UnaryOperator *E);
2314cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl  // FIXME Missing: ImplicitValueInitExpr, InitListExpr
2315b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman};
2316b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman} // end anonymous namespace
23171eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
2318b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedmanstatic bool EvaluateComplex(const Expr *E, ComplexValue &Result,
2319b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman                            EvalInfo &Info) {
2320b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman  assert(E->getType()->isAnyComplexType());
23218cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  return ComplexExprEvaluator(Info, Result).Visit(E);
2322b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman}
2323b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman
23248cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbournebool ComplexExprEvaluator::VisitImaginaryLiteral(const ImaginaryLiteral *E) {
23258cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne  const Expr* SubExpr = E->getSubExpr();
2326b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman
2327b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman  if (SubExpr->getType()->isRealFloatingType()) {
2328b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman    Result.makeComplexFloat();
2329b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman    APFloat &Imag = Result.FloatImag;
2330b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman    if (!EvaluateFloat(SubExpr, Imag, Info))
2331b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman      return false;
2332b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman
2333b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman    Result.FloatReal = APFloat(Imag.getSemantics());
2334b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman    return true;
2335b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman  } else {
2336b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman    assert(SubExpr->getType()->isIntegerType() &&
2337b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman           "Unexpected imaginary literal.");
2338b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman
2339b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman    Result.makeComplexInt();
2340b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman    APSInt &Imag = Result.IntImag;
2341b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman    if (!EvaluateInteger(SubExpr, Imag, Info))
2342b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman      return false;
2343b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman
2344b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman    Result.IntReal = APSInt(Imag.getBitWidth(), !Imag.isSigned());
2345b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman    return true;
2346b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman  }
2347b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman}
2348b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman
23498cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbournebool ComplexExprEvaluator::VisitCastExpr(const CastExpr *E) {
2350b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman
23518786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  switch (E->getCastKind()) {
23528786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  case CK_BitCast:
23538786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  case CK_BaseToDerived:
23548786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  case CK_DerivedToBase:
23558786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  case CK_UncheckedDerivedToBase:
23568786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  case CK_Dynamic:
23578786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  case CK_ToUnion:
23588786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  case CK_ArrayToPointerDecay:
23598786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  case CK_FunctionToPointerDecay:
23608786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  case CK_NullToPointer:
23618786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  case CK_NullToMemberPointer:
23628786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  case CK_BaseToDerivedMemberPointer:
23638786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  case CK_DerivedToBaseMemberPointer:
23648786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  case CK_MemberPointerToBoolean:
23658786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  case CK_ConstructorConversion:
23668786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  case CK_IntegralToPointer:
23678786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  case CK_PointerToIntegral:
23688786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  case CK_PointerToBoolean:
23698786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  case CK_ToVoid:
23708786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  case CK_VectorSplat:
23718786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  case CK_IntegralCast:
23728786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  case CK_IntegralToBoolean:
23738786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  case CK_IntegralToFloating:
23748786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  case CK_FloatingToIntegral:
23758786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  case CK_FloatingToBoolean:
23768786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  case CK_FloatingCast:
23771d9b3b25f7ac0d0195bba6b507a684fe5e7943eeJohn McCall  case CK_CPointerToObjCPointerCast:
23781d9b3b25f7ac0d0195bba6b507a684fe5e7943eeJohn McCall  case CK_BlockPointerToObjCPointerCast:
23798786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  case CK_AnyPointerToBlockPointerCast:
23808786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  case CK_ObjCObjectLValueCast:
23818786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  case CK_FloatingComplexToReal:
23828786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  case CK_FloatingComplexToBoolean:
23838786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  case CK_IntegralComplexToReal:
23848786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  case CK_IntegralComplexToBoolean:
238533e56f3273457bfa22c7c50bc46cf5a18216863dJohn McCall  case CK_ARCProduceObject:
238633e56f3273457bfa22c7c50bc46cf5a18216863dJohn McCall  case CK_ARCConsumeObject:
238733e56f3273457bfa22c7c50bc46cf5a18216863dJohn McCall  case CK_ARCReclaimReturnedObject:
238833e56f3273457bfa22c7c50bc46cf5a18216863dJohn McCall  case CK_ARCExtendBlockObject:
23898786da77984e81d48e0e1b2bd339809b1efc19f3John McCall    llvm_unreachable("invalid cast kind for complex value");
23908786da77984e81d48e0e1b2bd339809b1efc19f3John McCall
23918786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  case CK_LValueToRValue:
23928786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  case CK_NoOp:
23938786da77984e81d48e0e1b2bd339809b1efc19f3John McCall    return Visit(E->getSubExpr());
23942bb5d00fcf71a7b4d478d478be778fff0494aff6John McCall
23958786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  case CK_Dependent:
23968786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  case CK_GetObjCProperty:
239746a523285928aa07bf14803178dc04616ac85994Eli Friedman  case CK_LValueBitCast:
23988786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  case CK_UserDefinedConversion:
23998786da77984e81d48e0e1b2bd339809b1efc19f3John McCall    return false;
24008786da77984e81d48e0e1b2bd339809b1efc19f3John McCall
24018786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  case CK_FloatingRealToComplex: {
2402b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman    APFloat &Real = Result.FloatReal;
24038786da77984e81d48e0e1b2bd339809b1efc19f3John McCall    if (!EvaluateFloat(E->getSubExpr(), Real, Info))
2404b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman      return false;
2405b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman
24068786da77984e81d48e0e1b2bd339809b1efc19f3John McCall    Result.makeComplexFloat();
24078786da77984e81d48e0e1b2bd339809b1efc19f3John McCall    Result.FloatImag = APFloat(Real.getSemantics());
24088786da77984e81d48e0e1b2bd339809b1efc19f3John McCall    return true;
24098786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  }
24108786da77984e81d48e0e1b2bd339809b1efc19f3John McCall
24118786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  case CK_FloatingComplexCast: {
24128786da77984e81d48e0e1b2bd339809b1efc19f3John McCall    if (!Visit(E->getSubExpr()))
24138786da77984e81d48e0e1b2bd339809b1efc19f3John McCall      return false;
24148786da77984e81d48e0e1b2bd339809b1efc19f3John McCall
24158786da77984e81d48e0e1b2bd339809b1efc19f3John McCall    QualType To = E->getType()->getAs<ComplexType>()->getElementType();
24168786da77984e81d48e0e1b2bd339809b1efc19f3John McCall    QualType From
24178786da77984e81d48e0e1b2bd339809b1efc19f3John McCall      = E->getSubExpr()->getType()->getAs<ComplexType>()->getElementType();
24188786da77984e81d48e0e1b2bd339809b1efc19f3John McCall
24198786da77984e81d48e0e1b2bd339809b1efc19f3John McCall    Result.FloatReal
24208786da77984e81d48e0e1b2bd339809b1efc19f3John McCall      = HandleFloatToFloatCast(To, From, Result.FloatReal, Info.Ctx);
24218786da77984e81d48e0e1b2bd339809b1efc19f3John McCall    Result.FloatImag
24228786da77984e81d48e0e1b2bd339809b1efc19f3John McCall      = HandleFloatToFloatCast(To, From, Result.FloatImag, Info.Ctx);
24238786da77984e81d48e0e1b2bd339809b1efc19f3John McCall    return true;
24248786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  }
24258786da77984e81d48e0e1b2bd339809b1efc19f3John McCall
24268786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  case CK_FloatingComplexToIntegralComplex: {
24278786da77984e81d48e0e1b2bd339809b1efc19f3John McCall    if (!Visit(E->getSubExpr()))
24288786da77984e81d48e0e1b2bd339809b1efc19f3John McCall      return false;
24298786da77984e81d48e0e1b2bd339809b1efc19f3John McCall
24308786da77984e81d48e0e1b2bd339809b1efc19f3John McCall    QualType To = E->getType()->getAs<ComplexType>()->getElementType();
24318786da77984e81d48e0e1b2bd339809b1efc19f3John McCall    QualType From
24328786da77984e81d48e0e1b2bd339809b1efc19f3John McCall      = E->getSubExpr()->getType()->getAs<ComplexType>()->getElementType();
24338786da77984e81d48e0e1b2bd339809b1efc19f3John McCall    Result.makeComplexInt();
24348786da77984e81d48e0e1b2bd339809b1efc19f3John McCall    Result.IntReal = HandleFloatToIntCast(To, From, Result.FloatReal, Info.Ctx);
24358786da77984e81d48e0e1b2bd339809b1efc19f3John McCall    Result.IntImag = HandleFloatToIntCast(To, From, Result.FloatImag, Info.Ctx);
24368786da77984e81d48e0e1b2bd339809b1efc19f3John McCall    return true;
24378786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  }
24388786da77984e81d48e0e1b2bd339809b1efc19f3John McCall
24398786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  case CK_IntegralRealToComplex: {
2440b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman    APSInt &Real = Result.IntReal;
24418786da77984e81d48e0e1b2bd339809b1efc19f3John McCall    if (!EvaluateInteger(E->getSubExpr(), Real, Info))
2442b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman      return false;
24439ad16aebc0e840a5e7d425da72eb6cbe25e4b58cAnders Carlsson
24448786da77984e81d48e0e1b2bd339809b1efc19f3John McCall    Result.makeComplexInt();
24458786da77984e81d48e0e1b2bd339809b1efc19f3John McCall    Result.IntImag = APSInt(Real.getBitWidth(), !Real.isSigned());
24468786da77984e81d48e0e1b2bd339809b1efc19f3John McCall    return true;
24478786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  }
24488786da77984e81d48e0e1b2bd339809b1efc19f3John McCall
24498786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  case CK_IntegralComplexCast: {
24508786da77984e81d48e0e1b2bd339809b1efc19f3John McCall    if (!Visit(E->getSubExpr()))
2451b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman      return false;
2452ccc3fce5697e33f005990f9795e1c7cb8b4559ecAnders Carlsson
24538786da77984e81d48e0e1b2bd339809b1efc19f3John McCall    QualType To = E->getType()->getAs<ComplexType>()->getElementType();
24548786da77984e81d48e0e1b2bd339809b1efc19f3John McCall    QualType From
24558786da77984e81d48e0e1b2bd339809b1efc19f3John McCall      = E->getSubExpr()->getType()->getAs<ComplexType>()->getElementType();
24561725f683432715e5afe34d476024bd6f16eac3fcEli Friedman
24578786da77984e81d48e0e1b2bd339809b1efc19f3John McCall    Result.IntReal = HandleIntToIntCast(To, From, Result.IntReal, Info.Ctx);
24588786da77984e81d48e0e1b2bd339809b1efc19f3John McCall    Result.IntImag = HandleIntToIntCast(To, From, Result.IntImag, Info.Ctx);
24598786da77984e81d48e0e1b2bd339809b1efc19f3John McCall    return true;
24608786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  }
24618786da77984e81d48e0e1b2bd339809b1efc19f3John McCall
24628786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  case CK_IntegralComplexToFloatingComplex: {
24638786da77984e81d48e0e1b2bd339809b1efc19f3John McCall    if (!Visit(E->getSubExpr()))
24648786da77984e81d48e0e1b2bd339809b1efc19f3John McCall      return false;
24658786da77984e81d48e0e1b2bd339809b1efc19f3John McCall
24668786da77984e81d48e0e1b2bd339809b1efc19f3John McCall    QualType To = E->getType()->getAs<ComplexType>()->getElementType();
24678786da77984e81d48e0e1b2bd339809b1efc19f3John McCall    QualType From
24688786da77984e81d48e0e1b2bd339809b1efc19f3John McCall      = E->getSubExpr()->getType()->getAs<ComplexType>()->getElementType();
24698786da77984e81d48e0e1b2bd339809b1efc19f3John McCall    Result.makeComplexFloat();
24708786da77984e81d48e0e1b2bd339809b1efc19f3John McCall    Result.FloatReal = HandleIntToFloatCast(To, From, Result.IntReal, Info.Ctx);
24718786da77984e81d48e0e1b2bd339809b1efc19f3John McCall    Result.FloatImag = HandleIntToFloatCast(To, From, Result.IntImag, Info.Ctx);
24728786da77984e81d48e0e1b2bd339809b1efc19f3John McCall    return true;
24738786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  }
2474ccc3fce5697e33f005990f9795e1c7cb8b4559ecAnders Carlsson  }
24751eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
24768786da77984e81d48e0e1b2bd339809b1efc19f3John McCall  llvm_unreachable("unknown cast resulting in complex value");
2477b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman  return false;
24789ad16aebc0e840a5e7d425da72eb6cbe25e4b58cAnders Carlsson}
24799ad16aebc0e840a5e7d425da72eb6cbe25e4b58cAnders Carlsson
2480f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCallbool ComplexExprEvaluator::VisitBinaryOperator(const BinaryOperator *E) {
248196fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara  if (E->getOpcode() == BO_Comma) {
24828327fad71da34492d82c532f42a58cb4baff81a3Richard Smith    VisitIgnoredValue(E->getLHS());
24838327fad71da34492d82c532f42a58cb4baff81a3Richard Smith    return Visit(E->getRHS());
248496fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara  }
2485f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall  if (!Visit(E->getLHS()))
2486f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall    return false;
24871eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
2488f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall  ComplexValue RHS;
2489a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar  if (!EvaluateComplex(E->getRHS(), RHS, Info))
2490f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall    return false;
2491a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar
24923f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar  assert(Result.isComplexFloat() == RHS.isComplexFloat() &&
24933f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar         "Invalid operands to binary operator.");
2494ccc3fce5697e33f005990f9795e1c7cb8b4559ecAnders Carlsson  switch (E->getOpcode()) {
2495f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall  default: return false;
24962de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall  case BO_Add:
2497a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar    if (Result.isComplexFloat()) {
2498a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar      Result.getComplexFloatReal().add(RHS.getComplexFloatReal(),
2499a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar                                       APFloat::rmNearestTiesToEven);
2500a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar      Result.getComplexFloatImag().add(RHS.getComplexFloatImag(),
2501a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar                                       APFloat::rmNearestTiesToEven);
2502a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar    } else {
2503a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar      Result.getComplexIntReal() += RHS.getComplexIntReal();
2504a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar      Result.getComplexIntImag() += RHS.getComplexIntImag();
2505a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar    }
25063f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar    break;
25072de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall  case BO_Sub:
2508a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar    if (Result.isComplexFloat()) {
2509a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar      Result.getComplexFloatReal().subtract(RHS.getComplexFloatReal(),
2510a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar                                            APFloat::rmNearestTiesToEven);
2511a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar      Result.getComplexFloatImag().subtract(RHS.getComplexFloatImag(),
2512a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar                                            APFloat::rmNearestTiesToEven);
2513a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar    } else {
2514a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar      Result.getComplexIntReal() -= RHS.getComplexIntReal();
2515a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar      Result.getComplexIntImag() -= RHS.getComplexIntImag();
2516a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar    }
25173f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar    break;
25182de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall  case BO_Mul:
25193f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar    if (Result.isComplexFloat()) {
2520f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall      ComplexValue LHS = Result;
25213f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar      APFloat &LHS_r = LHS.getComplexFloatReal();
25223f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar      APFloat &LHS_i = LHS.getComplexFloatImag();
25233f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar      APFloat &RHS_r = RHS.getComplexFloatReal();
25243f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar      APFloat &RHS_i = RHS.getComplexFloatImag();
25251eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
25263f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar      APFloat Tmp = LHS_r;
25273f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar      Tmp.multiply(RHS_r, APFloat::rmNearestTiesToEven);
25283f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar      Result.getComplexFloatReal() = Tmp;
25293f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar      Tmp = LHS_i;
25303f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar      Tmp.multiply(RHS_i, APFloat::rmNearestTiesToEven);
25313f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar      Result.getComplexFloatReal().subtract(Tmp, APFloat::rmNearestTiesToEven);
25323f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar
25333f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar      Tmp = LHS_r;
25343f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar      Tmp.multiply(RHS_i, APFloat::rmNearestTiesToEven);
25353f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar      Result.getComplexFloatImag() = Tmp;
25363f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar      Tmp = LHS_i;
25373f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar      Tmp.multiply(RHS_r, APFloat::rmNearestTiesToEven);
25383f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar      Result.getComplexFloatImag().add(Tmp, APFloat::rmNearestTiesToEven);
25393f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar    } else {
2540f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall      ComplexValue LHS = Result;
25411eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump      Result.getComplexIntReal() =
25423f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar        (LHS.getComplexIntReal() * RHS.getComplexIntReal() -
25433f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar         LHS.getComplexIntImag() * RHS.getComplexIntImag());
25441eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump      Result.getComplexIntImag() =
25453f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar        (LHS.getComplexIntReal() * RHS.getComplexIntImag() +
25463f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar         LHS.getComplexIntImag() * RHS.getComplexIntReal());
25473f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar    }
25483f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar    break;
254996fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara  case BO_Div:
255096fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara    if (Result.isComplexFloat()) {
255196fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara      ComplexValue LHS = Result;
255296fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara      APFloat &LHS_r = LHS.getComplexFloatReal();
255396fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara      APFloat &LHS_i = LHS.getComplexFloatImag();
255496fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara      APFloat &RHS_r = RHS.getComplexFloatReal();
255596fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara      APFloat &RHS_i = RHS.getComplexFloatImag();
255696fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara      APFloat &Res_r = Result.getComplexFloatReal();
255796fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara      APFloat &Res_i = Result.getComplexFloatImag();
255896fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara
255996fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara      APFloat Den = RHS_r;
256096fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara      Den.multiply(RHS_r, APFloat::rmNearestTiesToEven);
256196fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara      APFloat Tmp = RHS_i;
256296fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara      Tmp.multiply(RHS_i, APFloat::rmNearestTiesToEven);
256396fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara      Den.add(Tmp, APFloat::rmNearestTiesToEven);
256496fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara
256596fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara      Res_r = LHS_r;
256696fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara      Res_r.multiply(RHS_r, APFloat::rmNearestTiesToEven);
256796fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara      Tmp = LHS_i;
256896fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara      Tmp.multiply(RHS_i, APFloat::rmNearestTiesToEven);
256996fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara      Res_r.add(Tmp, APFloat::rmNearestTiesToEven);
257096fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara      Res_r.divide(Den, APFloat::rmNearestTiesToEven);
257196fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara
257296fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara      Res_i = LHS_i;
257396fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara      Res_i.multiply(RHS_r, APFloat::rmNearestTiesToEven);
257496fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara      Tmp = LHS_r;
257596fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara      Tmp.multiply(RHS_i, APFloat::rmNearestTiesToEven);
257696fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara      Res_i.subtract(Tmp, APFloat::rmNearestTiesToEven);
257796fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara      Res_i.divide(Den, APFloat::rmNearestTiesToEven);
257896fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara    } else {
257996fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara      if (RHS.getComplexIntReal() == 0 && RHS.getComplexIntImag() == 0) {
258096fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara        // FIXME: what about diagnostics?
258196fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara        return false;
258296fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara      }
258396fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara      ComplexValue LHS = Result;
258496fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara      APSInt Den = RHS.getComplexIntReal() * RHS.getComplexIntReal() +
258596fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara        RHS.getComplexIntImag() * RHS.getComplexIntImag();
258696fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara      Result.getComplexIntReal() =
258796fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara        (LHS.getComplexIntReal() * RHS.getComplexIntReal() +
258896fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara         LHS.getComplexIntImag() * RHS.getComplexIntImag()) / Den;
258996fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara      Result.getComplexIntImag() =
259096fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara        (LHS.getComplexIntImag() * RHS.getComplexIntReal() -
259196fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara         LHS.getComplexIntReal() * RHS.getComplexIntImag()) / Den;
259296fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara    }
259396fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara    break;
2594ccc3fce5697e33f005990f9795e1c7cb8b4559ecAnders Carlsson  }
2595ccc3fce5697e33f005990f9795e1c7cb8b4559ecAnders Carlsson
2596f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall  return true;
2597ccc3fce5697e33f005990f9795e1c7cb8b4559ecAnders Carlsson}
2598ccc3fce5697e33f005990f9795e1c7cb8b4559ecAnders Carlsson
259996fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnarabool ComplexExprEvaluator::VisitUnaryOperator(const UnaryOperator *E) {
260096fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara  // Get the operand value into 'Result'.
260196fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara  if (!Visit(E->getSubExpr()))
260296fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara    return false;
260396fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara
260496fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara  switch (E->getOpcode()) {
260596fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara  default:
260696fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara    // FIXME: what about diagnostics?
260796fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara    return false;
260896fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara  case UO_Extension:
260996fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara    return true;
261096fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara  case UO_Plus:
261196fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara    // The result is always just the subexpr.
261296fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara    return true;
261396fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara  case UO_Minus:
261496fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara    if (Result.isComplexFloat()) {
261596fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara      Result.getComplexFloatReal().changeSign();
261696fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara      Result.getComplexFloatImag().changeSign();
261796fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara    }
261896fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara    else {
261996fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara      Result.getComplexIntReal() = -Result.getComplexIntReal();
262096fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara      Result.getComplexIntImag() = -Result.getComplexIntImag();
262196fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara    }
262296fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara    return true;
262396fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara  case UO_Not:
262496fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara    if (Result.isComplexFloat())
262596fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara      Result.getComplexFloatImag().changeSign();
262696fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara    else
262796fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara      Result.getComplexIntImag() = -Result.getComplexIntImag();
262896fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara    return true;
262996fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara  }
263096fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara}
263196fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara
26329ad16aebc0e840a5e7d425da72eb6cbe25e4b58cAnders Carlsson//===----------------------------------------------------------------------===//
26336ee7aa154e8bbb21a21254293410b944f78b0bfeChris Lattner// Top level Expr::Evaluate method.
2634f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner//===----------------------------------------------------------------------===//
2635f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner
26361e12c59e8f9bb76c23628c4e0d0a1dfced0b1fa0Richard Smithstatic bool Evaluate(APValue &Result, EvalInfo &Info, const Expr *E) {
2637efdb83e26f9a1fd2566afe54461216cd84814d42John McCall  if (E->getType()->isVectorType()) {
26381e12c59e8f9bb76c23628c4e0d0a1dfced0b1fa0Richard Smith    if (!EvaluateVector(E, Result, Info))
263959b5da6d853b4368b984700315adf7b37de05764Nate Begeman      return false;
2640575a1c9dc8dc5b4977194993e289f9eda7295c39Douglas Gregor  } else if (E->getType()->isIntegralOrEnumerationType()) {
26411e12c59e8f9bb76c23628c4e0d0a1dfced0b1fa0Richard Smith    if (!IntExprEvaluator(Info, Result).Visit(E))
26426dde0d5dc09f45f4d9508c964703e36fef1a0198Anders Carlsson      return false;
26431e12c59e8f9bb76c23628c4e0d0a1dfced0b1fa0Richard Smith    if (Result.isLValue() &&
26441e12c59e8f9bb76c23628c4e0d0a1dfced0b1fa0Richard Smith        !IsGlobalLValue(Result.getLValueBase()))
26450f2b692bb10be35fdc60d0a72a847bdd73124670John McCall      return false;
2646efdb83e26f9a1fd2566afe54461216cd84814d42John McCall  } else if (E->getType()->hasPointerRepresentation()) {
2647efdb83e26f9a1fd2566afe54461216cd84814d42John McCall    LValue LV;
2648efdb83e26f9a1fd2566afe54461216cd84814d42John McCall    if (!EvaluatePointer(E, LV, Info))
26496dde0d5dc09f45f4d9508c964703e36fef1a0198Anders Carlsson      return false;
2650e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara    if (!IsGlobalLValue(LV.Base))
265142c8f87eb60958170c46767273bf93e6c96125bfJohn McCall      return false;
26521e12c59e8f9bb76c23628c4e0d0a1dfced0b1fa0Richard Smith    LV.moveInto(Result);
2653efdb83e26f9a1fd2566afe54461216cd84814d42John McCall  } else if (E->getType()->isRealFloatingType()) {
2654efdb83e26f9a1fd2566afe54461216cd84814d42John McCall    llvm::APFloat F(0.0);
2655efdb83e26f9a1fd2566afe54461216cd84814d42John McCall    if (!EvaluateFloat(E, F, Info))
26566dde0d5dc09f45f4d9508c964703e36fef1a0198Anders Carlsson      return false;
26571eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
26581e12c59e8f9bb76c23628c4e0d0a1dfced0b1fa0Richard Smith    Result = APValue(F);
2659efdb83e26f9a1fd2566afe54461216cd84814d42John McCall  } else if (E->getType()->isAnyComplexType()) {
2660efdb83e26f9a1fd2566afe54461216cd84814d42John McCall    ComplexValue C;
2661efdb83e26f9a1fd2566afe54461216cd84814d42John McCall    if (!EvaluateComplex(E, C, Info))
2662660e6f79a138a30a437c02142f23e7ef4eb21b2eMike Stump      return false;
26631e12c59e8f9bb76c23628c4e0d0a1dfced0b1fa0Richard Smith    C.moveInto(Result);
2664660e6f79a138a30a437c02142f23e7ef4eb21b2eMike Stump  } else
2665660e6f79a138a30a437c02142f23e7ef4eb21b2eMike Stump    return false;
2666660e6f79a138a30a437c02142f23e7ef4eb21b2eMike Stump
2667660e6f79a138a30a437c02142f23e7ef4eb21b2eMike Stump  return true;
2668660e6f79a138a30a437c02142f23e7ef4eb21b2eMike Stump}
2669660e6f79a138a30a437c02142f23e7ef4eb21b2eMike Stump
267056ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall/// Evaluate - Return true if this is a constant which we can fold using
267156ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall/// any crazy technique (that has nothing to do with language standards) that
267256ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall/// we want to.  If this function returns true, it returns the folded constant
267356ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall/// in Result.
267456ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCallbool Expr::Evaluate(EvalResult &Result, const ASTContext &Ctx) const {
267556ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall  EvalInfo Info(Ctx, Result);
26761e12c59e8f9bb76c23628c4e0d0a1dfced0b1fa0Richard Smith  return ::Evaluate(Result.Val, Info, this);
267756ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall}
267856ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall
26794ba2a17694148e16eaa8d3917f657ffcd3667be4Jay Foadbool Expr::EvaluateAsBooleanCondition(bool &Result,
26804ba2a17694148e16eaa8d3917f657ffcd3667be4Jay Foad                                      const ASTContext &Ctx) const {
26811e12c59e8f9bb76c23628c4e0d0a1dfced0b1fa0Richard Smith  EvalStatus Scratch;
2682cd7a445c6b46c5585580dfb652300c8483c0cb6bJohn McCall  EvalInfo Info(Ctx, Scratch);
2683cd7a445c6b46c5585580dfb652300c8483c0cb6bJohn McCall
2684cd7a445c6b46c5585580dfb652300c8483c0cb6bJohn McCall  return HandleConversionToBool(this, Result, Info);
2685cd7a445c6b46c5585580dfb652300c8483c0cb6bJohn McCall}
2686cd7a445c6b46c5585580dfb652300c8483c0cb6bJohn McCall
2687a6b8b2c09610b8bc4330e948ece8b940c2386406Richard Smithbool Expr::EvaluateAsInt(APSInt &Result, const ASTContext &Ctx) const {
26881e12c59e8f9bb76c23628c4e0d0a1dfced0b1fa0Richard Smith  EvalStatus Scratch;
2689a6b8b2c09610b8bc4330e948ece8b940c2386406Richard Smith  EvalInfo Info(Ctx, Scratch);
2690a6b8b2c09610b8bc4330e948ece8b940c2386406Richard Smith
2691a6b8b2c09610b8bc4330e948ece8b940c2386406Richard Smith  return EvaluateInteger(this, Result, Info) && !Scratch.HasSideEffects;
2692a6b8b2c09610b8bc4330e948ece8b940c2386406Richard Smith}
2693a6b8b2c09610b8bc4330e948ece8b940c2386406Richard Smith
26944ba2a17694148e16eaa8d3917f657ffcd3667be4Jay Foadbool Expr::EvaluateAsLValue(EvalResult &Result, const ASTContext &Ctx) const {
26951b78276a75a5a0f496a82429c1ff9604d622a76dAnders Carlsson  EvalInfo Info(Ctx, Result);
26961b78276a75a5a0f496a82429c1ff9604d622a76dAnders Carlsson
2697efdb83e26f9a1fd2566afe54461216cd84814d42John McCall  LValue LV;
269842c8f87eb60958170c46767273bf93e6c96125bfJohn McCall  if (EvaluateLValue(this, LV, Info) &&
269942c8f87eb60958170c46767273bf93e6c96125bfJohn McCall      !Result.HasSideEffects &&
2700e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara      IsGlobalLValue(LV.Base)) {
2701e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara    LV.moveInto(Result.Val);
2702e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara    return true;
2703e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara  }
2704e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara  return false;
2705e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara}
2706e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara
27074ba2a17694148e16eaa8d3917f657ffcd3667be4Jay Foadbool Expr::EvaluateAsAnyLValue(EvalResult &Result,
27084ba2a17694148e16eaa8d3917f657ffcd3667be4Jay Foad                               const ASTContext &Ctx) const {
2709e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara  EvalInfo Info(Ctx, Result);
2710e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara
2711e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara  LValue LV;
2712e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara  if (EvaluateLValue(this, LV, Info)) {
2713efdb83e26f9a1fd2566afe54461216cd84814d42John McCall    LV.moveInto(Result.Val);
2714efdb83e26f9a1fd2566afe54461216cd84814d42John McCall    return true;
2715efdb83e26f9a1fd2566afe54461216cd84814d42John McCall  }
2716efdb83e26f9a1fd2566afe54461216cd84814d42John McCall  return false;
2717b2f295c8050fb8c141bf2cf38eed0a56e99d0092Eli Friedman}
2718b2f295c8050fb8c141bf2cf38eed0a56e99d0092Eli Friedman
27196ee7aa154e8bbb21a21254293410b944f78b0bfeChris Lattner/// isEvaluatable - Call Evaluate to see if this expression can be constant
272045b6b9d080ac56917337d73d8f1cd6374b27b05dChris Lattner/// folded, but discard the result.
27214ba2a17694148e16eaa8d3917f657ffcd3667be4Jay Foadbool Expr::isEvaluatable(const ASTContext &Ctx) const {
27224fdfb0965b396f2778091f7e6c051d17ff9791baAnders Carlsson  EvalResult Result;
27234fdfb0965b396f2778091f7e6c051d17ff9791baAnders Carlsson  return Evaluate(Result, Ctx) && !Result.HasSideEffects;
272445b6b9d080ac56917337d73d8f1cd6374b27b05dChris Lattner}
272551fe996231b1d7199f76e4005ff4c943d5deeecdAnders Carlsson
27264ba2a17694148e16eaa8d3917f657ffcd3667be4Jay Foadbool Expr::HasSideEffects(const ASTContext &Ctx) const {
27271e12c59e8f9bb76c23628c4e0d0a1dfced0b1fa0Richard Smith  return HasSideEffect(Ctx).Visit(this);
2728393c247fe025ccb5f914e37e948192ea86faef8cFariborz Jahanian}
2729393c247fe025ccb5f914e37e948192ea86faef8cFariborz Jahanian
2730a6b8b2c09610b8bc4330e948ece8b940c2386406Richard SmithAPSInt Expr::EvaluateKnownConstInt(const ASTContext &Ctx) const {
27311c0cfd4599e816cfd7a8f348286bf0ad79652ffcAnders Carlsson  EvalResult EvalResult;
27321c0cfd4599e816cfd7a8f348286bf0ad79652ffcAnders Carlsson  bool Result = Evaluate(EvalResult, Ctx);
2733c6ed729f669044f5072a49d79041f455d971ece3Jeffrey Yasskin  (void)Result;
273451fe996231b1d7199f76e4005ff4c943d5deeecdAnders Carlsson  assert(Result && "Could not evaluate expression");
27351c0cfd4599e816cfd7a8f348286bf0ad79652ffcAnders Carlsson  assert(EvalResult.Val.isInt() && "Expression did not evaluate to integer");
273651fe996231b1d7199f76e4005ff4c943d5deeecdAnders Carlsson
27371c0cfd4599e816cfd7a8f348286bf0ad79652ffcAnders Carlsson  return EvalResult.Val.getInt();
273851fe996231b1d7199f76e4005ff4c943d5deeecdAnders Carlsson}
2739d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall
2740e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara bool Expr::EvalResult::isGlobalLValue() const {
2741e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara   assert(Val.isLValue());
2742e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara   return IsGlobalLValue(Val.getLValueBase());
2743e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara }
2744e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara
2745e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara
2746d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall/// isIntegerConstantExpr - this recursive routine will test if an expression is
2747d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall/// an integer constant expression.
2748d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall
2749d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall/// FIXME: Pass up a reason why! Invalid operation in i-c-e, division by zero,
2750d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall/// comma, etc
2751d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall///
2752d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall/// FIXME: Handle offsetof.  Two things to do:  Handle GCC's __builtin_offsetof
2753d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall/// to support gcc 4.0+  and handle the idiom GCC recognizes with a null pointer
2754d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall/// cast+dereference.
2755d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall
2756d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall// CheckICE - This function does the fundamental ICE checking: the returned
2757d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall// ICEDiag contains a Val of 0, 1, or 2, and a possibly null SourceLocation.
2758d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall// Note that to reduce code duplication, this helper does no evaluation
2759d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall// itself; the caller checks whether the expression is evaluatable, and
2760d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall// in the rare cases where CheckICE actually cares about the evaluated
2761d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall// value, it calls into Evalute.
2762d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall//
2763d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall// Meanings of Val:
2764d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall// 0: This expression is an ICE if it can be evaluated by Evaluate.
2765d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall// 1: This expression is not an ICE, but if it isn't evaluated, it's
2766d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall//    a legal subexpression for an ICE. This return value is used to handle
2767d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall//    the comma operator in C99 mode.
2768d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall// 2: This expression is not an ICE, and is not a legal subexpression for one.
2769d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall
27703c46e8db99196179b30e7ac5c20c4efd5f3926d7Dan Gohmannamespace {
27713c46e8db99196179b30e7ac5c20c4efd5f3926d7Dan Gohman
2772d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCallstruct ICEDiag {
2773d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  unsigned Val;
2774d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  SourceLocation Loc;
2775d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall
2776d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  public:
2777d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  ICEDiag(unsigned v, SourceLocation l) : Val(v), Loc(l) {}
2778d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  ICEDiag() : Val(0) {}
2779d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall};
2780d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall
27813c46e8db99196179b30e7ac5c20c4efd5f3926d7Dan Gohman}
27823c46e8db99196179b30e7ac5c20c4efd5f3926d7Dan Gohman
27833c46e8db99196179b30e7ac5c20c4efd5f3926d7Dan Gohmanstatic ICEDiag NoDiag() { return ICEDiag(); }
2784d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall
2785d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCallstatic ICEDiag CheckEvalInICE(const Expr* E, ASTContext &Ctx) {
2786d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  Expr::EvalResult EVResult;
2787d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  if (!E->Evaluate(EVResult, Ctx) || EVResult.HasSideEffects ||
2788d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      !EVResult.Val.isInt()) {
2789d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    return ICEDiag(2, E->getLocStart());
2790d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  }
2791d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  return NoDiag();
2792d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall}
2793d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall
2794d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCallstatic ICEDiag CheckICE(const Expr* E, ASTContext &Ctx) {
2795d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  assert(!E->isValueDependent() && "Should not see value dependent exprs!");
27962ade35e2cfd554e49d35a52047cea98a82787af9Douglas Gregor  if (!E->getType()->isIntegralOrEnumerationType()) {
2797d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    return ICEDiag(2, E->getLocStart());
2798d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  }
2799d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall
2800d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  switch (E->getStmtClass()) {
280163c00d7f35fa060c0a446c9df3a4402d9c7757feJohn McCall#define ABSTRACT_STMT(Node)
2802d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall#define STMT(Node, Base) case Expr::Node##Class:
2803d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall#define EXPR(Node, Base)
2804d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall#include "clang/AST/StmtNodes.inc"
2805d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::PredefinedExprClass:
2806d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::FloatingLiteralClass:
2807d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::ImaginaryLiteralClass:
2808d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::StringLiteralClass:
2809d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::ArraySubscriptExprClass:
2810d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::MemberExprClass:
2811d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::CompoundAssignOperatorClass:
2812d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::CompoundLiteralExprClass:
2813d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::ExtVectorElementExprClass:
2814d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::DesignatedInitExprClass:
2815d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::ImplicitValueInitExprClass:
2816d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::ParenListExprClass:
2817d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::VAArgExprClass:
2818d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::AddrLabelExprClass:
2819d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::StmtExprClass:
2820d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::CXXMemberCallExprClass:
2821e08ce650a2b02410eddd1f60a4aa6b3d4be71e73Peter Collingbourne  case Expr::CUDAKernelCallExprClass:
2822d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::CXXDynamicCastExprClass:
2823d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::CXXTypeidExprClass:
28249be88403e965cc49af76c9d33d818781d44b333eFrancois Pichet  case Expr::CXXUuidofExprClass:
2825d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::CXXNullPtrLiteralExprClass:
2826d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::CXXThisExprClass:
2827d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::CXXThrowExprClass:
2828d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::CXXNewExprClass:
2829d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::CXXDeleteExprClass:
2830d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::CXXPseudoDestructorExprClass:
2831d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::UnresolvedLookupExprClass:
2832d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::DependentScopeDeclRefExprClass:
2833d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::CXXConstructExprClass:
2834d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::CXXBindTemporaryExprClass:
28354765fa05b5652fcc4356371c2f481d0ea9a1b007John McCall  case Expr::ExprWithCleanupsClass:
2836d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::CXXTemporaryObjectExprClass:
2837d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::CXXUnresolvedConstructExprClass:
2838d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::CXXDependentScopeMemberExprClass:
2839d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::UnresolvedMemberExprClass:
2840d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::ObjCStringLiteralClass:
2841d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::ObjCEncodeExprClass:
2842d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::ObjCMessageExprClass:
2843d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::ObjCSelectorExprClass:
2844d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::ObjCProtocolExprClass:
2845d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::ObjCIvarRefExprClass:
2846d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::ObjCPropertyRefExprClass:
2847d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::ObjCIsaExprClass:
2848d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::ShuffleVectorExprClass:
2849d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::BlockExprClass:
2850d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::BlockDeclRefExprClass:
2851d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::NoStmtClass:
28527cd7d1ad33fdf49eef83942e8855fe20d95aa1b9John McCall  case Expr::OpaqueValueExprClass:
2853be230c36e32142cbdcdbe9c97511d097beeecbabDouglas Gregor  case Expr::PackExpansionExprClass:
2854c7793c73ba8a343de3f2552d984851985a46f159Douglas Gregor  case Expr::SubstNonTypeTemplateParmPackExprClass:
285561eee0ca33b29e102f11bab77c8b74cc00e2392bTanya Lattner  case Expr::AsTypeExprClass:
2856f85e193739c953358c865005855253af4f68a497John McCall  case Expr::ObjCIndirectCopyRestoreExprClass:
285703e80030515c800d1ab44125b9052dfffd1bd04cDouglas Gregor  case Expr::MaterializeTemporaryExprClass:
2858276b061970939293f1abaf694bd3ef05b2cbda79Eli Friedman  case Expr::AtomicExprClass:
2859d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    return ICEDiag(2, E->getLocStart());
2860d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall
2861cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl  case Expr::InitListExprClass:
2862cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl    if (Ctx.getLangOptions().CPlusPlus0x) {
2863cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl      const InitListExpr *ILE = cast<InitListExpr>(E);
2864cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl      if (ILE->getNumInits() == 0)
2865cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl        return NoDiag();
2866cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl      if (ILE->getNumInits() == 1)
2867cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl        return CheckICE(ILE->getInit(0), Ctx);
2868cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl      // Fall through for more than 1 expression.
2869cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl    }
2870cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl    return ICEDiag(2, E->getLocStart());
2871cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl
2872ee8aff06f6a96214731de17b2cb6df407c6c1820Douglas Gregor  case Expr::SizeOfPackExprClass:
2873d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::GNUNullExprClass:
2874d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    // GCC considers the GNU __null value to be an integral constant expression.
2875d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    return NoDiag();
2876d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall
287791a5755ad73c5dc1dfb167e448fdd74e75a6df56John McCall  case Expr::SubstNonTypeTemplateParmExprClass:
287891a5755ad73c5dc1dfb167e448fdd74e75a6df56John McCall    return
287991a5755ad73c5dc1dfb167e448fdd74e75a6df56John McCall      CheckICE(cast<SubstNonTypeTemplateParmExpr>(E)->getReplacement(), Ctx);
288091a5755ad73c5dc1dfb167e448fdd74e75a6df56John McCall
2881d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::ParenExprClass:
2882d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    return CheckICE(cast<ParenExpr>(E)->getSubExpr(), Ctx);
2883f111d935722ed488144600cea5ed03a6b5069e8fPeter Collingbourne  case Expr::GenericSelectionExprClass:
2884f111d935722ed488144600cea5ed03a6b5069e8fPeter Collingbourne    return CheckICE(cast<GenericSelectionExpr>(E)->getResultExpr(), Ctx);
2885d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::IntegerLiteralClass:
2886d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::CharacterLiteralClass:
2887d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::CXXBoolLiteralExprClass:
2888ed8abf18329df67b0abcbb3a10458bd8c1d2a595Douglas Gregor  case Expr::CXXScalarValueInitExprClass:
2889d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::UnaryTypeTraitExprClass:
28906ad6f2848d7652ab2991286eb48be440d3493b28Francois Pichet  case Expr::BinaryTypeTraitExprClass:
289121ff2e516b0e0bc8c1dbf965cb3d44bac3c64330John Wiegley  case Expr::ArrayTypeTraitExprClass:
2892552622067dc45013d240f73952fece703f5e63bdJohn Wiegley  case Expr::ExpressionTraitExprClass:
28932e156225a29407a50dd19041aa5750171ad44ea3Sebastian Redl  case Expr::CXXNoexceptExprClass:
2894d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    return NoDiag();
2895d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::CallExprClass:
28966cf750298d3621d8a10a6dd07fcee8e274b9d94dSean Hunt  case Expr::CXXOperatorCallExprClass: {
2897d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    const CallExpr *CE = cast<CallExpr>(E);
2898d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    if (CE->isBuiltinCall(Ctx))
2899d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      return CheckEvalInICE(E, Ctx);
2900d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    return ICEDiag(2, E->getLocStart());
2901d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  }
2902d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::DeclRefExprClass:
2903d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    if (isa<EnumConstantDecl>(cast<DeclRefExpr>(E)->getDecl()))
2904d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      return NoDiag();
290503f96110bc2c2c773e06a42982b17a03dd2e5379Richard Smith    if (Ctx.getLangOptions().CPlusPlus && IsConstNonVolatile(E->getType())) {
2906d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      const NamedDecl *D = cast<DeclRefExpr>(E)->getDecl();
2907d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall
2908d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      // Parameter variables are never constants.  Without this check,
2909d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      // getAnyInitializer() can find a default argument, which leads
2910d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      // to chaos.
2911d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      if (isa<ParmVarDecl>(D))
2912d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall        return ICEDiag(2, cast<DeclRefExpr>(E)->getLocation());
2913d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall
2914d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      // C++ 7.1.5.1p2
2915d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      //   A variable of non-volatile const-qualified integral or enumeration
2916d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      //   type initialized by an ICE can be used in ICEs.
2917d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      if (const VarDecl *Dcl = dyn_cast<VarDecl>(D)) {
2918d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall        // Look for a declaration of this variable that has an initializer.
2919d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall        const VarDecl *ID = 0;
2920d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall        const Expr *Init = Dcl->getAnyInitializer(ID);
2921d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall        if (Init) {
2922d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall          if (ID->isInitKnownICE()) {
2923d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall            // We have already checked whether this subexpression is an
2924d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall            // integral constant expression.
2925d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall            if (ID->isInitICE())
2926d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall              return NoDiag();
2927d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall            else
2928d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall              return ICEDiag(2, cast<DeclRefExpr>(E)->getLocation());
2929d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall          }
2930d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall
2931d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall          // It's an ICE whether or not the definition we found is
2932d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall          // out-of-line.  See DR 721 and the discussion in Clang PR
2933d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall          // 6206 for details.
2934d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall
2935d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall          if (Dcl->isCheckingICE()) {
2936d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall            return ICEDiag(2, cast<DeclRefExpr>(E)->getLocation());
2937d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall          }
2938d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall
2939d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall          Dcl->setCheckingICE();
2940d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall          ICEDiag Result = CheckICE(Init, Ctx);
2941d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall          // Cache the result of the ICE test.
2942d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall          Dcl->setInitKnownICE(Result.Val == 0);
2943d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall          return Result;
2944d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall        }
2945d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      }
2946d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    }
2947d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    return ICEDiag(2, E->getLocStart());
2948d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::UnaryOperatorClass: {
2949d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    const UnaryOperator *Exp = cast<UnaryOperator>(E);
2950d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    switch (Exp->getOpcode()) {
29512de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case UO_PostInc:
29522de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case UO_PostDec:
29532de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case UO_PreInc:
29542de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case UO_PreDec:
29552de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case UO_AddrOf:
29562de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case UO_Deref:
2957d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      return ICEDiag(2, E->getLocStart());
29582de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case UO_Extension:
29592de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case UO_LNot:
29602de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case UO_Plus:
29612de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case UO_Minus:
29622de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case UO_Not:
29632de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case UO_Real:
29642de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case UO_Imag:
2965d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      return CheckICE(Exp->getSubExpr(), Ctx);
2966d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    }
2967d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall
2968d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    // OffsetOf falls through here.
2969d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  }
2970d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::OffsetOfExprClass: {
2971d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      // Note that per C99, offsetof must be an ICE. And AFAIK, using
2972d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      // Evaluate matches the proposed gcc behavior for cases like
2973d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      // "offsetof(struct s{int x[4];}, x[!.0])".  This doesn't affect
2974d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      // compliance: we should warn earlier for offsetof expressions with
2975d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      // array subscripts that aren't ICEs, and if the array subscripts
2976d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      // are ICEs, the value of the offsetof must be an integer constant.
2977d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      return CheckEvalInICE(E, Ctx);
2978d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  }
2979f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne  case Expr::UnaryExprOrTypeTraitExprClass: {
2980f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne    const UnaryExprOrTypeTraitExpr *Exp = cast<UnaryExprOrTypeTraitExpr>(E);
2981f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne    if ((Exp->getKind() ==  UETT_SizeOf) &&
2982f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne        Exp->getTypeOfArgument()->isVariableArrayType())
2983d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      return ICEDiag(2, E->getLocStart());
2984d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    return NoDiag();
2985d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  }
2986d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::BinaryOperatorClass: {
2987d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    const BinaryOperator *Exp = cast<BinaryOperator>(E);
2988d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    switch (Exp->getOpcode()) {
29892de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case BO_PtrMemD:
29902de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case BO_PtrMemI:
29912de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case BO_Assign:
29922de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case BO_MulAssign:
29932de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case BO_DivAssign:
29942de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case BO_RemAssign:
29952de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case BO_AddAssign:
29962de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case BO_SubAssign:
29972de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case BO_ShlAssign:
29982de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case BO_ShrAssign:
29992de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case BO_AndAssign:
30002de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case BO_XorAssign:
30012de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case BO_OrAssign:
3002d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      return ICEDiag(2, E->getLocStart());
3003d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall
30042de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case BO_Mul:
30052de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case BO_Div:
30062de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case BO_Rem:
30072de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case BO_Add:
30082de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case BO_Sub:
30092de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case BO_Shl:
30102de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case BO_Shr:
30112de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case BO_LT:
30122de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case BO_GT:
30132de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case BO_LE:
30142de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case BO_GE:
30152de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case BO_EQ:
30162de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case BO_NE:
30172de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case BO_And:
30182de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case BO_Xor:
30192de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case BO_Or:
30202de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case BO_Comma: {
3021d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      ICEDiag LHSResult = CheckICE(Exp->getLHS(), Ctx);
3022d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      ICEDiag RHSResult = CheckICE(Exp->getRHS(), Ctx);
30232de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall      if (Exp->getOpcode() == BO_Div ||
30242de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall          Exp->getOpcode() == BO_Rem) {
3025d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall        // Evaluate gives an error for undefined Div/Rem, so make sure
3026d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall        // we don't evaluate one.
30273b332ab132fa85c83833d74d400f6e126f52fbd2John McCall        if (LHSResult.Val == 0 && RHSResult.Val == 0) {
3028a6b8b2c09610b8bc4330e948ece8b940c2386406Richard Smith          llvm::APSInt REval = Exp->getRHS()->EvaluateKnownConstInt(Ctx);
3029d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall          if (REval == 0)
3030d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall            return ICEDiag(1, E->getLocStart());
3031d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall          if (REval.isSigned() && REval.isAllOnesValue()) {
3032a6b8b2c09610b8bc4330e948ece8b940c2386406Richard Smith            llvm::APSInt LEval = Exp->getLHS()->EvaluateKnownConstInt(Ctx);
3033d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall            if (LEval.isMinSignedValue())
3034d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall              return ICEDiag(1, E->getLocStart());
3035d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall          }
3036d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall        }
3037d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      }
30382de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall      if (Exp->getOpcode() == BO_Comma) {
3039d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall        if (Ctx.getLangOptions().C99) {
3040d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall          // C99 6.6p3 introduces a strange edge case: comma can be in an ICE
3041d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall          // if it isn't evaluated.
3042d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall          if (LHSResult.Val == 0 && RHSResult.Val == 0)
3043d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall            return ICEDiag(1, E->getLocStart());
3044d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall        } else {
3045d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall          // In both C89 and C++, commas in ICEs are illegal.
3046d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall          return ICEDiag(2, E->getLocStart());
3047d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall        }
3048d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      }
3049d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      if (LHSResult.Val >= RHSResult.Val)
3050d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall        return LHSResult;
3051d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      return RHSResult;
3052d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    }
30532de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case BO_LAnd:
30542de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall    case BO_LOr: {
3055d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      ICEDiag LHSResult = CheckICE(Exp->getLHS(), Ctx);
305663fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor
305763fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor      // C++0x [expr.const]p2:
305863fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor      //   [...] subexpressions of logical AND (5.14), logical OR
305963fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor      //   (5.15), and condi- tional (5.16) operations that are not
306063fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor      //   evaluated are not considered.
306163fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor      if (Ctx.getLangOptions().CPlusPlus0x && LHSResult.Val == 0) {
306263fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor        if (Exp->getOpcode() == BO_LAnd &&
3063a6b8b2c09610b8bc4330e948ece8b940c2386406Richard Smith            Exp->getLHS()->EvaluateKnownConstInt(Ctx) == 0)
306463fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor          return LHSResult;
306563fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor
306663fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor        if (Exp->getOpcode() == BO_LOr &&
3067a6b8b2c09610b8bc4330e948ece8b940c2386406Richard Smith            Exp->getLHS()->EvaluateKnownConstInt(Ctx) != 0)
306863fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor          return LHSResult;
306963fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor      }
307063fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor
3071d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      ICEDiag RHSResult = CheckICE(Exp->getRHS(), Ctx);
3072d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      if (LHSResult.Val == 0 && RHSResult.Val == 1) {
3073d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall        // Rare case where the RHS has a comma "side-effect"; we need
3074d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall        // to actually check the condition to see whether the side
3075d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall        // with the comma is evaluated.
30762de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall        if ((Exp->getOpcode() == BO_LAnd) !=
3077a6b8b2c09610b8bc4330e948ece8b940c2386406Richard Smith            (Exp->getLHS()->EvaluateKnownConstInt(Ctx) == 0))
3078d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall          return RHSResult;
3079d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall        return NoDiag();
3080d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      }
3081d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall
3082d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      if (LHSResult.Val >= RHSResult.Val)
3083d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall        return LHSResult;
3084d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      return RHSResult;
3085d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    }
3086d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    }
3087d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  }
3088d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::ImplicitCastExprClass:
3089d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::CStyleCastExprClass:
3090d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::CXXFunctionalCastExprClass:
3091d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::CXXStaticCastExprClass:
3092d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::CXXReinterpretCastExprClass:
309332cb47174304bc7ec11478b9497c4e10f48273d9Richard Smith  case Expr::CXXConstCastExprClass:
3094f85e193739c953358c865005855253af4f68a497John McCall  case Expr::ObjCBridgedCastExprClass: {
3095d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    const Expr *SubExpr = cast<CastExpr>(E)->getSubExpr();
309632cb47174304bc7ec11478b9497c4e10f48273d9Richard Smith    if (E->getStmtClass() != Expr::ImplicitCastExprClass &&
309732cb47174304bc7ec11478b9497c4e10f48273d9Richard Smith        isa<FloatingLiteral>(SubExpr->IgnoreParenImpCasts()))
309832cb47174304bc7ec11478b9497c4e10f48273d9Richard Smith      return NoDiag();
3099eea0e817c609c662f3fef61bb257fddf1ae8f7b7Eli Friedman    switch (cast<CastExpr>(E)->getCastKind()) {
3100eea0e817c609c662f3fef61bb257fddf1ae8f7b7Eli Friedman    case CK_LValueToRValue:
3101eea0e817c609c662f3fef61bb257fddf1ae8f7b7Eli Friedman    case CK_NoOp:
3102eea0e817c609c662f3fef61bb257fddf1ae8f7b7Eli Friedman    case CK_IntegralToBoolean:
3103eea0e817c609c662f3fef61bb257fddf1ae8f7b7Eli Friedman    case CK_IntegralCast:
3104d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      return CheckICE(SubExpr, Ctx);
3105eea0e817c609c662f3fef61bb257fddf1ae8f7b7Eli Friedman    default:
3106eea0e817c609c662f3fef61bb257fddf1ae8f7b7Eli Friedman      return ICEDiag(2, E->getLocStart());
3107eea0e817c609c662f3fef61bb257fddf1ae8f7b7Eli Friedman    }
3108d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  }
310956ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall  case Expr::BinaryConditionalOperatorClass: {
311056ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall    const BinaryConditionalOperator *Exp = cast<BinaryConditionalOperator>(E);
311156ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall    ICEDiag CommonResult = CheckICE(Exp->getCommon(), Ctx);
311256ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall    if (CommonResult.Val == 2) return CommonResult;
311356ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall    ICEDiag FalseResult = CheckICE(Exp->getFalseExpr(), Ctx);
311456ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall    if (FalseResult.Val == 2) return FalseResult;
311556ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall    if (CommonResult.Val == 1) return CommonResult;
311656ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall    if (FalseResult.Val == 1 &&
3117a6b8b2c09610b8bc4330e948ece8b940c2386406Richard Smith        Exp->getCommon()->EvaluateKnownConstInt(Ctx) == 0) return NoDiag();
311856ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall    return FalseResult;
311956ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall  }
3120d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::ConditionalOperatorClass: {
3121d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    const ConditionalOperator *Exp = cast<ConditionalOperator>(E);
3122d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    // If the condition (ignoring parens) is a __builtin_constant_p call,
3123d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    // then only the true side is actually considered in an integer constant
3124d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    // expression, and it is fully evaluated.  This is an important GNU
3125d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    // extension.  See GCC PR38377 for discussion.
3126d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    if (const CallExpr *CallCE
3127d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall        = dyn_cast<CallExpr>(Exp->getCond()->IgnoreParenCasts()))
3128d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      if (CallCE->isBuiltinCall(Ctx) == Builtin::BI__builtin_constant_p) {
3129d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall        Expr::EvalResult EVResult;
3130d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall        if (!E->Evaluate(EVResult, Ctx) || EVResult.HasSideEffects ||
3131d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall            !EVResult.Val.isInt()) {
3132d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall          return ICEDiag(2, E->getLocStart());
3133d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall        }
3134d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall        return NoDiag();
3135d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      }
3136d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    ICEDiag CondResult = CheckICE(Exp->getCond(), Ctx);
3137d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    if (CondResult.Val == 2)
3138d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      return CondResult;
313963fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor
314063fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor    // C++0x [expr.const]p2:
314163fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor    //   subexpressions of [...] conditional (5.16) operations that
314263fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor    //   are not evaluated are not considered
314363fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor    bool TrueBranch = Ctx.getLangOptions().CPlusPlus0x
3144a6b8b2c09610b8bc4330e948ece8b940c2386406Richard Smith      ? Exp->getCond()->EvaluateKnownConstInt(Ctx) != 0
314563fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor      : false;
314663fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor    ICEDiag TrueResult = NoDiag();
314763fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor    if (!Ctx.getLangOptions().CPlusPlus0x || TrueBranch)
314863fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor      TrueResult = CheckICE(Exp->getTrueExpr(), Ctx);
314963fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor    ICEDiag FalseResult = NoDiag();
315063fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor    if (!Ctx.getLangOptions().CPlusPlus0x || !TrueBranch)
315163fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor      FalseResult = CheckICE(Exp->getFalseExpr(), Ctx);
315263fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor
3153d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    if (TrueResult.Val == 2)
3154d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      return TrueResult;
3155d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    if (FalseResult.Val == 2)
3156d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      return FalseResult;
3157d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    if (CondResult.Val == 1)
3158d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      return CondResult;
3159d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    if (TrueResult.Val == 0 && FalseResult.Val == 0)
3160d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      return NoDiag();
3161d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    // Rare case where the diagnostics depend on which side is evaluated
3162d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    // Note that if we get here, CondResult is 0, and at least one of
3163d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    // TrueResult and FalseResult is non-zero.
3164a6b8b2c09610b8bc4330e948ece8b940c2386406Richard Smith    if (Exp->getCond()->EvaluateKnownConstInt(Ctx) == 0) {
3165d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall      return FalseResult;
3166d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    }
3167d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    return TrueResult;
3168d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  }
3169d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::CXXDefaultArgExprClass:
3170d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    return CheckICE(cast<CXXDefaultArgExpr>(E)->getExpr(), Ctx);
3171d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  case Expr::ChooseExprClass: {
3172d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    return CheckICE(cast<ChooseExpr>(E)->getChosenSubExpr(Ctx), Ctx);
3173d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  }
3174d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  }
3175d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall
3176d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  // Silence a GCC warning
3177d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  return ICEDiag(2, E->getLocStart());
3178d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall}
3179d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall
3180d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCallbool Expr::isIntegerConstantExpr(llvm::APSInt &Result, ASTContext &Ctx,
3181d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall                                 SourceLocation *Loc, bool isEvaluated) const {
3182d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  ICEDiag d = CheckICE(this, Ctx);
3183d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  if (d.Val != 0) {
3184d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    if (Loc) *Loc = d.Loc;
3185d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    return false;
3186d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  }
3187d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  EvalResult EvalResult;
3188d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  if (!Evaluate(EvalResult, Ctx))
3189d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall    llvm_unreachable("ICE cannot be evaluated!");
3190d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  assert(!EvalResult.HasSideEffects && "ICE with side effects!");
3191d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  assert(EvalResult.Val.isInt() && "ICE that isn't integer!");
3192d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  Result = EvalResult.Val.getInt();
3193d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall  return true;
3194d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall}
3195