diff options
| author | joerg <joerg@NetBSD.org> | 2021-05-30 01:25:15 +0000 |
|---|---|---|
| committer | joerg <joerg@NetBSD.org> | 2021-05-30 01:25:15 +0000 |
| commit | 13fbcb42fff2606c3ce926a7c4bb8989aa18758c (patch) | |
| tree | dcace6c89967106796d44b1a7c5e2269a20967e2 /external/apache2/llvm/dist/clang/lib/CodeGen/CGExprConstant.cpp | |
| parent | 13338e33506ade63440b4ba74479551bdc21c0f6 (diff) | |
Import clang 249b40b558955afe5ac2b549edcf2d7f859c8cc9.
Diffstat (limited to 'external/apache2/llvm/dist/clang/lib/CodeGen/CGExprConstant.cpp')
| -rw-r--r-- | external/apache2/llvm/dist/clang/lib/CodeGen/CGExprConstant.cpp | 120 |
1 files changed, 66 insertions, 54 deletions
diff --git a/external/apache2/llvm/dist/clang/lib/CodeGen/CGExprConstant.cpp b/external/apache2/llvm/dist/clang/lib/CodeGen/CGExprConstant.cpp index 96e8c9c0d0e..734024149bb 100644 --- a/external/apache2/llvm/dist/clang/lib/CodeGen/CGExprConstant.cpp +++ b/external/apache2/llvm/dist/clang/lib/CodeGen/CGExprConstant.cpp @@ -10,20 +10,21 @@ // //===----------------------------------------------------------------------===// -#include "CodeGenFunction.h" #include "CGCXXABI.h" #include "CGObjCRuntime.h" #include "CGRecordLayout.h" +#include "CodeGenFunction.h" #include "CodeGenModule.h" #include "ConstantEmitter.h" #include "TargetInfo.h" #include "clang/AST/APValue.h" #include "clang/AST/ASTContext.h" +#include "clang/AST/Attr.h" #include "clang/AST/RecordLayout.h" #include "clang/AST/StmtVisitor.h" #include "clang/Basic/Builtins.h" -#include "llvm/ADT/Sequence.h" #include "llvm/ADT/STLExtras.h" +#include "llvm/ADT/Sequence.h" #include "llvm/IR/Constants.h" #include "llvm/IR/DataLayout.h" #include "llvm/IR/Function.h" @@ -57,14 +58,14 @@ struct ConstantAggregateBuilderUtils { } llvm::Constant *getPadding(CharUnits PadSize) const { - llvm::Type *Ty = CGM.Int8Ty; + llvm::Type *Ty = CGM.CharTy; if (PadSize > CharUnits::One()) Ty = llvm::ArrayType::get(Ty, PadSize.getQuantity()); return llvm::UndefValue::get(Ty); } llvm::Constant *getZeroes(CharUnits ZeroSize) const { - llvm::Type *Ty = llvm::ArrayType::get(CGM.Int8Ty, ZeroSize.getQuantity()); + llvm::Type *Ty = llvm::ArrayType::get(CGM.CharTy, ZeroSize.getQuantity()); return llvm::ConstantAggregateZero::get(Ty); } }; @@ -317,12 +318,17 @@ bool ConstantAggregateBuilder::split(size_t Index, CharUnits Hint) { CharUnits Offset = Offsets[Index]; if (auto *CA = dyn_cast<llvm::ConstantAggregate>(C)) { + // Expand the sequence into its contained elements. + // FIXME: This assumes vector elements are byte-sized. replace(Elems, Index, Index + 1, llvm::map_range(llvm::seq(0u, CA->getNumOperands()), [&](unsigned Op) { return CA->getOperand(Op); })); - if (auto *Seq = dyn_cast<llvm::SequentialType>(CA->getType())) { + if (isa<llvm::ArrayType>(CA->getType()) || + isa<llvm::VectorType>(CA->getType())) { // Array or vector. - CharUnits ElemSize = getSize(Seq->getElementType()); + llvm::Type *ElemTy = + llvm::GetElementPtrInst::getTypeAtIndex(CA->getType(), (uint64_t)0); + CharUnits ElemSize = getSize(ElemTy); replace( Offsets, Index, Index + 1, llvm::map_range(llvm::seq(0u, CA->getNumOperands()), @@ -343,6 +349,8 @@ bool ConstantAggregateBuilder::split(size_t Index, CharUnits Hint) { } if (auto *CDS = dyn_cast<llvm::ConstantDataSequential>(C)) { + // Expand the sequence into its contained elements. + // FIXME: This assumes vector elements are byte-sized. // FIXME: If possible, split into two ConstantDataSequentials at Hint. CharUnits ElemSize = getSize(CDS->getElementType()); replace(Elems, Index, Index + 1, @@ -358,6 +366,7 @@ bool ConstantAggregateBuilder::split(size_t Index, CharUnits Hint) { } if (isa<llvm::ConstantAggregateZero>(C)) { + // Split into two zeros at the hinted offset. CharUnits ElemSize = getSize(C); assert(Hint > Offset && Hint < Offset + ElemSize && "nothing to split"); replace(Elems, Index, Index + 1, @@ -367,6 +376,7 @@ bool ConstantAggregateBuilder::split(size_t Index, CharUnits Hint) { } if (isa<llvm::UndefValue>(C)) { + // Drop undef; it doesn't contribute to the final layout. replace(Elems, Index, Index + 1, {}); replace(Offsets, Index, Index + 1, {}); return true; @@ -588,19 +598,21 @@ bool ConstStructBuilder::AppendBytes(CharUnits FieldOffsetInChars, bool ConstStructBuilder::AppendBitField( const FieldDecl *Field, uint64_t FieldOffset, llvm::ConstantInt *CI, bool AllowOverwrite) { - uint64_t FieldSize = Field->getBitWidthValue(CGM.getContext()); + const CGRecordLayout &RL = + CGM.getTypes().getCGRecordLayout(Field->getParent()); + const CGBitFieldInfo &Info = RL.getBitFieldInfo(Field); llvm::APInt FieldValue = CI->getValue(); // Promote the size of FieldValue if necessary // FIXME: This should never occur, but currently it can because initializer // constants are cast to bool, and because clang is not enforcing bitfield // width limits. - if (FieldSize > FieldValue.getBitWidth()) - FieldValue = FieldValue.zext(FieldSize); + if (Info.Size > FieldValue.getBitWidth()) + FieldValue = FieldValue.zext(Info.Size); // Truncate the size of FieldValue to the bit field size. - if (FieldSize < FieldValue.getBitWidth()) - FieldValue = FieldValue.trunc(FieldSize); + if (Info.Size < FieldValue.getBitWidth()) + FieldValue = FieldValue.trunc(Info.Size); return Builder.addBits(FieldValue, CGM.getContext().toBits(StartOffset) + FieldOffset, @@ -765,7 +777,7 @@ bool ConstStructBuilder::Build(const APValue &Val, const RecordDecl *RD, if (const CXXRecordDecl *CD = dyn_cast<CXXRecordDecl>(RD)) { // Add a vtable pointer, if we need one and it hasn't already been added. - if (CD->isDynamicClass() && !IsPrimaryBase) { + if (Layout.hasOwnVFPtr()) { llvm::Constant *VTableAddressPoint = CGM.getCXXABI().getVTableAddressPointForConstExpr( BaseSubobject(CD, Offset), VTableClass); @@ -999,6 +1011,8 @@ public: } llvm::Constant *VisitConstantExpr(ConstantExpr *CE, QualType T) { + if (llvm::Constant *Result = Emitter.tryEmitConstantExpr(CE)) + return Result; return Visit(CE->getSubExpr(), T); } @@ -1055,7 +1069,7 @@ public: assert(CurSize <= TotalSize && "Union size mismatch!"); if (unsigned NumPadBytes = TotalSize - CurSize) { - llvm::Type *Ty = CGM.Int8Ty; + llvm::Type *Ty = CGM.CharTy; if (NumPadBytes > 1) Ty = llvm::ArrayType::get(Ty, NumPadBytes); @@ -1149,11 +1163,14 @@ public: case CK_FloatingToIntegral: case CK_FloatingToBoolean: case CK_FloatingCast: + case CK_FloatingToFixedPoint: + case CK_FixedPointToFloating: case CK_FixedPointCast: case CK_FixedPointToBoolean: case CK_FixedPointToIntegral: case CK_IntegralToFixedPoint: case CK_ZeroToOCLOpaqueType: + case CK_MatrixCast: return nullptr; } llvm_unreachable("Invalid CastKind"); @@ -1166,14 +1183,12 @@ public: } llvm::Constant *VisitExprWithCleanups(ExprWithCleanups *E, QualType T) { - if (!E->cleanupsHaveSideEffects()) - return Visit(E->getSubExpr(), T); - return nullptr; + return Visit(E->getSubExpr(), T); } llvm::Constant *VisitMaterializeTemporaryExpr(MaterializeTemporaryExpr *E, QualType T) { - return Visit(E->GetTemporaryExpr(), T); + return Visit(E->getSubExpr(), T); } llvm::Constant *EmitArrayInitialization(InitListExpr *ILE, QualType T) { @@ -1268,19 +1283,7 @@ public: if (!E->getConstructor()->isTrivial()) return nullptr; - // FIXME: We should not have to call getBaseElementType here. - const auto *RT = - CGM.getContext().getBaseElementType(Ty)->castAs<RecordType>(); - const CXXRecordDecl *RD = cast<CXXRecordDecl>(RT->getDecl()); - - // If the class doesn't have a trivial destructor, we can't emit it as a - // constant expr. - if (!RD->hasTrivialDestructor()) - return nullptr; - - // Only copy and default constructors can be trivial. - - + // Only default and copy/move constructors can be trivial. if (E->getNumArgs()) { assert(E->getNumArgs() == 1 && "trivial ctor with > 1 argument"); assert(E->getConstructor()->isCopyOrMoveConstructor() && @@ -1360,6 +1363,20 @@ ConstantEmitter::tryEmitAbstract(const APValue &value, QualType destType) { return validateAndPopAbstract(C, state); } +llvm::Constant *ConstantEmitter::tryEmitConstantExpr(const ConstantExpr *CE) { + if (!CE->hasAPValueResult()) + return nullptr; + const Expr *Inner = CE->getSubExpr()->IgnoreImplicit(); + QualType RetType; + if (auto *Call = dyn_cast<CallExpr>(Inner)) + RetType = Call->getCallReturnType(CGF->getContext()); + else if (auto *Ctor = dyn_cast<CXXConstructExpr>(Inner)) + RetType = Ctor->getType(); + llvm::Constant *Res = + emitAbstract(CE->getBeginLoc(), CE->getAPValueResult(), RetType); + return Res; +} + llvm::Constant * ConstantEmitter::emitAbstract(const Expr *E, QualType destType) { auto state = pushAbstract(); @@ -1606,8 +1623,8 @@ llvm::Constant *ConstantEmitter::tryEmitPrivateForVarInit(const VarDecl &D) { if (CD->isTrivial() && CD->isDefaultConstructor()) return CGM.EmitNullConstant(D.getType()); } - InConstantContext = true; } + InConstantContext = D.hasConstantInitialization(); QualType destType = D.getType(); @@ -1728,7 +1745,7 @@ struct ConstantLValue { /*implicit*/ ConstantLValue(llvm::Constant *value, bool hasOffsetApplied = false) - : Value(value), HasOffsetApplied(false) {} + : Value(value), HasOffsetApplied(hasOffsetApplied) {} /*implicit*/ ConstantLValue(ConstantAddress address) : ConstantLValue(address.getPointer()) {} @@ -1768,7 +1785,6 @@ private: ConstantLValue VisitCallExpr(const CallExpr *E); ConstantLValue VisitBlockExpr(const BlockExpr *E); ConstantLValue VisitCXXTypeidExpr(const CXXTypeidExpr *E); - ConstantLValue VisitCXXUuidofExpr(const CXXUuidofExpr *E); ConstantLValue VisitMaterializeTemporaryExpr( const MaterializeTemporaryExpr *E); @@ -1864,6 +1880,10 @@ ConstantLValue ConstantLValueEmitter::tryEmitBase(const APValue::LValueBase &base) { // Handle values. if (const ValueDecl *D = base.dyn_cast<const ValueDecl*>()) { + // The constant always points to the canonical declaration. We want to look + // at properties of the most recent declaration at the point of emission. + D = cast<ValueDecl>(D->getMostRecentDecl()); + if (D->hasAttr<WeakRefAttr>()) return CGM.GetWeakRefReference(D).getPointer(); @@ -1883,6 +1903,12 @@ ConstantLValueEmitter::tryEmitBase(const APValue::LValueBase &base) { } } + if (auto *GD = dyn_cast<MSGuidDecl>(D)) + return CGM.GetAddrOfMSGuidDecl(GD); + + if (auto *TPO = dyn_cast<TemplateParamObjectDecl>(D)) + return CGM.GetAddrOfTemplateParamObject(TPO); + return nullptr; } @@ -1903,6 +1929,8 @@ ConstantLValueEmitter::tryEmitBase(const APValue::LValueBase &base) { ConstantLValue ConstantLValueEmitter::VisitConstantExpr(const ConstantExpr *E) { + if (llvm::Constant *Result = Emitter.tryEmitConstantExpr(E)) + return Result; return Visit(E->getSubExpr()); } @@ -1993,18 +2021,13 @@ ConstantLValueEmitter::VisitCXXTypeidExpr(const CXXTypeidExpr *E) { } ConstantLValue -ConstantLValueEmitter::VisitCXXUuidofExpr(const CXXUuidofExpr *E) { - return CGM.GetAddrOfUuidDescriptor(E); -} - -ConstantLValue ConstantLValueEmitter::VisitMaterializeTemporaryExpr( const MaterializeTemporaryExpr *E) { assert(E->getStorageDuration() == SD_Static); SmallVector<const Expr *, 2> CommaLHSs; SmallVector<SubobjectAdjustment, 2> Adjustments; - const Expr *Inner = E->GetTemporaryExpr() - ->skipRValueSubobjectAdjustments(CommaLHSs, Adjustments); + const Expr *Inner = + E->getSubExpr()->skipRValueSubobjectAdjustments(CommaLHSs, Adjustments); return CGM.GetAddrOfGlobalTemporary(E, Inner); } @@ -2095,8 +2118,7 @@ llvm::Constant *ConstantEmitter::tryEmitPrivate(const APValue &Value, case APValue::Union: return ConstStructBuilder::BuildStruct(*this, Value, DestType); case APValue::Array: { - const ConstantArrayType *CAT = - CGM.getContext().getAsConstantArrayType(DestType); + const ArrayType *ArrayTy = CGM.getContext().getAsArrayType(DestType); unsigned NumElements = Value.getArraySize(); unsigned NumInitElts = Value.getArrayInitializedElts(); @@ -2104,7 +2126,7 @@ llvm::Constant *ConstantEmitter::tryEmitPrivate(const APValue &Value, llvm::Constant *Filler = nullptr; if (Value.hasArrayFiller()) { Filler = tryEmitAbstractForMemory(Value.getArrayFiller(), - CAT->getElementType()); + ArrayTy->getElementType()); if (!Filler) return nullptr; } @@ -2119,7 +2141,7 @@ llvm::Constant *ConstantEmitter::tryEmitPrivate(const APValue &Value, llvm::Type *CommonElementType = nullptr; for (unsigned I = 0; I < NumInitElts; ++I) { llvm::Constant *C = tryEmitPrivateForMemory( - Value.getArrayInitializedElt(I), CAT->getElementType()); + Value.getArrayInitializedElt(I), ArrayTy->getElementType()); if (!C) return nullptr; if (I == 0) @@ -2129,16 +2151,6 @@ llvm::Constant *ConstantEmitter::tryEmitPrivate(const APValue &Value, Elts.push_back(C); } - // This means that the array type is probably "IncompleteType" or some - // type that is not ConstantArray. - if (CAT == nullptr && CommonElementType == nullptr && !NumInitElts) { - const ArrayType *AT = CGM.getContext().getAsArrayType(DestType); - CommonElementType = CGM.getTypes().ConvertType(AT->getElementType()); - llvm::ArrayType *AType = llvm::ArrayType::get(CommonElementType, - NumElements); - return llvm::ConstantAggregateZero::get(AType); - } - llvm::ArrayType *Desired = cast<llvm::ArrayType>(CGM.getTypes().ConvertType(DestType)); return EmitArrayConstant(CGM, Desired, CommonElementType, NumElements, Elts, |
