From 4cda71156464d20789bac5b31f6a1ea36b183edd Mon Sep 17 00:00:00 2001 From: Paul Eggert Date: Thu, 27 Jan 2022 18:34:09 -0800 Subject: [PATCH] dd: output final progress before syncing Problem reported by Sworddragon (Bug#51482). * src/dd.c (reported_w_bytes): New var. (print_xfer_stats): Set it. (dd_copy): Print a final progress report if useful before synchronizing output data. --- NEWS | 4 ++++ src/dd.c | 12 ++++++++++++ 2 files changed, 16 insertions(+) diff --git a/NEWS b/NEWS index 561087ccc..15c9428bd 100644 --- a/NEWS +++ b/NEWS @@ -58,6 +58,10 @@ GNU coreutils NEWS -*- outline -*- The new 'date' option --resolution outputs the timestamp resolution. + With conv=fdatasync or conv=fsync, dd status=progress now reports + any extra final progress just before synchronizing output data, + since synchronizing can take a long time. + sort --debug now diagnoses issues with --field-separator characters that conflict with characters possibly used in numbers. diff --git a/src/dd.c b/src/dd.c index a6a3708f1..957ad129e 100644 --- a/src/dd.c +++ b/src/dd.c @@ -196,6 +196,9 @@ static intmax_t r_full = 0; /* Number of bytes written. */ static intmax_t w_bytes = 0; +/* Last-reported number of bytes written, or negative if never reported. */ +static intmax_t reported_w_bytes = -1; + /* Time that dd started. */ static xtime_t start_time; @@ -815,6 +818,8 @@ print_xfer_stats (xtime_t progress_time) } else fputc ('\n', stderr); + + reported_w_bytes = w_bytes; } static void @@ -2365,6 +2370,13 @@ dd_copy (void) } } + /* fdatasync/fsync can take a long time, so issue a final progress + indication now if progress has been made since the previous indication. */ + if (conversions_mask & (C_FDATASYNC | C_FSYNC) + && status_level == STATUS_PROGRESS + && 0 <= reported_w_bytes && reported_w_bytes < w_bytes) + print_xfer_stats (0); + if ((conversions_mask & C_FDATASYNC) && ifdatasync (STDOUT_FILENO) != 0) { if (errno != ENOSYS && errno != EINVAL) -- 2.32.0