diff options
author | Oliver Reiche <oliver.reiche@huawei.com> | 2022-07-06 11:14:28 +0200 |
---|---|---|
committer | Oliver Reiche <oliver.reiche@huawei.com> | 2022-07-07 15:00:09 +0200 |
commit | 80c1d95114b46cc396a6b1c6a8bccaab8bf52a97 (patch) | |
tree | 4ec46665df9402736bdd80e00fe97e2d186d5206 /src/buildtool/execution_engine/traverser/traverser.hpp | |
parent | fa4bb79fa3e972efc0e59abfda89b3e57b472dfa (diff) | |
download | justbuild-80c1d95114b46cc396a6b1c6a8bccaab8bf52a97.tar.gz |
Traverser: Bring task system down gracefully on error
Diffstat (limited to 'src/buildtool/execution_engine/traverser/traverser.hpp')
-rw-r--r-- | src/buildtool/execution_engine/traverser/traverser.hpp | 26 |
1 files changed, 20 insertions, 6 deletions
diff --git a/src/buildtool/execution_engine/traverser/traverser.hpp b/src/buildtool/execution_engine/traverser/traverser.hpp index 930cf0fb..4d3fc7e9 100644 --- a/src/buildtool/execution_engine/traverser/traverser.hpp +++ b/src/buildtool/execution_engine/traverser/traverser.hpp @@ -1,6 +1,8 @@ #ifndef INCLUDED_SRC_BUILDTOOL_EXECUTION_ENGINE_TRAVERSER_TRAVERSER_HPP #define INCLUDED_SRC_BUILDTOOL_EXECUTION_ENGINE_TRAVERSER_TRAVERSER_HPP +#include <atomic> + #include "gsl-lite/gsl-lite.hpp" #include "src/buildtool/execution_engine/dag/dag.hpp" #include "src/buildtool/logging/logger.hpp" @@ -27,8 +29,14 @@ concept Runnable = requires(T const r, template <Runnable Executor> class Traverser { public: - Traverser(Executor const& r, DependencyGraph const& graph, std::size_t jobs) - : runner_{r}, graph_{graph}, tasker_{jobs} {} + Traverser(Executor const& r, + DependencyGraph const& graph, + std::size_t jobs, + gsl::not_null<std::atomic<bool>*> fail_flag) + : runner_{r}, + graph_{graph}, + failed_{std::move(fail_flag)}, + tasker_{jobs} {} Traverser() = delete; Traverser(Traverser const&) = delete; Traverser(Traverser&&) = delete; @@ -52,6 +60,7 @@ class Traverser { private: Executor const& runner_{}; DependencyGraph const& graph_; + gsl::not_null<std::atomic<bool>*> failed_; TaskSystem tasker_{}; // THIS SHOULD BE THE LAST MEMBER VARIABLE // Visits discover nodes and queue visits to their children nodes. @@ -77,7 +86,7 @@ class Traverser { void QueueVisit(NodeTypePtr node) noexcept { // in case the node was already discovered, there is no need to queue // the visit - if (node->TraversalState()->GetAndMarkDiscovered()) { + if (failed_->load() or node->TraversalState()->GetAndMarkDiscovered()) { return; } tasker_.QueueTask([this, node]() noexcept { Visit(node); }); @@ -89,7 +98,7 @@ class Traverser { // was successful template <typename NodeTypePtr> void QueueProcessing(NodeTypePtr node) noexcept { - if (not node->TraversalState()->IsRequired() or + if (failed_->load() or not node->TraversalState()->IsRequired() or node->TraversalState()->GetAndMarkQueuedToBeProcessed()) { return; } @@ -99,12 +108,16 @@ class Traverser { NotifyAvailable(node); } else { - Logger::Log(LogLevel::Error, "Build failed."); - std::exit(EXIT_FAILURE); + Abort(); } }; tasker_.QueueTask(process_node); } + + void Abort() noexcept { + failed_->store(true); + tasker_.Shutdown(); // skip execution of pending tasks + } }; template <Runnable Executor> @@ -116,6 +129,7 @@ auto Traverser<Executor>::Traverse( QueueVisit(artifact_node); } else { + Abort(); Logger::Log( LogLevel::Error, "artifact with id {} can not be found in dependency graph.", |