Skip to content

Commit c2db1b5

Browse files
Merge pull request #61646 from aschwaighofer/fix_constraint_existential_outlined_copy
IRGen: Fix outlined value operations for (constraint) existentials.
2 parents 0fc5ba1 + 443fe61 commit c2db1b5

File tree

2 files changed

+43
-0
lines changed

2 files changed

+43
-0
lines changed

lib/IRGen/Outlining.cpp

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -210,6 +210,12 @@ static bool canUseValueWitnessForValueOp(IRGenModule &IGM, SILType T) {
210210
if (!IGM.getSILModule().isTypeMetadataForLayoutAccessible(T))
211211
return false;
212212

213+
// It is not a good code size trade-off to instantiate a metatype for
214+
// existentials, and also does not back-deploy gracefully in the case of
215+
// constrained protocols.
216+
if (T.getASTType()->isExistentialType())
217+
return false;
218+
213219
if (needsSpecialOwnershipHandling(T))
214220
return false;
215221
if (T.getASTType()->hasDynamicSelfType())

test/IRGen/existentials.sil

Lines changed: 37 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
11
// RUN: %target-swift-frontend %s -emit-ir -disable-objc-interop | %FileCheck %s
2+
// RUN: %target-swift-frontend %s -emit-ir -disable-objc-interop -O | %FileCheck %s --check-prefix=OPT
23

34
// REQUIRES: CPU=x86_64
45

@@ -99,3 +100,39 @@ entry(%w : $*@sil_weak CP?, %a : $CP?):
99100

100101
return undef : $()
101102
}
103+
104+
protocol Constrained<T> {
105+
associatedtype T
106+
}
107+
108+
sil @keep_alive : $@convention(thin)(@inout any Constrained<Int>) -> ()
109+
sil @constrained_protocol : $@convention(thin) (@inout any Constrained<Int>) -> () {
110+
entry(%arg : $*any Constrained<Int>):
111+
112+
%dst = alloc_stack $any Constrained<Int>
113+
114+
copy_addr %arg to [initialization] %dst : $*any Constrained<Int>
115+
116+
%fn = function_ref @keep_alive : $@convention(thin)(@inout any Constrained<Int>) -> ()
117+
apply %fn(%dst) : $@convention(thin)(@inout any Constrained<Int>) -> ()
118+
119+
destroy_addr %dst : $*any Constrained<Int>
120+
121+
dealloc_stack %dst : $*any Constrained<Int>
122+
%t = tuple ()
123+
return %t : $()
124+
}
125+
126+
// Make sure we don't instantiate metadata for constrained existentials. Metadata
127+
// instatiation is not supported on older runtimes.
128+
129+
// OPT: define{{.*}} void @constrained_protocol(
130+
// OPT: call {{.*}} @"$s12existentials11Constrained_pSi1TAaBPRts_XPWOc"
131+
132+
// OPT: define{{.*}} @"$s12existentials11Constrained_pSi1TAaBPRts_XPWOc"
133+
// OPT-NOT: call {{.*}} instantiate
134+
// OPT-NOT: ret
135+
// OPT: load
136+
// OPT: store
137+
// OPT: call
138+
// OPT: ret

0 commit comments

Comments
 (0)