Skip to content

Commit fc8be62

Browse files
committed
RemoteAST: Add a request to get the underlying type from an opaque type descriptor.
1 parent e7cd0a1 commit fc8be62

File tree

8 files changed

+102
-11
lines changed

8 files changed

+102
-11
lines changed

include/swift/ABI/Metadata.h

Lines changed: 8 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -3044,11 +3044,16 @@ struct TargetOpaqueTypeDescriptor final
30443044
return getNumUnderlyingTypeArguments();
30453045
}
30463046

3047+
const RelativeDirectPointer<const char> &
3048+
getUnderlyingTypeArgumentMangledName(unsigned i) const {
3049+
assert(i < getNumUnderlyingTypeArguments());
3050+
return (this
3051+
->template getTrailingObjects<RelativeDirectPointer<const char>>())[i];
3052+
}
3053+
30473054
StringRef getUnderlyingTypeArgument(unsigned i) const {
30483055
assert(i < getNumUnderlyingTypeArguments());
3049-
const char *ptr =
3050-
(this->template getTrailingObjects<RelativeDirectPointer<const char>>())[i];
3051-
3056+
const char *ptr = getUnderlyingTypeArgumentMangledName(i);
30523057
return Demangle::makeSymbolicMangledNameStringRef(ptr);
30533058
}
30543059

include/swift/AST/ASTMangler.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -171,6 +171,8 @@ class ASTMangler : public Mangler {
171171

172172
std::string mangleTypeForDebugger(Type decl, const DeclContext *DC);
173173

174+
std::string mangleOpaqueTypeDescriptor(const OpaqueTypeDecl *decl);
175+
174176
std::string mangleDeclType(const ValueDecl *decl);
175177

176178
std::string mangleObjCRuntimeName(const NominalTypeDecl *Nominal);

include/swift/AST/Types.h

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4802,6 +4802,18 @@ class OpaqueTypeArchetypeType final : public ArchetypeType,
48024802
return T->getKind() == TypeKind::OpaqueTypeArchetype;
48034803
}
48044804

4805+
/// Get the ordinal of the type within the declaration's opaque signature.
4806+
///
4807+
/// If a method declared its return type as:
4808+
///
4809+
/// func foo() -> (some P, some Q)
4810+
///
4811+
/// then the underlying type of `some P` would be ordinal 0, and `some Q` would be ordinal 1.
4812+
unsigned getOrdinal() const {
4813+
// TODO: multiple opaque types
4814+
return 0;
4815+
}
4816+
48054817
static void Profile(llvm::FoldingSetNodeID &ID,
48064818
OpaqueTypeDecl *OpaqueDecl,
48074819
SubstitutionMap Substitutions);

include/swift/Remote/MetadataReader.h

Lines changed: 35 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -724,6 +724,35 @@ class MetadataReader {
724724
return nullptr;
725725
return buildContextMangling(context, Dem);
726726
}
727+
728+
/// Read the mangled underlying type from an opaque type descriptor.
729+
BuiltType
730+
readUnderlyingTypeForOpaqueTypeDescriptor(StoredPointer contextAddr,
731+
unsigned ordinal) {
732+
auto context = readContextDescriptor(contextAddr);
733+
if (!context)
734+
return BuiltType();
735+
if (context->getKind() != ContextDescriptorKind::OpaqueType)
736+
return BuiltType();
737+
738+
auto opaqueType =
739+
reinterpret_cast<const TargetOpaqueTypeDescriptor<Runtime> *>(
740+
context.getLocalBuffer());
741+
742+
if (ordinal >= opaqueType->getNumUnderlyingTypeArguments())
743+
return BuiltType();
744+
745+
auto nameAddr = resolveRelativeField(context,
746+
opaqueType->getUnderlyingTypeArgumentMangledName(ordinal));
747+
748+
Demangle::Demangler Dem;
749+
auto node = readMangledName(RemoteAddress(nameAddr),
750+
MangledNameKind::Type, Dem);
751+
if (!node)
752+
return BuiltType();
753+
754+
return decodeMangledType(node);
755+
}
727756

728757
bool isTaggedPointer(StoredPointer objectAddress) {
729758
if (getTaggedPointerEncoding() != TaggedPointerEncodingKind::Extended)
@@ -1396,6 +1425,12 @@ class MetadataReader {
13961425
case ContextDescriptorKind::Protocol:
13971426
baseSize = sizeof(TargetProtocolDescriptor<Runtime>);
13981427
break;
1428+
case ContextDescriptorKind::OpaqueType:
1429+
baseSize = sizeof(TargetOpaqueTypeDescriptor<Runtime>);
1430+
metadataInitSize =
1431+
sizeof(typename Runtime::template RelativeDirectPointer<const char>)
1432+
* flags.getKindSpecificFlags();
1433+
break;
13991434
default:
14001435
// We don't know about this kind of context.
14011436
return nullptr;

include/swift/RemoteAST/RemoteAST.h

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -240,6 +240,17 @@ class RemoteASTContext {
240240
Result<OpenedExistential>
241241
getDynamicTypeAndAddressForExistential(remote::RemoteAddress address,
242242
Type staticType);
243+
244+
/// Given a reference to an opaque type descriptor, an ordinal, and a set
245+
/// of substitutions, get the underlying type for the opaque type.
246+
///
247+
/// This does not recursively apply the transformation if the underlying
248+
/// type in turn refers to another opaque type.
249+
Result<Type>
250+
getUnderlyingTypeForOpaqueType(remote::RemoteAddress opaqueDescriptor,
251+
SubstitutionMap substitutions,
252+
unsigned ordinal);
253+
243254
};
244255

245256
} // end namespace remoteAST

lib/AST/ASTMangler.cpp

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2665,3 +2665,10 @@ void ASTMangler::appendOpParamForLayoutConstraint(LayoutConstraint layout) {
26652665
break;
26662666
}
26672667
}
2668+
2669+
std::string ASTMangler::mangleOpaqueTypeDescriptor(const OpaqueTypeDecl *decl) {
2670+
beginMangling();
2671+
appendOpaqueDeclName(decl);
2672+
appendOperator("MQ");
2673+
return finalize();
2674+
}

lib/IRGen/IRGenMangler.h

Lines changed: 0 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -123,13 +123,6 @@ class IRGenMangler : public Mangle::ASTMangler {
123123
return mangleNominalTypeSymbol(Decl, "Mn");
124124
}
125125

126-
std::string mangleOpaqueTypeDescriptor(const OpaqueTypeDecl *decl) {
127-
beginMangling();
128-
appendOpaqueDeclName(decl);
129-
appendOperator("MQ");
130-
return finalize();
131-
}
132-
133126
std::string mangleOpaqueTypeDescriptorAccessor(const OpaqueTypeDecl *decl) {
134127
beginMangling();
135128
appendOpaqueDeclName(decl);

lib/RemoteAST/RemoteAST.cpp

Lines changed: 27 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -109,7 +109,10 @@ class RemoteASTContextImpl {
109109
virtual Result<OpenedExistential>
110110
getDynamicTypeAndAddressForExistential(RemoteAddress object,
111111
Type staticType) = 0;
112-
112+
virtual Result<Type>
113+
getUnderlyingTypeForOpaqueType(remote::RemoteAddress opaqueDescriptor,
114+
SubstitutionMap substitutions,
115+
unsigned ordinal) = 0;
113116
Result<uint64_t>
114117
getOffsetOfMember(Type type, RemoteAddress optMetadata, StringRef memberName){
115118
// Sanity check: obviously invalid arguments.
@@ -622,6 +625,20 @@ class RemoteASTContextConcreteImpl final : public RemoteASTContextImpl {
622625
}
623626
llvm_unreachable("invalid type kind");
624627
}
628+
629+
Result<Type>
630+
getUnderlyingTypeForOpaqueType(remote::RemoteAddress opaqueDescriptor,
631+
SubstitutionMap substitutions,
632+
unsigned ordinal) override {
633+
auto underlyingType = Reader
634+
.readUnderlyingTypeForOpaqueTypeDescriptor(opaqueDescriptor.getAddressData(),
635+
ordinal);
636+
637+
if (!underlyingType)
638+
return getFailure<Type>();
639+
640+
return underlyingType.subst(substitutions);
641+
}
625642
};
626643

627644
} // end anonymous namespace
@@ -692,3 +709,12 @@ RemoteASTContext::getDynamicTypeAndAddressForExistential(
692709
return asImpl(Impl)->getDynamicTypeAndAddressForExistential(address,
693710
staticType);
694711
}
712+
713+
Result<Type>
714+
RemoteASTContext::getUnderlyingTypeForOpaqueType(
715+
remote::RemoteAddress opaqueDescriptor,
716+
SubstitutionMap substitutions,
717+
unsigned ordinal) {
718+
return asImpl(Impl)->getUnderlyingTypeForOpaqueType(opaqueDescriptor,
719+
substitutions, ordinal);
720+
}

0 commit comments

Comments
 (0)