Subject: bug#29666: Segfault at changing location

From: Jim Meyering <[email-masked]>
Date: Tue, 12 Dec 2017 09:47:17 -0800

On Mon, Dec 11, 2017 at 12:44 PM, Jeremy Feusi <[email-masked]> wrote:
> Hi,
> I am working on a project for school in which I use afl to find bugs in
> software and I decided to fuzz grep. In doing so I discovered a
> segfault. When using gdb, the location of the segfault varies, which
> puzzles me and so I cannot include any further information.
> The command to obtain this bug is:
> grep -o -E -f <seg-file>
> where <seg-file> is the file attached.
>
> I am using grep 3.1 on arch linux.
> cheers
> Jeremy

Thank you for the report.

This has been an issue since about grep-2.6.1.
It gave a proper diagnostic until 2.5.4:

  $ grep-2.5.4/bin/grep -E -f <(printf %080000d 0|tr 0 '(')
  grep-2.5.4/bin/grep: Unmatched ( or \(
  [Exit 2]

Starting in approximately 2.6.1 (I don't have 2.6.0 handy) it
would fail like this:

  $ grep-2.6.1/bin/grep -E -f <(printf %080000d 0|tr 0 '(')
  Segmentation fault (core dumped)

Using the latest with -P works fine:

  $ grep -P -f <(printf %080000d 0|tr 0 '(')
  grep: parentheses are too deeply nested
  [Exit 2]

Here's a nearly-complete patch to make grep diagnose the generic
"stack overflow" problem:
From 1751a1abf1ff26d5467e515c8da4dea7053f73c8 Mon Sep 17 00:00:00 2001
From: Jim Meyering <[email-masked]>
Date: Tue, 12 Dec 2017 09:05:55 -0800
Subject: [PATCH] grep: diagnose stack overflow rather than segfaulting

* bootstrap.conf (gnulib_modules): Add c-stack.
* src/grep.c: Include "c-stack.h".
(main): Call c_stack_action (NULL);
* tests/stack-overflow: New file.
* tests/Makefile.am (TESTS): Add name of new file.
* NEWS (Improvements): Mention it.
Reported by Jeremy Feusi in https://bugs.gnu.org/29666.
---
 NEWS                 |  4 ++++
 bootstrap.conf       |  1 +
 src/grep.c           |  2 ++
 tests/Makefile.am    |  1 +
 tests/stack-overflow | 16 ++++++++++++++++
 5 files changed, 24 insertions(+)
 create mode 100755 tests/stack-overflow

diff --git a/NEWS b/NEWS
index 51a1529..16c36d3 100644
--- a/NEWS
+++ b/NEWS
@@ -13,6 +13,10 @@ GNU grep NEWS                                    -*- outline -*-
   The --recursive (-r) option no longer fails on MS-Windows.
   [bug introduced in grep 2.11]

+** Improvements
+
+  grep now diagnoses stack overflow.  Before, it would often simply segfault.
+

 * Noteworthy changes in release 3.1 (2017-07-02) [stable]

diff --git a/bootstrap.conf b/bootstrap.conf
index 73f1573..185cd19 100644
--- a/bootstrap.conf
+++ b/bootstrap.conf
@@ -27,6 +27,7 @@ alloca
 announce-gen
 argmatch
 c-ctype
+c-stack
 closeout
 dfa
 do-release-commit-and-tag
diff --git a/src/grep.c b/src/grep.c
index ad5cfa2..a444cf3 100644
--- a/src/grep.c
+++ b/src/grep.c
@@ -30,6 +30,7 @@

 #include "argmatch.h"
 #include "c-ctype.h"
+#include "c-stack.h"
 #include "closeout.h"
 #include "colorize.h"
 #include "die.h"
@@ -2450,6 +2451,7 @@ main (int argc, char **argv)
   init_localeinfo (&localeinfo);

   atexit (clean_up_stdout);
+  c_stack_action (NULL);

   last_recursive = 0;

diff --git a/tests/Makefile.am b/tests/Makefile.am
index 66fb461..4aca63b 100644
--- a/tests/Makefile.am
+++ b/tests/Makefile.am
@@ -151,6 +151,7 @@ TESTS =						\
   skip-read					\
   spencer1					\
   spencer1-locale				\
+  stack-overflow				\
   status					\
   surrogate-pair				\
   symlink					\
diff --git a/tests/stack-overflow b/tests/stack-overflow
new file mode 100755
index 0000000..2042ebc
--- /dev/null
+++ b/tests/stack-overflow
@@ -0,0 +1,16 @@
+#!/bin/sh
+# Ensure a stack overflow no longer segfaults
+
+. "${srcdir=.}/init.sh"; path_prepend_ ../src
+
+# Too many open parentheses.
+printf %080000d 0|tr 0 '(' > in || framework_failure_
+echo grep: stack overflow > exp || framework_failure_
+
+fail=0
+returns_ 2 grep -E -f in >out 2>err || fail=1
+
+compare /dev/null out || fail=1
+compare exp err || fail=1
+
+Exit $fail
-- 
2.14.1.729.g59c0ea183