matcher.cc: use std::regex_search instead of std::regex_match

Prototype of non-working `dependencies` parameter of $cquery/freshenIndex
This commit is contained in:
Fangrui Song 2018-01-27 09:29:28 -08:00
parent e3d3a492d0
commit d605217c1a
4 changed files with 54 additions and 15 deletions

View File

@ -41,7 +41,7 @@ optional<Matcher> Matcher::Create(const std::string& search) {
bool Matcher::IsMatch(const std::string& value) const { bool Matcher::IsMatch(const std::string& value) const {
// std::smatch match; // std::smatch match;
// return std::regex_match(value, match, regex); // return std::regex_match(value, match, regex);
return std::regex_match(value, regex, std::regex_constants::match_any); return std::regex_search(value, regex, std::regex_constants::match_any);
} }
GroupMatch::GroupMatch(const std::vector<std::string>& whitelist, GroupMatch::GroupMatch(const std::vector<std::string>& whitelist,

View File

@ -8,14 +8,21 @@
#include "working_files.h" #include "working_files.h"
#include <loguru.hpp> #include <loguru.hpp>
#include <queue>
#include <unordered_set>
namespace { namespace {
struct Ipc_CqueryFreshenIndex : public RequestMessage<Ipc_CqueryFreshenIndex> { struct Ipc_CqueryFreshenIndex : public NotificationMessage<Ipc_CqueryFreshenIndex> {
const static IpcId kIpcId = IpcId::CqueryFreshenIndex; const static IpcId kIpcId = IpcId::CqueryFreshenIndex;
std::vector<std::string> whitelist; struct Params {
std::vector<std::string> blacklist; bool dependencies = true;
std::vector<std::string> whitelist;
std::vector<std::string> blacklist;
};
Params params;
}; };
MAKE_REFLECT_STRUCT(Ipc_CqueryFreshenIndex, id, whitelist, blacklist); MAKE_REFLECT_STRUCT(Ipc_CqueryFreshenIndex::Params, dependencies, whitelist, blacklist);
MAKE_REFLECT_STRUCT(Ipc_CqueryFreshenIndex, params);
REGISTER_IPC_MESSAGE(Ipc_CqueryFreshenIndex); REGISTER_IPC_MESSAGE(Ipc_CqueryFreshenIndex);
struct CqueryFreshenIndexHandler : BaseMessageHandler<Ipc_CqueryFreshenIndex> { struct CqueryFreshenIndexHandler : BaseMessageHandler<Ipc_CqueryFreshenIndex> {
@ -23,24 +30,52 @@ struct CqueryFreshenIndexHandler : BaseMessageHandler<Ipc_CqueryFreshenIndex> {
LOG_S(INFO) << "Freshening " << project->entries.size() << " files"; LOG_S(INFO) << "Freshening " << project->entries.size() << " files";
// TODO: think about this flow and test it more. // TODO: think about this flow and test it more.
GroupMatch matcher(request->whitelist, request->blacklist); GroupMatch matcher(request->params.whitelist, request->params.blacklist);
// Unmark all files whose timestamp has changed. // Unmark all files whose timestamp has changed.
std::unique_ptr<ICacheManager> cache_manager = ICacheManager::Make(config); std::unique_ptr<ICacheManager> cache_manager = ICacheManager::Make(config);
for (const auto& file : db->files) {
if (!file.def || !matcher.IsMatch(file.def->path)) std::queue<const QueryFile*> q;
continue; // |need_index| stores every filename ever enqueued.
std::unordered_set<std::string> need_index;
// Reverse dependency graph.
std::unordered_map<std::string, std::vector<std::string>> graph;
// filename -> QueryFile mapping for files haven't enqueued.
std::unordered_map<std::string, const QueryFile*> path_to_file;
for (const auto& file : db->files)
if (file.def) {
if (matcher.IsMatch(file.def->path))
q.push(&file);
else
path_to_file[file.def->path] = &file;
for (const std::string& dependency : file.def->dependencies)
graph[dependency].push_back(file.def->path);
}
while (!q.empty()) {
const QueryFile* file = q.front();
q.pop();
need_index.insert(file->def->path);
optional<int64_t> modification_timestamp = optional<int64_t> modification_timestamp =
GetLastModificationTime(file.def->path); GetLastModificationTime(file->def->path);
if (!modification_timestamp) if (!modification_timestamp)
continue; continue;
optional<int64_t> cached_modification = optional<int64_t> cached_modification =
timestamp_manager->GetLastCachedModificationTime(cache_manager.get(), timestamp_manager->GetLastCachedModificationTime(cache_manager.get(),
file.def->path); file->def->path);
if (modification_timestamp != cached_modification) if (modification_timestamp != cached_modification)
file_consumer_shared->Reset(file.def->path); file_consumer_shared->Reset(file->def->path);
if (request->params.dependencies)
for (const std::string& path : graph[file->def->path]) {
auto it = path_to_file.find(path);
if (it != path_to_file.end()) {
q.push(it->second);
path_to_file.erase(it);
}
}
} }
auto* queue = QueueManager::instance(); auto* queue = QueueManager::instance();
@ -48,7 +83,7 @@ struct CqueryFreshenIndexHandler : BaseMessageHandler<Ipc_CqueryFreshenIndex> {
// Send index requests for every file. // Send index requests for every file.
project->ForAllFilteredFiles( project->ForAllFilteredFiles(
config, [&](int i, const Project::Entry& entry) { config, [&](int i, const Project::Entry& entry) {
if (!matcher.IsMatch(entry.filename)) if (!need_index.count(entry.filename))
return; return;
optional<std::string> content = ReadContent(entry.filename); optional<std::string> content = ReadContent(entry.filename);
if (!content) { if (!content) {

View File

@ -201,6 +201,7 @@ QueryFile::Def BuildFileDef(const IdMap& id_map, const IndexFile& indexed) {
def.path = indexed.path; def.path = indexed.path;
def.includes = indexed.includes; def.includes = indexed.includes;
def.inactive_regions = indexed.skipped_by_preprocessor; def.inactive_regions = indexed.skipped_by_preprocessor;
def.dependencies = indexed.dependencies;
// Convert enum to markdown compatible strings // Convert enum to markdown compatible strings
def.language = [indexed]() { def.language = [indexed]() {

View File

@ -192,6 +192,8 @@ struct QueryFile {
std::vector<SymbolRef> all_symbols; std::vector<SymbolRef> all_symbols;
// Parts of the file which are disabled. // Parts of the file which are disabled.
std::vector<Range> inactive_regions; std::vector<Range> inactive_regions;
// Used by |$cquery/freshenIndex|.
std::vector<std::string> dependencies;
}; };
using DefUpdate = Def; using DefUpdate = Def;
@ -209,7 +211,8 @@ MAKE_REFLECT_STRUCT(QueryFile::Def,
language, language,
outline, outline,
all_symbols, all_symbols,
inactive_regions); inactive_regions,
dependencies);
struct QueryType { struct QueryType {
using Def = TypeDefDefinitionData<QueryTypeId, using Def = TypeDefDefinitionData<QueryTypeId,