From: Eli Friedman Date: Sat, 3 Dec 2011 00:54:26 +0000 (+0000) Subject: Track alignment in AggValueSlot. No functional change in this patch, but I'll be... X-Git-Url: https://granicus.if.org/sourcecode?a=commitdiff_plain;h=f394078fde147dcf27e9b6a7965517388d64dcb6;p=clang Track alignment in AggValueSlot. No functional change in this patch, but I'll be introducing uses of the specified alignment soon. git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@145736 91177308-0d34-0410-b5e6-96231b3b80d8 --- diff --git a/lib/CodeGen/CGClass.cpp b/lib/CodeGen/CGClass.cpp index c28ecc05de..b3d41fca9c 100644 --- a/lib/CodeGen/CGClass.cpp +++ b/lib/CodeGen/CGClass.cpp @@ -397,9 +397,10 @@ static void EmitBaseInitializer(CodeGenFunction &CGF, CGF.GetAddressOfDirectBaseInCompleteClass(ThisPtr, ClassDecl, BaseClassDecl, isBaseVirtual); - + unsigned Alignment = + CGF.getContext().getTypeAlignInChars(BaseType).getQuantity(); AggValueSlot AggSlot = - AggValueSlot::forAddr(V, Qualifiers(), + AggValueSlot::forAddr(V, Alignment, Qualifiers(), AggValueSlot::IsDestructed, AggValueSlot::DoesNotNeedGCBarriers, AggValueSlot::IsNotAliased); @@ -420,30 +421,35 @@ static void EmitAggMemberInitializer(CodeGenFunction &CGF, unsigned Index) { if (Index == MemberInit->getNumArrayIndices()) { CodeGenFunction::RunCleanupsScope Cleanups(CGF); - - llvm::Value *Dest = LHS.getAddress(); + + LValue LV = LHS; if (ArrayIndexVar) { // If we have an array index variable, load it and use it as an offset. // Then, increment the value. + llvm::Value *Dest = LHS.getAddress(); llvm::Value *ArrayIndex = CGF.Builder.CreateLoad(ArrayIndexVar); Dest = CGF.Builder.CreateInBoundsGEP(Dest, ArrayIndex, "destaddress"); llvm::Value *Next = llvm::ConstantInt::get(ArrayIndex->getType(), 1); Next = CGF.Builder.CreateAdd(ArrayIndex, Next, "inc"); - CGF.Builder.CreateStore(Next, ArrayIndexVar); + CGF.Builder.CreateStore(Next, ArrayIndexVar); + + // Update the LValue. + LV.setAddress(Dest); + unsigned Align = CGF.getContext().getTypeAlignInChars(T).getQuantity(); + LV.setAlignment(std::min(Align, LV.getAlignment())); } if (!CGF.hasAggregateLLVMType(T)) { - LValue lvalue = CGF.MakeAddrLValue(Dest, T); - CGF.EmitScalarInit(MemberInit->getInit(), /*decl*/ 0, lvalue, false); + CGF.EmitScalarInit(MemberInit->getInit(), /*decl*/ 0, LV, false); } else if (T->isAnyComplexType()) { - CGF.EmitComplexExprIntoAddr(MemberInit->getInit(), Dest, - LHS.isVolatileQualified()); - } else { + CGF.EmitComplexExprIntoAddr(MemberInit->getInit(), LV.getAddress(), + LV.isVolatileQualified()); + } else { AggValueSlot Slot = - AggValueSlot::forAddr(Dest, LHS.getQuals(), - AggValueSlot::IsDestructed, - AggValueSlot::DoesNotNeedGCBarriers, - AggValueSlot::IsNotAliased); + AggValueSlot::forLValue(LV, + AggValueSlot::IsDestructed, + AggValueSlot::DoesNotNeedGCBarriers, + AggValueSlot::IsNotAliased); CGF.EmitAggExpr(MemberInit->getInit(), Slot); } @@ -1338,8 +1344,10 @@ CodeGenFunction::EmitDelegatingCXXConstructorCall(const CXXConstructorDecl *Ctor llvm::Value *ThisPtr = LoadCXXThis(); + QualType Ty = getContext().getTagDeclType(Ctor->getParent()); + unsigned Alignment = getContext().getTypeAlignInChars(Ty).getQuantity(); AggValueSlot AggSlot = - AggValueSlot::forAddr(ThisPtr, Qualifiers(), + AggValueSlot::forAddr(ThisPtr, Alignment, Qualifiers(), AggValueSlot::IsDestructed, AggValueSlot::DoesNotNeedGCBarriers, AggValueSlot::IsNotAliased); diff --git a/lib/CodeGen/CGException.cpp b/lib/CodeGen/CGException.cpp index 15fc6a1e59..3a7b4d4107 100644 --- a/lib/CodeGen/CGException.cpp +++ b/lib/CodeGen/CGException.cpp @@ -1039,10 +1039,12 @@ static void InitCatchParam(CodeGenFunction &CGF, CGF.EHStack.pushTerminate(); // Perform the copy construction. - CGF.EmitAggExpr(copyExpr, AggValueSlot::forAddr(ParamAddr, Qualifiers(), - AggValueSlot::IsNotDestructed, - AggValueSlot::DoesNotNeedGCBarriers, - AggValueSlot::IsNotAliased)); + unsigned Alignment = CGF.getContext().getDeclAlign(&CatchParam).getQuantity(); + CGF.EmitAggExpr(copyExpr, + AggValueSlot::forAddr(ParamAddr, Alignment, Qualifiers(), + AggValueSlot::IsNotDestructed, + AggValueSlot::DoesNotNeedGCBarriers, + AggValueSlot::IsNotAliased)); // Leave the terminate scope. CGF.EHStack.popTerminate(); diff --git a/lib/CodeGen/CGExpr.cpp b/lib/CodeGen/CGExpr.cpp index 60e0121745..d527305386 100644 --- a/lib/CodeGen/CGExpr.cpp +++ b/lib/CodeGen/CGExpr.cpp @@ -135,14 +135,17 @@ void CodeGenFunction::EmitAnyExprToMem(const Expr *E, llvm::Value *Location, Qualifiers Quals, bool IsInit) { - if (E->getType()->isAnyComplexType()) + // FIXME: This function should take an LValue as an argument. + if (E->getType()->isAnyComplexType()) { EmitComplexExprIntoAddr(E, Location, Quals.hasVolatile()); - else if (hasAggregateLLVMType(E->getType())) - EmitAggExpr(E, AggValueSlot::forAddr(Location, Quals, + } else if (hasAggregateLLVMType(E->getType())) { + unsigned Alignment = + getContext().getTypeAlignInChars(E->getType()).getQuantity(); + EmitAggExpr(E, AggValueSlot::forAddr(Location, Alignment, Quals, AggValueSlot::IsDestructed_t(IsInit), AggValueSlot::DoesNotNeedGCBarriers, AggValueSlot::IsAliased_t(!IsInit))); - else { + } else { RValue RV = RValue::get(EmitScalarExpr(E, /*Ignore*/ false)); LValue LV = MakeAddrLValue(Location, E->getType()); EmitStoreThroughLValue(RV, LV); @@ -358,10 +361,12 @@ EmitExprForReferenceBinding(CodeGenFunction &CGF, const Expr *E, !E->getType()->isAnyComplexType()) { ReferenceTemporary = CreateReferenceTemporary(CGF, E->getType(), InitializedDecl); + unsigned Alignment = + CGF.getContext().getTypeAlignInChars(E->getType()).getQuantity(); AggValueSlot::IsDestructed_t isDestructed = AggValueSlot::IsDestructed_t(InitializedDecl != 0); - AggSlot = AggValueSlot::forAddr(ReferenceTemporary, Qualifiers(), - isDestructed, + AggSlot = AggValueSlot::forAddr(ReferenceTemporary, Alignment, + Qualifiers(), isDestructed, AggValueSlot::DoesNotNeedGCBarriers, AggValueSlot::IsNotAliased); } diff --git a/lib/CodeGen/CGExprCXX.cpp b/lib/CodeGen/CGExprCXX.cpp index 99ebad1786..e3afda62d4 100644 --- a/lib/CodeGen/CGExprCXX.cpp +++ b/lib/CodeGen/CGExprCXX.cpp @@ -760,7 +760,7 @@ static void StoreAnyExprIntoOneUnit(CodeGenFunction &CGF, const CXXNewExpr *E, AllocType.isVolatileQualified()); else { AggValueSlot Slot - = AggValueSlot::forAddr(NewPtr, AllocType.getQualifiers(), + = AggValueSlot::forAddr(NewPtr, Alignment, AllocType.getQualifiers(), AggValueSlot::IsDestructed, AggValueSlot::DoesNotNeedGCBarriers, AggValueSlot::IsNotAliased); diff --git a/lib/CodeGen/CGStmt.cpp b/lib/CodeGen/CGStmt.cpp index 6f020ccab0..adc0094e61 100644 --- a/lib/CodeGen/CGStmt.cpp +++ b/lib/CodeGen/CGStmt.cpp @@ -772,7 +772,9 @@ void CodeGenFunction::EmitReturnStmt(const ReturnStmt &S) { } else if (RV->getType()->isAnyComplexType()) { EmitComplexExprIntoAddr(RV, ReturnValue, false); } else { - EmitAggExpr(RV, AggValueSlot::forAddr(ReturnValue, Qualifiers(), + unsigned Alignment = + getContext().getTypeAlignInChars(RV->getType()).getQuantity(); + EmitAggExpr(RV, AggValueSlot::forAddr(ReturnValue, Alignment, Qualifiers(), AggValueSlot::IsDestructed, AggValueSlot::DoesNotNeedGCBarriers, AggValueSlot::IsNotAliased)); diff --git a/lib/CodeGen/CGValue.h b/lib/CodeGen/CGValue.h index 48f7f53255..e507e71866 100644 --- a/lib/CodeGen/CGValue.h +++ b/lib/CodeGen/CGValue.h @@ -220,6 +220,7 @@ public: unsigned getAddressSpace() const { return Quals.getAddressSpace(); } unsigned getAlignment() const { return Alignment; } + void setAlignment(unsigned A) { Alignment = A; } // simple lvalue llvm::Value *getAddress() const { assert(isSimple()); return V; } @@ -308,6 +309,8 @@ class AggValueSlot { // Qualifiers Qualifiers Quals; + unsigned short Alignment; + /// DestructedFlag - This is set to true if some external code is /// responsible for setting up a destructor for the slot. Otherwise /// the code which constructs it should push the appropriate cleanup. @@ -363,13 +366,15 @@ public: /// for calling destructors on this object /// \param needsGC - true if the slot is potentially located /// somewhere that ObjC GC calls should be emitted for - static AggValueSlot forAddr(llvm::Value *addr, Qualifiers quals, + static AggValueSlot forAddr(llvm::Value *addr, unsigned align, + Qualifiers quals, IsDestructed_t isDestructed, NeedsGCBarriers_t needsGC, IsAliased_t isAliased, IsZeroed_t isZeroed = IsNotZeroed) { AggValueSlot AV; AV.Addr = addr; + AV.Alignment = align; AV.Quals = quals; AV.DestructedFlag = isDestructed; AV.ObjCGCFlag = needsGC; @@ -382,7 +387,7 @@ public: NeedsGCBarriers_t needsGC, IsAliased_t isAliased, IsZeroed_t isZeroed = IsNotZeroed) { - return forAddr(LV.getAddress(), LV.getQuals(), + return forAddr(LV.getAddress(), LV.getAlignment(), LV.getQuals(), isDestructed, needsGC, isAliased, isZeroed); } @@ -415,10 +420,15 @@ public: return Addr == 0; } + unsigned getAlignment() const { + return Alignment; + } + IsAliased_t isPotentiallyAliased() const { return IsAliased_t(AliasedFlag); } + // FIXME: Alignment? RValue asRValue() const { return RValue::getAggregate(getAddr(), isVolatile()); } diff --git a/lib/CodeGen/CodeGenFunction.h b/lib/CodeGen/CodeGenFunction.h index 25436562e7..39a0bfc2f1 100644 --- a/lib/CodeGen/CodeGenFunction.h +++ b/lib/CodeGen/CodeGenFunction.h @@ -1574,7 +1574,9 @@ public: /// CreateAggTemp - Create a temporary memory object for the given /// aggregate type. AggValueSlot CreateAggTemp(QualType T, const Twine &Name = "tmp") { - return AggValueSlot::forAddr(CreateMemTemp(T, Name), T.getQualifiers(), + unsigned Alignment = getContext().getTypeAlignInChars(T).getQuantity(); + return AggValueSlot::forAddr(CreateMemTemp(T, Name), Alignment, + T.getQualifiers(), AggValueSlot::IsNotDestructed, AggValueSlot::DoesNotNeedGCBarriers, AggValueSlot::IsNotAliased);