emacs-bug-tracker
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[debbugs-tracker] bug#23321: closed ([PROPOSED PATCH] grep: /dev/null ou


From: GNU bug Tracking System
Subject: [debbugs-tracker] bug#23321: closed ([PROPOSED PATCH] grep: /dev/null output speedup)
Date: Mon, 02 May 2016 05:59:02 +0000

Your message dated Sun, 1 May 2016 22:58:13 -0700
with message-id <address@hidden>
and subject line Re: [PROPOSED PATCH] grep: /dev/null output speedup
has caused the debbugs.gnu.org bug report #23321,
regarding [PROPOSED PATCH] grep: /dev/null output speedup
to be marked as done.

(If you believe you have received this mail in error, please contact
address@hidden)


-- 
23321: http://debbugs.gnu.org/cgi/bugreport.cgi?bug=23321
GNU Bug Tracking System
Contact address@hidden with problems
--- Begin Message --- Subject: [PROPOSED PATCH] grep: /dev/null output speedup Date: Wed, 20 Apr 2016 10:08:48 -0700
This sped up 'seq 10000000000 | grep . >/dev/null' by a factor of
380,000 on my platform (Fedora 23, x86-64, AMD Phenom II X4 910e,
en_US.UTF-8 locale).
* NEWS: Document this.
* src/grep.c (grepbuf): exit_on_match no longer implies that -q
was specified, so when a match is found, exit with exit_failure if
an error was also found.
(grepdesc): Omit unnecessary S_ISREG and st_ino checks.
out_stat.st_ino is zero if stdout is not a regular file,
and this cannot possibly equal st->st_ino.
(main): Omit duplicate initialization of exit_failure.  Do not
bother with isatty unless -q is not used and stdout is a character
special file and --color=auto and TERM says colorization is
possible.  Most importantly, set exit_on_match if the output is
/dev/null.
* tests/grep-dev-null-out: New test.
* tests/Makefile.am (TESTS): Add it.
* tests/status: Do not require grep to actually read all the input
files when the output is /dev/null and a matching line has been
found.
---
 NEWS                    |  2 ++
 src/grep.c              | 67 ++++++++++++++++++++++++++++---------------------
 tests/Makefile.am       |  1 +
 tests/grep-dev-null-out | 11 ++++++++
 tests/status            |  4 +--
 5 files changed, 55 insertions(+), 30 deletions(-)
 create mode 100755 tests/grep-dev-null-out

diff --git a/NEWS b/NEWS
index 63767aa..2af0d6d 100644
--- a/NEWS
+++ b/NEWS
@@ -18,6 +18,8 @@ GNU grep NEWS                                    -*- outline 
-*-
 
 ** Improvements
 
+  grep can be much faster now when standard output is /dev/null.
+
   grep now outputs details more consistently when reporting a write error.
   E.g., "grep: write error: No space left on device" rather than just
   "grep: write error".
diff --git a/src/grep.c b/src/grep.c
index 8baca5a..d812bae 100644
--- a/src/grep.c
+++ b/src/grep.c
@@ -1387,7 +1387,7 @@ grepbuf (char *beg, char const *lim)
           if (!outleft || done_on_match)
             {
               if (exit_on_match)
-                exit (EXIT_SUCCESS);
+                exit (errseen ? exit_failure : EXIT_SUCCESS);
               break;
             }
         }
@@ -1751,7 +1751,6 @@ grepdesc (int desc, bool command_line)
      input==output, while there is no risk of infloop, there is a race
      condition that could result in "alternate" output.  */
   if (!out_quiet && list_files == 0 && 1 < max_count
-      && S_ISREG (out_stat.st_mode) && out_stat.st_ino
       && SAME_INODE (st, out_stat))
     {
       if (! suppress_errors)
@@ -2280,7 +2279,6 @@ main (int argc, char **argv)
   textdomain (PACKAGE);
 #endif
 
-  exit_failure = EXIT_TROUBLE;
   atexit (clean_up_stdout);
 
   last_recursive = 0;
@@ -2579,25 +2577,36 @@ main (int argc, char **argv)
 
       }
 
-  if (color_option == 2)
-    color_option = isatty (STDOUT_FILENO) && should_colorize ();
-  init_colorize ();
+  if (show_version)
+    {
+      version_etc (stdout, program_name, PACKAGE_NAME, VERSION, AUTHORS,
+                   (char *) NULL);
+      return EXIT_SUCCESS;
+    }
 
-  /* POSIX says that -q overrides -l, which in turn overrides the
-     other output options.  */
-  if (exit_on_match)
-    list_files = 0;
-  if (exit_on_match | list_files)
+  if (show_help)
+    usage (EXIT_SUCCESS);
+
+  bool possibly_tty = false;
+  struct stat tmp_stat;
+  if (! exit_on_match && fstat (STDOUT_FILENO, &tmp_stat) == 0)
     {
-      count_matches = false;
-      done_on_match = true;
+      if (S_ISREG (tmp_stat.st_mode))
+        out_stat = tmp_stat;
+      else if (S_ISCHR (tmp_stat.st_mode))
+        {
+          struct stat null_stat;
+          if (stat ("/dev/null", &null_stat) == 0
+              && SAME_INODE (tmp_stat, null_stat))
+            exit_on_match = true;
+          else
+            possibly_tty = true;
+        }
     }
-  out_quiet = count_matches | done_on_match;
 
-  if (out_after < 0)
-    out_after = default_context;
-  if (out_before < 0)
-    out_before = default_context;
+  if (color_option == 2)
+    color_option = possibly_tty && should_colorize () && isatty 
(STDOUT_FILENO);
+  init_colorize ();
 
   if (color_option)
     {
@@ -2610,19 +2619,21 @@ main (int argc, char **argv)
       parse_grep_colors ();
     }
 
-  if (show_version)
+  /* POSIX says -c, -l and -q are mutually exclusive.  In this
+     implementation, -q overrides -l and -L, which in turn override -c.  */
+  if (exit_on_match)
+    list_files = 0;
+  if (exit_on_match | list_files)
     {
-      version_etc (stdout, program_name, PACKAGE_NAME, VERSION, AUTHORS,
-                   (char *) NULL);
-      return EXIT_SUCCESS;
+      count_matches = false;
+      done_on_match = true;
     }
+  out_quiet = count_matches | done_on_match;
 
-  if (show_help)
-    usage (EXIT_SUCCESS);
-
-  struct stat tmp_stat;
-  if (fstat (STDOUT_FILENO, &tmp_stat) == 0 && S_ISREG (tmp_stat.st_mode))
-    out_stat = tmp_stat;
+  if (out_after < 0)
+    out_after = default_context;
+  if (out_before < 0)
+    out_before = default_context;
 
   if (keys)
     {
diff --git a/tests/Makefile.am b/tests/Makefile.am
index 45908ce..7effa57 100644
--- a/tests/Makefile.am
+++ b/tests/Makefile.am
@@ -82,6 +82,7 @@ TESTS =                                               \
   fmbtest                                      \
   foad1                                                \
   grep-dev-null                                        \
+  grep-dev-null-out                            \
   grep-dir                                     \
   help-version                                 \
   high-bit-range                               \
diff --git a/tests/grep-dev-null-out b/tests/grep-dev-null-out
new file mode 100755
index 0000000..f30700d
--- /dev/null
+++ b/tests/grep-dev-null-out
@@ -0,0 +1,11 @@
+#!/bin/sh
+# Outputting to /dev/null.
+
+. "${srcdir=.}/init.sh"; path_prepend_ ../src
+
+require_timeout_
+
+${AWK-awk} 'BEGIN {while (1) print "x"}' </dev/null |
+  timeout 1 grep x >/dev/null || fail=1
+
+Exit $fail
diff --git a/tests/status b/tests/status
index 9de98df..2a2d6e0 100755
--- a/tests/status
+++ b/tests/status
@@ -47,9 +47,9 @@ else
                 fail=1
         fi
 
-        # should return 2 file not found
+        # should return 0 (found a match) or 2 (file not found)
         echo "abcd" | grep -E -s 'abc' - MMMMMMMM.MMM > /dev/null 2>&1
-        if test $? -ne 2 ; then
+        if test $? -ne 0 && test $? -ne 2 ; then
                 echo "Status: Wrong status code, test \#5 failed"
                 fail=1
         fi
-- 
2.5.5




--- End Message ---
--- Begin Message --- Subject: Re: [PROPOSED PATCH] grep: /dev/null output speedup Date: Sun, 1 May 2016 22:58:13 -0700 User-agent: Mozilla/5.0 (X11; Linux x86_64; rv:38.0) Gecko/20100101 Thunderbird/38.7.2
I have installed this and am closing the bug report.


--- End Message ---

reply via email to

[Prev in Thread] Current Thread [Next in Thread]