Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Print status when edge finishes on dumb terminals #999

Merged
merged 1 commit into from
Nov 12, 2015

Conversation

colincross
Copy link
Contributor

On smart terminals ninja prints the status line both before
and after running a command, reusing the same line if possible.
On a dumb terminal that doesn't support reusing the line, it
only prints the status before starting the command, but prints
the output of the command when the command finishes, by which
point other commands may have started and printed their status
line. This makes it impossible to determine what command
produced a line of output.

Modify BuildEdgeStarted to only print the status line if the
command is going to lock the console, or if ninja is running
on a smart terminal. Modify BuildEdgeFinished to always
print the status line unless the command locked the console,
in which case the status was already printed and no other
command can have printed any lines.

The end result will be dumb terminal output that much more
closely matches smart terminal output. One disadvantage is
that dumb terminals won't show anything when starting a
command, making it harder to tell what commands are currently
running, but I expect most interactive uses of ninja will use
a smart terminal.

On smart terminals ninja prints the status line both before
and after running a command, reusing the same line if possible.
On a dumb terminal that doesn't support reusing the line, it
only prints the status before starting the command, but prints
the output of the command when the command finishes, by which
point other commands may have started and printed their status
line.  This makes it impossible to determine what command
produced a line of output.

Modify BuildEdgeStarted to only print the status line if the
command is going to lock the console, or if ninja is running
on a smart terminal.  Modify BuildEdgeFinished to always
print the status line unless the command locked the console,
in which case the status was already printed and no other
command can have printed any lines.

The end result will be dumb terminal output that much more
closely matches smart terminal output.  One disadvantage is
that dumb terminals won't show anything when starting a
command, making it harder to tell what commands are currently
running, but I expect most interactive uses of ninja will use
a smart terminal.
@nico
Copy link
Collaborator

nico commented Nov 12, 2015

I'm tentatively merging this as discussed on the "[rfc] changing ninja's progress output order when writing to a file?" thread.

nico added a commit that referenced this pull request Nov 12, 2015
Print status when edge finishes on dumb terminals
@nico nico merged commit a65240d into ninja-build:master Nov 12, 2015
@colincross colincross deleted the dumbstatus branch November 12, 2015 17:08
colincross added a commit to colincross/ninja that referenced this pull request Apr 28, 2016
PR ninja-build#999 changed the status line to be printed when edges finish on dumb
teerminals, but the default status message includes the number of
started edges, resulting in sequential status lines with identical
edge counts.

Change the default status to show the number of finished edges, which
will keep the count incrementing on every line.  This will slightly
change the output on smart terminals.  Previously a build that was just
starting would show a count equal to the number of concurrent jobs, and
a build waiting for the final jobs to finish would show a count equal to
the total number of edges.  Now a starting build will show 0, and build
waiting for the final jobs will show a count less than the total number
of edges by the number of remaining jobs.

Fixes: ninja-build#1142
colincross added a commit to colincross/ninja that referenced this pull request Apr 28, 2016
PR ninja-build#999 changed the status line to be printed when edges finish on dumb
teerminals, but the default status message includes the number of
started edges, resulting in sequential status lines with identical
edge counts.

Change the default status to show the number of finished edges, which
will keep the count incrementing on every line.  This will slightly
change the output on smart terminals.  Previously a build that was just
starting would show a count equal to the number of concurrent jobs, and
a build waiting for the final jobs to finish would show a count equal to
the total number of edges.  Now a starting build will show 0, and build
waiting for the final jobs will show a count less than the total number
of edges by the number of remaining jobs.

Fixes: ninja-build#1142
colincross added a commit to colincross/ninja that referenced this pull request Apr 28, 2016
PR ninja-build#999 made dumb terminals only output when edges
finish. BuildStatus::overall_rate_ stopwatch is only initialized to the
current time when PrintStatus is called with finished_edges_ == 0, but
on a dumb terminal it will be called for the first time when
finished_edge_ = 1, which results in very long elapsed times:
NINJA_STATUS="[%r processes, %f/%t @ %o/s : %es ] "
[0 processes, 2/2 @ 0.0/s : 1461869902.367s ]

Reset the stopwatches in BuildEdgeFinished before finshed_edges_ is
incremented instead.
colincross added a commit to colincross/ninja that referenced this pull request Apr 28, 2016
PR ninja-build#999 made dumb terminals only output when edges finish.  PrintStatus
is called after finished_edges_ is incremented, which means the
calculation for running edges will always return 1 less than the real
number of running processes.  This happens on smart terminals too, but
ninja will immediately print the status for the next edge with
starting_edges_ incremented, so the incorrect value is never visible.

Pass a boolean specifying whether the status is being printed on an edge
finishing, and if so count the edge that just finished as being running.
@sgraham
Copy link
Contributor

sgraham commented Apr 28, 2016

I think this might have regressed output on the Chrome bots. Dirk noticed un-nice output on https://build.chromium.org/p/chromium.linux/builders/Linux%20Builder%20%28dbg%29%2832%29/builds/52253/steps/compile/logs/stdio
where the failure happens and then a whole bunch of "completed" lines push the actual failure way back in the log. (Note that they're running -j50.)

Maybe because the jobs are finishing at that point? Seems like we might need a special case for failure if we want to keep this ordering of output.

@sgraham
Copy link
Contributor

sgraham commented Apr 28, 2016

(Should have been @dpranke above.)

@colincross
Copy link
Contributor Author

Before this patch output from commands that were running concurrently with failed command would appear after the output of the failed command, with no status line to separate the outputs of the different commands. Chromium probably never ran into this issue since your rules generally have no output. After this patch every command output is preceded by its status line, but that means that failures are followed by status lines for all concurrent commands.

Hiding the status lines for concurrent commands that have no output doesn't seem right, since those rules ran and completed. We could delay printing the error until all concurrent commands have finished, but then if you had an error concurrent with a long command you might get the error much later than you otherwise could have seen it.

On Android our commands are so noisy that identifying the build output from a failing command is impossible without this patch.

@dpranke
Copy link

dpranke commented Apr 28, 2016

I think delaying the error is probably okay; I don't know how often you really need to see the failures in real time or the delay would be long enough to matter. I agree that the change is generally an improvement and I would like to avoid hiding the output from completed edges as well.

@sgraham
Copy link
Contributor

sgraham commented Apr 28, 2016

I think it'd be OK to delay the error, but only in dumb-mode; that would be annoying locally in smart-terminal mode where there's often a long unrelated link finishing.

@dpranke
Copy link

dpranke commented Apr 28, 2016

sure, only in not-a-tty-mode is fine by me.

colincross added a commit to colincross/ninja that referenced this pull request Apr 29, 2016
PR ninja-build#999 made dumb terminals only output when edges finish.  PrintStatus
is called after finished_edges_ is incremented, which means the
calculation for running edges will always return 1 less than the real
number of running processes.  This happens on smart terminals too, but
ninja will immediately print the status for the next edge with
starting_edges_ incremented, so the incorrect value is never visible.

Pass a boolean specifying whether the status is being printed on an edge
finishing, and if so count the edge that just finished as being running.
@wjakob
Copy link

wjakob commented Sep 29, 2016

I just ran into this when 'ninja -v' did not print started jobs anymore (which run for many minutes, so there is basically no output at all). This is pretty annoying -- are there any plans to offer to revert to the previous behavior as an option?

@nico
Copy link
Collaborator

nico commented Nov 7, 2016

FWIW I find this annoying in -v mode too, so I agree it'd be nice to do something there.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

None yet

5 participants