]> git.ipfire.org Git - thirdparty/coreutils.git/commitdiff
tail: with -f don't warn if doing a blocking read of a tty
authorPádraig Brady <P@draigBrady.com>
Thu, 15 Jun 2017 09:41:14 +0000 (02:41 -0700)
committerPádraig Brady <P@draigBrady.com>
Sat, 17 Jun 2017 21:50:00 +0000 (14:50 -0700)
* src/tail.c: (main): Only issue the warning about -f being
ineffective when we're not going into simple blocking mode.
* tests/tail-2/follow-stdin.sh: Ensure the warning is output correctly.
Fixes http://bugs.gnu.org/27368

NEWS
src/tail.c
tests/tail-2/follow-stdin.sh

diff --git a/NEWS b/NEWS
index d2672e86bc9375353f995de061615f2c6154e26b..eb0271cf8f1291cedb6b481bc87f4ed268dddb9a 100644 (file)
--- a/NEWS
+++ b/NEWS
@@ -31,7 +31,7 @@ GNU coreutils NEWS                                    -*- outline -*-
   tail -F 'dir/file' is now monitored even when 'dir' is replaced.
   [bug introduced with inotify support added in coreutils-7.5]
 
-  tail -f with --pid=PID will now process all inotify events.
+  tail -f with --pid=PID now processes all inotify events.
   Previously events may have been ignored completely upon PID death,
   or ignored until future events on the monitored files.
   [bug introduced with inotify support added in coreutils-7.5]
@@ -53,9 +53,13 @@ GNU coreutils NEWS                                    -*- outline -*-
 
   mv --verbose now distinguishes rename and copy operations.
 
-  tail -f will now exit immediately if the output is piped
+  tail -f now exits immediately if the output is piped
   and the reader of the pipe terminates.
 
+  tail -f no longer erroneously warns about being ineffective
+  when following a single tty, as the simple blocking loop used
+  is effective in this case.
+
 
 * Noteworthy changes in release 8.27 (2017-03-08) [stable]
 
index 3918373f6095f3c20bfdeedd619ba76c832b4221..2f9b981f0daafc7c3e2ec698ff6d903e6058c233 100644 (file)
@@ -2365,12 +2365,22 @@ main (int argc, char **argv)
     if (found_hyphen && follow_mode == Follow_name)
       die (EXIT_FAILURE, 0, _("cannot follow %s by name"), quoteaf ("-"));
 
-    /* When following forever, warn if any file is '-'.
+    /* When following forever, and not using simple blocking, warn if
+       any file is '-' as the stats() used to check for input are ineffective.
        This is only a warning, since tail's output (before a failing seek,
        and that from any non-stdin files) might still be useful.  */
-    if (forever && found_hyphen && isatty (STDIN_FILENO))
-      error (0, 0, _("warning: following standard input"
-                     " indefinitely is ineffective"));
+    if (forever && found_hyphen)
+      {
+        struct stat in_stat;
+        bool blocking_stdin;
+        blocking_stdin = (pid == 0 && follow_mode == Follow_descriptor
+                          && n_files == 1 && ! fstat (STDIN_FILENO, &in_stat)
+                          && ! S_ISREG (in_stat.st_mode));
+
+        if (! blocking_stdin && isatty (STDIN_FILENO))
+          error (0, 0, _("warning: following standard input"
+                         " indefinitely is ineffective"));
+      }
   }
 
   /* Don't read anything if we'll never output anything.  */
index 7e82835ffb0835bdbd3e9317ac5488d52cd25ff6..c922ea11ad9ffc2777498fd5942b48da83f44d18 100755 (executable)
@@ -1,5 +1,5 @@
 #!/bin/sh
-# tail -f - would fail with the initial inotify implementation
+# Test tail -f -
 
 # Copyright (C) 2009-2017 Free Software Foundation, Inc.
 
@@ -19,6 +19,9 @@
 . "${srcdir=.}/tests/init.sh"; path_prepend_ ./src
 print_ver_ tail
 
+#################
+# tail -f - would fail with the initial inotify implementation
+
 check_tail_output()
 {
   local delay="$1"
@@ -51,6 +54,7 @@ for mode in '' '---disable-inotify'; do
 done
 
 
+#################
 # Before coreutils-8.26 this would induce an UMR under UBSAN
 returns_ 1 timeout 10 tail -f - <&- 2>errt || fail=1
 cat <<\EOF >exp || framework_failure_
@@ -63,4 +67,19 @@ sed 's/\(tail:.*\):.*/\1/' errt > err || framework_failure_
 compare exp err || fail=1
 
 
+#################
+# Before coreutils-8.28 this would erroneously issue a warning
+if tty -s </dev/tty && test -t 0; then
+  for input in '' '-' '/dev/tty'; do
+    returns_ 124 timeout 0.1 tail -f $input 2>err || fail=1
+    compare /dev/null err || fail=1
+  done
+
+  tail -f - /dev/null </dev/tty 2> out & pid=$!
+  # Wait up to 12.7s for output to appear:
+  tail_re='ineffective' retry_delay_ check_tail_output .1 7 ||
+    { cat out; fail=1; }
+  cleanup_
+fi
+
 Exit $fail