Skip to content

Commit

Permalink
Update status on edge finished
Browse files Browse the repository at this point in the history
In the terminal, when an edge finishes update the status to display the first started (longest running) action.
Usually this will be immediately overwritten with the next started action but if there is a bottleneck in the build or
if it is reaching the end, this ensures that the console displays status of a build that is actually running and not
one that has completed.
This ensures that the user attributes any delay to the (or an) action that is actually causing the slowdown and not
unfairly to an action that has already finished just because it happened to be the last started.

To make this clear, also change the default NINJA_STATUS to include current actual parallelism level - this will
reduce from number of cores to 1 as the bottleneck or end of build approaches.

Implementation stores currently running nodes in a deque, with NULL for interior completed nodes. This should be
fairly efficient and allows future extension to e.g. display multiple parallel action names, as in ninja-build#2249 and @orgads
prototype for ninja-build#111.

Partially resolves ninja-build#111 (should be enough for most purposes).
  • Loading branch information
ecatmur committed Aug 2, 2023
1 parent 36843d3 commit e981aa5
Show file tree
Hide file tree
Showing 2 changed files with 22 additions and 3 deletions.
22 changes: 19 additions & 3 deletions src/status.cc
Original file line number Diff line number Diff line change
Expand Up @@ -37,8 +37,12 @@ StatusPrinter::StatusPrinter(const BuildConfig& config)
printer_.set_smart_terminal(false);

progress_status_format_ = getenv("NINJA_STATUS");
if (!progress_status_format_)
progress_status_format_ = "[%f/%t] ";
if (!progress_status_format_) {
if (printer_.is_smart_terminal())
progress_status_format_ = "[%f*%r/%t] ";
else
progress_status_format_ = "[%f/%t] ";
}
}

void StatusPrinter::PlanHasTotalEdges(int total) {
Expand All @@ -50,6 +54,8 @@ void StatusPrinter::BuildEdgeStarted(const Edge* edge,
++started_edges_;
++running_edges_;
time_millis_ = start_time_millis;
if (printer_.is_smart_terminal())
edges_.push_back(edge);

if (edge->use_console() || printer_.is_smart_terminal())
PrintStatus(edge, start_time_millis);
Expand All @@ -63,13 +69,20 @@ void StatusPrinter::BuildEdgeFinished(Edge* edge, int64_t end_time_millis,
time_millis_ = end_time_millis;
++finished_edges_;

if (printer_.is_smart_terminal()) {
*std::find(edges_.begin(), edges_.end(), edge) = NULL;
while (!edges_.empty() && edges_.front() == NULL)
edges_.pop_front();
}

if (edge->use_console())
printer_.SetConsoleLocked(false);

if (config_.verbosity == BuildConfig::QUIET)
return;

if (!edge->use_console())
if (!edge->use_console()
&& (!printer_.is_smart_terminal() || !success || !output.empty()))
PrintStatus(edge, end_time_millis);

--running_edges_;
Expand Down Expand Up @@ -118,6 +131,9 @@ void StatusPrinter::BuildEdgeFinished(Edge* edge, int64_t end_time_millis,
_setmode(_fileno(stdout), _O_TEXT); // End Windows extra CR fix
#endif
}

if (printer_.is_smart_terminal() && !edges_.empty())
PrintStatus(edges_.front(), end_time_millis);
}

void StatusPrinter::BuildLoadDyndeps() {
Expand Down
3 changes: 3 additions & 0 deletions src/status.h
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,9 @@
#ifndef NINJA_STATUS_H_
#define NINJA_STATUS_H_

#include <deque>
#include <map>
#include <queue>
#include <string>

#include "build.h"
Expand Down Expand Up @@ -72,6 +74,7 @@ struct StatusPrinter : Status {

int started_edges_, finished_edges_, total_edges_, running_edges_;
int64_t time_millis_;
std::deque<const Edge*> edges_;

/// Prints progress output.
LinePrinter printer_;
Expand Down

0 comments on commit e981aa5

Please sign in to comment.