Skip to content

Commit 61d35f0

Browse files
authored
Merge pull request #40766 from DougGregor/mangle-multiple-opaque-types
Introduce a mangling for multiple opaque types within the declaration.
2 parents 0844bbd + f89ff04 commit 61d35f0

File tree

11 files changed

+43
-9
lines changed

11 files changed

+43
-9
lines changed

docs/ABI/Mangling.rst

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -737,15 +737,17 @@ implementation details of a function type.
737737
::
738738

739739
#if SWIFT_VERSION >= 5.1
740-
type ::= 'Qr' // opaque result type (of current decl)
740+
type ::= 'Qr' // opaque result type (of current decl, used for the first opaque type parameter only)
741+
type ::= 'QR' INDEX // same as above, for subsequent opaque type parameters, INDEX is the ordinal -1
741742
type ::= opaque-type-decl-name bound-generic-args 'Qo' INDEX // opaque type
742743

743744
opaque-type-decl-name ::= entity 'QO' // opaque result type of specified decl
744745
#endif
745746

746747
#if SWIFT_VERSION >= 5.4
747-
type ::= 'Qu' // opaque result type (of current decl)
748+
type ::= 'Qu' // opaque result type (of current decl, first param)
748749
// used for ObjC class runtime name purposes.
750+
type ::= 'QU' INDEX
749751
#endif
750752

751753
Opaque return types have a special short representation in the mangling of

include/swift/Demangling/DemangleNodes.def

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -329,5 +329,8 @@ NODE(AsyncSuspendResumePartialFunction)
329329
// Added in Swift 5.6
330330
NODE(AccessibleFunctionRecord)
331331

332+
// Added in Swift 5.7
333+
NODE(OpaqueReturnTypeIndexed)
334+
332335
#undef CONTEXT_NODE
333336
#undef NODE

lib/AST/ASTMangler.cpp

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1320,7 +1320,10 @@ void ASTMangler::appendType(Type type, GenericSignature sig,
13201320
auto opaqueDecl = opaqueType->getDecl();
13211321
if (opaqueDecl->getNamingDecl() == forDecl) {
13221322
assert(opaqueType->getSubstitutions().isIdentity());
1323-
return appendOperator("Qr");
1323+
if (opaqueType->getOrdinal() == 0)
1324+
return appendOperator("Qr");
1325+
1326+
return appendOperator("QR", Index(opaqueType->getOrdinal() - 1));
13241327
}
13251328

13261329
// Otherwise, try to substitute it.
@@ -1360,7 +1363,8 @@ void ASTMangler::appendType(Type type, GenericSignature sig,
13601363
addTypeSubstitution(nestedType, sig);
13611364
return;
13621365
}
1363-
1366+
1367+
// FIXME: Never actually used.
13641368
appendType(nestedType->getParent(), sig, forDecl);
13651369
appendIdentifier(nestedType->getName().str());
13661370
appendOperator("Qa");

lib/Demangling/Demangler.cpp

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2206,6 +2206,12 @@ NodePointer Demangler::demangleArchetype() {
22062206
case 'r': {
22072207
return createType(createNode(Node::Kind::OpaqueReturnType));
22082208
}
2209+
case 'R': {
2210+
int ordinal = demangleIndex();
2211+
if (ordinal < 0)
2212+
return NULL;
2213+
return createType(createNode(Node::Kind::OpaqueReturnTypeIndexed, ordinal));
2214+
}
22092215

22102216
case 'x': {
22112217
NodePointer T = demangleAssociatedTypeSimple(nullptr);

lib/Demangling/NodePrinter.cpp

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -568,6 +568,7 @@ class NodePrinter {
568568
case Node::Kind::OpaqueType:
569569
case Node::Kind::OpaqueTypeDescriptorSymbolicReference:
570570
case Node::Kind::OpaqueReturnType:
571+
case Node::Kind::OpaqueReturnTypeIndexed:
571572
case Node::Kind::OpaqueReturnTypeOf:
572573
case Node::Kind::CanonicalSpecializedGenericMetaclass:
573574
case Node::Kind::CanonicalSpecializedGenericTypeMetadataAccessFunction:
@@ -2817,6 +2818,7 @@ NodePointer NodePrinter::print(NodePointer Node, unsigned depth,
28172818
Printer << ")";
28182819
return nullptr;
28192820
case Node::Kind::OpaqueReturnType:
2821+
case Node::Kind::OpaqueReturnTypeIndexed:
28202822
Printer << "some";
28212823
return nullptr;
28222824
case Node::Kind::OpaqueReturnTypeOf:

lib/Demangling/OldDemangler.cpp

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2078,6 +2078,13 @@ class OldDemangler {
20782078
// Special mangling for opaque return type.
20792079
return Factory.createNode(Node::Kind::OpaqueReturnType);
20802080
}
2081+
if (Mangled.nextIf('U')) {
2082+
// Special mangling for opaque return type.
2083+
Node::IndexType ordinal;
2084+
if (!demangleIndex(ordinal, depth))
2085+
return nullptr;
2086+
return Factory.createNode(Node::Kind::OpaqueReturnTypeIndexed, ordinal);
2087+
}
20812088
return demangleArchetypeType(depth + 1);
20822089
}
20832090
if (c == 'q') {

lib/Demangling/OldRemangler.cpp

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2643,6 +2643,11 @@ ManglingError Remangler::mangleOpaqueReturnType(Node *node, unsigned depth) {
26432643
Buffer << "Qu";
26442644
return ManglingError::Success;
26452645
}
2646+
ManglingError Remangler::mangleOpaqueReturnTypeIndexed(Node *node, unsigned depth) {
2647+
Buffer << "QU";
2648+
mangleIndex(node->getIndex());
2649+
return ManglingError::Success;
2650+
}
26462651
ManglingError Remangler::mangleOpaqueReturnTypeOf(Node *node,
26472652
EntityContext &ctx,
26482653
unsigned depth) {

lib/Demangling/Remangler.cpp

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3280,6 +3280,11 @@ ManglingError Remangler::mangleOpaqueReturnType(Node *node, unsigned depth) {
32803280
Buffer << "Qr";
32813281
return ManglingError::Success;
32823282
}
3283+
ManglingError Remangler::mangleOpaqueReturnTypeIndexed(Node *node, unsigned depth) {
3284+
Buffer << "QR";
3285+
mangleIndex(node->getIndex());
3286+
return ManglingError::Success;
3287+
}
32833288
ManglingError Remangler::mangleOpaqueReturnTypeOf(Node *node, unsigned depth) {
32843289
RETURN_IF_ERROR(mangle(node->getChild(0), depth + 1));
32853290
Buffer << "QO";

test/IRGen/opaque_result_type.swift

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -188,7 +188,7 @@ public func useFoo(x: String, y: C) {
188188
let _ = bauble(z: y, u: y)
189189
}
190190

191-
// CHECK-LABEL: define {{.*}} @"$s18opaque_result_type6bauble1z1uSayQr_QrSgtGx_q_tAA6MarkerRzAA1PRzAA1QRzAaIR_r0_lF"
191+
// CHECK-LABEL: define {{.*}} @"$s18opaque_result_type6bauble1z1uSayQr_QR_SgtGx_q_tAA6MarkerRzAA1PRzAA1QRzAaIR_r0_lF"
192192

193193
// CHECK-LABEL: define {{.*}} @"$s18opaque_result_type6useFoo1x1yySS_AA1CCtF"
194194
// CHECK: [[OPAQUE:%.*]] = call {{.*}} @"$s18opaque_result_type3baz1zQrx_tAA1PRzAA1QRzlFQOMg"
@@ -203,7 +203,7 @@ struct Boom<T: P> {
203203
}
204204

205205
// CHECK-LABEL: define {{.*}} @"$s18opaque_result_type9gimmeBoomypyF
206-
// CHECK: call swiftcc void @"$s18opaque_result_type4BoomV5prop15prop2ACyxGSi_AcEQr_QrtvpQOyx_Qo__AcEQr_QrtvpQOyx_Qo0_ttcfcfA0_"
206+
// CHECK: call swiftcc void @"$s18opaque_result_type4BoomV5prop15prop2ACyxGSi_AcEQr_QR_tvpQOyx_Qo__AcEQr_QR_tvpQOyx_Qo0_ttcfcfA0_"
207207
public func gimmeBoom() -> Any {
208208
Boom<String>(prop1: 5)
209209
}

test/IRGen/opaque_result_type_debug.swift

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -68,9 +68,9 @@ public func bar<T: P>(genericValue: T) {
6868
// CHECK-DAG: {{![0-9]+}} = !DILocalVariable(name: "opaqueValue",{{.*}} type: ![[LET_OPAQUE_TYPE]])
6969
// CHECK-DAG: {{![0-9]+}} = !DILocalVariable(name: "opaquePropValue",{{.*}} type: ![[LET_OPAQUE_PROP_TYPE]])
7070
// CHECK-DAG: {{![0-9]+}} = !DILocalVariable(name: "opaqueSubValue",{{.*}} type: ![[LET_OPAQUE_SUB_TYPE]])
71-
// CHECK-DAG: ![[OPAQUE_ARRAY_FIRST_TYPE:[0-9]+]] = !DICompositeType({{.*}} name: "$s30opaque_result_type_debug_other3barSayQr_QrSgtGyFQOyQo_D"
71+
// CHECK-DAG: ![[OPAQUE_ARRAY_FIRST_TYPE:[0-9]+]] = !DICompositeType({{.*}} name: "$s30opaque_result_type_debug_other3barSayQr_QR_SgtGyFQOyQo_D"
7272
// CHECK-DAG: ![[LET_OPAQUE_ARRAY_FIRST_TYPE:[0-9]+]] = !DIDerivedType(tag: DW_TAG_const_type, baseType: ![[OPAQUE_ARRAY_FIRST_TYPE]])
7373
// CHECK-DAG: {{![0-9]+}} = !DILocalVariable(name: "opaqueArrayFirst",{{.*}} type: ![[LET_OPAQUE_ARRAY_FIRST_TYPE]])
74-
// CHECK-DAG: ![[OPAQUE_ARRAY_SECOND_TYPE:[0-9]+]] = !DICompositeType({{.*}} name: "$s30opaque_result_type_debug_other3barSayQr_QrSgtGyFQOyQo0_D"
74+
// CHECK-DAG: ![[OPAQUE_ARRAY_SECOND_TYPE:[0-9]+]] = !DICompositeType({{.*}} name: "$s30opaque_result_type_debug_other3barSayQr_QR_SgtGyFQOyQo0_D"
7575
// CHECK-DAG: ![[LET_OPAQUE_ARRAY_SECOND_TYPE:[0-9]+]] = !DIDerivedType(tag: DW_TAG_const_type, baseType: ![[OPAQUE_ARRAY_SECOND_TYPE]])
7676
// CHECK-DAG: {{![0-9]+}} = !DILocalVariable(name: "opaqueArraySecond",{{.*}} type: ![[LET_OPAQUE_ARRAY_SECOND_TYPE]])

test/Serialization/opaque_type_structured.swift

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,7 @@ func acceptR<T: R>(_: T) { }
99
// AST: func f() -> (some P, [some Q])
1010

1111
func passAnX(x: X) {
12-
// SIL: $@convention(method) (@in_guaranteed X) -> (@out @_opaqueReturnTypeOf("$s20OpaqueTypeStructured1XV1fQr_SayQrGtyF", 0) __, @owned Array<@_opaqueReturnTypeOf("$s20OpaqueTypeStructured1XV1fQr_SayQrGtyF", 1) __>)
12+
// SIL: $@convention(method) (@in_guaranteed X) -> (@out @_opaqueReturnTypeOf("$s20OpaqueTypeStructured1XV1fQr_SayQR_GtyF", 0) __, @owned Array<@_opaqueReturnTypeOf("$s20OpaqueTypeStructured1XV1fQr_SayQR_GtyF", 1) __>)
1313
acceptR(x)
1414
let _: X.A = x.f()
1515
}

0 commit comments

Comments
 (0)