parent
2b85de4383
commit
801cc3272a
|
@ -83,23 +83,22 @@ struct CopyStructVisitor : StructVisitor<Derived>,
|
|||
|
||||
template <class... Ts>
|
||||
void preVisit(QualType::PrimitiveCopyKind PCK, QualType FT,
|
||||
const FieldDecl *FD, CharUnits CurStructOffsset,
|
||||
Ts &&... Args) {
|
||||
const FieldDecl *FD, CharUnits CurStructOffset, Ts &&... Args) {
|
||||
if (PCK)
|
||||
asDerived().flushTrivialFields(std::forward<Ts>(Args)...);
|
||||
}
|
||||
|
||||
template <class... Ts>
|
||||
void visitWithKind(QualType::PrimitiveCopyKind PCK, QualType FT,
|
||||
const FieldDecl *FD, CharUnits CurStructOffsset,
|
||||
const FieldDecl *FD, CharUnits CurStructOffset,
|
||||
Ts &&... Args) {
|
||||
if (const auto *AT = asDerived().getContext().getAsArrayType(FT)) {
|
||||
asDerived().visitArray(PCK, AT, FT.isVolatileQualified(), FD,
|
||||
CurStructOffsset, std::forward<Ts>(Args)...);
|
||||
CurStructOffset, std::forward<Ts>(Args)...);
|
||||
return;
|
||||
}
|
||||
|
||||
Super::visitWithKind(PCK, FT, FD, CurStructOffsset,
|
||||
Super::visitWithKind(PCK, FT, FD, CurStructOffset,
|
||||
std::forward<Ts>(Args)...);
|
||||
}
|
||||
|
||||
|
@ -253,11 +252,11 @@ struct GenBinaryFuncName : CopyStructVisitor<GenBinaryFuncName<IsMove>, IsMove>,
|
|||
}
|
||||
|
||||
void visitVolatileTrivial(QualType FT, const FieldDecl *FD,
|
||||
CharUnits CurStackOffset) {
|
||||
CharUnits CurStructOffset) {
|
||||
// Because volatile fields can be bit-fields and are individually copied,
|
||||
// their offset and width are in bits.
|
||||
uint64_t OffsetInBits =
|
||||
this->Ctx.toBits(CurStackOffset) + this->getFieldOffsetInBits(FD);
|
||||
this->Ctx.toBits(CurStructOffset) + this->getFieldOffsetInBits(FD);
|
||||
this->appendStr("_tv" + llvm::to_string(OffsetInBits) + "w" +
|
||||
llvm::to_string(getFieldSize(FD, FT, this->Ctx)));
|
||||
}
|
||||
|
@ -286,8 +285,7 @@ struct GenDestructorFuncName : GenUnaryFuncName<GenDestructorFuncName>,
|
|||
using Super = DestructedTypeVisitor<GenDestructorFuncName>;
|
||||
GenDestructorFuncName(const char *Prefix, CharUnits DstAlignment,
|
||||
ASTContext &Ctx)
|
||||
: GenUnaryFuncName<GenDestructorFuncName>(Prefix, DstAlignment,
|
||||
Ctx) {}
|
||||
: GenUnaryFuncName<GenDestructorFuncName>(Prefix, DstAlignment, Ctx) {}
|
||||
void visitWithKind(QualType::DestructionKind DK, QualType FT,
|
||||
const FieldDecl *FD, CharUnits CurStructOffset) {
|
||||
if (const auto *AT = getContext().getAsArrayType(FT)) {
|
||||
|
@ -322,19 +320,19 @@ static const CGFunctionInfo &getFunctionInfo(CodeGenModule &CGM,
|
|||
// functions.
|
||||
template <class Derived> struct GenFuncBase {
|
||||
template <size_t N>
|
||||
void visitStruct(QualType FT, const FieldDecl *FD, CharUnits CurStackOffset,
|
||||
void visitStruct(QualType FT, const FieldDecl *FD, CharUnits CurStructOffset,
|
||||
std::array<Address, N> Addrs) {
|
||||
this->asDerived().callSpecialFunction(
|
||||
FT, CurStackOffset + asDerived().getFieldOffset(FD), Addrs);
|
||||
FT, CurStructOffset + asDerived().getFieldOffset(FD), Addrs);
|
||||
}
|
||||
|
||||
template <class FieldKind, size_t N>
|
||||
void visitArray(FieldKind FK, const ArrayType *AT, bool IsVolatile,
|
||||
const FieldDecl *FD, CharUnits CurStackOffset,
|
||||
const FieldDecl *FD, CharUnits CurStructOffset,
|
||||
std::array<Address, N> Addrs) {
|
||||
// Non-volatile trivial fields are copied when flushTrivialFields is called.
|
||||
if (!FK)
|
||||
return asDerived().visitTrivial(QualType(AT, 0), FD, CurStackOffset,
|
||||
return asDerived().visitTrivial(QualType(AT, 0), FD, CurStructOffset,
|
||||
Addrs);
|
||||
|
||||
asDerived().flushTrivialFields(Addrs);
|
||||
|
@ -345,7 +343,7 @@ template <class Derived> struct GenFuncBase {
|
|||
QualType BaseEltQT;
|
||||
std::array<Address, N> StartAddrs = Addrs;
|
||||
for (unsigned I = 0; I < N; ++I)
|
||||
StartAddrs[I] = getAddrWithOffset(Addrs[I], CurStackOffset, FD);
|
||||
StartAddrs[I] = getAddrWithOffset(Addrs[I], CurStructOffset, FD);
|
||||
Address DstAddr = StartAddrs[DstIdx];
|
||||
llvm::Value *NumElts = CGF.emitArrayLength(AT, BaseEltQT, DstAddr);
|
||||
unsigned BaseEltSize = Ctx.getTypeSizeInChars(BaseEltQT).getQuantity();
|
||||
|
@ -585,15 +583,15 @@ struct GenDestructor : StructVisitor<GenDestructor>,
|
|||
}
|
||||
|
||||
void visitARCStrong(QualType QT, const FieldDecl *FD,
|
||||
CharUnits CurStackOffset, std::array<Address, 1> Addrs) {
|
||||
CharUnits CurStructOffset, std::array<Address, 1> Addrs) {
|
||||
CGF->destroyARCStrongImprecise(
|
||||
*CGF, getAddrWithOffset(Addrs[DstIdx], CurStackOffset, FD), QT);
|
||||
*CGF, getAddrWithOffset(Addrs[DstIdx], CurStructOffset, FD), QT);
|
||||
}
|
||||
|
||||
void visitARCWeak(QualType QT, const FieldDecl *FD, CharUnits CurStackOffset,
|
||||
void visitARCWeak(QualType QT, const FieldDecl *FD, CharUnits CurStructOffset,
|
||||
std::array<Address, 1> Addrs) {
|
||||
CGF->destroyARCWeak(
|
||||
*CGF, getAddrWithOffset(Addrs[DstIdx], CurStackOffset, FD), QT);
|
||||
*CGF, getAddrWithOffset(Addrs[DstIdx], CurStructOffset, FD), QT);
|
||||
}
|
||||
|
||||
void callSpecialFunction(QualType FT, CharUnits Offset,
|
||||
|
@ -626,35 +624,35 @@ struct GenDefaultInitialize
|
|||
}
|
||||
|
||||
void visitARCStrong(QualType QT, const FieldDecl *FD,
|
||||
CharUnits CurStackOffset, std::array<Address, 1> Addrs) {
|
||||
CharUnits CurStructOffset, std::array<Address, 1> Addrs) {
|
||||
CGF->EmitNullInitialization(
|
||||
getAddrWithOffset(Addrs[DstIdx], CurStackOffset, FD), QT);
|
||||
getAddrWithOffset(Addrs[DstIdx], CurStructOffset, FD), QT);
|
||||
}
|
||||
|
||||
void visitARCWeak(QualType QT, const FieldDecl *FD, CharUnits CurStackOffset,
|
||||
void visitARCWeak(QualType QT, const FieldDecl *FD, CharUnits CurStructOffset,
|
||||
std::array<Address, 1> Addrs) {
|
||||
CGF->EmitNullInitialization(
|
||||
getAddrWithOffset(Addrs[DstIdx], CurStackOffset, FD), QT);
|
||||
getAddrWithOffset(Addrs[DstIdx], CurStructOffset, FD), QT);
|
||||
}
|
||||
|
||||
template <class FieldKind, size_t... Is>
|
||||
void visitArray(FieldKind FK, const ArrayType *AT, bool IsVolatile,
|
||||
const FieldDecl *FD, CharUnits CurStackOffset,
|
||||
const FieldDecl *FD, CharUnits CurStructOffset,
|
||||
std::array<Address, 1> Addrs) {
|
||||
if (!FK)
|
||||
return visitTrivial(QualType(AT, 0), FD, CurStackOffset, Addrs);
|
||||
return visitTrivial(QualType(AT, 0), FD, CurStructOffset, Addrs);
|
||||
|
||||
ASTContext &Ctx = getContext();
|
||||
CharUnits Size = Ctx.getTypeSizeInChars(QualType(AT, 0));
|
||||
QualType EltTy = Ctx.getBaseElementType(QualType(AT, 0));
|
||||
|
||||
if (Size < CharUnits::fromQuantity(16) || EltTy->getAs<RecordType>()) {
|
||||
GenFuncBaseTy::visitArray(FK, AT, IsVolatile, FD, CurStackOffset, Addrs);
|
||||
GenFuncBaseTy::visitArray(FK, AT, IsVolatile, FD, CurStructOffset, Addrs);
|
||||
return;
|
||||
}
|
||||
|
||||
llvm::Constant *SizeVal = CGF->Builder.getInt64(Size.getQuantity());
|
||||
Address DstAddr = getAddrWithOffset(Addrs[DstIdx], CurStackOffset, FD);
|
||||
Address DstAddr = getAddrWithOffset(Addrs[DstIdx], CurStructOffset, FD);
|
||||
Address Loc = CGF->Builder.CreateElementBitCast(DstAddr, CGF->Int8Ty);
|
||||
CGF->Builder.CreateMemSet(Loc, CGF->Builder.getInt8(0), SizeVal,
|
||||
IsVolatile);
|
||||
|
@ -672,19 +670,19 @@ struct GenCopyConstructor : GenBinaryFunc<GenCopyConstructor, false> {
|
|||
: GenBinaryFunc<GenCopyConstructor, false>(Ctx) {}
|
||||
|
||||
void visitARCStrong(QualType QT, const FieldDecl *FD,
|
||||
CharUnits CurStackOffset, std::array<Address, 2> Addrs) {
|
||||
Addrs[DstIdx] = getAddrWithOffset(Addrs[DstIdx], CurStackOffset, FD);
|
||||
Addrs[SrcIdx] = getAddrWithOffset(Addrs[SrcIdx], CurStackOffset, FD);
|
||||
CharUnits CurStructOffset, std::array<Address, 2> Addrs) {
|
||||
Addrs[DstIdx] = getAddrWithOffset(Addrs[DstIdx], CurStructOffset, FD);
|
||||
Addrs[SrcIdx] = getAddrWithOffset(Addrs[SrcIdx], CurStructOffset, FD);
|
||||
llvm::Value *SrcVal = CGF->EmitLoadOfScalar(
|
||||
Addrs[SrcIdx], QT.isVolatileQualified(), QT, SourceLocation());
|
||||
llvm::Value *Val = CGF->EmitARCRetain(QT, SrcVal);
|
||||
CGF->EmitStoreOfScalar(Val, CGF->MakeAddrLValue(Addrs[DstIdx], QT), true);
|
||||
}
|
||||
|
||||
void visitARCWeak(QualType QT, const FieldDecl *FD, CharUnits CurStackOffset,
|
||||
void visitARCWeak(QualType QT, const FieldDecl *FD, CharUnits CurStructOffset,
|
||||
std::array<Address, 2> Addrs) {
|
||||
Addrs[DstIdx] = getAddrWithOffset(Addrs[DstIdx], CurStackOffset, FD);
|
||||
Addrs[SrcIdx] = getAddrWithOffset(Addrs[SrcIdx], CurStackOffset, FD);
|
||||
Addrs[DstIdx] = getAddrWithOffset(Addrs[DstIdx], CurStructOffset, FD);
|
||||
Addrs[SrcIdx] = getAddrWithOffset(Addrs[SrcIdx], CurStructOffset, FD);
|
||||
CGF->EmitARCCopyWeak(Addrs[DstIdx], Addrs[SrcIdx]);
|
||||
}
|
||||
|
||||
|
@ -700,9 +698,9 @@ struct GenMoveConstructor : GenBinaryFunc<GenMoveConstructor, true> {
|
|||
: GenBinaryFunc<GenMoveConstructor, true>(Ctx) {}
|
||||
|
||||
void visitARCStrong(QualType QT, const FieldDecl *FD,
|
||||
CharUnits CurStackOffset, std::array<Address, 2> Addrs) {
|
||||
Addrs[DstIdx] = getAddrWithOffset(Addrs[DstIdx], CurStackOffset, FD);
|
||||
Addrs[SrcIdx] = getAddrWithOffset(Addrs[SrcIdx], CurStackOffset, FD);
|
||||
CharUnits CurStructOffset, std::array<Address, 2> Addrs) {
|
||||
Addrs[DstIdx] = getAddrWithOffset(Addrs[DstIdx], CurStructOffset, FD);
|
||||
Addrs[SrcIdx] = getAddrWithOffset(Addrs[SrcIdx], CurStructOffset, FD);
|
||||
LValue SrcLV = CGF->MakeAddrLValue(Addrs[SrcIdx], QT);
|
||||
llvm::Value *SrcVal =
|
||||
CGF->EmitLoadOfLValue(SrcLV, SourceLocation()).getScalarVal();
|
||||
|
@ -711,10 +709,10 @@ struct GenMoveConstructor : GenBinaryFunc<GenMoveConstructor, true> {
|
|||
/* isInitialization */ true);
|
||||
}
|
||||
|
||||
void visitARCWeak(QualType QT, const FieldDecl *FD, CharUnits CurStackOffset,
|
||||
void visitARCWeak(QualType QT, const FieldDecl *FD, CharUnits CurStructOffset,
|
||||
std::array<Address, 2> Addrs) {
|
||||
Addrs[DstIdx] = getAddrWithOffset(Addrs[DstIdx], CurStackOffset, FD);
|
||||
Addrs[SrcIdx] = getAddrWithOffset(Addrs[SrcIdx], CurStackOffset, FD);
|
||||
Addrs[DstIdx] = getAddrWithOffset(Addrs[DstIdx], CurStructOffset, FD);
|
||||
Addrs[SrcIdx] = getAddrWithOffset(Addrs[SrcIdx], CurStructOffset, FD);
|
||||
CGF->EmitARCMoveWeak(Addrs[DstIdx], Addrs[SrcIdx]);
|
||||
}
|
||||
|
||||
|
@ -730,19 +728,19 @@ struct GenCopyAssignment : GenBinaryFunc<GenCopyAssignment, false> {
|
|||
: GenBinaryFunc<GenCopyAssignment, false>(Ctx) {}
|
||||
|
||||
void visitARCStrong(QualType QT, const FieldDecl *FD,
|
||||
CharUnits CurStackOffset, std::array<Address, 2> Addrs) {
|
||||
Addrs[DstIdx] = getAddrWithOffset(Addrs[DstIdx], CurStackOffset, FD);
|
||||
Addrs[SrcIdx] = getAddrWithOffset(Addrs[SrcIdx], CurStackOffset, FD);
|
||||
CharUnits CurStructOffset, std::array<Address, 2> Addrs) {
|
||||
Addrs[DstIdx] = getAddrWithOffset(Addrs[DstIdx], CurStructOffset, FD);
|
||||
Addrs[SrcIdx] = getAddrWithOffset(Addrs[SrcIdx], CurStructOffset, FD);
|
||||
llvm::Value *SrcVal = CGF->EmitLoadOfScalar(
|
||||
Addrs[SrcIdx], QT.isVolatileQualified(), QT, SourceLocation());
|
||||
CGF->EmitARCStoreStrong(CGF->MakeAddrLValue(Addrs[DstIdx], QT), SrcVal,
|
||||
false);
|
||||
}
|
||||
|
||||
void visitARCWeak(QualType QT, const FieldDecl *FD, CharUnits CurStackOffset,
|
||||
void visitARCWeak(QualType QT, const FieldDecl *FD, CharUnits CurStructOffset,
|
||||
std::array<Address, 2> Addrs) {
|
||||
Addrs[DstIdx] = getAddrWithOffset(Addrs[DstIdx], CurStackOffset, FD);
|
||||
Addrs[SrcIdx] = getAddrWithOffset(Addrs[SrcIdx], CurStackOffset, FD);
|
||||
Addrs[DstIdx] = getAddrWithOffset(Addrs[DstIdx], CurStructOffset, FD);
|
||||
Addrs[SrcIdx] = getAddrWithOffset(Addrs[SrcIdx], CurStructOffset, FD);
|
||||
CGF->emitARCCopyAssignWeak(QT, Addrs[DstIdx], Addrs[SrcIdx]);
|
||||
}
|
||||
|
||||
|
@ -759,9 +757,9 @@ struct GenMoveAssignment : GenBinaryFunc<GenMoveAssignment, true> {
|
|||
: GenBinaryFunc<GenMoveAssignment, true>(Ctx) {}
|
||||
|
||||
void visitARCStrong(QualType QT, const FieldDecl *FD,
|
||||
CharUnits CurStackOffset, std::array<Address, 2> Addrs) {
|
||||
Addrs[DstIdx] = getAddrWithOffset(Addrs[DstIdx], CurStackOffset, FD);
|
||||
Addrs[SrcIdx] = getAddrWithOffset(Addrs[SrcIdx], CurStackOffset, FD);
|
||||
CharUnits CurStructOffset, std::array<Address, 2> Addrs) {
|
||||
Addrs[DstIdx] = getAddrWithOffset(Addrs[DstIdx], CurStructOffset, FD);
|
||||
Addrs[SrcIdx] = getAddrWithOffset(Addrs[SrcIdx], CurStructOffset, FD);
|
||||
LValue SrcLV = CGF->MakeAddrLValue(Addrs[SrcIdx], QT);
|
||||
llvm::Value *SrcVal =
|
||||
CGF->EmitLoadOfLValue(SrcLV, SourceLocation()).getScalarVal();
|
||||
|
@ -773,10 +771,10 @@ struct GenMoveAssignment : GenBinaryFunc<GenMoveAssignment, true> {
|
|||
CGF->EmitARCRelease(DstVal, ARCImpreciseLifetime);
|
||||
}
|
||||
|
||||
void visitARCWeak(QualType QT, const FieldDecl *FD, CharUnits CurStackOffset,
|
||||
void visitARCWeak(QualType QT, const FieldDecl *FD, CharUnits CurStructOffset,
|
||||
std::array<Address, 2> Addrs) {
|
||||
Addrs[DstIdx] = getAddrWithOffset(Addrs[DstIdx], CurStackOffset, FD);
|
||||
Addrs[SrcIdx] = getAddrWithOffset(Addrs[SrcIdx], CurStackOffset, FD);
|
||||
Addrs[DstIdx] = getAddrWithOffset(Addrs[DstIdx], CurStructOffset, FD);
|
||||
Addrs[SrcIdx] = getAddrWithOffset(Addrs[SrcIdx], CurStructOffset, FD);
|
||||
CGF->emitARCMoveAssignWeak(QT, Addrs[DstIdx], Addrs[SrcIdx]);
|
||||
}
|
||||
|
||||
|
@ -827,18 +825,16 @@ void CodeGenFunction::callCStructDefaultConstructor(LValue Dst) {
|
|||
IsVolatile, *this, std::array<Address, 1>({{DstPtr}}));
|
||||
}
|
||||
|
||||
std::string
|
||||
CodeGenFunction::getNonTrivialCopyConstructorStr(QualType QT,
|
||||
CharUnits Alignment,
|
||||
bool IsVolatile,
|
||||
ASTContext &Ctx) {
|
||||
std::string CodeGenFunction::getNonTrivialCopyConstructorStr(
|
||||
QualType QT, CharUnits Alignment, bool IsVolatile, ASTContext &Ctx) {
|
||||
GenBinaryFuncName<false> GenName("", Alignment, Alignment, Ctx);
|
||||
return GenName.getName(QT, IsVolatile);
|
||||
}
|
||||
|
||||
std::string
|
||||
CodeGenFunction::getNonTrivialDestructorStr(QualType QT, CharUnits Alignment,
|
||||
bool IsVolatile, ASTContext &Ctx) {
|
||||
std::string CodeGenFunction::getNonTrivialDestructorStr(QualType QT,
|
||||
CharUnits Alignment,
|
||||
bool IsVolatile,
|
||||
ASTContext &Ctx) {
|
||||
GenDestructorFuncName GenName("", Alignment, Ctx);
|
||||
return GenName.getName(QT, IsVolatile);
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue