Skip to content

Commit 5fd502b

Browse files
committed
[SILGen] InitAccessors: Generalize AccessorComponent::emitValue
Instead of taking a setter type, let's switch over to a more general `AccessorKind` which allows us to cover init accessors and simplify `emitApplySetterToBase`.
1 parent 75ac138 commit 5fd502b

File tree

3 files changed

+35
-27
lines changed

3 files changed

+35
-27
lines changed

lib/SILGen/SILGenFunction.cpp

Lines changed: 3 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1755,7 +1755,7 @@ ParamDecl *SILGenFunction::isMappedToInitAccessorArgument(VarDecl *property) {
17551755
return arg->second;
17561756
}
17571757

1758-
std::pair<SILValue, CanSILFunctionType>
1758+
SILValue
17591759
SILGenFunction::emitApplyOfSetterToBase(SILLocation loc, SILDeclRef setter,
17601760
ManagedValue base,
17611761
SubstitutionMap substitutions) {
@@ -1783,8 +1783,7 @@ SILGenFunction::emitApplyOfSetterToBase(SILLocation loc, SILDeclRef setter,
17831783
getTypeExpansionContext());
17841784
};
17851785

1786-
auto setterTy = getSetterType(setterFRef);
1787-
SILFunctionConventions setterConv(setterTy, SGM.M);
1786+
SILFunctionConventions setterConv(getSetterType(setterFRef), SGM.M);
17881787

17891788
// Emit captures for the setter
17901789
SmallVector<SILValue, 4> capturedArgs;
@@ -1822,5 +1821,5 @@ SILGenFunction::emitApplyOfSetterToBase(SILLocation loc, SILDeclRef setter,
18221821
PartialApplyInst *setterPAI =
18231822
B.createPartialApply(loc, setterFRef, substitutions, capturedArgs,
18241823
ParameterConvention::Direct_Guaranteed);
1825-
return {emitManagedRValueWithCleanup(setterPAI).getValue(), setterTy};
1824+
return emitManagedRValueWithCleanup(setterPAI).getValue();
18261825
}

lib/SILGen/SILGenFunction.h

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -815,9 +815,9 @@ class LLVM_LIBRARY_VISIBILITY SILGenFunction
815815
void emitInitAccessor(AccessorDecl *accessor);
816816

817817
/// Generates code to emit the given setter reference to the given base value.
818-
std::pair<SILValue, CanSILFunctionType>
819-
emitApplyOfSetterToBase(SILLocation loc, SILDeclRef setter, ManagedValue base,
820-
SubstitutionMap substitutions);
818+
SILValue emitApplyOfSetterToBase(SILLocation loc, SILDeclRef setter,
819+
ManagedValue base,
820+
SubstitutionMap substitutions);
821821

822822
/// Generates code to destroy the instance variables of a class.
823823
///

lib/SILGen/SILGenLValue.cpp

Lines changed: 29 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -1443,8 +1443,23 @@ namespace {
14431443
}
14441444

14451445
ManagedValue emitValue(SILGenFunction &SGF, SILLocation loc, VarDecl *field,
1446-
Type fieldType, ArgumentSource &&value,
1447-
CanSILFunctionType accessorTy) {
1446+
ArgumentSource &&value, AccessorKind accessorKind) {
1447+
auto accessorInfo = SGF.getConstantInfo(
1448+
SGF.getTypeExpansionContext(),
1449+
SILDeclRef(field->getOpaqueAccessor(accessorKind)));
1450+
1451+
auto fieldTy = field->getValueInterfaceType();
1452+
auto accessorTy = SGF.SGM.Types
1453+
.getLoweredType(accessorInfo.SILFnType,
1454+
SGF.getTypeExpansionContext())
1455+
.castTo<SILFunctionType>();
1456+
1457+
if (!Substitutions.empty()) {
1458+
fieldTy = fieldTy.subst(Substitutions);
1459+
accessorTy = accessorTy->substGenericArgs(
1460+
SGF.SGM.M, Substitutions, SGF.getTypeExpansionContext());
1461+
}
1462+
14481463
SILFunctionConventions accessorConv(accessorTy, SGF.SGM.M);
14491464

14501465
// FIXME: This should use CallEmission instead of doing everything
@@ -1458,19 +1473,23 @@ namespace {
14581473
loweredSubstArgType =
14591474
SILType::getPrimitiveAddressType(loweredSubstArgType.getASTType());
14601475
}
1476+
14611477
auto loweredSubstParamTy = SILType::getPrimitiveType(
14621478
param.getArgumentType(SGF.SGM.M, accessorTy,
14631479
SGF.getTypeExpansionContext()),
14641480
loweredSubstArgType.getCategory());
1481+
14651482
// Handle reabstraction differences.
14661483
if (Mval.getType() != loweredSubstParamTy) {
14671484
Mval = SGF.emitSubstToOrigValue(
14681485
loc, Mval, SGF.SGM.Types.getAbstractionPattern(field),
1469-
fieldType->getCanonicalType());
1486+
fieldTy->getCanonicalType());
14701487
}
14711488

1489+
auto newValueArgIdx = accessorConv.getNumIndirectSILResults();
14721490
// If we need the argument in memory, materialize an address.
1473-
if (accessorConv.getSILArgumentConvention(0).isIndirectConvention() &&
1491+
if (accessorConv.getSILArgumentConvention(newValueArgIdx)
1492+
.isIndirectConvention() &&
14741493
!Mval.getType().isAddress()) {
14751494
Mval = Mval.materialize(SGF, loc);
14761495
}
@@ -1507,29 +1526,21 @@ namespace {
15071526
void set(SILGenFunction &SGF, SILLocation loc, ArgumentSource &&value,
15081527
ManagedValue base) &&
15091528
override {
1510-
VarDecl *field = cast<VarDecl>(Storage);
1511-
auto fieldType = field->getValueInterfaceType();
1512-
if (!Substitutions.empty()) {
1513-
fieldType = fieldType.subst(Substitutions);
1514-
}
1515-
1529+
auto *field = cast<VarDecl>(Storage);
15161530
// Emit the init accessor function partially applied to the base.
15171531
SILValue initFRef =
15181532
emitPartialInitAccessorReference(SGF, loc, getAccessorDecl());
15191533

15201534
SILValue setterFRef;
1521-
CanSILFunctionType setterTy;
1522-
15231535
if (auto *setter = field->getOpaqueAccessor(AccessorKind::Set)) {
1524-
std::tie(setterFRef, setterTy) = SGF.emitApplyOfSetterToBase(
1525-
loc, SILDeclRef(setter), base, Substitutions);
1536+
setterFRef = SGF.emitApplyOfSetterToBase(loc, SILDeclRef(setter), base,
1537+
Substitutions);
15261538
} else {
15271539
setterFRef = SILUndef::get(initFRef->getType(), SGF.F);
1528-
setterTy = initFRef->getType().castTo<SILFunctionType>();
15291540
}
15301541

15311542
auto Mval =
1532-
emitValue(SGF, loc, field, fieldType, std::move(value), setterTy);
1543+
emitValue(SGF, loc, field, std::move(value), AccessorKind::Init);
15331544

15341545
SGF.B.createAssignOrInit(loc, base.getValue(), Mval.forward(SGF),
15351546
initFRef, setterFRef, AssignOrInitInst::Unknown);
@@ -1822,15 +1833,13 @@ namespace {
18221833
ManagedValue initFn = SGF.emitManagedRValueWithCleanup(initPAI);
18231834

18241835
// Create the allocating setter function. It captures the base address.
1825-
SILValue setterFn;
1826-
CanSILFunctionType setterTy;
1827-
std::tie(setterFn, setterTy) =
1836+
SILValue setterFn =
18281837
SGF.emitApplyOfSetterToBase(loc, Accessor, base, Substitutions);
18291838

18301839
// Create the assign_by_wrapper with the initializer and setter.
18311840

18321841
auto Mval =
1833-
emitValue(SGF, loc, field, FieldType, std::move(value), setterTy);
1842+
emitValue(SGF, loc, field, std::move(value), AccessorKind::Set);
18341843

18351844
SGF.B.createAssignByWrapper(loc, Mval.forward(SGF), proj.forward(SGF),
18361845
initFn.getValue(), setterFn,

0 commit comments

Comments
 (0)