ExprConstant.cpp revision 0a0d2b179085a52c10402feebeb6db8b4d96a140
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 { 105efdb83e26f9a1fd2566afe54461216cd84814d42John McCall Expr *Base; 106efdb83e26f9a1fd2566afe54461216cd84814d42John McCall CharUnits Offset; 107efdb83e26f9a1fd2566afe54461216cd84814d42John McCall 108efdb83e26f9a1fd2566afe54461216cd84814d42John McCall 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. 224a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar bool DestSigned = DestType->isSignedIntegerType(); 2251eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 226a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar // FIXME: Warning for overflow. 227a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar uint64_t Space[4]; 228a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar bool ignored; 229a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar (void)Value.convertToInteger(Space, DestWidth, DestSigned, 230a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar llvm::APFloat::rmTowardZero, &ignored); 231a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar return APSInt(llvm::APInt(DestWidth, 4, Space), !DestSigned); 232a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar} 233a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar 2341eb4433ac451dc16f4133a88af2d002ac26c58efMike Stumpstatic APFloat HandleFloatToFloatCast(QualType DestType, QualType SrcType, 2354ba2a17694148e16eaa8d3917f657ffcd3667be4Jay Foad APFloat &Value, const ASTContext &Ctx) { 236a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar bool ignored; 237a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar APFloat Result = Value; 2381eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump Result.convert(Ctx.getFloatTypeSemantics(DestType), 239a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar APFloat::rmNearestTiesToEven, &ignored); 240a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar return Result; 241a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar} 242a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar 2431eb4433ac451dc16f4133a88af2d002ac26c58efMike Stumpstatic APSInt HandleIntToIntCast(QualType DestType, QualType SrcType, 2444ba2a17694148e16eaa8d3917f657ffcd3667be4Jay Foad APSInt &Value, const ASTContext &Ctx) { 245a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar unsigned DestWidth = Ctx.getIntWidth(DestType); 246a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar APSInt Result = Value; 247a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar // Figure out if this is a truncate, extend or noop cast. 248a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar // If the input is signed, do a sign extend, noop, or truncate. 2499f71a8f4c7a182a5236da9e747d57cc1d1bd24c2Jay Foad Result = Result.extOrTrunc(DestWidth); 250a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar Result.setIsUnsigned(DestType->isUnsignedIntegerType()); 251a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar return Result; 252a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar} 253a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar 2541eb4433ac451dc16f4133a88af2d002ac26c58efMike Stumpstatic APFloat HandleIntToFloatCast(QualType DestType, QualType SrcType, 2554ba2a17694148e16eaa8d3917f657ffcd3667be4Jay Foad APSInt &Value, const ASTContext &Ctx) { 256a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar 257a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar APFloat Result(Ctx.getFloatTypeSemantics(DestType), 1); 258a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar Result.convertFromAPInt(Value, Value.isSigned(), 259a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar APFloat::rmNearestTiesToEven); 260a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar return Result; 261a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar} 262a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar 263c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stumpnamespace { 264770b4a8834670e9427d3ce5a1a8472eb86f45fd2Benjamin Kramerclass HasSideEffect 265c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump : public StmtVisitor<HasSideEffect, bool> { 266c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump EvalInfo &Info; 267c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stumppublic: 268c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump 269c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump HasSideEffect(EvalInfo &info) : Info(info) {} 270c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump 271c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump // Unhandled nodes conservatively default to having side effects. 272c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump bool VisitStmt(Stmt *S) { 273c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump return true; 274c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump } 275c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump 276c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump bool VisitParenExpr(ParenExpr *E) { return Visit(E->getSubExpr()); } 277c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump bool VisitDeclRefExpr(DeclRefExpr *E) { 278df317bf71653eeb235da8337b1e8e790f9653aa4Mike Stump if (Info.Ctx.getCanonicalType(E->getType()).isVolatileQualified()) 279c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump return true; 280c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump return false; 281c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump } 282c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump // We don't want to evaluate BlockExprs multiple times, as they generate 283c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump // a ton of code. 284c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump bool VisitBlockExpr(BlockExpr *E) { return true; } 285c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump bool VisitPredefinedExpr(PredefinedExpr *E) { return false; } 286c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump bool VisitCompoundLiteralExpr(CompoundLiteralExpr *E) 287c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump { return Visit(E->getInitializer()); } 288c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump bool VisitMemberExpr(MemberExpr *E) { return Visit(E->getBase()); } 289c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump bool VisitIntegerLiteral(IntegerLiteral *E) { return false; } 290c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump bool VisitFloatingLiteral(FloatingLiteral *E) { return false; } 291c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump bool VisitStringLiteral(StringLiteral *E) { return false; } 292c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump bool VisitCharacterLiteral(CharacterLiteral *E) { return false; } 293f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne bool VisitUnaryExprOrTypeTraitExpr(UnaryExprOrTypeTraitExpr *E) 294f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne { return false; } 295c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump bool VisitArraySubscriptExpr(ArraySubscriptExpr *E) 296980ca220848d27ef55ef4c2d37423461a8ed0da3Mike Stump { return Visit(E->getLHS()) || Visit(E->getRHS()); } 297c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump bool VisitChooseExpr(ChooseExpr *E) 298c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump { return Visit(E->getChosenSubExpr(Info.Ctx)); } 299c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump bool VisitCastExpr(CastExpr *E) { return Visit(E->getSubExpr()); } 300c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump bool VisitBinAssign(BinaryOperator *E) { return true; } 3013f0147e161df4725ff15fbb731f4f727afcc229fMike Stump bool VisitCompoundAssignOperator(BinaryOperator *E) { return true; } 302980ca220848d27ef55ef4c2d37423461a8ed0da3Mike Stump bool VisitBinaryOperator(BinaryOperator *E) 303980ca220848d27ef55ef4c2d37423461a8ed0da3Mike Stump { return Visit(E->getLHS()) || Visit(E->getRHS()); } 304c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump bool VisitUnaryPreInc(UnaryOperator *E) { return true; } 305c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump bool VisitUnaryPostInc(UnaryOperator *E) { return true; } 306c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump bool VisitUnaryPreDec(UnaryOperator *E) { return true; } 307c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump bool VisitUnaryPostDec(UnaryOperator *E) { return true; } 308c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump bool VisitUnaryDeref(UnaryOperator *E) { 309df317bf71653eeb235da8337b1e8e790f9653aa4Mike Stump if (Info.Ctx.getCanonicalType(E->getType()).isVolatileQualified()) 310c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump return true; 311980ca220848d27ef55ef4c2d37423461a8ed0da3Mike Stump return Visit(E->getSubExpr()); 312c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump } 313c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump bool VisitUnaryOperator(UnaryOperator *E) { return Visit(E->getSubExpr()); } 314363ff23cfddb51abe4ee4212a6dd3c9b534fcc8bChris Lattner 315363ff23cfddb51abe4ee4212a6dd3c9b534fcc8bChris Lattner // Has side effects if any element does. 316363ff23cfddb51abe4ee4212a6dd3c9b534fcc8bChris Lattner bool VisitInitListExpr(InitListExpr *E) { 317363ff23cfddb51abe4ee4212a6dd3c9b534fcc8bChris Lattner for (unsigned i = 0, e = E->getNumInits(); i != e; ++i) 318363ff23cfddb51abe4ee4212a6dd3c9b534fcc8bChris Lattner if (Visit(E->getInit(i))) return true; 319363ff23cfddb51abe4ee4212a6dd3c9b534fcc8bChris Lattner return false; 320363ff23cfddb51abe4ee4212a6dd3c9b534fcc8bChris Lattner } 321ee8aff06f6a96214731de17b2cb6df407c6c1820Douglas Gregor 322ee8aff06f6a96214731de17b2cb6df407c6c1820Douglas Gregor bool VisitSizeOfPackExpr(SizeOfPackExpr *) { return false; } 323c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump}; 324c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump 32556ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCallclass OpaqueValueEvaluation { 32656ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall EvalInfo &info; 32756ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall OpaqueValueExpr *opaqueValue; 32856ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall 32956ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCallpublic: 33056ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall OpaqueValueEvaluation(EvalInfo &info, OpaqueValueExpr *opaqueValue, 33156ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall Expr *value) 33256ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall : info(info), opaqueValue(opaqueValue) { 33356ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall 33456ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall // If evaluation fails, fail immediately. 33556ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall if (!Evaluate(info, value)) { 33656ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall this->opaqueValue = 0; 33756ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall return; 33856ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall } 33956ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall info.OpaqueValues[opaqueValue] = info.EvalResult.Val; 34056ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall } 34156ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall 34256ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall bool hasError() const { return opaqueValue == 0; } 34356ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall 34456ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall ~OpaqueValueEvaluation() { 34556ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall if (opaqueValue) info.OpaqueValues.erase(opaqueValue); 34656ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall } 34756ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall}; 34856ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall 349c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump} // end anonymous namespace 350c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump 3514efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman//===----------------------------------------------------------------------===// 3524efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman// LValue Evaluation 3534efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman//===----------------------------------------------------------------------===// 3544efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedmannamespace { 355770b4a8834670e9427d3ce5a1a8472eb86f45fd2Benjamin Kramerclass LValueExprEvaluator 356efdb83e26f9a1fd2566afe54461216cd84814d42John McCall : public StmtVisitor<LValueExprEvaluator, bool> { 3574efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman EvalInfo &Info; 358efdb83e26f9a1fd2566afe54461216cd84814d42John McCall LValue &Result; 359efdb83e26f9a1fd2566afe54461216cd84814d42John McCall 360efdb83e26f9a1fd2566afe54461216cd84814d42John McCall bool Success(Expr *E) { 361efdb83e26f9a1fd2566afe54461216cd84814d42John McCall Result.Base = E; 362efdb83e26f9a1fd2566afe54461216cd84814d42John McCall Result.Offset = CharUnits::Zero(); 363efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return true; 364efdb83e26f9a1fd2566afe54461216cd84814d42John McCall } 3654efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedmanpublic: 3661eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 367efdb83e26f9a1fd2566afe54461216cd84814d42John McCall LValueExprEvaluator(EvalInfo &info, LValue &Result) : 368efdb83e26f9a1fd2566afe54461216cd84814d42John McCall Info(info), Result(Result) {} 3694efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman 370efdb83e26f9a1fd2566afe54461216cd84814d42John McCall bool VisitStmt(Stmt *S) { 371efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return false; 3724efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman } 3738ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor 374efdb83e26f9a1fd2566afe54461216cd84814d42John McCall bool VisitParenExpr(ParenExpr *E) { return Visit(E->getSubExpr()); } 375efdb83e26f9a1fd2566afe54461216cd84814d42John McCall bool VisitDeclRefExpr(DeclRefExpr *E); 376efdb83e26f9a1fd2566afe54461216cd84814d42John McCall bool VisitPredefinedExpr(PredefinedExpr *E) { return Success(E); } 377efdb83e26f9a1fd2566afe54461216cd84814d42John McCall bool VisitCompoundLiteralExpr(CompoundLiteralExpr *E); 378efdb83e26f9a1fd2566afe54461216cd84814d42John McCall bool VisitMemberExpr(MemberExpr *E); 379efdb83e26f9a1fd2566afe54461216cd84814d42John McCall bool VisitStringLiteral(StringLiteral *E) { return Success(E); } 380efdb83e26f9a1fd2566afe54461216cd84814d42John McCall bool VisitObjCEncodeExpr(ObjCEncodeExpr *E) { return Success(E); } 381efdb83e26f9a1fd2566afe54461216cd84814d42John McCall bool VisitArraySubscriptExpr(ArraySubscriptExpr *E); 382efdb83e26f9a1fd2566afe54461216cd84814d42John McCall bool VisitUnaryDeref(UnaryOperator *E); 383efdb83e26f9a1fd2566afe54461216cd84814d42John McCall bool VisitUnaryExtension(const UnaryOperator *E) 384ba98d6bb414861965a1f22628494ea046785ecd4Eli Friedman { return Visit(E->getSubExpr()); } 385efdb83e26f9a1fd2566afe54461216cd84814d42John McCall bool VisitChooseExpr(const ChooseExpr *E) 386ba98d6bb414861965a1f22628494ea046785ecd4Eli Friedman { return Visit(E->getChosenSubExpr(Info.Ctx)); } 38726bc220377705292a0519a71d3ea3aef68fcfec6Anders Carlsson 388efdb83e26f9a1fd2566afe54461216cd84814d42John McCall bool VisitCastExpr(CastExpr *E) { 38926bc220377705292a0519a71d3ea3aef68fcfec6Anders Carlsson switch (E->getCastKind()) { 39026bc220377705292a0519a71d3ea3aef68fcfec6Anders Carlsson default: 391efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return false; 39226bc220377705292a0519a71d3ea3aef68fcfec6Anders Carlsson 3932de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case CK_NoOp: 39426bc220377705292a0519a71d3ea3aef68fcfec6Anders Carlsson return Visit(E->getSubExpr()); 39526bc220377705292a0519a71d3ea3aef68fcfec6Anders Carlsson } 39626bc220377705292a0519a71d3ea3aef68fcfec6Anders Carlsson } 397ba98d6bb414861965a1f22628494ea046785ecd4Eli Friedman // FIXME: Missing: __real__, __imag__ 3984efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman}; 3994efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman} // end anonymous namespace 4004efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman 401efdb83e26f9a1fd2566afe54461216cd84814d42John McCallstatic bool EvaluateLValue(const Expr* E, LValue& Result, EvalInfo &Info) { 402efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return LValueExprEvaluator(Info, Result).Visit(const_cast<Expr*>(E)); 4034efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman} 4044efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman 405efdb83e26f9a1fd2566afe54461216cd84814d42John McCallbool LValueExprEvaluator::VisitDeclRefExpr(DeclRefExpr *E) { 40650c39ea4858265f3f5f42a0c624557ce2281936bEli Friedman if (isa<FunctionDecl>(E->getDecl())) { 407efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return Success(E); 40850c39ea4858265f3f5f42a0c624557ce2281936bEli Friedman } else if (VarDecl* VD = dyn_cast<VarDecl>(E->getDecl())) { 40950c39ea4858265f3f5f42a0c624557ce2281936bEli Friedman if (!VD->getType()->isReferenceType()) 410efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return Success(E); 411761c94e3bffef0fcb8b4bbf202fd5ee73db134f3Chandler Carruth // Reference parameters can refer to anything even if they have an 412761c94e3bffef0fcb8b4bbf202fd5ee73db134f3Chandler Carruth // "initializer" in the form of a default argument. 413761c94e3bffef0fcb8b4bbf202fd5ee73db134f3Chandler Carruth if (isa<ParmVarDecl>(VD)) 414761c94e3bffef0fcb8b4bbf202fd5ee73db134f3Chandler Carruth return false; 415d933a0198f3ccce9c73bf2951625315b911d37bfEli Friedman // FIXME: Check whether VD might be overridden! 41631310a21fb2a9f13950f864f681c86080b05d5b2Sebastian Redl if (const Expr *Init = VD->getAnyInitializer()) 417cf3293eaeb3853d12cff47e648bbe835004e929fDouglas Gregor return Visit(const_cast<Expr *>(Init)); 41850c39ea4858265f3f5f42a0c624557ce2281936bEli Friedman } 41950c39ea4858265f3f5f42a0c624557ce2281936bEli Friedman 420efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return false; 42135873c49adad211ff466e34342a52665742794f5Anders Carlsson} 42235873c49adad211ff466e34342a52665742794f5Anders Carlsson 423efdb83e26f9a1fd2566afe54461216cd84814d42John McCallbool LValueExprEvaluator::VisitCompoundLiteralExpr(CompoundLiteralExpr *E) { 424efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return Success(E); 4254efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman} 4264efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman 427efdb83e26f9a1fd2566afe54461216cd84814d42John McCallbool LValueExprEvaluator::VisitMemberExpr(MemberExpr *E) { 4284efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman QualType Ty; 4294efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman if (E->isArrow()) { 430efdb83e26f9a1fd2566afe54461216cd84814d42John McCall if (!EvaluatePointer(E->getBase(), Result, Info)) 431efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return false; 4326217b80b7a1379b74cced1c076338262c3c980b3Ted Kremenek Ty = E->getBase()->getType()->getAs<PointerType>()->getPointeeType(); 4334efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman } else { 434efdb83e26f9a1fd2566afe54461216cd84814d42John McCall if (!Visit(E->getBase())) 435efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return false; 4364efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman Ty = E->getBase()->getType(); 4374efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman } 4384efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman 4396217b80b7a1379b74cced1c076338262c3c980b3Ted Kremenek RecordDecl *RD = Ty->getAs<RecordType>()->getDecl(); 4404efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman const ASTRecordLayout &RL = Info.Ctx.getASTRecordLayout(RD); 44186f194083504938df72135b5b66bf0c5cafd9498Douglas Gregor 44286f194083504938df72135b5b66bf0c5cafd9498Douglas Gregor FieldDecl *FD = dyn_cast<FieldDecl>(E->getMemberDecl()); 44386f194083504938df72135b5b66bf0c5cafd9498Douglas Gregor if (!FD) // FIXME: deal with other kinds of member expressions 444efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return false; 4452be586108bb401019647791feca19ea03fd477ceEli Friedman 4462be586108bb401019647791feca19ea03fd477ceEli Friedman if (FD->getType()->isReferenceType()) 447efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return false; 4482be586108bb401019647791feca19ea03fd477ceEli Friedman 4494efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman // FIXME: This is linear time. 45044b4321feab46299d3f5cfd404680884752a0fcfDouglas Gregor unsigned i = 0; 45117945a0f64fe03ff6ec0c2146005a87636e3ac12Argyrios Kyrtzidis for (RecordDecl::field_iterator Field = RD->field_begin(), 45217945a0f64fe03ff6ec0c2146005a87636e3ac12Argyrios Kyrtzidis FieldEnd = RD->field_end(); 45344b4321feab46299d3f5cfd404680884752a0fcfDouglas Gregor Field != FieldEnd; (void)++Field, ++i) { 45444b4321feab46299d3f5cfd404680884752a0fcfDouglas Gregor if (*Field == FD) 4554efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman break; 4564efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman } 4574efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman 458fb1e3bc29b667f4275e1d5a43d64ec173f4f9a7dKen Dyck Result.Offset += Info.Ctx.toCharUnitsFromBits(RL.getFieldOffset(i)); 459efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return true; 4604efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman} 4614efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman 462efdb83e26f9a1fd2566afe54461216cd84814d42John McCallbool LValueExprEvaluator::VisitArraySubscriptExpr(ArraySubscriptExpr *E) { 4633068d117951a8df54bae9db039b56201ab10962bAnders Carlsson if (!EvaluatePointer(E->getBase(), Result, Info)) 464efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return false; 4651eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 4663068d117951a8df54bae9db039b56201ab10962bAnders Carlsson APSInt Index; 4673068d117951a8df54bae9db039b56201ab10962bAnders Carlsson if (!EvaluateInteger(E->getIdx(), Index, Info)) 468efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return false; 4693068d117951a8df54bae9db039b56201ab10962bAnders Carlsson 470199c3d6cd16aebbb9c7f0d42af9d922c9628bf70Ken Dyck CharUnits ElementSize = Info.Ctx.getTypeSizeInChars(E->getType()); 471efdb83e26f9a1fd2566afe54461216cd84814d42John McCall Result.Offset += Index.getSExtValue() * ElementSize; 472efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return true; 4733068d117951a8df54bae9db039b56201ab10962bAnders Carlsson} 4744efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman 475efdb83e26f9a1fd2566afe54461216cd84814d42John McCallbool LValueExprEvaluator::VisitUnaryDeref(UnaryOperator *E) { 476efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return EvaluatePointer(E->getSubExpr(), Result, Info); 477e8761c8fe2ee6b628104a0885f49fd3c21c08a4fEli Friedman} 478e8761c8fe2ee6b628104a0885f49fd3c21c08a4fEli Friedman 4794efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman//===----------------------------------------------------------------------===// 480f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner// Pointer Evaluation 481f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner//===----------------------------------------------------------------------===// 482f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner 483c754aa62643e66ab967ca32ae8b0b3fc419bba25Anders Carlssonnamespace { 484770b4a8834670e9427d3ce5a1a8472eb86f45fd2Benjamin Kramerclass PointerExprEvaluator 485efdb83e26f9a1fd2566afe54461216cd84814d42John McCall : public StmtVisitor<PointerExprEvaluator, bool> { 48687eae5ecf94e38baa20d9a327b8f73f8bdc72436Chris Lattner EvalInfo &Info; 487efdb83e26f9a1fd2566afe54461216cd84814d42John McCall LValue &Result; 488efdb83e26f9a1fd2566afe54461216cd84814d42John McCall 489efdb83e26f9a1fd2566afe54461216cd84814d42John McCall bool Success(Expr *E) { 490efdb83e26f9a1fd2566afe54461216cd84814d42John McCall Result.Base = E; 491efdb83e26f9a1fd2566afe54461216cd84814d42John McCall Result.Offset = CharUnits::Zero(); 492efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return true; 493efdb83e26f9a1fd2566afe54461216cd84814d42John McCall } 4942bad1687fe6f00e10767a691a33b070b151902b6Anders Carlssonpublic: 4951eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 496efdb83e26f9a1fd2566afe54461216cd84814d42John McCall PointerExprEvaluator(EvalInfo &info, LValue &Result) 497efdb83e26f9a1fd2566afe54461216cd84814d42John McCall : Info(info), Result(Result) {} 498f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner 499efdb83e26f9a1fd2566afe54461216cd84814d42John McCall bool VisitStmt(Stmt *S) { 500efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return false; 5012bad1687fe6f00e10767a691a33b070b151902b6Anders Carlsson } 5022bad1687fe6f00e10767a691a33b070b151902b6Anders Carlsson 503efdb83e26f9a1fd2566afe54461216cd84814d42John McCall bool VisitParenExpr(ParenExpr *E) { return Visit(E->getSubExpr()); } 5042bad1687fe6f00e10767a691a33b070b151902b6Anders Carlsson 505efdb83e26f9a1fd2566afe54461216cd84814d42John McCall bool VisitBinaryOperator(const BinaryOperator *E); 506efdb83e26f9a1fd2566afe54461216cd84814d42John McCall bool VisitCastExpr(CastExpr* E); 507efdb83e26f9a1fd2566afe54461216cd84814d42John McCall bool VisitUnaryExtension(const UnaryOperator *E) 5082217c87bdc5ab357046a5453bdb06f469c41024eEli Friedman { return Visit(E->getSubExpr()); } 509efdb83e26f9a1fd2566afe54461216cd84814d42John McCall bool VisitUnaryAddrOf(const UnaryOperator *E); 510efdb83e26f9a1fd2566afe54461216cd84814d42John McCall bool VisitObjCStringLiteral(ObjCStringLiteral *E) 511efdb83e26f9a1fd2566afe54461216cd84814d42John McCall { return Success(E); } 512efdb83e26f9a1fd2566afe54461216cd84814d42John McCall bool VisitAddrLabelExpr(AddrLabelExpr *E) 513efdb83e26f9a1fd2566afe54461216cd84814d42John McCall { return Success(E); } 514efdb83e26f9a1fd2566afe54461216cd84814d42John McCall bool VisitCallExpr(CallExpr *E); 515efdb83e26f9a1fd2566afe54461216cd84814d42John McCall bool VisitBlockExpr(BlockExpr *E) { 516469a1eb996e1cb0be54f9b210f836afbddcbb2ccJohn McCall if (!E->getBlockDecl()->hasCaptures()) 517efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return Success(E); 518efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return false; 519b83d287bc7f47d36fb0751a481e2ef9308b37252Mike Stump } 520efdb83e26f9a1fd2566afe54461216cd84814d42John McCall bool VisitImplicitValueInitExpr(ImplicitValueInitExpr *E) 521efdb83e26f9a1fd2566afe54461216cd84814d42John McCall { return Success((Expr*)0); } 52256ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall bool VisitBinaryConditionalOperator(BinaryConditionalOperator *E); 523efdb83e26f9a1fd2566afe54461216cd84814d42John McCall bool VisitConditionalOperator(ConditionalOperator *E); 524efdb83e26f9a1fd2566afe54461216cd84814d42John McCall bool VisitChooseExpr(ChooseExpr *E) 5256e8ed16ffef02b82995a90bdcf10ffff7d63839aSebastian Redl { return Visit(E->getChosenSubExpr(Info.Ctx)); } 526efdb83e26f9a1fd2566afe54461216cd84814d42John McCall bool VisitCXXNullPtrLiteralExpr(CXXNullPtrLiteralExpr *E) 527efdb83e26f9a1fd2566afe54461216cd84814d42John McCall { return Success((Expr*)0); } 52856ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall 52956ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall bool VisitOpaqueValueExpr(OpaqueValueExpr *E); 530ba98d6bb414861965a1f22628494ea046785ecd4Eli Friedman // FIXME: Missing: @protocol, @selector 5312bad1687fe6f00e10767a691a33b070b151902b6Anders Carlsson}; 532f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner} // end anonymous namespace 5332bad1687fe6f00e10767a691a33b070b151902b6Anders Carlsson 534efdb83e26f9a1fd2566afe54461216cd84814d42John McCallstatic bool EvaluatePointer(const Expr* E, LValue& Result, EvalInfo &Info) { 5357db7acbbb84b82d0522266a50ebabc3a52a9e5d1John McCall assert(E->getType()->hasPointerRepresentation()); 536efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return PointerExprEvaluator(Info, Result).Visit(const_cast<Expr*>(E)); 537f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner} 538650c92fdcc27a950a8a848ecab6a74e6f5e80788Anders Carlsson 539efdb83e26f9a1fd2566afe54461216cd84814d42John McCallbool PointerExprEvaluator::VisitBinaryOperator(const BinaryOperator *E) { 5402de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall if (E->getOpcode() != BO_Add && 5412de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall E->getOpcode() != BO_Sub) 542efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return false; 5431eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 544650c92fdcc27a950a8a848ecab6a74e6f5e80788Anders Carlsson const Expr *PExp = E->getLHS(); 545650c92fdcc27a950a8a848ecab6a74e6f5e80788Anders Carlsson const Expr *IExp = E->getRHS(); 546650c92fdcc27a950a8a848ecab6a74e6f5e80788Anders Carlsson if (IExp->getType()->isPointerType()) 547f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner std::swap(PExp, IExp); 5481eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 549efdb83e26f9a1fd2566afe54461216cd84814d42John McCall if (!EvaluatePointer(PExp, Result, Info)) 550efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return false; 5511eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 552efdb83e26f9a1fd2566afe54461216cd84814d42John McCall llvm::APSInt Offset; 553efdb83e26f9a1fd2566afe54461216cd84814d42John McCall if (!EvaluateInteger(IExp, Offset, Info)) 554efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return false; 555efdb83e26f9a1fd2566afe54461216cd84814d42John McCall int64_t AdditionalOffset 556efdb83e26f9a1fd2566afe54461216cd84814d42John McCall = Offset.isSigned() ? Offset.getSExtValue() 557efdb83e26f9a1fd2566afe54461216cd84814d42John McCall : static_cast<int64_t>(Offset.getZExtValue()); 558650c92fdcc27a950a8a848ecab6a74e6f5e80788Anders Carlsson 559e0cdb4edd8f265d0fd22d178d03c597dd201cda2Daniel Dunbar // Compute the new offset in the appropriate width. 560e0cdb4edd8f265d0fd22d178d03c597dd201cda2Daniel Dunbar 561e0cdb4edd8f265d0fd22d178d03c597dd201cda2Daniel Dunbar QualType PointeeType = 562e0cdb4edd8f265d0fd22d178d03c597dd201cda2Daniel Dunbar PExp->getType()->getAs<PointerType>()->getPointeeType(); 563efdb83e26f9a1fd2566afe54461216cd84814d42John McCall CharUnits SizeOfPointee; 5641eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 5654d4c50dd8b4db191c38782414665fb7608315a36Anders Carlsson // Explicitly handle GNU void* and function pointer arithmetic extensions. 5664d4c50dd8b4db191c38782414665fb7608315a36Anders Carlsson if (PointeeType->isVoidType() || PointeeType->isFunctionType()) 567efdb83e26f9a1fd2566afe54461216cd84814d42John McCall SizeOfPointee = CharUnits::One(); 5684d4c50dd8b4db191c38782414665fb7608315a36Anders Carlsson else 569efdb83e26f9a1fd2566afe54461216cd84814d42John McCall SizeOfPointee = Info.Ctx.getTypeSizeInChars(PointeeType); 5704efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman 5712de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall if (E->getOpcode() == BO_Add) 572efdb83e26f9a1fd2566afe54461216cd84814d42John McCall Result.Offset += AdditionalOffset * SizeOfPointee; 573650c92fdcc27a950a8a848ecab6a74e6f5e80788Anders Carlsson else 574efdb83e26f9a1fd2566afe54461216cd84814d42John McCall Result.Offset -= AdditionalOffset * SizeOfPointee; 5754efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman 576efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return true; 577650c92fdcc27a950a8a848ecab6a74e6f5e80788Anders Carlsson} 5784efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman 579efdb83e26f9a1fd2566afe54461216cd84814d42John McCallbool PointerExprEvaluator::VisitUnaryAddrOf(const UnaryOperator *E) { 580efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return EvaluateLValue(E->getSubExpr(), Result, Info); 5814efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman} 5821eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 583650c92fdcc27a950a8a848ecab6a74e6f5e80788Anders Carlsson 584efdb83e26f9a1fd2566afe54461216cd84814d42John McCallbool PointerExprEvaluator::VisitCastExpr(CastExpr* E) { 58509a8a0e6ec1252cad52666e9dbb21002b9c80f38Eli Friedman Expr* SubExpr = E->getSubExpr(); 586650c92fdcc27a950a8a848ecab6a74e6f5e80788Anders Carlsson 58709a8a0e6ec1252cad52666e9dbb21002b9c80f38Eli Friedman switch (E->getCastKind()) { 58809a8a0e6ec1252cad52666e9dbb21002b9c80f38Eli Friedman default: 58909a8a0e6ec1252cad52666e9dbb21002b9c80f38Eli Friedman break; 59009a8a0e6ec1252cad52666e9dbb21002b9c80f38Eli Friedman 5912de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case CK_NoOp: 5922de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case CK_BitCast: 5932de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case CK_LValueBitCast: 5942de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case CK_AnyPointerToObjCPointerCast: 5952de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case CK_AnyPointerToBlockPointerCast: 59609a8a0e6ec1252cad52666e9dbb21002b9c80f38Eli Friedman return Visit(SubExpr); 59709a8a0e6ec1252cad52666e9dbb21002b9c80f38Eli Friedman 5985c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson case CK_DerivedToBase: 5995c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson case CK_UncheckedDerivedToBase: { 6005c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson LValue BaseLV; 6015c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson if (!EvaluatePointer(E->getSubExpr(), BaseLV, Info)) 6025c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson return false; 6035c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson 6045c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson // Now figure out the necessary offset to add to the baseLV to get from 6055c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson // the derived class to the base class. 6067c7f820d70c925b29290a8563b59615816a827fcKen Dyck CharUnits Offset = CharUnits::Zero(); 6075c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson 6085c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson QualType Ty = E->getSubExpr()->getType(); 6095c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson const CXXRecordDecl *DerivedDecl = 6105c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson Ty->getAs<PointerType>()->getPointeeType()->getAsCXXRecordDecl(); 6115c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson 6125c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson for (CastExpr::path_const_iterator PathI = E->path_begin(), 6135c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson PathE = E->path_end(); PathI != PathE; ++PathI) { 6145c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson const CXXBaseSpecifier *Base = *PathI; 6155c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson 6165c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson // FIXME: If the base is virtual, we'd need to determine the type of the 6175c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson // most derived class and we don't support that right now. 6185c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson if (Base->isVirtual()) 6195c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson return false; 6205c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson 6215c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson const CXXRecordDecl *BaseDecl = Base->getType()->getAsCXXRecordDecl(); 6225c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson const ASTRecordLayout &Layout = Info.Ctx.getASTRecordLayout(DerivedDecl); 6235c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson 6247c7f820d70c925b29290a8563b59615816a827fcKen Dyck Offset += Layout.getBaseClassOffset(BaseDecl); 6255c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson DerivedDecl = BaseDecl; 6265c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson } 6275c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson 6285c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson Result.Base = BaseLV.getLValueBase(); 6297c7f820d70c925b29290a8563b59615816a827fcKen Dyck Result.Offset = BaseLV.getLValueOffset() + Offset; 6305c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson return true; 6315c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson } 6325c5a764fcd256df6f6cfbce5cdd2a2dfb2c45e95Anders Carlsson 633404cd1669c3ba138a9ae0a619bd689cce5aae271John McCall case CK_NullToPointer: { 634404cd1669c3ba138a9ae0a619bd689cce5aae271John McCall Result.Base = 0; 635404cd1669c3ba138a9ae0a619bd689cce5aae271John McCall Result.Offset = CharUnits::Zero(); 636404cd1669c3ba138a9ae0a619bd689cce5aae271John McCall return true; 637404cd1669c3ba138a9ae0a619bd689cce5aae271John McCall } 638404cd1669c3ba138a9ae0a619bd689cce5aae271John McCall 6392de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case CK_IntegralToPointer: { 640efdb83e26f9a1fd2566afe54461216cd84814d42John McCall APValue Value; 641efdb83e26f9a1fd2566afe54461216cd84814d42John McCall if (!EvaluateIntegerOrLValue(SubExpr, Value, Info)) 64209a8a0e6ec1252cad52666e9dbb21002b9c80f38Eli Friedman break; 64369ab26a8623141f35e86817cfc6e0fbe7639a40fDaniel Dunbar 644efdb83e26f9a1fd2566afe54461216cd84814d42John McCall if (Value.isInt()) { 6459f71a8f4c7a182a5236da9e747d57cc1d1bd24c2Jay Foad Value.getInt() = Value.getInt().extOrTrunc((unsigned)Info.Ctx.getTypeSize(E->getType())); 646efdb83e26f9a1fd2566afe54461216cd84814d42John McCall Result.Base = 0; 647efdb83e26f9a1fd2566afe54461216cd84814d42John McCall Result.Offset = CharUnits::fromQuantity(Value.getInt().getZExtValue()); 648efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return true; 649efdb83e26f9a1fd2566afe54461216cd84814d42John McCall } else { 650efdb83e26f9a1fd2566afe54461216cd84814d42John McCall // Cast is of an lvalue, no need to change value. 651efdb83e26f9a1fd2566afe54461216cd84814d42John McCall Result.Base = Value.getLValueBase(); 652efdb83e26f9a1fd2566afe54461216cd84814d42John McCall Result.Offset = Value.getLValueOffset(); 653efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return true; 654650c92fdcc27a950a8a848ecab6a74e6f5e80788Anders Carlsson } 655650c92fdcc27a950a8a848ecab6a74e6f5e80788Anders Carlsson } 6562de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case CK_ArrayToPointerDecay: 6572de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case CK_FunctionToPointerDecay: 658efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return EvaluateLValue(SubExpr, Result, Info); 6594efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman } 6604efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman 661efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return false; 6621eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump} 663650c92fdcc27a950a8a848ecab6a74e6f5e80788Anders Carlsson 664efdb83e26f9a1fd2566afe54461216cd84814d42John McCallbool PointerExprEvaluator::VisitCallExpr(CallExpr *E) { 6651eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump if (E->isBuiltinCall(Info.Ctx) == 6660d13f6fdbdd6f06e2449b8834dda53334abd399aDavid Chisnall Builtin::BI__builtin___CFStringMakeConstantString || 6670d13f6fdbdd6f06e2449b8834dda53334abd399aDavid Chisnall E->isBuiltinCall(Info.Ctx) == 6680d13f6fdbdd6f06e2449b8834dda53334abd399aDavid Chisnall Builtin::BI__builtin___NSStringMakeConstantString) 669efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return Success(E); 670efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return false; 6713941b18b8e441c8c466efecd557de60b9a32d10bEli Friedman} 6723941b18b8e441c8c466efecd557de60b9a32d10bEli Friedman 67356ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCallbool PointerExprEvaluator::VisitOpaqueValueExpr(OpaqueValueExpr *e) { 67456ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall const APValue *value = Info.getOpaqueValue(e); 67556ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall if (!value) 67656ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall return (e->getSourceExpr() ? Visit(e->getSourceExpr()) : false); 67756ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall Result.setFrom(*value); 67856ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall return true; 67956ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall} 68056ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall 68156ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCallbool PointerExprEvaluator:: 68256ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCallVisitBinaryConditionalOperator(BinaryConditionalOperator *e) { 68356ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall OpaqueValueEvaluation opaque(Info, e->getOpaqueValue(), e->getCommon()); 68456ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall if (opaque.hasError()) return false; 68556ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall 68656ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall bool cond; 68756ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall if (!HandleConversionToBool(e->getCond(), cond, Info)) 68856ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall return false; 68956ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall 69056ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall return Visit(cond ? e->getTrueExpr() : e->getFalseExpr()); 69156ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall} 69256ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall 693efdb83e26f9a1fd2566afe54461216cd84814d42John McCallbool PointerExprEvaluator::VisitConditionalOperator(ConditionalOperator *E) { 6944efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman bool BoolResult; 6954efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman if (!HandleConversionToBool(E->getCond(), BoolResult, Info)) 696efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return false; 6974efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman 6984efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman Expr* EvalExpr = BoolResult ? E->getTrueExpr() : E->getFalseExpr(); 699efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return Visit(EvalExpr); 7004efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman} 701f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner 702f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner//===----------------------------------------------------------------------===// 70359b5da6d853b4368b984700315adf7b37de05764Nate Begeman// Vector Evaluation 70459b5da6d853b4368b984700315adf7b37de05764Nate Begeman//===----------------------------------------------------------------------===// 70559b5da6d853b4368b984700315adf7b37de05764Nate Begeman 70659b5da6d853b4368b984700315adf7b37de05764Nate Begemannamespace { 707770b4a8834670e9427d3ce5a1a8472eb86f45fd2Benjamin Kramer class VectorExprEvaluator 70859b5da6d853b4368b984700315adf7b37de05764Nate Begeman : public StmtVisitor<VectorExprEvaluator, APValue> { 70959b5da6d853b4368b984700315adf7b37de05764Nate Begeman EvalInfo &Info; 71091110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman APValue GetZeroVector(QualType VecType); 71159b5da6d853b4368b984700315adf7b37de05764Nate Begeman public: 7121eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 71359b5da6d853b4368b984700315adf7b37de05764Nate Begeman VectorExprEvaluator(EvalInfo &info) : Info(info) {} 7141eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 71559b5da6d853b4368b984700315adf7b37de05764Nate Begeman APValue VisitStmt(Stmt *S) { 71659b5da6d853b4368b984700315adf7b37de05764Nate Begeman return APValue(); 71759b5da6d853b4368b984700315adf7b37de05764Nate Begeman } 7181eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 71991110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman APValue VisitParenExpr(ParenExpr *E) 72091110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman { return Visit(E->getSubExpr()); } 72191110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman APValue VisitUnaryExtension(const UnaryOperator *E) 72291110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman { return Visit(E->getSubExpr()); } 72391110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman APValue VisitUnaryPlus(const UnaryOperator *E) 72491110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman { return Visit(E->getSubExpr()); } 72591110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman APValue VisitUnaryReal(const UnaryOperator *E) 72691110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman { return Visit(E->getSubExpr()); } 72791110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman APValue VisitImplicitValueInitExpr(const ImplicitValueInitExpr *E) 72891110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman { return GetZeroVector(E->getType()); } 72959b5da6d853b4368b984700315adf7b37de05764Nate Begeman APValue VisitCastExpr(const CastExpr* E); 73059b5da6d853b4368b984700315adf7b37de05764Nate Begeman APValue VisitCompoundLiteralExpr(const CompoundLiteralExpr *E); 73159b5da6d853b4368b984700315adf7b37de05764Nate Begeman APValue VisitInitListExpr(const InitListExpr *E); 73291110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman APValue VisitConditionalOperator(const ConditionalOperator *E); 733ba98d6bb414861965a1f22628494ea046785ecd4Eli Friedman APValue VisitChooseExpr(const ChooseExpr *E) 734ba98d6bb414861965a1f22628494ea046785ecd4Eli Friedman { return Visit(E->getChosenSubExpr(Info.Ctx)); } 73591110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman APValue VisitUnaryImag(const UnaryOperator *E); 73691110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman // FIXME: Missing: unary -, unary ~, binary add/sub/mul/div, 7372217c87bdc5ab357046a5453bdb06f469c41024eEli Friedman // binary comparisons, binary and/or/xor, 73891110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman // shufflevector, ExtVectorElementExpr 73991110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman // (Note that these require implementing conversions 74091110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman // between vector types.) 74159b5da6d853b4368b984700315adf7b37de05764Nate Begeman }; 74259b5da6d853b4368b984700315adf7b37de05764Nate Begeman} // end anonymous namespace 74359b5da6d853b4368b984700315adf7b37de05764Nate Begeman 74459b5da6d853b4368b984700315adf7b37de05764Nate Begemanstatic bool EvaluateVector(const Expr* E, APValue& Result, EvalInfo &Info) { 74559b5da6d853b4368b984700315adf7b37de05764Nate Begeman if (!E->getType()->isVectorType()) 74659b5da6d853b4368b984700315adf7b37de05764Nate Begeman return false; 74759b5da6d853b4368b984700315adf7b37de05764Nate Begeman Result = VectorExprEvaluator(Info).Visit(const_cast<Expr*>(E)); 74859b5da6d853b4368b984700315adf7b37de05764Nate Begeman return !Result.isUninit(); 74959b5da6d853b4368b984700315adf7b37de05764Nate Begeman} 75059b5da6d853b4368b984700315adf7b37de05764Nate Begeman 75159b5da6d853b4368b984700315adf7b37de05764Nate BegemanAPValue VectorExprEvaluator::VisitCastExpr(const CastExpr* E) { 752183700f494ec9b6701b6efe82bcb25f4c79ba561John McCall const VectorType *VTy = E->getType()->getAs<VectorType>(); 753c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman QualType EltTy = VTy->getElementType(); 754c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman unsigned NElts = VTy->getNumElements(); 755c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman unsigned EltWidth = Info.Ctx.getTypeSize(EltTy); 7561eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 75759b5da6d853b4368b984700315adf7b37de05764Nate Begeman const Expr* SE = E->getSubExpr(); 758e8c9e9218f215ec6089f12b076c7b9d310fd5194Nate Begeman QualType SETy = SE->getType(); 759e8c9e9218f215ec6089f12b076c7b9d310fd5194Nate Begeman APValue Result = APValue(); 76059b5da6d853b4368b984700315adf7b37de05764Nate Begeman 761e8c9e9218f215ec6089f12b076c7b9d310fd5194Nate Begeman // Check for vector->vector bitcast and scalar->vector splat. 762e8c9e9218f215ec6089f12b076c7b9d310fd5194Nate Begeman if (SETy->isVectorType()) { 76359b5da6d853b4368b984700315adf7b37de05764Nate Begeman return this->Visit(const_cast<Expr*>(SE)); 764e8c9e9218f215ec6089f12b076c7b9d310fd5194Nate Begeman } else if (SETy->isIntegerType()) { 765e8c9e9218f215ec6089f12b076c7b9d310fd5194Nate Begeman APSInt IntResult; 766d906dc7605b2d6352e16c27a5d3fb5f1a1b44ac8Daniel Dunbar if (!EvaluateInteger(SE, IntResult, Info)) 767d906dc7605b2d6352e16c27a5d3fb5f1a1b44ac8Daniel Dunbar return APValue(); 768d906dc7605b2d6352e16c27a5d3fb5f1a1b44ac8Daniel Dunbar Result = APValue(IntResult); 769e8c9e9218f215ec6089f12b076c7b9d310fd5194Nate Begeman } else if (SETy->isRealFloatingType()) { 770e8c9e9218f215ec6089f12b076c7b9d310fd5194Nate Begeman APFloat F(0.0); 771d906dc7605b2d6352e16c27a5d3fb5f1a1b44ac8Daniel Dunbar if (!EvaluateFloat(SE, F, Info)) 772d906dc7605b2d6352e16c27a5d3fb5f1a1b44ac8Daniel Dunbar return APValue(); 773d906dc7605b2d6352e16c27a5d3fb5f1a1b44ac8Daniel Dunbar Result = APValue(F); 774d906dc7605b2d6352e16c27a5d3fb5f1a1b44ac8Daniel Dunbar } else 775c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman return APValue(); 77659b5da6d853b4368b984700315adf7b37de05764Nate Begeman 777c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman // For casts of a scalar to ExtVector, convert the scalar to the element type 778c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman // and splat it to all elements. 779c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman if (E->getType()->isExtVectorType()) { 780c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman if (EltTy->isIntegerType() && Result.isInt()) 781c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman Result = APValue(HandleIntToIntCast(EltTy, SETy, Result.getInt(), 782c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman Info.Ctx)); 783c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman else if (EltTy->isIntegerType()) 784c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman Result = APValue(HandleFloatToIntCast(EltTy, SETy, Result.getFloat(), 785c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman Info.Ctx)); 786c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman else if (EltTy->isRealFloatingType() && Result.isInt()) 787c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman Result = APValue(HandleIntToFloatCast(EltTy, SETy, Result.getInt(), 788c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman Info.Ctx)); 789c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman else if (EltTy->isRealFloatingType()) 790c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman Result = APValue(HandleFloatToFloatCast(EltTy, SETy, Result.getFloat(), 791c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman Info.Ctx)); 792c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman else 793c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman return APValue(); 794c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman 795c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman // Splat and create vector APValue. 796c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman llvm::SmallVector<APValue, 4> Elts(NElts, Result); 797c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman return APValue(&Elts[0], Elts.size()); 798e8c9e9218f215ec6089f12b076c7b9d310fd5194Nate Begeman } 799c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman 800c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman // For casts of a scalar to regular gcc-style vector type, bitcast the scalar 801c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman // to the vector. To construct the APValue vector initializer, bitcast the 802c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman // initializing value to an APInt, and shift out the bits pertaining to each 803c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman // element. 804c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman APSInt Init; 805c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman Init = Result.isInt() ? Result.getInt() : Result.getFloat().bitcastToAPInt(); 8061eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 807c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman llvm::SmallVector<APValue, 4> Elts; 808c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman for (unsigned i = 0; i != NElts; ++i) { 8099f71a8f4c7a182a5236da9e747d57cc1d1bd24c2Jay Foad APSInt Tmp = Init.extOrTrunc(EltWidth); 8101eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 811c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman if (EltTy->isIntegerType()) 812c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman Elts.push_back(APValue(Tmp)); 813c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman else if (EltTy->isRealFloatingType()) 814c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman Elts.push_back(APValue(APFloat(Tmp))); 815c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman else 816c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman return APValue(); 817c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman 818c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman Init >>= EltWidth; 819c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman } 820c0b8b19bd8056d6b5d831623a0825cce150f4507Nate Begeman return APValue(&Elts[0], Elts.size()); 82159b5da6d853b4368b984700315adf7b37de05764Nate Begeman} 82259b5da6d853b4368b984700315adf7b37de05764Nate Begeman 8231eb4433ac451dc16f4133a88af2d002ac26c58efMike StumpAPValue 82459b5da6d853b4368b984700315adf7b37de05764Nate BegemanVectorExprEvaluator::VisitCompoundLiteralExpr(const CompoundLiteralExpr *E) { 82559b5da6d853b4368b984700315adf7b37de05764Nate Begeman return this->Visit(const_cast<Expr*>(E->getInitializer())); 82659b5da6d853b4368b984700315adf7b37de05764Nate Begeman} 82759b5da6d853b4368b984700315adf7b37de05764Nate Begeman 8281eb4433ac451dc16f4133a88af2d002ac26c58efMike StumpAPValue 82959b5da6d853b4368b984700315adf7b37de05764Nate BegemanVectorExprEvaluator::VisitInitListExpr(const InitListExpr *E) { 830183700f494ec9b6701b6efe82bcb25f4c79ba561John McCall const VectorType *VT = E->getType()->getAs<VectorType>(); 83159b5da6d853b4368b984700315adf7b37de05764Nate Begeman unsigned NumInits = E->getNumInits(); 83291110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman unsigned NumElements = VT->getNumElements(); 8331eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 83459b5da6d853b4368b984700315adf7b37de05764Nate Begeman QualType EltTy = VT->getElementType(); 83559b5da6d853b4368b984700315adf7b37de05764Nate Begeman llvm::SmallVector<APValue, 4> Elements; 83659b5da6d853b4368b984700315adf7b37de05764Nate Begeman 837a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall // If a vector is initialized with a single element, that value 838a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall // becomes every element of the vector, not just the first. 839a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall // This is the behavior described in the IBM AltiVec documentation. 840a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall if (NumInits == 1) { 841a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall APValue InitValue; 84259b5da6d853b4368b984700315adf7b37de05764Nate Begeman if (EltTy->isIntegerType()) { 84359b5da6d853b4368b984700315adf7b37de05764Nate Begeman llvm::APSInt sInt(32); 844a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall if (!EvaluateInteger(E->getInit(0), sInt, Info)) 845a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall return APValue(); 846a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall InitValue = APValue(sInt); 84759b5da6d853b4368b984700315adf7b37de05764Nate Begeman } else { 84859b5da6d853b4368b984700315adf7b37de05764Nate Begeman llvm::APFloat f(0.0); 849a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall if (!EvaluateFloat(E->getInit(0), f, Info)) 850a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall return APValue(); 851a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall InitValue = APValue(f); 852a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall } 853a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall for (unsigned i = 0; i < NumElements; i++) { 854a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall Elements.push_back(InitValue); 855a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall } 856a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall } else { 857a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall for (unsigned i = 0; i < NumElements; i++) { 858a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall if (EltTy->isIntegerType()) { 859a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall llvm::APSInt sInt(32); 860a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall if (i < NumInits) { 861a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall if (!EvaluateInteger(E->getInit(i), sInt, Info)) 862a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall return APValue(); 863a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall } else { 864a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall sInt = Info.Ctx.MakeIntValue(0, EltTy); 865a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall } 866a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall Elements.push_back(APValue(sInt)); 86791110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman } else { 868a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall llvm::APFloat f(0.0); 869a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall if (i < NumInits) { 870a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall if (!EvaluateFloat(E->getInit(i), f, Info)) 871a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall return APValue(); 872a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall } else { 873a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall f = APFloat::getZero(Info.Ctx.getFloatTypeSemantics(EltTy)); 874a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall } 875a7d6c221558fa8117aa1d1fd41cf0046c5c9fadeJohn McCall Elements.push_back(APValue(f)); 87691110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman } 87759b5da6d853b4368b984700315adf7b37de05764Nate Begeman } 87859b5da6d853b4368b984700315adf7b37de05764Nate Begeman } 87959b5da6d853b4368b984700315adf7b37de05764Nate Begeman return APValue(&Elements[0], Elements.size()); 88059b5da6d853b4368b984700315adf7b37de05764Nate Begeman} 88159b5da6d853b4368b984700315adf7b37de05764Nate Begeman 8821eb4433ac451dc16f4133a88af2d002ac26c58efMike StumpAPValue 88391110ee24e3475e0a3a38938c7b98439b5cf0b0eEli FriedmanVectorExprEvaluator::GetZeroVector(QualType T) { 884183700f494ec9b6701b6efe82bcb25f4c79ba561John McCall const VectorType *VT = T->getAs<VectorType>(); 88591110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman QualType EltTy = VT->getElementType(); 88691110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman APValue ZeroElement; 88791110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman if (EltTy->isIntegerType()) 88891110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman ZeroElement = APValue(Info.Ctx.MakeIntValue(0, EltTy)); 88991110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman else 89091110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman ZeroElement = 89191110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman APValue(APFloat::getZero(Info.Ctx.getFloatTypeSemantics(EltTy))); 89291110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman 89391110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman llvm::SmallVector<APValue, 4> Elements(VT->getNumElements(), ZeroElement); 89491110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman return APValue(&Elements[0], Elements.size()); 89591110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman} 89691110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman 89791110ee24e3475e0a3a38938c7b98439b5cf0b0eEli FriedmanAPValue VectorExprEvaluator::VisitConditionalOperator(const ConditionalOperator *E) { 89891110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman bool BoolResult; 89991110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman if (!HandleConversionToBool(E->getCond(), BoolResult, Info)) 90091110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman return APValue(); 90191110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman 90291110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman Expr* EvalExpr = BoolResult ? E->getTrueExpr() : E->getFalseExpr(); 90391110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman 90491110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman APValue Result; 90591110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman if (EvaluateVector(EvalExpr, Result, Info)) 90691110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman return Result; 90791110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman return APValue(); 90891110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman} 90991110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman 91091110ee24e3475e0a3a38938c7b98439b5cf0b0eEli FriedmanAPValue VectorExprEvaluator::VisitUnaryImag(const UnaryOperator *E) { 91191110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman if (!E->getSubExpr()->isEvaluatable(Info.Ctx)) 91291110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman Info.EvalResult.HasSideEffects = true; 91391110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman return GetZeroVector(E->getType()); 91491110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman} 91591110ee24e3475e0a3a38938c7b98439b5cf0b0eEli Friedman 91659b5da6d853b4368b984700315adf7b37de05764Nate Begeman//===----------------------------------------------------------------------===// 917f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner// Integer Evaluation 918f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner//===----------------------------------------------------------------------===// 919f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner 920f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattnernamespace { 921770b4a8834670e9427d3ce5a1a8472eb86f45fd2Benjamin Kramerclass IntExprEvaluator 922b542afe02d317411d53b3541946f9f2a8f509a11Chris Lattner : public StmtVisitor<IntExprEvaluator, bool> { 92387eae5ecf94e38baa20d9a327b8f73f8bdc72436Chris Lattner EvalInfo &Info; 92430c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar APValue &Result; 925f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattnerpublic: 92630c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar IntExprEvaluator(EvalInfo &info, APValue &result) 92787eae5ecf94e38baa20d9a327b8f73f8bdc72436Chris Lattner : Info(info), Result(result) {} 928f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner 9293f7d995390009fede92b333a040da80e1ce90997Daniel Dunbar bool Success(const llvm::APSInt &SI, const Expr *E) { 9302ade35e2cfd554e49d35a52047cea98a82787af9Douglas Gregor assert(E->getType()->isIntegralOrEnumerationType() && 9312ade35e2cfd554e49d35a52047cea98a82787af9Douglas Gregor "Invalid evaluation result."); 93230c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar assert(SI.isSigned() == E->getType()->isSignedIntegerType() && 9333f7d995390009fede92b333a040da80e1ce90997Daniel Dunbar "Invalid evaluation result."); 93430c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar assert(SI.getBitWidth() == Info.Ctx.getIntWidth(E->getType()) && 9353f7d995390009fede92b333a040da80e1ce90997Daniel Dunbar "Invalid evaluation result."); 93630c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar Result = APValue(SI); 9373f7d995390009fede92b333a040da80e1ce90997Daniel Dunbar return true; 9383f7d995390009fede92b333a040da80e1ce90997Daniel Dunbar } 9393f7d995390009fede92b333a040da80e1ce90997Daniel Dunbar 940131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar bool Success(const llvm::APInt &I, const Expr *E) { 9412ade35e2cfd554e49d35a52047cea98a82787af9Douglas Gregor assert(E->getType()->isIntegralOrEnumerationType() && 9422ade35e2cfd554e49d35a52047cea98a82787af9Douglas Gregor "Invalid evaluation result."); 94330c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar assert(I.getBitWidth() == Info.Ctx.getIntWidth(E->getType()) && 9443f7d995390009fede92b333a040da80e1ce90997Daniel Dunbar "Invalid evaluation result."); 94530c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar Result = APValue(APSInt(I)); 94630c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar Result.getInt().setIsUnsigned(E->getType()->isUnsignedIntegerType()); 947131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar return true; 948131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar } 949131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar 950131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar bool Success(uint64_t Value, const Expr *E) { 9512ade35e2cfd554e49d35a52047cea98a82787af9Douglas Gregor assert(E->getType()->isIntegralOrEnumerationType() && 9522ade35e2cfd554e49d35a52047cea98a82787af9Douglas Gregor "Invalid evaluation result."); 95330c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar Result = APValue(Info.Ctx.MakeIntValue(Value, E->getType())); 954131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar return true; 955131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar } 956131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar 9574f3bc8f7aa90b72832b03bee9201c98f4bb6b4d1Ken Dyck bool Success(CharUnits Size, const Expr *E) { 9584f3bc8f7aa90b72832b03bee9201c98f4bb6b4d1Ken Dyck return Success(Size.getQuantity(), E); 9594f3bc8f7aa90b72832b03bee9201c98f4bb6b4d1Ken Dyck } 9604f3bc8f7aa90b72832b03bee9201c98f4bb6b4d1Ken Dyck 9614f3bc8f7aa90b72832b03bee9201c98f4bb6b4d1Ken Dyck 96282206e267ce6cc709797127616f64672d255b310Anders Carlsson bool Error(SourceLocation L, diag::kind D, const Expr *E) { 96332fea9d18cc3658a1b01df5ca6f2ac302625c61dChris Lattner // Take the first error. 96454da0496616cb898596cfd5fae1f824098bd8435Anders Carlsson if (Info.EvalResult.Diag == 0) { 96554da0496616cb898596cfd5fae1f824098bd8435Anders Carlsson Info.EvalResult.DiagLoc = L; 96654da0496616cb898596cfd5fae1f824098bd8435Anders Carlsson Info.EvalResult.Diag = D; 96782206e267ce6cc709797127616f64672d255b310Anders Carlsson Info.EvalResult.DiagExpr = E; 96832fea9d18cc3658a1b01df5ca6f2ac302625c61dChris Lattner } 96954176fdb044312b4b77c3da6682d3575b3728d30Chris Lattner return false; 9707a76778e218da57a3b10c80066a0a938f28987b6Chris Lattner } 9711eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 972f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner //===--------------------------------------------------------------------===// 973f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner // Visitor Methods 974f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner //===--------------------------------------------------------------------===// 9751eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 97632fea9d18cc3658a1b01df5ca6f2ac302625c61dChris Lattner bool VisitStmt(Stmt *) { 97732fea9d18cc3658a1b01df5ca6f2ac302625c61dChris Lattner assert(0 && "This should be called on integers, stmts are not integers"); 97832fea9d18cc3658a1b01df5ca6f2ac302625c61dChris Lattner return false; 97932fea9d18cc3658a1b01df5ca6f2ac302625c61dChris Lattner } 9801eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 98132fea9d18cc3658a1b01df5ca6f2ac302625c61dChris Lattner bool VisitExpr(Expr *E) { 9820e8acbbba71ec6acd5dceb4fcbce63e463e1b755Anders Carlsson return Error(E->getLocStart(), diag::note_invalid_subexpr_in_ice, E); 983f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner } 9841eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 985b542afe02d317411d53b3541946f9f2a8f509a11Chris Lattner bool VisitParenExpr(ParenExpr *E) { return Visit(E->getSubExpr()); } 986f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner 9874c4867e140327fa3b56306fa03c64c8e6a7c95efChris Lattner bool VisitIntegerLiteral(const IntegerLiteral *E) { 988131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar return Success(E->getValue(), E); 9894c4867e140327fa3b56306fa03c64c8e6a7c95efChris Lattner } 9904c4867e140327fa3b56306fa03c64c8e6a7c95efChris Lattner bool VisitCharacterLiteral(const CharacterLiteral *E) { 991131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar return Success(E->getValue(), E); 9924c4867e140327fa3b56306fa03c64c8e6a7c95efChris Lattner } 993043097507f99b1156bfd8bad41e7d5166ae4b9b6Eli Friedman 99456ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall bool VisitOpaqueValueExpr(OpaqueValueExpr *e) { 99556ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall const APValue *value = Info.getOpaqueValue(e); 99656ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall if (!value) { 99756ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall if (e->getSourceExpr()) return Visit(e->getSourceExpr()); 99856ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall return Error(e->getExprLoc(), diag::note_invalid_subexpr_in_ice, e); 99956ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall } 100056ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall return Success(value->getInt(), e); 100156ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall } 100256ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall 1003043097507f99b1156bfd8bad41e7d5166ae4b9b6Eli Friedman bool CheckReferencedDecl(const Expr *E, const Decl *D); 1004043097507f99b1156bfd8bad41e7d5166ae4b9b6Eli Friedman bool VisitDeclRefExpr(const DeclRefExpr *E) { 1005043097507f99b1156bfd8bad41e7d5166ae4b9b6Eli Friedman return CheckReferencedDecl(E, E->getDecl()); 1006043097507f99b1156bfd8bad41e7d5166ae4b9b6Eli Friedman } 1007043097507f99b1156bfd8bad41e7d5166ae4b9b6Eli Friedman bool VisitMemberExpr(const MemberExpr *E) { 1008043097507f99b1156bfd8bad41e7d5166ae4b9b6Eli Friedman if (CheckReferencedDecl(E, E->getMemberDecl())) { 1009043097507f99b1156bfd8bad41e7d5166ae4b9b6Eli Friedman // Conservatively assume a MemberExpr will have side-effects 1010043097507f99b1156bfd8bad41e7d5166ae4b9b6Eli Friedman Info.EvalResult.HasSideEffects = true; 1011043097507f99b1156bfd8bad41e7d5166ae4b9b6Eli Friedman return true; 1012043097507f99b1156bfd8bad41e7d5166ae4b9b6Eli Friedman } 1013043097507f99b1156bfd8bad41e7d5166ae4b9b6Eli Friedman return false; 1014043097507f99b1156bfd8bad41e7d5166ae4b9b6Eli Friedman } 1015043097507f99b1156bfd8bad41e7d5166ae4b9b6Eli Friedman 1016c4a2638b5ef3e2d35d872614ceb655a7a22c58beEli Friedman bool VisitCallExpr(CallExpr *E); 1017b542afe02d317411d53b3541946f9f2a8f509a11Chris Lattner bool VisitBinaryOperator(const BinaryOperator *E); 10188ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor bool VisitOffsetOfExpr(const OffsetOfExpr *E); 1019b542afe02d317411d53b3541946f9f2a8f509a11Chris Lattner bool VisitUnaryOperator(const UnaryOperator *E); 1020ca7c2eaca35edac066ab7cec15f7ecebbb3731d8Nuno Lopes bool VisitConditionalOperator(const ConditionalOperator *E); 102156ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall bool VisitBinaryConditionalOperator(const BinaryConditionalOperator *E); 1022f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner 1023a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar bool VisitCastExpr(CastExpr* E); 1024f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne bool VisitUnaryExprOrTypeTraitExpr(const UnaryExprOrTypeTraitExpr *E); 10250518999d3adcc289997bd974dce90cc97f5c1c44Sebastian Redl 10263068d117951a8df54bae9db039b56201ab10962bAnders Carlsson bool VisitCXXBoolLiteralExpr(const CXXBoolLiteralExpr *E) { 1027131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar return Success(E->getValue(), E); 10283068d117951a8df54bae9db039b56201ab10962bAnders Carlsson } 10291eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 10303f70456b8adb0405ef2a47d51f9fc2d5937ae8aeAnders Carlsson bool VisitGNUNullExpr(const GNUNullExpr *E) { 1031131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar return Success(0, E); 10323f70456b8adb0405ef2a47d51f9fc2d5937ae8aeAnders Carlsson } 10331eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1034ed8abf18329df67b0abcbb3a10458bd8c1d2a595Douglas Gregor bool VisitCXXScalarValueInitExpr(const CXXScalarValueInitExpr *E) { 1035131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar return Success(0, E); 10363068d117951a8df54bae9db039b56201ab10962bAnders Carlsson } 10373068d117951a8df54bae9db039b56201ab10962bAnders Carlsson 1038664a104ba0b8f47b8908ec6af694d9646adba1fcEli Friedman bool VisitImplicitValueInitExpr(const ImplicitValueInitExpr *E) { 1039664a104ba0b8f47b8908ec6af694d9646adba1fcEli Friedman return Success(0, E); 1040664a104ba0b8f47b8908ec6af694d9646adba1fcEli Friedman } 1041664a104ba0b8f47b8908ec6af694d9646adba1fcEli Friedman 104264b45f7e0d3167f040841ac2920aead7f080730dSebastian Redl bool VisitUnaryTypeTraitExpr(const UnaryTypeTraitExpr *E) { 10430dfd848fa4c9664852ba8c929a8bd3fce93ddca2Sebastian Redl return Success(E->getValue(), E); 104464b45f7e0d3167f040841ac2920aead7f080730dSebastian Redl } 104564b45f7e0d3167f040841ac2920aead7f080730dSebastian Redl 10466ad6f2848d7652ab2991286eb48be440d3493b28Francois Pichet bool VisitBinaryTypeTraitExpr(const BinaryTypeTraitExpr *E) { 10476ad6f2848d7652ab2991286eb48be440d3493b28Francois Pichet return Success(E->getValue(), E); 10486ad6f2848d7652ab2991286eb48be440d3493b28Francois Pichet } 10496ad6f2848d7652ab2991286eb48be440d3493b28Francois Pichet 1050ba98d6bb414861965a1f22628494ea046785ecd4Eli Friedman bool VisitChooseExpr(const ChooseExpr *E) { 1051ba98d6bb414861965a1f22628494ea046785ecd4Eli Friedman return Visit(E->getChosenSubExpr(Info.Ctx)); 1052ba98d6bb414861965a1f22628494ea046785ecd4Eli Friedman } 1053ba98d6bb414861965a1f22628494ea046785ecd4Eli Friedman 1054722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman bool VisitUnaryReal(const UnaryOperator *E); 1055664a104ba0b8f47b8908ec6af694d9646adba1fcEli Friedman bool VisitUnaryImag(const UnaryOperator *E); 1056664a104ba0b8f47b8908ec6af694d9646adba1fcEli Friedman 1057295995c9c3196416372c9cd35d9cedb6da37bd3dSebastian Redl bool VisitCXXNoexceptExpr(const CXXNoexceptExpr *E); 1058ee8aff06f6a96214731de17b2cb6df407c6c1820Douglas Gregor bool VisitSizeOfPackExpr(const SizeOfPackExpr *E); 1059ee8aff06f6a96214731de17b2cb6df407c6c1820Douglas Gregor 1060fcee0019b76f9f368f2b3d6d4048a98232593f29Chris Lattnerprivate: 10618b752f10c394b140f9ef89e049cbad1a7676fc25Ken Dyck CharUnits GetAlignOfExpr(const Expr *E); 10628b752f10c394b140f9ef89e049cbad1a7676fc25Ken Dyck CharUnits GetAlignOfType(QualType T); 106342c8f87eb60958170c46767273bf93e6c96125bfJohn McCall static QualType GetObjectType(const Expr *E); 106442c8f87eb60958170c46767273bf93e6c96125bfJohn McCall bool TryEvaluateBuiltinObjectSize(CallExpr *E); 1065664a104ba0b8f47b8908ec6af694d9646adba1fcEli Friedman // FIXME: Missing: array subscript of vector, member of vector 1066f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner}; 1067f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner} // end anonymous namespace 1068f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner 106969ab26a8623141f35e86817cfc6e0fbe7639a40fDaniel Dunbarstatic bool EvaluateIntegerOrLValue(const Expr* E, APValue &Result, EvalInfo &Info) { 10702ade35e2cfd554e49d35a52047cea98a82787af9Douglas Gregor assert(E->getType()->isIntegralOrEnumerationType()); 107169ab26a8623141f35e86817cfc6e0fbe7639a40fDaniel Dunbar return IntExprEvaluator(Info, Result).Visit(const_cast<Expr*>(E)); 107269ab26a8623141f35e86817cfc6e0fbe7639a40fDaniel Dunbar} 107369ab26a8623141f35e86817cfc6e0fbe7639a40fDaniel Dunbar 107469ab26a8623141f35e86817cfc6e0fbe7639a40fDaniel Dunbarstatic bool EvaluateInteger(const Expr* E, APSInt &Result, EvalInfo &Info) { 10752ade35e2cfd554e49d35a52047cea98a82787af9Douglas Gregor assert(E->getType()->isIntegralOrEnumerationType()); 10767db7acbbb84b82d0522266a50ebabc3a52a9e5d1John McCall 107730c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar APValue Val; 107869ab26a8623141f35e86817cfc6e0fbe7639a40fDaniel Dunbar if (!EvaluateIntegerOrLValue(E, Val, Info) || !Val.isInt()) 107930c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar return false; 108030c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar Result = Val.getInt(); 108130c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar return true; 1082f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner} 1083f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner 1084043097507f99b1156bfd8bad41e7d5166ae4b9b6Eli Friedmanbool IntExprEvaluator::CheckReferencedDecl(const Expr* E, const Decl* D) { 10854c4867e140327fa3b56306fa03c64c8e6a7c95efChris Lattner // Enums are integer constant exprs. 108629a7f3342c3c6dd15d914c61ae22246c36d51ce7Eli Friedman if (const EnumConstantDecl *ECD = dyn_cast<EnumConstantDecl>(D)) 108729a7f3342c3c6dd15d914c61ae22246c36d51ce7Eli Friedman return Success(ECD->getInitVal(), E); 1088b2bc62bd35129f09d0746ef6a5ef4dc392b6d6e1Sebastian Redl 1089b2bc62bd35129f09d0746ef6a5ef4dc392b6d6e1Sebastian Redl // In C++, const, non-volatile integers initialized with ICEs are ICEs. 1090e1646da3bb0fe97b372e5fe8cefc537b22048fc4Eli Friedman // In C, they can also be folded, although they are not ICEs. 1091cf3293eaeb3853d12cff47e648bbe835004e929fDouglas Gregor if (Info.Ctx.getCanonicalType(E->getType()).getCVRQualifiers() 1092cf3293eaeb3853d12cff47e648bbe835004e929fDouglas Gregor == Qualifiers::Const) { 1093f6b6025a4e26bb0295a57e0efece73253038f278Anders Carlsson 1094f6b6025a4e26bb0295a57e0efece73253038f278Anders Carlsson if (isa<ParmVarDecl>(D)) 1095f6b6025a4e26bb0295a57e0efece73253038f278Anders Carlsson return Error(E->getLocStart(), diag::note_invalid_subexpr_in_ice, E); 1096f6b6025a4e26bb0295a57e0efece73253038f278Anders Carlsson 1097043097507f99b1156bfd8bad41e7d5166ae4b9b6Eli Friedman if (const VarDecl *VD = dyn_cast<VarDecl>(D)) { 109831310a21fb2a9f13950f864f681c86080b05d5b2Sebastian Redl if (const Expr *Init = VD->getAnyInitializer()) { 1099c013118155077cf8bdaef743c5dbce760114eed3Eli Friedman if (APValue *V = VD->getEvaluatedValue()) { 1100c013118155077cf8bdaef743c5dbce760114eed3Eli Friedman if (V->isInt()) 1101c013118155077cf8bdaef743c5dbce760114eed3Eli Friedman return Success(V->getInt(), E); 1102c013118155077cf8bdaef743c5dbce760114eed3Eli Friedman return Error(E->getLocStart(), diag::note_invalid_subexpr_in_ice, E); 1103c013118155077cf8bdaef743c5dbce760114eed3Eli Friedman } 1104c013118155077cf8bdaef743c5dbce760114eed3Eli Friedman 1105c013118155077cf8bdaef743c5dbce760114eed3Eli Friedman if (VD->isEvaluatingValue()) 1106c013118155077cf8bdaef743c5dbce760114eed3Eli Friedman return Error(E->getLocStart(), diag::note_invalid_subexpr_in_ice, E); 1107c013118155077cf8bdaef743c5dbce760114eed3Eli Friedman 1108c013118155077cf8bdaef743c5dbce760114eed3Eli Friedman VD->setEvaluatingValue(); 1109c013118155077cf8bdaef743c5dbce760114eed3Eli Friedman 1110a7dedf7004e8ac3f947d6817370b2778fa648c2bEli Friedman Expr::EvalResult EResult; 1111a7dedf7004e8ac3f947d6817370b2778fa648c2bEli Friedman if (Init->Evaluate(EResult, Info.Ctx) && !EResult.HasSideEffects && 1112a7dedf7004e8ac3f947d6817370b2778fa648c2bEli Friedman EResult.Val.isInt()) { 111378d1583d0b36b7d6d8d10234cdc19ab94adf765aDouglas Gregor // Cache the evaluated value in the variable declaration. 1114a7dedf7004e8ac3f947d6817370b2778fa648c2bEli Friedman Result = EResult.Val; 1115c013118155077cf8bdaef743c5dbce760114eed3Eli Friedman VD->setEvaluatedValue(Result); 111678d1583d0b36b7d6d8d10234cdc19ab94adf765aDouglas Gregor return true; 111778d1583d0b36b7d6d8d10234cdc19ab94adf765aDouglas Gregor } 111878d1583d0b36b7d6d8d10234cdc19ab94adf765aDouglas Gregor 1119c013118155077cf8bdaef743c5dbce760114eed3Eli Friedman VD->setEvaluatedValue(APValue()); 112078d1583d0b36b7d6d8d10234cdc19ab94adf765aDouglas Gregor } 1121b2bc62bd35129f09d0746ef6a5ef4dc392b6d6e1Sebastian Redl } 1122b2bc62bd35129f09d0746ef6a5ef4dc392b6d6e1Sebastian Redl } 1123b2bc62bd35129f09d0746ef6a5ef4dc392b6d6e1Sebastian Redl 11244c4867e140327fa3b56306fa03c64c8e6a7c95efChris Lattner // Otherwise, random variable references are not constants. 11250e8acbbba71ec6acd5dceb4fcbce63e463e1b755Anders Carlsson return Error(E->getLocStart(), diag::note_invalid_subexpr_in_ice, E); 11264c4867e140327fa3b56306fa03c64c8e6a7c95efChris Lattner} 11274c4867e140327fa3b56306fa03c64c8e6a7c95efChris Lattner 1128a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner/// EvaluateBuiltinClassifyType - Evaluate __builtin_classify_type the same way 1129a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner/// as GCC. 1130a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattnerstatic int EvaluateBuiltinClassifyType(const CallExpr *E) { 1131a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner // The following enum mimics the values returned by GCC. 11327c80bd64032e610c0dbd74fc0ef6ea334447f2fdSebastian Redl // FIXME: Does GCC differ between lvalue and rvalue references here? 1133a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner enum gcc_type_class { 1134a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner no_type_class = -1, 1135a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner void_type_class, integer_type_class, char_type_class, 1136a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner enumeral_type_class, boolean_type_class, 1137a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner pointer_type_class, reference_type_class, offset_type_class, 1138a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner real_type_class, complex_type_class, 1139a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner function_type_class, method_type_class, 1140a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner record_type_class, union_type_class, 1141a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner array_type_class, string_type_class, 1142a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner lang_type_class 1143a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner }; 11441eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 11451eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump // If no argument was supplied, default to "no_type_class". This isn't 1146a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner // ideal, however it is what gcc does. 1147a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner if (E->getNumArgs() == 0) 1148a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner return no_type_class; 11491eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1150a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner QualType ArgTy = E->getArg(0)->getType(); 1151a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner if (ArgTy->isVoidType()) 1152a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner return void_type_class; 1153a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner else if (ArgTy->isEnumeralType()) 1154a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner return enumeral_type_class; 1155a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner else if (ArgTy->isBooleanType()) 1156a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner return boolean_type_class; 1157a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner else if (ArgTy->isCharType()) 1158a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner return string_type_class; // gcc doesn't appear to use char_type_class 1159a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner else if (ArgTy->isIntegerType()) 1160a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner return integer_type_class; 1161a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner else if (ArgTy->isPointerType()) 1162a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner return pointer_type_class; 1163a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner else if (ArgTy->isReferenceType()) 1164a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner return reference_type_class; 1165a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner else if (ArgTy->isRealType()) 1166a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner return real_type_class; 1167a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner else if (ArgTy->isComplexType()) 1168a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner return complex_type_class; 1169a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner else if (ArgTy->isFunctionType()) 1170a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner return function_type_class; 1171fb87b89fc9eb103e19fb8e4b925c23f0bd091b99Douglas Gregor else if (ArgTy->isStructureOrClassType()) 1172a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner return record_type_class; 1173a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner else if (ArgTy->isUnionType()) 1174a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner return union_type_class; 1175a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner else if (ArgTy->isArrayType()) 1176a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner return array_type_class; 1177a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner else if (ArgTy->isUnionType()) 1178a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner return union_type_class; 1179a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner else // FIXME: offset_type_class, method_type_class, & lang_type_class? 1180a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner assert(0 && "CallExpr::isBuiltinClassifyType(): unimplemented type"); 1181a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner return -1; 1182a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner} 1183a4d55d89c8076b402bb168e3edeef0c2cd2a78c3Chris Lattner 118442c8f87eb60958170c46767273bf93e6c96125bfJohn McCall/// Retrieves the "underlying object type" of the given expression, 118542c8f87eb60958170c46767273bf93e6c96125bfJohn McCall/// as used by __builtin_object_size. 118642c8f87eb60958170c46767273bf93e6c96125bfJohn McCallQualType IntExprEvaluator::GetObjectType(const Expr *E) { 118742c8f87eb60958170c46767273bf93e6c96125bfJohn McCall if (const DeclRefExpr *DRE = dyn_cast<DeclRefExpr>(E)) { 118842c8f87eb60958170c46767273bf93e6c96125bfJohn McCall if (const VarDecl *VD = dyn_cast<VarDecl>(DRE->getDecl())) 118942c8f87eb60958170c46767273bf93e6c96125bfJohn McCall return VD->getType(); 119042c8f87eb60958170c46767273bf93e6c96125bfJohn McCall } else if (isa<CompoundLiteralExpr>(E)) { 119142c8f87eb60958170c46767273bf93e6c96125bfJohn McCall return E->getType(); 119242c8f87eb60958170c46767273bf93e6c96125bfJohn McCall } 119342c8f87eb60958170c46767273bf93e6c96125bfJohn McCall 119442c8f87eb60958170c46767273bf93e6c96125bfJohn McCall return QualType(); 119542c8f87eb60958170c46767273bf93e6c96125bfJohn McCall} 119642c8f87eb60958170c46767273bf93e6c96125bfJohn McCall 119742c8f87eb60958170c46767273bf93e6c96125bfJohn McCallbool IntExprEvaluator::TryEvaluateBuiltinObjectSize(CallExpr *E) { 119842c8f87eb60958170c46767273bf93e6c96125bfJohn McCall // TODO: Perhaps we should let LLVM lower this? 119942c8f87eb60958170c46767273bf93e6c96125bfJohn McCall LValue Base; 120042c8f87eb60958170c46767273bf93e6c96125bfJohn McCall if (!EvaluatePointer(E->getArg(0), Base, Info)) 120142c8f87eb60958170c46767273bf93e6c96125bfJohn McCall return false; 120242c8f87eb60958170c46767273bf93e6c96125bfJohn McCall 120342c8f87eb60958170c46767273bf93e6c96125bfJohn McCall // If we can prove the base is null, lower to zero now. 120442c8f87eb60958170c46767273bf93e6c96125bfJohn McCall const Expr *LVBase = Base.getLValueBase(); 120542c8f87eb60958170c46767273bf93e6c96125bfJohn McCall if (!LVBase) return Success(0, E); 120642c8f87eb60958170c46767273bf93e6c96125bfJohn McCall 120742c8f87eb60958170c46767273bf93e6c96125bfJohn McCall QualType T = GetObjectType(LVBase); 120842c8f87eb60958170c46767273bf93e6c96125bfJohn McCall if (T.isNull() || 120942c8f87eb60958170c46767273bf93e6c96125bfJohn McCall T->isIncompleteType() || 12101357869bc5983cdfbc986db1f3d18265bb34cb0eEli Friedman T->isFunctionType() || 121142c8f87eb60958170c46767273bf93e6c96125bfJohn McCall T->isVariablyModifiedType() || 121242c8f87eb60958170c46767273bf93e6c96125bfJohn McCall T->isDependentType()) 121342c8f87eb60958170c46767273bf93e6c96125bfJohn McCall return false; 121442c8f87eb60958170c46767273bf93e6c96125bfJohn McCall 121542c8f87eb60958170c46767273bf93e6c96125bfJohn McCall CharUnits Size = Info.Ctx.getTypeSizeInChars(T); 121642c8f87eb60958170c46767273bf93e6c96125bfJohn McCall CharUnits Offset = Base.getLValueOffset(); 121742c8f87eb60958170c46767273bf93e6c96125bfJohn McCall 121842c8f87eb60958170c46767273bf93e6c96125bfJohn McCall if (!Offset.isNegative() && Offset <= Size) 121942c8f87eb60958170c46767273bf93e6c96125bfJohn McCall Size -= Offset; 122042c8f87eb60958170c46767273bf93e6c96125bfJohn McCall else 122142c8f87eb60958170c46767273bf93e6c96125bfJohn McCall Size = CharUnits::Zero(); 12224f3bc8f7aa90b72832b03bee9201c98f4bb6b4d1Ken Dyck return Success(Size, E); 122342c8f87eb60958170c46767273bf93e6c96125bfJohn McCall} 122442c8f87eb60958170c46767273bf93e6c96125bfJohn McCall 1225c4a2638b5ef3e2d35d872614ceb655a7a22c58beEli Friedmanbool IntExprEvaluator::VisitCallExpr(CallExpr *E) { 12263c385e5f8d9008fff18597ca302be19fa86e51f6Douglas Gregor switch (E->isBuiltinCall(Info.Ctx)) { 1227019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner default: 12280e8acbbba71ec6acd5dceb4fcbce63e463e1b755Anders Carlsson return Error(E->getLocStart(), diag::note_invalid_subexpr_in_ice, E); 122964eda9e50b593f935c95bd1edc98c4bfda03f601Mike Stump 123064eda9e50b593f935c95bd1edc98c4bfda03f601Mike Stump case Builtin::BI__builtin_object_size: { 123142c8f87eb60958170c46767273bf93e6c96125bfJohn McCall if (TryEvaluateBuiltinObjectSize(E)) 123242c8f87eb60958170c46767273bf93e6c96125bfJohn McCall return true; 123364eda9e50b593f935c95bd1edc98c4bfda03f601Mike Stump 1234b2aaf51ed73a4774322a39a0dd59d0fe7e3258c0Eric Christopher // If evaluating the argument has side-effects we can't determine 1235b2aaf51ed73a4774322a39a0dd59d0fe7e3258c0Eric Christopher // the size of the object and lower it to unknown now. 1236393c247fe025ccb5f914e37e948192ea86faef8cFariborz Jahanian if (E->getArg(0)->HasSideEffects(Info.Ctx)) { 12373f27b384801de26ce7efaa395699b42719372f24Benjamin Kramer if (E->getArg(1)->EvaluateAsInt(Info.Ctx).getZExtValue() <= 1) 1238cf184655319cf7a5b811067cff9d26a5741fd161Chris Lattner return Success(-1ULL, E); 123964eda9e50b593f935c95bd1edc98c4bfda03f601Mike Stump return Success(0, E); 124064eda9e50b593f935c95bd1edc98c4bfda03f601Mike Stump } 1241c4c9045dabfc0f0d37dea1b3eb2992654d5b2db1Mike Stump 124264eda9e50b593f935c95bd1edc98c4bfda03f601Mike Stump return Error(E->getLocStart(), diag::note_invalid_subexpr_in_ice, E); 124364eda9e50b593f935c95bd1edc98c4bfda03f601Mike Stump } 124464eda9e50b593f935c95bd1edc98c4bfda03f601Mike Stump 1245019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner case Builtin::BI__builtin_classify_type: 1246131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar return Success(EvaluateBuiltinClassifyType(E), E); 12471eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 12484bbc0e05a714d4ee4918a92a4a7049dd6ef33ad0Anders Carlsson case Builtin::BI__builtin_constant_p: 1249019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner // __builtin_constant_p always has one operand: it returns true if that 1250019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner // operand can be folded, false otherwise. 1251131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar return Success(E->getArg(0)->isEvaluatable(Info.Ctx), E); 125221fb98ee003e992b0c4e204d98a19e0ef544cae3Chris Lattner 125321fb98ee003e992b0c4e204d98a19e0ef544cae3Chris Lattner case Builtin::BI__builtin_eh_return_data_regno: { 125421fb98ee003e992b0c4e204d98a19e0ef544cae3Chris Lattner int Operand = E->getArg(0)->EvaluateAsInt(Info.Ctx).getZExtValue(); 125521fb98ee003e992b0c4e204d98a19e0ef544cae3Chris Lattner Operand = Info.Ctx.Target.getEHDataRegisterNumber(Operand); 125621fb98ee003e992b0c4e204d98a19e0ef544cae3Chris Lattner return Success(Operand, E); 125721fb98ee003e992b0c4e204d98a19e0ef544cae3Chris Lattner } 1258c4a2638b5ef3e2d35d872614ceb655a7a22c58beEli Friedman 1259c4a2638b5ef3e2d35d872614ceb655a7a22c58beEli Friedman case Builtin::BI__builtin_expect: 1260c4a2638b5ef3e2d35d872614ceb655a7a22c58beEli Friedman return Visit(E->getArg(0)); 12615726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor 12625726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor case Builtin::BIstrlen: 12635726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor case Builtin::BI__builtin_strlen: 12645726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor // As an extension, we support strlen() and __builtin_strlen() as constant 12655726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor // expressions when the argument is a string literal. 12665726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor if (StringLiteral *S 12675726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor = dyn_cast<StringLiteral>(E->getArg(0)->IgnoreParenImpCasts())) { 12685726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor // The string literal may have embedded null characters. Find the first 12695726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor // one and truncate there. 12705726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor llvm::StringRef Str = S->getString(); 12715726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor llvm::StringRef::size_type Pos = Str.find(0); 12725726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor if (Pos != llvm::StringRef::npos) 12735726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor Str = Str.substr(0, Pos); 12745726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor 12755726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor return Success(Str.size(), E); 12765726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor } 12775726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor 12785726d405e71f11feaaf0c8f518abe26e909537a4Douglas Gregor return Error(E->getLocStart(), diag::note_invalid_subexpr_in_ice, E); 1279019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner } 12804c4867e140327fa3b56306fa03c64c8e6a7c95efChris Lattner} 1281f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner 1282b542afe02d317411d53b3541946f9f2a8f509a11Chris Lattnerbool IntExprEvaluator::VisitBinaryOperator(const BinaryOperator *E) { 12832de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall if (E->getOpcode() == BO_Comma) { 1284027f62ec1860f4ab0c91bd863b238938880b8102Anders Carlsson if (!Visit(E->getRHS())) 1285027f62ec1860f4ab0c91bd863b238938880b8102Anders Carlsson return false; 12864fdfb0965b396f2778091f7e6c051d17ff9791baAnders Carlsson 128733ef1456a19779fb15c51aea362bd9c7cb4087f3Eli Friedman // If we can't evaluate the LHS, it might have side effects; 128833ef1456a19779fb15c51aea362bd9c7cb4087f3Eli Friedman // conservatively mark it. 128933ef1456a19779fb15c51aea362bd9c7cb4087f3Eli Friedman if (!E->getLHS()->isEvaluatable(Info.Ctx)) 129033ef1456a19779fb15c51aea362bd9c7cb4087f3Eli Friedman Info.EvalResult.HasSideEffects = true; 1291c8cc9ccc7b87a7ed1749b074f6b670bcec49abc1Chris Lattner 1292027f62ec1860f4ab0c91bd863b238938880b8102Anders Carlsson return true; 1293a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman } 1294a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman 1295a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman if (E->isLogicalOp()) { 1296a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman // These need to be handled specially because the operands aren't 1297a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman // necessarily integral 1298fcb4d09531abbf2a5cf398c2f946fb3bc2875f64Anders Carlsson bool lhsResult, rhsResult; 12991eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1300fcb4d09531abbf2a5cf398c2f946fb3bc2875f64Anders Carlsson if (HandleConversionToBool(E->getLHS(), lhsResult, Info)) { 130151fe996231b1d7199f76e4005ff4c943d5deeecdAnders Carlsson // We were able to evaluate the LHS, see if we can get away with not 130251fe996231b1d7199f76e4005ff4c943d5deeecdAnders Carlsson // evaluating the RHS: 0 && X -> 0, 1 || X -> 1 13032de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall if (lhsResult == (E->getOpcode() == BO_LOr)) 13043f7d995390009fede92b333a040da80e1ce90997Daniel Dunbar return Success(lhsResult, E); 1305a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman 1306fcb4d09531abbf2a5cf398c2f946fb3bc2875f64Anders Carlsson if (HandleConversionToBool(E->getRHS(), rhsResult, Info)) { 13072de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall if (E->getOpcode() == BO_LOr) 1308131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar return Success(lhsResult || rhsResult, E); 13094bbc0e05a714d4ee4918a92a4a7049dd6ef33ad0Anders Carlsson else 1310131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar return Success(lhsResult && rhsResult, E); 13114bbc0e05a714d4ee4918a92a4a7049dd6ef33ad0Anders Carlsson } 13124bbc0e05a714d4ee4918a92a4a7049dd6ef33ad0Anders Carlsson } else { 1313fcb4d09531abbf2a5cf398c2f946fb3bc2875f64Anders Carlsson if (HandleConversionToBool(E->getRHS(), rhsResult, Info)) { 13144bbc0e05a714d4ee4918a92a4a7049dd6ef33ad0Anders Carlsson // We can't evaluate the LHS; however, sometimes the result 13154bbc0e05a714d4ee4918a92a4a7049dd6ef33ad0Anders Carlsson // is determined by the RHS: X && 0 -> 0, X || 1 -> 1. 13162de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall if (rhsResult == (E->getOpcode() == BO_LOr) || 13172de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall !rhsResult == (E->getOpcode() == BO_LAnd)) { 1318131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar // Since we weren't able to evaluate the left hand side, it 1319fcb4d09531abbf2a5cf398c2f946fb3bc2875f64Anders Carlsson // must have had side effects. 1320fcb4d09531abbf2a5cf398c2f946fb3bc2875f64Anders Carlsson Info.EvalResult.HasSideEffects = true; 1321131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar 1322131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar return Success(rhsResult, E); 13234bbc0e05a714d4ee4918a92a4a7049dd6ef33ad0Anders Carlsson } 13244bbc0e05a714d4ee4918a92a4a7049dd6ef33ad0Anders Carlsson } 1325a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman } 1326a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman 1327a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman return false; 1328c8cc9ccc7b87a7ed1749b074f6b670bcec49abc1Chris Lattner } 132954176fdb044312b4b77c3da6682d3575b3728d30Chris Lattner 1330286f85e791dda3634fee7f6c67f0ed92296c028fAnders Carlsson QualType LHSTy = E->getLHS()->getType(); 1331286f85e791dda3634fee7f6c67f0ed92296c028fAnders Carlsson QualType RHSTy = E->getRHS()->getType(); 13324087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar 13334087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar if (LHSTy->isAnyComplexType()) { 13344087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar assert(RHSTy->isAnyComplexType() && "Invalid comparison"); 1335f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall ComplexValue LHS, RHS; 13364087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar 13374087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar if (!EvaluateComplex(E->getLHS(), LHS, Info)) 13384087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar return false; 13394087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar 13404087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar if (!EvaluateComplex(E->getRHS(), RHS, Info)) 13414087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar return false; 13424087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar 13434087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar if (LHS.isComplexFloat()) { 13441eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump APFloat::cmpResult CR_r = 13454087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar LHS.getComplexFloatReal().compare(RHS.getComplexFloatReal()); 13461eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump APFloat::cmpResult CR_i = 13474087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar LHS.getComplexFloatImag().compare(RHS.getComplexFloatImag()); 13484087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar 13492de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall if (E->getOpcode() == BO_EQ) 1350131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar return Success((CR_r == APFloat::cmpEqual && 1351131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar CR_i == APFloat::cmpEqual), E); 1352131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar else { 13532de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall assert(E->getOpcode() == BO_NE && 1354131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar "Invalid complex comparison."); 13551eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump return Success(((CR_r == APFloat::cmpGreaterThan || 1356fc39dc4c7886723310419b1869cf651ca55b7af4Mon P Wang CR_r == APFloat::cmpLessThan || 1357fc39dc4c7886723310419b1869cf651ca55b7af4Mon P Wang CR_r == APFloat::cmpUnordered) || 13581eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump (CR_i == APFloat::cmpGreaterThan || 1359fc39dc4c7886723310419b1869cf651ca55b7af4Mon P Wang CR_i == APFloat::cmpLessThan || 1360fc39dc4c7886723310419b1869cf651ca55b7af4Mon P Wang CR_i == APFloat::cmpUnordered)), E); 1361131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar } 13624087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar } else { 13632de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall if (E->getOpcode() == BO_EQ) 1364131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar return Success((LHS.getComplexIntReal() == RHS.getComplexIntReal() && 1365131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar LHS.getComplexIntImag() == RHS.getComplexIntImag()), E); 1366131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar else { 13672de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall assert(E->getOpcode() == BO_NE && 1368131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar "Invalid compex comparison."); 1369131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar return Success((LHS.getComplexIntReal() != RHS.getComplexIntReal() || 1370131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar LHS.getComplexIntImag() != RHS.getComplexIntImag()), E); 1371131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar } 13724087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar } 13734087e24f73d05d96ac2d259679751d054d3ddfbcDaniel Dunbar } 13741eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1375286f85e791dda3634fee7f6c67f0ed92296c028fAnders Carlsson if (LHSTy->isRealFloatingType() && 1376286f85e791dda3634fee7f6c67f0ed92296c028fAnders Carlsson RHSTy->isRealFloatingType()) { 1377286f85e791dda3634fee7f6c67f0ed92296c028fAnders Carlsson APFloat RHS(0.0), LHS(0.0); 13781eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1379286f85e791dda3634fee7f6c67f0ed92296c028fAnders Carlsson if (!EvaluateFloat(E->getRHS(), RHS, Info)) 1380286f85e791dda3634fee7f6c67f0ed92296c028fAnders Carlsson return false; 13811eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1382286f85e791dda3634fee7f6c67f0ed92296c028fAnders Carlsson if (!EvaluateFloat(E->getLHS(), LHS, Info)) 1383286f85e791dda3634fee7f6c67f0ed92296c028fAnders Carlsson return false; 13841eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1385286f85e791dda3634fee7f6c67f0ed92296c028fAnders Carlsson APFloat::cmpResult CR = LHS.compare(RHS); 1386529569e68d10b0fd3750fd2124faf742249b846bAnders Carlsson 1387286f85e791dda3634fee7f6c67f0ed92296c028fAnders Carlsson switch (E->getOpcode()) { 1388286f85e791dda3634fee7f6c67f0ed92296c028fAnders Carlsson default: 1389286f85e791dda3634fee7f6c67f0ed92296c028fAnders Carlsson assert(0 && "Invalid binary operator!"); 13902de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_LT: 1391131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar return Success(CR == APFloat::cmpLessThan, E); 13922de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_GT: 1393131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar return Success(CR == APFloat::cmpGreaterThan, E); 13942de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_LE: 1395131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar return Success(CR == APFloat::cmpLessThan || CR == APFloat::cmpEqual, E); 13962de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_GE: 13971eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump return Success(CR == APFloat::cmpGreaterThan || CR == APFloat::cmpEqual, 1398131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar E); 13992de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_EQ: 1400131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar return Success(CR == APFloat::cmpEqual, E); 14012de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_NE: 14021eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump return Success(CR == APFloat::cmpGreaterThan 1403fc39dc4c7886723310419b1869cf651ca55b7af4Mon P Wang || CR == APFloat::cmpLessThan 1404fc39dc4c7886723310419b1869cf651ca55b7af4Mon P Wang || CR == APFloat::cmpUnordered, E); 1405286f85e791dda3634fee7f6c67f0ed92296c028fAnders Carlsson } 1406286f85e791dda3634fee7f6c67f0ed92296c028fAnders Carlsson } 14071eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1408ad02d7debd03ff275ac8ea27891a4ecccdb78068Eli Friedman if (LHSTy->isPointerType() && RHSTy->isPointerType()) { 14092de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall if (E->getOpcode() == BO_Sub || E->isEqualityOp()) { 1410efdb83e26f9a1fd2566afe54461216cd84814d42John McCall LValue LHSValue; 14113068d117951a8df54bae9db039b56201ab10962bAnders Carlsson if (!EvaluatePointer(E->getLHS(), LHSValue, Info)) 14123068d117951a8df54bae9db039b56201ab10962bAnders Carlsson return false; 1413a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman 1414efdb83e26f9a1fd2566afe54461216cd84814d42John McCall LValue RHSValue; 14153068d117951a8df54bae9db039b56201ab10962bAnders Carlsson if (!EvaluatePointer(E->getRHS(), RHSValue, Info)) 14163068d117951a8df54bae9db039b56201ab10962bAnders Carlsson return false; 1417a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman 14185bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman // Reject any bases from the normal codepath; we special-case comparisons 14195bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman // to null. 14205bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman if (LHSValue.getLValueBase()) { 14215bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman if (!E->isEqualityOp()) 14225bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman return false; 1423a73058324197b7bdfd19307965954f626e26199dKen Dyck if (RHSValue.getLValueBase() || !RHSValue.getLValueOffset().isZero()) 14245bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman return false; 14255bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman bool bres; 14265bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman if (!EvalPointerValueAsBool(LHSValue, bres)) 14275bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman return false; 14282de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall return Success(bres ^ (E->getOpcode() == BO_EQ), E); 14295bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman } else if (RHSValue.getLValueBase()) { 14305bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman if (!E->isEqualityOp()) 14315bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman return false; 1432a73058324197b7bdfd19307965954f626e26199dKen Dyck if (LHSValue.getLValueBase() || !LHSValue.getLValueOffset().isZero()) 14335bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman return false; 14345bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman bool bres; 14355bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman if (!EvalPointerValueAsBool(RHSValue, bres)) 14365bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman return false; 14372de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall return Success(bres ^ (E->getOpcode() == BO_EQ), E); 14385bc86103767c2abcbfdd6518e0ccbbbb6aa59e0fEli Friedman } 1439a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman 14402de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall if (E->getOpcode() == BO_Sub) { 14414992bdde387c5f033bb450a716eaabc0fda52688Chris Lattner QualType Type = E->getLHS()->getType(); 14424992bdde387c5f033bb450a716eaabc0fda52688Chris Lattner QualType ElementType = Type->getAs<PointerType>()->getPointeeType(); 14433068d117951a8df54bae9db039b56201ab10962bAnders Carlsson 1444a73058324197b7bdfd19307965954f626e26199dKen Dyck CharUnits ElementSize = CharUnits::One(); 1445ce1bca73aef9bbf6359ab8420278203dda81a054Eli Friedman if (!ElementType->isVoidType() && !ElementType->isFunctionType()) 1446a73058324197b7bdfd19307965954f626e26199dKen Dyck ElementSize = Info.Ctx.getTypeSizeInChars(ElementType); 1447a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman 1448a73058324197b7bdfd19307965954f626e26199dKen Dyck CharUnits Diff = LHSValue.getLValueOffset() - 1449a73058324197b7bdfd19307965954f626e26199dKen Dyck RHSValue.getLValueOffset(); 1450a73058324197b7bdfd19307965954f626e26199dKen Dyck return Success(Diff / ElementSize, E); 1451ad02d7debd03ff275ac8ea27891a4ecccdb78068Eli Friedman } 1452ad02d7debd03ff275ac8ea27891a4ecccdb78068Eli Friedman bool Result; 14532de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall if (E->getOpcode() == BO_EQ) { 1454ad02d7debd03ff275ac8ea27891a4ecccdb78068Eli Friedman Result = LHSValue.getLValueOffset() == RHSValue.getLValueOffset(); 1455267c0ab1b9a15768f3f15abbfc40ce344751c78bEli Friedman } else { 1456ad02d7debd03ff275ac8ea27891a4ecccdb78068Eli Friedman Result = LHSValue.getLValueOffset() != RHSValue.getLValueOffset(); 1457ad02d7debd03ff275ac8ea27891a4ecccdb78068Eli Friedman } 1458ad02d7debd03ff275ac8ea27891a4ecccdb78068Eli Friedman return Success(Result, E); 14593068d117951a8df54bae9db039b56201ab10962bAnders Carlsson } 14603068d117951a8df54bae9db039b56201ab10962bAnders Carlsson } 14612ade35e2cfd554e49d35a52047cea98a82787af9Douglas Gregor if (!LHSTy->isIntegralOrEnumerationType() || 14622ade35e2cfd554e49d35a52047cea98a82787af9Douglas Gregor !RHSTy->isIntegralOrEnumerationType()) { 1463a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman // We can't continue from here for non-integral types, and they 1464a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman // could potentially confuse the following operations. 1465a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman return false; 1466a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman } 1467a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman 1468a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman // The LHS of a constant expr is always evaluated and needed. 146930c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar if (!Visit(E->getLHS())) 1470a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman return false; // error in subexpression. 1471d9f4bcda18bfbf79341edd9d381d4b6a3cffe655Eli Friedman 147242edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman APValue RHSVal; 147342edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman if (!EvaluateIntegerOrLValue(E->getRHS(), RHSVal, Info)) 147430c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar return false; 147542edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman 147642edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman // Handle cases like (unsigned long)&a + 4. 147742edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman if (E->isAdditiveOp() && Result.isLValue() && RHSVal.isInt()) { 1478a73058324197b7bdfd19307965954f626e26199dKen Dyck CharUnits Offset = Result.getLValueOffset(); 1479a73058324197b7bdfd19307965954f626e26199dKen Dyck CharUnits AdditionalOffset = CharUnits::fromQuantity( 1480a73058324197b7bdfd19307965954f626e26199dKen Dyck RHSVal.getInt().getZExtValue()); 14812de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall if (E->getOpcode() == BO_Add) 1482a73058324197b7bdfd19307965954f626e26199dKen Dyck Offset += AdditionalOffset; 148342edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman else 1484a73058324197b7bdfd19307965954f626e26199dKen Dyck Offset -= AdditionalOffset; 1485a73058324197b7bdfd19307965954f626e26199dKen Dyck Result = APValue(Result.getLValueBase(), Offset); 148642edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman return true; 148742edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman } 148842edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman 148942edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman // Handle cases like 4 + (unsigned long)&a 14902de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall if (E->getOpcode() == BO_Add && 149142edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman RHSVal.isLValue() && Result.isInt()) { 1492a73058324197b7bdfd19307965954f626e26199dKen Dyck CharUnits Offset = RHSVal.getLValueOffset(); 1493a73058324197b7bdfd19307965954f626e26199dKen Dyck Offset += CharUnits::fromQuantity(Result.getInt().getZExtValue()); 1494a73058324197b7bdfd19307965954f626e26199dKen Dyck Result = APValue(RHSVal.getLValueBase(), Offset); 149542edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman return true; 149642edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman } 149742edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman 149842edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman // All the following cases expect both operands to be an integer 149942edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman if (!Result.isInt() || !RHSVal.isInt()) 1500b542afe02d317411d53b3541946f9f2a8f509a11Chris Lattner return false; 1501a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman 150242edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman APSInt& RHS = RHSVal.getInt(); 150342edd0d32a729d2735a6fb152ba6bf349bf0a169Eli Friedman 1504a25ae3d68d84d2b89907f998df6a396549589da5Anders Carlsson switch (E->getOpcode()) { 150532fea9d18cc3658a1b01df5ca6f2ac302625c61dChris Lattner default: 15060e8acbbba71ec6acd5dceb4fcbce63e463e1b755Anders Carlsson return Error(E->getOperatorLoc(), diag::note_invalid_subexpr_in_ice, E); 15072de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Mul: return Success(Result.getInt() * RHS, E); 15082de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Add: return Success(Result.getInt() + RHS, E); 15092de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Sub: return Success(Result.getInt() - RHS, E); 15102de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_And: return Success(Result.getInt() & RHS, E); 15112de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Xor: return Success(Result.getInt() ^ RHS, E); 15122de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Or: return Success(Result.getInt() | RHS, E); 15132de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Div: 151454176fdb044312b4b77c3da6682d3575b3728d30Chris Lattner if (RHS == 0) 15150e8acbbba71ec6acd5dceb4fcbce63e463e1b755Anders Carlsson return Error(E->getOperatorLoc(), diag::note_expr_divide_by_zero, E); 151630c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar return Success(Result.getInt() / RHS, E); 15172de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Rem: 151854176fdb044312b4b77c3da6682d3575b3728d30Chris Lattner if (RHS == 0) 15190e8acbbba71ec6acd5dceb4fcbce63e463e1b755Anders Carlsson return Error(E->getOperatorLoc(), diag::note_expr_divide_by_zero, E); 152030c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar return Success(Result.getInt() % RHS, E); 15212de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Shl: { 1522091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall // During constant-folding, a negative shift is an opposite shift. 1523091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall if (RHS.isSigned() && RHS.isNegative()) { 1524091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall RHS = -RHS; 1525091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall goto shift_right; 1526091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall } 1527091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall 1528091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall shift_left: 1529091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall unsigned SA 1530091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall = (unsigned) RHS.getLimitedValue(Result.getInt().getBitWidth()-1); 153130c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar return Success(Result.getInt() << SA, E); 15323f7d995390009fede92b333a040da80e1ce90997Daniel Dunbar } 15332de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Shr: { 1534091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall // During constant-folding, a negative shift is an opposite shift. 1535091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall if (RHS.isSigned() && RHS.isNegative()) { 1536091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall RHS = -RHS; 1537091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall goto shift_left; 1538091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall } 1539091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall 1540091f23f1d6d4bcffd6641cda72a6831e08c02ea7John McCall shift_right: 15411eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump unsigned SA = 154230c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar (unsigned) RHS.getLimitedValue(Result.getInt().getBitWidth()-1); 154330c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar return Success(Result.getInt() >> SA, E); 15443f7d995390009fede92b333a040da80e1ce90997Daniel Dunbar } 15451eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 15462de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_LT: return Success(Result.getInt() < RHS, E); 15472de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_GT: return Success(Result.getInt() > RHS, E); 15482de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_LE: return Success(Result.getInt() <= RHS, E); 15492de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_GE: return Success(Result.getInt() >= RHS, E); 15502de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_EQ: return Success(Result.getInt() == RHS, E); 15512de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_NE: return Success(Result.getInt() != RHS, E); 1552b11e77836dd0867955c5abf32baf1c3e6c7f81e1Eli Friedman } 1553a25ae3d68d84d2b89907f998df6a396549589da5Anders Carlsson} 1554a25ae3d68d84d2b89907f998df6a396549589da5Anders Carlsson 155556ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCallbool IntExprEvaluator:: 155656ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCallVisitBinaryConditionalOperator(const BinaryConditionalOperator *e) { 155756ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall OpaqueValueEvaluation opaque(Info, e->getOpaqueValue(), e->getCommon()); 155856ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall if (opaque.hasError()) return false; 155956ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall 156056ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall bool cond; 156156ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall if (!HandleConversionToBool(e->getCond(), cond, Info)) 156256ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall return false; 156356ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall 156456ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall return Visit(cond ? e->getTrueExpr() : e->getFalseExpr()); 156556ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall} 156656ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall 1567ca7c2eaca35edac066ab7cec15f7ecebbb3731d8Nuno Lopesbool IntExprEvaluator::VisitConditionalOperator(const ConditionalOperator *E) { 1568a25bd55e63b9ab26ca69390533356aaae7f1a40eNuno Lopes bool Cond; 1569a25bd55e63b9ab26ca69390533356aaae7f1a40eNuno Lopes if (!HandleConversionToBool(E->getCond(), Cond, Info)) 1570ca7c2eaca35edac066ab7cec15f7ecebbb3731d8Nuno Lopes return false; 1571ca7c2eaca35edac066ab7cec15f7ecebbb3731d8Nuno Lopes 1572a25bd55e63b9ab26ca69390533356aaae7f1a40eNuno Lopes return Visit(Cond ? E->getTrueExpr() : E->getFalseExpr()); 1573ca7c2eaca35edac066ab7cec15f7ecebbb3731d8Nuno Lopes} 1574ca7c2eaca35edac066ab7cec15f7ecebbb3731d8Nuno Lopes 15758b752f10c394b140f9ef89e049cbad1a7676fc25Ken DyckCharUnits IntExprEvaluator::GetAlignOfType(QualType T) { 15765d484e8cf710207010720589d89602233de61d01Sebastian Redl // C++ [expr.sizeof]p2: "When applied to a reference or a reference type, 15775d484e8cf710207010720589d89602233de61d01Sebastian Redl // the result is the size of the referenced type." 15785d484e8cf710207010720589d89602233de61d01Sebastian Redl // C++ [expr.alignof]p3: "When alignof is applied to a reference type, the 15795d484e8cf710207010720589d89602233de61d01Sebastian Redl // result shall be the alignment of the referenced type." 15805d484e8cf710207010720589d89602233de61d01Sebastian Redl if (const ReferenceType *Ref = T->getAs<ReferenceType>()) 15815d484e8cf710207010720589d89602233de61d01Sebastian Redl T = Ref->getPointeeType(); 15825d484e8cf710207010720589d89602233de61d01Sebastian Redl 15832be586108bb401019647791feca19ea03fd477ceEli Friedman // __alignof is defined to return the preferred alignment. 1584fb1e3bc29b667f4275e1d5a43d64ec173f4f9a7dKen Dyck return Info.Ctx.toCharUnitsFromBits( 1585fb1e3bc29b667f4275e1d5a43d64ec173f4f9a7dKen Dyck Info.Ctx.getPreferredTypeAlign(T.getTypePtr())); 1586e9feb475d72ba50dc29cec62a8c47cae721065ebChris Lattner} 1587e9feb475d72ba50dc29cec62a8c47cae721065ebChris Lattner 15888b752f10c394b140f9ef89e049cbad1a7676fc25Ken DyckCharUnits IntExprEvaluator::GetAlignOfExpr(const Expr *E) { 1589af707ab8fbb9451e8febb8d766f6c043628125c4Chris Lattner E = E->IgnoreParens(); 1590af707ab8fbb9451e8febb8d766f6c043628125c4Chris Lattner 1591af707ab8fbb9451e8febb8d766f6c043628125c4Chris Lattner // alignof decl is always accepted, even if it doesn't make sense: we default 15921eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump // to 1 in those cases. 1593af707ab8fbb9451e8febb8d766f6c043628125c4Chris Lattner if (const DeclRefExpr *DRE = dyn_cast<DeclRefExpr>(E)) 15948b752f10c394b140f9ef89e049cbad1a7676fc25Ken Dyck return Info.Ctx.getDeclAlign(DRE->getDecl(), 15958b752f10c394b140f9ef89e049cbad1a7676fc25Ken Dyck /*RefAsPointee*/true); 1596a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman 1597af707ab8fbb9451e8febb8d766f6c043628125c4Chris Lattner if (const MemberExpr *ME = dyn_cast<MemberExpr>(E)) 15988b752f10c394b140f9ef89e049cbad1a7676fc25Ken Dyck return Info.Ctx.getDeclAlign(ME->getMemberDecl(), 15998b752f10c394b140f9ef89e049cbad1a7676fc25Ken Dyck /*RefAsPointee*/true); 1600af707ab8fbb9451e8febb8d766f6c043628125c4Chris Lattner 1601e9feb475d72ba50dc29cec62a8c47cae721065ebChris Lattner return GetAlignOfType(E->getType()); 1602e9feb475d72ba50dc29cec62a8c47cae721065ebChris Lattner} 1603e9feb475d72ba50dc29cec62a8c47cae721065ebChris Lattner 1604e9feb475d72ba50dc29cec62a8c47cae721065ebChris Lattner 1605f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne/// VisitUnaryExprOrTypeTraitExpr - Evaluate a sizeof, alignof or vec_step with 1606f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne/// a result as the expression's type. 1607f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbournebool IntExprEvaluator::VisitUnaryExprOrTypeTraitExpr( 1608f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne const UnaryExprOrTypeTraitExpr *E) { 1609f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne switch(E->getKind()) { 1610f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne case UETT_AlignOf: { 1611e9feb475d72ba50dc29cec62a8c47cae721065ebChris Lattner if (E->isArgumentType()) 16124f3bc8f7aa90b72832b03bee9201c98f4bb6b4d1Ken Dyck return Success(GetAlignOfType(E->getArgumentType()), E); 1613e9feb475d72ba50dc29cec62a8c47cae721065ebChris Lattner else 16144f3bc8f7aa90b72832b03bee9201c98f4bb6b4d1Ken Dyck return Success(GetAlignOfExpr(E->getArgumentExpr()), E); 1615e9feb475d72ba50dc29cec62a8c47cae721065ebChris Lattner } 1616a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman 1617f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne case UETT_VecStep: { 1618f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne QualType Ty = E->getTypeOfArgument(); 16190518999d3adcc289997bd974dce90cc97f5c1c44Sebastian Redl 1620f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne if (Ty->isVectorType()) { 1621f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne unsigned n = Ty->getAs<VectorType>()->getNumElements(); 1622a1f47c447a919c6a05c63801cb6a52c4c288e2ccEli Friedman 1623f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne // The vec_step built-in functions that take a 3-component 1624f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne // vector return 4. (OpenCL 1.1 spec 6.11.12) 1625f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne if (n == 3) 1626f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne n = 4; 1627f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne 1628f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne return Success(n, E); 1629f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne } else 1630f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne return Success(1, E); 1631f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne } 1632f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne 1633f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne case UETT_SizeOf: { 1634f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne QualType SrcTy = E->getTypeOfArgument(); 1635f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne // C++ [expr.sizeof]p2: "When applied to a reference or a reference type, 1636f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne // the result is the size of the referenced type." 1637f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne // C++ [expr.alignof]p3: "When alignof is applied to a reference type, the 1638f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne // result shall be the alignment of the referenced type." 1639f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne if (const ReferenceType *Ref = SrcTy->getAs<ReferenceType>()) 1640f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne SrcTy = Ref->getPointeeType(); 1641f2da9dfef96dc11b7b5effb1d02cb427b2d71599Eli Friedman 1642f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne // sizeof(void), __alignof__(void), sizeof(function) = 1 as a gcc 1643f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne // extension. 1644f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne if (SrcTy->isVoidType() || SrcTy->isFunctionType()) 1645f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne return Success(1, E); 1646f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne 1647f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne // sizeof(vla) is not a constantexpr: C99 6.5.3.4p2. 1648f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne if (!SrcTy->isConstantSizeType()) 1649f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne return false; 1650f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne 1651f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne // Get information about the size. 1652f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne return Success(Info.Ctx.getTypeSizeInChars(SrcTy), E); 1653f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne } 1654f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne } 1655f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne 1656f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne llvm_unreachable("unknown expr/type trait"); 1657f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne return false; 1658fcee0019b76f9f368f2b3d6d4048a98232593f29Chris Lattner} 1659fcee0019b76f9f368f2b3d6d4048a98232593f29Chris Lattner 16608ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregorbool IntExprEvaluator::VisitOffsetOfExpr(const OffsetOfExpr *E) { 16618ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor CharUnits Result; 16628ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor unsigned n = E->getNumComponents(); 16638ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor OffsetOfExpr* OOE = const_cast<OffsetOfExpr*>(E); 16648ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor if (n == 0) 16658ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor return false; 16668ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor QualType CurrentType = E->getTypeSourceInfo()->getType(); 16678ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor for (unsigned i = 0; i != n; ++i) { 16688ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor OffsetOfExpr::OffsetOfNode ON = OOE->getComponent(i); 16698ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor switch (ON.getKind()) { 16708ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor case OffsetOfExpr::OffsetOfNode::Array: { 16718ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor Expr *Idx = OOE->getIndexExpr(ON.getArrayExprIndex()); 16728ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor APSInt IdxResult; 16738ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor if (!EvaluateInteger(Idx, IdxResult, Info)) 16748ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor return false; 16758ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor const ArrayType *AT = Info.Ctx.getAsArrayType(CurrentType); 16768ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor if (!AT) 16778ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor return false; 16788ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor CurrentType = AT->getElementType(); 16798ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor CharUnits ElementSize = Info.Ctx.getTypeSizeInChars(CurrentType); 16808ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor Result += IdxResult.getSExtValue() * ElementSize; 16818ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor break; 16828ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor } 16838ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor 16848ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor case OffsetOfExpr::OffsetOfNode::Field: { 16858ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor FieldDecl *MemberDecl = ON.getField(); 16868ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor const RecordType *RT = CurrentType->getAs<RecordType>(); 16878ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor if (!RT) 16888ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor return false; 16898ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor RecordDecl *RD = RT->getDecl(); 16908ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor const ASTRecordLayout &RL = Info.Ctx.getASTRecordLayout(RD); 1691ba4f5d5754c8291690d01ca9581926673d69b24cJohn McCall unsigned i = MemberDecl->getFieldIndex(); 1692cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor assert(i < RL.getFieldCount() && "offsetof field in wrong type"); 1693fb1e3bc29b667f4275e1d5a43d64ec173f4f9a7dKen Dyck Result += Info.Ctx.toCharUnitsFromBits(RL.getFieldOffset(i)); 16948ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor CurrentType = MemberDecl->getType().getNonReferenceType(); 16958ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor break; 16968ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor } 16978ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor 16988ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor case OffsetOfExpr::OffsetOfNode::Identifier: 16998ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor llvm_unreachable("dependent __builtin_offsetof"); 1700cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor return false; 1701cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor 1702cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor case OffsetOfExpr::OffsetOfNode::Base: { 1703cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor CXXBaseSpecifier *BaseSpec = ON.getBase(); 1704cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor if (BaseSpec->isVirtual()) 1705cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor return false; 1706cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor 1707cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor // Find the layout of the class whose base we are looking into. 1708cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor const RecordType *RT = CurrentType->getAs<RecordType>(); 1709cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor if (!RT) 1710cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor return false; 1711cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor RecordDecl *RD = RT->getDecl(); 1712cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor const ASTRecordLayout &RL = Info.Ctx.getASTRecordLayout(RD); 1713cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor 1714cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor // Find the base class itself. 1715cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor CurrentType = BaseSpec->getType(); 1716cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor const RecordType *BaseRT = CurrentType->getAs<RecordType>(); 1717cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor if (!BaseRT) 1718cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor return false; 1719cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor 1720cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor // Add the offset to the base. 17217c7f820d70c925b29290a8563b59615816a827fcKen Dyck Result += RL.getBaseClassOffset(cast<CXXRecordDecl>(BaseRT->getDecl())); 1722cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor break; 1723cc8a5d5f90bbbbcb46f342117b851b7e07ec34f1Douglas Gregor } 17248ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor } 17258ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor } 17264f3bc8f7aa90b72832b03bee9201c98f4bb6b4d1Ken Dyck return Success(Result, E); 17278ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor} 17288ecdb65716cd7914ffb2eeee993fa9039fcd31e8Douglas Gregor 1729b542afe02d317411d53b3541946f9f2a8f509a11Chris Lattnerbool IntExprEvaluator::VisitUnaryOperator(const UnaryOperator *E) { 17302de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall if (E->getOpcode() == UO_LNot) { 1731a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman // LNot's operand isn't necessarily an integer, so we handle it specially. 1732a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman bool bres; 1733a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman if (!HandleConversionToBool(E->getSubExpr(), bres, Info)) 1734a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman return false; 1735131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar return Success(!bres, E); 1736a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman } 1737a6afa768aa7bd3102a2807aa720917e4a1771e4eEli Friedman 17384fff4819a913c65ae23cfd389bc47c61919e4e1fDaniel Dunbar // Only handle integral operations... 17392ade35e2cfd554e49d35a52047cea98a82787af9Douglas Gregor if (!E->getSubExpr()->getType()->isIntegralOrEnumerationType()) 17404fff4819a913c65ae23cfd389bc47c61919e4e1fDaniel Dunbar return false; 17414fff4819a913c65ae23cfd389bc47c61919e4e1fDaniel Dunbar 174287eae5ecf94e38baa20d9a327b8f73f8bdc72436Chris Lattner // Get the operand value into 'Result'. 174387eae5ecf94e38baa20d9a327b8f73f8bdc72436Chris Lattner if (!Visit(E->getSubExpr())) 174475a4881047deeb3a300ff9293dc6ba8570048bb5Chris Lattner return false; 1745a25ae3d68d84d2b89907f998df6a396549589da5Anders Carlsson 174675a4881047deeb3a300ff9293dc6ba8570048bb5Chris Lattner switch (E->getOpcode()) { 17474c4867e140327fa3b56306fa03c64c8e6a7c95efChris Lattner default: 174875a4881047deeb3a300ff9293dc6ba8570048bb5Chris Lattner // Address, indirect, pre/post inc/dec, etc are not valid constant exprs. 174975a4881047deeb3a300ff9293dc6ba8570048bb5Chris Lattner // See C99 6.6p3. 17500e8acbbba71ec6acd5dceb4fcbce63e463e1b755Anders Carlsson return Error(E->getOperatorLoc(), diag::note_invalid_subexpr_in_ice, E); 17512de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case UO_Extension: 17524c4867e140327fa3b56306fa03c64c8e6a7c95efChris Lattner // FIXME: Should extension allow i-c-e extension expressions in its scope? 17534c4867e140327fa3b56306fa03c64c8e6a7c95efChris Lattner // If so, we could clear the diagnostic ID. 17543f7d995390009fede92b333a040da80e1ce90997Daniel Dunbar return true; 17552de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case UO_Plus: 17561eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump // The result is always just the subexpr. 17573f7d995390009fede92b333a040da80e1ce90997Daniel Dunbar return true; 17582de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case UO_Minus: 175930c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar if (!Result.isInt()) return false; 176030c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar return Success(-Result.getInt(), E); 17612de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case UO_Not: 176230c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar if (!Result.isInt()) return false; 176330c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar return Success(~Result.getInt(), E); 176406a3675627e3b3c47b49c689c8e404a33144194aAnders Carlsson } 1765a25ae3d68d84d2b89907f998df6a396549589da5Anders Carlsson} 17661eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1767732b2236ae4a4f11e7642677cebbd169c07ea877Chris Lattner/// HandleCast - This is used to evaluate implicit or explicit casts where the 1768732b2236ae4a4f11e7642677cebbd169c07ea877Chris Lattner/// result type is integer. 1769a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbarbool IntExprEvaluator::VisitCastExpr(CastExpr *E) { 177082206e267ce6cc709797127616f64672d255b310Anders Carlsson Expr *SubExpr = E->getSubExpr(); 177182206e267ce6cc709797127616f64672d255b310Anders Carlsson QualType DestType = E->getType(); 1772b92dac8bc2f6f73919825f9af693a8a7e89ae1d4Daniel Dunbar QualType SrcType = SubExpr->getType(); 177382206e267ce6cc709797127616f64672d255b310Anders Carlsson 17744efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman if (DestType->isBooleanType()) { 17754efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman bool BoolResult; 17764efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman if (!HandleConversionToBool(SubExpr, BoolResult, Info)) 17774efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman return false; 1778131eb438d8c216b2e2a4f8fa8158ea88b787dc14Daniel Dunbar return Success(BoolResult, E); 17794efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman } 17804efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman 1781a25ae3d68d84d2b89907f998df6a396549589da5Anders Carlsson // Handle simple integer->integer casts. 17822ade35e2cfd554e49d35a52047cea98a82787af9Douglas Gregor if (SrcType->isIntegralOrEnumerationType()) { 1783732b2236ae4a4f11e7642677cebbd169c07ea877Chris Lattner if (!Visit(SubExpr)) 1784b542afe02d317411d53b3541946f9f2a8f509a11Chris Lattner return false; 1785a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar 1786be26570e3faa009bdcefedfaf04473e518940520Eli Friedman if (!Result.isInt()) { 1787be26570e3faa009bdcefedfaf04473e518940520Eli Friedman // Only allow casts of lvalues if they are lossless. 1788be26570e3faa009bdcefedfaf04473e518940520Eli Friedman return Info.Ctx.getTypeSize(DestType) == Info.Ctx.getTypeSize(SrcType); 1789be26570e3faa009bdcefedfaf04473e518940520Eli Friedman } 179030c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar 1791dd2116462ae311043986ae8b7fba27e68c1b2e66Daniel Dunbar return Success(HandleIntToIntCast(DestType, SrcType, 179230c37f4d2ee5811e85f692c22fb67d74ddc88079Daniel Dunbar Result.getInt(), Info.Ctx), E); 1793732b2236ae4a4f11e7642677cebbd169c07ea877Chris Lattner } 17941eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1795732b2236ae4a4f11e7642677cebbd169c07ea877Chris Lattner // FIXME: Clean this up! 1796b92dac8bc2f6f73919825f9af693a8a7e89ae1d4Daniel Dunbar if (SrcType->isPointerType()) { 1797efdb83e26f9a1fd2566afe54461216cd84814d42John McCall LValue LV; 179887eae5ecf94e38baa20d9a327b8f73f8bdc72436Chris Lattner if (!EvaluatePointer(SubExpr, LV, Info)) 1799b542afe02d317411d53b3541946f9f2a8f509a11Chris Lattner return false; 18004efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman 1801dd2116462ae311043986ae8b7fba27e68c1b2e66Daniel Dunbar if (LV.getLValueBase()) { 1802dd2116462ae311043986ae8b7fba27e68c1b2e66Daniel Dunbar // Only allow based lvalue casts if they are lossless. 1803dd2116462ae311043986ae8b7fba27e68c1b2e66Daniel Dunbar if (Info.Ctx.getTypeSize(DestType) != Info.Ctx.getTypeSize(SrcType)) 1804dd2116462ae311043986ae8b7fba27e68c1b2e66Daniel Dunbar return false; 1805dd2116462ae311043986ae8b7fba27e68c1b2e66Daniel Dunbar 1806efdb83e26f9a1fd2566afe54461216cd84814d42John McCall LV.moveInto(Result); 1807dd2116462ae311043986ae8b7fba27e68c1b2e66Daniel Dunbar return true; 1808dd2116462ae311043986ae8b7fba27e68c1b2e66Daniel Dunbar } 18094efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman 1810a73058324197b7bdfd19307965954f626e26199dKen Dyck APSInt AsInt = Info.Ctx.MakeIntValue(LV.getLValueOffset().getQuantity(), 1811a73058324197b7bdfd19307965954f626e26199dKen Dyck SrcType); 1812dd2116462ae311043986ae8b7fba27e68c1b2e66Daniel Dunbar return Success(HandleIntToIntCast(DestType, SrcType, AsInt, Info.Ctx), E); 18132bad1687fe6f00e10767a691a33b070b151902b6Anders Carlsson } 18144efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman 1815be26570e3faa009bdcefedfaf04473e518940520Eli Friedman if (SrcType->isArrayType() || SrcType->isFunctionType()) { 1816be26570e3faa009bdcefedfaf04473e518940520Eli Friedman // This handles double-conversion cases, where there's both 1817be26570e3faa009bdcefedfaf04473e518940520Eli Friedman // an l-value promotion and an implicit conversion to int. 1818efdb83e26f9a1fd2566afe54461216cd84814d42John McCall LValue LV; 1819be26570e3faa009bdcefedfaf04473e518940520Eli Friedman if (!EvaluateLValue(SubExpr, LV, Info)) 1820be26570e3faa009bdcefedfaf04473e518940520Eli Friedman return false; 1821be26570e3faa009bdcefedfaf04473e518940520Eli Friedman 1822be26570e3faa009bdcefedfaf04473e518940520Eli Friedman if (Info.Ctx.getTypeSize(DestType) != Info.Ctx.getTypeSize(Info.Ctx.VoidPtrTy)) 1823be26570e3faa009bdcefedfaf04473e518940520Eli Friedman return false; 1824be26570e3faa009bdcefedfaf04473e518940520Eli Friedman 1825efdb83e26f9a1fd2566afe54461216cd84814d42John McCall LV.moveInto(Result); 1826be26570e3faa009bdcefedfaf04473e518940520Eli Friedman return true; 1827be26570e3faa009bdcefedfaf04473e518940520Eli Friedman } 1828be26570e3faa009bdcefedfaf04473e518940520Eli Friedman 18291725f683432715e5afe34d476024bd6f16eac3fcEli Friedman if (SrcType->isAnyComplexType()) { 1830f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall ComplexValue C; 18311725f683432715e5afe34d476024bd6f16eac3fcEli Friedman if (!EvaluateComplex(SubExpr, C, Info)) 18321725f683432715e5afe34d476024bd6f16eac3fcEli Friedman return false; 18331725f683432715e5afe34d476024bd6f16eac3fcEli Friedman if (C.isComplexFloat()) 18341725f683432715e5afe34d476024bd6f16eac3fcEli Friedman return Success(HandleFloatToIntCast(DestType, SrcType, 18351725f683432715e5afe34d476024bd6f16eac3fcEli Friedman C.getComplexFloatReal(), Info.Ctx), 18361725f683432715e5afe34d476024bd6f16eac3fcEli Friedman E); 18371725f683432715e5afe34d476024bd6f16eac3fcEli Friedman else 18381725f683432715e5afe34d476024bd6f16eac3fcEli Friedman return Success(HandleIntToIntCast(DestType, SrcType, 18391725f683432715e5afe34d476024bd6f16eac3fcEli Friedman C.getComplexIntReal(), Info.Ctx), E); 18401725f683432715e5afe34d476024bd6f16eac3fcEli Friedman } 18412217c87bdc5ab357046a5453bdb06f469c41024eEli Friedman // FIXME: Handle vectors 18422217c87bdc5ab357046a5453bdb06f469c41024eEli Friedman 1843b92dac8bc2f6f73919825f9af693a8a7e89ae1d4Daniel Dunbar if (!SrcType->isRealFloatingType()) 18440e8acbbba71ec6acd5dceb4fcbce63e463e1b755Anders Carlsson return Error(E->getExprLoc(), diag::note_invalid_subexpr_in_ice, E); 1845732b2236ae4a4f11e7642677cebbd169c07ea877Chris Lattner 1846d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman APFloat F(0.0); 1847d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman if (!EvaluateFloat(SubExpr, F, Info)) 18480e8acbbba71ec6acd5dceb4fcbce63e463e1b755Anders Carlsson return Error(E->getExprLoc(), diag::note_invalid_subexpr_in_ice, E); 18491eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1850b92dac8bc2f6f73919825f9af693a8a7e89ae1d4Daniel Dunbar return Success(HandleFloatToIntCast(DestType, SrcType, F, Info.Ctx), E); 1851a25ae3d68d84d2b89907f998df6a396549589da5Anders Carlsson} 18522bad1687fe6f00e10767a691a33b070b151902b6Anders Carlsson 1853722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedmanbool IntExprEvaluator::VisitUnaryReal(const UnaryOperator *E) { 1854722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman if (E->getSubExpr()->getType()->isAnyComplexType()) { 1855f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall ComplexValue LV; 1856722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman if (!EvaluateComplex(E->getSubExpr(), LV, Info) || !LV.isComplexInt()) 1857722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman return Error(E->getExprLoc(), diag::note_invalid_subexpr_in_ice, E); 1858722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman return Success(LV.getComplexIntReal(), E); 1859722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman } 1860722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman 1861722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman return Visit(E->getSubExpr()); 1862722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman} 1863722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman 1864664a104ba0b8f47b8908ec6af694d9646adba1fcEli Friedmanbool IntExprEvaluator::VisitUnaryImag(const UnaryOperator *E) { 1865722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman if (E->getSubExpr()->getType()->isComplexIntegerType()) { 1866f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall ComplexValue LV; 1867722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman if (!EvaluateComplex(E->getSubExpr(), LV, Info) || !LV.isComplexInt()) 1868722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman return Error(E->getExprLoc(), diag::note_invalid_subexpr_in_ice, E); 1869722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman return Success(LV.getComplexIntImag(), E); 1870722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman } 1871722c717cd833e410ca6e7976d78baea16995e0c4Eli Friedman 1872664a104ba0b8f47b8908ec6af694d9646adba1fcEli Friedman if (!E->getSubExpr()->isEvaluatable(Info.Ctx)) 1873664a104ba0b8f47b8908ec6af694d9646adba1fcEli Friedman Info.EvalResult.HasSideEffects = true; 1874664a104ba0b8f47b8908ec6af694d9646adba1fcEli Friedman return Success(0, E); 1875664a104ba0b8f47b8908ec6af694d9646adba1fcEli Friedman} 1876664a104ba0b8f47b8908ec6af694d9646adba1fcEli Friedman 1877ee8aff06f6a96214731de17b2cb6df407c6c1820Douglas Gregorbool IntExprEvaluator::VisitSizeOfPackExpr(const SizeOfPackExpr *E) { 1878ee8aff06f6a96214731de17b2cb6df407c6c1820Douglas Gregor return Success(E->getPackLength(), E); 1879ee8aff06f6a96214731de17b2cb6df407c6c1820Douglas Gregor} 1880ee8aff06f6a96214731de17b2cb6df407c6c1820Douglas Gregor 1881295995c9c3196416372c9cd35d9cedb6da37bd3dSebastian Redlbool IntExprEvaluator::VisitCXXNoexceptExpr(const CXXNoexceptExpr *E) { 1882295995c9c3196416372c9cd35d9cedb6da37bd3dSebastian Redl return Success(E->getValue(), E); 1883295995c9c3196416372c9cd35d9cedb6da37bd3dSebastian Redl} 1884295995c9c3196416372c9cd35d9cedb6da37bd3dSebastian Redl 1885f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner//===----------------------------------------------------------------------===// 1886d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman// Float Evaluation 1887d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman//===----------------------------------------------------------------------===// 1888d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman 1889d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedmannamespace { 1890770b4a8834670e9427d3ce5a1a8472eb86f45fd2Benjamin Kramerclass FloatExprEvaluator 1891d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman : public StmtVisitor<FloatExprEvaluator, bool> { 1892d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman EvalInfo &Info; 1893d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman APFloat &Result; 1894d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedmanpublic: 1895d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman FloatExprEvaluator(EvalInfo &info, APFloat &result) 1896d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman : Info(info), Result(result) {} 1897d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman 1898d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman bool VisitStmt(Stmt *S) { 1899d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman return false; 1900d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman } 1901d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman 1902d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman bool VisitParenExpr(ParenExpr *E) { return Visit(E->getSubExpr()); } 1903019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner bool VisitCallExpr(const CallExpr *E); 1904d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman 19055db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar bool VisitUnaryOperator(const UnaryOperator *E); 1906d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman bool VisitBinaryOperator(const BinaryOperator *E); 1907d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman bool VisitFloatingLiteral(const FloatingLiteral *E); 19084efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman bool VisitCastExpr(CastExpr *E); 1909ed8abf18329df67b0abcbb3a10458bd8c1d2a595Douglas Gregor bool VisitCXXScalarValueInitExpr(CXXScalarValueInitExpr *E); 191067f85fcdab64f36233a7211f963ed1cccffcbfb8Eli Friedman bool VisitConditionalOperator(ConditionalOperator *E); 191156ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall bool VisitBinaryConditionalOperator(BinaryConditionalOperator *E); 19122217c87bdc5ab357046a5453bdb06f469c41024eEli Friedman 1913ba98d6bb414861965a1f22628494ea046785ecd4Eli Friedman bool VisitChooseExpr(const ChooseExpr *E) 1914ba98d6bb414861965a1f22628494ea046785ecd4Eli Friedman { return Visit(E->getChosenSubExpr(Info.Ctx)); } 1915ba98d6bb414861965a1f22628494ea046785ecd4Eli Friedman bool VisitUnaryExtension(const UnaryOperator *E) 1916ba98d6bb414861965a1f22628494ea046785ecd4Eli Friedman { return Visit(E->getSubExpr()); } 1917abd3a857ace59100305790545d1baae5877b8945John McCall bool VisitUnaryReal(const UnaryOperator *E); 1918abd3a857ace59100305790545d1baae5877b8945John McCall bool VisitUnaryImag(const UnaryOperator *E); 1919ba98d6bb414861965a1f22628494ea046785ecd4Eli Friedman 1920189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall bool VisitDeclRefExpr(const DeclRefExpr *E); 1921189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall 192256ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall bool VisitOpaqueValueExpr(const OpaqueValueExpr *e) { 192356ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall const APValue *value = Info.getOpaqueValue(e); 192456ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall if (!value) 192556ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall return (e->getSourceExpr() ? Visit(e->getSourceExpr()) : false); 192656ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall Result = value->getFloat(); 192756ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall return true; 192856ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall } 192956ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall 1930abd3a857ace59100305790545d1baae5877b8945John McCall // FIXME: Missing: array subscript of vector, member of vector, 1931abd3a857ace59100305790545d1baae5877b8945John McCall // ImplicitValueInitExpr 1932d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman}; 1933d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman} // end anonymous namespace 1934d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman 1935d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedmanstatic bool EvaluateFloat(const Expr* E, APFloat& Result, EvalInfo &Info) { 19367db7acbbb84b82d0522266a50ebabc3a52a9e5d1John McCall assert(E->getType()->isRealFloatingType()); 1937d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman return FloatExprEvaluator(Info, Result).Visit(const_cast<Expr*>(E)); 1938d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman} 1939d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman 19404ba2a17694148e16eaa8d3917f657ffcd3667be4Jay Foadstatic bool TryEvaluateBuiltinNaN(const ASTContext &Context, 1941db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall QualType ResultTy, 1942db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall const Expr *Arg, 1943db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall bool SNaN, 1944db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall llvm::APFloat &Result) { 1945db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall const StringLiteral *S = dyn_cast<StringLiteral>(Arg->IgnoreParenCasts()); 1946db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall if (!S) return false; 1947db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall 1948db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall const llvm::fltSemantics &Sem = Context.getFloatTypeSemantics(ResultTy); 1949db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall 1950db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall llvm::APInt fill; 1951db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall 1952db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall // Treat empty strings as if they were zero. 1953db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall if (S->getString().empty()) 1954db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall fill = llvm::APInt(32, 0); 1955db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall else if (S->getString().getAsInteger(0, fill)) 1956db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall return false; 1957db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall 1958db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall if (SNaN) 1959db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall Result = llvm::APFloat::getSNaN(Sem, false, &fill); 1960db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall else 1961db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall Result = llvm::APFloat::getQNaN(Sem, false, &fill); 1962db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall return true; 1963db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall} 1964db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall 1965019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattnerbool FloatExprEvaluator::VisitCallExpr(const CallExpr *E) { 19663c385e5f8d9008fff18597ca302be19fa86e51f6Douglas Gregor switch (E->isBuiltinCall(Info.Ctx)) { 196734a74ab81600a40c6324fd76adb724b803dfaf91Chris Lattner default: return false; 1968019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner case Builtin::BI__builtin_huge_val: 1969019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner case Builtin::BI__builtin_huge_valf: 1970019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner case Builtin::BI__builtin_huge_vall: 1971019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner case Builtin::BI__builtin_inf: 1972019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner case Builtin::BI__builtin_inff: 19737cbed03c00e246682e5292785d01e1c120ce54bdDaniel Dunbar case Builtin::BI__builtin_infl: { 19747cbed03c00e246682e5292785d01e1c120ce54bdDaniel Dunbar const llvm::fltSemantics &Sem = 19757cbed03c00e246682e5292785d01e1c120ce54bdDaniel Dunbar Info.Ctx.getFloatTypeSemantics(E->getType()); 197634a74ab81600a40c6324fd76adb724b803dfaf91Chris Lattner Result = llvm::APFloat::getInf(Sem); 197734a74ab81600a40c6324fd76adb724b803dfaf91Chris Lattner return true; 19787cbed03c00e246682e5292785d01e1c120ce54bdDaniel Dunbar } 19791eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 1980db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall case Builtin::BI__builtin_nans: 1981db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall case Builtin::BI__builtin_nansf: 1982db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall case Builtin::BI__builtin_nansl: 1983db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall return TryEvaluateBuiltinNaN(Info.Ctx, E->getType(), E->getArg(0), 1984db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall true, Result); 1985db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall 19869e62171a25e3a08fb5c49fb370f83faf5ae786f5Chris Lattner case Builtin::BI__builtin_nan: 19879e62171a25e3a08fb5c49fb370f83faf5ae786f5Chris Lattner case Builtin::BI__builtin_nanf: 19889e62171a25e3a08fb5c49fb370f83faf5ae786f5Chris Lattner case Builtin::BI__builtin_nanl: 19894572baba9d18c275968ac113fd73b0e3c77cccb8Mike Stump // If this is __builtin_nan() turn this into a nan, otherwise we 19909e62171a25e3a08fb5c49fb370f83faf5ae786f5Chris Lattner // can't constant fold it. 1991db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall return TryEvaluateBuiltinNaN(Info.Ctx, E->getType(), E->getArg(0), 1992db7b72a82a6834680ccf1eeb51dc57e6d935c655John McCall false, Result); 19935db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar 19945db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar case Builtin::BI__builtin_fabs: 19955db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar case Builtin::BI__builtin_fabsf: 19965db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar case Builtin::BI__builtin_fabsl: 19975db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar if (!EvaluateFloat(E->getArg(0), Result, Info)) 19985db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar return false; 19991eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 20005db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar if (Result.isNegative()) 20015db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar Result.changeSign(); 20025db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar return true; 20035db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar 20041eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump case Builtin::BI__builtin_copysign: 20051eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump case Builtin::BI__builtin_copysignf: 20065db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar case Builtin::BI__builtin_copysignl: { 20075db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar APFloat RHS(0.); 20085db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar if (!EvaluateFloat(E->getArg(0), Result, Info) || 20095db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar !EvaluateFloat(E->getArg(1), RHS, Info)) 20105db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar return false; 20115db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar Result.copySign(RHS); 20125db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar return true; 20135db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar } 2014019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner } 2015019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner} 2016019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner 2017189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCallbool FloatExprEvaluator::VisitDeclRefExpr(const DeclRefExpr *E) { 2018189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall const Decl *D = E->getDecl(); 2019189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall if (!isa<VarDecl>(D) || isa<ParmVarDecl>(D)) return false; 2020189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall const VarDecl *VD = cast<VarDecl>(D); 2021189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall 2022189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall // Require the qualifiers to be const and not volatile. 2023189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall CanQualType T = Info.Ctx.getCanonicalType(E->getType()); 2024189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall if (!T.isConstQualified() || T.isVolatileQualified()) 2025189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall return false; 2026189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall 2027189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall const Expr *Init = VD->getAnyInitializer(); 2028189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall if (!Init) return false; 2029189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall 2030189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall if (APValue *V = VD->getEvaluatedValue()) { 2031189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall if (V->isFloat()) { 2032189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall Result = V->getFloat(); 2033189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall return true; 2034189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall } 2035189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall return false; 2036189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall } 2037189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall 2038189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall if (VD->isEvaluatingValue()) 2039189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall return false; 2040189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall 2041189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall VD->setEvaluatingValue(); 2042189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall 2043189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall Expr::EvalResult InitResult; 2044189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall if (Init->Evaluate(InitResult, Info.Ctx) && !InitResult.HasSideEffects && 2045189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall InitResult.Val.isFloat()) { 2046189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall // Cache the evaluated value in the variable declaration. 2047189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall Result = InitResult.Val.getFloat(); 2048189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall VD->setEvaluatedValue(InitResult.Val); 2049189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall return true; 2050189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall } 2051189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall 2052189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall VD->setEvaluatedValue(APValue()); 2053189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall return false; 2054189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall} 2055189d6ef40eff11b83b2cda941d5ed89a5cef09b2John McCall 2056abd3a857ace59100305790545d1baae5877b8945John McCallbool FloatExprEvaluator::VisitUnaryReal(const UnaryOperator *E) { 205743efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman if (E->getSubExpr()->getType()->isAnyComplexType()) { 205843efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman ComplexValue CV; 205943efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman if (!EvaluateComplex(E->getSubExpr(), CV, Info)) 206043efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman return false; 206143efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman Result = CV.FloatReal; 206243efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman return true; 206343efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman } 206443efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman 206543efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman return Visit(E->getSubExpr()); 2066abd3a857ace59100305790545d1baae5877b8945John McCall} 2067abd3a857ace59100305790545d1baae5877b8945John McCall 2068abd3a857ace59100305790545d1baae5877b8945John McCallbool FloatExprEvaluator::VisitUnaryImag(const UnaryOperator *E) { 206943efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman if (E->getSubExpr()->getType()->isAnyComplexType()) { 207043efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman ComplexValue CV; 207143efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman if (!EvaluateComplex(E->getSubExpr(), CV, Info)) 207243efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman return false; 207343efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman Result = CV.FloatImag; 207443efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman return true; 207543efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman } 207643efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman 207743efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman if (!E->getSubExpr()->isEvaluatable(Info.Ctx)) 207843efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman Info.EvalResult.HasSideEffects = true; 207943efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman const llvm::fltSemantics &Sem = Info.Ctx.getFloatTypeSemantics(E->getType()); 208043efa31fe601bb7c3f132f02246dc3c903d9f361Eli Friedman Result = llvm::APFloat::getZero(Sem); 2081abd3a857ace59100305790545d1baae5877b8945John McCall return true; 2082abd3a857ace59100305790545d1baae5877b8945John McCall} 2083abd3a857ace59100305790545d1baae5877b8945John McCall 20845db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbarbool FloatExprEvaluator::VisitUnaryOperator(const UnaryOperator *E) { 20852de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall if (E->getOpcode() == UO_Deref) 2086a468d34bed16861f25aff6c8354f4e75d3358c1aNuno Lopes return false; 2087a468d34bed16861f25aff6c8354f4e75d3358c1aNuno Lopes 20885db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar if (!EvaluateFloat(E->getSubExpr(), Result, Info)) 20895db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar return false; 20905db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar 20915db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar switch (E->getOpcode()) { 20925db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar default: return false; 20932de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case UO_Plus: 20945db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar return true; 20952de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case UO_Minus: 20965db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar Result.changeSign(); 20975db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar return true; 20985db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar } 20995db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar} 2100019f4e858e78587f2241ff1a76c747d7bcd7578cChris Lattner 2101d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedmanbool FloatExprEvaluator::VisitBinaryOperator(const BinaryOperator *E) { 21022de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall if (E->getOpcode() == BO_Comma) { 21037f92f0362ef2cf218bc19bb83e1a97dd254b5527Eli Friedman if (!EvaluateFloat(E->getRHS(), Result, Info)) 21047f92f0362ef2cf218bc19bb83e1a97dd254b5527Eli Friedman return false; 21057f92f0362ef2cf218bc19bb83e1a97dd254b5527Eli Friedman 21067f92f0362ef2cf218bc19bb83e1a97dd254b5527Eli Friedman // If we can't evaluate the LHS, it might have side effects; 21077f92f0362ef2cf218bc19bb83e1a97dd254b5527Eli Friedman // conservatively mark it. 21087f92f0362ef2cf218bc19bb83e1a97dd254b5527Eli Friedman if (!E->getLHS()->isEvaluatable(Info.Ctx)) 21097f92f0362ef2cf218bc19bb83e1a97dd254b5527Eli Friedman Info.EvalResult.HasSideEffects = true; 21107f92f0362ef2cf218bc19bb83e1a97dd254b5527Eli Friedman 21117f92f0362ef2cf218bc19bb83e1a97dd254b5527Eli Friedman return true; 21127f92f0362ef2cf218bc19bb83e1a97dd254b5527Eli Friedman } 21137f92f0362ef2cf218bc19bb83e1a97dd254b5527Eli Friedman 211496e93660124c8028a4c3bcc038ab0cdd18cd7ab2Anders Carlsson // We can't evaluate pointer-to-member operations. 211596e93660124c8028a4c3bcc038ab0cdd18cd7ab2Anders Carlsson if (E->isPtrMemOp()) 211696e93660124c8028a4c3bcc038ab0cdd18cd7ab2Anders Carlsson return false; 211796e93660124c8028a4c3bcc038ab0cdd18cd7ab2Anders Carlsson 2118d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman // FIXME: Diagnostics? I really don't understand how the warnings 2119d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman // and errors are supposed to work. 21205db4b3f3ed9f769d5b02c1d1ccc52bfd71fb9afbDaniel Dunbar APFloat RHS(0.0); 2121d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman if (!EvaluateFloat(E->getLHS(), Result, Info)) 2122d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman return false; 2123d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman if (!EvaluateFloat(E->getRHS(), RHS, Info)) 2124d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman return false; 2125d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman 2126d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman switch (E->getOpcode()) { 2127d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman default: return false; 21282de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Mul: 2129d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman Result.multiply(RHS, APFloat::rmNearestTiesToEven); 2130d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman return true; 21312de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Add: 2132d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman Result.add(RHS, APFloat::rmNearestTiesToEven); 2133d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman return true; 21342de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Sub: 2135d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman Result.subtract(RHS, APFloat::rmNearestTiesToEven); 2136d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman return true; 21372de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Div: 2138d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman Result.divide(RHS, APFloat::rmNearestTiesToEven); 2139d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman return true; 2140d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman } 2141d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman} 2142d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman 2143d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedmanbool FloatExprEvaluator::VisitFloatingLiteral(const FloatingLiteral *E) { 2144d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman Result = E->getValue(); 2145d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman return true; 2146d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman} 2147d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman 21484efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedmanbool FloatExprEvaluator::VisitCastExpr(CastExpr *E) { 21494efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman Expr* SubExpr = E->getSubExpr(); 21501eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 21512ade35e2cfd554e49d35a52047cea98a82787af9Douglas Gregor if (SubExpr->getType()->isIntegralOrEnumerationType()) { 21524efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman APSInt IntResult; 21533f7d995390009fede92b333a040da80e1ce90997Daniel Dunbar if (!EvaluateInteger(SubExpr, IntResult, Info)) 21544efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman return false; 21551eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump Result = HandleIntToFloatCast(E->getType(), SubExpr->getType(), 2156a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar IntResult, Info.Ctx); 21574efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman return true; 21584efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman } 21594efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman if (SubExpr->getType()->isRealFloatingType()) { 21604efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman if (!Visit(SubExpr)) 21614efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman return false; 2162a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar Result = HandleFloatToFloatCast(E->getType(), SubExpr->getType(), 2163a2cfd34952204c9a160fe1a5da5ba2f231df891dDaniel Dunbar Result, Info.Ctx); 21644efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman return true; 21654efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman } 2166f3ea8cfe6b1c2ef0702efe130561e9e66708d799John McCall 2167f3ea8cfe6b1c2ef0702efe130561e9e66708d799John McCall if (E->getCastKind() == CK_FloatingComplexToReal) { 2168f3ea8cfe6b1c2ef0702efe130561e9e66708d799John McCall ComplexValue V; 2169f3ea8cfe6b1c2ef0702efe130561e9e66708d799John McCall if (!EvaluateComplex(SubExpr, V, Info)) 2170f3ea8cfe6b1c2ef0702efe130561e9e66708d799John McCall return false; 2171f3ea8cfe6b1c2ef0702efe130561e9e66708d799John McCall Result = V.getComplexFloatReal(); 2172f3ea8cfe6b1c2ef0702efe130561e9e66708d799John McCall return true; 2173f3ea8cfe6b1c2ef0702efe130561e9e66708d799John McCall } 21744efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman 21754efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman return false; 21764efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman} 21774efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman 2178ed8abf18329df67b0abcbb3a10458bd8c1d2a595Douglas Gregorbool FloatExprEvaluator::VisitCXXScalarValueInitExpr(CXXScalarValueInitExpr *E) { 21794efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman Result = APFloat::getZero(Info.Ctx.getFloatTypeSemantics(E->getType())); 21804efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman return true; 21814efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman} 21824efaa276bc0ce8f7baf6138ead11915f3e3e58d9Eli Friedman 218356ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCallbool FloatExprEvaluator:: 218456ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCallVisitBinaryConditionalOperator(BinaryConditionalOperator *e) { 218556ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall OpaqueValueEvaluation opaque(Info, e->getOpaqueValue(), e->getCommon()); 218656ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall if (opaque.hasError()) return false; 218756ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall 218856ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall bool cond; 218956ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall if (!HandleConversionToBool(e->getCond(), cond, Info)) 219056ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall return false; 219156ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall 219256ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall return Visit(cond ? e->getTrueExpr() : e->getFalseExpr()); 219356ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall} 219456ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall 219567f85fcdab64f36233a7211f963ed1cccffcbfb8Eli Friedmanbool FloatExprEvaluator::VisitConditionalOperator(ConditionalOperator *E) { 219667f85fcdab64f36233a7211f963ed1cccffcbfb8Eli Friedman bool Cond; 219767f85fcdab64f36233a7211f963ed1cccffcbfb8Eli Friedman if (!HandleConversionToBool(E->getCond(), Cond, Info)) 219867f85fcdab64f36233a7211f963ed1cccffcbfb8Eli Friedman return false; 219967f85fcdab64f36233a7211f963ed1cccffcbfb8Eli Friedman 220067f85fcdab64f36233a7211f963ed1cccffcbfb8Eli Friedman return Visit(Cond ? E->getTrueExpr() : E->getFalseExpr()); 220167f85fcdab64f36233a7211f963ed1cccffcbfb8Eli Friedman} 220267f85fcdab64f36233a7211f963ed1cccffcbfb8Eli Friedman 2203d8bfe7f25a695ca947effbccdf9ecbe3e018e221Eli Friedman//===----------------------------------------------------------------------===// 2204a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar// Complex Evaluation (for float and integer) 22059ad16aebc0e840a5e7d425da72eb6cbe25e4b58cAnders Carlsson//===----------------------------------------------------------------------===// 22069ad16aebc0e840a5e7d425da72eb6cbe25e4b58cAnders Carlsson 22079ad16aebc0e840a5e7d425da72eb6cbe25e4b58cAnders Carlssonnamespace { 2208770b4a8834670e9427d3ce5a1a8472eb86f45fd2Benjamin Kramerclass ComplexExprEvaluator 2209f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall : public StmtVisitor<ComplexExprEvaluator, bool> { 22109ad16aebc0e840a5e7d425da72eb6cbe25e4b58cAnders Carlsson EvalInfo &Info; 2211f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall ComplexValue &Result; 22121eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 22139ad16aebc0e840a5e7d425da72eb6cbe25e4b58cAnders Carlssonpublic: 2214f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall ComplexExprEvaluator(EvalInfo &info, ComplexValue &Result) 2215f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall : Info(info), Result(Result) {} 22161eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 22179ad16aebc0e840a5e7d425da72eb6cbe25e4b58cAnders Carlsson //===--------------------------------------------------------------------===// 22189ad16aebc0e840a5e7d425da72eb6cbe25e4b58cAnders Carlsson // Visitor Methods 22199ad16aebc0e840a5e7d425da72eb6cbe25e4b58cAnders Carlsson //===--------------------------------------------------------------------===// 22209ad16aebc0e840a5e7d425da72eb6cbe25e4b58cAnders Carlsson 2221f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall bool VisitStmt(Stmt *S) { 2222f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall return false; 22239ad16aebc0e840a5e7d425da72eb6cbe25e4b58cAnders Carlsson } 22241eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 2225f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall bool VisitParenExpr(ParenExpr *E) { return Visit(E->getSubExpr()); } 22269ad16aebc0e840a5e7d425da72eb6cbe25e4b58cAnders Carlsson 2227b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman bool VisitImaginaryLiteral(ImaginaryLiteral *E); 2228a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar 2229b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman bool VisitCastExpr(CastExpr *E); 2230b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman 2231b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman bool VisitBinaryOperator(const BinaryOperator *E); 223296fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara bool VisitUnaryOperator(const UnaryOperator *E); 223396fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara bool VisitConditionalOperator(const ConditionalOperator *E); 223456ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall bool VisitBinaryConditionalOperator(const BinaryConditionalOperator *E); 2235b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman bool VisitChooseExpr(const ChooseExpr *E) 2236b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman { return Visit(E->getChosenSubExpr(Info.Ctx)); } 2237b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman bool VisitUnaryExtension(const UnaryOperator *E) 2238b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman { return Visit(E->getSubExpr()); } 223956ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall bool VisitOpaqueValueExpr(const OpaqueValueExpr *e) { 224056ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall const APValue *value = Info.getOpaqueValue(e); 224156ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall if (!value) 224256ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall return (e->getSourceExpr() ? Visit(e->getSourceExpr()) : false); 224356ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall Result.setFrom(*value); 224456ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall return true; 224556ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall } 224696fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara // FIXME Missing: ImplicitValueInitExpr 2247b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman}; 2248b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman} // end anonymous namespace 22491eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 2250b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedmanstatic bool EvaluateComplex(const Expr *E, ComplexValue &Result, 2251b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman EvalInfo &Info) { 2252b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman assert(E->getType()->isAnyComplexType()); 2253b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman return ComplexExprEvaluator(Info, Result).Visit(const_cast<Expr*>(E)); 2254b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman} 2255b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman 2256b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedmanbool ComplexExprEvaluator::VisitImaginaryLiteral(ImaginaryLiteral *E) { 2257b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman Expr* SubExpr = E->getSubExpr(); 2258b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman 2259b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman if (SubExpr->getType()->isRealFloatingType()) { 2260b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman Result.makeComplexFloat(); 2261b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman APFloat &Imag = Result.FloatImag; 2262b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman if (!EvaluateFloat(SubExpr, Imag, Info)) 2263b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman return false; 2264b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman 2265b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman Result.FloatReal = APFloat(Imag.getSemantics()); 2266b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman return true; 2267b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman } else { 2268b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman assert(SubExpr->getType()->isIntegerType() && 2269b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman "Unexpected imaginary literal."); 2270b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman 2271b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman Result.makeComplexInt(); 2272b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman APSInt &Imag = Result.IntImag; 2273b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman if (!EvaluateInteger(SubExpr, Imag, Info)) 2274b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman return false; 2275b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman 2276b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman Result.IntReal = APSInt(Imag.getBitWidth(), !Imag.isSigned()); 2277b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman return true; 2278b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman } 2279b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman} 2280b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman 2281b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedmanbool ComplexExprEvaluator::VisitCastExpr(CastExpr *E) { 2282b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman 22838786da77984e81d48e0e1b2bd339809b1efc19f3John McCall switch (E->getCastKind()) { 22848786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_BitCast: 22858786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_LValueBitCast: 22868786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_BaseToDerived: 22878786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_DerivedToBase: 22888786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_UncheckedDerivedToBase: 22898786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_Dynamic: 22908786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_ToUnion: 22918786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_ArrayToPointerDecay: 22928786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_FunctionToPointerDecay: 22938786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_NullToPointer: 22948786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_NullToMemberPointer: 22958786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_BaseToDerivedMemberPointer: 22968786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_DerivedToBaseMemberPointer: 22978786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_MemberPointerToBoolean: 22988786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_ConstructorConversion: 22998786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_IntegralToPointer: 23008786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_PointerToIntegral: 23018786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_PointerToBoolean: 23028786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_ToVoid: 23038786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_VectorSplat: 23048786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_IntegralCast: 23058786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_IntegralToBoolean: 23068786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_IntegralToFloating: 23078786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_FloatingToIntegral: 23088786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_FloatingToBoolean: 23098786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_FloatingCast: 23108786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_AnyPointerToObjCPointerCast: 23118786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_AnyPointerToBlockPointerCast: 23128786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_ObjCObjectLValueCast: 23138786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_FloatingComplexToReal: 23148786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_FloatingComplexToBoolean: 23158786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_IntegralComplexToReal: 23168786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_IntegralComplexToBoolean: 23178786da77984e81d48e0e1b2bd339809b1efc19f3John McCall llvm_unreachable("invalid cast kind for complex value"); 23188786da77984e81d48e0e1b2bd339809b1efc19f3John McCall 23198786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_LValueToRValue: 23208786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_NoOp: 23218786da77984e81d48e0e1b2bd339809b1efc19f3John McCall return Visit(E->getSubExpr()); 23222bb5d00fcf71a7b4d478d478be778fff0494aff6John McCall 23238786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_Dependent: 23248786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_GetObjCProperty: 23258786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_UserDefinedConversion: 23268786da77984e81d48e0e1b2bd339809b1efc19f3John McCall return false; 23278786da77984e81d48e0e1b2bd339809b1efc19f3John McCall 23288786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_FloatingRealToComplex: { 2329b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman APFloat &Real = Result.FloatReal; 23308786da77984e81d48e0e1b2bd339809b1efc19f3John McCall if (!EvaluateFloat(E->getSubExpr(), Real, Info)) 2331b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman return false; 2332b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman 23338786da77984e81d48e0e1b2bd339809b1efc19f3John McCall Result.makeComplexFloat(); 23348786da77984e81d48e0e1b2bd339809b1efc19f3John McCall Result.FloatImag = APFloat(Real.getSemantics()); 23358786da77984e81d48e0e1b2bd339809b1efc19f3John McCall return true; 23368786da77984e81d48e0e1b2bd339809b1efc19f3John McCall } 23378786da77984e81d48e0e1b2bd339809b1efc19f3John McCall 23388786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_FloatingComplexCast: { 23398786da77984e81d48e0e1b2bd339809b1efc19f3John McCall if (!Visit(E->getSubExpr())) 23408786da77984e81d48e0e1b2bd339809b1efc19f3John McCall return false; 23418786da77984e81d48e0e1b2bd339809b1efc19f3John McCall 23428786da77984e81d48e0e1b2bd339809b1efc19f3John McCall QualType To = E->getType()->getAs<ComplexType>()->getElementType(); 23438786da77984e81d48e0e1b2bd339809b1efc19f3John McCall QualType From 23448786da77984e81d48e0e1b2bd339809b1efc19f3John McCall = E->getSubExpr()->getType()->getAs<ComplexType>()->getElementType(); 23458786da77984e81d48e0e1b2bd339809b1efc19f3John McCall 23468786da77984e81d48e0e1b2bd339809b1efc19f3John McCall Result.FloatReal 23478786da77984e81d48e0e1b2bd339809b1efc19f3John McCall = HandleFloatToFloatCast(To, From, Result.FloatReal, Info.Ctx); 23488786da77984e81d48e0e1b2bd339809b1efc19f3John McCall Result.FloatImag 23498786da77984e81d48e0e1b2bd339809b1efc19f3John McCall = HandleFloatToFloatCast(To, From, Result.FloatImag, Info.Ctx); 23508786da77984e81d48e0e1b2bd339809b1efc19f3John McCall return true; 23518786da77984e81d48e0e1b2bd339809b1efc19f3John McCall } 23528786da77984e81d48e0e1b2bd339809b1efc19f3John McCall 23538786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_FloatingComplexToIntegralComplex: { 23548786da77984e81d48e0e1b2bd339809b1efc19f3John McCall if (!Visit(E->getSubExpr())) 23558786da77984e81d48e0e1b2bd339809b1efc19f3John McCall return false; 23568786da77984e81d48e0e1b2bd339809b1efc19f3John McCall 23578786da77984e81d48e0e1b2bd339809b1efc19f3John McCall QualType To = E->getType()->getAs<ComplexType>()->getElementType(); 23588786da77984e81d48e0e1b2bd339809b1efc19f3John McCall QualType From 23598786da77984e81d48e0e1b2bd339809b1efc19f3John McCall = E->getSubExpr()->getType()->getAs<ComplexType>()->getElementType(); 23608786da77984e81d48e0e1b2bd339809b1efc19f3John McCall Result.makeComplexInt(); 23618786da77984e81d48e0e1b2bd339809b1efc19f3John McCall Result.IntReal = HandleFloatToIntCast(To, From, Result.FloatReal, Info.Ctx); 23628786da77984e81d48e0e1b2bd339809b1efc19f3John McCall Result.IntImag = HandleFloatToIntCast(To, From, Result.FloatImag, Info.Ctx); 23638786da77984e81d48e0e1b2bd339809b1efc19f3John McCall return true; 23648786da77984e81d48e0e1b2bd339809b1efc19f3John McCall } 23658786da77984e81d48e0e1b2bd339809b1efc19f3John McCall 23668786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_IntegralRealToComplex: { 2367b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman APSInt &Real = Result.IntReal; 23688786da77984e81d48e0e1b2bd339809b1efc19f3John McCall if (!EvaluateInteger(E->getSubExpr(), Real, Info)) 2369b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman return false; 23709ad16aebc0e840a5e7d425da72eb6cbe25e4b58cAnders Carlsson 23718786da77984e81d48e0e1b2bd339809b1efc19f3John McCall Result.makeComplexInt(); 23728786da77984e81d48e0e1b2bd339809b1efc19f3John McCall Result.IntImag = APSInt(Real.getBitWidth(), !Real.isSigned()); 23738786da77984e81d48e0e1b2bd339809b1efc19f3John McCall return true; 23748786da77984e81d48e0e1b2bd339809b1efc19f3John McCall } 23758786da77984e81d48e0e1b2bd339809b1efc19f3John McCall 23768786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_IntegralComplexCast: { 23778786da77984e81d48e0e1b2bd339809b1efc19f3John McCall if (!Visit(E->getSubExpr())) 2378b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman return false; 2379ccc3fce5697e33f005990f9795e1c7cb8b4559ecAnders Carlsson 23808786da77984e81d48e0e1b2bd339809b1efc19f3John McCall QualType To = E->getType()->getAs<ComplexType>()->getElementType(); 23818786da77984e81d48e0e1b2bd339809b1efc19f3John McCall QualType From 23828786da77984e81d48e0e1b2bd339809b1efc19f3John McCall = E->getSubExpr()->getType()->getAs<ComplexType>()->getElementType(); 23831725f683432715e5afe34d476024bd6f16eac3fcEli Friedman 23848786da77984e81d48e0e1b2bd339809b1efc19f3John McCall Result.IntReal = HandleIntToIntCast(To, From, Result.IntReal, Info.Ctx); 23858786da77984e81d48e0e1b2bd339809b1efc19f3John McCall Result.IntImag = HandleIntToIntCast(To, From, Result.IntImag, Info.Ctx); 23868786da77984e81d48e0e1b2bd339809b1efc19f3John McCall return true; 23878786da77984e81d48e0e1b2bd339809b1efc19f3John McCall } 23888786da77984e81d48e0e1b2bd339809b1efc19f3John McCall 23898786da77984e81d48e0e1b2bd339809b1efc19f3John McCall case CK_IntegralComplexToFloatingComplex: { 23908786da77984e81d48e0e1b2bd339809b1efc19f3John McCall if (!Visit(E->getSubExpr())) 23918786da77984e81d48e0e1b2bd339809b1efc19f3John McCall return false; 23928786da77984e81d48e0e1b2bd339809b1efc19f3John McCall 23938786da77984e81d48e0e1b2bd339809b1efc19f3John McCall QualType To = E->getType()->getAs<ComplexType>()->getElementType(); 23948786da77984e81d48e0e1b2bd339809b1efc19f3John McCall QualType From 23958786da77984e81d48e0e1b2bd339809b1efc19f3John McCall = E->getSubExpr()->getType()->getAs<ComplexType>()->getElementType(); 23968786da77984e81d48e0e1b2bd339809b1efc19f3John McCall Result.makeComplexFloat(); 23978786da77984e81d48e0e1b2bd339809b1efc19f3John McCall Result.FloatReal = HandleIntToFloatCast(To, From, Result.IntReal, Info.Ctx); 23988786da77984e81d48e0e1b2bd339809b1efc19f3John McCall Result.FloatImag = HandleIntToFloatCast(To, From, Result.IntImag, Info.Ctx); 23998786da77984e81d48e0e1b2bd339809b1efc19f3John McCall return true; 24008786da77984e81d48e0e1b2bd339809b1efc19f3John McCall } 2401ccc3fce5697e33f005990f9795e1c7cb8b4559ecAnders Carlsson } 24021eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 24038786da77984e81d48e0e1b2bd339809b1efc19f3John McCall llvm_unreachable("unknown cast resulting in complex value"); 2404b2dc7f59fe4c762cba73badc3bbc6f356fcd7b5bEli Friedman return false; 24059ad16aebc0e840a5e7d425da72eb6cbe25e4b58cAnders Carlsson} 24069ad16aebc0e840a5e7d425da72eb6cbe25e4b58cAnders Carlsson 2407f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCallbool ComplexExprEvaluator::VisitBinaryOperator(const BinaryOperator *E) { 240896fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara if (E->getOpcode() == BO_Comma) { 240996fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara if (!Visit(E->getRHS())) 241096fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara return false; 241196fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara 241296fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara // If we can't evaluate the LHS, it might have side effects; 241396fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara // conservatively mark it. 241496fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara if (!E->getLHS()->isEvaluatable(Info.Ctx)) 241596fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Info.EvalResult.HasSideEffects = true; 241696fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara 241796fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara return true; 241896fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara } 2419f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall if (!Visit(E->getLHS())) 2420f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall return false; 24211eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 2422f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall ComplexValue RHS; 2423a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar if (!EvaluateComplex(E->getRHS(), RHS, Info)) 2424f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall return false; 2425a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar 24263f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar assert(Result.isComplexFloat() == RHS.isComplexFloat() && 24273f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar "Invalid operands to binary operator."); 2428ccc3fce5697e33f005990f9795e1c7cb8b4559ecAnders Carlsson switch (E->getOpcode()) { 2429f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall default: return false; 24302de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Add: 2431a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar if (Result.isComplexFloat()) { 2432a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar Result.getComplexFloatReal().add(RHS.getComplexFloatReal(), 2433a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar APFloat::rmNearestTiesToEven); 2434a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar Result.getComplexFloatImag().add(RHS.getComplexFloatImag(), 2435a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar APFloat::rmNearestTiesToEven); 2436a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar } else { 2437a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar Result.getComplexIntReal() += RHS.getComplexIntReal(); 2438a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar Result.getComplexIntImag() += RHS.getComplexIntImag(); 2439a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar } 24403f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar break; 24412de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Sub: 2442a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar if (Result.isComplexFloat()) { 2443a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar Result.getComplexFloatReal().subtract(RHS.getComplexFloatReal(), 2444a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar APFloat::rmNearestTiesToEven); 2445a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar Result.getComplexFloatImag().subtract(RHS.getComplexFloatImag(), 2446a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar APFloat::rmNearestTiesToEven); 2447a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar } else { 2448a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar Result.getComplexIntReal() -= RHS.getComplexIntReal(); 2449a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar Result.getComplexIntImag() -= RHS.getComplexIntImag(); 2450a5fd07bbc5e4bae542c06643da3fbfe4967a9379Daniel Dunbar } 24513f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar break; 24522de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Mul: 24533f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar if (Result.isComplexFloat()) { 2454f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall ComplexValue LHS = Result; 24553f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar APFloat &LHS_r = LHS.getComplexFloatReal(); 24563f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar APFloat &LHS_i = LHS.getComplexFloatImag(); 24573f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar APFloat &RHS_r = RHS.getComplexFloatReal(); 24583f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar APFloat &RHS_i = RHS.getComplexFloatImag(); 24591eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 24603f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar APFloat Tmp = LHS_r; 24613f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar Tmp.multiply(RHS_r, APFloat::rmNearestTiesToEven); 24623f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar Result.getComplexFloatReal() = Tmp; 24633f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar Tmp = LHS_i; 24643f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar Tmp.multiply(RHS_i, APFloat::rmNearestTiesToEven); 24653f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar Result.getComplexFloatReal().subtract(Tmp, APFloat::rmNearestTiesToEven); 24663f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar 24673f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar Tmp = LHS_r; 24683f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar Tmp.multiply(RHS_i, APFloat::rmNearestTiesToEven); 24693f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar Result.getComplexFloatImag() = Tmp; 24703f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar Tmp = LHS_i; 24713f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar Tmp.multiply(RHS_r, APFloat::rmNearestTiesToEven); 24723f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar Result.getComplexFloatImag().add(Tmp, APFloat::rmNearestTiesToEven); 24733f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar } else { 2474f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall ComplexValue LHS = Result; 24751eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump Result.getComplexIntReal() = 24763f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar (LHS.getComplexIntReal() * RHS.getComplexIntReal() - 24773f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar LHS.getComplexIntImag() * RHS.getComplexIntImag()); 24781eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump Result.getComplexIntImag() = 24793f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar (LHS.getComplexIntReal() * RHS.getComplexIntImag() + 24803f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar LHS.getComplexIntImag() * RHS.getComplexIntReal()); 24813f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar } 24823f2798757c9ee353e207e18115e2e966432a4beeDaniel Dunbar break; 248396fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara case BO_Div: 248496fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara if (Result.isComplexFloat()) { 248596fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara ComplexValue LHS = Result; 248696fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara APFloat &LHS_r = LHS.getComplexFloatReal(); 248796fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara APFloat &LHS_i = LHS.getComplexFloatImag(); 248896fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara APFloat &RHS_r = RHS.getComplexFloatReal(); 248996fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara APFloat &RHS_i = RHS.getComplexFloatImag(); 249096fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara APFloat &Res_r = Result.getComplexFloatReal(); 249196fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara APFloat &Res_i = Result.getComplexFloatImag(); 249296fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara 249396fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara APFloat Den = RHS_r; 249496fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Den.multiply(RHS_r, APFloat::rmNearestTiesToEven); 249596fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara APFloat Tmp = RHS_i; 249696fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Tmp.multiply(RHS_i, APFloat::rmNearestTiesToEven); 249796fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Den.add(Tmp, APFloat::rmNearestTiesToEven); 249896fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara 249996fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Res_r = LHS_r; 250096fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Res_r.multiply(RHS_r, APFloat::rmNearestTiesToEven); 250196fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Tmp = LHS_i; 250296fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Tmp.multiply(RHS_i, APFloat::rmNearestTiesToEven); 250396fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Res_r.add(Tmp, APFloat::rmNearestTiesToEven); 250496fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Res_r.divide(Den, APFloat::rmNearestTiesToEven); 250596fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara 250696fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Res_i = LHS_i; 250796fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Res_i.multiply(RHS_r, APFloat::rmNearestTiesToEven); 250896fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Tmp = LHS_r; 250996fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Tmp.multiply(RHS_i, APFloat::rmNearestTiesToEven); 251096fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Res_i.subtract(Tmp, APFloat::rmNearestTiesToEven); 251196fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Res_i.divide(Den, APFloat::rmNearestTiesToEven); 251296fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara } else { 251396fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara if (RHS.getComplexIntReal() == 0 && RHS.getComplexIntImag() == 0) { 251496fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara // FIXME: what about diagnostics? 251596fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara return false; 251696fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara } 251796fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara ComplexValue LHS = Result; 251896fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara APSInt Den = RHS.getComplexIntReal() * RHS.getComplexIntReal() + 251996fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara RHS.getComplexIntImag() * RHS.getComplexIntImag(); 252096fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Result.getComplexIntReal() = 252196fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara (LHS.getComplexIntReal() * RHS.getComplexIntReal() + 252296fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara LHS.getComplexIntImag() * RHS.getComplexIntImag()) / Den; 252396fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Result.getComplexIntImag() = 252496fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara (LHS.getComplexIntImag() * RHS.getComplexIntReal() - 252596fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara LHS.getComplexIntReal() * RHS.getComplexIntImag()) / Den; 252696fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara } 252796fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara break; 2528ccc3fce5697e33f005990f9795e1c7cb8b4559ecAnders Carlsson } 2529ccc3fce5697e33f005990f9795e1c7cb8b4559ecAnders Carlsson 2530f4cf1a18d09d57b757b3cb47eab36c1457091ef7John McCall return true; 2531ccc3fce5697e33f005990f9795e1c7cb8b4559ecAnders Carlsson} 2532ccc3fce5697e33f005990f9795e1c7cb8b4559ecAnders Carlsson 253396fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnarabool ComplexExprEvaluator::VisitUnaryOperator(const UnaryOperator *E) { 253496fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara // Get the operand value into 'Result'. 253596fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara if (!Visit(E->getSubExpr())) 253696fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara return false; 253796fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara 253896fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara switch (E->getOpcode()) { 253996fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara default: 254096fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara // FIXME: what about diagnostics? 254196fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara return false; 254296fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara case UO_Extension: 254396fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara return true; 254496fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara case UO_Plus: 254596fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara // The result is always just the subexpr. 254696fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara return true; 254796fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara case UO_Minus: 254896fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara if (Result.isComplexFloat()) { 254996fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Result.getComplexFloatReal().changeSign(); 255096fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Result.getComplexFloatImag().changeSign(); 255196fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara } 255296fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara else { 255396fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Result.getComplexIntReal() = -Result.getComplexIntReal(); 255496fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Result.getComplexIntImag() = -Result.getComplexIntImag(); 255596fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara } 255696fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara return true; 255796fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara case UO_Not: 255896fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara if (Result.isComplexFloat()) 255996fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Result.getComplexFloatImag().changeSign(); 256096fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara else 256196fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara Result.getComplexIntImag() = -Result.getComplexIntImag(); 256296fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara return true; 256396fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara } 256496fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara} 256596fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara 256656ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCallbool ComplexExprEvaluator:: 256756ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCallVisitBinaryConditionalOperator(const BinaryConditionalOperator *e) { 256856ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall OpaqueValueEvaluation opaque(Info, e->getOpaqueValue(), e->getCommon()); 256956ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall if (opaque.hasError()) return false; 257056ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall 257156ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall bool cond; 257256ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall if (!HandleConversionToBool(e->getCond(), cond, Info)) 257356ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall return false; 257456ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall 257556ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall return Visit(cond ? e->getTrueExpr() : e->getFalseExpr()); 257656ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall} 257756ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall 257896fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnarabool ComplexExprEvaluator::VisitConditionalOperator(const ConditionalOperator *E) { 257996fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara bool Cond; 258096fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara if (!HandleConversionToBool(E->getCond(), Cond, Info)) 258196fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara return false; 258296fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara 258396fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara return Visit(Cond ? E->getTrueExpr() : E->getFalseExpr()); 258496fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara} 258596fc8e4086df323c49f17cac594db1d2f066a2e9Abramo Bagnara 25869ad16aebc0e840a5e7d425da72eb6cbe25e4b58cAnders Carlsson//===----------------------------------------------------------------------===// 25876ee7aa154e8bbb21a21254293410b944f78b0bfeChris Lattner// Top level Expr::Evaluate method. 2588f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner//===----------------------------------------------------------------------===// 2589f5eeb055ecbadbc25c83df0867cdada2c2559dcfChris Lattner 259056ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCallstatic bool Evaluate(EvalInfo &Info, const Expr *E) { 2591efdb83e26f9a1fd2566afe54461216cd84814d42John McCall if (E->getType()->isVectorType()) { 2592efdb83e26f9a1fd2566afe54461216cd84814d42John McCall if (!EvaluateVector(E, Info.EvalResult.Val, Info)) 259359b5da6d853b4368b984700315adf7b37de05764Nate Begeman return false; 2594efdb83e26f9a1fd2566afe54461216cd84814d42John McCall } else if (E->getType()->isIntegerType()) { 2595efdb83e26f9a1fd2566afe54461216cd84814d42John McCall if (!IntExprEvaluator(Info, Info.EvalResult.Val).Visit(const_cast<Expr*>(E))) 25966dde0d5dc09f45f4d9508c964703e36fef1a0198Anders Carlsson return false; 259756ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall if (Info.EvalResult.Val.isLValue() && 259856ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall !IsGlobalLValue(Info.EvalResult.Val.getLValueBase())) 25990f2b692bb10be35fdc60d0a72a847bdd73124670John McCall return false; 2600efdb83e26f9a1fd2566afe54461216cd84814d42John McCall } else if (E->getType()->hasPointerRepresentation()) { 2601efdb83e26f9a1fd2566afe54461216cd84814d42John McCall LValue LV; 2602efdb83e26f9a1fd2566afe54461216cd84814d42John McCall if (!EvaluatePointer(E, LV, Info)) 26036dde0d5dc09f45f4d9508c964703e36fef1a0198Anders Carlsson return false; 2604e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara if (!IsGlobalLValue(LV.Base)) 260542c8f87eb60958170c46767273bf93e6c96125bfJohn McCall return false; 2606efdb83e26f9a1fd2566afe54461216cd84814d42John McCall LV.moveInto(Info.EvalResult.Val); 2607efdb83e26f9a1fd2566afe54461216cd84814d42John McCall } else if (E->getType()->isRealFloatingType()) { 2608efdb83e26f9a1fd2566afe54461216cd84814d42John McCall llvm::APFloat F(0.0); 2609efdb83e26f9a1fd2566afe54461216cd84814d42John McCall if (!EvaluateFloat(E, F, Info)) 26106dde0d5dc09f45f4d9508c964703e36fef1a0198Anders Carlsson return false; 26111eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump 2612efdb83e26f9a1fd2566afe54461216cd84814d42John McCall Info.EvalResult.Val = APValue(F); 2613efdb83e26f9a1fd2566afe54461216cd84814d42John McCall } else if (E->getType()->isAnyComplexType()) { 2614efdb83e26f9a1fd2566afe54461216cd84814d42John McCall ComplexValue C; 2615efdb83e26f9a1fd2566afe54461216cd84814d42John McCall if (!EvaluateComplex(E, C, Info)) 2616660e6f79a138a30a437c02142f23e7ef4eb21b2eMike Stump return false; 2617efdb83e26f9a1fd2566afe54461216cd84814d42John McCall C.moveInto(Info.EvalResult.Val); 2618660e6f79a138a30a437c02142f23e7ef4eb21b2eMike Stump } else 2619660e6f79a138a30a437c02142f23e7ef4eb21b2eMike Stump return false; 2620660e6f79a138a30a437c02142f23e7ef4eb21b2eMike Stump 2621660e6f79a138a30a437c02142f23e7ef4eb21b2eMike Stump return true; 2622660e6f79a138a30a437c02142f23e7ef4eb21b2eMike Stump} 2623660e6f79a138a30a437c02142f23e7ef4eb21b2eMike Stump 262456ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall/// Evaluate - Return true if this is a constant which we can fold using 262556ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall/// any crazy technique (that has nothing to do with language standards) that 262656ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall/// we want to. If this function returns true, it returns the folded constant 262756ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall/// in Result. 262856ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCallbool Expr::Evaluate(EvalResult &Result, const ASTContext &Ctx) const { 262956ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall EvalInfo Info(Ctx, Result); 263056ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall return ::Evaluate(Info, this); 263156ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall} 263256ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall 26334ba2a17694148e16eaa8d3917f657ffcd3667be4Jay Foadbool Expr::EvaluateAsBooleanCondition(bool &Result, 26344ba2a17694148e16eaa8d3917f657ffcd3667be4Jay Foad const ASTContext &Ctx) const { 2635cd7a445c6b46c5585580dfb652300c8483c0cb6bJohn McCall EvalResult Scratch; 2636cd7a445c6b46c5585580dfb652300c8483c0cb6bJohn McCall EvalInfo Info(Ctx, Scratch); 2637cd7a445c6b46c5585580dfb652300c8483c0cb6bJohn McCall 2638cd7a445c6b46c5585580dfb652300c8483c0cb6bJohn McCall return HandleConversionToBool(this, Result, Info); 2639cd7a445c6b46c5585580dfb652300c8483c0cb6bJohn McCall} 2640cd7a445c6b46c5585580dfb652300c8483c0cb6bJohn McCall 26414ba2a17694148e16eaa8d3917f657ffcd3667be4Jay Foadbool Expr::EvaluateAsLValue(EvalResult &Result, const ASTContext &Ctx) const { 26421b78276a75a5a0f496a82429c1ff9604d622a76dAnders Carlsson EvalInfo Info(Ctx, Result); 26431b78276a75a5a0f496a82429c1ff9604d622a76dAnders Carlsson 2644efdb83e26f9a1fd2566afe54461216cd84814d42John McCall LValue LV; 264542c8f87eb60958170c46767273bf93e6c96125bfJohn McCall if (EvaluateLValue(this, LV, Info) && 264642c8f87eb60958170c46767273bf93e6c96125bfJohn McCall !Result.HasSideEffects && 2647e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara IsGlobalLValue(LV.Base)) { 2648e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara LV.moveInto(Result.Val); 2649e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara return true; 2650e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara } 2651e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara return false; 2652e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara} 2653e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara 26544ba2a17694148e16eaa8d3917f657ffcd3667be4Jay Foadbool Expr::EvaluateAsAnyLValue(EvalResult &Result, 26554ba2a17694148e16eaa8d3917f657ffcd3667be4Jay Foad const ASTContext &Ctx) const { 2656e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara EvalInfo Info(Ctx, Result); 2657e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara 2658e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara LValue LV; 2659e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara if (EvaluateLValue(this, LV, Info)) { 2660efdb83e26f9a1fd2566afe54461216cd84814d42John McCall LV.moveInto(Result.Val); 2661efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return true; 2662efdb83e26f9a1fd2566afe54461216cd84814d42John McCall } 2663efdb83e26f9a1fd2566afe54461216cd84814d42John McCall return false; 2664b2f295c8050fb8c141bf2cf38eed0a56e99d0092Eli Friedman} 2665b2f295c8050fb8c141bf2cf38eed0a56e99d0092Eli Friedman 26666ee7aa154e8bbb21a21254293410b944f78b0bfeChris Lattner/// isEvaluatable - Call Evaluate to see if this expression can be constant 266745b6b9d080ac56917337d73d8f1cd6374b27b05dChris Lattner/// folded, but discard the result. 26684ba2a17694148e16eaa8d3917f657ffcd3667be4Jay Foadbool Expr::isEvaluatable(const ASTContext &Ctx) const { 26694fdfb0965b396f2778091f7e6c051d17ff9791baAnders Carlsson EvalResult Result; 26704fdfb0965b396f2778091f7e6c051d17ff9791baAnders Carlsson return Evaluate(Result, Ctx) && !Result.HasSideEffects; 267145b6b9d080ac56917337d73d8f1cd6374b27b05dChris Lattner} 267251fe996231b1d7199f76e4005ff4c943d5deeecdAnders Carlsson 26734ba2a17694148e16eaa8d3917f657ffcd3667be4Jay Foadbool Expr::HasSideEffects(const ASTContext &Ctx) const { 2674393c247fe025ccb5f914e37e948192ea86faef8cFariborz Jahanian Expr::EvalResult Result; 2675393c247fe025ccb5f914e37e948192ea86faef8cFariborz Jahanian EvalInfo Info(Ctx, Result); 2676393c247fe025ccb5f914e37e948192ea86faef8cFariborz Jahanian return HasSideEffect(Info).Visit(const_cast<Expr*>(this)); 2677393c247fe025ccb5f914e37e948192ea86faef8cFariborz Jahanian} 2678393c247fe025ccb5f914e37e948192ea86faef8cFariborz Jahanian 26794ba2a17694148e16eaa8d3917f657ffcd3667be4Jay FoadAPSInt Expr::EvaluateAsInt(const ASTContext &Ctx) const { 26801c0cfd4599e816cfd7a8f348286bf0ad79652ffcAnders Carlsson EvalResult EvalResult; 26811c0cfd4599e816cfd7a8f348286bf0ad79652ffcAnders Carlsson bool Result = Evaluate(EvalResult, Ctx); 2682c6ed729f669044f5072a49d79041f455d971ece3Jeffrey Yasskin (void)Result; 268351fe996231b1d7199f76e4005ff4c943d5deeecdAnders Carlsson assert(Result && "Could not evaluate expression"); 26841c0cfd4599e816cfd7a8f348286bf0ad79652ffcAnders Carlsson assert(EvalResult.Val.isInt() && "Expression did not evaluate to integer"); 268551fe996231b1d7199f76e4005ff4c943d5deeecdAnders Carlsson 26861c0cfd4599e816cfd7a8f348286bf0ad79652ffcAnders Carlsson return EvalResult.Val.getInt(); 268751fe996231b1d7199f76e4005ff4c943d5deeecdAnders Carlsson} 2688d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall 2689e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara bool Expr::EvalResult::isGlobalLValue() const { 2690e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara assert(Val.isLValue()); 2691e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara return IsGlobalLValue(Val.getLValueBase()); 2692e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara } 2693e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara 2694e17a6436b429e4b18a5e157061fb13bbc677b3b0Abramo Bagnara 2695d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall/// isIntegerConstantExpr - this recursive routine will test if an expression is 2696d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall/// an integer constant expression. 2697d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall 2698d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall/// FIXME: Pass up a reason why! Invalid operation in i-c-e, division by zero, 2699d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall/// comma, etc 2700d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall/// 2701d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall/// FIXME: Handle offsetof. Two things to do: Handle GCC's __builtin_offsetof 2702d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall/// to support gcc 4.0+ and handle the idiom GCC recognizes with a null pointer 2703d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall/// cast+dereference. 2704d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall 2705d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall// CheckICE - This function does the fundamental ICE checking: the returned 2706d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall// ICEDiag contains a Val of 0, 1, or 2, and a possibly null SourceLocation. 2707d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall// Note that to reduce code duplication, this helper does no evaluation 2708d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall// itself; the caller checks whether the expression is evaluatable, and 2709d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall// in the rare cases where CheckICE actually cares about the evaluated 2710d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall// value, it calls into Evalute. 2711d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall// 2712d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall// Meanings of Val: 2713d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall// 0: This expression is an ICE if it can be evaluated by Evaluate. 2714d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall// 1: This expression is not an ICE, but if it isn't evaluated, it's 2715d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall// a legal subexpression for an ICE. This return value is used to handle 2716d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall// the comma operator in C99 mode. 2717d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall// 2: This expression is not an ICE, and is not a legal subexpression for one. 2718d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall 27193c46e8db99196179b30e7ac5c20c4efd5f3926d7Dan Gohmannamespace { 27203c46e8db99196179b30e7ac5c20c4efd5f3926d7Dan Gohman 2721d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCallstruct ICEDiag { 2722d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall unsigned Val; 2723d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall SourceLocation Loc; 2724d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall 2725d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall public: 2726d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall ICEDiag(unsigned v, SourceLocation l) : Val(v), Loc(l) {} 2727d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall ICEDiag() : Val(0) {} 2728d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall}; 2729d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall 27303c46e8db99196179b30e7ac5c20c4efd5f3926d7Dan Gohman} 27313c46e8db99196179b30e7ac5c20c4efd5f3926d7Dan Gohman 27323c46e8db99196179b30e7ac5c20c4efd5f3926d7Dan Gohmanstatic ICEDiag NoDiag() { return ICEDiag(); } 2733d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall 2734d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCallstatic ICEDiag CheckEvalInICE(const Expr* E, ASTContext &Ctx) { 2735d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall Expr::EvalResult EVResult; 2736d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (!E->Evaluate(EVResult, Ctx) || EVResult.HasSideEffects || 2737d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall !EVResult.Val.isInt()) { 2738d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return ICEDiag(2, E->getLocStart()); 2739d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 2740d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return NoDiag(); 2741d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall} 2742d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall 2743d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCallstatic ICEDiag CheckICE(const Expr* E, ASTContext &Ctx) { 2744d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall assert(!E->isValueDependent() && "Should not see value dependent exprs!"); 27452ade35e2cfd554e49d35a52047cea98a82787af9Douglas Gregor if (!E->getType()->isIntegralOrEnumerationType()) { 2746d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return ICEDiag(2, E->getLocStart()); 2747d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 2748d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall 2749d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall switch (E->getStmtClass()) { 275063c00d7f35fa060c0a446c9df3a4402d9c7757feJohn McCall#define ABSTRACT_STMT(Node) 2751d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall#define STMT(Node, Base) case Expr::Node##Class: 2752d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall#define EXPR(Node, Base) 2753d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall#include "clang/AST/StmtNodes.inc" 2754d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::PredefinedExprClass: 2755d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::FloatingLiteralClass: 2756d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::ImaginaryLiteralClass: 2757d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::StringLiteralClass: 2758d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::ArraySubscriptExprClass: 2759d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::MemberExprClass: 2760d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CompoundAssignOperatorClass: 2761d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CompoundLiteralExprClass: 2762d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::ExtVectorElementExprClass: 2763d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::InitListExprClass: 2764d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::DesignatedInitExprClass: 2765d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::ImplicitValueInitExprClass: 2766d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::ParenListExprClass: 2767d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::VAArgExprClass: 2768d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::AddrLabelExprClass: 2769d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::StmtExprClass: 2770d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CXXMemberCallExprClass: 2771e08ce650a2b02410eddd1f60a4aa6b3d4be71e73Peter Collingbourne case Expr::CUDAKernelCallExprClass: 2772d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CXXDynamicCastExprClass: 2773d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CXXTypeidExprClass: 27749be88403e965cc49af76c9d33d818781d44b333eFrancois Pichet case Expr::CXXUuidofExprClass: 2775d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CXXNullPtrLiteralExprClass: 2776d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CXXThisExprClass: 2777d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CXXThrowExprClass: 2778d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CXXNewExprClass: 2779d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CXXDeleteExprClass: 2780d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CXXPseudoDestructorExprClass: 2781d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::UnresolvedLookupExprClass: 2782d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::DependentScopeDeclRefExprClass: 2783d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CXXConstructExprClass: 2784d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CXXBindTemporaryExprClass: 27854765fa05b5652fcc4356371c2f481d0ea9a1b007John McCall case Expr::ExprWithCleanupsClass: 2786d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CXXTemporaryObjectExprClass: 2787d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CXXUnresolvedConstructExprClass: 2788d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CXXDependentScopeMemberExprClass: 2789d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::UnresolvedMemberExprClass: 2790d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::ObjCStringLiteralClass: 2791d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::ObjCEncodeExprClass: 2792d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::ObjCMessageExprClass: 2793d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::ObjCSelectorExprClass: 2794d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::ObjCProtocolExprClass: 2795d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::ObjCIvarRefExprClass: 2796d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::ObjCPropertyRefExprClass: 2797d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::ObjCIsaExprClass: 2798d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::ShuffleVectorExprClass: 2799d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::BlockExprClass: 2800d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::BlockDeclRefExprClass: 2801d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::NoStmtClass: 28027cd7d1ad33fdf49eef83942e8855fe20d95aa1b9John McCall case Expr::OpaqueValueExprClass: 2803be230c36e32142cbdcdbe9c97511d097beeecbabDouglas Gregor case Expr::PackExpansionExprClass: 2804c7793c73ba8a343de3f2552d984851985a46f159Douglas Gregor case Expr::SubstNonTypeTemplateParmPackExprClass: 2805d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return ICEDiag(2, E->getLocStart()); 2806d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall 2807ee8aff06f6a96214731de17b2cb6df407c6c1820Douglas Gregor case Expr::SizeOfPackExprClass: 2808d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::GNUNullExprClass: 2809d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // GCC considers the GNU __null value to be an integral constant expression. 2810d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return NoDiag(); 2811d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall 2812d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::ParenExprClass: 2813d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return CheckICE(cast<ParenExpr>(E)->getSubExpr(), Ctx); 2814d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::IntegerLiteralClass: 2815d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CharacterLiteralClass: 2816d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CXXBoolLiteralExprClass: 2817ed8abf18329df67b0abcbb3a10458bd8c1d2a595Douglas Gregor case Expr::CXXScalarValueInitExprClass: 2818d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::UnaryTypeTraitExprClass: 28196ad6f2848d7652ab2991286eb48be440d3493b28Francois Pichet case Expr::BinaryTypeTraitExprClass: 28202e156225a29407a50dd19041aa5750171ad44ea3Sebastian Redl case Expr::CXXNoexceptExprClass: 2821d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return NoDiag(); 2822d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CallExprClass: 28236cf750298d3621d8a10a6dd07fcee8e274b9d94dSean Hunt case Expr::CXXOperatorCallExprClass: { 2824d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall const CallExpr *CE = cast<CallExpr>(E); 2825d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (CE->isBuiltinCall(Ctx)) 2826d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return CheckEvalInICE(E, Ctx); 2827d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return ICEDiag(2, E->getLocStart()); 2828d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 2829d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::DeclRefExprClass: 2830d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (isa<EnumConstantDecl>(cast<DeclRefExpr>(E)->getDecl())) 2831d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return NoDiag(); 2832d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (Ctx.getLangOptions().CPlusPlus && 2833d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall E->getType().getCVRQualifiers() == Qualifiers::Const) { 2834d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall const NamedDecl *D = cast<DeclRefExpr>(E)->getDecl(); 2835d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall 2836d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // Parameter variables are never constants. Without this check, 2837d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // getAnyInitializer() can find a default argument, which leads 2838d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // to chaos. 2839d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (isa<ParmVarDecl>(D)) 2840d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return ICEDiag(2, cast<DeclRefExpr>(E)->getLocation()); 2841d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall 2842d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // C++ 7.1.5.1p2 2843d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // A variable of non-volatile const-qualified integral or enumeration 2844d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // type initialized by an ICE can be used in ICEs. 2845d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (const VarDecl *Dcl = dyn_cast<VarDecl>(D)) { 2846d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall Qualifiers Quals = Ctx.getCanonicalType(Dcl->getType()).getQualifiers(); 2847d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (Quals.hasVolatile() || !Quals.hasConst()) 2848d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return ICEDiag(2, cast<DeclRefExpr>(E)->getLocation()); 2849d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall 2850d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // Look for a declaration of this variable that has an initializer. 2851d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall const VarDecl *ID = 0; 2852d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall const Expr *Init = Dcl->getAnyInitializer(ID); 2853d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (Init) { 2854d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (ID->isInitKnownICE()) { 2855d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // We have already checked whether this subexpression is an 2856d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // integral constant expression. 2857d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (ID->isInitICE()) 2858d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return NoDiag(); 2859d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall else 2860d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return ICEDiag(2, cast<DeclRefExpr>(E)->getLocation()); 2861d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 2862d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall 2863d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // It's an ICE whether or not the definition we found is 2864d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // out-of-line. See DR 721 and the discussion in Clang PR 2865d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // 6206 for details. 2866d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall 2867d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (Dcl->isCheckingICE()) { 2868d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return ICEDiag(2, cast<DeclRefExpr>(E)->getLocation()); 2869d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 2870d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall 2871d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall Dcl->setCheckingICE(); 2872d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall ICEDiag Result = CheckICE(Init, Ctx); 2873d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // Cache the result of the ICE test. 2874d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall Dcl->setInitKnownICE(Result.Val == 0); 2875d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return Result; 2876d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 2877d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 2878d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 2879d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return ICEDiag(2, E->getLocStart()); 2880d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::UnaryOperatorClass: { 2881d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall const UnaryOperator *Exp = cast<UnaryOperator>(E); 2882d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall switch (Exp->getOpcode()) { 28832de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case UO_PostInc: 28842de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case UO_PostDec: 28852de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case UO_PreInc: 28862de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case UO_PreDec: 28872de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case UO_AddrOf: 28882de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case UO_Deref: 2889d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return ICEDiag(2, E->getLocStart()); 28902de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case UO_Extension: 28912de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case UO_LNot: 28922de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case UO_Plus: 28932de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case UO_Minus: 28942de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case UO_Not: 28952de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case UO_Real: 28962de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case UO_Imag: 2897d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return CheckICE(Exp->getSubExpr(), Ctx); 2898d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 2899d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall 2900d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // OffsetOf falls through here. 2901d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 2902d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::OffsetOfExprClass: { 2903d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // Note that per C99, offsetof must be an ICE. And AFAIK, using 2904d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // Evaluate matches the proposed gcc behavior for cases like 2905d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // "offsetof(struct s{int x[4];}, x[!.0])". This doesn't affect 2906d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // compliance: we should warn earlier for offsetof expressions with 2907d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // array subscripts that aren't ICEs, and if the array subscripts 2908d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // are ICEs, the value of the offsetof must be an integer constant. 2909d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return CheckEvalInICE(E, Ctx); 2910d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 2911f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne case Expr::UnaryExprOrTypeTraitExprClass: { 2912f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne const UnaryExprOrTypeTraitExpr *Exp = cast<UnaryExprOrTypeTraitExpr>(E); 2913f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne if ((Exp->getKind() == UETT_SizeOf) && 2914f4e3cfbe8abd124be6341ef5d714819b4fbd9082Peter Collingbourne Exp->getTypeOfArgument()->isVariableArrayType()) 2915d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return ICEDiag(2, E->getLocStart()); 2916d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return NoDiag(); 2917d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 2918d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::BinaryOperatorClass: { 2919d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall const BinaryOperator *Exp = cast<BinaryOperator>(E); 2920d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall switch (Exp->getOpcode()) { 29212de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_PtrMemD: 29222de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_PtrMemI: 29232de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Assign: 29242de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_MulAssign: 29252de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_DivAssign: 29262de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_RemAssign: 29272de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_AddAssign: 29282de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_SubAssign: 29292de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_ShlAssign: 29302de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_ShrAssign: 29312de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_AndAssign: 29322de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_XorAssign: 29332de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_OrAssign: 2934d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return ICEDiag(2, E->getLocStart()); 2935d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall 29362de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Mul: 29372de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Div: 29382de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Rem: 29392de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Add: 29402de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Sub: 29412de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Shl: 29422de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Shr: 29432de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_LT: 29442de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_GT: 29452de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_LE: 29462de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_GE: 29472de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_EQ: 29482de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_NE: 29492de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_And: 29502de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Xor: 29512de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Or: 29522de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_Comma: { 2953d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall ICEDiag LHSResult = CheckICE(Exp->getLHS(), Ctx); 2954d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall ICEDiag RHSResult = CheckICE(Exp->getRHS(), Ctx); 29552de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall if (Exp->getOpcode() == BO_Div || 29562de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall Exp->getOpcode() == BO_Rem) { 2957d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // Evaluate gives an error for undefined Div/Rem, so make sure 2958d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // we don't evaluate one. 29593b332ab132fa85c83833d74d400f6e126f52fbd2John McCall if (LHSResult.Val == 0 && RHSResult.Val == 0) { 2960d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall llvm::APSInt REval = Exp->getRHS()->EvaluateAsInt(Ctx); 2961d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (REval == 0) 2962d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return ICEDiag(1, E->getLocStart()); 2963d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (REval.isSigned() && REval.isAllOnesValue()) { 2964d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall llvm::APSInt LEval = Exp->getLHS()->EvaluateAsInt(Ctx); 2965d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (LEval.isMinSignedValue()) 2966d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return ICEDiag(1, E->getLocStart()); 2967d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 2968d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 2969d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 29702de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall if (Exp->getOpcode() == BO_Comma) { 2971d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (Ctx.getLangOptions().C99) { 2972d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // C99 6.6p3 introduces a strange edge case: comma can be in an ICE 2973d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // if it isn't evaluated. 2974d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (LHSResult.Val == 0 && RHSResult.Val == 0) 2975d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return ICEDiag(1, E->getLocStart()); 2976d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } else { 2977d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // In both C89 and C++, commas in ICEs are illegal. 2978d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return ICEDiag(2, E->getLocStart()); 2979d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 2980d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 2981d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (LHSResult.Val >= RHSResult.Val) 2982d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return LHSResult; 2983d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return RHSResult; 2984d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 29852de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_LAnd: 29862de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall case BO_LOr: { 2987d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall ICEDiag LHSResult = CheckICE(Exp->getLHS(), Ctx); 2988d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall ICEDiag RHSResult = CheckICE(Exp->getRHS(), Ctx); 2989d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (LHSResult.Val == 0 && RHSResult.Val == 1) { 2990d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // Rare case where the RHS has a comma "side-effect"; we need 2991d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // to actually check the condition to see whether the side 2992d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // with the comma is evaluated. 29932de56d1d0c3a504ad1529de2677628bdfbb95cd4John McCall if ((Exp->getOpcode() == BO_LAnd) != 2994d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall (Exp->getLHS()->EvaluateAsInt(Ctx) == 0)) 2995d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return RHSResult; 2996d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return NoDiag(); 2997d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 2998d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall 2999d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (LHSResult.Val >= RHSResult.Val) 3000d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return LHSResult; 3001d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return RHSResult; 3002d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 3003d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 3004d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 3005d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::ImplicitCastExprClass: 3006d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CStyleCastExprClass: 3007d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CXXFunctionalCastExprClass: 3008d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CXXStaticCastExprClass: 3009d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CXXReinterpretCastExprClass: 3010d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CXXConstCastExprClass: { 3011d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall const Expr *SubExpr = cast<CastExpr>(E)->getSubExpr(); 30122ade35e2cfd554e49d35a52047cea98a82787af9Douglas Gregor if (SubExpr->getType()->isIntegralOrEnumerationType()) 3013d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return CheckICE(SubExpr, Ctx); 3014d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (isa<FloatingLiteral>(SubExpr->IgnoreParens())) 3015d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return NoDiag(); 3016d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return ICEDiag(2, E->getLocStart()); 3017d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 301856ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall case Expr::BinaryConditionalOperatorClass: { 301956ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall const BinaryConditionalOperator *Exp = cast<BinaryConditionalOperator>(E); 302056ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall ICEDiag CommonResult = CheckICE(Exp->getCommon(), Ctx); 302156ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall if (CommonResult.Val == 2) return CommonResult; 302256ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall ICEDiag FalseResult = CheckICE(Exp->getFalseExpr(), Ctx); 302356ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall if (FalseResult.Val == 2) return FalseResult; 302456ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall if (CommonResult.Val == 1) return CommonResult; 302556ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall if (FalseResult.Val == 1 && 302656ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall Exp->getCommon()->EvaluateAsInt(Ctx) == 0) return NoDiag(); 302756ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall return FalseResult; 302856ca35d396d8692c384c785f9aeebcf22563fe1eJohn McCall } 3029d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::ConditionalOperatorClass: { 3030d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall const ConditionalOperator *Exp = cast<ConditionalOperator>(E); 3031d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // If the condition (ignoring parens) is a __builtin_constant_p call, 3032d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // then only the true side is actually considered in an integer constant 3033d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // expression, and it is fully evaluated. This is an important GNU 3034d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // extension. See GCC PR38377 for discussion. 3035d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (const CallExpr *CallCE 3036d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall = dyn_cast<CallExpr>(Exp->getCond()->IgnoreParenCasts())) 3037d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (CallCE->isBuiltinCall(Ctx) == Builtin::BI__builtin_constant_p) { 3038d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall Expr::EvalResult EVResult; 3039d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (!E->Evaluate(EVResult, Ctx) || EVResult.HasSideEffects || 3040d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall !EVResult.Val.isInt()) { 3041d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return ICEDiag(2, E->getLocStart()); 3042d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 3043d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return NoDiag(); 3044d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 3045d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall ICEDiag CondResult = CheckICE(Exp->getCond(), Ctx); 3046d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall ICEDiag TrueResult = CheckICE(Exp->getTrueExpr(), Ctx); 3047d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall ICEDiag FalseResult = CheckICE(Exp->getFalseExpr(), Ctx); 3048d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (CondResult.Val == 2) 3049d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return CondResult; 3050d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (TrueResult.Val == 2) 3051d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return TrueResult; 3052d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (FalseResult.Val == 2) 3053d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return FalseResult; 3054d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (CondResult.Val == 1) 3055d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return CondResult; 3056d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (TrueResult.Val == 0 && FalseResult.Val == 0) 3057d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return NoDiag(); 3058d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // Rare case where the diagnostics depend on which side is evaluated 3059d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // Note that if we get here, CondResult is 0, and at least one of 3060d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // TrueResult and FalseResult is non-zero. 3061d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (Exp->getCond()->EvaluateAsInt(Ctx) == 0) { 3062d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return FalseResult; 3063d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 3064d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return TrueResult; 3065d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 3066d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::CXXDefaultArgExprClass: 3067d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return CheckICE(cast<CXXDefaultArgExpr>(E)->getExpr(), Ctx); 3068d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall case Expr::ChooseExprClass: { 3069d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return CheckICE(cast<ChooseExpr>(E)->getChosenSubExpr(Ctx), Ctx); 3070d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 3071d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 3072d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall 3073d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall // Silence a GCC warning 3074d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return ICEDiag(2, E->getLocStart()); 3075d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall} 3076d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall 3077d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCallbool Expr::isIntegerConstantExpr(llvm::APSInt &Result, ASTContext &Ctx, 3078d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall SourceLocation *Loc, bool isEvaluated) const { 3079d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall ICEDiag d = CheckICE(this, Ctx); 3080d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (d.Val != 0) { 3081d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (Loc) *Loc = d.Loc; 3082d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return false; 3083d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall } 3084d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall EvalResult EvalResult; 3085d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall if (!Evaluate(EvalResult, Ctx)) 3086d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall llvm_unreachable("ICE cannot be evaluated!"); 3087d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall assert(!EvalResult.HasSideEffects && "ICE with side effects!"); 3088d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall assert(EvalResult.Val.isInt() && "ICE that isn't integer!"); 3089d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall Result = EvalResult.Val.getInt(); 3090d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall return true; 3091d905f5ad540c415d1a21b4f8b7bd715bfb7bb920John McCall} 3092