Summary:
Pros:
o Loading macros from preamble for every completion is slow (see profile).
o Calculating macro USR is also slow (see profile).
o Sema can provide a lot of macro completion results (e.g. when filter is empty,
60k for some large TUs!).
Cons:
o Slight memory increase in dynamic index (~1%).
o Some extra work during preamble build (should be fine as preamble build and
indexAST is way slower).
Before:
{
F7195645}
After:
{
F7195646}
Reviewers: ilya-biryukov, sammccall
Reviewed By: sammccall
Subscribers: MaskRay, jkorous, arphaman, kadircet, cfe-commits
Differential Revision: https://reviews.llvm.org/D52078
llvm-svn: 342529
#include "index/Index.h"
#include "index/Merge.h"
#include "clang/Index/IndexingAction.h"
+#include "clang/Lex/MacroInfo.h"
#include "clang/Lex/Preprocessor.h"
#include <memory>
IndexOpts.SystemSymbolFilter =
index::IndexingOptions::SystemSymbolFilterKind::DeclarationsOnly;
IndexOpts.IndexFunctionLocals = false;
-
- if (IsIndexMainAST)
+ if (IsIndexMainAST) {
// We only collect refs when indexing main AST.
CollectorOpts.RefFilter = RefKind::All;
+ }else {
+ IndexOpts.IndexMacrosInPreprocessor = true;
+ CollectorOpts.CollectMacro = true;
+ }
SymbolCollector Collector(std::move(CollectorOpts));
Collector.setPreprocessor(PP);
void TestAfterDotCompletion(clangd::CodeCompleteOptions Opts) {
auto Results = completions(
R"cpp(
- #define MACRO X
-
int global_var;
int global_func();
+ // Make sure this is not in preamble.
+ #define MACRO X
+
struct GlobalClass {};
struct ClassWithMembers {
void TestGlobalScopeCompletion(clangd::CodeCompleteOptions Opts) {
auto Results = completions(
R"cpp(
- #define MACRO X
-
int global_var;
int global_func();
+ // Make sure this is not in preamble.
+ #define MACRO X
+
struct GlobalClass {};
struct ClassWithMembers {
TEST(CompletionTest, Kinds) {
auto Results = completions(
R"cpp(
- #define MACRO X
int variable;
struct Struct {};
int function();
+ // make sure MACRO is not included in preamble.
+ #define MACRO 10
int X = ^
)cpp",
{func("indexFunction"), var("indexVariable"), cls("indexClass")});
UnorderedElementsAre(Named("Clangd_Macro_Test")));
}
+TEST(CompletionTest, NoMacroFromPreambleIfIndexIsSet) {
+ auto Results = completions(
+ R"cpp(#define CLANGD_PREAMBLE x
+
+ int x = 0;
+ #define CLANGD_MAIN x
+ void f() { CLANGD_^ }
+ )cpp",
+ {func("CLANGD_INDEX")});
+ // Index is overriden in code completion options, so the preamble symbol is
+ // not seen.
+ EXPECT_THAT(Results.Completions, UnorderedElementsAre(Named("CLANGD_MAIN"),
+ Named("CLANGD_INDEX")));
+}
+
TEST(CompletionTest, DeprecatedResults) {
std::string Body = R"cpp(
void TestClangd();
#include "index/FileIndex.h"
#include "clang/Frontend/CompilerInvocation.h"
#include "clang/Frontend/PCHContainerOperations.h"
+#include "clang/Index/IndexSymbol.h"
#include "clang/Lex/Preprocessor.h"
#include "clang/Tooling/CompilationDatabase.h"
#include "gtest/gtest.h"
FileURI("unittest:///test2.cc"))}));
}
+TEST(FileIndexTest, CollectMacros) {
+ FileIndex M;
+ update(M, "f", "#define CLANGD 1");
+
+ FuzzyFindRequest Req;
+ Req.Query = "";
+ bool SeenSymbol = false;
+ M.index().fuzzyFind(Req, [&](const Symbol &Sym) {
+ EXPECT_EQ(Sym.Name, "CLANGD");
+ EXPECT_EQ(Sym.SymInfo.Kind, index::SymbolKind::Macro);
+ SeenSymbol = true;
+ });
+ EXPECT_TRUE(SeenSymbol);
+}
+
} // namespace
} // namespace clangd
} // namespace clang