mirror of
https://github.com/apple/swift.git
synced 2025-12-21 12:14:44 +01:00
[Serialization] Drop extensions whose base type can't be deserialized. (#11323)
This shows up with swift_wrapper typedefs, which get imported into Swift as structs. If someone makes an extension of a swift_wrapper type, but the swift_wrapper is only applied in Swift 4 mode, that extension will break any Swift 3 clients. Recover by just dropping the extension entirely. There's still more complexity around extensions---what if a requirement can't be deserialized? what if something's depending on the protocol conformance provided by the extension?---but the missing base type case should be pretty safe. If you can't see the type at all, things that depend on its conformances are already in trouble. rdar://problem/33636733
This commit is contained in:
@@ -2482,9 +2482,17 @@ void Serializer::writeDecl(const Decl *D) {
|
||||
ConformanceLookupKind::All,
|
||||
nullptr, /*sorted=*/true);
|
||||
|
||||
SmallVector<TypeID, 8> inheritedTypes;
|
||||
SmallVector<TypeID, 8> inheritedAndDependencyTypes;
|
||||
for (auto inherited : extension->getInherited())
|
||||
inheritedTypes.push_back(addTypeRef(inherited.getType()));
|
||||
inheritedAndDependencyTypes.push_back(addTypeRef(inherited.getType()));
|
||||
size_t numInherited = inheritedAndDependencyTypes.size();
|
||||
|
||||
// FIXME: Figure out what to do with requirements and such, which the
|
||||
// extension also depends on. Right now just do what is safe to drop, which
|
||||
// is the base declaration.
|
||||
auto dependencies = collectDependenciesFromType(baseTy);
|
||||
for (auto dependencyTy : dependencies)
|
||||
inheritedAndDependencyTypes.push_back(addTypeRef(dependencyTy));
|
||||
|
||||
unsigned abbrCode = DeclTypeAbbrCodes[ExtensionLayout::Code];
|
||||
ExtensionLayout::emitRecord(Out, ScratchRecord, abbrCode,
|
||||
@@ -2494,7 +2502,8 @@ void Serializer::writeDecl(const Decl *D) {
|
||||
addGenericEnvironmentRef(
|
||||
extension->getGenericEnvironment()),
|
||||
conformances.size(),
|
||||
inheritedTypes);
|
||||
numInherited,
|
||||
inheritedAndDependencyTypes);
|
||||
|
||||
bool isClassExtension = false;
|
||||
if (baseNominal) {
|
||||
|
||||
Reference in New Issue
Block a user