Skip to content

Commit 4eb9c3b

Browse files
committed
[cxx-interop] Make sure to create empty initializers for C++ structs
The existing synthesis mechanism had a bug: `cxxRecordDecl->hasDefaultConstructor()` returns true for C++ types with an implicit default constructor, for instance, `pthread_mutexattr_t`. rdar://113708880
1 parent f02ca3b commit 4eb9c3b

File tree

5 files changed

+34
-2
lines changed

5 files changed

+34
-2
lines changed

lib/ClangImporter/ImportDecl.cpp

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2381,8 +2381,12 @@ namespace {
23812381
hasMemberwiseInitializer = false;
23822382
}
23832383

2384-
if (hasZeroInitializableStorage &&
2385-
!(cxxRecordDecl && cxxRecordDecl->hasDefaultConstructor())) {
2384+
bool needsEmptyInitializer = true;
2385+
if (cxxRecordDecl) {
2386+
needsEmptyInitializer = !cxxRecordDecl->hasDefaultConstructor() ||
2387+
cxxRecordDecl->ctors().empty();
2388+
}
2389+
if (hasZeroInitializableStorage && needsEmptyInitializer) {
23862390
// Add default constructor for the struct if compiling in C mode.
23872391
// If we're compiling for C++:
23882392
// 1. If a default constructor is declared, don't synthesize one.
Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
// RUN: %target-typecheck-verify-swift -verify-ignore-unknown -I %S/Inputs -enable-objc-interop -enable-experimental-cxx-interop
2+
// REQUIRES: OS=macosx
3+
4+
import Darwin
5+
6+
_ = pthread_mutexattr_t() // expected-warning {{'init()' is deprecated: This zero-initializes the backing memory of the struct}}

test/Interop/Cxx/symbolic-imports/indexing-emit-symbolic-module-interface-used-decls.swift

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -35,6 +35,9 @@ public func useConcreteTemplate() {
3535
// CHECK-EMPTY:
3636
// CHECK-NEXT: public struct TemplateRecord {
3737
// CHECK-EMPTY:
38+
// CHECK-NEXT: @available(*, deprecated, message:
39+
// CHECK-NEXT: public init()
40+
// CHECK-EMPTY:
3841
// CHECK-NEXT: public func methodFunc(_ x: Any)
3942
// CHECK-NEXT:}
4043
// CHECK-NEXT:}

test/Interop/Cxx/symbolic-imports/indexing-emit-symbolic-module-interface.swift

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -123,15 +123,24 @@ import CxxModule
123123
// CHECK-EMPTY:
124124
// CHECK-NEXT: struct TemplateRecord {
125125
// CHECK-EMPTY:
126+
// CHECK-NEXT: @available(*, deprecated, message:
127+
// CHECK-NEXT: public init()
128+
// CHECK-EMPTY:
126129
// CHECK-NEXT: mutating func methodFunc(_ x: Any)
127130
// CHECK-EMPTY:
128131
// CHECK-NEXT: struct InnerRecord {
129132
// CHECK-EMPTY:
133+
// CHECK-NEXT: @available(*, deprecated, message:
134+
// CHECK-NEXT: public init()
135+
// CHECK-EMPTY:
130136
// CHECK-NEXT: mutating func innerMethod(_ y: Any)
131137
// CHECK-NEXT: }
132138
// CHECK-EMPTY:
133139
// CHECK-NEXT: struct InnerTemplate {
134140
// CHECK-EMPTY:
141+
// CHECK-NEXT: @available(*, deprecated, message:
142+
// CHECK-NEXT: public init()
143+
// CHECK-EMPTY:
135144
// CHECK-NEXT: mutating func innerTemplateMethod()
136145
// CHECK-NEXT: }
137146
// CHECK-EMPTY:

test/Interop/Cxx/symbolic-imports/print-symbolic-module-interface.swift

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -66,11 +66,17 @@ public:
6666
// CHECK-NEXT: var y: Int32
6767
// CHECK-NEXT: }
6868
// CHECK-NEXT: struct TemplateRecord {
69+
// CHECK-NEXT: @available(*, deprecated, message:
70+
// CHECK-NEXT: init()
6971
// CHECK-NEXT: mutating func methodFunc(_ x: Any)
7072
// CHECK-NEXT: struct InnerRecord {
73+
// CHECK-NEXT: @available(*, deprecated, message:
74+
// CHECK-NEXT: init()
7175
// CHECK-NEXT: mutating func innerMethod(_ y: Any)
7276
// CHECK-NEXT: }
7377
// CHECK-NEXT: struct InnerTemplate {
78+
// CHECK-NEXT: @available(*, deprecated, message:
79+
// CHECK-NEXT: init()
7480
// CHECK-NEXT: mutating func innerTemplateMethod()
7581
// CHECK-NEXT: }
7682
// CHECK-NEXT: mutating func returnsTemplateMethod()
@@ -79,7 +85,11 @@ public:
7985
// CHECK-NEXT: }
8086
// CHECK-NEXT: typealias MyType = ns.TemplateRecord
8187
// CHECK-NEXT: struct OuterTemp2 {
88+
// CHECK-NEXT: @available(*, deprecated, message:
89+
// CHECK-NEXT: init()
8290
// CHECK-NEXT: struct InnerTemp2 {
91+
// CHECK-NEXT: @available(*, deprecated, message:
92+
// CHECK-NEXT: init()
8393
// CHECK-NEXT: init(x2: Any)
8494
// CHECK-NEXT: mutating func testMe(_ p: Any, _ x: Any)
8595
// CHECK-NEXT: var x2: Any

0 commit comments

Comments
 (0)