[vcpkg] Remove calls to where.exe to improve startup performance

This commit is contained in:
Robert Schumacher 2018-06-27 16:29:16 -07:00
parent 0ad79a67c7
commit 3314845a92
3 changed files with 54 additions and 30 deletions

View File

@ -57,13 +57,9 @@ namespace vcpkg::Files
std::error_code& ec) = 0;
virtual fs::file_status status(const fs::path& path, std::error_code& ec) const = 0;
inline void write_contents(const fs::path& file_path, const std::string& data)
{
std::error_code ec;
write_contents(file_path, data, ec);
Checks::check_exit(
VCPKG_LINE_INFO, !ec, "error while writing file: %s: %s", file_path.u8string(), ec.message());
}
virtual std::vector<fs::path> find_from_PATH(const std::string& name) const = 0;
void write_contents(const fs::path& file_path, const std::string& data);
};
Filesystem& get_real_filesystem();
@ -73,6 +69,4 @@ namespace vcpkg::Files
bool has_invalid_chars_for_filesystem(const std::string& s);
void print_paths(const std::vector<fs::path>& paths);
std::vector<fs::path> find_from_PATH(const std::string& name);
}

View File

@ -16,6 +16,14 @@ namespace vcpkg::Files
{
static const std::regex FILESYSTEM_INVALID_CHARACTERS_REGEX = std::regex(R"([\/:*?"<>|])");
void Filesystem::write_contents(const fs::path& file_path, const std::string& data)
{
std::error_code ec;
write_contents(file_path, data, ec);
Checks::check_exit(
VCPKG_LINE_INFO, !ec, "error while writing file: %s: %s", file_path.u8string(), ec.message());
}
struct RealFilesystem final : Filesystem
{
virtual Expected<std::string> read_contents(const fs::path& file_path) const override
@ -241,6 +249,40 @@ namespace vcpkg::Files
}
}
}
virtual std::vector<fs::path> find_from_PATH(const std::string& name) const override
{
#if defined(_WIN32)
static constexpr StringLiteral EXTS[] = {".cmd", ".exe", ".bat"};
auto paths = Strings::split(System::get_environment_variable("PATH").value_or_exit(VCPKG_LINE_INFO), ";");
std::vector<fs::path> ret;
for (auto&& path : paths)
{
auto base = path + "/" + name;
for (auto&& ext : EXTS)
{
auto p = fs::u8path(base + ext.c_str());
if (Util::find(ret, p) != ret.end() && this->exists(p))
{
ret.push_back(p);
Debug::println("Found path: %s", p.u8string());
}
}
}
return ret;
#else
const std::string cmd = Strings::format("which %s", name);
auto out = System::cmd_execute_and_capture_output(cmd);
if (out.exit_code != 0)
{
return {};
}
return Util::fmap(Strings::split(out.output, "\n"), [](auto&& s) { return fs::path(s); });
#endif
}
};
Filesystem& get_real_filesystem()
@ -263,20 +305,4 @@ namespace vcpkg::Files
}
System::println();
}
std::vector<fs::path> find_from_PATH(const std::string& name)
{
#if defined(_WIN32)
const std::string cmd = Strings::format("where.exe %s", name);
#else
const std::string cmd = Strings::format("which %s", name);
#endif
auto out = System::cmd_execute_and_capture_output(cmd);
if (out.exit_code != 0)
{
return {};
}
return Util::fmap(Strings::split(out.output, "\n"), [](auto&& s) { return fs::path(s); });
}
}

View File

@ -9,7 +9,6 @@
#include <vcpkg/base/util.h>
#include <vcpkg/commands.h>
#include <vcpkg/help.h>
#
namespace vcpkg::Commands::Fetch
{
@ -151,15 +150,20 @@ namespace vcpkg::Commands::Fetch
std::vector<PathAndVersion> get_versions(const std::vector<fs::path>& candidate_paths) const
{
auto&& fs = Files::get_real_filesystem();
std::vector<PathAndVersion> output;
for (auto&& p : candidate_paths)
{
if (!fs.exists(p)) continue;
auto maybe_version = this->get_version(p);
if (const auto version = maybe_version.get())
{
output.emplace_back(PathAndVersion{p, *version});
return output;
}
}
return output;
}
};
@ -254,7 +258,7 @@ namespace vcpkg::Commands::Fetch
#else
static const ToolData TOOL_DATA = ToolData{{3, 5, 1}, ""};
#endif
const std::vector<fs::path> from_path = Files::find_from_PATH("cmake");
const std::vector<fs::path> from_path = paths.get_filesystem().find_from_PATH("cmake");
candidate_paths.insert(candidate_paths.end(), from_path.cbegin(), from_path.cend());
const auto& program_files = System::get_program_files_platform_bitness();
@ -315,7 +319,7 @@ namespace vcpkg::Commands::Fetch
std::vector<fs::path> candidate_paths;
candidate_paths.push_back(TOOL_DATA.exe_path);
const std::vector<fs::path> from_path = Files::find_from_PATH("ninja");
const std::vector<fs::path> from_path = paths.get_filesystem().find_from_PATH("ninja");
candidate_paths.insert(candidate_paths.end(), from_path.cbegin(), from_path.cend());
const NinjaVersionProvider version_provider{};
@ -360,7 +364,7 @@ Type 'NuGet help <command>' for help on a specific command.
std::vector<fs::path> candidate_paths;
candidate_paths.push_back(TOOL_DATA.exe_path);
const std::vector<fs::path> from_path = Files::find_from_PATH("nuget");
const std::vector<fs::path> from_path = paths.get_filesystem().find_from_PATH("nuget");
candidate_paths.insert(candidate_paths.end(), from_path.cbegin(), from_path.cend());
const NugetVersionProvider version_provider{};
@ -408,7 +412,7 @@ git version 2.17.1.windows.2
#if defined(_WIN32)
candidate_paths.push_back(TOOL_DATA.exe_path);
#endif
const std::vector<fs::path> from_path = Files::find_from_PATH("git");
const std::vector<fs::path> from_path = paths.get_filesystem().find_from_PATH("git");
candidate_paths.insert(candidate_paths.end(), from_path.cbegin(), from_path.cend());
const auto& program_files = System::get_program_files_platform_bitness();