Skip to content

Commit c95c179

Browse files
committed
Reflection: Record superclass as its own field instead of an associated type of AnyObject
The "superclass as associated type" modeling was put in to maintain backward compatibility. We just bumped the version number because of new mangling so we may as well fix this sillyness too.
1 parent 23fbdb5 commit c95c179

File tree

3 files changed

+30
-67
lines changed

3 files changed

+30
-67
lines changed

include/swift/Reflection/Records.h

Lines changed: 10 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -19,7 +19,7 @@
1919

2020
#include "swift/Basic/RelativePointer.h"
2121

22-
const uint16_t SWIFT_REFLECTION_METADATA_VERSION = 2; // use new mangling
22+
const uint16_t SWIFT_REFLECTION_METADATA_VERSION = 3; // superclass field
2323

2424
namespace swift {
2525
namespace reflection {
@@ -145,6 +145,7 @@ class FieldDescriptor {
145145
}
146146

147147
const RelativeDirectPointer<const char> MangledTypeName;
148+
const RelativeDirectPointer<const char> Superclass;
148149

149150
public:
150151
FieldDescriptor() = delete;
@@ -190,6 +191,14 @@ class FieldDescriptor {
190191
std::string getMangledTypeName() const {
191192
return MangledTypeName.get();
192193
}
194+
195+
bool hasSuperclass() const {
196+
return Superclass;
197+
}
198+
199+
std::string getSuperclass() const {
200+
return Superclass.get();
201+
}
193202
};
194203

195204
class FieldDescriptorIterator

lib/IRGen/GenReflection.cpp

Lines changed: 12 additions & 56 deletions
Original file line numberDiff line numberDiff line change
@@ -321,43 +321,6 @@ class AssociatedTypeMetadataBuilder : public ReflectionMetadataBuilder {
321321
}
322322
};
323323

324-
class SuperclassMetadataBuilder : public ReflectionMetadataBuilder {
325-
static const uint32_t AssociatedTypeRecordSize = 8;
326-
327-
const ClassDecl *Class;
328-
CanType Superclass;
329-
330-
void layout() override {
331-
PrettyStackTraceDecl DebugStack("emitting superclass metadata",
332-
Class);
333-
334-
auto *M = IGM.getSILModule().getSwiftModule();
335-
336-
addTypeRef(M, Class->getDeclaredType()->getCanonicalType());
337-
addTypeRef(M, IGM.Context.getAnyObjectType());
338-
339-
B.addInt32(1);
340-
B.addInt32(AssociatedTypeRecordSize);
341-
342-
auto NameGlobal = IGM.getAddrOfStringForTypeRef("super");
343-
B.addRelativeAddress(NameGlobal);
344-
addTypeRef(M, Superclass);
345-
}
346-
347-
public:
348-
SuperclassMetadataBuilder(IRGenModule &IGM,
349-
const ClassDecl *Class,
350-
CanType Superclass)
351-
: ReflectionMetadataBuilder(IGM), Class(Class),
352-
Superclass(Superclass) {}
353-
354-
llvm::GlobalVariable *emit() {
355-
auto entity = LinkEntity::forReflectionSuperclassDescriptor(Class);
356-
auto section = IGM.getAssociatedTypeMetadataSectionName();
357-
return ReflectionMetadataBuilder::emit(entity, section);
358-
}
359-
};
360-
361324
class FieldTypeMetadataBuilder : public ReflectionMetadataBuilder {
362325
const uint32_t fieldRecordSize = 12;
363326
const NominalTypeDecl *NTD;
@@ -465,15 +428,23 @@ class FieldTypeMetadataBuilder : public ReflectionMetadataBuilder {
465428
}
466429

467430
void layout() override {
468-
PrettyStackTraceDecl DebugStack("emitting field type metadata", NTD);
469-
auto type = NTD->getDeclaredType()->getCanonicalType();
470-
addTypeRef(NTD->getModuleContext(), type);
471-
472431
if (NTD->hasClangNode() &&
473432
!isa<ClassDecl>(NTD) &&
474433
!isa<ProtocolDecl>(NTD))
475434
return;
476435

436+
PrettyStackTraceDecl DebugStack("emitting field type metadata", NTD);
437+
auto type = NTD->getDeclaredType()->getCanonicalType();
438+
addTypeRef(NTD->getModuleContext(), type);
439+
440+
auto *CD = dyn_cast<ClassDecl>(NTD);
441+
if (CD && CD->getSuperclass()) {
442+
addTypeRef(NTD->getModuleContext(),
443+
CD->getSuperclass()->getCanonicalType());
444+
} else {
445+
B.addInt32(0);
446+
}
447+
477448
switch (NTD->getKind()) {
478449
case DeclKind::Class:
479450
case DeclKind::Struct:
@@ -992,21 +963,6 @@ void IRGenModule::emitFieldMetadataRecord(const NominalTypeDecl *Decl) {
992963

993964
FieldTypeMetadataBuilder builder(*this, Decl);
994965
builder.emit();
995-
996-
// So that -parse-stdlib tests don't need to define an AnyObject
997-
// protocol (which will go away one day anyway).
998-
if (!Context.getProtocol(KnownProtocolKind::AnyObject))
999-
return;
1000-
1001-
// If this is a class declaration with a superclass, record the
1002-
// superclass as a special associated type named 'super' on the
1003-
// 'AnyObject' protocol.
1004-
if (auto Superclass = Decl->getDeclaredInterfaceType()
1005-
->getSuperclass()) {
1006-
SuperclassMetadataBuilder builder(*this, cast<ClassDecl>(Decl),
1007-
Superclass->getCanonicalType());
1008-
builder.emit();
1009-
}
1010966
}
1011967

1012968
void IRGenModule::emitReflectionMetadataVersion() {

stdlib/public/Reflection/TypeRefBuilder.cpp

Lines changed: 8 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -82,19 +82,17 @@ lookupSuperclass(const std::string &MangledTypeName) {
8282

8383
const TypeRef * TypeRefBuilder::
8484
lookupSuperclass(const TypeRef *TR) {
85-
const TypeRef *Superclass = nullptr;
86-
87-
if (auto *Nominal = dyn_cast<NominalTypeRef>(TR)) {
88-
Superclass = lookupSuperclass(Nominal->getMangledName());
89-
} else {
90-
auto BG = cast<BoundGenericTypeRef>(TR);
91-
Superclass = lookupSuperclass(BG->getMangledName());
92-
}
85+
auto *FD = getFieldTypeInfo(TR);
86+
if (FD == nullptr)
87+
return nullptr;
9388

94-
if (Superclass == nullptr)
89+
Demangle::Demangler Dem;
90+
auto Demangled = Dem.demangleType(FD->getSuperclass());
91+
auto Unsubstituted = swift::remote::decodeMangledType(*this, Demangled);
92+
if (!Unsubstituted)
9593
return nullptr;
9694

97-
return Superclass->subst(*this, TR->getSubstMap());
95+
return Unsubstituted->subst(*this, TR->getSubstMap());
9896
}
9997

10098
const FieldDescriptor *

0 commit comments

Comments
 (0)