ExprConstant.cpp revision a6b8b2c09610b8bc4330e948ece8b940c2386406
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 49c54061a679d8db4169438b2f97f81e3f443c6a25Benjamin Kramer /// EvalResult - Contains information about the evaluation. 50c54061a679d8db4169438b2f97f81e3f443c6a25Benjamin Kramer Expr::EvalResult &EvalResult; 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 60c54061a679d8db4169438b2f97f81e3f443c6a25Benjamin Kramer EvalInfo(const ASTContext &ctx, Expr::EvalResult &evalresult) 61c54061a679d8db4169438b2f97f81e3f443c6a25Benjamin Kramer : Ctx(ctx), EvalResult(evalresult) {} 62c54061a679d8db4169438b2f97f81e3f443c6a25Benjamin Kramer }; 6387eae5ecf94e38baa20d9a327b8f73f8bdc72436Chris Lattner 64f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall struct ComplexValue { 65f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall private: 66f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall bool IsInt; 67f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall 68f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall public: 69f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall APSInt IntReal, IntImag; 70f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall APFloat FloatReal, FloatImag; 71f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall 72f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall ComplexValue() : FloatReal(APFloat::Bogus), FloatImag(APFloat::Bogus) {} 73f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall 74f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall void makeComplexFloat() { IsInt = false; } 75f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall bool isComplexFloat() const { return !IsInt; } 76f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall APFloat &getComplexFloatReal() { return FloatReal; } 77f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall APFloat &getComplexFloatImag() { return FloatImag; } 78f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall 79f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall void makeComplexInt() { IsInt = true; } 80f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall bool isComplexInt() const { return IsInt; } 81f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall APSInt &getComplexIntReal() { return IntReal; } 82f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall APSInt &getComplexIntImag() { return IntImag; } 83f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall 8456ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall void moveInto(APValue &v) const { 85f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall if (isComplexFloat()) 86f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall v = APValue(FloatReal, FloatImag); 87f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall else 88f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall v = APValue(IntReal, IntImag); 89f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall } 9056ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall void setFrom(const APValue &v) { 9156ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall assert(v.isComplexFloat() || v.isComplexInt()); 9256ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall if (v.isComplexFloat()) { 9356ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall makeComplexFloat(); 9456ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall FloatReal = v.getComplexFloatReal(); 9556ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall FloatImag = v.getComplexFloatImag(); 9656ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall } else { 9756ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall makeComplexInt(); 9856ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall IntReal = v.getComplexIntReal(); 9956ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall IntImag = v.getComplexIntImag(); 10056ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall } 10156ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall } 102f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall }; 103efdb83e26f9a1fd2566afe54461216cd84814d42John McCall 104efdb83e26f9a1fd2566afe54461216cd84814d42John McCall struct LValue { 1058cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne const Expr *Base; 106efdb83e26f9a1fd2566afe54461216cd84814d42John McCall CharUnits Offset; 107efdb83e26f9a1fd2566afe54461216cd84814d42John McCall 1088cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne const Expr *getLValueBase() { return Base; } 109efdb83e26f9a1fd2566afe54461216cd84814d42John McCall CharUnits getLValueOffset() { return Offset; } 110efdb83e26f9a1fd2566afe54461216cd84814d42John McCall 11156ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall void moveInto(APValue &v) const { 112efdb83e26f9a1fd2566afe54461216cd84814d42John McCall v = APValue(Base, Offset); 113efdb83e26f9a1fd2566afe54461216cd84814d42John McCall } 11456ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall void setFrom(const APValue &v) { 11556ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall assert(v.isLValue()); 11656ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall Base = v.getLValueBase(); 11756ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall Offset = v.getLValueOffset(); 11856ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall } 119efdb83e26f9a1fd2566afe54461216cd84814d42John McCall }; 120f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall} 12187eae5ecf94e38baa20d9a327b8f73f8bdc72436Chris Lattner 12256ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCallstatic bool Evaluate(EvalInfo &info, const Expr *E); 123efdb83e26f9a1fd2566afe54461216cd84814d42John McCallstatic bool EvaluateLValue(const Expr *E, LValue &Result, EvalInfo &Info); 124efdb83e26f9a1fd2566afe54461216cd84814d42John McCallstatic bool EvaluatePointer(const Expr *E, LValue &Result, EvalInfo &Info); 12587eae5ecf94e38baa20d9a327b8f73f8bdc72436Chris Lattnerstatic bool EvaluateInteger(const Expr *E, APSInt &Result, EvalInfo &Info); 126d9becd1846e2c72bf6ad283faa1b048f33dd3afeChris Lattnerstatic bool EvaluateIntegerOrLValue(const Expr *E, APValue &Result, 127d9becd1846e2c72bf6ad283faa1b048f33dd3afeChris Lattner EvalInfo &Info); 128d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedmanstatic bool EvaluateFloat(const Expr *E, APFloat &Result, EvalInfo &Info); 129f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCallstatic bool EvaluateComplex(const Expr *E, ComplexValue &Res, EvalInfo &Info); 130f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner 131f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner//===----------------------------------------------------------------------===// 1324efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman// Misc utilities 1334efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman//===----------------------------------------------------------------------===// 1344efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman 135e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnarastatic bool IsGlobalLValue(const Expr* E) { 13642c8f87eb60958170c46767273bf93e6c96125bfJohn McCall if (!E) return true; 13742c8f87eb60958170c46767273bf93e6c96125bfJohn McCall 13842c8f87eb60958170c46767273bf93e6c96125bfJohn McCall if (const DeclRefExpr *DRE = dyn_cast<DeclRefExpr>(E)) { 13942c8f87eb60958170c46767273bf93e6c96125bfJohn McCall if (isa<FunctionDecl>(DRE->getDecl())) 14042c8f87eb60958170c46767273bf93e6c96125bfJohn McCall return true; 14142c8f87eb60958170c46767273bf93e6c96125bfJohn McCall if (const VarDecl *VD = dyn_cast<VarDecl>(DRE->getDecl())) 14242c8f87eb60958170c46767273bf93e6c96125bfJohn McCall return VD->hasGlobalStorage(); 14342c8f87eb60958170c46767273bf93e6c96125bfJohn McCall return false; 14442c8f87eb60958170c46767273bf93e6c96125bfJohn McCall } 14542c8f87eb60958170c46767273bf93e6c96125bfJohn McCall 14642c8f87eb60958170c46767273bf93e6c96125bfJohn McCall if (const CompoundLiteralExpr *CLE = dyn_cast<CompoundLiteralExpr>(E)) 14742c8f87eb60958170c46767273bf93e6c96125bfJohn McCall return CLE->isFileScope(); 14842c8f87eb60958170c46767273bf93e6c96125bfJohn McCall 14942c8f87eb60958170c46767273bf93e6c96125bfJohn McCall return true; 15042c8f87eb60958170c46767273bf93e6c96125bfJohn McCall} 15142c8f87eb60958170c46767273bf93e6c96125bfJohn McCall 152efdb83e26f9a1fd2566afe54461216cd84814d42John McCallstatic bool EvalPointerValueAsBool(LValue& Value, bool& Result) { 153efdb83e26f9a1fd2566afe54461216cd84814d42John McCall const Expr* Base = Value.Base; 154a7d3c04fcfe9d4af2f7758f46aef26b1a8f8ac09Rafael Espindola 1553554283157190e67918fad4221a5e6faf9317362John McCall // A null base expression indicates a null pointer. These are always 1563554283157190e67918fad4221a5e6faf9317362John McCall // evaluatable, and they are false unless the offset is zero. 1573554283157190e67918fad4221a5e6faf9317362John McCall if (!Base) { 1583554283157190e67918fad4221a5e6faf9317362John McCall Result = !Value.Offset.isZero(); 1593554283157190e67918fad4221a5e6faf9317362John McCall return true; 1603554283157190e67918fad4221a5e6faf9317362John McCall } 1613554283157190e67918fad4221a5e6faf9317362John McCall 16242c8f87eb60958170c46767273bf93e6c96125bfJohn McCall // Require the base expression to be a global l-value. 163e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara if (!IsGlobalLValue(Base)) return false; 16442c8f87eb60958170c46767273bf93e6c96125bfJohn McCall 1653554283157190e67918fad4221a5e6faf9317362John McCall // We have a non-null base expression. These are generally known to 1663554283157190e67918fad4221a5e6faf9317362John McCall // be true, but if it'a decl-ref to a weak symbol it can be null at 1673554283157190e67918fad4221a5e6faf9317362John McCall // runtime. 1683554283157190e67918fad4221a5e6faf9317362John McCall Result = true; 169a7d3c04fcfe9d4af2f7758f46aef26b1a8f8ac09Rafael Espindola 1703554283157190e67918fad4221a5e6faf9317362John McCall const DeclRefExpr* DeclRef = dyn_cast<DeclRefExpr>(Base); 171a7d3c04fcfe9d4af2f7758f46aef26b1a8f8ac09Rafael Espindola if (!DeclRef) 172a7d3c04fcfe9d4af2f7758f46aef26b1a8f8ac09Rafael Espindola return true; 173a7d3c04fcfe9d4af2f7758f46aef26b1a8f8ac09Rafael Espindola 1743554283157190e67918fad4221a5e6faf9317362John McCall // If it's a weak symbol, it isn't constant-evaluable. 175a7d3c04fcfe9d4af2f7758f46aef26b1a8f8ac09Rafael Espindola const ValueDecl* Decl = DeclRef->getDecl(); 176a7d3c04fcfe9d4af2f7758f46aef26b1a8f8ac09Rafael Espindola if (Decl->hasAttr<WeakAttr>() || 177a7d3c04fcfe9d4af2f7758f46aef26b1a8f8ac09Rafael Espindola Decl->hasAttr<WeakRefAttr>() || 1780a0d2b179085a52c10402feebeb6db8b4d96a140Douglas Gregor Decl->isWeakImported()) 179a7d3c04fcfe9d4af2f7758f46aef26b1a8f8ac09Rafael Espindola return false; 180a7d3c04fcfe9d4af2f7758f46aef26b1a8f8ac09Rafael Espindola 1815bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman return true; 1825bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman} 1835bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman 184cd7a445c6b46c5585580dfb652300c8483c0cb6bJohn McCallstatic bool HandleConversionToBool(const Expr* E, bool& Result, 185cd7a445c6b46c5585580dfb652300c8483c0cb6bJohn McCall EvalInfo &Info) { 1862ade35e2cfd554e49d35a52047cea98a82787af9Douglas Gregor if (E->getType()->isIntegralOrEnumerationType()) { 1874efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman APSInt IntResult; 1884efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman if (!EvaluateInteger(E, IntResult, Info)) 1894efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman return false; 1904efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman Result = IntResult != 0; 1914efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman return true; 1924efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman } else if (E->getType()->isRealFloatingType()) { 1934efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman APFloat FloatResult(0.0); 1944efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman if (!EvaluateFloat(E, FloatResult, Info)) 1954efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman return false; 1964efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman Result = !FloatResult.isZero(); 1974efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman return true; 198a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman } else if (E->getType()->hasPointerRepresentation()) { 199efdb83e26f9a1fd2566afe54461216cd84814d42John McCall LValue PointerResult; 2004efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman if (!EvaluatePointer(E, PointerResult, Info)) 2014efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman return false; 2025bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman return EvalPointerValueAsBool(PointerResult, Result); 203a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman } else if (E->getType()->isAnyComplexType()) { 204f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall ComplexValue ComplexResult; 205a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman if (!EvaluateComplex(E, ComplexResult, Info)) 206a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman return false; 207a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman if (ComplexResult.isComplexFloat()) { 208a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman Result = !ComplexResult.getComplexFloatReal().isZero() || 209a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman !ComplexResult.getComplexFloatImag().isZero(); 210a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman } else { 211a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman Result = ComplexResult.getComplexIntReal().getBoolValue() || 212a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman ComplexResult.getComplexIntImag().getBoolValue(); 213a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman } 214a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman return true; 2154efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman } 2164efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman 2174efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman return false; 2184efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman} 2194efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman 2201eb4433ac451dc16f4133a88af2d002ac26c58efMike Stumpstatic APSInt HandleFloatToIntCast(QualType DestType, QualType SrcType, 2214ba2a17694148e16eaa8d3917f657ffcd3667be4Jay Foad APFloat &Value, const ASTContext &Ctx) { 222a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar unsigned DestWidth = Ctx.getIntWidth(DestType); 223a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar // Determine whether we are converting to unsigned or signed. 224575a1c9dc8dc5b4977194993e289f9eda7295c39Douglas Gregor bool DestSigned = DestType->isSignedIntegerOrEnumerationType(); 2251eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 226a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar // FIXME: Warning for overflow. 2273e1ef7849845a9e7bf79156bbb8a2c26d77a1d2eJeffrey Yasskin APSInt Result(DestWidth, !DestSigned); 228a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar bool ignored; 2293e1ef7849845a9e7bf79156bbb8a2c26d77a1d2eJeffrey Yasskin (void)Value.convertToInteger(Result, llvm::APFloat::rmTowardZero, &ignored); 2303e1ef7849845a9e7bf79156bbb8a2c26d77a1d2eJeffrey Yasskin return Result; 231a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar} 232a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar 2331eb4433ac451dc16f4133a88af2d002ac26c58efMike Stumpstatic APFloat HandleFloatToFloatCast(QualType DestType, QualType SrcType, 2344ba2a17694148e16eaa8d3917f657ffcd3667be4Jay Foad APFloat &Value, const ASTContext &Ctx) { 235a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar bool ignored; 236a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar APFloat Result = Value; 2371eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump Result.convert(Ctx.getFloatTypeSemantics(DestType), 238a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar APFloat::rmNearestTiesToEven, &ignored); 239a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar return Result; 240a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar} 241a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar 2421eb4433ac451dc16f4133a88af2d002ac26c58efMike Stumpstatic APSInt HandleIntToIntCast(QualType DestType, QualType SrcType, 2434ba2a17694148e16eaa8d3917f657ffcd3667be4Jay Foad APSInt &Value, const ASTContext &Ctx) { 244a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar unsigned DestWidth = Ctx.getIntWidth(DestType); 245a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar APSInt Result = Value; 246a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar // Figure out if this is a truncate, extend or noop cast. 247a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar // If the input is signed, do a sign extend, noop, or truncate. 2489f71a8f4c7a182a5236da9e747d57cc1d1bd24c2Jay Foad Result = Result.extOrTrunc(DestWidth); 249575a1c9dc8dc5b4977194993e289f9eda7295c39Douglas Gregor Result.setIsUnsigned(DestType->isUnsignedIntegerOrEnumerationType()); 250a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar return Result; 251a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar} 252a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar 2531eb4433ac451dc16f4133a88af2d002ac26c58efMike Stumpstatic APFloat HandleIntToFloatCast(QualType DestType, QualType SrcType, 2544ba2a17694148e16eaa8d3917f657ffcd3667be4Jay Foad APSInt &Value, const ASTContext &Ctx) { 255a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar 256a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar APFloat Result(Ctx.getFloatTypeSemantics(DestType), 1); 257a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar Result.convertFromAPInt(Value, Value.isSigned(), 258a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar APFloat::rmNearestTiesToEven); 259a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar return Result; 260a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar} 261a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar 262c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stumpnamespace { 263770b4a8834670e9427d3ce5a1a8472eb86f45fd2Benjamin Kramerclass HasSideEffect 2648cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne : public ConstStmtVisitor<HasSideEffect, bool> { 265c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump EvalInfo &Info; 266c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stumppublic: 267c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump 268c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump HasSideEffect(EvalInfo &info) : Info(info) {} 269c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump 270c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump // Unhandled nodes conservatively default to having side effects. 2718cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitStmt(const Stmt *S) { 272c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump return true; 273c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump } 274c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump 2758cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitParenExpr(const ParenExpr *E) { return Visit(E->getSubExpr()); } 2768cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitGenericSelectionExpr(const GenericSelectionExpr *E) { 277f111d935722ed488144600cea5ed03a6b5069e8fPeter Collingbourne return Visit(E->getResultExpr()); 278f111d935722ed488144600cea5ed03a6b5069e8fPeter Collingbourne } 2798cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitDeclRefExpr(const DeclRefExpr *E) { 280df317bf71653eeb235da8337b1e8e790f9653aa4Mike Stump if (Info.Ctx.getCanonicalType(E->getType()).isVolatileQualified()) 281c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump return true; 282c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump return false; 283c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump } 284f85e193739c953358c865005855253af4f68a497John McCall bool VisitObjCIvarRefExpr(const ObjCIvarRefExpr *E) { 285f85e193739c953358c865005855253af4f68a497John McCall if (Info.Ctx.getCanonicalType(E->getType()).isVolatileQualified()) 286f85e193739c953358c865005855253af4f68a497John McCall return true; 287f85e193739c953358c865005855253af4f68a497John McCall return false; 288f85e193739c953358c865005855253af4f68a497John McCall } 289f85e193739c953358c865005855253af4f68a497John McCall bool VisitBlockDeclRefExpr (const BlockDeclRefExpr *E) { 290f85e193739c953358c865005855253af4f68a497John McCall if (Info.Ctx.getCanonicalType(E->getType()).isVolatileQualified()) 291f85e193739c953358c865005855253af4f68a497John McCall return true; 292f85e193739c953358c865005855253af4f68a497John McCall return false; 293f85e193739c953358c865005855253af4f68a497John McCall } 294f85e193739c953358c865005855253af4f68a497John McCall 295c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump // We don't want to evaluate BlockExprs multiple times, as they generate 296c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump // a ton of code. 2978cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitBlockExpr(const BlockExpr *E) { return true; } 2988cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitPredefinedExpr(const PredefinedExpr *E) { return false; } 2998cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitCompoundLiteralExpr(const CompoundLiteralExpr *E) 300c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump { return Visit(E->getInitializer()); } 3018cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitMemberExpr(const MemberExpr *E) { return Visit(E->getBase()); } 3028cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitIntegerLiteral(const IntegerLiteral *E) { return false; } 3038cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitFloatingLiteral(const FloatingLiteral *E) { return false; } 3048cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitStringLiteral(const StringLiteral *E) { return false; } 3058cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitCharacterLiteral(const CharacterLiteral *E) { return false; } 3068cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitUnaryExprOrTypeTraitExpr(const UnaryExprOrTypeTraitExpr *E) 307f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne { return false; } 3088cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitArraySubscriptExpr(const ArraySubscriptExpr *E) 309980ca220848d27ef55ef4c2d37423461a8ed0da3Mike Stump { return Visit(E->getLHS()) || Visit(E->getRHS()); } 3108cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitChooseExpr(const ChooseExpr *E) 311c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump { return Visit(E->getChosenSubExpr(Info.Ctx)); } 3128cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitCastExpr(const CastExpr *E) { return Visit(E->getSubExpr()); } 3138cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitBinAssign(const BinaryOperator *E) { return true; } 3148cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitCompoundAssignOperator(const BinaryOperator *E) { return true; } 3158cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitBinaryOperator(const BinaryOperator *E) 316980ca220848d27ef55ef4c2d37423461a8ed0da3Mike Stump { return Visit(E->getLHS()) || Visit(E->getRHS()); } 3178cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitUnaryPreInc(const UnaryOperator *E) { return true; } 3188cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitUnaryPostInc(const UnaryOperator *E) { return true; } 3198cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitUnaryPreDec(const UnaryOperator *E) { return true; } 3208cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitUnaryPostDec(const UnaryOperator *E) { return true; } 3218cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitUnaryDeref(const UnaryOperator *E) { 322df317bf71653eeb235da8337b1e8e790f9653aa4Mike Stump if (Info.Ctx.getCanonicalType(E->getType()).isVolatileQualified()) 323c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump return true; 324980ca220848d27ef55ef4c2d37423461a8ed0da3Mike Stump return Visit(E->getSubExpr()); 325c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump } 3268cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitUnaryOperator(const UnaryOperator *E) { return Visit(E->getSubExpr()); } 327363ff23cfddb51abe4ee4212a6dd3c9b534fcc8bChris Lattner 328363ff23cfddb51abe4ee4212a6dd3c9b534fcc8bChris Lattner // Has side effects if any element does. 3298cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitInitListExpr(const InitListExpr *E) { 330363ff23cfddb51abe4ee4212a6dd3c9b534fcc8bChris Lattner for (unsigned i = 0, e = E->getNumInits(); i != e; ++i) 331363ff23cfddb51abe4ee4212a6dd3c9b534fcc8bChris Lattner if (Visit(E->getInit(i))) return true; 3328cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne if (const Expr *filler = E->getArrayFiller()) 3334423ac0282acb8ba801eb05b38712438dc0c1e3eArgyrios Kyrtzidis return Visit(filler); 334363ff23cfddb51abe4ee4212a6dd3c9b534fcc8bChris Lattner return false; 335363ff23cfddb51abe4ee4212a6dd3c9b534fcc8bChris Lattner } 336ee8aff06f6a96214731de17b2cb6df407c6c1820Douglas Gregor 3378cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitSizeOfPackExpr(const SizeOfPackExpr *) { return false; } 338c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump}; 339c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump 34056ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCallclass OpaqueValueEvaluation { 34156ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall EvalInfo &info; 34256ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall OpaqueValueExpr *opaqueValue; 34356ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall 34456ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCallpublic: 34556ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall OpaqueValueEvaluation(EvalInfo &info, OpaqueValueExpr *opaqueValue, 34656ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall Expr *value) 34756ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall : info(info), opaqueValue(opaqueValue) { 34856ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall 34956ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall // If evaluation fails, fail immediately. 35056ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall if (!Evaluate(info, value)) { 35156ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall this->opaqueValue = 0; 35256ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall return; 35356ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall } 35456ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall info.OpaqueValues[opaqueValue] = info.EvalResult.Val; 35556ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall } 35656ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall 35756ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall bool hasError() const { return opaqueValue == 0; } 35856ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall 35956ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall ~OpaqueValueEvaluation() { 36056ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall if (opaqueValue) info.OpaqueValues.erase(opaqueValue); 36156ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall } 36256ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall}; 36356ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall 364c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump} // end anonymous namespace 365c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump 3664efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman//===----------------------------------------------------------------------===// 3678cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne// Generic Evaluation 3688cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne//===----------------------------------------------------------------------===// 3698cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbournenamespace { 3708cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne 3718cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbournetemplate <class Derived, typename RetTy=void> 3728cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourneclass ExprEvaluatorBase 3738cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne : public ConstStmtVisitor<Derived, RetTy> { 3748cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourneprivate: 3758cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne RetTy DerivedSuccess(const APValue &V, const Expr *E) { 3768cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne return static_cast<Derived*>(this)->Success(V, E); 3778cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne } 3788cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne RetTy DerivedError(const Expr *E) { 3798cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne return static_cast<Derived*>(this)->Error(E); 3808cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne } 3818cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne 3828cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourneprotected: 3838cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne EvalInfo &Info; 3848cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne typedef ConstStmtVisitor<Derived, RetTy> StmtVisitorTy; 3858cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne typedef ExprEvaluatorBase ExprEvaluatorBaseTy; 3868cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne 3878cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbournepublic: 3888cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne ExprEvaluatorBase(EvalInfo &Info) : Info(Info) {} 3898cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne 3908cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne RetTy VisitStmt(const Stmt *) { 391b219cfc4d75f0a03630b7c4509ef791b7e97b2c8David Blaikie llvm_unreachable("Expression evaluator should not be called on stmts"); 3928cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne } 3938cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne RetTy VisitExpr(const Expr *E) { 3948cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne return DerivedError(E); 3958cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne } 3968cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne 3978cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne RetTy VisitParenExpr(const ParenExpr *E) 3988cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne { return StmtVisitorTy::Visit(E->getSubExpr()); } 3998cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne RetTy VisitUnaryExtension(const UnaryOperator *E) 4008cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne { return StmtVisitorTy::Visit(E->getSubExpr()); } 4018cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne RetTy VisitUnaryPlus(const UnaryOperator *E) 4028cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne { return StmtVisitorTy::Visit(E->getSubExpr()); } 4038cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne RetTy VisitChooseExpr(const ChooseExpr *E) 4048cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne { return StmtVisitorTy::Visit(E->getChosenSubExpr(Info.Ctx)); } 4058cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne RetTy VisitGenericSelectionExpr(const GenericSelectionExpr *E) 4068cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne { return StmtVisitorTy::Visit(E->getResultExpr()); } 40791a5755ad73c5dc1dfb167e448fdd74e75a6df56John McCall RetTy VisitSubstNonTypeTemplateParmExpr(const SubstNonTypeTemplateParmExpr *E) 40891a5755ad73c5dc1dfb167e448fdd74e75a6df56John McCall { return StmtVisitorTy::Visit(E->getReplacement()); } 4098cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne 4108cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne RetTy VisitBinaryConditionalOperator(const BinaryConditionalOperator *E) { 4118cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne OpaqueValueEvaluation opaque(Info, E->getOpaqueValue(), E->getCommon()); 4128cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne if (opaque.hasError()) 4138cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne return DerivedError(E); 4148cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne 4158cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool cond; 4168cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne if (!HandleConversionToBool(E->getCond(), cond, Info)) 4178cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne return DerivedError(E); 4188cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne 4198cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne return StmtVisitorTy::Visit(cond ? E->getTrueExpr() : E->getFalseExpr()); 4208cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne } 4218cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne 4228cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne RetTy VisitConditionalOperator(const ConditionalOperator *E) { 4238cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool BoolResult; 4248cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne if (!HandleConversionToBool(E->getCond(), BoolResult, Info)) 4258cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne return DerivedError(E); 4268cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne 4278cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne Expr* EvalExpr = BoolResult ? E->getTrueExpr() : E->getFalseExpr(); 4288cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne return StmtVisitorTy::Visit(EvalExpr); 4298cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne } 4308cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne 4318cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne RetTy VisitOpaqueValueExpr(const OpaqueValueExpr *E) { 4328cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne const APValue *value = Info.getOpaqueValue(E); 4338cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne if (!value) 4348cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne return (E->getSourceExpr() ? StmtVisitorTy::Visit(E->getSourceExpr()) 4358cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne : DerivedError(E)); 4368cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne return DerivedSuccess(*value, E); 4378cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne } 4388cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne}; 4398cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne 4408cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne} 4418cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne 4428cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne//===----------------------------------------------------------------------===// 4434efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman// LValue Evaluation 4444efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman//===----------------------------------------------------------------------===// 4454efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedmannamespace { 446770b4a8834670e9427d3ce5a1a8472eb86f45fd2Benjamin Kramerclass LValueExprEvaluator 4478cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne : public ExprEvaluatorBase<LValueExprEvaluator, bool> { 448efdb83e26f9a1fd2566afe54461216cd84814d42John McCall LValue &Result; 4490124839d7fb3d846795190ba2ccf3951f27784feChandler Carruth const Decl *PrevDecl; 450efdb83e26f9a1fd2566afe54461216cd84814d42John McCall 4518cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool Success(const Expr *E) { 452efdb83e26f9a1fd2566afe54461216cd84814d42John McCall Result.Base = E; 453efdb83e26f9a1fd2566afe54461216cd84814d42John McCall Result.Offset = CharUnits::Zero(); 454efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return true; 455efdb83e26f9a1fd2566afe54461216cd84814d42John McCall } 4564efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedmanpublic: 4571eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 458efdb83e26f9a1fd2566afe54461216cd84814d42John McCall LValueExprEvaluator(EvalInfo &info, LValue &Result) : 4590124839d7fb3d846795190ba2ccf3951f27784feChandler Carruth ExprEvaluatorBaseTy(info), Result(Result), PrevDecl(0) {} 4604efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman 4618cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool Success(const APValue &V, const Expr *E) { 4628cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne Result.setFrom(V); 4638cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne return true; 4648cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne } 4658cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool Error(const Expr *E) { 466efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return false; 4674efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman } 4688ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor 4698cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitDeclRefExpr(const DeclRefExpr *E); 4708cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitPredefinedExpr(const PredefinedExpr *E) { return Success(E); } 4718cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitCompoundLiteralExpr(const CompoundLiteralExpr *E); 4728cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitMemberExpr(const MemberExpr *E); 4738cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitStringLiteral(const StringLiteral *E) { return Success(E); } 4748cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitObjCEncodeExpr(const ObjCEncodeExpr *E) { return Success(E); } 4758cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitArraySubscriptExpr(const ArraySubscriptExpr *E); 4768cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitUnaryDeref(const UnaryOperator *E); 4778cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne 4788cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitCastExpr(const CastExpr *E) { 47926bc220377705292a0519a71d3ea3aef68fcfec6Anders Carlsson switch (E->getCastKind()) { 48026bc220377705292a0519a71d3ea3aef68fcfec6Anders Carlsson default: 481efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return false; 48226bc220377705292a0519a71d3ea3aef68fcfec6Anders Carlsson 4832de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case CK_NoOp: 48426bc220377705292a0519a71d3ea3aef68fcfec6Anders Carlsson return Visit(E->getSubExpr()); 48526bc220377705292a0519a71d3ea3aef68fcfec6Anders Carlsson } 48626bc220377705292a0519a71d3ea3aef68fcfec6Anders Carlsson } 487cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl 488cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl bool VisitInitListExpr(const InitListExpr *E) { 489cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl if (Info.Ctx.getLangOptions().CPlusPlus0x && E->getNumInits() == 1) 490cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl return Visit(E->getInit(0)); 491cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl return Error(E); 492cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl } 493cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl 494ba98d6bb414861965a1f22628494ea046785ecd4Eli Friedman // FIXME: Missing: __real__, __imag__ 4958cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne 4964efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman}; 4974efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman} // end anonymous namespace 4984efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman 499efdb83e26f9a1fd2566afe54461216cd84814d42John McCallstatic bool EvaluateLValue(const Expr* E, LValue& Result, EvalInfo &Info) { 5008cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne return LValueExprEvaluator(Info, Result).Visit(E); 5014efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman} 5024efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman 5038cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbournebool LValueExprEvaluator::VisitDeclRefExpr(const DeclRefExpr *E) { 50450c39ea4858265f3f5f42a0c624557ce2281936bEli Friedman if (isa<FunctionDecl>(E->getDecl())) { 505efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return Success(E); 5068cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne } else if (const VarDecl* VD = dyn_cast<VarDecl>(E->getDecl())) { 50750c39ea4858265f3f5f42a0c624557ce2281936bEli Friedman if (!VD->getType()->isReferenceType()) 508efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return Success(E); 509761c94e3bffef0fcb8b4bbf202fd5ee73db134f3Chandler Carruth // Reference parameters can refer to anything even if they have an 510761c94e3bffef0fcb8b4bbf202fd5ee73db134f3Chandler Carruth // "initializer" in the form of a default argument. 5110124839d7fb3d846795190ba2ccf3951f27784feChandler Carruth if (!isa<ParmVarDecl>(VD)) { 5128cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne // FIXME: Check whether VD might be overridden! 5130124839d7fb3d846795190ba2ccf3951f27784feChandler Carruth 5140124839d7fb3d846795190ba2ccf3951f27784feChandler Carruth // Check for recursive initializers of references. 5150124839d7fb3d846795190ba2ccf3951f27784feChandler Carruth if (PrevDecl == VD) 5160124839d7fb3d846795190ba2ccf3951f27784feChandler Carruth return Error(E); 5170124839d7fb3d846795190ba2ccf3951f27784feChandler Carruth PrevDecl = VD; 5188cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne if (const Expr *Init = VD->getAnyInitializer()) 5198cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne return Visit(Init); 5200124839d7fb3d846795190ba2ccf3951f27784feChandler Carruth } 52150c39ea4858265f3f5f42a0c624557ce2281936bEli Friedman } 52250c39ea4858265f3f5f42a0c624557ce2281936bEli Friedman 5238cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne return ExprEvaluatorBaseTy::VisitDeclRefExpr(E); 52435873c49adad211ff466e34342a52665742794f5Anders Carlsson} 52535873c49adad211ff466e34342a52665742794f5Anders Carlsson 5268cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbournebool 5278cad3046be06ea73ff8892d947697a21d7a440d3Peter CollingbourneLValueExprEvaluator::VisitCompoundLiteralExpr(const CompoundLiteralExpr *E) { 528efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return Success(E); 5294efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman} 5304efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman 5318cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbournebool LValueExprEvaluator::VisitMemberExpr(const MemberExpr *E) { 5324efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman QualType Ty; 5334efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman if (E->isArrow()) { 534efdb83e26f9a1fd2566afe54461216cd84814d42John McCall if (!EvaluatePointer(E->getBase(), Result, Info)) 535efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return false; 5366217b80b7a1379b74cced1c076338262c3c980b3Ted Kremenek Ty = E->getBase()->getType()->getAs<PointerType>()->getPointeeType(); 5374efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman } else { 538efdb83e26f9a1fd2566afe54461216cd84814d42John McCall if (!Visit(E->getBase())) 539efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return false; 5404efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman Ty = E->getBase()->getType(); 5414efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman } 5424efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman 5438cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne const RecordDecl *RD = Ty->getAs<RecordType>()->getDecl(); 5444efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman const ASTRecordLayout &RL = Info.Ctx.getASTRecordLayout(RD); 54586f194083504938df72135b5b66bf0c5cafd9498Douglas Gregor 5468cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne const FieldDecl *FD = dyn_cast<FieldDecl>(E->getMemberDecl()); 54786f194083504938df72135b5b66bf0c5cafd9498Douglas Gregor if (!FD) // FIXME: deal with other kinds of member expressions 548efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return false; 5492be586108bb401019647791feca19ea03fd477ceEli Friedman 5502be586108bb401019647791feca19ea03fd477ceEli Friedman if (FD->getType()->isReferenceType()) 551efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return false; 5522be586108bb401019647791feca19ea03fd477ceEli Friedman 55382905749d5c8d8b4edec11de754a73349cb96603Eli Friedman unsigned i = FD->getFieldIndex(); 554fb1e3bc29b667f4275e1d5a43d64ec173f4f9a7dKen Dyck Result.Offset += Info.Ctx.toCharUnitsFromBits(RL.getFieldOffset(i)); 555efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return true; 5564efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman} 5574efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman 5588cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbournebool LValueExprEvaluator::VisitArraySubscriptExpr(const ArraySubscriptExpr *E) { 5593068d117951a8df54bae9db039b56201ab10962bAnders Carlsson if (!EvaluatePointer(E->getBase(), Result, Info)) 560efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return false; 5611eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 5623068d117951a8df54bae9db039b56201ab10962bAnders Carlsson APSInt Index; 5633068d117951a8df54bae9db039b56201ab10962bAnders Carlsson if (!EvaluateInteger(E->getIdx(), Index, Info)) 564efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return false; 5653068d117951a8df54bae9db039b56201ab10962bAnders Carlsson 566199c3d6cd16aebbb9c7f0d42af9d922c9628bf70Ken Dyck CharUnits ElementSize = Info.Ctx.getTypeSizeInChars(E->getType()); 567efdb83e26f9a1fd2566afe54461216cd84814d42John McCall Result.Offset += Index.getSExtValue() * ElementSize; 568efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return true; 5693068d117951a8df54bae9db039b56201ab10962bAnders Carlsson} 5704efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman 5718cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbournebool LValueExprEvaluator::VisitUnaryDeref(const UnaryOperator *E) { 572efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return EvaluatePointer(E->getSubExpr(), Result, Info); 573e8761c8fe2ee6b628104a0885f49fd3c21c08a4fEli Friedman} 574e8761c8fe2ee6b628104a0885f49fd3c21c08a4fEli Friedman 5754efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman//===----------------------------------------------------------------------===// 576f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner// Pointer Evaluation 577f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner//===----------------------------------------------------------------------===// 578f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner 579c754aa62643e66ab967ca32ae8b0b3fc419bba25Anders Carlssonnamespace { 580770b4a8834670e9427d3ce5a1a8472eb86f45fd2Benjamin Kramerclass PointerExprEvaluator 5818cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne : public ExprEvaluatorBase<PointerExprEvaluator, bool> { 582efdb83e26f9a1fd2566afe54461216cd84814d42John McCall LValue &Result; 583efdb83e26f9a1fd2566afe54461216cd84814d42John McCall 5848cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool Success(const Expr *E) { 585efdb83e26f9a1fd2566afe54461216cd84814d42John McCall Result.Base = E; 586efdb83e26f9a1fd2566afe54461216cd84814d42John McCall Result.Offset = CharUnits::Zero(); 587efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return true; 588efdb83e26f9a1fd2566afe54461216cd84814d42John McCall } 5892bad1687fe6f00e10767a691a33b070b151902b6Anders Carlssonpublic: 5901eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 591efdb83e26f9a1fd2566afe54461216cd84814d42John McCall PointerExprEvaluator(EvalInfo &info, LValue &Result) 5928cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne : ExprEvaluatorBaseTy(info), Result(Result) {} 593f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner 5948cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool Success(const APValue &V, const Expr *E) { 5958cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne Result.setFrom(V); 5968cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne return true; 5972bad1687fe6f00e10767a691a33b070b151902b6Anders Carlsson } 5988cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool Error(const Stmt *S) { 5998cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne return false; 600f111d935722ed488144600cea5ed03a6b5069e8fPeter Collingbourne } 6012bad1687fe6f00e10767a691a33b070b151902b6Anders Carlsson 602efdb83e26f9a1fd2566afe54461216cd84814d42John McCall bool VisitBinaryOperator(const BinaryOperator *E); 6038cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitCastExpr(const CastExpr* E); 604efdb83e26f9a1fd2566afe54461216cd84814d42John McCall bool VisitUnaryAddrOf(const UnaryOperator *E); 6058cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitObjCStringLiteral(const ObjCStringLiteral *E) 606efdb83e26f9a1fd2566afe54461216cd84814d42John McCall { return Success(E); } 6078cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitAddrLabelExpr(const AddrLabelExpr *E) 608efdb83e26f9a1fd2566afe54461216cd84814d42John McCall { return Success(E); } 6098cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitCallExpr(const CallExpr *E); 6108cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitBlockExpr(const BlockExpr *E) { 611469a1eb996e1cb0be54f9b210f836afbddcbb2ccJohn McCall if (!E->getBlockDecl()->hasCaptures()) 612efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return Success(E); 613efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return false; 614b83d287bc7f47d36fb0751a481e2ef9308b37252Mike Stump } 6158cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitImplicitValueInitExpr(const ImplicitValueInitExpr *E) 616efdb83e26f9a1fd2566afe54461216cd84814d42John McCall { return Success((Expr*)0); } 6178cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitCXXNullPtrLiteralExpr(const CXXNullPtrLiteralExpr *E) 618efdb83e26f9a1fd2566afe54461216cd84814d42John McCall { return Success((Expr*)0); } 619620b9338dce31ace41f2f1fa491def3043412568Peter Collingbourne bool VisitCXXScalarValueInitExpr(const CXXScalarValueInitExpr *E) 620620b9338dce31ace41f2f1fa491def3043412568Peter Collingbourne { return Success((Expr*)0); } 62156ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall 622ba98d6bb414861965a1f22628494ea046785ecd4Eli Friedman // FIXME: Missing: @protocol, @selector 6232bad1687fe6f00e10767a691a33b070b151902b6Anders Carlsson}; 624f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner} // end anonymous namespace 6252bad1687fe6f00e10767a691a33b070b151902b6Anders Carlsson 626efdb83e26f9a1fd2566afe54461216cd84814d42John McCallstatic bool EvaluatePointer(const Expr* E, LValue& Result, EvalInfo &Info) { 6277db7acbbb84b82d0522266a50ebabc3a52a9e5d1John McCall assert(E->getType()->hasPointerRepresentation()); 6288cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne return PointerExprEvaluator(Info, Result).Visit(E); 629f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner} 630650c92fdcc27a950a8a848ecab6a74e6f5e80788Anders Carlsson 631efdb83e26f9a1fd2566afe54461216cd84814d42John McCallbool PointerExprEvaluator::VisitBinaryOperator(const BinaryOperator *E) { 6322de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall if (E->getOpcode() != BO_Add && 6332de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall E->getOpcode() != BO_Sub) 634efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return false; 6351eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 636650c92fdcc27a950a8a848ecab6a74e6f5e80788Anders Carlsson const Expr *PExp = E->getLHS(); 637650c92fdcc27a950a8a848ecab6a74e6f5e80788Anders Carlsson const Expr *IExp = E->getRHS(); 638650c92fdcc27a950a8a848ecab6a74e6f5e80788Anders Carlsson if (IExp->getType()->isPointerType()) 639f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner std::swap(PExp, IExp); 6401eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 641efdb83e26f9a1fd2566afe54461216cd84814d42John McCall if (!EvaluatePointer(PExp, Result, Info)) 642efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return false; 6431eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 644efdb83e26f9a1fd2566afe54461216cd84814d42John McCall llvm::APSInt Offset; 645efdb83e26f9a1fd2566afe54461216cd84814d42John McCall if (!EvaluateInteger(IExp, Offset, Info)) 646efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return false; 647efdb83e26f9a1fd2566afe54461216cd84814d42John McCall int64_t AdditionalOffset 648efdb83e26f9a1fd2566afe54461216cd84814d42John McCall = Offset.isSigned() ? Offset.getSExtValue() 649efdb83e26f9a1fd2566afe54461216cd84814d42John McCall : static_cast<int64_t>(Offset.getZExtValue()); 650650c92fdcc27a950a8a848ecab6a74e6f5e80788Anders Carlsson 651e0cdb4edd8f265d0fd22d178d03c597dd201cda2Daniel Dunbar // Compute the new offset in the appropriate width. 652e0cdb4edd8f265d0fd22d178d03c597dd201cda2Daniel Dunbar 653e0cdb4edd8f265d0fd22d178d03c597dd201cda2Daniel Dunbar QualType PointeeType = 654e0cdb4edd8f265d0fd22d178d03c597dd201cda2Daniel Dunbar PExp->getType()->getAs<PointerType>()->getPointeeType(); 655efdb83e26f9a1fd2566afe54461216cd84814d42John McCall CharUnits SizeOfPointee; 6561eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 6574d4c50dd8b4db191c38782414665fb7608315a36Anders Carlsson // Explicitly handle GNU void* and function pointer arithmetic extensions. 6584d4c50dd8b4db191c38782414665fb7608315a36Anders Carlsson if (PointeeType->isVoidType() || PointeeType->isFunctionType()) 659efdb83e26f9a1fd2566afe54461216cd84814d42John McCall SizeOfPointee = CharUnits::One(); 6604d4c50dd8b4db191c38782414665fb7608315a36Anders Carlsson else 661efdb83e26f9a1fd2566afe54461216cd84814d42John McCall SizeOfPointee = Info.Ctx.getTypeSizeInChars(PointeeType); 6624efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman 6632de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall if (E->getOpcode() == BO_Add) 664efdb83e26f9a1fd2566afe54461216cd84814d42John McCall Result.Offset += AdditionalOffset * SizeOfPointee; 665650c92fdcc27a950a8a848ecab6a74e6f5e80788Anders Carlsson else 666efdb83e26f9a1fd2566afe54461216cd84814d42John McCall Result.Offset -= AdditionalOffset * SizeOfPointee; 6674efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman 668efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return true; 669650c92fdcc27a950a8a848ecab6a74e6f5e80788Anders Carlsson} 6704efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman 671efdb83e26f9a1fd2566afe54461216cd84814d42John McCallbool PointerExprEvaluator::VisitUnaryAddrOf(const UnaryOperator *E) { 672efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return EvaluateLValue(E->getSubExpr(), Result, Info); 6734efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman} 6741eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 675650c92fdcc27a950a8a848ecab6a74e6f5e80788Anders Carlsson 6768cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbournebool PointerExprEvaluator::VisitCastExpr(const CastExpr* E) { 6778cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne const Expr* SubExpr = E->getSubExpr(); 678650c92fdcc27a950a8a848ecab6a74e6f5e80788Anders Carlsson 67909a8a0e6ec1252cad52666e9dbb21002b9c80f38Eli Friedman switch (E->getCastKind()) { 68009a8a0e6ec1252cad52666e9dbb21002b9c80f38Eli Friedman default: 68109a8a0e6ec1252cad52666e9dbb21002b9c80f38Eli Friedman break; 68209a8a0e6ec1252cad52666e9dbb21002b9c80f38Eli Friedman 6832de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case CK_NoOp: 6842de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case CK_BitCast: 6851d9b3b25f7ac0d0195bba6b507a684fe5e7943eeJohn McCall case CK_CPointerToObjCPointerCast: 6861d9b3b25f7ac0d0195bba6b507a684fe5e7943eeJohn McCall case CK_BlockPointerToObjCPointerCast: 6872de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case CK_AnyPointerToBlockPointerCast: 68809a8a0e6ec1252cad52666e9dbb21002b9c80f38Eli Friedman return Visit(SubExpr); 68909a8a0e6ec1252cad52666e9dbb21002b9c80f38Eli Friedman 6905c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson case CK_DerivedToBase: 6915c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson case CK_UncheckedDerivedToBase: { 6925c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson LValue BaseLV; 6935c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson if (!EvaluatePointer(E->getSubExpr(), BaseLV, Info)) 6945c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson return false; 6955c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson 6965c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson // Now figure out the necessary offset to add to the baseLV to get from 6975c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson // the derived class to the base class. 6987c7f820d70c925b29290a8563b59615816a827fcKen Dyck CharUnits Offset = CharUnits::Zero(); 6995c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson 7005c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson QualType Ty = E->getSubExpr()->getType(); 7015c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson const CXXRecordDecl *DerivedDecl = 7025c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson Ty->getAs<PointerType>()->getPointeeType()->getAsCXXRecordDecl(); 7035c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson 7045c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson for (CastExpr::path_const_iterator PathI = E->path_begin(), 7055c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson PathE = E->path_end(); PathI != PathE; ++PathI) { 7065c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson const CXXBaseSpecifier *Base = *PathI; 7075c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson 7085c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson // FIXME: If the base is virtual, we'd need to determine the type of the 7095c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson // most derived class and we don't support that right now. 7105c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson if (Base->isVirtual()) 7115c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson return false; 7125c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson 7135c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson const CXXRecordDecl *BaseDecl = Base->getType()->getAsCXXRecordDecl(); 7145c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson const ASTRecordLayout &Layout = Info.Ctx.getASTRecordLayout(DerivedDecl); 7155c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson 7167c7f820d70c925b29290a8563b59615816a827fcKen Dyck Offset += Layout.getBaseClassOffset(BaseDecl); 7175c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson DerivedDecl = BaseDecl; 7185c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson } 7195c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson 7205c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson Result.Base = BaseLV.getLValueBase(); 7217c7f820d70c925b29290a8563b59615816a827fcKen Dyck Result.Offset = BaseLV.getLValueOffset() + Offset; 7225c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson return true; 7235c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson } 7245c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson 725404cd1669c3ba138a9ae0a619bd689cce5aae271John McCall case CK_NullToPointer: { 726404cd1669c3ba138a9ae0a619bd689cce5aae271John McCall Result.Base = 0; 727404cd1669c3ba138a9ae0a619bd689cce5aae271John McCall Result.Offset = CharUnits::Zero(); 728404cd1669c3ba138a9ae0a619bd689cce5aae271John McCall return true; 729404cd1669c3ba138a9ae0a619bd689cce5aae271John McCall } 730404cd1669c3ba138a9ae0a619bd689cce5aae271John McCall 7312de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case CK_IntegralToPointer: { 732efdb83e26f9a1fd2566afe54461216cd84814d42John McCall APValue Value; 733efdb83e26f9a1fd2566afe54461216cd84814d42John McCall if (!EvaluateIntegerOrLValue(SubExpr, Value, Info)) 73409a8a0e6ec1252cad52666e9dbb21002b9c80f38Eli Friedman break; 73569ab26a8623141f35e86817cfc6e0fbe7639a40fDaniel Dunbar 736efdb83e26f9a1fd2566afe54461216cd84814d42John McCall if (Value.isInt()) { 7379f71a8f4c7a182a5236da9e747d57cc1d1bd24c2Jay Foad Value.getInt() = Value.getInt().extOrTrunc((unsigned)Info.Ctx.getTypeSize(E->getType())); 738efdb83e26f9a1fd2566afe54461216cd84814d42John McCall Result.Base = 0; 739efdb83e26f9a1fd2566afe54461216cd84814d42John McCall Result.Offset = CharUnits::fromQuantity(Value.getInt().getZExtValue()); 740efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return true; 741efdb83e26f9a1fd2566afe54461216cd84814d42John McCall } else { 742efdb83e26f9a1fd2566afe54461216cd84814d42John McCall // Cast is of an lvalue, no need to change value. 743efdb83e26f9a1fd2566afe54461216cd84814d42John McCall Result.Base = Value.getLValueBase(); 744efdb83e26f9a1fd2566afe54461216cd84814d42John McCall Result.Offset = Value.getLValueOffset(); 745efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return true; 746650c92fdcc27a950a8a848ecab6a74e6f5e80788Anders Carlsson } 747650c92fdcc27a950a8a848ecab6a74e6f5e80788Anders Carlsson } 7482de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case CK_ArrayToPointerDecay: 7492de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case CK_FunctionToPointerDecay: 750efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return EvaluateLValue(SubExpr, Result, Info); 7514efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman } 7524efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman 753efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return false; 7541eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump} 755650c92fdcc27a950a8a848ecab6a74e6f5e80788Anders Carlsson 7568cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbournebool PointerExprEvaluator::VisitCallExpr(const CallExpr *E) { 7571eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump if (E->isBuiltinCall(Info.Ctx) == 7580d13f6fdbdd6f06e2449b8834dda53334abd399aDavid Chisnall Builtin::BI__builtin___CFStringMakeConstantString || 7590d13f6fdbdd6f06e2449b8834dda53334abd399aDavid Chisnall E->isBuiltinCall(Info.Ctx) == 7600d13f6fdbdd6f06e2449b8834dda53334abd399aDavid Chisnall Builtin::BI__builtin___NSStringMakeConstantString) 761efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return Success(E); 76256ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall 7638cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne return ExprEvaluatorBaseTy::VisitCallExpr(E); 7644efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman} 765f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner 766f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner//===----------------------------------------------------------------------===// 76759b5da6d853b4368b984700315adf7b37de05764Nate Begeman// Vector Evaluation 76859b5da6d853b4368b984700315adf7b37de05764Nate Begeman//===----------------------------------------------------------------------===// 76959b5da6d853b4368b984700315adf7b37de05764Nate Begeman 77059b5da6d853b4368b984700315adf7b37de05764Nate Begemannamespace { 771770b4a8834670e9427d3ce5a1a8472eb86f45fd2Benjamin Kramer class VectorExprEvaluator 7728cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne : public ExprEvaluatorBase<VectorExprEvaluator, APValue> { 77391110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman APValue GetZeroVector(QualType VecType); 77459b5da6d853b4368b984700315adf7b37de05764Nate Begeman public: 7751eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 7768cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne VectorExprEvaluator(EvalInfo &info) : ExprEvaluatorBaseTy(info) {} 7771eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 7788cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne APValue Success(const APValue &V, const Expr *E) { return V; } 7798cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne APValue Error(const Expr *E) { return APValue(); } 7801eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 78191110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman APValue VisitUnaryReal(const UnaryOperator *E) 78291110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman { return Visit(E->getSubExpr()); } 78391110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman APValue VisitImplicitValueInitExpr(const ImplicitValueInitExpr *E) 78491110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman { return GetZeroVector(E->getType()); } 78559b5da6d853b4368b984700315adf7b37de05764Nate Begeman APValue VisitCastExpr(const CastExpr* E); 78659b5da6d853b4368b984700315adf7b37de05764Nate Begeman APValue VisitCompoundLiteralExpr(const CompoundLiteralExpr *E); 78759b5da6d853b4368b984700315adf7b37de05764Nate Begeman APValue VisitInitListExpr(const InitListExpr *E); 78891110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman APValue VisitUnaryImag(const UnaryOperator *E); 78991110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman // FIXME: Missing: unary -, unary ~, binary add/sub/mul/div, 7902217c87bdc5ab357046a5453bdb06f469c41024eEli Friedman // binary comparisons, binary and/or/xor, 79191110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman // shufflevector, ExtVectorElementExpr 79291110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman // (Note that these require implementing conversions 79391110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman // between vector types.) 79459b5da6d853b4368b984700315adf7b37de05764Nate Begeman }; 79559b5da6d853b4368b984700315adf7b37de05764Nate Begeman} // end anonymous namespace 79659b5da6d853b4368b984700315adf7b37de05764Nate Begeman 79759b5da6d853b4368b984700315adf7b37de05764Nate Begemanstatic bool EvaluateVector(const Expr* E, APValue& Result, EvalInfo &Info) { 79859b5da6d853b4368b984700315adf7b37de05764Nate Begeman if (!E->getType()->isVectorType()) 79959b5da6d853b4368b984700315adf7b37de05764Nate Begeman return false; 8008cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne Result = VectorExprEvaluator(Info).Visit(E); 80159b5da6d853b4368b984700315adf7b37de05764Nate Begeman return !Result.isUninit(); 80259b5da6d853b4368b984700315adf7b37de05764Nate Begeman} 80359b5da6d853b4368b984700315adf7b37de05764Nate Begeman 80459b5da6d853b4368b984700315adf7b37de05764Nate BegemanAPValue VectorExprEvaluator::VisitCastExpr(const CastExpr* E) { 805183700f494ec9b6701b6efe82bcb25f4c79ba561John McCall const VectorType *VTy = E->getType()->getAs<VectorType>(); 806c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman QualType EltTy = VTy->getElementType(); 807c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman unsigned NElts = VTy->getNumElements(); 808c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman unsigned EltWidth = Info.Ctx.getTypeSize(EltTy); 8091eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 81059b5da6d853b4368b984700315adf7b37de05764Nate Begeman const Expr* SE = E->getSubExpr(); 811e8c9e9218f215ec6089f12b076c7b9d310fd5194Nate Begeman QualType SETy = SE->getType(); 81259b5da6d853b4368b984700315adf7b37de05764Nate Begeman 81346a523285928aa07bf14803178dc04616ac85994Eli Friedman switch (E->getCastKind()) { 81446a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_VectorSplat: { 81546a523285928aa07bf14803178dc04616ac85994Eli Friedman APValue Result = APValue(); 81646a523285928aa07bf14803178dc04616ac85994Eli Friedman if (SETy->isIntegerType()) { 81746a523285928aa07bf14803178dc04616ac85994Eli Friedman APSInt IntResult; 81846a523285928aa07bf14803178dc04616ac85994Eli Friedman if (!EvaluateInteger(SE, IntResult, Info)) 81946a523285928aa07bf14803178dc04616ac85994Eli Friedman return APValue(); 82046a523285928aa07bf14803178dc04616ac85994Eli Friedman Result = APValue(IntResult); 82146a523285928aa07bf14803178dc04616ac85994Eli Friedman } else if (SETy->isRealFloatingType()) { 82246a523285928aa07bf14803178dc04616ac85994Eli Friedman APFloat F(0.0); 82346a523285928aa07bf14803178dc04616ac85994Eli Friedman if (!EvaluateFloat(SE, F, Info)) 82446a523285928aa07bf14803178dc04616ac85994Eli Friedman return APValue(); 82546a523285928aa07bf14803178dc04616ac85994Eli Friedman Result = APValue(F); 82646a523285928aa07bf14803178dc04616ac85994Eli Friedman } else { 8270254e70b189a2400648d1cc53e279cc3786186e8Anders Carlsson return APValue(); 82846a523285928aa07bf14803178dc04616ac85994Eli Friedman } 829c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman 830c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman // Splat and create vector APValue. 8315f9e272e632e951b1efe824cd16acb4d96077930Chris Lattner SmallVector<APValue, 4> Elts(NElts, Result); 832c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman return APValue(&Elts[0], Elts.size()); 833e8c9e9218f215ec6089f12b076c7b9d310fd5194Nate Begeman } 83446a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_BitCast: { 83546a523285928aa07bf14803178dc04616ac85994Eli Friedman if (SETy->isVectorType()) 8368cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne return Visit(SE); 837c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman 83846a523285928aa07bf14803178dc04616ac85994Eli Friedman if (!SETy->isIntegerType()) 8390254e70b189a2400648d1cc53e279cc3786186e8Anders Carlsson return APValue(); 8401eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 84146a523285928aa07bf14803178dc04616ac85994Eli Friedman APSInt Init; 84246a523285928aa07bf14803178dc04616ac85994Eli Friedman if (!EvaluateInteger(SE, Init, Info)) 843c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman return APValue(); 844c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman 84546a523285928aa07bf14803178dc04616ac85994Eli Friedman assert((EltTy->isIntegerType() || EltTy->isRealFloatingType()) && 84646a523285928aa07bf14803178dc04616ac85994Eli Friedman "Vectors must be composed of ints or floats"); 84746a523285928aa07bf14803178dc04616ac85994Eli Friedman 8485f9e272e632e951b1efe824cd16acb4d96077930Chris Lattner SmallVector<APValue, 4> Elts; 84946a523285928aa07bf14803178dc04616ac85994Eli Friedman for (unsigned i = 0; i != NElts; ++i) { 85046a523285928aa07bf14803178dc04616ac85994Eli Friedman APSInt Tmp = Init.extOrTrunc(EltWidth); 85146a523285928aa07bf14803178dc04616ac85994Eli Friedman 85246a523285928aa07bf14803178dc04616ac85994Eli Friedman if (EltTy->isIntegerType()) 85346a523285928aa07bf14803178dc04616ac85994Eli Friedman Elts.push_back(APValue(Tmp)); 85446a523285928aa07bf14803178dc04616ac85994Eli Friedman else 85546a523285928aa07bf14803178dc04616ac85994Eli Friedman Elts.push_back(APValue(APFloat(Tmp))); 85646a523285928aa07bf14803178dc04616ac85994Eli Friedman 85746a523285928aa07bf14803178dc04616ac85994Eli Friedman Init >>= EltWidth; 85846a523285928aa07bf14803178dc04616ac85994Eli Friedman } 85946a523285928aa07bf14803178dc04616ac85994Eli Friedman return APValue(&Elts[0], Elts.size()); 86046a523285928aa07bf14803178dc04616ac85994Eli Friedman } 86146a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_LValueToRValue: 86246a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_NoOp: 8638cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne return Visit(SE); 86446a523285928aa07bf14803178dc04616ac85994Eli Friedman default: 8650254e70b189a2400648d1cc53e279cc3786186e8Anders Carlsson return APValue(); 866c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman } 86759b5da6d853b4368b984700315adf7b37de05764Nate Begeman} 86859b5da6d853b4368b984700315adf7b37de05764Nate Begeman 8691eb4433ac451dc16f4133a88af2d002ac26c58efMike StumpAPValue 87059b5da6d853b4368b984700315adf7b37de05764Nate BegemanVectorExprEvaluator::VisitCompoundLiteralExpr(const CompoundLiteralExpr *E) { 8718cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne return this->Visit(E->getInitializer()); 87259b5da6d853b4368b984700315adf7b37de05764Nate Begeman} 87359b5da6d853b4368b984700315adf7b37de05764Nate Begeman 8741eb4433ac451dc16f4133a88af2d002ac26c58efMike StumpAPValue 87559b5da6d853b4368b984700315adf7b37de05764Nate BegemanVectorExprEvaluator::VisitInitListExpr(const InitListExpr *E) { 876183700f494ec9b6701b6efe82bcb25f4c79ba561John McCall const VectorType *VT = E->getType()->getAs<VectorType>(); 87759b5da6d853b4368b984700315adf7b37de05764Nate Begeman unsigned NumInits = E->getNumInits(); 87891110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman unsigned NumElements = VT->getNumElements(); 8791eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 88059b5da6d853b4368b984700315adf7b37de05764Nate Begeman QualType EltTy = VT->getElementType(); 8815f9e272e632e951b1efe824cd16acb4d96077930Chris Lattner SmallVector<APValue, 4> Elements; 88259b5da6d853b4368b984700315adf7b37de05764Nate Begeman 883a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall // If a vector is initialized with a single element, that value 884a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall // becomes every element of the vector, not just the first. 885a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall // This is the behavior described in the IBM AltiVec documentation. 886a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall if (NumInits == 1) { 887b92ae0e31126e5630d7022f2d6abe7eed2e17746Tanya Lattner 888b92ae0e31126e5630d7022f2d6abe7eed2e17746Tanya Lattner // Handle the case where the vector is initialized by a another 889b92ae0e31126e5630d7022f2d6abe7eed2e17746Tanya Lattner // vector (OpenCL 6.1.6). 890b92ae0e31126e5630d7022f2d6abe7eed2e17746Tanya Lattner if (E->getInit(0)->getType()->isVectorType()) 891b92ae0e31126e5630d7022f2d6abe7eed2e17746Tanya Lattner return this->Visit(const_cast<Expr*>(E->getInit(0))); 892b92ae0e31126e5630d7022f2d6abe7eed2e17746Tanya Lattner 893a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall APValue InitValue; 89459b5da6d853b4368b984700315adf7b37de05764Nate Begeman if (EltTy->isIntegerType()) { 89559b5da6d853b4368b984700315adf7b37de05764Nate Begeman llvm::APSInt sInt(32); 896a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall if (!EvaluateInteger(E->getInit(0), sInt, Info)) 897a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall return APValue(); 898a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall InitValue = APValue(sInt); 89959b5da6d853b4368b984700315adf7b37de05764Nate Begeman } else { 90059b5da6d853b4368b984700315adf7b37de05764Nate Begeman llvm::APFloat f(0.0); 901a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall if (!EvaluateFloat(E->getInit(0), f, Info)) 902a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall return APValue(); 903a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall InitValue = APValue(f); 904a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall } 905a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall for (unsigned i = 0; i < NumElements; i++) { 906a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall Elements.push_back(InitValue); 907a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall } 908a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall } else { 909a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall for (unsigned i = 0; i < NumElements; i++) { 910a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall if (EltTy->isIntegerType()) { 911a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall llvm::APSInt sInt(32); 912a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall if (i < NumInits) { 913a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall if (!EvaluateInteger(E->getInit(i), sInt, Info)) 914a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall return APValue(); 915a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall } else { 916a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall sInt = Info.Ctx.MakeIntValue(0, EltTy); 917a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall } 918a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall Elements.push_back(APValue(sInt)); 91991110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman } else { 920a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall llvm::APFloat f(0.0); 921a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall if (i < NumInits) { 922a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall if (!EvaluateFloat(E->getInit(i), f, Info)) 923a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall return APValue(); 924a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall } else { 925a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall f = APFloat::getZero(Info.Ctx.getFloatTypeSemantics(EltTy)); 926a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall } 927a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall Elements.push_back(APValue(f)); 92891110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman } 92959b5da6d853b4368b984700315adf7b37de05764Nate Begeman } 93059b5da6d853b4368b984700315adf7b37de05764Nate Begeman } 93159b5da6d853b4368b984700315adf7b37de05764Nate Begeman return APValue(&Elements[0], Elements.size()); 93259b5da6d853b4368b984700315adf7b37de05764Nate Begeman} 93359b5da6d853b4368b984700315adf7b37de05764Nate Begeman 9341eb4433ac451dc16f4133a88af2d002ac26c58efMike StumpAPValue 93591110ee24e3475e0a3a38938c7b98439b5cf0b0eEli FriedmanVectorExprEvaluator::GetZeroVector(QualType T) { 936183700f494ec9b6701b6efe82bcb25f4c79ba561John McCall const VectorType *VT = T->getAs<VectorType>(); 93791110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman QualType EltTy = VT->getElementType(); 93891110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman APValue ZeroElement; 93991110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman if (EltTy->isIntegerType()) 94091110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman ZeroElement = APValue(Info.Ctx.MakeIntValue(0, EltTy)); 94191110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman else 94291110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman ZeroElement = 94391110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman APValue(APFloat::getZero(Info.Ctx.getFloatTypeSemantics(EltTy))); 94491110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman 9455f9e272e632e951b1efe824cd16acb4d96077930Chris Lattner SmallVector<APValue, 4> Elements(VT->getNumElements(), ZeroElement); 94691110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman return APValue(&Elements[0], Elements.size()); 94791110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman} 94891110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman 94991110ee24e3475e0a3a38938c7b98439b5cf0b0eEli FriedmanAPValue VectorExprEvaluator::VisitUnaryImag(const UnaryOperator *E) { 95091110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman if (!E->getSubExpr()->isEvaluatable(Info.Ctx)) 95191110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman Info.EvalResult.HasSideEffects = true; 95291110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman return GetZeroVector(E->getType()); 95391110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman} 95491110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman 95559b5da6d853b4368b984700315adf7b37de05764Nate Begeman//===----------------------------------------------------------------------===// 956f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner// Integer Evaluation 957f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner//===----------------------------------------------------------------------===// 958f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner 959f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattnernamespace { 960770b4a8834670e9427d3ce5a1a8472eb86f45fd2Benjamin Kramerclass IntExprEvaluator 9618cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne : public ExprEvaluatorBase<IntExprEvaluator, bool> { 96230c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar APValue &Result; 963f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattnerpublic: 96430c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar IntExprEvaluator(EvalInfo &info, APValue &result) 9658cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne : ExprEvaluatorBaseTy(info), Result(result) {} 966f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner 967973c4fc0b0a88f9cea273b16f2082788a6e57d74Abramo Bagnara bool Success(const llvm::APSInt &SI, const Expr *E) { 968973c4fc0b0a88f9cea273b16f2082788a6e57d74Abramo Bagnara assert(E->getType()->isIntegralOrEnumerationType() && 9692ade35e2cfd554e49d35a52047cea98a82787af9Douglas Gregor "Invalid evaluation result."); 970973c4fc0b0a88f9cea273b16f2082788a6e57d74Abramo Bagnara assert(SI.isSigned() == E->getType()->isSignedIntegerOrEnumerationType() && 9713f7d995390009fede92b333a040da80e1ce90997Daniel Dunbar "Invalid evaluation result."); 972973c4fc0b0a88f9cea273b16f2082788a6e57d74Abramo Bagnara assert(SI.getBitWidth() == Info.Ctx.getIntWidth(E->getType()) && 9733f7d995390009fede92b333a040da80e1ce90997Daniel Dunbar "Invalid evaluation result."); 97430c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar Result = APValue(SI); 9753f7d995390009fede92b333a040da80e1ce90997Daniel Dunbar return true; 9763f7d995390009fede92b333a040da80e1ce90997Daniel Dunbar } 9773f7d995390009fede92b333a040da80e1ce90997Daniel Dunbar 978131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar bool Success(const llvm::APInt &I, const Expr *E) { 9792ade35e2cfd554e49d35a52047cea98a82787af9Douglas Gregor assert(E->getType()->isIntegralOrEnumerationType() && 9802ade35e2cfd554e49d35a52047cea98a82787af9Douglas Gregor "Invalid evaluation result."); 98130c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar assert(I.getBitWidth() == Info.Ctx.getIntWidth(E->getType()) && 9823f7d995390009fede92b333a040da80e1ce90997Daniel Dunbar "Invalid evaluation result."); 98330c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar Result = APValue(APSInt(I)); 984575a1c9dc8dc5b4977194993e289f9eda7295c39Douglas Gregor Result.getInt().setIsUnsigned( 985575a1c9dc8dc5b4977194993e289f9eda7295c39Douglas Gregor E->getType()->isUnsignedIntegerOrEnumerationType()); 986131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar return true; 987131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar } 988131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar 989131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar bool Success(uint64_t Value, const Expr *E) { 9902ade35e2cfd554e49d35a52047cea98a82787af9Douglas Gregor assert(E->getType()->isIntegralOrEnumerationType() && 9912ade35e2cfd554e49d35a52047cea98a82787af9Douglas Gregor "Invalid evaluation result."); 99230c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar Result = APValue(Info.Ctx.MakeIntValue(Value, E->getType())); 993131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar return true; 994131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar } 995131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar 9964f3bc8f7aa90b72832b03bee9201c98f4bb6b4d1Ken Dyck bool Success(CharUnits Size, const Expr *E) { 9974f3bc8f7aa90b72832b03bee9201c98f4bb6b4d1Ken Dyck return Success(Size.getQuantity(), E); 9984f3bc8f7aa90b72832b03bee9201c98f4bb6b4d1Ken Dyck } 9994f3bc8f7aa90b72832b03bee9201c98f4bb6b4d1Ken Dyck 10004f3bc8f7aa90b72832b03bee9201c98f4bb6b4d1Ken Dyck 100182206e267ce6cc709797127616f64672d255b310Anders Carlsson bool Error(SourceLocation L, diag::kind D, const Expr *E) { 100232fea9d18cc3658a1b01df5ca6f2ac302625c61dChris Lattner // Take the first error. 100354da0496616cb898596cfd5fae1f824098bd8435Anders Carlsson if (Info.EvalResult.Diag == 0) { 100454da0496616cb898596cfd5fae1f824098bd8435Anders Carlsson Info.EvalResult.DiagLoc = L; 100554da0496616cb898596cfd5fae1f824098bd8435Anders Carlsson Info.EvalResult.Diag = D; 100682206e267ce6cc709797127616f64672d255b310Anders Carlsson Info.EvalResult.DiagExpr = E; 100732fea9d18cc3658a1b01df5ca6f2ac302625c61dChris Lattner } 100854176fdb044312b4b77c3da6682d3575b3728d30Chris Lattner return false; 10097a76778e218da57a3b10c80066a0a938f28987b6Chris Lattner } 10101eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 10118cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool Success(const APValue &V, const Expr *E) { 10128cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne return Success(V.getInt(), E); 101332fea9d18cc3658a1b01df5ca6f2ac302625c61dChris Lattner } 10148cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool Error(const Expr *E) { 10150e8acbbba71ec6acd5dceb4fcbce63e463e1b755Anders Carlsson return Error(E->getLocStart(), diag::note_invalid_subexpr_in_ice, E); 1016f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner } 10171eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 10188cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne //===--------------------------------------------------------------------===// 10198cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne // Visitor Methods 10208cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne //===--------------------------------------------------------------------===// 1021f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner 10224c4867e140327fa3b56306fa03c64c8e6a7c95efChris Lattner bool VisitIntegerLiteral(const IntegerLiteral *E) { 1023131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar return Success(E->getValue(), E); 10244c4867e140327fa3b56306fa03c64c8e6a7c95efChris Lattner } 10254c4867e140327fa3b56306fa03c64c8e6a7c95efChris Lattner bool VisitCharacterLiteral(const CharacterLiteral *E) { 1026131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar return Success(E->getValue(), E); 10274c4867e140327fa3b56306fa03c64c8e6a7c95efChris Lattner } 1028043097507f99b1156bfd8bad41e7d5166ae4b9b6Eli Friedman 1029043097507f99b1156bfd8bad41e7d5166ae4b9b6Eli Friedman bool CheckReferencedDecl(const Expr *E, const Decl *D); 1030043097507f99b1156bfd8bad41e7d5166ae4b9b6Eli Friedman bool VisitDeclRefExpr(const DeclRefExpr *E) { 10318cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne if (CheckReferencedDecl(E, E->getDecl())) 10328cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne return true; 10338cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne 10348cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne return ExprEvaluatorBaseTy::VisitDeclRefExpr(E); 1035043097507f99b1156bfd8bad41e7d5166ae4b9b6Eli Friedman } 1036043097507f99b1156bfd8bad41e7d5166ae4b9b6Eli Friedman bool VisitMemberExpr(const MemberExpr *E) { 1037043097507f99b1156bfd8bad41e7d5166ae4b9b6Eli Friedman if (CheckReferencedDecl(E, E->getMemberDecl())) { 1038043097507f99b1156bfd8bad41e7d5166ae4b9b6Eli Friedman // Conservatively assume a MemberExpr will have side-effects 1039043097507f99b1156bfd8bad41e7d5166ae4b9b6Eli Friedman Info.EvalResult.HasSideEffects = true; 1040043097507f99b1156bfd8bad41e7d5166ae4b9b6Eli Friedman return true; 1041043097507f99b1156bfd8bad41e7d5166ae4b9b6Eli Friedman } 10428cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne 10438cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne return ExprEvaluatorBaseTy::VisitMemberExpr(E); 1044043097507f99b1156bfd8bad41e7d5166ae4b9b6Eli Friedman } 1045043097507f99b1156bfd8bad41e7d5166ae4b9b6Eli Friedman 10468cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitCallExpr(const CallExpr *E); 1047b542afe02d317411d53b3541946f9f2a8f509a11Chris Lattner bool VisitBinaryOperator(const BinaryOperator *E); 10488ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor bool VisitOffsetOfExpr(const OffsetOfExpr *E); 1049b542afe02d317411d53b3541946f9f2a8f509a11Chris Lattner bool VisitUnaryOperator(const UnaryOperator *E); 1050f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner 10518cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitCastExpr(const CastExpr* E); 1052f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne bool VisitUnaryExprOrTypeTraitExpr(const UnaryExprOrTypeTraitExpr *E); 10530518999d3adcc289997bd974dce90cc97f5c1c44Sebastian Redl 10543068d117951a8df54bae9db039b56201ab10962bAnders Carlsson bool VisitCXXBoolLiteralExpr(const CXXBoolLiteralExpr *E) { 1055131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar return Success(E->getValue(), E); 10563068d117951a8df54bae9db039b56201ab10962bAnders Carlsson } 10571eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 10583f70456b8adb0405ef2a47d51f9fc2d5937ae8aeAnders Carlsson bool VisitGNUNullExpr(const GNUNullExpr *E) { 1059131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar return Success(0, E); 10603f70456b8adb0405ef2a47d51f9fc2d5937ae8aeAnders Carlsson } 10611eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1062ed8abf18329df67b0abcbb3a10458bd8c1d2a595Douglas Gregor bool VisitCXXScalarValueInitExpr(const CXXScalarValueInitExpr *E) { 1063131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar return Success(0, E); 10643068d117951a8df54bae9db039b56201ab10962bAnders Carlsson } 10653068d117951a8df54bae9db039b56201ab10962bAnders Carlsson 1066664a104ba0b8f47b8908ec6af694d9646adba1fcEli Friedman bool VisitImplicitValueInitExpr(const ImplicitValueInitExpr *E) { 1067664a104ba0b8f47b8908ec6af694d9646adba1fcEli Friedman return Success(0, E); 1068664a104ba0b8f47b8908ec6af694d9646adba1fcEli Friedman } 1069664a104ba0b8f47b8908ec6af694d9646adba1fcEli Friedman 107064b45f7e0d3167f040841ac2920aead7f080730dSebastian Redl bool VisitUnaryTypeTraitExpr(const UnaryTypeTraitExpr *E) { 10710dfd848fa4c9664852ba8c929a8bd3fce93ddca2Sebastian Redl return Success(E->getValue(), E); 107264b45f7e0d3167f040841ac2920aead7f080730dSebastian Redl } 107364b45f7e0d3167f040841ac2920aead7f080730dSebastian Redl 10746ad6f2848d7652ab2991286eb48be440d3493b28Francois Pichet bool VisitBinaryTypeTraitExpr(const BinaryTypeTraitExpr *E) { 10756ad6f2848d7652ab2991286eb48be440d3493b28Francois Pichet return Success(E->getValue(), E); 10766ad6f2848d7652ab2991286eb48be440d3493b28Francois Pichet } 10776ad6f2848d7652ab2991286eb48be440d3493b28Francois Pichet 107821ff2e516b0e0bc8c1dbf965cb3d44bac3c64330John Wiegley bool VisitArrayTypeTraitExpr(const ArrayTypeTraitExpr *E) { 107921ff2e516b0e0bc8c1dbf965cb3d44bac3c64330John Wiegley return Success(E->getValue(), E); 108021ff2e516b0e0bc8c1dbf965cb3d44bac3c64330John Wiegley } 108121ff2e516b0e0bc8c1dbf965cb3d44bac3c64330John Wiegley 1082552622067dc45013d240f73952fece703f5e63bdJohn Wiegley bool VisitExpressionTraitExpr(const ExpressionTraitExpr *E) { 1083552622067dc45013d240f73952fece703f5e63bdJohn Wiegley return Success(E->getValue(), E); 1084552622067dc45013d240f73952fece703f5e63bdJohn Wiegley } 1085552622067dc45013d240f73952fece703f5e63bdJohn Wiegley 1086722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman bool VisitUnaryReal(const UnaryOperator *E); 1087664a104ba0b8f47b8908ec6af694d9646adba1fcEli Friedman bool VisitUnaryImag(const UnaryOperator *E); 1088664a104ba0b8f47b8908ec6af694d9646adba1fcEli Friedman 1089295995c9c3196416372c9cd35d9cedb6da37bd3dSebastian Redl bool VisitCXXNoexceptExpr(const CXXNoexceptExpr *E); 1090ee8aff06f6a96214731de17b2cb6df407c6c1820Douglas Gregor bool VisitSizeOfPackExpr(const SizeOfPackExpr *E); 1091cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl 1092cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl bool VisitInitListExpr(const InitListExpr *E); 1093cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl 1094fcee0019b76f9f368f2b3d6d4048a98232593f29Chris Lattnerprivate: 10958b752f10c394b140f9ef89e049cbad1a7676fc25Ken Dyck CharUnits GetAlignOfExpr(const Expr *E); 10968b752f10c394b140f9ef89e049cbad1a7676fc25Ken Dyck CharUnits GetAlignOfType(QualType T); 109742c8f87eb60958170c46767273bf93e6c96125bfJohn McCall static QualType GetObjectType(const Expr *E); 10988cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool TryEvaluateBuiltinObjectSize(const CallExpr *E); 1099664a104ba0b8f47b8908ec6af694d9646adba1fcEli Friedman // FIXME: Missing: array subscript of vector, member of vector 1100f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner}; 1101f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner} // end anonymous namespace 1102f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner 110369ab26a8623141f35e86817cfc6e0fbe7639a40fDaniel Dunbarstatic bool EvaluateIntegerOrLValue(const Expr* E, APValue &Result, EvalInfo &Info) { 11042ade35e2cfd554e49d35a52047cea98a82787af9Douglas Gregor assert(E->getType()->isIntegralOrEnumerationType()); 11058cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne return IntExprEvaluator(Info, Result).Visit(E); 110669ab26a8623141f35e86817cfc6e0fbe7639a40fDaniel Dunbar} 110769ab26a8623141f35e86817cfc6e0fbe7639a40fDaniel Dunbar 110869ab26a8623141f35e86817cfc6e0fbe7639a40fDaniel Dunbarstatic bool EvaluateInteger(const Expr* E, APSInt &Result, EvalInfo &Info) { 11092ade35e2cfd554e49d35a52047cea98a82787af9Douglas Gregor assert(E->getType()->isIntegralOrEnumerationType()); 11107db7acbbb84b82d0522266a50ebabc3a52a9e5d1John McCall 111130c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar APValue Val; 111269ab26a8623141f35e86817cfc6e0fbe7639a40fDaniel Dunbar if (!EvaluateIntegerOrLValue(E, Val, Info) || !Val.isInt()) 111330c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar return false; 111430c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar Result = Val.getInt(); 111530c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar return true; 1116f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner} 1117f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner 1118043097507f99b1156bfd8bad41e7d5166ae4b9b6Eli Friedmanbool IntExprEvaluator::CheckReferencedDecl(const Expr* E, const Decl* D) { 11194c4867e140327fa3b56306fa03c64c8e6a7c95efChris Lattner // Enums are integer constant exprs. 1120bfbdcd861a4364bfc21a9e5047bdbd56812d6693Abramo Bagnara if (const EnumConstantDecl *ECD = dyn_cast<EnumConstantDecl>(D)) { 1121973c4fc0b0a88f9cea273b16f2082788a6e57d74Abramo Bagnara // Check for signedness/width mismatches between E type and ECD value. 1122973c4fc0b0a88f9cea273b16f2082788a6e57d74Abramo Bagnara bool SameSign = (ECD->getInitVal().isSigned() 1123973c4fc0b0a88f9cea273b16f2082788a6e57d74Abramo Bagnara == E->getType()->isSignedIntegerOrEnumerationType()); 1124973c4fc0b0a88f9cea273b16f2082788a6e57d74Abramo Bagnara bool SameWidth = (ECD->getInitVal().getBitWidth() 1125973c4fc0b0a88f9cea273b16f2082788a6e57d74Abramo Bagnara == Info.Ctx.getIntWidth(E->getType())); 1126973c4fc0b0a88f9cea273b16f2082788a6e57d74Abramo Bagnara if (SameSign && SameWidth) 1127973c4fc0b0a88f9cea273b16f2082788a6e57d74Abramo Bagnara return Success(ECD->getInitVal(), E); 1128973c4fc0b0a88f9cea273b16f2082788a6e57d74Abramo Bagnara else { 1129973c4fc0b0a88f9cea273b16f2082788a6e57d74Abramo Bagnara // Get rid of mismatch (otherwise Success assertions will fail) 1130973c4fc0b0a88f9cea273b16f2082788a6e57d74Abramo Bagnara // by computing a new value matching the type of E. 1131973c4fc0b0a88f9cea273b16f2082788a6e57d74Abramo Bagnara llvm::APSInt Val = ECD->getInitVal(); 1132973c4fc0b0a88f9cea273b16f2082788a6e57d74Abramo Bagnara if (!SameSign) 1133973c4fc0b0a88f9cea273b16f2082788a6e57d74Abramo Bagnara Val.setIsSigned(!ECD->getInitVal().isSigned()); 1134973c4fc0b0a88f9cea273b16f2082788a6e57d74Abramo Bagnara if (!SameWidth) 1135973c4fc0b0a88f9cea273b16f2082788a6e57d74Abramo Bagnara Val = Val.extOrTrunc(Info.Ctx.getIntWidth(E->getType())); 1136973c4fc0b0a88f9cea273b16f2082788a6e57d74Abramo Bagnara return Success(Val, E); 1137973c4fc0b0a88f9cea273b16f2082788a6e57d74Abramo Bagnara } 1138bfbdcd861a4364bfc21a9e5047bdbd56812d6693Abramo Bagnara } 1139b2bc62bd35129f09d0746ef6a5ef4dc392b6d6e1Sebastian Redl 1140b2bc62bd35129f09d0746ef6a5ef4dc392b6d6e1Sebastian Redl // In C++, const, non-volatile integers initialized with ICEs are ICEs. 1141e1646da3bb0fe97b372e5fe8cefc537b22048fc4Eli Friedman // In C, they can also be folded, although they are not ICEs. 1142cf3293eaeb3853d12cff47e648bbe835004e929fDouglas Gregor if (Info.Ctx.getCanonicalType(E->getType()).getCVRQualifiers() 1143cf3293eaeb3853d12cff47e648bbe835004e929fDouglas Gregor == Qualifiers::Const) { 1144f6b6025a4e26bb0295a57e0efece73253038f278Anders Carlsson 1145f6b6025a4e26bb0295a57e0efece73253038f278Anders Carlsson if (isa<ParmVarDecl>(D)) 11468cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne return false; 1147f6b6025a4e26bb0295a57e0efece73253038f278Anders Carlsson 1148043097507f99b1156bfd8bad41e7d5166ae4b9b6Eli Friedman if (const VarDecl *VD = dyn_cast<VarDecl>(D)) { 114931310a21fb2a9f13950f864f681c86080b05d5b2Sebastian Redl if (const Expr *Init = VD->getAnyInitializer()) { 1150c013118155077cf8bdaef743c5dbce760114eed3Eli Friedman if (APValue *V = VD->getEvaluatedValue()) { 1151c013118155077cf8bdaef743c5dbce760114eed3Eli Friedman if (V->isInt()) 1152c013118155077cf8bdaef743c5dbce760114eed3Eli Friedman return Success(V->getInt(), E); 11538cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne return false; 1154c013118155077cf8bdaef743c5dbce760114eed3Eli Friedman } 1155c013118155077cf8bdaef743c5dbce760114eed3Eli Friedman 1156c013118155077cf8bdaef743c5dbce760114eed3Eli Friedman if (VD->isEvaluatingValue()) 11578cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne return false; 1158c013118155077cf8bdaef743c5dbce760114eed3Eli Friedman 1159c013118155077cf8bdaef743c5dbce760114eed3Eli Friedman VD->setEvaluatingValue(); 1160c013118155077cf8bdaef743c5dbce760114eed3Eli Friedman 1161a7dedf7004e8ac3f947d6817370b2778fa648c2bEli Friedman Expr::EvalResult EResult; 1162a7dedf7004e8ac3f947d6817370b2778fa648c2bEli Friedman if (Init->Evaluate(EResult, Info.Ctx) && !EResult.HasSideEffects && 1163a7dedf7004e8ac3f947d6817370b2778fa648c2bEli Friedman EResult.Val.isInt()) { 116478d1583d0b36b7d6d8d10234cdc19ab94adf765aDouglas Gregor // Cache the evaluated value in the variable declaration. 1165a7dedf7004e8ac3f947d6817370b2778fa648c2bEli Friedman Result = EResult.Val; 1166c013118155077cf8bdaef743c5dbce760114eed3Eli Friedman VD->setEvaluatedValue(Result); 116778d1583d0b36b7d6d8d10234cdc19ab94adf765aDouglas Gregor return true; 116878d1583d0b36b7d6d8d10234cdc19ab94adf765aDouglas Gregor } 116978d1583d0b36b7d6d8d10234cdc19ab94adf765aDouglas Gregor 1170c013118155077cf8bdaef743c5dbce760114eed3Eli Friedman VD->setEvaluatedValue(APValue()); 117178d1583d0b36b7d6d8d10234cdc19ab94adf765aDouglas Gregor } 1172b2bc62bd35129f09d0746ef6a5ef4dc392b6d6e1Sebastian Redl } 1173b2bc62bd35129f09d0746ef6a5ef4dc392b6d6e1Sebastian Redl } 1174b2bc62bd35129f09d0746ef6a5ef4dc392b6d6e1Sebastian Redl 11754c4867e140327fa3b56306fa03c64c8e6a7c95efChris Lattner // Otherwise, random variable references are not constants. 11768cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne return false; 11774c4867e140327fa3b56306fa03c64c8e6a7c95efChris Lattner} 11784c4867e140327fa3b56306fa03c64c8e6a7c95efChris Lattner 1179a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner/// EvaluateBuiltinClassifyType - Evaluate __builtin_classify_type the same way 1180a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner/// as GCC. 1181a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattnerstatic int EvaluateBuiltinClassifyType(const CallExpr *E) { 1182a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner // The following enum mimics the values returned by GCC. 11837c80bd64032e610c0dbd74fc0ef6ea334447f2fdSebastian Redl // FIXME: Does GCC differ between lvalue and rvalue references here? 1184a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner enum gcc_type_class { 1185a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner no_type_class = -1, 1186a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner void_type_class, integer_type_class, char_type_class, 1187a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner enumeral_type_class, boolean_type_class, 1188a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner pointer_type_class, reference_type_class, offset_type_class, 1189a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner real_type_class, complex_type_class, 1190a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner function_type_class, method_type_class, 1191a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner record_type_class, union_type_class, 1192a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner array_type_class, string_type_class, 1193a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner lang_type_class 1194a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner }; 11951eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 11961eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump // If no argument was supplied, default to "no_type_class". This isn't 1197a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner // ideal, however it is what gcc does. 1198a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner if (E->getNumArgs() == 0) 1199a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner return no_type_class; 12001eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1201a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner QualType ArgTy = E->getArg(0)->getType(); 1202a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner if (ArgTy->isVoidType()) 1203a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner return void_type_class; 1204a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner else if (ArgTy->isEnumeralType()) 1205a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner return enumeral_type_class; 1206a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner else if (ArgTy->isBooleanType()) 1207a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner return boolean_type_class; 1208a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner else if (ArgTy->isCharType()) 1209a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner return string_type_class; // gcc doesn't appear to use char_type_class 1210a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner else if (ArgTy->isIntegerType()) 1211a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner return integer_type_class; 1212a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner else if (ArgTy->isPointerType()) 1213a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner return pointer_type_class; 1214a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner else if (ArgTy->isReferenceType()) 1215a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner return reference_type_class; 1216a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner else if (ArgTy->isRealType()) 1217a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner return real_type_class; 1218a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner else if (ArgTy->isComplexType()) 1219a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner return complex_type_class; 1220a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner else if (ArgTy->isFunctionType()) 1221a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner return function_type_class; 1222fb87b89fc9eb103e19fb8e4b925c23f0bd091b99Douglas Gregor else if (ArgTy->isStructureOrClassType()) 1223a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner return record_type_class; 1224a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner else if (ArgTy->isUnionType()) 1225a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner return union_type_class; 1226a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner else if (ArgTy->isArrayType()) 1227a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner return array_type_class; 1228a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner else if (ArgTy->isUnionType()) 1229a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner return union_type_class; 1230a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner else // FIXME: offset_type_class, method_type_class, & lang_type_class? 1231b219cfc4d75f0a03630b7c4509ef791b7e97b2c8David Blaikie llvm_unreachable("CallExpr::isBuiltinClassifyType(): unimplemented type"); 1232a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner return -1; 1233a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner} 1234a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner 123542c8f87eb60958170c46767273bf93e6c96125bfJohn McCall/// Retrieves the "underlying object type" of the given expression, 123642c8f87eb60958170c46767273bf93e6c96125bfJohn McCall/// as used by __builtin_object_size. 123742c8f87eb60958170c46767273bf93e6c96125bfJohn McCallQualType IntExprEvaluator::GetObjectType(const Expr *E) { 123842c8f87eb60958170c46767273bf93e6c96125bfJohn McCall if (const DeclRefExpr *DRE = dyn_cast<DeclRefExpr>(E)) { 123942c8f87eb60958170c46767273bf93e6c96125bfJohn McCall if (const VarDecl *VD = dyn_cast<VarDecl>(DRE->getDecl())) 124042c8f87eb60958170c46767273bf93e6c96125bfJohn McCall return VD->getType(); 124142c8f87eb60958170c46767273bf93e6c96125bfJohn McCall } else if (isa<CompoundLiteralExpr>(E)) { 124242c8f87eb60958170c46767273bf93e6c96125bfJohn McCall return E->getType(); 124342c8f87eb60958170c46767273bf93e6c96125bfJohn McCall } 124442c8f87eb60958170c46767273bf93e6c96125bfJohn McCall 124542c8f87eb60958170c46767273bf93e6c96125bfJohn McCall return QualType(); 124642c8f87eb60958170c46767273bf93e6c96125bfJohn McCall} 124742c8f87eb60958170c46767273bf93e6c96125bfJohn McCall 12488cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbournebool IntExprEvaluator::TryEvaluateBuiltinObjectSize(const CallExpr *E) { 124942c8f87eb60958170c46767273bf93e6c96125bfJohn McCall // TODO: Perhaps we should let LLVM lower this? 125042c8f87eb60958170c46767273bf93e6c96125bfJohn McCall LValue Base; 125142c8f87eb60958170c46767273bf93e6c96125bfJohn McCall if (!EvaluatePointer(E->getArg(0), Base, Info)) 125242c8f87eb60958170c46767273bf93e6c96125bfJohn McCall return false; 125342c8f87eb60958170c46767273bf93e6c96125bfJohn McCall 125442c8f87eb60958170c46767273bf93e6c96125bfJohn McCall // If we can prove the base is null, lower to zero now. 125542c8f87eb60958170c46767273bf93e6c96125bfJohn McCall const Expr *LVBase = Base.getLValueBase(); 125642c8f87eb60958170c46767273bf93e6c96125bfJohn McCall if (!LVBase) return Success(0, E); 125742c8f87eb60958170c46767273bf93e6c96125bfJohn McCall 125842c8f87eb60958170c46767273bf93e6c96125bfJohn McCall QualType T = GetObjectType(LVBase); 125942c8f87eb60958170c46767273bf93e6c96125bfJohn McCall if (T.isNull() || 126042c8f87eb60958170c46767273bf93e6c96125bfJohn McCall T->isIncompleteType() || 12611357869bc5983cdfbc986db1f3d18265bb34cb0eEli Friedman T->isFunctionType() || 126242c8f87eb60958170c46767273bf93e6c96125bfJohn McCall T->isVariablyModifiedType() || 126342c8f87eb60958170c46767273bf93e6c96125bfJohn McCall T->isDependentType()) 126442c8f87eb60958170c46767273bf93e6c96125bfJohn McCall return false; 126542c8f87eb60958170c46767273bf93e6c96125bfJohn McCall 126642c8f87eb60958170c46767273bf93e6c96125bfJohn McCall CharUnits Size = Info.Ctx.getTypeSizeInChars(T); 126742c8f87eb60958170c46767273bf93e6c96125bfJohn McCall CharUnits Offset = Base.getLValueOffset(); 126842c8f87eb60958170c46767273bf93e6c96125bfJohn McCall 126942c8f87eb60958170c46767273bf93e6c96125bfJohn McCall if (!Offset.isNegative() && Offset <= Size) 127042c8f87eb60958170c46767273bf93e6c96125bfJohn McCall Size -= Offset; 127142c8f87eb60958170c46767273bf93e6c96125bfJohn McCall else 127242c8f87eb60958170c46767273bf93e6c96125bfJohn McCall Size = CharUnits::Zero(); 12734f3bc8f7aa90b72832b03bee9201c98f4bb6b4d1Ken Dyck return Success(Size, E); 127442c8f87eb60958170c46767273bf93e6c96125bfJohn McCall} 127542c8f87eb60958170c46767273bf93e6c96125bfJohn McCall 12768cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbournebool IntExprEvaluator::VisitCallExpr(const CallExpr *E) { 12773c385e5f8d9008fff18597ca302be19fa86e51f6Douglas Gregor switch (E->isBuiltinCall(Info.Ctx)) { 1278019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner default: 12798cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne return ExprEvaluatorBaseTy::VisitCallExpr(E); 128064eda9e50b593f935c95bd1edc98c4bfda03f601Mike Stump 128164eda9e50b593f935c95bd1edc98c4bfda03f601Mike Stump case Builtin::BI__builtin_object_size: { 128242c8f87eb60958170c46767273bf93e6c96125bfJohn McCall if (TryEvaluateBuiltinObjectSize(E)) 128342c8f87eb60958170c46767273bf93e6c96125bfJohn McCall return true; 128464eda9e50b593f935c95bd1edc98c4bfda03f601Mike Stump 1285b2aaf51ed73a4774322a39a0dd59d0fe7e3258c0Eric Christopher // If evaluating the argument has side-effects we can't determine 1286b2aaf51ed73a4774322a39a0dd59d0fe7e3258c0Eric Christopher // the size of the object and lower it to unknown now. 1287393c247fe025ccb5f914e37e948192ea86faef8cFariborz Jahanian if (E->getArg(0)->HasSideEffects(Info.Ctx)) { 1288a6b8b2c09610b8bc4330e948ece8b940c2386406Richard Smith if (E->getArg(1)->EvaluateKnownConstInt(Info.Ctx).getZExtValue() <= 1) 1289cf184655319cf7a5b811067cff9d26a5741fd161Chris Lattner return Success(-1ULL, E); 129064eda9e50b593f935c95bd1edc98c4bfda03f601Mike Stump return Success(0, E); 129164eda9e50b593f935c95bd1edc98c4bfda03f601Mike Stump } 1292c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump 129364eda9e50b593f935c95bd1edc98c4bfda03f601Mike Stump return Error(E->getLocStart(), diag::note_invalid_subexpr_in_ice, E); 129464eda9e50b593f935c95bd1edc98c4bfda03f601Mike Stump } 129564eda9e50b593f935c95bd1edc98c4bfda03f601Mike Stump 1296019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner case Builtin::BI__builtin_classify_type: 1297131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar return Success(EvaluateBuiltinClassifyType(E), E); 12981eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 12994bbc0e05a714d4ee4918a92a4a7049dd6ef33ad0Anders Carlsson case Builtin::BI__builtin_constant_p: 1300019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner // __builtin_constant_p always has one operand: it returns true if that 1301019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner // operand can be folded, false otherwise. 1302131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar return Success(E->getArg(0)->isEvaluatable(Info.Ctx), E); 130321fb98ee003e992b0c4e204d98a19e0ef544cae3Chris Lattner 130421fb98ee003e992b0c4e204d98a19e0ef544cae3Chris Lattner case Builtin::BI__builtin_eh_return_data_regno: { 1305a6b8b2c09610b8bc4330e948ece8b940c2386406Richard Smith int Operand = E->getArg(0)->EvaluateKnownConstInt(Info.Ctx).getZExtValue(); 1306bcfd1f55bfbb3e5944cd5e03d07b343e280838c4Douglas Gregor Operand = Info.Ctx.getTargetInfo().getEHDataRegisterNumber(Operand); 130721fb98ee003e992b0c4e204d98a19e0ef544cae3Chris Lattner return Success(Operand, E); 130821fb98ee003e992b0c4e204d98a19e0ef544cae3Chris Lattner } 1309c4a2638b5ef3e2d35d872614ceb655a7a22c58beEli Friedman 1310c4a2638b5ef3e2d35d872614ceb655a7a22c58beEli Friedman case Builtin::BI__builtin_expect: 1311c4a2638b5ef3e2d35d872614ceb655a7a22c58beEli Friedman return Visit(E->getArg(0)); 13125726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor 13135726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor case Builtin::BIstrlen: 13145726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor case Builtin::BI__builtin_strlen: 13155726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor // As an extension, we support strlen() and __builtin_strlen() as constant 13165726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor // expressions when the argument is a string literal. 13178cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne if (const StringLiteral *S 13185726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor = dyn_cast<StringLiteral>(E->getArg(0)->IgnoreParenImpCasts())) { 13195726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor // The string literal may have embedded null characters. Find the first 13205726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor // one and truncate there. 13215f9e272e632e951b1efe824cd16acb4d96077930Chris Lattner StringRef Str = S->getString(); 13225f9e272e632e951b1efe824cd16acb4d96077930Chris Lattner StringRef::size_type Pos = Str.find(0); 13235f9e272e632e951b1efe824cd16acb4d96077930Chris Lattner if (Pos != StringRef::npos) 13245726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor Str = Str.substr(0, Pos); 13255726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor 13265726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor return Success(Str.size(), E); 13275726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor } 13285726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor 13295726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor return Error(E->getLocStart(), diag::note_invalid_subexpr_in_ice, E); 1330019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner } 13314c4867e140327fa3b56306fa03c64c8e6a7c95efChris Lattner} 1332f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner 1333b542afe02d317411d53b3541946f9f2a8f509a11Chris Lattnerbool IntExprEvaluator::VisitBinaryOperator(const BinaryOperator *E) { 13342de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall if (E->getOpcode() == BO_Comma) { 1335027f62ec1860f4ab0c91bd863b238938880b8102Anders Carlsson if (!Visit(E->getRHS())) 1336027f62ec1860f4ab0c91bd863b238938880b8102Anders Carlsson return false; 13374fdfb0965b396f2778091f7e6c051d17ff9791baAnders Carlsson 133833ef1456a19779fb15c51aea362bd9c7cb4087f3Eli Friedman // If we can't evaluate the LHS, it might have side effects; 133933ef1456a19779fb15c51aea362bd9c7cb4087f3Eli Friedman // conservatively mark it. 134033ef1456a19779fb15c51aea362bd9c7cb4087f3Eli Friedman if (!E->getLHS()->isEvaluatable(Info.Ctx)) 134133ef1456a19779fb15c51aea362bd9c7cb4087f3Eli Friedman Info.EvalResult.HasSideEffects = true; 1342c8cc9ccc7b87a7ed1749b074f6b670bcec49abc1Chris Lattner 1343027f62ec1860f4ab0c91bd863b238938880b8102Anders Carlsson return true; 1344a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman } 1345a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman 1346a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman if (E->isLogicalOp()) { 1347a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman // These need to be handled specially because the operands aren't 1348a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman // necessarily integral 1349fcb4d09531abbf2a5cf398c2f946fb3bc2875f64Anders Carlsson bool lhsResult, rhsResult; 13501eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1351fcb4d09531abbf2a5cf398c2f946fb3bc2875f64Anders Carlsson if (HandleConversionToBool(E->getLHS(), lhsResult, Info)) { 135251fe996231b1d7199f76e4005ff4c943d5deeecdAnders Carlsson // We were able to evaluate the LHS, see if we can get away with not 135351fe996231b1d7199f76e4005ff4c943d5deeecdAnders Carlsson // evaluating the RHS: 0 && X -> 0, 1 || X -> 1 13542de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall if (lhsResult == (E->getOpcode() == BO_LOr)) 13553f7d995390009fede92b333a040da80e1ce90997Daniel Dunbar return Success(lhsResult, E); 1356a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman 1357fcb4d09531abbf2a5cf398c2f946fb3bc2875f64Anders Carlsson if (HandleConversionToBool(E->getRHS(), rhsResult, Info)) { 13582de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall if (E->getOpcode() == BO_LOr) 1359131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar return Success(lhsResult || rhsResult, E); 13604bbc0e05a714d4ee4918a92a4a7049dd6ef33ad0Anders Carlsson else 1361131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar return Success(lhsResult && rhsResult, E); 13624bbc0e05a714d4ee4918a92a4a7049dd6ef33ad0Anders Carlsson } 13634bbc0e05a714d4ee4918a92a4a7049dd6ef33ad0Anders Carlsson } else { 1364fcb4d09531abbf2a5cf398c2f946fb3bc2875f64Anders Carlsson if (HandleConversionToBool(E->getRHS(), rhsResult, Info)) { 13654bbc0e05a714d4ee4918a92a4a7049dd6ef33ad0Anders Carlsson // We can't evaluate the LHS; however, sometimes the result 13664bbc0e05a714d4ee4918a92a4a7049dd6ef33ad0Anders Carlsson // is determined by the RHS: X && 0 -> 0, X || 1 -> 1. 13672de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall if (rhsResult == (E->getOpcode() == BO_LOr) || 13682de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall !rhsResult == (E->getOpcode() == BO_LAnd)) { 1369131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar // Since we weren't able to evaluate the left hand side, it 1370fcb4d09531abbf2a5cf398c2f946fb3bc2875f64Anders Carlsson // must have had side effects. 1371fcb4d09531abbf2a5cf398c2f946fb3bc2875f64Anders Carlsson Info.EvalResult.HasSideEffects = true; 1372131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar 1373131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar return Success(rhsResult, E); 13744bbc0e05a714d4ee4918a92a4a7049dd6ef33ad0Anders Carlsson } 13754bbc0e05a714d4ee4918a92a4a7049dd6ef33ad0Anders Carlsson } 1376a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman } 1377a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman 1378a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman return false; 1379c8cc9ccc7b87a7ed1749b074f6b670bcec49abc1Chris Lattner } 138054176fdb044312b4b77c3da6682d3575b3728d30Chris Lattner 1381286f85e791dda3634fee7f6c67f0ed92296c028fAnders Carlsson QualType LHSTy = E->getLHS()->getType(); 1382286f85e791dda3634fee7f6c67f0ed92296c028fAnders Carlsson QualType RHSTy = E->getRHS()->getType(); 13834087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar 13844087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar if (LHSTy->isAnyComplexType()) { 13854087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar assert(RHSTy->isAnyComplexType() && "Invalid comparison"); 1386f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall ComplexValue LHS, RHS; 13874087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar 13884087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar if (!EvaluateComplex(E->getLHS(), LHS, Info)) 13894087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar return false; 13904087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar 13914087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar if (!EvaluateComplex(E->getRHS(), RHS, Info)) 13924087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar return false; 13934087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar 13944087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar if (LHS.isComplexFloat()) { 13951eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump APFloat::cmpResult CR_r = 13964087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar LHS.getComplexFloatReal().compare(RHS.getComplexFloatReal()); 13971eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump APFloat::cmpResult CR_i = 13984087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar LHS.getComplexFloatImag().compare(RHS.getComplexFloatImag()); 13994087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar 14002de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall if (E->getOpcode() == BO_EQ) 1401131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar return Success((CR_r == APFloat::cmpEqual && 1402131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar CR_i == APFloat::cmpEqual), E); 1403131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar else { 14042de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall assert(E->getOpcode() == BO_NE && 1405131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar "Invalid complex comparison."); 14061eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump return Success(((CR_r == APFloat::cmpGreaterThan || 1407fc39dc4c7886723310419b1869cf651ca55b7af4Mon P Wang CR_r == APFloat::cmpLessThan || 1408fc39dc4c7886723310419b1869cf651ca55b7af4Mon P Wang CR_r == APFloat::cmpUnordered) || 14091eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump (CR_i == APFloat::cmpGreaterThan || 1410fc39dc4c7886723310419b1869cf651ca55b7af4Mon P Wang CR_i == APFloat::cmpLessThan || 1411fc39dc4c7886723310419b1869cf651ca55b7af4Mon P Wang CR_i == APFloat::cmpUnordered)), E); 1412131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar } 14134087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar } else { 14142de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall if (E->getOpcode() == BO_EQ) 1415131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar return Success((LHS.getComplexIntReal() == RHS.getComplexIntReal() && 1416131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar LHS.getComplexIntImag() == RHS.getComplexIntImag()), E); 1417131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar else { 14182de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall assert(E->getOpcode() == BO_NE && 1419131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar "Invalid compex comparison."); 1420131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar return Success((LHS.getComplexIntReal() != RHS.getComplexIntReal() || 1421131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar LHS.getComplexIntImag() != RHS.getComplexIntImag()), E); 1422131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar } 14234087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar } 14244087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar } 14251eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1426286f85e791dda3634fee7f6c67f0ed92296c028fAnders Carlsson if (LHSTy->isRealFloatingType() && 1427286f85e791dda3634fee7f6c67f0ed92296c028fAnders Carlsson RHSTy->isRealFloatingType()) { 1428286f85e791dda3634fee7f6c67f0ed92296c028fAnders Carlsson APFloat RHS(0.0), LHS(0.0); 14291eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1430286f85e791dda3634fee7f6c67f0ed92296c028fAnders Carlsson if (!EvaluateFloat(E->getRHS(), RHS, Info)) 1431286f85e791dda3634fee7f6c67f0ed92296c028fAnders Carlsson return false; 14321eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1433286f85e791dda3634fee7f6c67f0ed92296c028fAnders Carlsson if (!EvaluateFloat(E->getLHS(), LHS, Info)) 1434286f85e791dda3634fee7f6c67f0ed92296c028fAnders Carlsson return false; 14351eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1436286f85e791dda3634fee7f6c67f0ed92296c028fAnders Carlsson APFloat::cmpResult CR = LHS.compare(RHS); 1437529569e68d10b0fd3750fd2124faf742249b846bAnders Carlsson 1438286f85e791dda3634fee7f6c67f0ed92296c028fAnders Carlsson switch (E->getOpcode()) { 1439286f85e791dda3634fee7f6c67f0ed92296c028fAnders Carlsson default: 1440b219cfc4d75f0a03630b7c4509ef791b7e97b2c8David Blaikie llvm_unreachable("Invalid binary operator!"); 14412de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_LT: 1442131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar return Success(CR == APFloat::cmpLessThan, E); 14432de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_GT: 1444131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar return Success(CR == APFloat::cmpGreaterThan, E); 14452de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_LE: 1446131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar return Success(CR == APFloat::cmpLessThan || CR == APFloat::cmpEqual, E); 14472de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_GE: 14481eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump return Success(CR == APFloat::cmpGreaterThan || CR == APFloat::cmpEqual, 1449131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar E); 14502de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_EQ: 1451131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar return Success(CR == APFloat::cmpEqual, E); 14522de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_NE: 14531eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump return Success(CR == APFloat::cmpGreaterThan 1454fc39dc4c7886723310419b1869cf651ca55b7af4Mon P Wang || CR == APFloat::cmpLessThan 1455fc39dc4c7886723310419b1869cf651ca55b7af4Mon P Wang || CR == APFloat::cmpUnordered, E); 1456286f85e791dda3634fee7f6c67f0ed92296c028fAnders Carlsson } 1457286f85e791dda3634fee7f6c67f0ed92296c028fAnders Carlsson } 14581eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1459ad02d7debd03ff275ac8ea27891a4ecccdb78068Eli Friedman if (LHSTy->isPointerType() && RHSTy->isPointerType()) { 14602de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall if (E->getOpcode() == BO_Sub || E->isEqualityOp()) { 1461efdb83e26f9a1fd2566afe54461216cd84814d42John McCall LValue LHSValue; 14623068d117951a8df54bae9db039b56201ab10962bAnders Carlsson if (!EvaluatePointer(E->getLHS(), LHSValue, Info)) 14633068d117951a8df54bae9db039b56201ab10962bAnders Carlsson return false; 1464a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman 1465efdb83e26f9a1fd2566afe54461216cd84814d42John McCall LValue RHSValue; 14663068d117951a8df54bae9db039b56201ab10962bAnders Carlsson if (!EvaluatePointer(E->getRHS(), RHSValue, Info)) 14673068d117951a8df54bae9db039b56201ab10962bAnders Carlsson return false; 1468a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman 14695bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman // Reject any bases from the normal codepath; we special-case comparisons 14705bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman // to null. 14715bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman if (LHSValue.getLValueBase()) { 14725bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman if (!E->isEqualityOp()) 14735bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman return false; 1474a73058324197b7bdfd19307965954f626e26199dKen Dyck if (RHSValue.getLValueBase() || !RHSValue.getLValueOffset().isZero()) 14755bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman return false; 14765bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman bool bres; 14775bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman if (!EvalPointerValueAsBool(LHSValue, bres)) 14785bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman return false; 14792de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall return Success(bres ^ (E->getOpcode() == BO_EQ), E); 14805bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman } else if (RHSValue.getLValueBase()) { 14815bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman if (!E->isEqualityOp()) 14825bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman return false; 1483a73058324197b7bdfd19307965954f626e26199dKen Dyck if (LHSValue.getLValueBase() || !LHSValue.getLValueOffset().isZero()) 14845bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman return false; 14855bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman bool bres; 14865bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman if (!EvalPointerValueAsBool(RHSValue, bres)) 14875bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman return false; 14882de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall return Success(bres ^ (E->getOpcode() == BO_EQ), E); 14895bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman } 1490a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman 14912de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall if (E->getOpcode() == BO_Sub) { 14924992bdde387c5f033bb450a716eaabc0fda52688Chris Lattner QualType Type = E->getLHS()->getType(); 14934992bdde387c5f033bb450a716eaabc0fda52688Chris Lattner QualType ElementType = Type->getAs<PointerType>()->getPointeeType(); 14943068d117951a8df54bae9db039b56201ab10962bAnders Carlsson 1495a73058324197b7bdfd19307965954f626e26199dKen Dyck CharUnits ElementSize = CharUnits::One(); 1496ce1bca73aef9bbf6359ab8420278203dda81a054Eli Friedman if (!ElementType->isVoidType() && !ElementType->isFunctionType()) 1497a73058324197b7bdfd19307965954f626e26199dKen Dyck ElementSize = Info.Ctx.getTypeSizeInChars(ElementType); 1498a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman 1499a73058324197b7bdfd19307965954f626e26199dKen Dyck CharUnits Diff = LHSValue.getLValueOffset() - 1500a73058324197b7bdfd19307965954f626e26199dKen Dyck RHSValue.getLValueOffset(); 1501a73058324197b7bdfd19307965954f626e26199dKen Dyck return Success(Diff / ElementSize, E); 1502ad02d7debd03ff275ac8ea27891a4ecccdb78068Eli Friedman } 1503ad02d7debd03ff275ac8ea27891a4ecccdb78068Eli Friedman bool Result; 15042de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall if (E->getOpcode() == BO_EQ) { 1505ad02d7debd03ff275ac8ea27891a4ecccdb78068Eli Friedman Result = LHSValue.getLValueOffset() == RHSValue.getLValueOffset(); 1506267c0ab1b9a15768f3f15abbfc40ce344751c78bEli Friedman } else { 1507ad02d7debd03ff275ac8ea27891a4ecccdb78068Eli Friedman Result = LHSValue.getLValueOffset() != RHSValue.getLValueOffset(); 1508ad02d7debd03ff275ac8ea27891a4ecccdb78068Eli Friedman } 1509ad02d7debd03ff275ac8ea27891a4ecccdb78068Eli Friedman return Success(Result, E); 15103068d117951a8df54bae9db039b56201ab10962bAnders Carlsson } 15113068d117951a8df54bae9db039b56201ab10962bAnders Carlsson } 15122ade35e2cfd554e49d35a52047cea98a82787af9Douglas Gregor if (!LHSTy->isIntegralOrEnumerationType() || 15132ade35e2cfd554e49d35a52047cea98a82787af9Douglas Gregor !RHSTy->isIntegralOrEnumerationType()) { 1514a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman // We can't continue from here for non-integral types, and they 1515a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman // could potentially confuse the following operations. 1516a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman return false; 1517a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman } 1518a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman 1519a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman // The LHS of a constant expr is always evaluated and needed. 152030c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar if (!Visit(E->getLHS())) 1521a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman return false; // error in subexpression. 1522d9f4bcda18bfbf79341edd9d381d4b6a3cffe655Eli Friedman 152342edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman APValue RHSVal; 152442edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman if (!EvaluateIntegerOrLValue(E->getRHS(), RHSVal, Info)) 152530c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar return false; 152642edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman 152742edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman // Handle cases like (unsigned long)&a + 4. 152842edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman if (E->isAdditiveOp() && Result.isLValue() && RHSVal.isInt()) { 1529a73058324197b7bdfd19307965954f626e26199dKen Dyck CharUnits Offset = Result.getLValueOffset(); 1530a73058324197b7bdfd19307965954f626e26199dKen Dyck CharUnits AdditionalOffset = CharUnits::fromQuantity( 1531a73058324197b7bdfd19307965954f626e26199dKen Dyck RHSVal.getInt().getZExtValue()); 15322de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall if (E->getOpcode() == BO_Add) 1533a73058324197b7bdfd19307965954f626e26199dKen Dyck Offset += AdditionalOffset; 153442edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman else 1535a73058324197b7bdfd19307965954f626e26199dKen Dyck Offset -= AdditionalOffset; 1536a73058324197b7bdfd19307965954f626e26199dKen Dyck Result = APValue(Result.getLValueBase(), Offset); 153742edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman return true; 153842edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman } 153942edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman 154042edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman // Handle cases like 4 + (unsigned long)&a 15412de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall if (E->getOpcode() == BO_Add && 154242edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman RHSVal.isLValue() && Result.isInt()) { 1543a73058324197b7bdfd19307965954f626e26199dKen Dyck CharUnits Offset = RHSVal.getLValueOffset(); 1544a73058324197b7bdfd19307965954f626e26199dKen Dyck Offset += CharUnits::fromQuantity(Result.getInt().getZExtValue()); 1545a73058324197b7bdfd19307965954f626e26199dKen Dyck Result = APValue(RHSVal.getLValueBase(), Offset); 154642edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman return true; 154742edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman } 154842edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman 154942edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman // All the following cases expect both operands to be an integer 155042edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman if (!Result.isInt() || !RHSVal.isInt()) 1551b542afe02d317411d53b3541946f9f2a8f509a11Chris Lattner return false; 1552a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman 155342edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman APSInt& RHS = RHSVal.getInt(); 155442edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman 1555a25ae3d68d84d2b89907f998df6a396549589da5Anders Carlsson switch (E->getOpcode()) { 155632fea9d18cc3658a1b01df5ca6f2ac302625c61dChris Lattner default: 15570e8acbbba71ec6acd5dceb4fcbce63e463e1b755Anders Carlsson return Error(E->getOperatorLoc(), diag::note_invalid_subexpr_in_ice, E); 15582de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Mul: return Success(Result.getInt() * RHS, E); 15592de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Add: return Success(Result.getInt() + RHS, E); 15602de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Sub: return Success(Result.getInt() - RHS, E); 15612de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_And: return Success(Result.getInt() & RHS, E); 15622de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Xor: return Success(Result.getInt() ^ RHS, E); 15632de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Or: return Success(Result.getInt() | RHS, E); 15642de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Div: 156554176fdb044312b4b77c3da6682d3575b3728d30Chris Lattner if (RHS == 0) 15660e8acbbba71ec6acd5dceb4fcbce63e463e1b755Anders Carlsson return Error(E->getOperatorLoc(), diag::note_expr_divide_by_zero, E); 156730c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar return Success(Result.getInt() / RHS, E); 15682de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Rem: 156954176fdb044312b4b77c3da6682d3575b3728d30Chris Lattner if (RHS == 0) 15700e8acbbba71ec6acd5dceb4fcbce63e463e1b755Anders Carlsson return Error(E->getOperatorLoc(), diag::note_expr_divide_by_zero, E); 157130c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar return Success(Result.getInt() % RHS, E); 15722de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Shl: { 1573091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall // During constant-folding, a negative shift is an opposite shift. 1574091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall if (RHS.isSigned() && RHS.isNegative()) { 1575091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall RHS = -RHS; 1576091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall goto shift_right; 1577091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall } 1578091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall 1579091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall shift_left: 1580091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall unsigned SA 1581091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall = (unsigned) RHS.getLimitedValue(Result.getInt().getBitWidth()-1); 158230c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar return Success(Result.getInt() << SA, E); 15833f7d995390009fede92b333a040da80e1ce90997Daniel Dunbar } 15842de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Shr: { 1585091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall // During constant-folding, a negative shift is an opposite shift. 1586091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall if (RHS.isSigned() && RHS.isNegative()) { 1587091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall RHS = -RHS; 1588091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall goto shift_left; 1589091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall } 1590091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall 1591091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall shift_right: 15921eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump unsigned SA = 159330c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar (unsigned) RHS.getLimitedValue(Result.getInt().getBitWidth()-1); 159430c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar return Success(Result.getInt() >> SA, E); 15953f7d995390009fede92b333a040da80e1ce90997Daniel Dunbar } 15961eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 15972de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_LT: return Success(Result.getInt() < RHS, E); 15982de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_GT: return Success(Result.getInt() > RHS, E); 15992de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_LE: return Success(Result.getInt() <= RHS, E); 16002de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_GE: return Success(Result.getInt() >= RHS, E); 16012de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_EQ: return Success(Result.getInt() == RHS, E); 16022de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_NE: return Success(Result.getInt() != RHS, E); 1603b11e77836dd0867955c5abf32baf1c3e6c7f81e1Eli Friedman } 1604a25ae3d68d84d2b89907f998df6a396549589da5Anders Carlsson} 1605a25ae3d68d84d2b89907f998df6a396549589da5Anders Carlsson 16068b752f10c394b140f9ef89e049cbad1a7676fc25Ken DyckCharUnits IntExprEvaluator::GetAlignOfType(QualType T) { 16075d484e8cf710207010720589d89602233de61d01Sebastian Redl // C++ [expr.sizeof]p2: "When applied to a reference or a reference type, 16085d484e8cf710207010720589d89602233de61d01Sebastian Redl // the result is the size of the referenced type." 16095d484e8cf710207010720589d89602233de61d01Sebastian Redl // C++ [expr.alignof]p3: "When alignof is applied to a reference type, the 16105d484e8cf710207010720589d89602233de61d01Sebastian Redl // result shall be the alignment of the referenced type." 16115d484e8cf710207010720589d89602233de61d01Sebastian Redl if (const ReferenceType *Ref = T->getAs<ReferenceType>()) 16125d484e8cf710207010720589d89602233de61d01Sebastian Redl T = Ref->getPointeeType(); 16139f1210c3280104417a4ad30f0a00825ac8fa718aChad Rosier 16149f1210c3280104417a4ad30f0a00825ac8fa718aChad Rosier // __alignof is defined to return the preferred alignment. 16159f1210c3280104417a4ad30f0a00825ac8fa718aChad Rosier return Info.Ctx.toCharUnitsFromBits( 16169f1210c3280104417a4ad30f0a00825ac8fa718aChad Rosier Info.Ctx.getPreferredTypeAlign(T.getTypePtr())); 1617e9feb475d72ba50dc29cec62a8c47cae721065ebChris Lattner} 1618e9feb475d72ba50dc29cec62a8c47cae721065ebChris Lattner 16198b752f10c394b140f9ef89e049cbad1a7676fc25Ken DyckCharUnits IntExprEvaluator::GetAlignOfExpr(const Expr *E) { 1620af707ab8fbb9451e8febb8d766f6c043628125c4Chris Lattner E = E->IgnoreParens(); 1621af707ab8fbb9451e8febb8d766f6c043628125c4Chris Lattner 1622af707ab8fbb9451e8febb8d766f6c043628125c4Chris Lattner // alignof decl is always accepted, even if it doesn't make sense: we default 16231eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump // to 1 in those cases. 1624af707ab8fbb9451e8febb8d766f6c043628125c4Chris Lattner if (const DeclRefExpr *DRE = dyn_cast<DeclRefExpr>(E)) 16258b752f10c394b140f9ef89e049cbad1a7676fc25Ken Dyck return Info.Ctx.getDeclAlign(DRE->getDecl(), 16268b752f10c394b140f9ef89e049cbad1a7676fc25Ken Dyck /*RefAsPointee*/true); 1627a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman 1628af707ab8fbb9451e8febb8d766f6c043628125c4Chris Lattner if (const MemberExpr *ME = dyn_cast<MemberExpr>(E)) 16298b752f10c394b140f9ef89e049cbad1a7676fc25Ken Dyck return Info.Ctx.getDeclAlign(ME->getMemberDecl(), 16308b752f10c394b140f9ef89e049cbad1a7676fc25Ken Dyck /*RefAsPointee*/true); 1631af707ab8fbb9451e8febb8d766f6c043628125c4Chris Lattner 1632e9feb475d72ba50dc29cec62a8c47cae721065ebChris Lattner return GetAlignOfType(E->getType()); 1633e9feb475d72ba50dc29cec62a8c47cae721065ebChris Lattner} 1634e9feb475d72ba50dc29cec62a8c47cae721065ebChris Lattner 1635e9feb475d72ba50dc29cec62a8c47cae721065ebChris Lattner 1636f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne/// VisitUnaryExprOrTypeTraitExpr - Evaluate a sizeof, alignof or vec_step with 1637f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne/// a result as the expression's type. 1638f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbournebool IntExprEvaluator::VisitUnaryExprOrTypeTraitExpr( 1639f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne const UnaryExprOrTypeTraitExpr *E) { 1640f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne switch(E->getKind()) { 1641f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne case UETT_AlignOf: { 1642e9feb475d72ba50dc29cec62a8c47cae721065ebChris Lattner if (E->isArgumentType()) 16434f3bc8f7aa90b72832b03bee9201c98f4bb6b4d1Ken Dyck return Success(GetAlignOfType(E->getArgumentType()), E); 1644e9feb475d72ba50dc29cec62a8c47cae721065ebChris Lattner else 16454f3bc8f7aa90b72832b03bee9201c98f4bb6b4d1Ken Dyck return Success(GetAlignOfExpr(E->getArgumentExpr()), E); 1646e9feb475d72ba50dc29cec62a8c47cae721065ebChris Lattner } 1647a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman 1648f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne case UETT_VecStep: { 1649f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne QualType Ty = E->getTypeOfArgument(); 16500518999d3adcc289997bd974dce90cc97f5c1c44Sebastian Redl 1651f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne if (Ty->isVectorType()) { 1652f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne unsigned n = Ty->getAs<VectorType>()->getNumElements(); 1653a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman 1654f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne // The vec_step built-in functions that take a 3-component 1655f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne // vector return 4. (OpenCL 1.1 spec 6.11.12) 1656f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne if (n == 3) 1657f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne n = 4; 1658f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne 1659f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne return Success(n, E); 1660f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne } else 1661f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne return Success(1, E); 1662f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne } 1663f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne 1664f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne case UETT_SizeOf: { 1665f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne QualType SrcTy = E->getTypeOfArgument(); 1666f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne // C++ [expr.sizeof]p2: "When applied to a reference or a reference type, 1667f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne // the result is the size of the referenced type." 1668f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne // C++ [expr.alignof]p3: "When alignof is applied to a reference type, the 1669f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne // result shall be the alignment of the referenced type." 1670f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne if (const ReferenceType *Ref = SrcTy->getAs<ReferenceType>()) 1671f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne SrcTy = Ref->getPointeeType(); 1672f2da9dfef96dc11b7b5effb1d02cb427b2d71599Eli Friedman 1673f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne // sizeof(void), __alignof__(void), sizeof(function) = 1 as a gcc 1674f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne // extension. 1675f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne if (SrcTy->isVoidType() || SrcTy->isFunctionType()) 1676f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne return Success(1, E); 1677f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne 1678f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne // sizeof(vla) is not a constantexpr: C99 6.5.3.4p2. 1679f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne if (!SrcTy->isConstantSizeType()) 1680f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne return false; 1681f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne 1682f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne // Get information about the size. 1683f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne return Success(Info.Ctx.getTypeSizeInChars(SrcTy), E); 1684f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne } 1685f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne } 1686f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne 1687f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne llvm_unreachable("unknown expr/type trait"); 1688f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne return false; 1689fcee0019b76f9f368f2b3d6d4048a98232593f29Chris Lattner} 1690fcee0019b76f9f368f2b3d6d4048a98232593f29Chris Lattner 16918cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbournebool IntExprEvaluator::VisitOffsetOfExpr(const OffsetOfExpr *OOE) { 16928ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor CharUnits Result; 16938cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne unsigned n = OOE->getNumComponents(); 16948ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor if (n == 0) 16958ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor return false; 16968cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne QualType CurrentType = OOE->getTypeSourceInfo()->getType(); 16978ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor for (unsigned i = 0; i != n; ++i) { 16988ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor OffsetOfExpr::OffsetOfNode ON = OOE->getComponent(i); 16998ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor switch (ON.getKind()) { 17008ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor case OffsetOfExpr::OffsetOfNode::Array: { 17018cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne const Expr *Idx = OOE->getIndexExpr(ON.getArrayExprIndex()); 17028ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor APSInt IdxResult; 17038ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor if (!EvaluateInteger(Idx, IdxResult, Info)) 17048ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor return false; 17058ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor const ArrayType *AT = Info.Ctx.getAsArrayType(CurrentType); 17068ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor if (!AT) 17078ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor return false; 17088ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor CurrentType = AT->getElementType(); 17098ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor CharUnits ElementSize = Info.Ctx.getTypeSizeInChars(CurrentType); 17108ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor Result += IdxResult.getSExtValue() * ElementSize; 17118ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor break; 17128ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor } 17138ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor 17148ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor case OffsetOfExpr::OffsetOfNode::Field: { 17158ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor FieldDecl *MemberDecl = ON.getField(); 17168ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor const RecordType *RT = CurrentType->getAs<RecordType>(); 17178ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor if (!RT) 17188ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor return false; 17198ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor RecordDecl *RD = RT->getDecl(); 17208ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor const ASTRecordLayout &RL = Info.Ctx.getASTRecordLayout(RD); 1721ba4f5d5754c8291690d01ca9581926673d69b24cJohn McCall unsigned i = MemberDecl->getFieldIndex(); 1722cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor assert(i < RL.getFieldCount() && "offsetof field in wrong type"); 1723fb1e3bc29b667f4275e1d5a43d64ec173f4f9a7dKen Dyck Result += Info.Ctx.toCharUnitsFromBits(RL.getFieldOffset(i)); 17248ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor CurrentType = MemberDecl->getType().getNonReferenceType(); 17258ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor break; 17268ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor } 17278ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor 17288ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor case OffsetOfExpr::OffsetOfNode::Identifier: 17298ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor llvm_unreachable("dependent __builtin_offsetof"); 1730cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor return false; 1731cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor 1732cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor case OffsetOfExpr::OffsetOfNode::Base: { 1733cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor CXXBaseSpecifier *BaseSpec = ON.getBase(); 1734cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor if (BaseSpec->isVirtual()) 1735cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor return false; 1736cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor 1737cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor // Find the layout of the class whose base we are looking into. 1738cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor const RecordType *RT = CurrentType->getAs<RecordType>(); 1739cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor if (!RT) 1740cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor return false; 1741cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor RecordDecl *RD = RT->getDecl(); 1742cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor const ASTRecordLayout &RL = Info.Ctx.getASTRecordLayout(RD); 1743cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor 1744cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor // Find the base class itself. 1745cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor CurrentType = BaseSpec->getType(); 1746cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor const RecordType *BaseRT = CurrentType->getAs<RecordType>(); 1747cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor if (!BaseRT) 1748cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor return false; 1749cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor 1750cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor // Add the offset to the base. 17517c7f820d70c925b29290a8563b59615816a827fcKen Dyck Result += RL.getBaseClassOffset(cast<CXXRecordDecl>(BaseRT->getDecl())); 1752cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor break; 1753cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor } 17548ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor } 17558ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor } 17568cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne return Success(Result, OOE); 17578ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor} 17588ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor 1759b542afe02d317411d53b3541946f9f2a8f509a11Chris Lattnerbool IntExprEvaluator::VisitUnaryOperator(const UnaryOperator *E) { 17602de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall if (E->getOpcode() == UO_LNot) { 1761a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman // LNot's operand isn't necessarily an integer, so we handle it specially. 1762a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman bool bres; 1763a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman if (!HandleConversionToBool(E->getSubExpr(), bres, Info)) 1764a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman return false; 1765131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar return Success(!bres, E); 1766a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman } 1767a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman 17684fff4819a913c65ae23cfd389bc47c61919e4e1fDaniel Dunbar // Only handle integral operations... 17692ade35e2cfd554e49d35a52047cea98a82787af9Douglas Gregor if (!E->getSubExpr()->getType()->isIntegralOrEnumerationType()) 17704fff4819a913c65ae23cfd389bc47c61919e4e1fDaniel Dunbar return false; 17714fff4819a913c65ae23cfd389bc47c61919e4e1fDaniel Dunbar 177287eae5ecf94e38baa20d9a327b8f73f8bdc72436Chris Lattner // Get the operand value into 'Result'. 177387eae5ecf94e38baa20d9a327b8f73f8bdc72436Chris Lattner if (!Visit(E->getSubExpr())) 177475a4881047deeb3a300ff9293dc6ba8570048bb5Chris Lattner return false; 1775a25ae3d68d84d2b89907f998df6a396549589da5Anders Carlsson 177675a4881047deeb3a300ff9293dc6ba8570048bb5Chris Lattner switch (E->getOpcode()) { 17774c4867e140327fa3b56306fa03c64c8e6a7c95efChris Lattner default: 177875a4881047deeb3a300ff9293dc6ba8570048bb5Chris Lattner // Address, indirect, pre/post inc/dec, etc are not valid constant exprs. 177975a4881047deeb3a300ff9293dc6ba8570048bb5Chris Lattner // See C99 6.6p3. 17800e8acbbba71ec6acd5dceb4fcbce63e463e1b755Anders Carlsson return Error(E->getOperatorLoc(), diag::note_invalid_subexpr_in_ice, E); 17812de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case UO_Extension: 17824c4867e140327fa3b56306fa03c64c8e6a7c95efChris Lattner // FIXME: Should extension allow i-c-e extension expressions in its scope? 17834c4867e140327fa3b56306fa03c64c8e6a7c95efChris Lattner // If so, we could clear the diagnostic ID. 17843f7d995390009fede92b333a040da80e1ce90997Daniel Dunbar return true; 17852de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case UO_Plus: 17861eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump // The result is always just the subexpr. 17873f7d995390009fede92b333a040da80e1ce90997Daniel Dunbar return true; 17882de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case UO_Minus: 178930c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar if (!Result.isInt()) return false; 179030c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar return Success(-Result.getInt(), E); 17912de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case UO_Not: 179230c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar if (!Result.isInt()) return false; 179330c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar return Success(~Result.getInt(), E); 179406a3675627e3b3c47b49c689c8e404a33144194aAnders Carlsson } 1795a25ae3d68d84d2b89907f998df6a396549589da5Anders Carlsson} 17961eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1797732b2236ae4a4f11e7642677cebbd169c07ea877Chris Lattner/// HandleCast - This is used to evaluate implicit or explicit casts where the 1798732b2236ae4a4f11e7642677cebbd169c07ea877Chris Lattner/// result type is integer. 17998cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbournebool IntExprEvaluator::VisitCastExpr(const CastExpr *E) { 18008cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne const Expr *SubExpr = E->getSubExpr(); 180182206e267ce6cc709797127616f64672d255b310Anders Carlsson QualType DestType = E->getType(); 1802b92dac8bc2f6f73919825f9af693a8a7e89ae1d4Daniel Dunbar QualType SrcType = SubExpr->getType(); 180382206e267ce6cc709797127616f64672d255b310Anders Carlsson 180446a523285928aa07bf14803178dc04616ac85994Eli Friedman switch (E->getCastKind()) { 180546a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_BaseToDerived: 180646a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_DerivedToBase: 180746a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_UncheckedDerivedToBase: 180846a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_Dynamic: 180946a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_ToUnion: 181046a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_ArrayToPointerDecay: 181146a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_FunctionToPointerDecay: 181246a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_NullToPointer: 181346a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_NullToMemberPointer: 181446a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_BaseToDerivedMemberPointer: 181546a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_DerivedToBaseMemberPointer: 181646a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_ConstructorConversion: 181746a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_IntegralToPointer: 181846a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_ToVoid: 181946a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_VectorSplat: 182046a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_IntegralToFloating: 182146a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_FloatingCast: 18221d9b3b25f7ac0d0195bba6b507a684fe5e7943eeJohn McCall case CK_CPointerToObjCPointerCast: 18231d9b3b25f7ac0d0195bba6b507a684fe5e7943eeJohn McCall case CK_BlockPointerToObjCPointerCast: 182446a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_AnyPointerToBlockPointerCast: 182546a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_ObjCObjectLValueCast: 182646a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_FloatingRealToComplex: 182746a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_FloatingComplexToReal: 182846a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_FloatingComplexCast: 182946a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_FloatingComplexToIntegralComplex: 183046a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_IntegralRealToComplex: 183146a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_IntegralComplexCast: 183246a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_IntegralComplexToFloatingComplex: 183346a523285928aa07bf14803178dc04616ac85994Eli Friedman llvm_unreachable("invalid cast kind for integral value"); 183446a523285928aa07bf14803178dc04616ac85994Eli Friedman 1835e50c297f92914ca996deb8b597624193273b62e4Eli Friedman case CK_BitCast: 183646a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_Dependent: 183746a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_GetObjCProperty: 183846a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_LValueBitCast: 183946a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_UserDefinedConversion: 184033e56f3273457bfa22c7c50bc46cf5a18216863dJohn McCall case CK_ARCProduceObject: 184133e56f3273457bfa22c7c50bc46cf5a18216863dJohn McCall case CK_ARCConsumeObject: 184233e56f3273457bfa22c7c50bc46cf5a18216863dJohn McCall case CK_ARCReclaimReturnedObject: 184333e56f3273457bfa22c7c50bc46cf5a18216863dJohn McCall case CK_ARCExtendBlockObject: 184446a523285928aa07bf14803178dc04616ac85994Eli Friedman return false; 184546a523285928aa07bf14803178dc04616ac85994Eli Friedman 184646a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_LValueToRValue: 184746a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_NoOp: 184846a523285928aa07bf14803178dc04616ac85994Eli Friedman return Visit(E->getSubExpr()); 184946a523285928aa07bf14803178dc04616ac85994Eli Friedman 185046a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_MemberPointerToBoolean: 185146a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_PointerToBoolean: 185246a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_IntegralToBoolean: 185346a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_FloatingToBoolean: 185446a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_FloatingComplexToBoolean: 185546a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_IntegralComplexToBoolean: { 18564efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman bool BoolResult; 18574efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman if (!HandleConversionToBool(SubExpr, BoolResult, Info)) 18584efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman return false; 1859131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar return Success(BoolResult, E); 18604efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman } 18614efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman 186246a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_IntegralCast: { 1863732b2236ae4a4f11e7642677cebbd169c07ea877Chris Lattner if (!Visit(SubExpr)) 1864b542afe02d317411d53b3541946f9f2a8f509a11Chris Lattner return false; 1865a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar 1866be26570e3faa009bdcefedfaf04473e518940520Eli Friedman if (!Result.isInt()) { 1867be26570e3faa009bdcefedfaf04473e518940520Eli Friedman // Only allow casts of lvalues if they are lossless. 1868be26570e3faa009bdcefedfaf04473e518940520Eli Friedman return Info.Ctx.getTypeSize(DestType) == Info.Ctx.getTypeSize(SrcType); 1869be26570e3faa009bdcefedfaf04473e518940520Eli Friedman } 187030c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar 1871dd2116462ae311043986ae8b7fba27e68c1b2e66Daniel Dunbar return Success(HandleIntToIntCast(DestType, SrcType, 187230c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar Result.getInt(), Info.Ctx), E); 1873732b2236ae4a4f11e7642677cebbd169c07ea877Chris Lattner } 18741eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 187546a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_PointerToIntegral: { 1876efdb83e26f9a1fd2566afe54461216cd84814d42John McCall LValue LV; 187787eae5ecf94e38baa20d9a327b8f73f8bdc72436Chris Lattner if (!EvaluatePointer(SubExpr, LV, Info)) 1878b542afe02d317411d53b3541946f9f2a8f509a11Chris Lattner return false; 18794efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman 1880dd2116462ae311043986ae8b7fba27e68c1b2e66Daniel Dunbar if (LV.getLValueBase()) { 1881dd2116462ae311043986ae8b7fba27e68c1b2e66Daniel Dunbar // Only allow based lvalue casts if they are lossless. 1882dd2116462ae311043986ae8b7fba27e68c1b2e66Daniel Dunbar if (Info.Ctx.getTypeSize(DestType) != Info.Ctx.getTypeSize(SrcType)) 1883dd2116462ae311043986ae8b7fba27e68c1b2e66Daniel Dunbar return false; 1884dd2116462ae311043986ae8b7fba27e68c1b2e66Daniel Dunbar 1885efdb83e26f9a1fd2566afe54461216cd84814d42John McCall LV.moveInto(Result); 1886dd2116462ae311043986ae8b7fba27e68c1b2e66Daniel Dunbar return true; 1887dd2116462ae311043986ae8b7fba27e68c1b2e66Daniel Dunbar } 18884efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman 1889a73058324197b7bdfd19307965954f626e26199dKen Dyck APSInt AsInt = Info.Ctx.MakeIntValue(LV.getLValueOffset().getQuantity(), 1890a73058324197b7bdfd19307965954f626e26199dKen Dyck SrcType); 1891dd2116462ae311043986ae8b7fba27e68c1b2e66Daniel Dunbar return Success(HandleIntToIntCast(DestType, SrcType, AsInt, Info.Ctx), E); 18922bad1687fe6f00e10767a691a33b070b151902b6Anders Carlsson } 18934efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman 189446a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_IntegralComplexToReal: { 1895f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall ComplexValue C; 18961725f683432715e5afe34d476024bd6f16eac3fcEli Friedman if (!EvaluateComplex(SubExpr, C, Info)) 18971725f683432715e5afe34d476024bd6f16eac3fcEli Friedman return false; 189846a523285928aa07bf14803178dc04616ac85994Eli Friedman return Success(C.getComplexIntReal(), E); 18991725f683432715e5afe34d476024bd6f16eac3fcEli Friedman } 19002217c87bdc5ab357046a5453bdb06f469c41024eEli Friedman 190146a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_FloatingToIntegral: { 190246a523285928aa07bf14803178dc04616ac85994Eli Friedman APFloat F(0.0); 190346a523285928aa07bf14803178dc04616ac85994Eli Friedman if (!EvaluateFloat(SubExpr, F, Info)) 190446a523285928aa07bf14803178dc04616ac85994Eli Friedman return false; 1905732b2236ae4a4f11e7642677cebbd169c07ea877Chris Lattner 190646a523285928aa07bf14803178dc04616ac85994Eli Friedman return Success(HandleFloatToIntCast(DestType, SrcType, F, Info.Ctx), E); 190746a523285928aa07bf14803178dc04616ac85994Eli Friedman } 190846a523285928aa07bf14803178dc04616ac85994Eli Friedman } 19091eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 191046a523285928aa07bf14803178dc04616ac85994Eli Friedman llvm_unreachable("unknown cast resulting in integral value"); 191146a523285928aa07bf14803178dc04616ac85994Eli Friedman return false; 1912a25ae3d68d84d2b89907f998df6a396549589da5Anders Carlsson} 19132bad1687fe6f00e10767a691a33b070b151902b6Anders Carlsson 1914722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedmanbool IntExprEvaluator::VisitUnaryReal(const UnaryOperator *E) { 1915722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman if (E->getSubExpr()->getType()->isAnyComplexType()) { 1916f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall ComplexValue LV; 1917722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman if (!EvaluateComplex(E->getSubExpr(), LV, Info) || !LV.isComplexInt()) 1918722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman return Error(E->getExprLoc(), diag::note_invalid_subexpr_in_ice, E); 1919722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman return Success(LV.getComplexIntReal(), E); 1920722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman } 1921722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman 1922722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman return Visit(E->getSubExpr()); 1923722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman} 1924722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman 1925664a104ba0b8f47b8908ec6af694d9646adba1fcEli Friedmanbool IntExprEvaluator::VisitUnaryImag(const UnaryOperator *E) { 1926722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman if (E->getSubExpr()->getType()->isComplexIntegerType()) { 1927f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall ComplexValue LV; 1928722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman if (!EvaluateComplex(E->getSubExpr(), LV, Info) || !LV.isComplexInt()) 1929722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman return Error(E->getExprLoc(), diag::note_invalid_subexpr_in_ice, E); 1930722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman return Success(LV.getComplexIntImag(), E); 1931722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman } 1932722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman 1933664a104ba0b8f47b8908ec6af694d9646adba1fcEli Friedman if (!E->getSubExpr()->isEvaluatable(Info.Ctx)) 1934664a104ba0b8f47b8908ec6af694d9646adba1fcEli Friedman Info.EvalResult.HasSideEffects = true; 1935664a104ba0b8f47b8908ec6af694d9646adba1fcEli Friedman return Success(0, E); 1936664a104ba0b8f47b8908ec6af694d9646adba1fcEli Friedman} 1937664a104ba0b8f47b8908ec6af694d9646adba1fcEli Friedman 1938ee8aff06f6a96214731de17b2cb6df407c6c1820Douglas Gregorbool IntExprEvaluator::VisitSizeOfPackExpr(const SizeOfPackExpr *E) { 1939ee8aff06f6a96214731de17b2cb6df407c6c1820Douglas Gregor return Success(E->getPackLength(), E); 1940ee8aff06f6a96214731de17b2cb6df407c6c1820Douglas Gregor} 1941ee8aff06f6a96214731de17b2cb6df407c6c1820Douglas Gregor 1942295995c9c3196416372c9cd35d9cedb6da37bd3dSebastian Redlbool IntExprEvaluator::VisitCXXNoexceptExpr(const CXXNoexceptExpr *E) { 1943295995c9c3196416372c9cd35d9cedb6da37bd3dSebastian Redl return Success(E->getValue(), E); 1944295995c9c3196416372c9cd35d9cedb6da37bd3dSebastian Redl} 1945295995c9c3196416372c9cd35d9cedb6da37bd3dSebastian Redl 1946cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redlbool IntExprEvaluator::VisitInitListExpr(const InitListExpr *E) { 1947cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl if (!Info.Ctx.getLangOptions().CPlusPlus0x) 1948cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl return Error(E); 1949cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl 1950cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl if (E->getNumInits() == 0) 1951cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl return Success(0, E); 1952cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl 1953cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl assert(E->getNumInits() == 1 && "Excess initializers for integer in C++11."); 1954cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl return Visit(E->getInit(0)); 1955cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl} 1956cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl 1957f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner//===----------------------------------------------------------------------===// 1958d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman// Float Evaluation 1959d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman//===----------------------------------------------------------------------===// 1960d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman 1961d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedmannamespace { 1962770b4a8834670e9427d3ce5a1a8472eb86f45fd2Benjamin Kramerclass FloatExprEvaluator 19638cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne : public ExprEvaluatorBase<FloatExprEvaluator, bool> { 1964d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman APFloat &Result; 1965d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedmanpublic: 1966d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman FloatExprEvaluator(EvalInfo &info, APFloat &result) 19678cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne : ExprEvaluatorBaseTy(info), Result(result) {} 1968d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman 19698cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool Success(const APValue &V, const Expr *e) { 19708cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne Result = V.getFloat(); 19718cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne return true; 19728cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne } 19738cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool Error(const Stmt *S) { 1974d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman return false; 1975d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman } 1976d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman 1977019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner bool VisitCallExpr(const CallExpr *E); 1978d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman 19795db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar bool VisitUnaryOperator(const UnaryOperator *E); 1980d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman bool VisitBinaryOperator(const BinaryOperator *E); 1981d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman bool VisitFloatingLiteral(const FloatingLiteral *E); 19828cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitCastExpr(const CastExpr *E); 19838cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitCXXScalarValueInitExpr(const CXXScalarValueInitExpr *E); 19842217c87bdc5ab357046a5453bdb06f469c41024eEli Friedman 1985abd3a857ace59100305790545d1baae5877b8945John McCall bool VisitUnaryReal(const UnaryOperator *E); 1986abd3a857ace59100305790545d1baae5877b8945John McCall bool VisitUnaryImag(const UnaryOperator *E); 1987ba98d6bb414861965a1f22628494ea046785ecd4Eli Friedman 1988189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall bool VisitDeclRefExpr(const DeclRefExpr *E); 1989189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall 1990cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl bool VisitInitListExpr(const InitListExpr *E); 1991cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl 1992abd3a857ace59100305790545d1baae5877b8945John McCall // FIXME: Missing: array subscript of vector, member of vector, 1993abd3a857ace59100305790545d1baae5877b8945John McCall // ImplicitValueInitExpr 1994d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman}; 1995d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman} // end anonymous namespace 1996d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman 1997d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedmanstatic bool EvaluateFloat(const Expr* E, APFloat& Result, EvalInfo &Info) { 19987db7acbbb84b82d0522266a50ebabc3a52a9e5d1John McCall assert(E->getType()->isRealFloatingType()); 19998cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne return FloatExprEvaluator(Info, Result).Visit(E); 2000d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman} 2001d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman 20024ba2a17694148e16eaa8d3917f657ffcd3667be4Jay Foadstatic bool TryEvaluateBuiltinNaN(const ASTContext &Context, 2003db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall QualType ResultTy, 2004db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall const Expr *Arg, 2005db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall bool SNaN, 2006db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall llvm::APFloat &Result) { 2007db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall const StringLiteral *S = dyn_cast<StringLiteral>(Arg->IgnoreParenCasts()); 2008db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall if (!S) return false; 2009db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall 2010db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall const llvm::fltSemantics &Sem = Context.getFloatTypeSemantics(ResultTy); 2011db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall 2012db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall llvm::APInt fill; 2013db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall 2014db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall // Treat empty strings as if they were zero. 2015db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall if (S->getString().empty()) 2016db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall fill = llvm::APInt(32, 0); 2017db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall else if (S->getString().getAsInteger(0, fill)) 2018db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall return false; 2019db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall 2020db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall if (SNaN) 2021db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall Result = llvm::APFloat::getSNaN(Sem, false, &fill); 2022db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall else 2023db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall Result = llvm::APFloat::getQNaN(Sem, false, &fill); 2024db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall return true; 2025db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall} 2026db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall 2027019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattnerbool FloatExprEvaluator::VisitCallExpr(const CallExpr *E) { 20283c385e5f8d9008fff18597ca302be19fa86e51f6Douglas Gregor switch (E->isBuiltinCall(Info.Ctx)) { 20298cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne default: 20308cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne return ExprEvaluatorBaseTy::VisitCallExpr(E); 20318cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne 2032019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner case Builtin::BI__builtin_huge_val: 2033019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner case Builtin::BI__builtin_huge_valf: 2034019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner case Builtin::BI__builtin_huge_vall: 2035019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner case Builtin::BI__builtin_inf: 2036019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner case Builtin::BI__builtin_inff: 20377cbed03c00e246682e5292785d01e1c120ce54bdDaniel Dunbar case Builtin::BI__builtin_infl: { 20387cbed03c00e246682e5292785d01e1c120ce54bdDaniel Dunbar const llvm::fltSemantics &Sem = 20397cbed03c00e246682e5292785d01e1c120ce54bdDaniel Dunbar Info.Ctx.getFloatTypeSemantics(E->getType()); 204034a74ab81600a40c6324fd76adb724b803dfaf91Chris Lattner Result = llvm::APFloat::getInf(Sem); 204134a74ab81600a40c6324fd76adb724b803dfaf91Chris Lattner return true; 20427cbed03c00e246682e5292785d01e1c120ce54bdDaniel Dunbar } 20431eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 2044db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall case Builtin::BI__builtin_nans: 2045db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall case Builtin::BI__builtin_nansf: 2046db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall case Builtin::BI__builtin_nansl: 2047db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall return TryEvaluateBuiltinNaN(Info.Ctx, E->getType(), E->getArg(0), 2048db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall true, Result); 2049db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall 20509e62171a25e3a08fb5c49fb370f83faf5ae786f5Chris Lattner case Builtin::BI__builtin_nan: 20519e62171a25e3a08fb5c49fb370f83faf5ae786f5Chris Lattner case Builtin::BI__builtin_nanf: 20529e62171a25e3a08fb5c49fb370f83faf5ae786f5Chris Lattner case Builtin::BI__builtin_nanl: 20534572baba9d18c275968ac113fd73b0e3c77cccb8Mike Stump // If this is __builtin_nan() turn this into a nan, otherwise we 20549e62171a25e3a08fb5c49fb370f83faf5ae786f5Chris Lattner // can't constant fold it. 2055db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall return TryEvaluateBuiltinNaN(Info.Ctx, E->getType(), E->getArg(0), 2056db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall false, Result); 20575db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar 20585db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar case Builtin::BI__builtin_fabs: 20595db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar case Builtin::BI__builtin_fabsf: 20605db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar case Builtin::BI__builtin_fabsl: 20615db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar if (!EvaluateFloat(E->getArg(0), Result, Info)) 20625db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar return false; 20631eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 20645db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar if (Result.isNegative()) 20655db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar Result.changeSign(); 20665db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar return true; 20675db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar 20681eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump case Builtin::BI__builtin_copysign: 20691eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump case Builtin::BI__builtin_copysignf: 20705db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar case Builtin::BI__builtin_copysignl: { 20715db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar APFloat RHS(0.); 20725db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar if (!EvaluateFloat(E->getArg(0), Result, Info) || 20735db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar !EvaluateFloat(E->getArg(1), RHS, Info)) 20745db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar return false; 20755db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar Result.copySign(RHS); 20765db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar return true; 20775db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar } 2078019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner } 2079019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner} 2080019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner 2081189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCallbool FloatExprEvaluator::VisitDeclRefExpr(const DeclRefExpr *E) { 20828cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne if (ExprEvaluatorBaseTy::VisitDeclRefExpr(E)) 20838cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne return true; 20848cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne 2085189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall const Decl *D = E->getDecl(); 2086189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall if (!isa<VarDecl>(D) || isa<ParmVarDecl>(D)) return false; 2087189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall const VarDecl *VD = cast<VarDecl>(D); 2088189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall 2089189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall // Require the qualifiers to be const and not volatile. 2090189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall CanQualType T = Info.Ctx.getCanonicalType(E->getType()); 2091189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall if (!T.isConstQualified() || T.isVolatileQualified()) 2092189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall return false; 2093189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall 2094189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall const Expr *Init = VD->getAnyInitializer(); 2095189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall if (!Init) return false; 2096189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall 2097189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall if (APValue *V = VD->getEvaluatedValue()) { 2098189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall if (V->isFloat()) { 2099189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall Result = V->getFloat(); 2100189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall return true; 2101189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall } 2102189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall return false; 2103189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall } 2104189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall 2105189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall if (VD->isEvaluatingValue()) 2106189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall return false; 2107189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall 2108189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall VD->setEvaluatingValue(); 2109189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall 2110189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall Expr::EvalResult InitResult; 2111189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall if (Init->Evaluate(InitResult, Info.Ctx) && !InitResult.HasSideEffects && 2112189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall InitResult.Val.isFloat()) { 2113189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall // Cache the evaluated value in the variable declaration. 2114189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall Result = InitResult.Val.getFloat(); 2115189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall VD->setEvaluatedValue(InitResult.Val); 2116189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall return true; 2117189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall } 2118189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall 2119189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall VD->setEvaluatedValue(APValue()); 2120189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall return false; 2121189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall} 2122189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall 2123abd3a857ace59100305790545d1baae5877b8945John McCallbool FloatExprEvaluator::VisitUnaryReal(const UnaryOperator *E) { 212443efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman if (E->getSubExpr()->getType()->isAnyComplexType()) { 212543efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman ComplexValue CV; 212643efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman if (!EvaluateComplex(E->getSubExpr(), CV, Info)) 212743efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman return false; 212843efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman Result = CV.FloatReal; 212943efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman return true; 213043efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman } 213143efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman 213243efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman return Visit(E->getSubExpr()); 2133abd3a857ace59100305790545d1baae5877b8945John McCall} 2134abd3a857ace59100305790545d1baae5877b8945John McCall 2135abd3a857ace59100305790545d1baae5877b8945John McCallbool FloatExprEvaluator::VisitUnaryImag(const UnaryOperator *E) { 213643efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman if (E->getSubExpr()->getType()->isAnyComplexType()) { 213743efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman ComplexValue CV; 213843efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman if (!EvaluateComplex(E->getSubExpr(), CV, Info)) 213943efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman return false; 214043efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman Result = CV.FloatImag; 214143efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman return true; 214243efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman } 214343efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman 214443efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman if (!E->getSubExpr()->isEvaluatable(Info.Ctx)) 214543efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman Info.EvalResult.HasSideEffects = true; 214643efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman const llvm::fltSemantics &Sem = Info.Ctx.getFloatTypeSemantics(E->getType()); 214743efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman Result = llvm::APFloat::getZero(Sem); 2148abd3a857ace59100305790545d1baae5877b8945John McCall return true; 2149abd3a857ace59100305790545d1baae5877b8945John McCall} 2150abd3a857ace59100305790545d1baae5877b8945John McCall 21515db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbarbool FloatExprEvaluator::VisitUnaryOperator(const UnaryOperator *E) { 21522de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall if (E->getOpcode() == UO_Deref) 2153a468d34bed16861f25aff6c8354f4e75d3358c1aNuno Lopes return false; 2154a468d34bed16861f25aff6c8354f4e75d3358c1aNuno Lopes 21555db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar if (!EvaluateFloat(E->getSubExpr(), Result, Info)) 21565db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar return false; 21575db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar 21585db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar switch (E->getOpcode()) { 21595db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar default: return false; 21602de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case UO_Plus: 21615db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar return true; 21622de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case UO_Minus: 21635db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar Result.changeSign(); 21645db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar return true; 21655db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar } 21665db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar} 2167019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner 2168d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedmanbool FloatExprEvaluator::VisitBinaryOperator(const BinaryOperator *E) { 21692de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall if (E->getOpcode() == BO_Comma) { 21707f92f0362ef2cf218bc19bb83e1a97dd254b5527Eli Friedman if (!EvaluateFloat(E->getRHS(), Result, Info)) 21717f92f0362ef2cf218bc19bb83e1a97dd254b5527Eli Friedman return false; 21727f92f0362ef2cf218bc19bb83e1a97dd254b5527Eli Friedman 21737f92f0362ef2cf218bc19bb83e1a97dd254b5527Eli Friedman // If we can't evaluate the LHS, it might have side effects; 21747f92f0362ef2cf218bc19bb83e1a97dd254b5527Eli Friedman // conservatively mark it. 21757f92f0362ef2cf218bc19bb83e1a97dd254b5527Eli Friedman if (!E->getLHS()->isEvaluatable(Info.Ctx)) 21767f92f0362ef2cf218bc19bb83e1a97dd254b5527Eli Friedman Info.EvalResult.HasSideEffects = true; 21777f92f0362ef2cf218bc19bb83e1a97dd254b5527Eli Friedman 21787f92f0362ef2cf218bc19bb83e1a97dd254b5527Eli Friedman return true; 21797f92f0362ef2cf218bc19bb83e1a97dd254b5527Eli Friedman } 21807f92f0362ef2cf218bc19bb83e1a97dd254b5527Eli Friedman 218196e93660124c8028a4c3bcc038ab0cdd18cd7ab2Anders Carlsson // We can't evaluate pointer-to-member operations. 218296e93660124c8028a4c3bcc038ab0cdd18cd7ab2Anders Carlsson if (E->isPtrMemOp()) 218396e93660124c8028a4c3bcc038ab0cdd18cd7ab2Anders Carlsson return false; 218496e93660124c8028a4c3bcc038ab0cdd18cd7ab2Anders Carlsson 2185d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman // FIXME: Diagnostics? I really don't understand how the warnings 2186d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman // and errors are supposed to work. 21875db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar APFloat RHS(0.0); 2188d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman if (!EvaluateFloat(E->getLHS(), Result, Info)) 2189d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman return false; 2190d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman if (!EvaluateFloat(E->getRHS(), RHS, Info)) 2191d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman return false; 2192d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman 2193d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman switch (E->getOpcode()) { 2194d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman default: return false; 21952de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Mul: 2196d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman Result.multiply(RHS, APFloat::rmNearestTiesToEven); 2197d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman return true; 21982de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Add: 2199d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman Result.add(RHS, APFloat::rmNearestTiesToEven); 2200d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman return true; 22012de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Sub: 2202d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman Result.subtract(RHS, APFloat::rmNearestTiesToEven); 2203d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman return true; 22042de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Div: 2205d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman Result.divide(RHS, APFloat::rmNearestTiesToEven); 2206d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman return true; 2207d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman } 2208d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman} 2209d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman 2210d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedmanbool FloatExprEvaluator::VisitFloatingLiteral(const FloatingLiteral *E) { 2211d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman Result = E->getValue(); 2212d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman return true; 2213d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman} 2214d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman 22158cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbournebool FloatExprEvaluator::VisitCastExpr(const CastExpr *E) { 22168cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne const Expr* SubExpr = E->getSubExpr(); 22171eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 22182a523eec6a31955be876625819b89e8dc5def707Eli Friedman switch (E->getCastKind()) { 22192a523eec6a31955be876625819b89e8dc5def707Eli Friedman default: 22202a523eec6a31955be876625819b89e8dc5def707Eli Friedman return false; 22212a523eec6a31955be876625819b89e8dc5def707Eli Friedman 22222a523eec6a31955be876625819b89e8dc5def707Eli Friedman case CK_LValueToRValue: 22232a523eec6a31955be876625819b89e8dc5def707Eli Friedman case CK_NoOp: 22242a523eec6a31955be876625819b89e8dc5def707Eli Friedman return Visit(SubExpr); 22252a523eec6a31955be876625819b89e8dc5def707Eli Friedman 22262a523eec6a31955be876625819b89e8dc5def707Eli Friedman case CK_IntegralToFloating: { 22274efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman APSInt IntResult; 22283f7d995390009fede92b333a040da80e1ce90997Daniel Dunbar if (!EvaluateInteger(SubExpr, IntResult, Info)) 22294efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman return false; 22301eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump Result = HandleIntToFloatCast(E->getType(), SubExpr->getType(), 2231a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar IntResult, Info.Ctx); 22324efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman return true; 22334efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman } 22342a523eec6a31955be876625819b89e8dc5def707Eli Friedman 22352a523eec6a31955be876625819b89e8dc5def707Eli Friedman case CK_FloatingCast: { 22364efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman if (!Visit(SubExpr)) 22374efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman return false; 2238a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar Result = HandleFloatToFloatCast(E->getType(), SubExpr->getType(), 2239a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar Result, Info.Ctx); 22404efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman return true; 22414efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman } 2242f3ea8cfe6b1c2ef0702efe130561e9e66708d799John McCall 22432a523eec6a31955be876625819b89e8dc5def707Eli Friedman case CK_FloatingComplexToReal: { 2244f3ea8cfe6b1c2ef0702efe130561e9e66708d799John McCall ComplexValue V; 2245f3ea8cfe6b1c2ef0702efe130561e9e66708d799John McCall if (!EvaluateComplex(SubExpr, V, Info)) 2246f3ea8cfe6b1c2ef0702efe130561e9e66708d799John McCall return false; 2247f3ea8cfe6b1c2ef0702efe130561e9e66708d799John McCall Result = V.getComplexFloatReal(); 2248f3ea8cfe6b1c2ef0702efe130561e9e66708d799John McCall return true; 2249f3ea8cfe6b1c2ef0702efe130561e9e66708d799John McCall } 22502a523eec6a31955be876625819b89e8dc5def707Eli Friedman } 22514efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman 22524efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman return false; 22534efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman} 22544efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman 22558cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbournebool FloatExprEvaluator::VisitCXXScalarValueInitExpr(const CXXScalarValueInitExpr *E) { 22564efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman Result = APFloat::getZero(Info.Ctx.getFloatTypeSemantics(E->getType())); 22574efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman return true; 22584efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman} 22594efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman 2260cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redlbool FloatExprEvaluator::VisitInitListExpr(const InitListExpr *E) { 2261cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl if (!Info.Ctx.getLangOptions().CPlusPlus0x) 2262cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl return Error(E); 2263cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl 2264cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl if (E->getNumInits() == 0) { 2265cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl Result = APFloat::getZero(Info.Ctx.getFloatTypeSemantics(E->getType())); 2266cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl return true; 2267cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl } 2268cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl 2269cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl assert(E->getNumInits() == 1 && "Excess initializers for integer in C++11."); 2270cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl return Visit(E->getInit(0)); 2271cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl} 2272cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl 2273d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman//===----------------------------------------------------------------------===// 2274a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar// Complex Evaluation (for float and integer) 22759ad16aebc0e840a5e7d425da72eb6cbe25e4b58cAnders Carlsson//===----------------------------------------------------------------------===// 22769ad16aebc0e840a5e7d425da72eb6cbe25e4b58cAnders Carlsson 22779ad16aebc0e840a5e7d425da72eb6cbe25e4b58cAnders Carlssonnamespace { 2278770b4a8834670e9427d3ce5a1a8472eb86f45fd2Benjamin Kramerclass ComplexExprEvaluator 22798cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne : public ExprEvaluatorBase<ComplexExprEvaluator, bool> { 2280f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall ComplexValue &Result; 22811eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 22829ad16aebc0e840a5e7d425da72eb6cbe25e4b58cAnders Carlssonpublic: 2283f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall ComplexExprEvaluator(EvalInfo &info, ComplexValue &Result) 22848cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne : ExprEvaluatorBaseTy(info), Result(Result) {} 22851eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 22868cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool Success(const APValue &V, const Expr *e) { 22878cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne Result.setFrom(V); 22888cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne return true; 22898cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne } 22908cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool Error(const Expr *E) { 2291f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall return false; 22929ad16aebc0e840a5e7d425da72eb6cbe25e4b58cAnders Carlsson } 22931eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 22948cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne //===--------------------------------------------------------------------===// 22958cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne // Visitor Methods 22968cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne //===--------------------------------------------------------------------===// 22979ad16aebc0e840a5e7d425da72eb6cbe25e4b58cAnders Carlsson 22988cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitImaginaryLiteral(const ImaginaryLiteral *E); 2299a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar 23008cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne bool VisitCastExpr(const CastExpr *E); 2301b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman 2302b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman bool VisitBinaryOperator(const BinaryOperator *E); 230396fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara bool VisitUnaryOperator(const UnaryOperator *E); 2304cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl // FIXME Missing: ImplicitValueInitExpr, InitListExpr 2305b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman}; 2306b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman} // end anonymous namespace 23071eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 2308b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedmanstatic bool EvaluateComplex(const Expr *E, ComplexValue &Result, 2309b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman EvalInfo &Info) { 2310b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman assert(E->getType()->isAnyComplexType()); 23118cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne return ComplexExprEvaluator(Info, Result).Visit(E); 2312b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman} 2313b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman 23148cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbournebool ComplexExprEvaluator::VisitImaginaryLiteral(const ImaginaryLiteral *E) { 23158cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne const Expr* SubExpr = E->getSubExpr(); 2316b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman 2317b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman if (SubExpr->getType()->isRealFloatingType()) { 2318b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman Result.makeComplexFloat(); 2319b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman APFloat &Imag = Result.FloatImag; 2320b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman if (!EvaluateFloat(SubExpr, Imag, Info)) 2321b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman return false; 2322b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman 2323b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman Result.FloatReal = APFloat(Imag.getSemantics()); 2324b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman return true; 2325b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman } else { 2326b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman assert(SubExpr->getType()->isIntegerType() && 2327b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman "Unexpected imaginary literal."); 2328b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman 2329b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman Result.makeComplexInt(); 2330b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman APSInt &Imag = Result.IntImag; 2331b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman if (!EvaluateInteger(SubExpr, Imag, Info)) 2332b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman return false; 2333b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman 2334b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman Result.IntReal = APSInt(Imag.getBitWidth(), !Imag.isSigned()); 2335b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman return true; 2336b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman } 2337b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman} 2338b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman 23398cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbournebool ComplexExprEvaluator::VisitCastExpr(const CastExpr *E) { 2340b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman 23418786da77984e81d48e0e1b2bd339809b1efc19f3John McCall switch (E->getCastKind()) { 23428786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_BitCast: 23438786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_BaseToDerived: 23448786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_DerivedToBase: 23458786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_UncheckedDerivedToBase: 23468786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_Dynamic: 23478786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_ToUnion: 23488786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_ArrayToPointerDecay: 23498786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_FunctionToPointerDecay: 23508786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_NullToPointer: 23518786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_NullToMemberPointer: 23528786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_BaseToDerivedMemberPointer: 23538786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_DerivedToBaseMemberPointer: 23548786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_MemberPointerToBoolean: 23558786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_ConstructorConversion: 23568786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_IntegralToPointer: 23578786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_PointerToIntegral: 23588786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_PointerToBoolean: 23598786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_ToVoid: 23608786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_VectorSplat: 23618786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_IntegralCast: 23628786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_IntegralToBoolean: 23638786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_IntegralToFloating: 23648786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_FloatingToIntegral: 23658786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_FloatingToBoolean: 23668786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_FloatingCast: 23671d9b3b25f7ac0d0195bba6b507a684fe5e7943eeJohn McCall case CK_CPointerToObjCPointerCast: 23681d9b3b25f7ac0d0195bba6b507a684fe5e7943eeJohn McCall case CK_BlockPointerToObjCPointerCast: 23698786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_AnyPointerToBlockPointerCast: 23708786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_ObjCObjectLValueCast: 23718786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_FloatingComplexToReal: 23728786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_FloatingComplexToBoolean: 23738786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_IntegralComplexToReal: 23748786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_IntegralComplexToBoolean: 237533e56f3273457bfa22c7c50bc46cf5a18216863dJohn McCall case CK_ARCProduceObject: 237633e56f3273457bfa22c7c50bc46cf5a18216863dJohn McCall case CK_ARCConsumeObject: 237733e56f3273457bfa22c7c50bc46cf5a18216863dJohn McCall case CK_ARCReclaimReturnedObject: 237833e56f3273457bfa22c7c50bc46cf5a18216863dJohn McCall case CK_ARCExtendBlockObject: 23798786da77984e81d48e0e1b2bd339809b1efc19f3John McCall llvm_unreachable("invalid cast kind for complex value"); 23808786da77984e81d48e0e1b2bd339809b1efc19f3John McCall 23818786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_LValueToRValue: 23828786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_NoOp: 23838786da77984e81d48e0e1b2bd339809b1efc19f3John McCall return Visit(E->getSubExpr()); 23842bb5d00fcf71a7b4d478d478be778fff0494aff6John McCall 23858786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_Dependent: 23868786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_GetObjCProperty: 238746a523285928aa07bf14803178dc04616ac85994Eli Friedman case CK_LValueBitCast: 23888786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_UserDefinedConversion: 23898786da77984e81d48e0e1b2bd339809b1efc19f3John McCall return false; 23908786da77984e81d48e0e1b2bd339809b1efc19f3John McCall 23918786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_FloatingRealToComplex: { 2392b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman APFloat &Real = Result.FloatReal; 23938786da77984e81d48e0e1b2bd339809b1efc19f3John McCall if (!EvaluateFloat(E->getSubExpr(), Real, Info)) 2394b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman return false; 2395b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman 23968786da77984e81d48e0e1b2bd339809b1efc19f3John McCall Result.makeComplexFloat(); 23978786da77984e81d48e0e1b2bd339809b1efc19f3John McCall Result.FloatImag = APFloat(Real.getSemantics()); 23988786da77984e81d48e0e1b2bd339809b1efc19f3John McCall return true; 23998786da77984e81d48e0e1b2bd339809b1efc19f3John McCall } 24008786da77984e81d48e0e1b2bd339809b1efc19f3John McCall 24018786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_FloatingComplexCast: { 24028786da77984e81d48e0e1b2bd339809b1efc19f3John McCall if (!Visit(E->getSubExpr())) 24038786da77984e81d48e0e1b2bd339809b1efc19f3John McCall return false; 24048786da77984e81d48e0e1b2bd339809b1efc19f3John McCall 24058786da77984e81d48e0e1b2bd339809b1efc19f3John McCall QualType To = E->getType()->getAs<ComplexType>()->getElementType(); 24068786da77984e81d48e0e1b2bd339809b1efc19f3John McCall QualType From 24078786da77984e81d48e0e1b2bd339809b1efc19f3John McCall = E->getSubExpr()->getType()->getAs<ComplexType>()->getElementType(); 24088786da77984e81d48e0e1b2bd339809b1efc19f3John McCall 24098786da77984e81d48e0e1b2bd339809b1efc19f3John McCall Result.FloatReal 24108786da77984e81d48e0e1b2bd339809b1efc19f3John McCall = HandleFloatToFloatCast(To, From, Result.FloatReal, Info.Ctx); 24118786da77984e81d48e0e1b2bd339809b1efc19f3John McCall Result.FloatImag 24128786da77984e81d48e0e1b2bd339809b1efc19f3John McCall = HandleFloatToFloatCast(To, From, Result.FloatImag, Info.Ctx); 24138786da77984e81d48e0e1b2bd339809b1efc19f3John McCall return true; 24148786da77984e81d48e0e1b2bd339809b1efc19f3John McCall } 24158786da77984e81d48e0e1b2bd339809b1efc19f3John McCall 24168786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_FloatingComplexToIntegralComplex: { 24178786da77984e81d48e0e1b2bd339809b1efc19f3John McCall if (!Visit(E->getSubExpr())) 24188786da77984e81d48e0e1b2bd339809b1efc19f3John McCall return false; 24198786da77984e81d48e0e1b2bd339809b1efc19f3John McCall 24208786da77984e81d48e0e1b2bd339809b1efc19f3John McCall QualType To = E->getType()->getAs<ComplexType>()->getElementType(); 24218786da77984e81d48e0e1b2bd339809b1efc19f3John McCall QualType From 24228786da77984e81d48e0e1b2bd339809b1efc19f3John McCall = E->getSubExpr()->getType()->getAs<ComplexType>()->getElementType(); 24238786da77984e81d48e0e1b2bd339809b1efc19f3John McCall Result.makeComplexInt(); 24248786da77984e81d48e0e1b2bd339809b1efc19f3John McCall Result.IntReal = HandleFloatToIntCast(To, From, Result.FloatReal, Info.Ctx); 24258786da77984e81d48e0e1b2bd339809b1efc19f3John McCall Result.IntImag = HandleFloatToIntCast(To, From, Result.FloatImag, Info.Ctx); 24268786da77984e81d48e0e1b2bd339809b1efc19f3John McCall return true; 24278786da77984e81d48e0e1b2bd339809b1efc19f3John McCall } 24288786da77984e81d48e0e1b2bd339809b1efc19f3John McCall 24298786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_IntegralRealToComplex: { 2430b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman APSInt &Real = Result.IntReal; 24318786da77984e81d48e0e1b2bd339809b1efc19f3John McCall if (!EvaluateInteger(E->getSubExpr(), Real, Info)) 2432b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman return false; 24339ad16aebc0e840a5e7d425da72eb6cbe25e4b58cAnders Carlsson 24348786da77984e81d48e0e1b2bd339809b1efc19f3John McCall Result.makeComplexInt(); 24358786da77984e81d48e0e1b2bd339809b1efc19f3John McCall Result.IntImag = APSInt(Real.getBitWidth(), !Real.isSigned()); 24368786da77984e81d48e0e1b2bd339809b1efc19f3John McCall return true; 24378786da77984e81d48e0e1b2bd339809b1efc19f3John McCall } 24388786da77984e81d48e0e1b2bd339809b1efc19f3John McCall 24398786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_IntegralComplexCast: { 24408786da77984e81d48e0e1b2bd339809b1efc19f3John McCall if (!Visit(E->getSubExpr())) 2441b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman return false; 2442ccc3fce5697e33f005990f9795e1c7cb8b4559ecAnders Carlsson 24438786da77984e81d48e0e1b2bd339809b1efc19f3John McCall QualType To = E->getType()->getAs<ComplexType>()->getElementType(); 24448786da77984e81d48e0e1b2bd339809b1efc19f3John McCall QualType From 24458786da77984e81d48e0e1b2bd339809b1efc19f3John McCall = E->getSubExpr()->getType()->getAs<ComplexType>()->getElementType(); 24461725f683432715e5afe34d476024bd6f16eac3fcEli Friedman 24478786da77984e81d48e0e1b2bd339809b1efc19f3John McCall Result.IntReal = HandleIntToIntCast(To, From, Result.IntReal, Info.Ctx); 24488786da77984e81d48e0e1b2bd339809b1efc19f3John McCall Result.IntImag = HandleIntToIntCast(To, From, Result.IntImag, Info.Ctx); 24498786da77984e81d48e0e1b2bd339809b1efc19f3John McCall return true; 24508786da77984e81d48e0e1b2bd339809b1efc19f3John McCall } 24518786da77984e81d48e0e1b2bd339809b1efc19f3John McCall 24528786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_IntegralComplexToFloatingComplex: { 24538786da77984e81d48e0e1b2bd339809b1efc19f3John McCall if (!Visit(E->getSubExpr())) 24548786da77984e81d48e0e1b2bd339809b1efc19f3John McCall return false; 24558786da77984e81d48e0e1b2bd339809b1efc19f3John McCall 24568786da77984e81d48e0e1b2bd339809b1efc19f3John McCall QualType To = E->getType()->getAs<ComplexType>()->getElementType(); 24578786da77984e81d48e0e1b2bd339809b1efc19f3John McCall QualType From 24588786da77984e81d48e0e1b2bd339809b1efc19f3John McCall = E->getSubExpr()->getType()->getAs<ComplexType>()->getElementType(); 24598786da77984e81d48e0e1b2bd339809b1efc19f3John McCall Result.makeComplexFloat(); 24608786da77984e81d48e0e1b2bd339809b1efc19f3John McCall Result.FloatReal = HandleIntToFloatCast(To, From, Result.IntReal, Info.Ctx); 24618786da77984e81d48e0e1b2bd339809b1efc19f3John McCall Result.FloatImag = HandleIntToFloatCast(To, From, Result.IntImag, Info.Ctx); 24628786da77984e81d48e0e1b2bd339809b1efc19f3John McCall return true; 24638786da77984e81d48e0e1b2bd339809b1efc19f3John McCall } 2464ccc3fce5697e33f005990f9795e1c7cb8b4559ecAnders Carlsson } 24651eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 24668786da77984e81d48e0e1b2bd339809b1efc19f3John McCall llvm_unreachable("unknown cast resulting in complex value"); 2467b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman return false; 24689ad16aebc0e840a5e7d425da72eb6cbe25e4b58cAnders Carlsson} 24699ad16aebc0e840a5e7d425da72eb6cbe25e4b58cAnders Carlsson 2470f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCallbool ComplexExprEvaluator::VisitBinaryOperator(const BinaryOperator *E) { 247196fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara if (E->getOpcode() == BO_Comma) { 247296fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara if (!Visit(E->getRHS())) 247396fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara return false; 247496fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara 247596fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara // If we can't evaluate the LHS, it might have side effects; 247696fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara // conservatively mark it. 247796fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara if (!E->getLHS()->isEvaluatable(Info.Ctx)) 247896fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Info.EvalResult.HasSideEffects = true; 247996fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara 248096fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara return true; 248196fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara } 2482f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall if (!Visit(E->getLHS())) 2483f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall return false; 24841eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 2485f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall ComplexValue RHS; 2486a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar if (!EvaluateComplex(E->getRHS(), RHS, Info)) 2487f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall return false; 2488a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar 24893f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar assert(Result.isComplexFloat() == RHS.isComplexFloat() && 24903f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar "Invalid operands to binary operator."); 2491ccc3fce5697e33f005990f9795e1c7cb8b4559ecAnders Carlsson switch (E->getOpcode()) { 2492f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall default: return false; 24932de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Add: 2494a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar if (Result.isComplexFloat()) { 2495a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar Result.getComplexFloatReal().add(RHS.getComplexFloatReal(), 2496a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar APFloat::rmNearestTiesToEven); 2497a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar Result.getComplexFloatImag().add(RHS.getComplexFloatImag(), 2498a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar APFloat::rmNearestTiesToEven); 2499a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar } else { 2500a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar Result.getComplexIntReal() += RHS.getComplexIntReal(); 2501a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar Result.getComplexIntImag() += RHS.getComplexIntImag(); 2502a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar } 25033f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar break; 25042de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Sub: 2505a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar if (Result.isComplexFloat()) { 2506a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar Result.getComplexFloatReal().subtract(RHS.getComplexFloatReal(), 2507a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar APFloat::rmNearestTiesToEven); 2508a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar Result.getComplexFloatImag().subtract(RHS.getComplexFloatImag(), 2509a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar APFloat::rmNearestTiesToEven); 2510a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar } else { 2511a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar Result.getComplexIntReal() -= RHS.getComplexIntReal(); 2512a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar Result.getComplexIntImag() -= RHS.getComplexIntImag(); 2513a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar } 25143f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar break; 25152de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Mul: 25163f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar if (Result.isComplexFloat()) { 2517f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall ComplexValue LHS = Result; 25183f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar APFloat &LHS_r = LHS.getComplexFloatReal(); 25193f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar APFloat &LHS_i = LHS.getComplexFloatImag(); 25203f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar APFloat &RHS_r = RHS.getComplexFloatReal(); 25213f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar APFloat &RHS_i = RHS.getComplexFloatImag(); 25221eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 25233f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar APFloat Tmp = LHS_r; 25243f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar Tmp.multiply(RHS_r, APFloat::rmNearestTiesToEven); 25253f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar Result.getComplexFloatReal() = Tmp; 25263f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar Tmp = LHS_i; 25273f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar Tmp.multiply(RHS_i, APFloat::rmNearestTiesToEven); 25283f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar Result.getComplexFloatReal().subtract(Tmp, APFloat::rmNearestTiesToEven); 25293f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar 25303f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar Tmp = LHS_r; 25313f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar Tmp.multiply(RHS_i, APFloat::rmNearestTiesToEven); 25323f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar Result.getComplexFloatImag() = Tmp; 25333f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar Tmp = LHS_i; 25343f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar Tmp.multiply(RHS_r, APFloat::rmNearestTiesToEven); 25353f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar Result.getComplexFloatImag().add(Tmp, APFloat::rmNearestTiesToEven); 25363f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar } else { 2537f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall ComplexValue LHS = Result; 25381eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump Result.getComplexIntReal() = 25393f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar (LHS.getComplexIntReal() * RHS.getComplexIntReal() - 25403f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar LHS.getComplexIntImag() * RHS.getComplexIntImag()); 25411eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump Result.getComplexIntImag() = 25423f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar (LHS.getComplexIntReal() * RHS.getComplexIntImag() + 25433f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar LHS.getComplexIntImag() * RHS.getComplexIntReal()); 25443f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar } 25453f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar break; 254696fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara case BO_Div: 254796fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara if (Result.isComplexFloat()) { 254896fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara ComplexValue LHS = Result; 254996fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara APFloat &LHS_r = LHS.getComplexFloatReal(); 255096fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara APFloat &LHS_i = LHS.getComplexFloatImag(); 255196fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara APFloat &RHS_r = RHS.getComplexFloatReal(); 255296fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara APFloat &RHS_i = RHS.getComplexFloatImag(); 255396fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara APFloat &Res_r = Result.getComplexFloatReal(); 255496fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara APFloat &Res_i = Result.getComplexFloatImag(); 255596fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara 255696fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara APFloat Den = RHS_r; 255796fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Den.multiply(RHS_r, APFloat::rmNearestTiesToEven); 255896fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara APFloat Tmp = RHS_i; 255996fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Tmp.multiply(RHS_i, APFloat::rmNearestTiesToEven); 256096fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Den.add(Tmp, APFloat::rmNearestTiesToEven); 256196fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara 256296fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Res_r = LHS_r; 256396fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Res_r.multiply(RHS_r, APFloat::rmNearestTiesToEven); 256496fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Tmp = LHS_i; 256596fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Tmp.multiply(RHS_i, APFloat::rmNearestTiesToEven); 256696fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Res_r.add(Tmp, APFloat::rmNearestTiesToEven); 256796fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Res_r.divide(Den, APFloat::rmNearestTiesToEven); 256896fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara 256996fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Res_i = LHS_i; 257096fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Res_i.multiply(RHS_r, APFloat::rmNearestTiesToEven); 257196fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Tmp = LHS_r; 257296fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Tmp.multiply(RHS_i, APFloat::rmNearestTiesToEven); 257396fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Res_i.subtract(Tmp, APFloat::rmNearestTiesToEven); 257496fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Res_i.divide(Den, APFloat::rmNearestTiesToEven); 257596fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara } else { 257696fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara if (RHS.getComplexIntReal() == 0 && RHS.getComplexIntImag() == 0) { 257796fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara // FIXME: what about diagnostics? 257896fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara return false; 257996fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara } 258096fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara ComplexValue LHS = Result; 258196fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara APSInt Den = RHS.getComplexIntReal() * RHS.getComplexIntReal() + 258296fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara RHS.getComplexIntImag() * RHS.getComplexIntImag(); 258396fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Result.getComplexIntReal() = 258496fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara (LHS.getComplexIntReal() * RHS.getComplexIntReal() + 258596fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara LHS.getComplexIntImag() * RHS.getComplexIntImag()) / Den; 258696fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Result.getComplexIntImag() = 258796fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara (LHS.getComplexIntImag() * RHS.getComplexIntReal() - 258896fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara LHS.getComplexIntReal() * RHS.getComplexIntImag()) / Den; 258996fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara } 259096fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara break; 2591ccc3fce5697e33f005990f9795e1c7cb8b4559ecAnders Carlsson } 2592ccc3fce5697e33f005990f9795e1c7cb8b4559ecAnders Carlsson 2593f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall return true; 2594ccc3fce5697e33f005990f9795e1c7cb8b4559ecAnders Carlsson} 2595ccc3fce5697e33f005990f9795e1c7cb8b4559ecAnders Carlsson 259696fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnarabool ComplexExprEvaluator::VisitUnaryOperator(const UnaryOperator *E) { 259796fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara // Get the operand value into 'Result'. 259896fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara if (!Visit(E->getSubExpr())) 259996fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara return false; 260096fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara 260196fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara switch (E->getOpcode()) { 260296fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara default: 260396fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara // FIXME: what about diagnostics? 260496fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara return false; 260596fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara case UO_Extension: 260696fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara return true; 260796fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara case UO_Plus: 260896fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara // The result is always just the subexpr. 260996fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara return true; 261096fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara case UO_Minus: 261196fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara if (Result.isComplexFloat()) { 261296fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Result.getComplexFloatReal().changeSign(); 261396fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Result.getComplexFloatImag().changeSign(); 261496fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara } 261596fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara else { 261696fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Result.getComplexIntReal() = -Result.getComplexIntReal(); 261796fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Result.getComplexIntImag() = -Result.getComplexIntImag(); 261896fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara } 261996fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara return true; 262096fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara case UO_Not: 262196fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara if (Result.isComplexFloat()) 262296fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Result.getComplexFloatImag().changeSign(); 262396fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara else 262496fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Result.getComplexIntImag() = -Result.getComplexIntImag(); 262596fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara return true; 262696fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara } 262796fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara} 262896fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara 26299ad16aebc0e840a5e7d425da72eb6cbe25e4b58cAnders Carlsson//===----------------------------------------------------------------------===// 26306ee7aa154e8bbb21a21254293410b944f78b0bfeChris Lattner// Top level Expr::Evaluate method. 2631f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner//===----------------------------------------------------------------------===// 2632f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner 263356ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCallstatic bool Evaluate(EvalInfo &Info, const Expr *E) { 2634efdb83e26f9a1fd2566afe54461216cd84814d42John McCall if (E->getType()->isVectorType()) { 2635efdb83e26f9a1fd2566afe54461216cd84814d42John McCall if (!EvaluateVector(E, Info.EvalResult.Val, Info)) 263659b5da6d853b4368b984700315adf7b37de05764Nate Begeman return false; 2637575a1c9dc8dc5b4977194993e289f9eda7295c39Douglas Gregor } else if (E->getType()->isIntegralOrEnumerationType()) { 26388cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne if (!IntExprEvaluator(Info, Info.EvalResult.Val).Visit(E)) 26396dde0d5dc09f45f4d9508c964703e36fef1a0198Anders Carlsson return false; 264056ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall if (Info.EvalResult.Val.isLValue() && 264156ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall !IsGlobalLValue(Info.EvalResult.Val.getLValueBase())) 26420f2b692bb10be35fdc60d0a72a847bdd73124670John McCall return false; 2643efdb83e26f9a1fd2566afe54461216cd84814d42John McCall } else if (E->getType()->hasPointerRepresentation()) { 2644efdb83e26f9a1fd2566afe54461216cd84814d42John McCall LValue LV; 2645efdb83e26f9a1fd2566afe54461216cd84814d42John McCall if (!EvaluatePointer(E, LV, Info)) 26466dde0d5dc09f45f4d9508c964703e36fef1a0198Anders Carlsson return false; 2647e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara if (!IsGlobalLValue(LV.Base)) 264842c8f87eb60958170c46767273bf93e6c96125bfJohn McCall return false; 2649efdb83e26f9a1fd2566afe54461216cd84814d42John McCall LV.moveInto(Info.EvalResult.Val); 2650efdb83e26f9a1fd2566afe54461216cd84814d42John McCall } else if (E->getType()->isRealFloatingType()) { 2651efdb83e26f9a1fd2566afe54461216cd84814d42John McCall llvm::APFloat F(0.0); 2652efdb83e26f9a1fd2566afe54461216cd84814d42John McCall if (!EvaluateFloat(E, F, Info)) 26536dde0d5dc09f45f4d9508c964703e36fef1a0198Anders Carlsson return false; 26541eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 2655efdb83e26f9a1fd2566afe54461216cd84814d42John McCall Info.EvalResult.Val = APValue(F); 2656efdb83e26f9a1fd2566afe54461216cd84814d42John McCall } else if (E->getType()->isAnyComplexType()) { 2657efdb83e26f9a1fd2566afe54461216cd84814d42John McCall ComplexValue C; 2658efdb83e26f9a1fd2566afe54461216cd84814d42John McCall if (!EvaluateComplex(E, C, Info)) 2659660e6f79a138a30a437c02142f23e7ef4eb21b2eMike Stump return false; 2660efdb83e26f9a1fd2566afe54461216cd84814d42John McCall C.moveInto(Info.EvalResult.Val); 2661660e6f79a138a30a437c02142f23e7ef4eb21b2eMike Stump } else 2662660e6f79a138a30a437c02142f23e7ef4eb21b2eMike Stump return false; 2663660e6f79a138a30a437c02142f23e7ef4eb21b2eMike Stump 2664660e6f79a138a30a437c02142f23e7ef4eb21b2eMike Stump return true; 2665660e6f79a138a30a437c02142f23e7ef4eb21b2eMike Stump} 2666660e6f79a138a30a437c02142f23e7ef4eb21b2eMike Stump 266756ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall/// Evaluate - Return true if this is a constant which we can fold using 266856ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall/// any crazy technique (that has nothing to do with language standards) that 266956ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall/// we want to. If this function returns true, it returns the folded constant 267056ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall/// in Result. 267156ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCallbool Expr::Evaluate(EvalResult &Result, const ASTContext &Ctx) const { 267256ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall EvalInfo Info(Ctx, Result); 267356ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall return ::Evaluate(Info, this); 267456ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall} 267556ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall 26764ba2a17694148e16eaa8d3917f657ffcd3667be4Jay Foadbool Expr::EvaluateAsBooleanCondition(bool &Result, 26774ba2a17694148e16eaa8d3917f657ffcd3667be4Jay Foad const ASTContext &Ctx) const { 2678cd7a445c6b46c5585580dfb652300c8483c0cb6bJohn McCall EvalResult Scratch; 2679cd7a445c6b46c5585580dfb652300c8483c0cb6bJohn McCall EvalInfo Info(Ctx, Scratch); 2680cd7a445c6b46c5585580dfb652300c8483c0cb6bJohn McCall 2681cd7a445c6b46c5585580dfb652300c8483c0cb6bJohn McCall return HandleConversionToBool(this, Result, Info); 2682cd7a445c6b46c5585580dfb652300c8483c0cb6bJohn McCall} 2683cd7a445c6b46c5585580dfb652300c8483c0cb6bJohn McCall 2684a6b8b2c09610b8bc4330e948ece8b940c2386406Richard Smithbool Expr::EvaluateAsInt(APSInt &Result, const ASTContext &Ctx) const { 2685a6b8b2c09610b8bc4330e948ece8b940c2386406Richard Smith EvalResult Scratch; 2686a6b8b2c09610b8bc4330e948ece8b940c2386406Richard Smith EvalInfo Info(Ctx, Scratch); 2687a6b8b2c09610b8bc4330e948ece8b940c2386406Richard Smith 2688a6b8b2c09610b8bc4330e948ece8b940c2386406Richard Smith return EvaluateInteger(this, Result, Info) && !Scratch.HasSideEffects; 2689a6b8b2c09610b8bc4330e948ece8b940c2386406Richard Smith} 2690a6b8b2c09610b8bc4330e948ece8b940c2386406Richard Smith 26914ba2a17694148e16eaa8d3917f657ffcd3667be4Jay Foadbool Expr::EvaluateAsLValue(EvalResult &Result, const ASTContext &Ctx) const { 26921b78276a75a5a0f496a82429c1ff9604d622a76dAnders Carlsson EvalInfo Info(Ctx, Result); 26931b78276a75a5a0f496a82429c1ff9604d622a76dAnders Carlsson 2694efdb83e26f9a1fd2566afe54461216cd84814d42John McCall LValue LV; 269542c8f87eb60958170c46767273bf93e6c96125bfJohn McCall if (EvaluateLValue(this, LV, Info) && 269642c8f87eb60958170c46767273bf93e6c96125bfJohn McCall !Result.HasSideEffects && 2697e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara IsGlobalLValue(LV.Base)) { 2698e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara LV.moveInto(Result.Val); 2699e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara return true; 2700e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara } 2701e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara return false; 2702e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara} 2703e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara 27044ba2a17694148e16eaa8d3917f657ffcd3667be4Jay Foadbool Expr::EvaluateAsAnyLValue(EvalResult &Result, 27054ba2a17694148e16eaa8d3917f657ffcd3667be4Jay Foad const ASTContext &Ctx) const { 2706e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara EvalInfo Info(Ctx, Result); 2707e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara 2708e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara LValue LV; 2709e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara if (EvaluateLValue(this, LV, Info)) { 2710efdb83e26f9a1fd2566afe54461216cd84814d42John McCall LV.moveInto(Result.Val); 2711efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return true; 2712efdb83e26f9a1fd2566afe54461216cd84814d42John McCall } 2713efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return false; 2714b2f295c8050fb8c141bf2cf38eed0a56e99d0092Eli Friedman} 2715b2f295c8050fb8c141bf2cf38eed0a56e99d0092Eli Friedman 27166ee7aa154e8bbb21a21254293410b944f78b0bfeChris Lattner/// isEvaluatable - Call Evaluate to see if this expression can be constant 271745b6b9d080ac56917337d73d8f1cd6374b27b05dChris Lattner/// folded, but discard the result. 27184ba2a17694148e16eaa8d3917f657ffcd3667be4Jay Foadbool Expr::isEvaluatable(const ASTContext &Ctx) const { 27194fdfb0965b396f2778091f7e6c051d17ff9791baAnders Carlsson EvalResult Result; 27204fdfb0965b396f2778091f7e6c051d17ff9791baAnders Carlsson return Evaluate(Result, Ctx) && !Result.HasSideEffects; 272145b6b9d080ac56917337d73d8f1cd6374b27b05dChris Lattner} 272251fe996231b1d7199f76e4005ff4c943d5deeecdAnders Carlsson 27234ba2a17694148e16eaa8d3917f657ffcd3667be4Jay Foadbool Expr::HasSideEffects(const ASTContext &Ctx) const { 2724393c247fe025ccb5f914e37e948192ea86faef8cFariborz Jahanian Expr::EvalResult Result; 2725393c247fe025ccb5f914e37e948192ea86faef8cFariborz Jahanian EvalInfo Info(Ctx, Result); 27268cad3046be06ea73ff8892d947697a21d7a440d3Peter Collingbourne return HasSideEffect(Info).Visit(this); 2727393c247fe025ccb5f914e37e948192ea86faef8cFariborz Jahanian} 2728393c247fe025ccb5f914e37e948192ea86faef8cFariborz Jahanian 2729a6b8b2c09610b8bc4330e948ece8b940c2386406Richard SmithAPSInt Expr::EvaluateKnownConstInt(const ASTContext &Ctx) const { 27301c0cfd4599e816cfd7a8f348286bf0ad79652ffcAnders Carlsson EvalResult EvalResult; 27311c0cfd4599e816cfd7a8f348286bf0ad79652ffcAnders Carlsson bool Result = Evaluate(EvalResult, Ctx); 2732c6ed729f669044f5072a49d79041f455d971ece3Jeffrey Yasskin (void)Result; 273351fe996231b1d7199f76e4005ff4c943d5deeecdAnders Carlsson assert(Result && "Could not evaluate expression"); 27341c0cfd4599e816cfd7a8f348286bf0ad79652ffcAnders Carlsson assert(EvalResult.Val.isInt() && "Expression did not evaluate to integer"); 273551fe996231b1d7199f76e4005ff4c943d5deeecdAnders Carlsson 27361c0cfd4599e816cfd7a8f348286bf0ad79652ffcAnders Carlsson return EvalResult.Val.getInt(); 273751fe996231b1d7199f76e4005ff4c943d5deeecdAnders Carlsson} 2738d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall 2739e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara bool Expr::EvalResult::isGlobalLValue() const { 2740e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara assert(Val.isLValue()); 2741e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara return IsGlobalLValue(Val.getLValueBase()); 2742e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara } 2743e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara 2744e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara 2745d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall/// isIntegerConstantExpr - this recursive routine will test if an expression is 2746d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall/// an integer constant expression. 2747d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall 2748d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall/// FIXME: Pass up a reason why! Invalid operation in i-c-e, division by zero, 2749d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall/// comma, etc 2750d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall/// 2751d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall/// FIXME: Handle offsetof. Two things to do: Handle GCC's __builtin_offsetof 2752d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall/// to support gcc 4.0+ and handle the idiom GCC recognizes with a null pointer 2753d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall/// cast+dereference. 2754d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall 2755d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall// CheckICE - This function does the fundamental ICE checking: the returned 2756d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall// ICEDiag contains a Val of 0, 1, or 2, and a possibly null SourceLocation. 2757d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall// Note that to reduce code duplication, this helper does no evaluation 2758d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall// itself; the caller checks whether the expression is evaluatable, and 2759d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall// in the rare cases where CheckICE actually cares about the evaluated 2760d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall// value, it calls into Evalute. 2761d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall// 2762d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall// Meanings of Val: 2763d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall// 0: This expression is an ICE if it can be evaluated by Evaluate. 2764d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall// 1: This expression is not an ICE, but if it isn't evaluated, it's 2765d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall// a legal subexpression for an ICE. This return value is used to handle 2766d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall// the comma operator in C99 mode. 2767d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall// 2: This expression is not an ICE, and is not a legal subexpression for one. 2768d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall 27693c46e8db99196179b30e7ac5c20c4efd5f3926d7Dan Gohmannamespace { 27703c46e8db99196179b30e7ac5c20c4efd5f3926d7Dan Gohman 2771d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCallstruct ICEDiag { 2772d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall unsigned Val; 2773d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall SourceLocation Loc; 2774d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall 2775d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall public: 2776d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall ICEDiag(unsigned v, SourceLocation l) : Val(v), Loc(l) {} 2777d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall ICEDiag() : Val(0) {} 2778d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall}; 2779d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall 27803c46e8db99196179b30e7ac5c20c4efd5f3926d7Dan Gohman} 27813c46e8db99196179b30e7ac5c20c4efd5f3926d7Dan Gohman 27823c46e8db99196179b30e7ac5c20c4efd5f3926d7Dan Gohmanstatic ICEDiag NoDiag() { return ICEDiag(); } 2783d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall 2784d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCallstatic ICEDiag CheckEvalInICE(const Expr* E, ASTContext &Ctx) { 2785d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall Expr::EvalResult EVResult; 2786d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (!E->Evaluate(EVResult, Ctx) || EVResult.HasSideEffects || 2787d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall !EVResult.Val.isInt()) { 2788d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return ICEDiag(2, E->getLocStart()); 2789d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 2790d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return NoDiag(); 2791d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall} 2792d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall 2793d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCallstatic ICEDiag CheckICE(const Expr* E, ASTContext &Ctx) { 2794d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall assert(!E->isValueDependent() && "Should not see value dependent exprs!"); 27952ade35e2cfd554e49d35a52047cea98a82787af9Douglas Gregor if (!E->getType()->isIntegralOrEnumerationType()) { 2796d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return ICEDiag(2, E->getLocStart()); 2797d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 2798d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall 2799d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall switch (E->getStmtClass()) { 280063c00d7f35fa060c0a446c9df3a4402d9c7757feJohn McCall#define ABSTRACT_STMT(Node) 2801d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall#define STMT(Node, Base) case Expr::Node##Class: 2802d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall#define EXPR(Node, Base) 2803d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall#include "clang/AST/StmtNodes.inc" 2804d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::PredefinedExprClass: 2805d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::FloatingLiteralClass: 2806d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::ImaginaryLiteralClass: 2807d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::StringLiteralClass: 2808d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::ArraySubscriptExprClass: 2809d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::MemberExprClass: 2810d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CompoundAssignOperatorClass: 2811d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CompoundLiteralExprClass: 2812d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::ExtVectorElementExprClass: 2813d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::DesignatedInitExprClass: 2814d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::ImplicitValueInitExprClass: 2815d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::ParenListExprClass: 2816d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::VAArgExprClass: 2817d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::AddrLabelExprClass: 2818d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::StmtExprClass: 2819d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CXXMemberCallExprClass: 2820e08ce650a2b02410eddd1f60a4aa6b3d4be71e73Peter Collingbourne case Expr::CUDAKernelCallExprClass: 2821d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CXXDynamicCastExprClass: 2822d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CXXTypeidExprClass: 28239be88403e965cc49af76c9d33d818781d44b333eFrancois Pichet case Expr::CXXUuidofExprClass: 2824d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CXXNullPtrLiteralExprClass: 2825d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CXXThisExprClass: 2826d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CXXThrowExprClass: 2827d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CXXNewExprClass: 2828d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CXXDeleteExprClass: 2829d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CXXPseudoDestructorExprClass: 2830d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::UnresolvedLookupExprClass: 2831d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::DependentScopeDeclRefExprClass: 2832d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CXXConstructExprClass: 2833d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CXXBindTemporaryExprClass: 28344765fa05b5652fcc4356371c2f481d0ea9a1b007John McCall case Expr::ExprWithCleanupsClass: 2835d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CXXTemporaryObjectExprClass: 2836d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CXXUnresolvedConstructExprClass: 2837d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CXXDependentScopeMemberExprClass: 2838d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::UnresolvedMemberExprClass: 2839d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::ObjCStringLiteralClass: 2840d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::ObjCEncodeExprClass: 2841d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::ObjCMessageExprClass: 2842d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::ObjCSelectorExprClass: 2843d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::ObjCProtocolExprClass: 2844d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::ObjCIvarRefExprClass: 2845d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::ObjCPropertyRefExprClass: 2846d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::ObjCIsaExprClass: 2847d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::ShuffleVectorExprClass: 2848d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::BlockExprClass: 2849d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::BlockDeclRefExprClass: 2850d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::NoStmtClass: 28517cd7d1ad33fdf49eef83942e8855fe20d95aa1b9John McCall case Expr::OpaqueValueExprClass: 2852be230c36e32142cbdcdbe9c97511d097beeecbabDouglas Gregor case Expr::PackExpansionExprClass: 2853c7793c73ba8a343de3f2552d984851985a46f159Douglas Gregor case Expr::SubstNonTypeTemplateParmPackExprClass: 285461eee0ca33b29e102f11bab77c8b74cc00e2392bTanya Lattner case Expr::AsTypeExprClass: 2855f85e193739c953358c865005855253af4f68a497John McCall case Expr::ObjCIndirectCopyRestoreExprClass: 285603e80030515c800d1ab44125b9052dfffd1bd04cDouglas Gregor case Expr::MaterializeTemporaryExprClass: 2857d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return ICEDiag(2, E->getLocStart()); 2858d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall 2859cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl case Expr::InitListExprClass: 2860cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl if (Ctx.getLangOptions().CPlusPlus0x) { 2861cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl const InitListExpr *ILE = cast<InitListExpr>(E); 2862cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl if (ILE->getNumInits() == 0) 2863cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl return NoDiag(); 2864cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl if (ILE->getNumInits() == 1) 2865cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl return CheckICE(ILE->getInit(0), Ctx); 2866cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl // Fall through for more than 1 expression. 2867cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl } 2868cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl return ICEDiag(2, E->getLocStart()); 2869cea8d966f826554f0679595e9371e314e8dbc1cfSebastian Redl 2870ee8aff06f6a96214731de17b2cb6df407c6c1820Douglas Gregor case Expr::SizeOfPackExprClass: 2871d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::GNUNullExprClass: 2872d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // GCC considers the GNU __null value to be an integral constant expression. 2873d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return NoDiag(); 2874d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall 287591a5755ad73c5dc1dfb167e448fdd74e75a6df56John McCall case Expr::SubstNonTypeTemplateParmExprClass: 287691a5755ad73c5dc1dfb167e448fdd74e75a6df56John McCall return 287791a5755ad73c5dc1dfb167e448fdd74e75a6df56John McCall CheckICE(cast<SubstNonTypeTemplateParmExpr>(E)->getReplacement(), Ctx); 287891a5755ad73c5dc1dfb167e448fdd74e75a6df56John McCall 2879d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::ParenExprClass: 2880d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return CheckICE(cast<ParenExpr>(E)->getSubExpr(), Ctx); 2881f111d935722ed488144600cea5ed03a6b5069e8fPeter Collingbourne case Expr::GenericSelectionExprClass: 2882f111d935722ed488144600cea5ed03a6b5069e8fPeter Collingbourne return CheckICE(cast<GenericSelectionExpr>(E)->getResultExpr(), Ctx); 2883d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::IntegerLiteralClass: 2884d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CharacterLiteralClass: 2885d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CXXBoolLiteralExprClass: 2886ed8abf18329df67b0abcbb3a10458bd8c1d2a595Douglas Gregor case Expr::CXXScalarValueInitExprClass: 2887d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::UnaryTypeTraitExprClass: 28886ad6f2848d7652ab2991286eb48be440d3493b28Francois Pichet case Expr::BinaryTypeTraitExprClass: 288921ff2e516b0e0bc8c1dbf965cb3d44bac3c64330John Wiegley case Expr::ArrayTypeTraitExprClass: 2890552622067dc45013d240f73952fece703f5e63bdJohn Wiegley case Expr::ExpressionTraitExprClass: 28912e156225a29407a50dd19041aa5750171ad44ea3Sebastian Redl case Expr::CXXNoexceptExprClass: 2892d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return NoDiag(); 2893d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CallExprClass: 28946cf750298d3621d8a10a6dd07fcee8e274b9d94dSean Hunt case Expr::CXXOperatorCallExprClass: { 2895d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall const CallExpr *CE = cast<CallExpr>(E); 2896d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (CE->isBuiltinCall(Ctx)) 2897d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return CheckEvalInICE(E, Ctx); 2898d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return ICEDiag(2, E->getLocStart()); 2899d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 2900d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::DeclRefExprClass: 2901d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (isa<EnumConstantDecl>(cast<DeclRefExpr>(E)->getDecl())) 2902d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return NoDiag(); 2903d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (Ctx.getLangOptions().CPlusPlus && 2904d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall E->getType().getCVRQualifiers() == Qualifiers::Const) { 2905d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall const NamedDecl *D = cast<DeclRefExpr>(E)->getDecl(); 2906d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall 2907d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // Parameter variables are never constants. Without this check, 2908d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // getAnyInitializer() can find a default argument, which leads 2909d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // to chaos. 2910d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (isa<ParmVarDecl>(D)) 2911d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return ICEDiag(2, cast<DeclRefExpr>(E)->getLocation()); 2912d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall 2913d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // C++ 7.1.5.1p2 2914d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // A variable of non-volatile const-qualified integral or enumeration 2915d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // type initialized by an ICE can be used in ICEs. 2916d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (const VarDecl *Dcl = dyn_cast<VarDecl>(D)) { 2917d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall Qualifiers Quals = Ctx.getCanonicalType(Dcl->getType()).getQualifiers(); 2918d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (Quals.hasVolatile() || !Quals.hasConst()) 2919d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return ICEDiag(2, cast<DeclRefExpr>(E)->getLocation()); 2920d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall 2921d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // Look for a declaration of this variable that has an initializer. 2922d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall const VarDecl *ID = 0; 2923d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall const Expr *Init = Dcl->getAnyInitializer(ID); 2924d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (Init) { 2925d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (ID->isInitKnownICE()) { 2926d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // We have already checked whether this subexpression is an 2927d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // integral constant expression. 2928d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (ID->isInitICE()) 2929d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return NoDiag(); 2930d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall else 2931d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return ICEDiag(2, cast<DeclRefExpr>(E)->getLocation()); 2932d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 2933d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall 2934d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // It's an ICE whether or not the definition we found is 2935d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // out-of-line. See DR 721 and the discussion in Clang PR 2936d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // 6206 for details. 2937d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall 2938d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (Dcl->isCheckingICE()) { 2939d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return ICEDiag(2, cast<DeclRefExpr>(E)->getLocation()); 2940d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 2941d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall 2942d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall Dcl->setCheckingICE(); 2943d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall ICEDiag Result = CheckICE(Init, Ctx); 2944d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // Cache the result of the ICE test. 2945d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall Dcl->setInitKnownICE(Result.Val == 0); 2946d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return Result; 2947d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 2948d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 2949d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 2950d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return ICEDiag(2, E->getLocStart()); 2951d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::UnaryOperatorClass: { 2952d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall const UnaryOperator *Exp = cast<UnaryOperator>(E); 2953d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall switch (Exp->getOpcode()) { 29542de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case UO_PostInc: 29552de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case UO_PostDec: 29562de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case UO_PreInc: 29572de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case UO_PreDec: 29582de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case UO_AddrOf: 29592de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case UO_Deref: 2960d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return ICEDiag(2, E->getLocStart()); 29612de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case UO_Extension: 29622de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case UO_LNot: 29632de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case UO_Plus: 29642de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case UO_Minus: 29652de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case UO_Not: 29662de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case UO_Real: 29672de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case UO_Imag: 2968d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return CheckICE(Exp->getSubExpr(), Ctx); 2969d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 2970d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall 2971d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // OffsetOf falls through here. 2972d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 2973d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::OffsetOfExprClass: { 2974d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // Note that per C99, offsetof must be an ICE. And AFAIK, using 2975d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // Evaluate matches the proposed gcc behavior for cases like 2976d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // "offsetof(struct s{int x[4];}, x[!.0])". This doesn't affect 2977d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // compliance: we should warn earlier for offsetof expressions with 2978d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // array subscripts that aren't ICEs, and if the array subscripts 2979d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // are ICEs, the value of the offsetof must be an integer constant. 2980d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return CheckEvalInICE(E, Ctx); 2981d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 2982f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne case Expr::UnaryExprOrTypeTraitExprClass: { 2983f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne const UnaryExprOrTypeTraitExpr *Exp = cast<UnaryExprOrTypeTraitExpr>(E); 2984f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne if ((Exp->getKind() == UETT_SizeOf) && 2985f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne Exp->getTypeOfArgument()->isVariableArrayType()) 2986d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return ICEDiag(2, E->getLocStart()); 2987d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return NoDiag(); 2988d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 2989d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::BinaryOperatorClass: { 2990d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall const BinaryOperator *Exp = cast<BinaryOperator>(E); 2991d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall switch (Exp->getOpcode()) { 29922de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_PtrMemD: 29932de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_PtrMemI: 29942de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Assign: 29952de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_MulAssign: 29962de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_DivAssign: 29972de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_RemAssign: 29982de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_AddAssign: 29992de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_SubAssign: 30002de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_ShlAssign: 30012de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_ShrAssign: 30022de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_AndAssign: 30032de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_XorAssign: 30042de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_OrAssign: 3005d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return ICEDiag(2, E->getLocStart()); 3006d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall 30072de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Mul: 30082de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Div: 30092de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Rem: 30102de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Add: 30112de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Sub: 30122de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Shl: 30132de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Shr: 30142de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_LT: 30152de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_GT: 30162de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_LE: 30172de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_GE: 30182de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_EQ: 30192de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_NE: 30202de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_And: 30212de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Xor: 30222de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Or: 30232de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Comma: { 3024d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall ICEDiag LHSResult = CheckICE(Exp->getLHS(), Ctx); 3025d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall ICEDiag RHSResult = CheckICE(Exp->getRHS(), Ctx); 30262de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall if (Exp->getOpcode() == BO_Div || 30272de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall Exp->getOpcode() == BO_Rem) { 3028d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // Evaluate gives an error for undefined Div/Rem, so make sure 3029d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // we don't evaluate one. 30303b332ab132fa85c83833d74d400f6e126f52fbd2John McCall if (LHSResult.Val == 0 && RHSResult.Val == 0) { 3031a6b8b2c09610b8bc4330e948ece8b940c2386406Richard Smith llvm::APSInt REval = Exp->getRHS()->EvaluateKnownConstInt(Ctx); 3032d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (REval == 0) 3033d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return ICEDiag(1, E->getLocStart()); 3034d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (REval.isSigned() && REval.isAllOnesValue()) { 3035a6b8b2c09610b8bc4330e948ece8b940c2386406Richard Smith llvm::APSInt LEval = Exp->getLHS()->EvaluateKnownConstInt(Ctx); 3036d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (LEval.isMinSignedValue()) 3037d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return ICEDiag(1, E->getLocStart()); 3038d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 3039d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 3040d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 30412de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall if (Exp->getOpcode() == BO_Comma) { 3042d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (Ctx.getLangOptions().C99) { 3043d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // C99 6.6p3 introduces a strange edge case: comma can be in an ICE 3044d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // if it isn't evaluated. 3045d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (LHSResult.Val == 0 && RHSResult.Val == 0) 3046d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return ICEDiag(1, E->getLocStart()); 3047d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } else { 3048d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // In both C89 and C++, commas in ICEs are illegal. 3049d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return ICEDiag(2, E->getLocStart()); 3050d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 3051d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 3052d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (LHSResult.Val >= RHSResult.Val) 3053d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return LHSResult; 3054d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return RHSResult; 3055d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 30562de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_LAnd: 30572de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_LOr: { 3058d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall ICEDiag LHSResult = CheckICE(Exp->getLHS(), Ctx); 305963fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor 306063fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor // C++0x [expr.const]p2: 306163fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor // [...] subexpressions of logical AND (5.14), logical OR 306263fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor // (5.15), and condi- tional (5.16) operations that are not 306363fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor // evaluated are not considered. 306463fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor if (Ctx.getLangOptions().CPlusPlus0x && LHSResult.Val == 0) { 306563fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor if (Exp->getOpcode() == BO_LAnd && 3066a6b8b2c09610b8bc4330e948ece8b940c2386406Richard Smith Exp->getLHS()->EvaluateKnownConstInt(Ctx) == 0) 306763fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor return LHSResult; 306863fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor 306963fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor if (Exp->getOpcode() == BO_LOr && 3070a6b8b2c09610b8bc4330e948ece8b940c2386406Richard Smith Exp->getLHS()->EvaluateKnownConstInt(Ctx) != 0) 307163fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor return LHSResult; 307263fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor } 307363fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor 3074d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall ICEDiag RHSResult = CheckICE(Exp->getRHS(), Ctx); 3075d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (LHSResult.Val == 0 && RHSResult.Val == 1) { 3076d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // Rare case where the RHS has a comma "side-effect"; we need 3077d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // to actually check the condition to see whether the side 3078d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // with the comma is evaluated. 30792de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall if ((Exp->getOpcode() == BO_LAnd) != 3080a6b8b2c09610b8bc4330e948ece8b940c2386406Richard Smith (Exp->getLHS()->EvaluateKnownConstInt(Ctx) == 0)) 3081d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return RHSResult; 3082d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return NoDiag(); 3083d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 3084d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall 3085d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (LHSResult.Val >= RHSResult.Val) 3086d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return LHSResult; 3087d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return RHSResult; 3088d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 3089d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 3090d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 3091d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::ImplicitCastExprClass: 3092d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CStyleCastExprClass: 3093d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CXXFunctionalCastExprClass: 3094d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CXXStaticCastExprClass: 3095d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CXXReinterpretCastExprClass: 3096f85e193739c953358c865005855253af4f68a497John McCall case Expr::CXXConstCastExprClass: 3097f85e193739c953358c865005855253af4f68a497John McCall case Expr::ObjCBridgedCastExprClass: { 3098d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall const Expr *SubExpr = cast<CastExpr>(E)->getSubExpr(); 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 if (isa<FloatingLiteral>(SubExpr->IgnoreParens())) 3107eea0e817c609c662f3fef61bb257fddf1ae8f7b7Eli Friedman return NoDiag(); 3108eea0e817c609c662f3fef61bb257fddf1ae8f7b7Eli Friedman return ICEDiag(2, E->getLocStart()); 3109eea0e817c609c662f3fef61bb257fddf1ae8f7b7Eli Friedman } 3110d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 311156ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall case Expr::BinaryConditionalOperatorClass: { 311256ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall const BinaryConditionalOperator *Exp = cast<BinaryConditionalOperator>(E); 311356ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall ICEDiag CommonResult = CheckICE(Exp->getCommon(), Ctx); 311456ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall if (CommonResult.Val == 2) return CommonResult; 311556ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall ICEDiag FalseResult = CheckICE(Exp->getFalseExpr(), Ctx); 311656ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall if (FalseResult.Val == 2) return FalseResult; 311756ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall if (CommonResult.Val == 1) return CommonResult; 311856ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall if (FalseResult.Val == 1 && 3119a6b8b2c09610b8bc4330e948ece8b940c2386406Richard Smith Exp->getCommon()->EvaluateKnownConstInt(Ctx) == 0) return NoDiag(); 312056ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall return FalseResult; 312156ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall } 3122d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::ConditionalOperatorClass: { 3123d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall const ConditionalOperator *Exp = cast<ConditionalOperator>(E); 3124d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // If the condition (ignoring parens) is a __builtin_constant_p call, 3125d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // then only the true side is actually considered in an integer constant 3126d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // expression, and it is fully evaluated. This is an important GNU 3127d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // extension. See GCC PR38377 for discussion. 3128d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (const CallExpr *CallCE 3129d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall = dyn_cast<CallExpr>(Exp->getCond()->IgnoreParenCasts())) 3130d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (CallCE->isBuiltinCall(Ctx) == Builtin::BI__builtin_constant_p) { 3131d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall Expr::EvalResult EVResult; 3132d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (!E->Evaluate(EVResult, Ctx) || EVResult.HasSideEffects || 3133d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall !EVResult.Val.isInt()) { 3134d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return ICEDiag(2, E->getLocStart()); 3135d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 3136d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return NoDiag(); 3137d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 3138d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall ICEDiag CondResult = CheckICE(Exp->getCond(), Ctx); 3139d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (CondResult.Val == 2) 3140d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return CondResult; 314163fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor 314263fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor // C++0x [expr.const]p2: 314363fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor // subexpressions of [...] conditional (5.16) operations that 314463fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor // are not evaluated are not considered 314563fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor bool TrueBranch = Ctx.getLangOptions().CPlusPlus0x 3146a6b8b2c09610b8bc4330e948ece8b940c2386406Richard Smith ? Exp->getCond()->EvaluateKnownConstInt(Ctx) != 0 314763fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor : false; 314863fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor ICEDiag TrueResult = NoDiag(); 314963fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor if (!Ctx.getLangOptions().CPlusPlus0x || TrueBranch) 315063fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor TrueResult = CheckICE(Exp->getTrueExpr(), Ctx); 315163fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor ICEDiag FalseResult = NoDiag(); 315263fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor if (!Ctx.getLangOptions().CPlusPlus0x || !TrueBranch) 315363fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor FalseResult = CheckICE(Exp->getFalseExpr(), Ctx); 315463fe6814f339df30b8463b39995947cbdf920e48Douglas Gregor 3155d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (TrueResult.Val == 2) 3156d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return TrueResult; 3157d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (FalseResult.Val == 2) 3158d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return FalseResult; 3159d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (CondResult.Val == 1) 3160d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return CondResult; 3161d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (TrueResult.Val == 0 && FalseResult.Val == 0) 3162d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return NoDiag(); 3163d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // Rare case where the diagnostics depend on which side is evaluated 3164d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // Note that if we get here, CondResult is 0, and at least one of 3165d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // TrueResult and FalseResult is non-zero. 3166a6b8b2c09610b8bc4330e948ece8b940c2386406Richard Smith if (Exp->getCond()->EvaluateKnownConstInt(Ctx) == 0) { 3167d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return FalseResult; 3168d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 3169d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return TrueResult; 3170d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 3171d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CXXDefaultArgExprClass: 3172d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return CheckICE(cast<CXXDefaultArgExpr>(E)->getExpr(), Ctx); 3173d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::ChooseExprClass: { 3174d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return CheckICE(cast<ChooseExpr>(E)->getChosenSubExpr(Ctx), Ctx); 3175d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 3176d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 3177d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall 3178d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // Silence a GCC warning 3179d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return ICEDiag(2, E->getLocStart()); 3180d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall} 3181d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall 3182d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCallbool Expr::isIntegerConstantExpr(llvm::APSInt &Result, ASTContext &Ctx, 3183d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall SourceLocation *Loc, bool isEvaluated) const { 3184d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall ICEDiag d = CheckICE(this, Ctx); 3185d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (d.Val != 0) { 3186d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (Loc) *Loc = d.Loc; 3187d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return false; 3188d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 3189d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall EvalResult EvalResult; 3190d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (!Evaluate(EvalResult, Ctx)) 3191d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall llvm_unreachable("ICE cannot be evaluated!"); 3192d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall assert(!EvalResult.HasSideEffects && "ICE with side effects!"); 3193d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall assert(EvalResult.Val.isInt() && "ICE that isn't integer!"); 3194d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall Result = EvalResult.Val.getInt(); 3195d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return true; 3196d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall} 3197