Revision: 325
http://vcs.pcre.org/viewvc?view=rev&revision=325
Author: ph10
Date: 2008-03-08 17:13:02 +0000 (Sat, 08 Mar 2008)
Log Message:
-----------
Add --include_dir and --exclude_dir to pcregrep.
Modified Paths:
--------------
code/trunk/ChangeLog
code/trunk/RunGrepTest
code/trunk/doc/pcregrep.1
code/trunk/pcregrep.c
Modified: code/trunk/ChangeLog
===================================================================
--- code/trunk/ChangeLog 2008-03-07 19:48:32 UTC (rev 324)
+++ code/trunk/ChangeLog 2008-03-08 17:13:02 UTC (rev 325)
@@ -26,6 +26,9 @@
pcregrep specification - which I improved to make it absolutely clear).
The action now is always to scan all levels of directory, and just
apply the include/exclude patterns to regular files.
+
+5. Added the --include_dir and --exclude_dir patterns to pcregrep, and used
+ --exclude_dir in the tests to avoid scanning .svn directories.
Version 7.6 28-Jan-08
Modified: code/trunk/RunGrepTest
===================================================================
--- code/trunk/RunGrepTest 2008-03-07 19:48:32 UTC (rev 324)
+++ code/trunk/RunGrepTest 2008-03-08 17:13:02 UTC (rev 325)
@@ -147,11 +147,11 @@
echo "RC=$?" >>testtry
echo "---------------------------- Test 35 -----------------------------" >>testtry
-(cd $srcdir; $valgrind $pcregrep -L -r --include=grepinputx 'fox' ./testdata) >>testtry
+(cd $srcdir; $valgrind $pcregrep -L -r --include=grepinputx --exclude_dir='^\.' 'fox' ./testdata) >>testtry
echo "RC=$?" >>testtry
echo "---------------------------- Test 36 -----------------------------" >>testtry
-(cd $srcdir; $valgrind $pcregrep -L -r --include=grepinput --exclude 'grepinput$' 'fox' ./testdata | sort) >>testtry
+(cd $srcdir; $valgrind $pcregrep -L -r --include=grepinput --exclude 'grepinput$' --exclude_dir='^\.' 'fox' ./testdata | sort) >>testtry
echo "RC=$?" >>testtry
echo "---------------------------- Test 37 -----------------------------" >>testtry
Modified: code/trunk/doc/pcregrep.1
===================================================================
--- code/trunk/doc/pcregrep.1 2008-03-07 19:48:32 UTC (rev 324)
+++ code/trunk/doc/pcregrep.1 2008-03-08 17:13:02 UTC (rev 325)
@@ -158,12 +158,22 @@
\fB--exclude\fP=\fIpattern\fP
When \fBpcregrep\fP is searching the files in a directory as a consequence of
the \fB-r\fP (recursive search) option, any regular files whose names match the
-pattern are excluded (subdirectories are not excluded; they are searched
-recursively). The pattern is a PCRE regular expression, and is matched against
-the final component of the file name (not the entire path). If a file name
-matches both \fB--include\fP and \fB--exclude\fP, it is excluded. There is no
-short form for this option.
+pattern are excluded. Subdirectories are not excluded by this option; they are
+searched recursively, subject to the \fB--exclude_dir\fP and
+\fB--include_dir\fP options. The pattern is a PCRE regular expression, and is
+matched against the final component of the file name (not the entire path). If
+a file name matches both \fB--include\fP and \fB--exclude\fP, it is excluded.
+There is no short form for this option.
.TP
+\fB--exclude_dir\fP=\fIpattern\fP
+When \fBpcregrep\fP is searching the contents of a directory as a consequence
+of the \fB-r\fP (recursive search) option, any subdirectories whose names match
+the pattern are excluded. (Note that the \fP--exclude\fP option does not affect
+subdirectories.) The pattern is a PCRE regular expression, and is matched
+against the final component of the name (not the entire path). If a
+subdirectory name matches both \fB--include_dir\fP and \fB--exclude_dir\fP, it
+is excluded. There is no short form for this option.
+.TP
\fB-F\fP, \fB--fixed-strings\fP
Interpret each pattern as a list of fixed strings, separated by newlines,
instead of as a regular expression. The \fB-w\fP (match as a word) and \fB-x\fP
@@ -215,12 +225,22 @@
\fB--include\fP=\fIpattern\fP
When \fBpcregrep\fP is searching the files in a directory as a consequence of
the \fB-r\fP (recursive search) option, only those regular files whose names
-match the pattern are included (but subdirectories are always included and
-searched recursively). The pattern is a PCRE regular expression, and is matched
-against the final component of the file name (not the entire path). If a file
-name matches both \fB--include\fP and \fB--exclude\fP, it is excluded. There is
-no short form for this option.
+match the pattern are included. Subdirectories are always included and searched
+recursively, subject to the \fP--include_dir\fP and \fB--exclude_dir\fP
+options. The pattern is a PCRE regular expression, and is matched against the
+final component of the file name (not the entire path). If a file name matches
+both \fB--include\fP and \fB--exclude\fP, it is excluded. There is no short
+form for this option.
.TP
+\fB--include_dir\fP=\fIpattern\fP
+When \fBpcregrep\fP is searching the contents of a directory as a consequence
+of the \fB-r\fP (recursive search) option, only those subdirectories whose
+names match the pattern are included. (Note that the \fB--include\fP option
+does not affect subdirectories.) The pattern is a PCRE regular expression, and
+is matched against the final component of the name (not the entire path). If a
+subdirectory name matches both \fB--include_dir\fP and \fB--exclude_dir\fP, it
+is excluded. There is no short form for this option.
+.TP
\fB-L\fP, \fB--files-without-match\fP
Instead of outputting lines from the files, just output the names of the files
that do not contain any lines that would have been output. Each file name is
@@ -438,6 +458,6 @@
.rs
.sp
.nf
-Last updated: 07 March 2008
+Last updated: 08 March 2008
Copyright (c) 1997-2008 University of Cambridge.
.fi
Modified: code/trunk/pcregrep.c
===================================================================
--- code/trunk/pcregrep.c 2008-03-07 19:48:32 UTC (rev 324)
+++ code/trunk/pcregrep.c 2008-03-08 17:13:02 UTC (rev 325)
@@ -139,9 +139,13 @@
static char *include_pattern = NULL;
static char *exclude_pattern = NULL;
+static char *include_dir_pattern = NULL;
+static char *exclude_dir_pattern = NULL;
static pcre *include_compiled = NULL;
static pcre *exclude_compiled = NULL;
+static pcre *include_dir_compiled = NULL;
+static pcre *exclude_dir_compiled = NULL;
static int after_context = 0;
static int before_context = 0;
@@ -181,15 +185,17 @@
/* Options without a single-letter equivalent get a negative value. This can be
used to identify them. */
-#define N_COLOUR (-1)
-#define N_EXCLUDE (-2)
-#define N_HELP (-3)
-#define N_INCLUDE (-4)
-#define N_LABEL (-5)
-#define N_LOCALE (-6)
-#define N_NULL (-7)
-#define N_LOFFSETS (-8)
-#define N_FOFFSETS (-9)
+#define N_COLOUR (-1)
+#define N_EXCLUDE (-2)
+#define N_EXCLUDE_DIR (-3)
+#define N_HELP (-4)
+#define N_INCLUDE (-5)
+#define N_INCLUDE_DIR (-6)
+#define N_LABEL (-7)
+#define N_LOCALE (-8)
+#define N_NULL (-9)
+#define N_LOFFSETS (-10)
+#define N_FOFFSETS (-11)
static option_item optionlist[] = {
{ OP_NODATA, N_NULL, NULL, "", " terminate options" },
@@ -222,6 +228,8 @@
{ OP_NODATA, 'r', NULL, "recursive", "recursively scan sub-directories" },
{ OP_STRING, N_EXCLUDE,&exclude_pattern, "exclude=pattern","exclude matching files when recursing" },
{ OP_STRING, N_INCLUDE,&include_pattern, "include=pattern","include matching files when recursing" },
+ { OP_STRING, N_EXCLUDE_DIR,&exclude_dir_pattern, "exclude_dir=pattern","exclude matching directories when recursing" },
+ { OP_STRING, N_INCLUDE_DIR,&include_dir_pattern, "include_dir=pattern","include matching directories when recursing" },
#ifdef JFRIEDL_DEBUG
{ OP_OP_NUMBER, 'S', &S_arg, "jeffS", "replace matched (sub)string with X" },
#endif
@@ -1361,8 +1369,9 @@
}
/* If the file is a directory, skip if skipping or if we are recursing, scan
-each file within it, subject to any include or exclude patterns that were set.
-The scanning code is localized so it can be made system-specific. */
+each file and directory within it, subject to any include or exclude patterns
+that were set. The scanning code is localized so it can be made
+system-specific. */
if ((sep = isdirectory(pathname)) != 0)
{
@@ -1387,7 +1396,17 @@
sprintf(buffer, "%.512s%c%.128s", pathname, sep, nextfile);
nflen = strlen(nextfile);
- if (!isdirectory(buffer))
+ if (isdirectory(buffer))
+ {
+ if (exclude_dir_compiled != NULL &&
+ pcre_exec(exclude_dir_compiled, NULL, nextfile, nflen, 0, 0, NULL, 0) >= 0)
+ continue;
+
+ if (include_dir_compiled != NULL &&
+ pcre_exec(include_dir_compiled, NULL, nextfile, nflen, 0, 0, NULL, 0) < 0)
+ continue;
+ }
+ else
{
if (exclude_compiled != NULL &&
pcre_exec(exclude_compiled, NULL, nextfile, nflen, 0, 0, NULL, 0) >= 0)
@@ -2292,6 +2311,30 @@
}
}
+if (exclude_dir_pattern != NULL)
+ {
+ exclude_dir_compiled = pcre_compile(exclude_dir_pattern, 0, &error, &errptr,
+ pcretables);
+ if (exclude_dir_compiled == NULL)
+ {
+ fprintf(stderr, "pcregrep: Error in 'exclude_dir' regex at offset %d: %s\n",
+ errptr, error);
+ goto EXIT2;
+ }
+ }
+
+if (include_dir_pattern != NULL)
+ {
+ include_dir_compiled = pcre_compile(include_dir_pattern, 0, &error, &errptr,
+ pcretables);
+ if (include_dir_compiled == NULL)
+ {
+ fprintf(stderr, "pcregrep: Error in 'include_dir' regex at offset %d: %s\n",
+ errptr, error);
+ goto EXIT2;
+ }
+ }
+
/* If there are no further arguments, do the business on stdin and exit. */
if (i >= argc)