Skip to content

IRGen: Take enable-testing into account when computing whether a class has resilient metadata #41044

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
12 changes: 11 additions & 1 deletion lib/IRGen/ClassMetadataVisitor.h
Original file line number Diff line number Diff line change
Expand Up @@ -116,7 +116,17 @@ template <class Impl> class ClassMetadataVisitor
if (superclassDecl->hasClangNode()) {
// Nothing to do; Objective-C classes do not add new members to
// Swift class metadata.
} else if (IGM.hasResilientMetadata(superclassDecl, ResilienceExpansion::Maximal)) {

// Super class metadata is resilient if
// the superclass is resilient when viewed from the currrent module.
// But not if the current class is defined in an external module and
// not publically accessible (e.g private or internal). This would
// normally not happen except if we compile theClass's module with
// enable-testing.
} else if (IGM.hasResilientMetadata(superclassDecl, ResilienceExpansion::Maximal) &&
(theClass->getModuleContext() == IGM.getSwiftModule() ||
theClass->getFormalAccessScope(/*useDC=*/nullptr,
/*treatUsableFromInlineAsPublic=*/true).isPublic())) {
// Runtime metadata instantiation will initialize our field offset
// vector and vtable entries.
//
Expand Down
7 changes: 7 additions & 0 deletions test/IRGen/Inputs/resilient-class.swift
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
open class Base {
var x = 1
}

internal class SubClass : Base {
var y = 2
}
20 changes: 20 additions & 0 deletions test/IRGen/testing-enabled-resilient-super-class.swift
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
// RUN: %empty-directory(%t)
// RUN: %target-swift-frontend -enable-testing -enable-library-evolution -module-name=resilient %S/Inputs/resilient-class.swift -emit-module -emit-module-path %t/resilient.swiftmodule
// RUN: %target-swift-frontend -I %t -emit-ir %s | %FileCheck %s

// Check that linking succeeds.
// RUN: %empty-directory(%t)
// RUN: %target-build-swift-dylib(%t/%target-library-name(resilient)) %S/Inputs/resilient-class.swift -module-name resilient -emit-module -emit-module-path %t/resilient.swiftmodule -enable-library-evolution -enable-testing
// RUN: %target-build-swift -I %t -L %t -lresilient %s -o %t/main %target-rpath(%t)
// RUN: %target-build-swift -O -I %t -L %t -lresilient %s -o %t/main %target-rpath(%t)

@testable import resilient

// Don't access via the class offset global. Use a fragile access pattern instead.

// CHECK-NOT: s9resilient8SubClassCMo

public func testCase() {
let t = SubClass()
print(t.y)
}