Skip to content

Commit bea89c6

Browse files
committed
[SILGen] Serialize and give PublicNonABI linkage to property wrapper
generator functions for parameters of public functions.
1 parent 99e0666 commit bea89c6

File tree

2 files changed

+46
-6
lines changed

2 files changed

+46
-6
lines changed

lib/SIL/IR/SILDeclRef.cpp

Lines changed: 18 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -248,8 +248,15 @@ SILLinkage SILDeclRef::getLinkage(ForDefinition_t forDefinition) const {
248248
return forDefinition ? linkage : addExternalToLinkage(linkage);
249249
};
250250

251-
// Function-local declarations have private linkage, unless serialized.
252251
ValueDecl *d = getDecl();
252+
253+
// Property wrapper generators of public functions have PublicNonABI linkage
254+
if (isPropertyWrapperBackingInitializer() && isa<ParamDecl>(d)) {
255+
if (isSerialized())
256+
return maybeAddExternal(SILLinkage::PublicNonABI);
257+
}
258+
259+
// Function-local declarations have private linkage, unless serialized.
253260
DeclContext *moduleContext = d->getDeclContext();
254261
while (!moduleContext->isModuleScopeContext()) {
255262
if (moduleContext->isLocalContext()) {
@@ -488,9 +495,16 @@ IsSerialized_t SILDeclRef::isSerialized() const {
488495

489496
auto *d = getDecl();
490497

491-
// Default argument generators are serialized if the containing
492-
// declaration is public.
493-
if (isDefaultArgGenerator()) {
498+
// Default and property wrapper argument generators are serialized if the
499+
// containing declaration is public.
500+
if (isDefaultArgGenerator() || (isPropertyWrapperBackingInitializer() &&
501+
isa<ParamDecl>(d))) {
502+
if (isPropertyWrapperBackingInitializer()) {
503+
if (auto *func = dyn_cast_or_null<ValueDecl>(d->getDeclContext()->getAsDecl())) {
504+
d = func;
505+
}
506+
}
507+
494508
// Ask the AST if we're inside an @inlinable context.
495509
if (d->getDeclContext()->getResilienceExpansion()
496510
== ResilienceExpansion::Minimal) {

test/SILGen/property_wrapper_parameter.swift

Lines changed: 28 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -30,10 +30,10 @@ public func testSimpleWrapperParameter(@Wrapper value: Int) {
3030
_ = $value
3131

3232
// property wrapper backing initializer of value #1 in testSimpleWrapperParameter(value:)
33-
// CHECK: sil private [ossa] @$s26property_wrapper_parameter26testSimpleWrapperParameter5valueyAA0F0VySiG_tFACL_SivpfP : $@convention(thin) (Int) -> Wrapper<Int>
33+
// CHECK: sil non_abi [serialized] [ossa] @$s26property_wrapper_parameter26testSimpleWrapperParameter5valueyAA0F0VySiG_tFACL_SivpfP : $@convention(thin) (Int) -> Wrapper<Int>
3434

3535
// property wrapper init from projected value of value #1 in testSimpleWrapperParameter(value:)
36-
// CHECK: sil private [ossa] @$s26property_wrapper_parameter26testSimpleWrapperParameter5valueyAA0F0VySiG_tFACL_SivpfW : $@convention(thin) (Projection<Int>) -> Wrapper<Int>
36+
// CHECK: sil non_abi [serialized] [ossa] @$s26property_wrapper_parameter26testSimpleWrapperParameter5valueyAA0F0VySiG_tFACL_SivpfW : $@convention(thin) (Projection<Int>) -> Wrapper<Int>
3737

3838
// getter of $value #1 in testSimpleWrapperParameter(value:)
3939
// CHECK: sil private [ossa] @$s26property_wrapper_parameter26testSimpleWrapperParameter5valueyAA0F0VySiG_tF6$valueL_AA10ProjectionVySiGvg : $@convention(thin) (Wrapper<Int>) -> Projection<Int>
@@ -184,3 +184,29 @@ func testImplicitPropertyWrapper(projection: ProjectionWrapper<Int>) {
184184
// getter of value #1 in closure #2 in implicit closure #2 in testImplicitPropertyWrapper(projection:)
185185
// CHECK: sil private [ossa] @$s26property_wrapper_parameter27testImplicitPropertyWrapper10projectionyAA010ProjectionG0VySiG_tFSi_AFtAFcfu0_Si_AFtAFcfU0_5valueL_Sivg : $@convention(thin) () -> Int
186186
}
187+
188+
@propertyWrapper
189+
public struct PublicWrapper<T> {
190+
public var wrappedValue: T
191+
192+
public init(wrappedValue: T) {
193+
self.wrappedValue = wrappedValue
194+
}
195+
196+
public var projectedValue: PublicWrapper<T> {
197+
return self
198+
}
199+
200+
public init(projectedValue: PublicWrapper<T>) {
201+
self.wrappedValue = projectedValue.wrappedValue
202+
}
203+
}
204+
205+
// CHECK-LABEL: sil [ossa] @$s26property_wrapper_parameter10publicFunc5valueyAA13PublicWrapperVySSG_tF : $@convention(thin) (@guaranteed PublicWrapper<String>) -> ()
206+
public func publicFunc(@PublicWrapper value: String) {
207+
// property wrapper backing initializer of value #1 in publicFunc(value:)
208+
// CHECK: sil non_abi [serialized] [ossa] @$s26property_wrapper_parameter10publicFunc5valueyAA13PublicWrapperVySSG_tFACL_SSvpfP : $@convention(thin) (@owned String) -> @owned PublicWrapper<String>
209+
210+
// property wrapper init from projected value of value #1 in publicFunc(value:)
211+
// CHECK: sil non_abi [serialized] [ossa] @$s26property_wrapper_parameter10publicFunc5valueyAA13PublicWrapperVySSG_tFACL_SSvpfW : $@convention(thin) (@owned PublicWrapper<String>) -> @owned PublicWrapper<String>
212+
}

0 commit comments

Comments
 (0)