Skip to content

Commit a1b4514

Browse files
committed
Teach loadNamedMembers to import inherited constructors
1 parent ac75f31 commit a1b4514

File tree

7 files changed

+48
-22
lines changed

7 files changed

+48
-22
lines changed

lib/AST/NameLookup.cpp

Lines changed: 0 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1274,13 +1274,6 @@ TinyPtrVector<ValueDecl *> NominalTypeDecl::lookupDirect(
12741274
bool includeAttrImplements =
12751275
flags.contains(LookupDirectFlags::IncludeAttrImplements);
12761276

1277-
// FIXME: At present, lazy member is not able to find inherited constructors
1278-
// in imported classes, because SwiftDeclConverter::importInheritedConstructors()
1279-
// is only called via ClangImporter::Implementation::loadAllMembers().
1280-
if (hasClangNode() &&
1281-
name.getBaseName() == DeclBaseName::createConstructor())
1282-
useNamedLazyMemberLoading = false;
1283-
12841277
LLVM_DEBUG(llvm::dbgs() << getNameStr() << ".lookupDirect("
12851278
<< name << ")"
12861279
<< ", isLookupTablePopulated()=" << isLookupTablePopulated()

lib/ClangImporter/ClangImporter.cpp

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3822,6 +3822,16 @@ ClangImporter::Implementation::loadNamedMembers(
38223822
}
38233823
}
38243824
}
3825+
3826+
if (N == DeclBaseName::createConstructor()) {
3827+
if (auto *classDecl = dyn_cast<ClassDecl>(D)) {
3828+
SmallVector<Decl *, 4> ctors;
3829+
importInheritedConstructors(cast<clang::ObjCInterfaceDecl>(CD),
3830+
classDecl, ctors);
3831+
for (auto ctor : ctors)
3832+
Members.push_back(cast<ValueDecl>(ctor));
3833+
}
3834+
}
38253835
return Members;
38263836
}
38273837

lib/ClangImporter/ImportDecl.cpp

Lines changed: 11 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -4518,8 +4518,7 @@ namespace {
45184518
void importMirroredProtocolMembers(const clang::ObjCContainerDecl *decl,
45194519
DeclContext *dc,
45204520
ArrayRef<ProtocolDecl *> protocols,
4521-
SmallVectorImpl<Decl *> &members,
4522-
ASTContext &Ctx);
4521+
SmallVectorImpl<Decl *> &members);
45234522

45244523
void importNonOverriddenMirroredMethods(DeclContext *dc,
45254524
MutableArrayRef<MirroredMethodEntry> entries,
@@ -8672,6 +8671,15 @@ void ClangImporter::Implementation::insertMembersAndAlternates(
86728671
});
86738672
}
86748673

8674+
void ClangImporter::Implementation::importInheritedConstructors(
8675+
const clang::ObjCInterfaceDecl *curObjCClass,
8676+
const ClassDecl *classDecl, SmallVectorImpl<Decl *> &newMembers) {
8677+
if (curObjCClass->getName() != "Protocol") {
8678+
SwiftDeclConverter converter(*this, CurrentVersion);
8679+
converter.importInheritedConstructors(classDecl, newMembers);
8680+
}
8681+
}
8682+
86758683
void ClangImporter::Implementation::collectMembersToAdd(
86768684
const clang::ObjCContainerDecl *objcContainer, Decl *D, DeclContext *DC,
86778685
SmallVectorImpl<Decl *> &members) {
@@ -8686,15 +8694,8 @@ void ClangImporter::Implementation::collectMembersToAdd(
86868694

86878695
auto protos = getImportedProtocols(D);
86888696
if (auto clangClass = dyn_cast<clang::ObjCInterfaceDecl>(objcContainer)) {
8689-
auto swiftClass = cast<ClassDecl>(D);
86908697
objcContainer = clangClass = clangClass->getDefinition();
8691-
8692-
// Imported inherited initializers.
8693-
if (clangClass->getName() != "Protocol") {
8694-
converter.importInheritedConstructors(const_cast<ClassDecl *>(swiftClass),
8695-
members);
8696-
}
8697-
8698+
importInheritedConstructors(clangClass, cast<ClassDecl>(D), members);
86988699
} else if (auto clangProto
86998700
= dyn_cast<clang::ObjCProtocolDecl>(objcContainer)) {
87008701
objcContainer = clangProto->getDefinition();

lib/ClangImporter/ImporterImpl.h

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -812,6 +812,10 @@ class LLVM_LIBRARY_VISIBILITY ClangImporter::Implementation
812812
Decl *importMirroredDecl(const clang::NamedDecl *decl, DeclContext *dc,
813813
Version version, ProtocolDecl *proto);
814814

815+
void importInheritedConstructors(const clang::ObjCInterfaceDecl *curObjCClass,
816+
const ClassDecl *classDecl,
817+
SmallVectorImpl<Decl *> &newMembers);
818+
815819
/// Utility function for building simple generic signatures.
816820
GenericSignature buildGenericSignature(GenericParamList *genericParams,
817821
DeclContext *dc);

test/ClangImporter/attr-swift_name.swift

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
// RUN: %empty-directory(%t.mcp)
2-
// RUN: %target-swift-frontend(mock-sdk: %clang-importer-sdk) -I %S/Inputs/custom-modules -Xcc -w -typecheck %s -module-cache-path %t.mcp 2>&1 | %FileCheck %s
2+
// RUN: %target-swift-frontend(mock-sdk: %clang-importer-sdk) -I %S/Inputs/custom-modules -Xcc -w -typecheck %s -module-cache-path %t.mcp -disable-named-lazy-member-loading 2>&1 | %FileCheck %s
33

44
// REQUIRES: objc_interop
55

test/NameBinding/Inputs/NamedLazyMembers/NamedLazyMembers.h

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -26,6 +26,8 @@
2626
// Don't conform to the protocol; that loads all protocol members.
2727
@interface SimpleDoer
2828

29+
- (instancetype)initWithValue: (int)value;
30+
2931
// These are names we're hoping don't interfere with Doer, above.
3032
+ (SimpleDoer*)Doer;
3133
+ (SimpleDoer*)DoerOfNoWork;
@@ -107,4 +109,14 @@
107109
@interface SimpleDoerSubclass : SimpleDoer
108110
- (void)simplyDoSomeWorkWithSpeed:(int)s thoroughness:(int)t
109111
NS_SWIFT_NAME(simplyDoVeryImportantWork(speed:thoroughness:));
112+
113+
- (void)exuberantlyGoForWalk;
114+
- (void)exuberantlyTakeNap;
115+
- (void)exuberantlyEatMeal;
116+
- (void)exuberantlyTidyHome;
117+
- (void)exuberantlyCallFamily;
118+
- (void)exuberantlySingSong;
119+
- (void)exuberantlyReadBook;
120+
- (void)exuberantlyAttendLecture;
121+
- (void)exuberantlyWriteLetter;
110122
@end

test/NameBinding/named_lazy_member_loading_objc_interface.swift

Lines changed: 10 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -8,17 +8,23 @@
88
// Check that named-lazy-member-loading reduces the number of Decls deserialized
99
// RUN: %target-swift-frontend -typecheck -I %S/Inputs/NamedLazyMembers -disable-named-lazy-member-loading -stats-output-dir %t/stats-pre -primary-file %s %S/Inputs/NamedLazyMembers/NamedLazyMembersExt.swift
1010
// RUN: %target-swift-frontend -typecheck -I %S/Inputs/NamedLazyMembers -stats-output-dir %t/stats-post -primary-file %s %S/Inputs/NamedLazyMembers/NamedLazyMembersExt.swift
11-
// RUN: %{python} %utils/process-stats-dir.py --evaluate-delta 'NumTotalClangImportedEntities <= -1' %t/stats-pre %t/stats-post
11+
// RUN: %{python} %utils/process-stats-dir.py --evaluate-delta 'NumTotalClangImportedEntities <= -10' %t/stats-pre %t/stats-post
1212

1313
import NamedLazyMembers
1414

15-
public func bar(d: SimpleDoerSubclass) {
16-
let _ = d.simplyDoVeryImportantWork(speed: 10, motivation: 42)
15+
public func bar() {
16+
let d = SimpleDoerSubclass(value: 123)!
17+
let _ = d.simplyDoVeryImportantWork(speed: 10, motivation: 42)
1718
}
1819

19-
public func foo(d: SimpleDoer) {
20+
public func foo() {
21+
let d = SimpleDoer(value: 123)!
2022
let _ = d.simplyDoSomeWork()
2123
let _ = d.simplyDoSomeWork(withSpeed:10)
2224
let _ = d.simplyDoVeryImportantWork(speed:10, thoroughness:12)
2325
let _ = d.simplyDoSomeWorkWithSpeed(speed:10, levelOfAlacrity:12)
2426
}
27+
28+
// Make sure that simply subclassing an imported subclass doesn't page in all
29+
// members.
30+
class MostDoerSubclass : SimpleDoerSubclass {}

0 commit comments

Comments
 (0)