mirror of
https://github.com/MaskRay/ccls.git
synced 2024-11-22 15:45:08 +00:00
Do not remove querydb defined type/func/var if the final reference is removed from a file.
We still remove the defined type/func/var if it was defined in that file, though.
This commit is contained in:
parent
97832f2a73
commit
d47869ad0f
69
src/query.cc
69
src/query.cc
@ -21,8 +21,6 @@ namespace {
|
||||
optional<QueryType::DefUpdate> ToQuery(const IdMap& id_map, const IndexType::Def& type) {
|
||||
if (type.detailed_name.empty())
|
||||
return nullopt;
|
||||
if (!type.definition_extent)
|
||||
return nullopt;
|
||||
|
||||
QueryType::DefUpdate result(type.usr);
|
||||
result.short_name = type.short_name;
|
||||
@ -40,8 +38,6 @@ optional<QueryType::DefUpdate> ToQuery(const IdMap& id_map, const IndexType::Def
|
||||
optional<QueryFunc::DefUpdate> ToQuery(const IdMap& id_map, const IndexFunc::Def& func) {
|
||||
if (func.detailed_name.empty())
|
||||
return nullopt;
|
||||
if (!func.definition_extent)
|
||||
return nullopt;
|
||||
|
||||
QueryFunc::DefUpdate result(func.usr);
|
||||
result.short_name = func.short_name;
|
||||
@ -58,8 +54,6 @@ optional<QueryFunc::DefUpdate> ToQuery(const IdMap& id_map, const IndexFunc::Def
|
||||
optional<QueryVar::DefUpdate> ToQuery(const IdMap& id_map, const IndexVar::Def& var) {
|
||||
if (var.detailed_name.empty())
|
||||
return nullopt;
|
||||
if (!var.definition_extent)
|
||||
return nullopt;
|
||||
|
||||
QueryVar::DefUpdate result(var.usr);
|
||||
result.short_name = var.short_name;
|
||||
@ -463,10 +457,24 @@ IndexUpdate::IndexUpdate(const IdMap& previous_id_map, const IdMap& current_id_m
|
||||
// File
|
||||
files_def_update.push_back(BuildFileDef(current_id_map, current_file));
|
||||
|
||||
// **NOTE** We only remove entries if they were defined in the previous index.
|
||||
// For example, if a type is included from another file it will be defined
|
||||
// simply so we can attribute the usage/reference to it. If the reference goes
|
||||
// away we don't want to remove the type/func/var usage.
|
||||
|
||||
// Types
|
||||
CompareGroups<IndexType>(previous_file.types, current_file.types,
|
||||
/*onRemoved:*/[this](IndexType* def) {
|
||||
types_removed.push_back(def->def.usr);
|
||||
/*onRemoved:*/[this, &previous_id_map](IndexType* type) {
|
||||
if (type->def.definition_spelling)
|
||||
types_removed.push_back(type->def.usr);
|
||||
else {
|
||||
if (!type->derived.empty())
|
||||
types_derived.push_back(QueryType::DerivedUpdate(previous_id_map.ToQuery(type->id), {}, previous_id_map.ToQuery(type->derived)));
|
||||
if (!type->instances.empty())
|
||||
types_instances.push_back(QueryType::InstancesUpdate(previous_id_map.ToQuery(type->id), {}, previous_id_map.ToQuery(type->instances)));
|
||||
if (!type->uses.empty())
|
||||
types_uses.push_back(QueryType::UsesUpdate(previous_id_map.ToQuery(type->id), {}, previous_id_map.ToQuery(type->uses)));
|
||||
}
|
||||
},
|
||||
/*onAdded:*/[this, ¤t_id_map](IndexType* type) {
|
||||
optional<QueryType::DefUpdate> def_update = ToQuery(current_id_map, type->def);
|
||||
@ -492,8 +500,18 @@ IndexUpdate::IndexUpdate(const IdMap& previous_id_map, const IdMap& current_id_m
|
||||
|
||||
// Functions
|
||||
CompareGroups<IndexFunc>(previous_file.funcs, current_file.funcs,
|
||||
/*onRemoved:*/[this](IndexFunc* def) {
|
||||
funcs_removed.push_back(def->def.usr);
|
||||
/*onRemoved:*/[this, &previous_id_map](IndexFunc* func) {
|
||||
if (func->def.definition_spelling) {
|
||||
funcs_removed.push_back(func->def.usr);
|
||||
}
|
||||
else {
|
||||
if (!func->declarations.empty())
|
||||
funcs_declarations.push_back(QueryFunc::DeclarationsUpdate(previous_id_map.ToQuery(func->id), {}, previous_id_map.ToQuery(func->declarations)));
|
||||
if (!func->derived.empty())
|
||||
funcs_derived.push_back(QueryFunc::DerivedUpdate(previous_id_map.ToQuery(func->id), {}, previous_id_map.ToQuery(func->derived)));
|
||||
if (!func->callers.empty())
|
||||
funcs_callers.push_back(QueryFunc::CallersUpdate(previous_id_map.ToQuery(func->id), {}, previous_id_map.ToQuery(func->callers)));
|
||||
}
|
||||
},
|
||||
/*onAdded:*/[this, ¤t_id_map](IndexFunc* func) {
|
||||
optional<QueryFunc::DefUpdate> def_update = ToQuery(current_id_map, func->def);
|
||||
@ -519,8 +537,14 @@ IndexUpdate::IndexUpdate(const IdMap& previous_id_map, const IdMap& current_id_m
|
||||
|
||||
// Variables
|
||||
CompareGroups<IndexVar>(previous_file.vars, current_file.vars,
|
||||
/*onRemoved:*/[this](IndexVar* def) {
|
||||
vars_removed.push_back(def->def.usr);
|
||||
/*onRemoved:*/[this, &previous_id_map](IndexVar* var) {
|
||||
if (var->def.definition_spelling) {
|
||||
vars_removed.push_back(var->def.usr);
|
||||
}
|
||||
else {
|
||||
if (!var->uses.empty())
|
||||
vars_uses.push_back(QueryVar::UsesUpdate(previous_id_map.ToQuery(var->id), {}, previous_id_map.ToQuery(var->uses)));
|
||||
}
|
||||
},
|
||||
/*onAdded:*/[this, ¤t_id_map](IndexVar* var) {
|
||||
optional<QueryVar::DefUpdate> def_update = ToQuery(current_id_map, var->def);
|
||||
@ -799,9 +823,9 @@ TEST_CASE("remove defs") {
|
||||
IndexFile previous("foo.cc");
|
||||
IndexFile current("foo.cc");
|
||||
|
||||
previous.ToTypeId("usr1");
|
||||
previous.ToFuncId("usr2");
|
||||
previous.ToVarId("usr3");
|
||||
previous.Resolve(previous.ToTypeId("usr1"))->def.definition_spelling = Range(Position(1, 0));
|
||||
previous.Resolve(previous.ToFuncId("usr2"))->def.definition_spelling = Range(Position(2, 0));
|
||||
previous.Resolve(previous.ToVarId("usr3"))->def.definition_spelling = Range(Position(3, 0));
|
||||
|
||||
IndexUpdate update = GetDelta(previous, current);
|
||||
|
||||
@ -810,6 +834,21 @@ TEST_CASE("remove defs") {
|
||||
REQUIRE(update.vars_removed == std::vector<Usr>{ "usr3" });
|
||||
}
|
||||
|
||||
TEST_CASE("do not remove ref-only defs") {
|
||||
IndexFile previous("foo.cc");
|
||||
IndexFile current("foo.cc");
|
||||
|
||||
previous.Resolve(previous.ToTypeId("usr1"))->uses.push_back(Range(Position(1, 0)));
|
||||
previous.Resolve(previous.ToFuncId("usr2"))->callers.push_back(IndexFuncRef(IndexFuncId(0), Range(Position(2, 0)), false /*is_implicit*/));
|
||||
previous.Resolve(previous.ToVarId("usr3"))->uses.push_back(Range(Position(3, 0)));
|
||||
|
||||
IndexUpdate update = GetDelta(previous, current);
|
||||
|
||||
REQUIRE(update.types_removed == std::vector<Usr>{});
|
||||
REQUIRE(update.funcs_removed == std::vector<Usr>{});
|
||||
REQUIRE(update.vars_removed == std::vector<Usr>{});
|
||||
}
|
||||
|
||||
TEST_CASE("func callers") {
|
||||
IndexFile previous("foo.cc");
|
||||
IndexFile current("foo.cc");
|
||||
|
Loading…
Reference in New Issue
Block a user