Skip to content

Commit d302323

Browse files
committed
[IRGen] Ensure that empty structs respect non-trivial destruction of members
An empty struct that is noncopyable can nonetheless have a `deinit`, so it is not trivially destructible. In such cases, embedded them in another empty struct means that the outer struct should also not be trivially destructible. Make it so. (cherry picked from commit b19a325)
1 parent 07994da commit d302323

File tree

2 files changed

+19
-4
lines changed

2 files changed

+19
-4
lines changed

lib/IRGen/StructLayout.cpp

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -178,10 +178,10 @@ StructLayout::StructLayout(IRGenModule &IGM, std::optional<CanType> type,
178178
SpareBits.clear();
179179
IsFixedLayout = true;
180180
IsLoadable = true;
181-
IsKnownTriviallyDestroyable = deinit;
182-
IsKnownBitwiseTakable = IsBitwiseTakable;
183-
IsKnownAlwaysFixedSize = IsFixedSize;
184-
IsKnownCopyable = copyable;
181+
IsKnownTriviallyDestroyable = deinit & builder.isTriviallyDestroyable();
182+
IsKnownBitwiseTakable = builder.isBitwiseTakable();
183+
IsKnownAlwaysFixedSize = builder.isAlwaysFixedSize();
184+
IsKnownCopyable = copyable & builder.isCopyable();
185185
Ty = (typeToFill ? typeToFill : IGM.OpaqueTy);
186186
} else {
187187
MinimumAlign = builder.getAlignment();

test/IRGen/moveonly_deinits.swift

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -373,3 +373,18 @@ public func testKlassEnumPairWithDeinit() {
373373
consumeKlassEnumPairWithDeinit(f)
374374
}
375375
}
376+
377+
struct EmptyMoveOnlyWithDeinit: ~Copyable {
378+
deinit {}
379+
}
380+
381+
struct EnclosesEmptyMoveOnlyWithDeinit: ~Copyable {
382+
var stored: EmptyMoveOnlyWithDeinit
383+
}
384+
385+
// IR-LABEL: define {{.*}}swiftcc void @"$s16moveonly_deinits35testEnclosesEmptyMoveOnlyWithDeinityyF"()
386+
func testEnclosesEmptyMoveOnlyWithDeinit() {
387+
// CHECK-NOT: ret
388+
// CHECK: call swiftcc void @"$s16moveonly_deinits23EmptyMoveOnlyWithDeinitVfD"()
389+
_ = EnclosesEmptyMoveOnlyWithDeinit(stored: EmptyMoveOnlyWithDeinit())
390+
}

0 commit comments

Comments
 (0)