summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/buildtool/common/cli.hpp11
-rw-r--r--src/buildtool/execution_engine/executor/executor.hpp37
-rw-r--r--src/buildtool/graph_traverser/graph_traverser.hpp9
3 files changed, 43 insertions, 14 deletions
diff --git a/src/buildtool/common/cli.hpp b/src/buildtool/common/cli.hpp
index 97efb9d3..7e93b9ec 100644
--- a/src/buildtool/common/cli.hpp
+++ b/src/buildtool/common/cli.hpp
@@ -1,6 +1,7 @@
#ifndef INCLUDED_SRC_BUILDTOOL_COMMON_CLI_HPP
#define INCLUDED_SRC_BUILDTOOL_COMMON_CLI_HPP
+#include <chrono>
#include <cstdlib>
#include <filesystem>
#include <string>
@@ -14,6 +15,7 @@
#include "src/buildtool/logging/log_level.hpp"
constexpr auto kDefaultLogLevel = LogLevel::Info;
+constexpr auto kDefaultTimeout = std::chrono::milliseconds{300000};
/// \brief Arguments common to all commands.
struct CommonArguments {
@@ -59,6 +61,7 @@ struct EndpointArguments {
struct BuildArguments {
std::optional<std::vector<std::string>> local_launcher{std::nullopt};
std::map<std::string, std::string> platform_properties;
+ std::chrono::milliseconds timeout{kDefaultTimeout};
std::size_t build_jobs{};
std::optional<std::string> dump_artifacts{std::nullopt};
std::optional<std::string> print_to_stdout{std::nullopt};
@@ -269,6 +272,14 @@ static inline auto SetupBuildArguments(
->allow_extra_args(false)
->expected(1, 1);
+ app->add_option_function<unsigned int>(
+ "--action_timeout",
+ [clargs](auto const& seconds) {
+ clargs->timeout = seconds * std::chrono::seconds{1};
+ },
+ "Action timeout in seconds. (Default: 300).")
+ ->type_name("NUM");
+
app->add_option(
"-J,--build_jobs",
clargs->build_jobs,
diff --git a/src/buildtool/execution_engine/executor/executor.hpp b/src/buildtool/execution_engine/executor/executor.hpp
index d7447ed8..3cba3896 100644
--- a/src/buildtool/execution_engine/executor/executor.hpp
+++ b/src/buildtool/execution_engine/executor/executor.hpp
@@ -2,6 +2,7 @@
#define INCLUDED_SRC_BUILDTOOL_EXECUTION_ENGINE_EXECUTOR_EXECUTOR_HPP
#include <algorithm>
+#include <chrono>
#include <functional>
#include <iostream>
#include <map>
@@ -29,6 +30,7 @@ class ExecutorImpl {
gsl::not_null<DependencyGraph::ActionNode const*> const& action,
gsl::not_null<IExecutionApi*> const& api,
std::map<std::string, std::string> const& properties,
+ std::chrono::milliseconds const& timeout,
IExecutionAction::CacheFlag cache_flag)
-> std::optional<IExecutionResponse::Ptr> {
auto const& inputs = action->Dependencies();
@@ -81,7 +83,7 @@ class ExecutorImpl {
// set action options
remote_action->SetCacheFlag(cache_flag);
- remote_action->SetTimeout(IExecutionAction::kDefaultTimeout);
+ remote_action->SetTimeout(timeout);
return remote_action->Execute(&logger);
}
@@ -343,9 +345,11 @@ class Executor {
using CF = IExecutionAction::CacheFlag;
public:
- explicit Executor(IExecutionApi* api,
- std::map<std::string, std::string> properties)
- : api_{api}, properties_{std::move(properties)} {}
+ explicit Executor(
+ IExecutionApi* api,
+ std::map<std::string, std::string> properties,
+ std::chrono::milliseconds timeout = IExecutionAction::kDefaultTimeout)
+ : api_{api}, properties_{std::move(properties)}, timeout_{timeout} {}
/// \brief Run an action in a blocking manner
/// This method must be thread-safe as it could be called in parallel
@@ -361,6 +365,7 @@ class Executor {
action,
api_,
properties_,
+ timeout_,
action->NoCache() ? CF::DoNotCacheOutput : CF::CacheOutput);
// check response and save digests of results
@@ -379,6 +384,7 @@ class Executor {
private:
gsl::not_null<IExecutionApi*> api_;
std::map<std::string, std::string> properties_;
+ std::chrono::milliseconds timeout_;
};
/// \brief Rebuilder for running and comparing actions of two API endpoints.
@@ -391,12 +397,16 @@ class Rebuilder {
/// \param api Rebuild endpoint, executes without action cache.
/// \param api_cached Reference endpoint, serves everything from cache.
/// \param properties Platform properties for execution.
- Rebuilder(IExecutionApi* api,
- IExecutionApi* api_cached,
- std::map<std::string, std::string> properties)
+ /// \param timeout Timeout for action execution.
+ Rebuilder(
+ IExecutionApi* api,
+ IExecutionApi* api_cached,
+ std::map<std::string, std::string> properties,
+ std::chrono::milliseconds timeout = IExecutionAction::kDefaultTimeout)
: api_{api},
api_cached_{api_cached},
- properties_{std::move(properties)} {}
+ properties_{std::move(properties)},
+ timeout_{timeout} {}
[[nodiscard]] auto Process(
gsl::not_null<DependencyGraph::ActionNode const*> const& action)
@@ -404,15 +414,19 @@ class Rebuilder {
auto const& action_id = action->Content().Id();
Logger logger("rebuild:" + action_id);
auto response = Impl::ExecuteAction(
- logger, action, api_, properties_, CF::PretendCached);
+ logger, action, api_, properties_, timeout_, CF::PretendCached);
if (not response) {
return true; // action without response (e.g., tree action)
}
Logger logger_cached("cached:" + action_id);
- auto response_cached = Impl::ExecuteAction(
- logger_cached, action, api_cached_, properties_, CF::FromCacheOnly);
+ auto response_cached = Impl::ExecuteAction(logger_cached,
+ action,
+ api_cached_,
+ properties_,
+ timeout_,
+ CF::FromCacheOnly);
if (not response_cached) {
logger_cached.Emit(LogLevel::Error,
@@ -446,6 +460,7 @@ class Rebuilder {
gsl::not_null<IExecutionApi*> api_;
gsl::not_null<IExecutionApi*> api_cached_;
std::map<std::string, std::string> properties_;
+ std::chrono::milliseconds timeout_;
mutable std::mutex m_;
mutable std::vector<std::string> cache_misses_{};
mutable std::unordered_map<
diff --git a/src/buildtool/graph_traverser/graph_traverser.hpp b/src/buildtool/graph_traverser/graph_traverser.hpp
index c92fbbf8..7a078ecd 100644
--- a/src/buildtool/graph_traverser/graph_traverser.hpp
+++ b/src/buildtool/graph_traverser/graph_traverser.hpp
@@ -282,7 +282,8 @@ class GraphTraverser {
[[nodiscard]] auto Traverse(
DependencyGraph const& g,
std::vector<ArtifactIdentifier> const& artifact_ids) const -> bool {
- Executor executor{&(*api_), clargs_.build.platform_properties};
+ Executor executor{
+ &(*api_), clargs_.build.platform_properties, clargs_.build.timeout};
Traverser t{executor, g, clargs_.jobs};
return t.Traverse({std::begin(artifact_ids), std::end(artifact_ids)});
}
@@ -301,8 +302,10 @@ class GraphTraverser {
// setup rebuilder with api for cache endpoint
auto api_cached = CreateExecutionApi(cache_args);
- Rebuilder executor{
- &(*api_), &(*api_cached), clargs_.build.platform_properties};
+ Rebuilder executor{&(*api_),
+ &(*api_cached),
+ clargs_.build.platform_properties,
+ clargs_.build.timeout};
bool success{false};
{
Traverser t{executor, g, clargs_.jobs};