@@ -113,6 +113,7 @@ void swift::simple_display(llvm::raw_ostream &out,
113
113
{UnqualifiedLookupFlags::IncludeOuterResults, " IncludeOuterResults" },
114
114
{UnqualifiedLookupFlags::TypeLookup, " TypeLookup" },
115
115
{UnqualifiedLookupFlags::MacroLookup, " MacroLookup" },
116
+ {UnqualifiedLookupFlags::ModuleLookup, " ModuleLookup" },
116
117
};
117
118
118
119
auto flagsToPrint = llvm::make_filter_range (
@@ -1621,41 +1622,59 @@ static DeclName adjustLazyMacroExpansionNameKey(
1621
1622
return name;
1622
1623
}
1623
1624
1624
- SmallVector<MacroDecl *, 1 >
1625
- namelookup::lookupMacros (DeclContext *dc, DeclNameRef macroName,
1626
- MacroRoles roles) {
1625
+ SmallVector<MacroDecl *, 1 > namelookup::lookupMacros (DeclContext *dc,
1626
+ DeclNameRef moduleName,
1627
+ DeclNameRef macroName,
1628
+ MacroRoles roles) {
1627
1629
SmallVector<MacroDecl *, 1 > choices;
1628
1630
auto moduleScopeDC = dc->getModuleScopeContext ();
1629
1631
ASTContext &ctx = moduleScopeDC->getASTContext ();
1630
1632
1631
- // When performing lookup for freestanding macro roles, only consider
1632
- // macro names, ignoring types.
1633
- bool onlyMacros = static_cast <bool >(roles & getFreestandingMacroRoles ()) &&
1634
- !(roles - getFreestandingMacroRoles ());
1635
-
1636
- // Macro lookup should always exclude macro expansions; macro
1637
- // expansions cannot introduce new macro declarations. Note that
1638
- // the source location here doesn't matter.
1639
- UnqualifiedLookupDescriptor descriptor{
1640
- macroName, moduleScopeDC, SourceLoc (),
1641
- UnqualifiedLookupFlags::ExcludeMacroExpansions
1642
- };
1643
-
1644
- if (onlyMacros)
1645
- descriptor.Options |= UnqualifiedLookupFlags::MacroLookup;
1646
-
1647
- auto lookup = evaluateOrDefault (
1648
- ctx.evaluator , UnqualifiedLookupRequest{descriptor}, {});
1649
-
1650
- for (const auto &found : lookup.allResults ()) {
1651
- if (auto macro = dyn_cast<MacroDecl>(found.getValueDecl ())) {
1633
+ auto addChoiceIfApplicable = [&](ValueDecl *decl) {
1634
+ if (auto macro = dyn_cast<MacroDecl>(decl)) {
1652
1635
auto candidateRoles = macro->getMacroRoles ();
1653
1636
if ((candidateRoles && roles.contains (candidateRoles)) ||
1654
1637
// FIXME: `externalMacro` should have all roles.
1655
1638
macro->getBaseIdentifier ().str () == " externalMacro" ) {
1656
1639
choices.push_back (macro);
1657
1640
}
1658
1641
}
1642
+ };
1643
+
1644
+ // When a module is specified, it's a module-qualified lookup.
1645
+ if (moduleName) {
1646
+ UnqualifiedLookupDescriptor moduleLookupDesc (
1647
+ moduleName, moduleScopeDC, SourceLoc (),
1648
+ UnqualifiedLookupFlags::ModuleLookup);
1649
+ auto moduleLookup = evaluateOrDefault (
1650
+ ctx.evaluator , UnqualifiedLookupRequest{moduleLookupDesc}, {});
1651
+ auto foundTypeDecl = moduleLookup.getSingleTypeResult ();
1652
+ auto *moduleDecl = dyn_cast_or_null<ModuleDecl>(foundTypeDecl);
1653
+ if (!moduleDecl)
1654
+ return {};
1655
+
1656
+ ModuleQualifiedLookupRequest req{moduleScopeDC, moduleDecl, macroName,
1657
+ SourceLoc (),
1658
+ NL_ExcludeMacroExpansions | NL_OnlyMacros};
1659
+ auto lookup = evaluateOrDefault (ctx.evaluator , req, {});
1660
+ for (auto *found : lookup)
1661
+ addChoiceIfApplicable (found);
1662
+ }
1663
+ // Otherwise it's an unqualified lookup.
1664
+ else {
1665
+ // Macro lookup should always exclude macro expansions; macro
1666
+ // expansions cannot introduce new macro declarations. Note that
1667
+ // the source location here doesn't matter.
1668
+ UnqualifiedLookupDescriptor descriptor{
1669
+ macroName, moduleScopeDC, SourceLoc (),
1670
+ UnqualifiedLookupFlags::ExcludeMacroExpansions |
1671
+ UnqualifiedLookupFlags::MacroLookup};
1672
+
1673
+ auto lookup = evaluateOrDefault (ctx.evaluator ,
1674
+ UnqualifiedLookupRequest{descriptor}, {});
1675
+
1676
+ for (const auto &found : lookup.allResults ())
1677
+ addChoiceIfApplicable (found.getValueDecl ());
1659
1678
}
1660
1679
1661
1680
return choices;
@@ -1683,8 +1702,9 @@ namelookup::isInMacroArgument(SourceFile *sourceFile, SourceLoc loc) {
1683
1702
inMacroArgument = true ;
1684
1703
} else if (auto *attr = macro.getAttr ()) {
1685
1704
auto *moduleScope = sourceFile->getModuleScopeContext ();
1686
- auto results = lookupMacros (moduleScope, macro.getMacroName (),
1687
- getAttachedMacroRoles ());
1705
+ auto results =
1706
+ lookupMacros (moduleScope, macro.getModuleName (),
1707
+ macro.getMacroName (), getAttachedMacroRoles ());
1688
1708
inMacroArgument = !results.empty ();
1689
1709
}
1690
1710
@@ -1705,9 +1725,9 @@ void namelookup::forEachPotentialResolvedMacro(
1705
1725
) {
1706
1726
ASTContext &ctx = moduleScopeCtx->getASTContext ();
1707
1727
UnqualifiedLookupDescriptor lookupDesc{
1708
- macroName, moduleScopeCtx, SourceLoc (),
1709
- UnqualifiedLookupFlags::ExcludeMacroExpansions
1710
- };
1728
+ macroName, moduleScopeCtx, SourceLoc (),
1729
+ UnqualifiedLookupFlags::ExcludeMacroExpansions |
1730
+ UnqualifiedLookupFlags::MacroLookup };
1711
1731
1712
1732
auto lookup = evaluateOrDefault (
1713
1733
ctx.evaluator , UnqualifiedLookupRequest{lookupDesc}, {});
@@ -3568,13 +3588,13 @@ CustomAttrNominalRequest::evaluate(Evaluator &evaluator,
3568
3588
// Look for names at module scope, so we don't trigger name lookup for
3569
3589
// nested scopes. At this point, we're looking to see whether there are
3570
3590
// any suitable macros.
3571
- if ( auto *identTypeRepr =
3572
- dyn_cast_or_null<IdentTypeRepr>(attr-> getTypeRepr ())) {
3573
- auto macros = namelookup::lookupMacros (
3574
- dc, identTypeRepr-> getNameRef (), getAttachedMacroRoles ());
3575
- if (!macros. empty ())
3576
- return nullptr ;
3577
- }
3591
+ auto [ module , macro] = attr-> destructureMacroRef ();
3592
+ auto moduleName = ( module ) ? module -> getNameRef () : DeclNameRef ();
3593
+ auto macroName = (macro) ? macro-> getNameRef () : DeclNameRef ();
3594
+ auto macros = namelookup::lookupMacros ( dc, moduleName, macroName,
3595
+ getAttachedMacroRoles ());
3596
+ if (!macros. empty ())
3597
+ return nullptr ;
3578
3598
3579
3599
// Find the types referenced by the custom attribute.
3580
3600
auto &ctx = dc->getASTContext ();
0 commit comments