Author: rsmith Date: Mon May 21 13:36:58 2018 New Revision: 332886 URL: http://llvm.org/viewvc/llvm-project?rev=332886&view=rev Log: Revert r332847; it caused us to miscompile certain forms of reference initialization.
Added: cfe/trunk/test/SemaCXX/large-array-init.cpp - copied unchanged from r332846, cfe/trunk/test/SemaCXX/large-array-init.cpp Modified: cfe/trunk/include/clang/AST/Expr.h cfe/trunk/lib/AST/ExprConstant.cpp cfe/trunk/lib/CodeGen/CGExprConstant.cpp cfe/trunk/test/CodeGen/const-init.c cfe/trunk/test/CodeGen/designated-initializers.c cfe/trunk/test/CodeGen/union-init2.c cfe/trunk/test/CodeGenCXX/cxx11-initializer-aggregate.cpp cfe/trunk/test/CodeGenCXX/cxx1z-initializer-aggregate.cpp cfe/trunk/test/CodeGenCXX/reference-init.cpp Modified: cfe/trunk/include/clang/AST/Expr.h URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/AST/Expr.h?rev=332886&r1=332885&r2=332886&view=diff ============================================================================== --- cfe/trunk/include/clang/AST/Expr.h (original) +++ cfe/trunk/include/clang/AST/Expr.h Mon May 21 13:36:58 2018 @@ -537,13 +537,6 @@ public: bool isConstantInitializer(ASTContext &Ctx, bool ForRef, const Expr **Culprit = nullptr) const; - enum SideEffectsKind { - SE_NoSideEffects, ///< Strictly evaluate the expression. - SE_AllowUndefinedBehavior, ///< Allow UB that we can give a value, but not - ///< arbitrary unmodeled side effects. - SE_AllowSideEffects ///< Allow any unmodeled side effect. - }; - /// EvalStatus is a struct with detailed info about an evaluation in progress. struct EvalStatus { /// Whether the evaluated expression has side effects. @@ -572,11 +565,6 @@ public: bool hasSideEffects() const { return HasSideEffects; } - - bool hasUnacceptableSideEffect(SideEffectsKind SEK) { - return (SEK < SE_AllowSideEffects && HasSideEffects) || - (SEK < SE_AllowUndefinedBehavior && HasUndefinedBehavior); - } }; /// EvalResult is a struct with detailed info about an evaluated expression. @@ -603,6 +591,13 @@ public: /// side-effects. bool EvaluateAsBooleanCondition(bool &Result, const ASTContext &Ctx) const; + enum SideEffectsKind { + SE_NoSideEffects, ///< Strictly evaluate the expression. + SE_AllowUndefinedBehavior, ///< Allow UB that we can give a value, but not + ///< arbitrary unmodeled side effects. + SE_AllowSideEffects ///< Allow any unmodeled side effect. + }; + /// EvaluateAsInt - Return true if this is a constant which we can fold and /// convert to an integer, using any crazy technique that we want to. bool EvaluateAsInt(llvm::APSInt &Result, const ASTContext &Ctx, Modified: cfe/trunk/lib/AST/ExprConstant.cpp URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/ExprConstant.cpp?rev=332886&r1=332885&r2=332886&view=diff ============================================================================== --- cfe/trunk/lib/AST/ExprConstant.cpp (original) +++ cfe/trunk/lib/AST/ExprConstant.cpp Mon May 21 13:36:58 2018 @@ -10312,6 +10312,12 @@ bool Expr::EvaluateAsBooleanCondition(bo HandleConversionToBool(Scratch.Val, Result); } +static bool hasUnacceptableSideEffect(Expr::EvalStatus &Result, + Expr::SideEffectsKind SEK) { + return (SEK < Expr::SE_AllowSideEffects && Result.HasSideEffects) || + (SEK < Expr::SE_AllowUndefinedBehavior && Result.HasUndefinedBehavior); +} + bool Expr::EvaluateAsInt(APSInt &Result, const ASTContext &Ctx, SideEffectsKind AllowSideEffects) const { if (!getType()->isIntegralOrEnumerationType()) @@ -10319,7 +10325,7 @@ bool Expr::EvaluateAsInt(APSInt &Result, EvalResult ExprResult; if (!EvaluateAsRValue(ExprResult, Ctx) || !ExprResult.Val.isInt() || - ExprResult.hasUnacceptableSideEffect(AllowSideEffects)) + hasUnacceptableSideEffect(ExprResult, AllowSideEffects)) return false; Result = ExprResult.Val.getInt(); @@ -10333,7 +10339,7 @@ bool Expr::EvaluateAsFloat(APFloat &Resu EvalResult ExprResult; if (!EvaluateAsRValue(ExprResult, Ctx) || !ExprResult.Val.isFloat() || - ExprResult.hasUnacceptableSideEffect(AllowSideEffects)) + hasUnacceptableSideEffect(ExprResult, AllowSideEffects)) return false; Result = ExprResult.Val.getFloat(); @@ -10411,7 +10417,7 @@ bool Expr::EvaluateAsInitializer(APValue bool Expr::isEvaluatable(const ASTContext &Ctx, SideEffectsKind SEK) const { EvalResult Result; return EvaluateAsRValue(Result, Ctx) && - !Result.hasUnacceptableSideEffect(SEK); + !hasUnacceptableSideEffect(Result, SEK); } APSInt Expr::EvaluateKnownConstInt(const ASTContext &Ctx, Modified: cfe/trunk/lib/CodeGen/CGExprConstant.cpp URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/CodeGen/CGExprConstant.cpp?rev=332886&r1=332885&r2=332886&view=diff ============================================================================== --- cfe/trunk/lib/CodeGen/CGExprConstant.cpp (original) +++ cfe/trunk/lib/CodeGen/CGExprConstant.cpp Mon May 21 13:36:58 2018 @@ -1392,40 +1392,20 @@ static QualType getNonMemoryType(CodeGen return type; } -/// Checks if the specified initializer is equivalent to zero initialization. -static bool isZeroInitializer(ConstantEmitter &CE, const Expr *Init) { - if (auto *E = dyn_cast_or_null<CXXConstructExpr>(Init)) { - CXXConstructorDecl *CD = E->getConstructor(); - return CD->isDefaultConstructor() && CD->isTrivial(); - } - - if (auto *IL = dyn_cast_or_null<InitListExpr>(Init)) { - for (auto I : IL->inits()) - if (!isZeroInitializer(CE, I)) - return false; - if (const Expr *Filler = IL->getArrayFiller()) - return isZeroInitializer(CE, Filler); - return true; - } - - QualType InitTy = Init->getType(); - if (InitTy->isIntegralOrEnumerationType() || InitTy->isPointerType()) { - Expr::EvalResult Result; - if (Init->EvaluateAsRValue(Result, CE.CGM.getContext()) && - !Result.hasUnacceptableSideEffect(Expr::SE_NoSideEffects)) - return (Result.Val.isInt() && Result.Val.getInt().isNullValue()) || - (Result.Val.isLValue() && Result.Val.isNullPointer()); - } - - return false; -} - llvm::Constant *ConstantEmitter::tryEmitPrivateForVarInit(const VarDecl &D) { // Make a quick check if variable can be default NULL initialized // and avoid going through rest of code which may do, for c++11, // initialization of memory to all NULLs. - if (!D.hasLocalStorage() && isZeroInitializer(*this, D.getInit())) - return CGM.EmitNullConstant(D.getType()); + if (!D.hasLocalStorage()) { + QualType Ty = CGM.getContext().getBaseElementType(D.getType()); + if (Ty->isRecordType()) + if (const CXXConstructExpr *E = + dyn_cast_or_null<CXXConstructExpr>(D.getInit())) { + const CXXConstructorDecl *CD = E->getConstructor(); + if (CD->isTrivial() && CD->isDefaultConstructor()) + return CGM.EmitNullConstant(D.getType()); + } + } QualType destType = D.getType(); Modified: cfe/trunk/test/CodeGen/const-init.c URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/CodeGen/const-init.c?rev=332886&r1=332885&r2=332886&view=diff ============================================================================== --- cfe/trunk/test/CodeGen/const-init.c (original) +++ cfe/trunk/test/CodeGen/const-init.c Mon May 21 13:36:58 2018 @@ -167,7 +167,7 @@ void g30() { int : 1; int x; } a = {}; - // CHECK: @g30.a = internal global %struct.anon.1 zeroinitializer, align 1 + // CHECK: @g30.a = internal global %struct.anon.1 <{ i8 undef, i32 0 }>, align 1 #pragma pack() } Modified: cfe/trunk/test/CodeGen/designated-initializers.c URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/CodeGen/designated-initializers.c?rev=332886&r1=332885&r2=332886&view=diff ============================================================================== --- cfe/trunk/test/CodeGen/designated-initializers.c (original) +++ cfe/trunk/test/CodeGen/designated-initializers.c Mon May 21 13:36:58 2018 @@ -8,7 +8,7 @@ struct foo { // CHECK: @u = global %union.anon zeroinitializer union { int i; float f; } u = { }; -// CHECK: @u2 = global %union.anon.0 zeroinitializer +// CHECK: @u2 = global { i32, [4 x i8] } { i32 0, [4 x i8] undef } union { int i; double f; } u2 = { }; // CHECK: @u3 = global %union.anon.1 zeroinitializer Modified: cfe/trunk/test/CodeGen/union-init2.c URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/CodeGen/union-init2.c?rev=332886&r1=332885&r2=332886&view=diff ============================================================================== --- cfe/trunk/test/CodeGen/union-init2.c (original) +++ cfe/trunk/test/CodeGen/union-init2.c Mon May 21 13:36:58 2018 @@ -5,7 +5,7 @@ union x {long long b;union x* a;} r = {.a = &r}; -// CHECK: global %union.z zeroinitializer +// CHECK: global { [3 x i8], [5 x i8] } { [3 x i8] zeroinitializer, [5 x i8] undef } union z { char a[3]; long long b; Modified: cfe/trunk/test/CodeGenCXX/cxx11-initializer-aggregate.cpp URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/CodeGenCXX/cxx11-initializer-aggregate.cpp?rev=332886&r1=332885&r2=332886&view=diff ============================================================================== --- cfe/trunk/test/CodeGenCXX/cxx11-initializer-aggregate.cpp (original) +++ cfe/trunk/test/CodeGenCXX/cxx11-initializer-aggregate.cpp Mon May 21 13:36:58 2018 @@ -51,30 +51,3 @@ namespace NonTrivialInit { // meaningful. B b[30] = {}; } - -namespace ZeroInit { - enum { Zero, One }; - constexpr int zero() { return 0; } - constexpr int *null() { return nullptr; } - struct Filler { - int x; - Filler(); - }; - struct S1 { - int x; - }; - - // These declarations, if implemented elementwise, require huge - // amout of memory and compiler time. - unsigned char data_1[1024 * 1024 * 1024 * 2u] = { 0 }; - unsigned char data_2[1024 * 1024 * 1024 * 2u] = { Zero }; - unsigned char data_3[1024][1024][1024] = {{{0}}}; - unsigned char data_4[1024 * 1024 * 1024 * 2u] = { zero() }; - int *data_5[1024 * 1024 * 512] = { nullptr }; - int *data_6[1024 * 1024 * 512] = { null() }; - struct S1 data_7[1024 * 1024 * 512] = {{0}}; - - // This variable must be initialized elementwise. - Filler data_e1[1024] = {}; - // CHECK: getelementptr inbounds {{.*}} @_ZN8ZeroInit7data_e1E -} Modified: cfe/trunk/test/CodeGenCXX/cxx1z-initializer-aggregate.cpp URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/CodeGenCXX/cxx1z-initializer-aggregate.cpp?rev=332886&r1=332885&r2=332886&view=diff ============================================================================== --- cfe/trunk/test/CodeGenCXX/cxx1z-initializer-aggregate.cpp (original) +++ cfe/trunk/test/CodeGenCXX/cxx1z-initializer-aggregate.cpp Mon May 21 13:36:58 2018 @@ -17,14 +17,14 @@ namespace Constant { C c1 = {}; C c2 = {1}; - // CHECK: @_ZN8Constant2c1E = global %"struct.Constant::C" zeroinitializer, align 1 + // CHECK: @_ZN8Constant2c1E = global { i8 } zeroinitializer, align 1 // CHECK: @_ZN8Constant2c2E = global { i8 } { i8 1 }, align 1 // Test packing bases into tail padding. D d1 = {}; D d2 = {1, 2, 3}; D d3 = {1}; - // CHECK: @_ZN8Constant2d1E = global %"struct.Constant::D" zeroinitializer, align 4 + // CHECK: @_ZN8Constant2d1E = global { i32, i8, i8 } zeroinitializer, align 4 // CHECK: @_ZN8Constant2d2E = global { i32, i8, i8 } { i32 1, i8 2, i8 3 }, align 4 // CHECK: @_ZN8Constant2d3E = global { i32, i8, i8 } { i32 1, i8 0, i8 0 }, align 4 Modified: cfe/trunk/test/CodeGenCXX/reference-init.cpp URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/CodeGenCXX/reference-init.cpp?rev=332886&r1=332885&r2=332886&view=diff ============================================================================== --- cfe/trunk/test/CodeGenCXX/reference-init.cpp (original) +++ cfe/trunk/test/CodeGenCXX/reference-init.cpp Mon May 21 13:36:58 2018 @@ -3,6 +3,12 @@ // RUN: %clang_cc1 -triple %itanium_abi_triple -emit-llvm %s -o - -std=c++11 | FileCheck %s --check-prefix=CHECK-CXX11 // expected-no-diagnostics +#if __cplusplus >= 201103L +// CHECK-CXX11: @_ZZ15InitRefWithListvE1r = internal constant i32* @_ZGRZ15InitRefWithListvE1r_ +// CHECK-CXX11: @_ZGRZ15InitRefWithListvE1r_ = internal constant i32 123 +int InitRefWithList() { static const int &r = {123}; return r; } +#endif + struct XPTParamDescriptor {}; struct nsXPTParamInfo { nsXPTParamInfo(const XPTParamDescriptor& desc); _______________________________________________ cfe-commits mailing list cfe-commits@lists.llvm.org http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits