@@ -432,52 +432,73 @@ ReferencesResult findReferences(ParsedAST &AST, Position Pos, uint32_t Limit,
432
432
elog (" Failed to get a path for the main file, so no references" );
433
433
return Results;
434
434
}
435
+ auto URIMainFile = URIForFile::canonicalize (*MainFilePath, *MainFilePath);
435
436
auto Loc = SM.getMacroArgExpandedLocation (
436
437
getBeginningOfIdentifier (Pos, SM, AST.getLangOpts ()));
437
- // TODO: should we handle macros, too?
438
- // We also show references to the targets of using-decls, so we include
439
- // DeclRelation::Underlying.
440
- DeclRelationSet Relations = DeclRelation::TemplatePattern |
441
- DeclRelation::Alias | DeclRelation::Underlying;
442
- auto Decls = getDeclAtPosition (AST, Loc, Relations);
443
-
444
- // We traverse the AST to find references in the main file.
445
- auto MainFileRefs = findRefs (Decls, AST);
446
- // We may get multiple refs with the same location and different Roles, as
447
- // cross-reference is only interested in locations, we deduplicate them
448
- // by the location to avoid emitting duplicated locations.
449
- MainFileRefs.erase (std::unique (MainFileRefs.begin (), MainFileRefs.end (),
450
- [](const ReferenceFinder::Reference &L,
451
- const ReferenceFinder::Reference &R) {
452
- return L.Loc == R.Loc ;
453
- }),
454
- MainFileRefs.end ());
455
- for (const auto &Ref : MainFileRefs) {
456
- if (auto Range = getTokenRange (SM, AST.getLangOpts (), Ref.Loc )) {
457
- Location Result;
458
- Result.range = *Range;
459
- Result.uri = URIForFile::canonicalize (*MainFilePath, *MainFilePath);
460
- Results.References .push_back (std::move (Result));
438
+ RefsRequest Req;
439
+
440
+ if (auto Macro = locateMacroAt (Loc, AST.getPreprocessor ())) {
441
+ // Handle references to macro.
442
+ if (auto MacroSID = getSymbolID (Macro->Name , Macro->Info , SM)) {
443
+ // Collect macro references from main file.
444
+ const auto &IDToRefs = AST.getMacros ().MacroRefs ;
445
+ auto Refs = IDToRefs.find (*MacroSID);
446
+ if (Refs != IDToRefs.end ()) {
447
+ for (const auto Ref : Refs->second ) {
448
+ Location Result;
449
+ Result.range = Ref;
450
+ Result.uri = URIMainFile;
451
+ Results.References .push_back (std::move (Result));
452
+ }
453
+ }
454
+ Req.IDs .insert (*MacroSID);
455
+ }
456
+ } else {
457
+ // Handle references to Decls.
458
+
459
+ // We also show references to the targets of using-decls, so we include
460
+ // DeclRelation::Underlying.
461
+ DeclRelationSet Relations = DeclRelation::TemplatePattern |
462
+ DeclRelation::Alias | DeclRelation::Underlying;
463
+ auto Decls = getDeclAtPosition (AST, Loc, Relations);
464
+
465
+ // We traverse the AST to find references in the main file.
466
+ auto MainFileRefs = findRefs (Decls, AST);
467
+ // We may get multiple refs with the same location and different Roles, as
468
+ // cross-reference is only interested in locations, we deduplicate them
469
+ // by the location to avoid emitting duplicated locations.
470
+ MainFileRefs.erase (std::unique (MainFileRefs.begin (), MainFileRefs.end (),
471
+ [](const ReferenceFinder::Reference &L,
472
+ const ReferenceFinder::Reference &R) {
473
+ return L.Loc == R.Loc ;
474
+ }),
475
+ MainFileRefs.end ());
476
+ for (const auto &Ref : MainFileRefs) {
477
+ if (auto Range = getTokenRange (SM, AST.getLangOpts (), Ref.Loc )) {
478
+ Location Result;
479
+ Result.range = *Range;
480
+ Result.uri = URIMainFile;
481
+ Results.References .push_back (std::move (Result));
482
+ }
483
+ }
484
+ if (Index && Results.References .size () <= Limit) {
485
+ for (const Decl *D : Decls) {
486
+ // Not all symbols can be referenced from outside (e.g.
487
+ // function-locals).
488
+ // TODO: we could skip TU-scoped symbols here (e.g. static functions) if
489
+ // we know this file isn't a header. The details might be tricky.
490
+ if (D->getParentFunctionOrMethod ())
491
+ continue ;
492
+ if (auto ID = getSymbolID (D))
493
+ Req.IDs .insert (*ID);
494
+ }
461
495
}
462
496
}
463
497
// Now query the index for references from other files.
464
- if (Index && Results.References .size () <= Limit) {
465
- RefsRequest Req;
498
+ if (!Req.IDs .empty () && Index && Results.References .size () <= Limit) {
466
499
Req.Limit = Limit;
467
-
468
- for (const Decl *D : Decls) {
469
- // Not all symbols can be referenced from outside (e.g. function-locals).
470
- // TODO: we could skip TU-scoped symbols here (e.g. static functions) if
471
- // we know this file isn't a header. The details might be tricky.
472
- if (D->getParentFunctionOrMethod ())
473
- continue ;
474
- if (auto ID = getSymbolID (D))
475
- Req.IDs .insert (*ID);
476
- }
477
- if (Req.IDs .empty ())
478
- return Results;
479
500
Results.HasMore |= Index->refs (Req, [&](const Ref &R) {
480
- // no need to continue process if we reach the limit.
501
+ // No need to continue process if we reach the limit.
481
502
if (Results.References .size () > Limit)
482
503
return ;
483
504
auto LSPLoc = toLSPLocation (R.Location , *MainFilePath);
0 commit comments