Skip to content

Commit e5e5a80

Browse files
authored
Merge pull request #15272 from aschwaighofer/swift-4.1-branch-irgen_fix_typelayout_protocol_metatype
[4.1] IRGen: The type layout of a metatype is not the same as the NativeObject.Type
2 parents b2e070f + b62adb9 commit e5e5a80

File tree

3 files changed

+51
-0
lines changed

3 files changed

+51
-0
lines changed

lib/IRGen/GenMeta.cpp

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1902,6 +1902,10 @@ namespace {
19021902
return emitFromValueWitnessTable(IGF.IGM.Context.TheEmptyTupleType);
19031903
}
19041904
case MetatypeRepresentation::Thick:
1905+
if (isa<ExistentialMetatypeType>(type)) {
1906+
return emitFromTypeMetadata(type);
1907+
}
1908+
// Otherwise, this is a metatype that looks like a pointer.
19051909
case MetatypeRepresentation::ObjC:
19061910
// Thick metatypes look like pointers with spare bits.
19071911
return emitFromValueWitnessTable(

test/IRGen/type_layout_reference_storage.swift

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -91,3 +91,21 @@ struct ReferenceStorageTypeLayout<T, Native : C, Unknown : AnyObject> {
9191
// CHECK: store i8** getelementptr inbounds (i8*, i8** @_T0[[UNKNOWN]]SgXwWV, i32 9)
9292
weak var uwi: Unknown!
9393
}
94+
95+
96+
public class Base {
97+
var a: UInt32 = 0
98+
}
99+
100+
// CHECK-LABEL: %swift.type* @create_generic_metadata_Derived(%swift.type_pattern*, i8**)
101+
// CHECK-NOT: store {{.*}}getelementptr{{.*}}T0BomWV
102+
// CHECK: call %swift.type* @{{.*}}type_layout_reference_storage1P_pXmTMa()
103+
// CHECK: store {{.*}}getelementptr{{.*}}T0BoWV
104+
// CHECK: ret
105+
public class Derived<T> : Base {
106+
var type : P.Type
107+
var k = C()
108+
init(_ t: P.Type) {
109+
type = t
110+
}
111+
}

test/Interpreter/metatype.swift

Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,29 @@
1+
// RUN: %target-run-simple-swift | %FileCheck %s
2+
// REQUIRES: executable_test
3+
4+
protocol Bar : class {
5+
}
6+
7+
public class Foo : Bar {
8+
}
9+
10+
public class Base {
11+
final fileprivate(set) var a: UInt32 = 0
12+
}
13+
14+
public class Derived<T> : Base {
15+
final var type : Bar.Type
16+
final var k = Foo()
17+
18+
init(_ t: Bar.Type, _ kl: Foo ) {
19+
type = t
20+
k = kl
21+
}
22+
}
23+
24+
public func dontCrash() {
25+
// CHECK: Derived<Swift.Int>
26+
print(Derived<Int>(Foo.self, Foo()))
27+
}
28+
29+
dontCrash()

0 commit comments

Comments
 (0)