Skip to content

Commit c45dc6d

Browse files
committed
More resilient class layout tests
Looks like subclassing classes with resiliently-sized properties works, as long as the subclass is @_fixed_layout, so let's ensure that's tested. We don't want @_fixed_layout classes to be a thing though, and we still can't handle changes to the number of stored properties in a base class, so a couple of tests are disabled until I land some more patches.
1 parent 52b00c6 commit c45dc6d

File tree

3 files changed

+200
-0
lines changed

3 files changed

+200
-0
lines changed

test/IRGen/class_resilience.swift

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -37,6 +37,7 @@ public class ClassWithResilientProperty {
3737
}
3838
}
3939

40+
4041
// Concrete class with non-fixed size stored property
4142

4243
public class ClassWithResilientlySizedProperty {

test/Inputs/resilient_class.swift

Lines changed: 49 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,9 @@
1+
2+
import resilient_struct
3+
4+
5+
// Fixed-layout, fixed-size base class
6+
17
@_fixed_layout
28
public class OutsideParent {
39
public var property: String = "OutsideParent.property"
@@ -19,6 +25,25 @@ public class OutsideParent {
1925
}
2026
}
2127

28+
29+
// Fixed-layout, resiliently-sized base class
30+
31+
@_fixed_layout
32+
public class OutsideParentWithResilientProperty {
33+
public let p: Point
34+
public let s: Size
35+
public let color: Int32
36+
37+
public init(p: Point, s: Size, color: Int32) {
38+
self.p = p
39+
self.s = s
40+
self.color = color
41+
}
42+
}
43+
44+
45+
// Resilient base class
46+
2247
public class ResilientOutsideParent {
2348
public var property: String = "ResilientOutsideParent.property"
2449
public final var finalProperty: String = "ResilientOutsideParent.finalProperty"
@@ -40,6 +65,9 @@ public class ResilientOutsideParent {
4065
}
4166
}
4267

68+
69+
// Fixed-layout, fixed-size subclass
70+
4371
@_fixed_layout
4472
public class OutsideChild : OutsideParent {
4573
public override func method() {
@@ -53,6 +81,9 @@ public class OutsideChild : OutsideParent {
5381
}
5482
}
5583

84+
85+
// Resilient subclass
86+
5687
public class ResilientOutsideChild : ResilientOutsideParent {
5788
public override func method() {
5889
print("ResilientOutsideChild.method()")
@@ -65,6 +96,9 @@ public class ResilientOutsideChild : ResilientOutsideParent {
6596
}
6697
}
6798

99+
100+
// Fixed-layout, dependently-sized, generic base class
101+
68102
@_fixed_layout
69103
public class GenericOutsideParent<A> {
70104
public var property: A
@@ -82,6 +116,9 @@ public class GenericOutsideParent<A> {
82116
}
83117
}
84118

119+
120+
// Resilient generic base class
121+
85122
public class ResilientGenericOutsideParent<A> {
86123
public var property: A
87124
public init(property: A) {
@@ -98,6 +135,9 @@ public class ResilientGenericOutsideParent<A> {
98135
}
99136
}
100137

138+
139+
// Fixed-layout, dependently-sized, generic subclass
140+
101141
@_fixed_layout
102142
public class GenericOutsideChild<A> : GenericOutsideParent<A> {
103143
public override init(property: A) {
@@ -116,6 +156,9 @@ public class GenericOutsideChild<A> : GenericOutsideParent<A> {
116156
}
117157
}
118158

159+
160+
// Resilient generic subclass
161+
119162
public class ResilientGenericOutsideChild<A> : ResilientGenericOutsideParent<A> {
120163
public override init(property: A) {
121164
print("ResilientGenericOutsideGenericChild.init(a: A)")
@@ -133,6 +176,9 @@ public class ResilientGenericOutsideChild<A> : ResilientGenericOutsideParent<A>
133176
}
134177
}
135178

179+
180+
// Fixed-layout, fixed-size subclass of generic class
181+
136182
@_fixed_layout
137183
public class ConcreteOutsideChild : GenericOutsideParent<String> {
138184
public override init(property: String) {
@@ -151,6 +197,9 @@ public class ConcreteOutsideChild : GenericOutsideParent<String> {
151197
}
152198
}
153199

200+
201+
// Resilient subclass of generic class
202+
154203
public class ResilientConcreteOutsideChild : ResilientGenericOutsideParent<String> {
155204
public override init(property: String) {
156205
print("ResilientConcreteOutsideChild.init(property: String)")

test/Interpreter/class_resilience.swift

Lines changed: 150 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -43,6 +43,35 @@ ResilientClassTestSuite.test("ClassWithResilientProperty") {
4343
expectEqual(c.color, 50)
4444
}
4545

46+
47+
// Generic class with resilient stored property
48+
49+
public class GenericClassWithResilientProperty<T> {
50+
public let s1: Size
51+
public let t: T
52+
public let s2: Size
53+
54+
public init(s1: Size, t: T, s2: Size) {
55+
self.s1 = s1
56+
self.t = t
57+
self.s2 = s2
58+
}
59+
}
60+
61+
ResilientClassTestSuite.test("GenericClassWithResilientProperty") {
62+
let c = GenericClassWithResilientProperty<Int32>(
63+
s1: Size(w: 10, h: 20),
64+
t: 30,
65+
s2: Size(w: 40, h: 50))
66+
67+
expectEqual(c.s1.w, 10)
68+
expectEqual(c.s1.h, 20)
69+
expectEqual(c.t, 30)
70+
expectEqual(c.s2.w, 40)
71+
expectEqual(c.s2.h, 50)
72+
}
73+
74+
4675
// Concrete class with non-fixed size stored property
4776

4877
public class ClassWithResilientlySizedProperty {
@@ -71,4 +100,125 @@ ResilientClassTestSuite.test("ClassWithResilientlySizedProperty") {
71100
expectEqual(c.color, 60)
72101
}
73102

103+
104+
// Concrete subclass of fixed-layout class with resilient stored property
105+
106+
public class ChildOfParentWithResilientStoredProperty : ClassWithResilientProperty {
107+
let enabled: Int32
108+
109+
public init(p: Point, s: Size, color: Int32, enabled: Int32) {
110+
self.enabled = enabled
111+
super.init(p: p, s: s, color: color)
112+
}
113+
}
114+
115+
ResilientClassTestSuite.test("ChildOfParentWithResilientStoredProperty") {
116+
let c = ChildOfParentWithResilientStoredProperty(
117+
p: Point(x: 10, y: 20),
118+
s: Size(w: 30, h: 40),
119+
color: 50,
120+
enabled: 60)
121+
122+
expectEqual(c.p.x, 10)
123+
expectEqual(c.p.y, 20)
124+
expectEqual(c.s.w, 30)
125+
expectEqual(c.s.h, 40)
126+
expectEqual(c.color, 50)
127+
expectEqual(c.enabled, 60)
128+
}
129+
130+
131+
// Concrete subclass of fixed-layout class with resilient stored property
132+
133+
public class ChildOfOutsideParentWithResilientStoredProperty : OutsideParentWithResilientProperty {
134+
let enabled: Int32
135+
136+
public init(p: Point, s: Size, color: Int32, enabled: Int32) {
137+
self.enabled = enabled
138+
super.init(p: p, s: s, color: color)
139+
}
140+
}
141+
142+
ResilientClassTestSuite.test("ChildOfOutsideParentWithResilientStoredProperty") {
143+
let c = ChildOfOutsideParentWithResilientStoredProperty(
144+
p: Point(x: 10, y: 20),
145+
s: Size(w: 30, h: 40),
146+
color: 50,
147+
enabled: 60)
148+
149+
expectEqual(c.p.x, 10)
150+
expectEqual(c.p.y, 20)
151+
expectEqual(c.s.w, 30)
152+
expectEqual(c.s.h, 40)
153+
expectEqual(c.color, 50)
154+
expectEqual(c.enabled, 60)
155+
}
156+
157+
158+
// Resilient class from a different resilience domain
159+
160+
ResilientClassTestSuite.test("ResilientOutsideParent") {
161+
let c = ResilientOutsideParent()
162+
163+
expectEqual(c.property, "ResilientOutsideParent.property")
164+
expectEqual(c.finalProperty, "ResilientOutsideParent.finalProperty")
165+
}
166+
167+
168+
// FIXME: needs indirect metadata access
169+
170+
#if false
171+
// Concrete subclass of resilient class
172+
173+
public class ChildOfResilientOutsideParent : ResilientOutsideParent {
174+
let enabled: Int32
175+
176+
public init(enabled: Int32) {
177+
self.enabled = enabled
178+
super.init()
179+
}
180+
}
181+
182+
ResilientClassTestSuite.test("ChildOfResilientOutsideParent") {
183+
let c = ChildOfResilientOutsideParent(enabled: 60)
184+
185+
expectEqual(c.property, "ResilientOutsideParent.property")
186+
expectEqual(c.finalProperty, "ResilientOutsideParent.finalProperty")
187+
expectEqual(c.enabled, 60)
188+
}
189+
190+
191+
// Concrete subclass of resilient class
192+
193+
public class ChildOfResilientOutsideParentWithResilientStoredProperty : ResilientOutsideParent {
194+
public let p: Point
195+
public let s: Size
196+
public let color: Int32
197+
198+
public init(p: Point, s: Size, color: Int32) {
199+
self.p = p
200+
self.s = s
201+
self.color = color
202+
super.init()
203+
}
204+
}
205+
206+
ResilientClassTestSuite.test("ChildOfResilientOutsideParentWithResilientStoredProperty") {
207+
let c = ChildOfResilientOutsideParentWithResilientStoredProperty(
208+
p: Point(x: 10, y: 20),
209+
s: Size(w: 30, h: 40),
210+
color: 50)
211+
212+
expectEqual(c.property, "ResilientOutsideParent.property")
213+
expectEqual(c.finalProperty, "ResilientOutsideParent.finalProperty")
214+
215+
expectEqual(c.p.x, 10)
216+
expectEqual(c.p.y, 20)
217+
expectEqual(c.s.w, 30)
218+
expectEqual(c.s.h, 40)
219+
expectEqual(c.color, 50)
220+
}
221+
#endif
222+
223+
74224
runAllTests()

0 commit comments

Comments
 (0)