Skip to content

Commit 1c2acc1

Browse files
committed
Add a special case to handle "abstract" conformances in IRGen
that GenericSignature minimization resolves as concrete. rdar://25695389
1 parent b3a2762 commit 1c2acc1

File tree

2 files changed

+40
-0
lines changed

2 files changed

+40
-0
lines changed

lib/IRGen/GenArchetype.cpp

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -180,6 +180,20 @@ class ArchetypeTypeInfoBase {
180180
auto wtable = IGF.tryGetLocalTypeData(archetype, localDataKind);
181181
if (wtable) return wtable;
182182

183+
// It can happen with class constraints that Sema will consider a
184+
// constraint to be abstract, but the minimized signature will
185+
// eliminate it as concrete. Handle this by performing a concrete
186+
// lookup.
187+
// TODO: maybe Sema shouldn't ever do this?
188+
if (Type classBound = archetype->getSuperclass()) {
189+
auto conformance =
190+
IGF.IGM.getSwiftModule()->lookupConformance(classBound, protocol,
191+
nullptr);
192+
if (conformance && conformance->isConcrete()) {
193+
return emitWitnessTableRef(IGF, archetype, *conformance);
194+
}
195+
}
196+
183197
// If that's not present, this conformance must be implied by some
184198
// associated-type relationship.
185199
auto accessPath =

test/IRGen/class_constraint.sil

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,26 @@
1+
// RUN: %target-swift-frontend -emit-ir -primary-file %s | FileCheck %s
2+
3+
protocol P {}
4+
class A : P {}
5+
6+
sil_vtable A {}
7+
8+
// <rdar://25695389>
9+
// Ensure that an "abstract" conformance that minimization
10+
// resolves as concrete doesn't mess up IRGen. Note that this test case
11+
// is only meaningful if type-checking actually resolves the conformance
12+
// as abstract, which it does today for both Swift and SIL inputs.
13+
// If it stops doing that, we can drop the special case in IRGen.
14+
sil @foo : $@convention(thin) <T where T : A, T : P> (@guaranteed T) -> () {
15+
bb0(%0 : $T):
16+
%1 = alloc_stack $P
17+
%2 = init_existential_addr %1 : $*P, $T
18+
strong_retain %0 : $T
19+
store %0 to %2 : $*T
20+
destroy_addr %1 : $*P
21+
dealloc_stack %1 : $*P
22+
%3 = tuple ()
23+
return %3 : $()
24+
}
25+
// CHECK: define {{.*}}void @foo(%C16class_constraint1A*, %swift.type* %T)
26+
// CHECK: store i8** @_TWPC16class_constraint1AS_1PS_,

0 commit comments

Comments
 (0)