Fix file finding on windows when path case changes.

This commit is contained in:
Jacob Dufault 2017-05-22 00:14:11 -07:00
parent 8d9374ee59
commit 1598129d8b
5 changed files with 19 additions and 7 deletions

View File

@ -178,7 +178,7 @@ void PushBack(NonElidedVector<lsLocation>* result, optional<lsLocation> location
}
QueryFile* FindFile(QueryDatabase* db, const std::string& filename, QueryFileId* file_id) {
auto it = db->usr_to_file.find(filename);
auto it = db->usr_to_file.find(LowerPathIfCaseInsensitive(filename));
if (it != db->usr_to_file.end()) {
optional<QueryFile>& file = db->files[it->second.id];
if (file) {
@ -193,8 +193,7 @@ QueryFile* FindFile(QueryDatabase* db, const std::string& filename, QueryFileId*
}
QueryFile* FindFile(QueryDatabase* db, const std::string& filename) {
// TODO: consider calling NormalizePath here. It might add too much latency though.
auto it = db->usr_to_file.find(filename);
auto it = db->usr_to_file.find(LowerPathIfCaseInsensitive(filename));
if (it != db->usr_to_file.end()) {
optional<QueryFile>& file = db->files[it->second.id];
if (file)

View File

@ -261,12 +261,12 @@ QueryFile::Def BuildFileDef(const IdMap& id_map, const IndexFile& indexed) {
QueryFileId GetQueryFileIdFromPath(QueryDatabase* query_db, const std::string& path) {
auto it = query_db->usr_to_file.find(path);
auto it = query_db->usr_to_file.find(LowerPathIfCaseInsensitive(path));
if (it != query_db->usr_to_file.end())
return QueryFileId(it->second.id);
size_t idx = query_db->files.size();
query_db->usr_to_file[path] = QueryFileId(idx);
query_db->usr_to_file[LowerPathIfCaseInsensitive(path)] = QueryFileId(idx);
query_db->files.push_back(QueryFile(path));
return QueryFileId(idx);
}
@ -625,7 +625,7 @@ void QueryDatabase::RemoveUsrs(SymbolKind usr_kind, const std::vector<Usr>& to_r
switch (usr_kind) {
case SymbolKind::File: {
for (const Usr& usr : to_remove)
files[usr_to_file[usr].id] = nullopt;
files[usr_to_file[LowerPathIfCaseInsensitive(usr)].id] = nullopt;
break;
}
case SymbolKind::Type: {
@ -691,7 +691,7 @@ void QueryDatabase::ImportOrUpdate(const std::vector<QueryFile::DefUpdate>& upda
// This function runs on the querydb thread.
for (auto& def : updates) {
auto it = usr_to_file.find(def.path);
auto it = usr_to_file.find(LowerPathIfCaseInsensitive(def.path));
assert(it != usr_to_file.end());
optional<QueryFile>& existing = files[it->second.id];

View File

@ -281,6 +281,8 @@ struct QueryDatabase {
std::vector<optional<QueryVar>> vars;
// Lookup symbol based on a usr.
// NOTE: For usr_to_file make sure to call LowerPathIfCaseInsensitive on key.
// TODO: add type wrapper to enforce we call it
spp::sparse_hash_map<Usr, QueryFileId> usr_to_file;
spp::sparse_hash_map<Usr, QueryTypeId> usr_to_type;
spp::sparse_hash_map<Usr, QueryFuncId> usr_to_func;

View File

@ -95,6 +95,15 @@ std::vector<std::string> SplitString(const std::string& str, const std::string&
return strings;
}
std::string LowerPathIfCaseInsensitive(const std::string& path) {
std::string result = path;
#if defined(_WIN32)
for (size_t i = 0; i < result.size(); ++i)
result[i] = (char)tolower(result[i]);
#endif
return result;
}
static void GetFilesInFolderHelper(
std::string folder, bool recursive, std::string output_prefix, const std::function<void(const std::string&)>& handler) {
tinydir_dir dir;

View File

@ -23,6 +23,8 @@ std::string ReplaceAll(const std::string& source, const std::string& from, const
std::vector<std::string> SplitString(const std::string& str, const std::string& delimiter);
std::string LowerPathIfCaseInsensitive(const std::string& path);
template <typename TValues>
std::string StringJoin(const TValues& values) {
std::string result;