2

If I pipe data into grep AND pass the "-r" flag (recurse subdirs) AND pass the "--exclude-dir" flag (e.g. to skip ".git" directories), then it segfaults. If any one of these things is missing, then it's fine.

$ ls | grep -r --exclude-dir=\.git pattern
Segmentation fault

Does anyone else see this behaviour?

I'm using grep 2.11 (the latest) installed by Homebrew on OSX, because the built-in OSX grep is so old that it doesn't support features I use heavily, such as '--exclude-dir' itself.

You might wonder why I'm passing these flags, since they are both meaningless when grep is filtering stdin (as opposed to searching files), but the reason is that I have these flags specified in an alias, 'grp':

alias grp='grep -r --exclude-dir=\.git'

because I want them to be on-by-default every time I manually invoke grp from a command-line. My actual 'grp' contains many more flags than this, but these are the ones which are causing me trouble today.

Hence these flags are useful (and work fine) when I go:

grp pattern .

which I believe must be expanding to:

grep -r --exclude-dir=\.git pattern .

But the flags are still present when I use grep in it's "alternate-fire" mode, where it filters lines on stdin:

ll | grp pattern

which I believe must be expanding to:

ll | grep -r --exclude-dir=\.git pattern

and this is what segfaults. Removing either the '-r' or the '--exclude-dir', or the pipe on stdin, makes the segfault go away.

I took a look at the corefile produced and found this:

$ gdb grep /cores/core.31786
GNU gdb 6.3.50-20050815 (Apple version gdb-1515) (Sat Jan 15 08:33:48 UTC 2011)
...
This GDB was configured as "x86_64-apple-darwin"
...
#0  0x00007fff8897ac00 in strlen ()
(gdb) bt
#0  0x00007fff8897ac00 in strlen ()
#1  0x0000000100015576 in excluded_file_name (ex=0x1001005a0, f=0x0) at exclude.c:445
#2  0x0000000100012305 in grepdir (dir=0x0, stats=0x100048620) at main.c:1364
#3  0x0000000100014048 in main (argc=11, argv=0x7fff5fbff0b8) at main.c:2216

So it's segfaulting in strlen called from 'excluded_file_name'. That sounds relevant, but I don't know what to do with that information.

This arrangement used to work fine with grep from MacPorts (and on Ubuntu before that) so I figured my problem might be caused by Homebrew. So I tried compiling my own grep from gnu 2.11 source, but the behaviour persists. I can't go back to MacPorts - I had to switch to Homebrew for other reasons, and as I understand it, they don't play nicely together.

Incidentally, I don't like using GREP_OPTIONS environment variable to set my defaults, since it breaks any tools I run which invoke grep internally.

So, my questions are:

  • Does anyone else see this behaviour, or is it just me?
  • Can I stop grep from segfaulting? Or just understand more about why it's segfaulting?
  • How would I change my alias so that it removes '-r' from the command when stdin is coming from a pipe?

1 Answers1

1

Looks like it might be a regression related to the latest release:

** New features

If no file operand is given, and a command-line -r or equivalent option is given, grep now searches the working directory. Formerly grep ignored the -r and searched standard input nonrecursively. An -r found in GREP_OPTIONS does not have this new effect.

In other words, the behavior of -r changed, and maybe wasn't exhaustively tested before release. I'd post a bug report to them - It's probably more likely to result in a fix.

l0b0
  • 7,453