Skip to content

Commit 467f8f5

Browse files
committed
[Macros] Ensure that we can find peer macros for members of extensions.
When populating the name lookup tables for a nominal type, we were only visiting declarations with peer macros within the nominal type declaration itself. Also visit the members of extensions of the nominal type. Without this change, peer-macro-defined members of extensions are not visible.
1 parent 11a4ff5 commit 467f8f5

File tree

4 files changed

+42
-9
lines changed

4 files changed

+42
-9
lines changed

include/swift/AST/TypeOrExtensionDecl.h

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -23,6 +23,9 @@
2323

2424
namespace swift {
2525

26+
class DeclContext;
27+
class IterableDeclContext;
28+
2629
/// Describes either a nominal type declaration or an extension
2730
/// declaration.
2831
struct TypeOrExtensionDecl {
@@ -38,6 +41,8 @@ struct TypeOrExtensionDecl {
3841
class Decl *getAsDecl() const;
3942
/// Return the contained *Decl as the DeclContext superclass.
4043
DeclContext *getAsDeclContext() const;
44+
/// Return the contained *Decl as the DeclContext superclass.
45+
IterableDeclContext *getAsIterableDeclContext() const;
4146
/// Return the contained NominalTypeDecl or that of the extended type
4247
/// in the ExtensionDecl.
4348
NominalTypeDecl *getBaseNominal() const;

lib/AST/Decl.cpp

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -9891,6 +9891,14 @@ Decl *TypeOrExtensionDecl::getAsDecl() const {
98919891
DeclContext *TypeOrExtensionDecl::getAsDeclContext() const {
98929892
return getAsDecl()->getInnermostDeclContext();
98939893
}
9894+
9895+
IterableDeclContext *TypeOrExtensionDecl::getAsIterableDeclContext() const {
9896+
if (auto nominal = Decl.dyn_cast<NominalTypeDecl *>())
9897+
return nominal;
9898+
9899+
return Decl.get<ExtensionDecl *>();
9900+
}
9901+
98949902
NominalTypeDecl *TypeOrExtensionDecl::getBaseNominal() const {
98959903
return getAsDeclContext()->getSelfNominalTypeDecl();
98969904
}

lib/AST/NameLookup.cpp

Lines changed: 9 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1538,10 +1538,12 @@ static void
15381538
populateLookupTableEntryFromMacroExpansions(ASTContext &ctx,
15391539
MemberLookupTable &table,
15401540
DeclName name,
1541-
NominalTypeDecl *dc) {
1541+
TypeOrExtensionDecl container) {
1542+
auto dc = container.getAsDeclContext();
15421543
auto *moduleScopeCtx = dc->getModuleScopeContext();
1543-
auto *module = dc->getModuleContext();
1544-
for (auto *member : dc->getCurrentMembersWithoutLoading()) {
1544+
auto *module = dc->getParentModule();
1545+
auto idc = container.getAsIterableDeclContext();
1546+
for (auto *member : idc->getCurrentMembersWithoutLoading()) {
15451547
// Collect all macro introduced names, along with its corresponding macro
15461548
// reference. We need the macro reference to prevent adding auxiliary decls
15471549
// that weren't introduced by the macro.
@@ -1773,6 +1775,10 @@ DirectLookupRequest::evaluate(Evaluator &evaluator,
17731775
if (!Table.isLazilyCompleteForMacroExpansion(macroExpansionKey)) {
17741776
populateLookupTableEntryFromMacroExpansions(
17751777
ctx, Table, macroExpansionKey, decl);
1778+
for (auto ext : decl->getExtensions()) {
1779+
populateLookupTableEntryFromMacroExpansions(
1780+
ctx, Table, macroExpansionKey, ext);
1781+
}
17761782
Table.markLazilyCompleteForMacroExpansion(macroExpansionKey);
17771783
}
17781784

test/Macros/macro_expand_peers.swift

Lines changed: 20 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -36,12 +36,26 @@ struct S {
3636
}
3737
}
3838

39-
// CHECK-DUMP: @__swiftmacro_18macro_expand_peers1f1a3for_SSSi_SSSdtYaF20addCompletionHandlerfMp_.swift
40-
// CHECK-DUMP: func f(a: Int, for b: String, _ value: Double, completionHandler: @escaping (String) -> Void) {
41-
// CHECK-DUMP: Task {
42-
// CHECK-DUMP: completionHandler(await f(a: a, for: b, value))
43-
// CHECK-DUMP: }
44-
// CHECK-DUMP: }
39+
extension S {
40+
@addCompletionHandler
41+
func g(a: Int, for b: String, _ value: Double) async -> String {
42+
return b
43+
}
44+
45+
// CHECK-DUMP: @__swiftmacro_18macro_expand_peers1SV1g1a3for_SSSi_SSSdtYaF20addCompletionHandlerfMp_.swift
46+
// CHECK-DUMP: func f(a: Int, for b: String, _ value: Double, completionHandler: @escaping (String) -> Void) {
47+
// CHECK-DUMP: Task {
48+
// CHECK-DUMP: completionHandler(await f(a: a, for: b, value))
49+
// CHECK-DUMP: }
50+
// CHECK-DUMP: }
51+
52+
}
53+
54+
func useCompletionHandlerG(s: S, _ body: @escaping (String) -> Void) {
55+
s.g(a: 1, for: "hahaha local", 2.0) {
56+
body($0)
57+
}
58+
}
4559

4660
@addCompletionHandler
4761
func f(a: Int, for b: String, _ value: Double) async -> String {

0 commit comments

Comments
 (0)