Skip to content

Commit 506fbb3

Browse files
authored
[Runtime] Fix alignment of tuples in runtime layout string instantiation (#69975)
rdar://118366415 If a tuple was not already aligned, this would cause a wrong offset to be used in the layout string.
1 parent 52eab43 commit 506fbb3

File tree

3 files changed

+41
-0
lines changed

3 files changed

+41
-0
lines changed

stdlib/public/runtime/Metadata.cpp

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2933,6 +2933,7 @@ void swift::_swift_addRefCountStringForMetatype(LayoutStringWriter &writer,
29332933
previousFieldOffset = offset + fieldType->vw_size();
29342934
fullOffset += fieldType->vw_size();
29352935
} else if (auto *tuple = dyn_cast<TupleTypeMetadata>(fieldType)) {
2936+
previousFieldOffset = offset;
29362937
for (InProcess::StoredSize i = 0; i < tuple->NumElements; i++) {
29372938
_swift_addRefCountStringForMetatype(writer, flags,
29382939
tuple->getElement(i).Type, fullOffset,

test/Interpreter/Inputs/layout_string_witnesses_types.swift

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -555,6 +555,17 @@ public enum SinglePayloadEnumExistential {
555555
case c
556556
}
557557

558+
public struct TupleLargeAlignment<T> {
559+
let x: AnyObject? = nil
560+
let x1: AnyObject? = nil
561+
let x2: AnyObject? = nil
562+
let x3: (T, SIMD4<Int>)
563+
564+
public init(_ t: T) {
565+
self.x3 = (t, .init(Int(Int32.max) + 32, Int(Int32.max) + 32, Int(Int32.max) + 32, Int(Int32.max) + 32))
566+
}
567+
}
568+
558569
@inline(never)
559570
public func consume<T>(_ x: T.Type) {
560571
withExtendedLifetime(x) {}

test/Interpreter/layout_string_witnesses_dynamic.swift

Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1132,6 +1132,35 @@ func testArrayAssignWithCopy() {
11321132

11331133
testArrayAssignWithCopy()
11341134

1135+
// This is a regression test for rdar://118366415
1136+
func testTupleAlignment() {
1137+
let ptr = allocateInternalGenericPtr(of: TupleLargeAlignment<TestClass>.self)
1138+
1139+
do {
1140+
let x = TupleLargeAlignment(TestClass())
1141+
testGenericInit(ptr, to: x)
1142+
}
1143+
1144+
do {
1145+
let y = TupleLargeAlignment(TestClass())
1146+
// CHECK: Before deinit
1147+
print("Before deinit")
1148+
1149+
// CHECK-NEXT: TestClass deinitialized!
1150+
testGenericAssign(ptr, from: y)
1151+
}
1152+
1153+
// CHECK-NEXT: Before deinit
1154+
print("Before deinit")
1155+
1156+
// CHECK-NEXT: TestClass deinitialized!
1157+
testGenericDestroy(ptr, of: TupleLargeAlignment<TestClass>.self)
1158+
1159+
ptr.deallocate()
1160+
}
1161+
1162+
testTupleAlignment()
1163+
11351164
#if os(macOS)
11361165

11371166
import Foundation

0 commit comments

Comments
 (0)