Skip site navigation (1)Skip section navigation (2)
Date:      Thu, 24 Jul 2008 15:24:21 GMT
From:      Gabor Kovesdan <gabor@FreeBSD.org>
To:        Perforce Change Reviews <perforce@freebsd.org>
Subject:   PERFORCE change 145816 for review
Message-ID:  <200807241524.m6OFOLEh067746@repoman.freebsd.org>

next in thread | raw e-mail | index | archive | help
http://perforce.freebsd.org/chv.cgi?CH=145816

Change 145816 by gabor@gabor_server on 2008/07/24 15:24:14

	IFC

Affected files ...

.. //depot/projects/soc2008/gabor_textproc/src/share/mk/bsd.sys.mk#2 integrate
.. //depot/projects/soc2008/gabor_textproc/src/usr.bin/grep/Makefile#2 integrate
.. //depot/projects/soc2008/gabor_textproc/src/usr.bin/grep/file.c#2 integrate
.. //depot/projects/soc2008/gabor_textproc/src/usr.bin/grep/grep.1#2 integrate
.. //depot/projects/soc2008/gabor_textproc/src/usr.bin/grep/grep.c#2 integrate
.. //depot/projects/soc2008/gabor_textproc/src/usr.bin/grep/grep.h#2 integrate
.. //depot/projects/soc2008/gabor_textproc/src/usr.bin/grep/nls/C.msg#2 integrate
.. //depot/projects/soc2008/gabor_textproc/src/usr.bin/grep/nls/hu_HU.ISO8859-2.msg#2 integrate
.. //depot/projects/soc2008/gabor_textproc/src/usr.bin/grep/nls/pt_BR.ISO8859-1.msg#2 integrate
.. //depot/projects/soc2008/gabor_textproc/src/usr.bin/grep/util.c#2 integrate

Differences ...

==== //depot/projects/soc2008/gabor_textproc/src/share/mk/bsd.sys.mk#2 (text+ko) ====

@@ -1,4 +1,4 @@
-# $FreeBSD: src/share/mk/bsd.sys.mk,v 1.45 2008/06/25 21:33:28 ru Exp $
+# $FreeBSD: src/share/mk/bsd.sys.mk,v 1.47 2008/07/23 06:14:21 imp Exp $
 #
 # This file contains common settings used for building FreeBSD
 # sources.
@@ -74,7 +74,8 @@
 CWARNFLAGS	+=	-Wno-unknown-pragmas
 .endif
 
-.if ${MK_SSP} != "no" && ${CC} != "icc" && ${MACHINE_ARCH} != "ia64"
+.if ${MK_SSP} != "no" && ${CC} != "icc" && ${MACHINE_ARCH} != "ia64" && \
+	${MACHINE_ARCH} != "arm" && ${MACHINE_ARCH} != "mips"
 # Don't use -Wstack-protector as it breaks world with -Werror.
 SSP_CFLAGS	?=	-fstack-protector
 CFLAGS		+=	${SSP_CFLAGS}

==== //depot/projects/soc2008/gabor_textproc/src/usr.bin/grep/Makefile#2 (text+ko) ====

@@ -20,6 +20,13 @@
 LDADD=	-lz -lbz2
 DPADD=	${LIBZ} ${LIBBZ2}
 
+.if defined(WITH_PCRE)
+CFLAGS+=	-DWITH_PCRE=yes -I/usr/local/include
+LDFLAGS+=	-L/usr/local/lib
+LDADD+=	-lpcre
+DPADD+=	/usr/local/lib/libpcre.a
+.endif
+
 .if !defined(WITHOUT_NLS)
 NLS=	hu_HU.ISO8859-2
 NLS+=	pt_BR.ISO8859-1

==== //depot/projects/soc2008/gabor_textproc/src/usr.bin/grep/file.c#2 (text+ko) ====

@@ -1,5 +1,6 @@
 /*-
  * Copyright (c) 1999 James Howard and Dag-Erling Coďdan Smřrgrav
+ * Copyright (C) 2008 Gabor Kovesdan <gabor@FreeBSD.org>
  * All rights reserved.
  *
  * Redistribution and use in source and binary forms, with or without
@@ -49,39 +50,132 @@
 
 #include "grep.h"
 
-static char	 fname[MAXPATHLEN];
+static char	 fname[MAXPATHLEN];	/* file name */
+
+/* Some global variable for the buffering and reading. */
+static char	*lnbuf;
+static size_t	 lnbuflen;
+static char	 binbuf[BUFSIZ * 4];
+static int	 binbufsiz;
+char		*binbufptr;
+static int	 bzerr;
+
+#define iswbinary(ch)	(!iswspace((ch)) && iswcntrl((ch)) && (ch != L'\b') && (ch != L'\0'))
+
+/*
+ * Returns a single character according to the file type.
+ * Returns -1 on failure.
+ */
+int
+grep_fgetc(struct file *f)
+{
+	char	 c;
 
-#define iswbinary(ch)	(!iswspace((ch)) && iswcntrl((ch)))
+	switch (filebehave) {
+	case FILE_STDIO:
+		return (fgetc(f->f));
+	case FILE_GZIP:
+		return (gzgetc(f->gzf));
+	case FILE_BZIP:
+		BZ2_bzRead(&bzerr, f->bzf, &c, 1);
+		if (bzerr == BZ_STREAM_END)
+			return (-1);
+		else if (bzerr != BZ_SEQUENCE_ERROR && bzerr != BZ_OK)
+			errx(2, getstr(16));
+		return (c);
+	}
+	return (-1);
+}
 
+/*
+ * Returns true if the file position is a EOF, returns false
+ * otherwise.
+ */
 int
-bin_file(struct file *f)
+grep_feof(struct file *f)
+{
+
+	switch (filebehave) {
+	case FILE_STDIO:
+		return (feof(f->f));
+	case FILE_GZIP:
+		return (gzeof(f->gzf));
+	case FILE_BZIP:
+		return (bzerr == BZ_STREAM_END);
+	}
+	return (1);
+}
+
+/*
+ * At the first call, fills in an internal buffer and checks if the given
+ * file is a binary file and sets the binary flag accordingly.  Then returns
+ * a single line and sets len to the length of the returned line.
+ * At any other call returns a single line either from the internal buffer
+ * or from the file if the buffer is exhausted and sets len to the length
+ * of the line.
+ */
+char *
+grep_fgetln(struct file *f, size_t *len)
 {
-	wint_t	 ch = L'\0';
-	size_t	 i;
-	int	 ret = 0;
+	int		 i = 0;
+	char		 ch;
+	size_t		 size;
+	wchar_t		 wbinbuf[BUFSIZ];
+	const char	*src = binbuf;
+	mbstate_t	 mbs;
 
-	if (f->noseek)
-		return (0);
+	/* Fill in the buffer if it is empty. */
+	if (binbufptr == NULL) {
+		/* Only pre-read to the buffer if we need the binary check. */
+		if (binbehave != BINFILE_TEXT) {
+			for (; (i < (BUFSIZ * sizeof(wint_t))) && !grep_feof(f); i++) {
+				ch = grep_fgetc(f);
+				binbuf[i] = ch;
+			}
+			binbufsiz = i;
+			binbufptr = binbuf;
 
-	if (fseek(f->f, 0L, SEEK_SET) == -1)
-		return (0);
+			/* Convert at most (BUFSIZ * sizeof(wint_t)) characters or
+				(BUFSIZ - 1) bytes to wide character string. */
+			size = mbsnrtowcs(wbinbuf, &src, BUFSIZ * sizeof(wint_t), BUFSIZ - 1, &mbs);
+			f->binary = 0;
+			for (; size > 0; size--)
+				if (iswbinary(wbinbuf[size])) {
+					f->binary = 1;
+					break;
+				}
+			
+		} else {
+			binbufsiz = i;
+			binbufptr = binbuf;
+		}
+	}
 
-	for (i = 0; i <= BUFSIZ; i++) {
-		if ((ch = fgetwc(f->f)) == WEOF) {
-			if (errno == EILSEQ)
-				ret = 1;
-			break;
+	/* Read a line whether from the buffer or from the file itself. */
+	for (i = 0; !grep_feof(f); i++) {
+		if (binbufptr == &binbuf[binbufsiz]) {
+			ch = grep_fgetc(f);
+		} else {
+			ch = binbufptr[0];
+			binbufptr++;
+		}
+		if (i >= lnbuflen) {
+			lnbuflen *= 2;
+			lnbuf = grep_realloc(lnbuf, ++lnbuflen);
 		}
-		if (iswbinary(ch)) {
-			ret = 1;
+		if (ch == '\n')
 			break;
-		}
+		lnbuf[i] = ch;
 	}
-
-	rewind(f->f);
-	return (ret);
+	if (grep_feof(f) && (i == 0))
+		return (NULL);
+	*len = i;
+	return (lnbuf);
 }
 
+/*
+ * Opens the standard input for processing.
+ */
 struct file *
 grep_stdin_open(void)
 {
@@ -91,7 +185,6 @@
 
 	f = grep_malloc(sizeof *f);
 
-	f->noseek = isatty(STDIN_FILENO);
 	if ((f->f = fdopen(STDIN_FILENO, "r")) != NULL)
 		return (f);
 
@@ -99,67 +192,54 @@
 	return (NULL);
 }
 
+/*
+ * Opens a normal, a gzipped or a bzip2 compressed file for processing.
+ */
 struct file *
 grep_open(char *path)
 {
 	struct file	*f;
-	char		*templ;
-	int		 tempfd;
 
 	snprintf(fname, sizeof fname, "%s", path);
 
 	f = grep_malloc(sizeof *f);
-	f->noseek = 0;
+
+	switch (filebehave) {
+	case FILE_STDIO:
+		if ((f->f = fopen(path, "r")) != NULL)
+			return (f);
+		break;
+	case FILE_GZIP:
+		if ((f->gzf = gzopen(fname, "r")) != NULL)
+			return (f);
+		break;
+	case FILE_BZIP:
+		if ((f->bzf = BZ2_bzopen(fname, "r")) != NULL)
+			return (f);
+		break;
+	}
 
-	if (Zflag || Jflag) {
-		templ = grep_malloc(sizeof(char) * 15);
-		strlcpy(templ, "/tmp/grep.XXXXXXXX", 14);
-		if ((tempfd = mkstemp(templ)) == -1)
-			err(2, NULL);
-		free(templ);
-		if (Zflag) {
-			gzFile	*gzf;
-			char	 buf[BUFSIZ];
-			int	 i;
+	free(f);
+	return (NULL);
+}
 
-			if ((gzf = gzopen(fname, "r")) == NULL)
-				err(2, NULL);
-			while ((i = gzread(gzf, buf, BUFSIZ)) > 0) {
-				write(tempfd, buf, BUFSIZ);
-			}
-			gzclose(gzf);
-			lseek(tempfd, 0L, SEEK_SET);
-			if ((f->f = fdopen(tempfd, "r")) != NULL)
-				return (f);
-			else
-				return (NULL);
-		} else {
-			BZFILE	*bzf;
-			char	 buf[BUFSIZ];
-			int	 bzerror;
-			FILE	*file;
+/*
+ * Closes a normal, a gzipped or a bzip2 compressed file.
+ */
+void
+grep_close(struct file *f)
+{
 
-			if ((file = fopen(fname, "r")) == NULL)
-				err(2, NULL);
-			if ((bzf = BZ2_bzReadOpen(&bzerror, file, 0, 0, NULL, 0)) == NULL)
-				err(2, NULL);
-			do {
-				BZ2_bzRead(&bzerror, bzf, buf, BUFSIZ);
-				write(tempfd, buf, BUFSIZ);
-			} while (bzerror == BZ_OK);
-			BZ2_bzReadClose(&bzerror, bzf);
-			fclose(file);
-			lseek(tempfd, 0L, SEEK_SET);
-			if ((f->f = fdopen(tempfd, "r")) != NULL)
-				return (f);
-			else
-				return (NULL);
-		}
+	switch (filebehave) {
+	case FILE_STDIO:
+		fclose(f->f);
+		break;
+	case FILE_GZIP:
+		gzclose(f->gzf);
+		break;
+	case FILE_BZIP:
+		BZ2_bzclose(f->bzf);
+		break;
 	}
-
-	if ((f->f = fopen(path, "r")) != NULL)
-		return (f);
-
 	free(f);
-	return (NULL);
 }

==== //depot/projects/soc2008/gabor_textproc/src/usr.bin/grep/grep.1#2 (text+ko) ====

@@ -29,7 +29,7 @@
 .\"
 .\"	@(#)grep.1	8.3 (Berkeley) 4/18/94
 .\"
-.Dd 16 Jun, 2008
+.Dd 8 Jul, 2008
 .Dt GREP 1
 .Os
 .Sh NAME
@@ -39,7 +39,7 @@
 .Sh SYNOPSIS
 .Nm grep
 .Bk -words
-.Op Fl abcdDEFGHhIiJLlmnOoPqRSsUVvwxZ
+.Op Fl abcdDEFGHhIiJLlmnOopqRSsUVvwxZ
 .Op Fl A Ar num
 .Op Fl B Ar num
 .Op Fl C Ns Op Ar num
@@ -281,7 +281,7 @@
 The default is not to follow symbolic links.
 .It Fl o, Fl Fl only-matching
 Prints only the matching part of the lines.
-.It Fl P
+.It Fl p
 If
 .Fl R
 is specified, no symbolic links are followed.

==== //depot/projects/soc2008/gabor_textproc/src/usr.bin/grep/grep.c#2 (text+ko) ====

@@ -1,5 +1,6 @@
 /*-
  * Copyright (c) 1999 James Howard and Dag-Erling Coďdan Smřrgrav
+ * Copyright (C) 2008 Gabor Kovesdan <gabor@FreeBSD.org>
  * All rights reserved.
  *
  * Redistribution and use in source and binary forms, with or without
@@ -42,8 +43,8 @@
 #include <err.h>
 #include <errno.h>
 #include <getopt.h>
+#include <libgen.h>
 #include <locale.h>
-#include <regex.h>
 #include <stdio.h>
 #include <stdlib.h>
 #include <string.h>
@@ -56,6 +57,10 @@
 nl_catd	 catalog;
 #endif
 
+/*
+ * Default messags to use when NLS is disabled or no catalogue
+ * is found.
+ */
 char	*errstr[] = {
 	"",
 /* 1*/	"(standard input)",
@@ -67,42 +72,52 @@
 /* 7*/	"\t[--null] [pattern] [file ...]\n",
 /* 8*/	"parentheses not balanced",
 /* 9*/	"context out of range",
-/*10*/	"FreeBSD grep 2.5.1\n",
+/*10*/	"%s (BSD grep) %s\n",
 /*11*/	"unknown --binary-files option",
 /*12*/	"Binary file %s matches\n",
-/*12*/	"value out of range",
-/*13*/	"unknown -d or --directory option",
-/*14*/	"unknown --color option"
+/*13*/	"value out of range",
+/*14*/	"unknown -d or --directory option",
+/*15*/	"unknown --color option",
+/*16*/	"cannot read bzip2 compressed file",
+/*17*/	"PCRE is not enabled in this version of grep. "
+	"To enable this feature, please install libpcre and"
+	"recompile grep with WITH_PCRE set."
 };
 
 /* Flags passed to regcomp() and regexec() */
 int		 cflags;
 int		 eflags = REG_STARTEND;
 
-int		 matchall;	/* shortcut */
+/* Shortcut for matching all cases like empty regex */
+int		 matchall;
+
+/* Searching patterns */
 int		 patterns, pattern_sz;
 char		**pattern;
 regex_t		*r_pattern;
+#ifdef WITH_PCRE
+pcre		**perl_pattern;
+#endif
 
+/* Filename exclusion/inclusion patterns */
+int		 epatterns, epattern_sz;
+char		**epattern;
+
 /* For regex errors  */
 char	 re_error[RE_ERROR_BUF + 1];
 
 /* Command-line flags */
 unsigned long long Aflag;	/* -A x: print x lines trailing each match */
 unsigned long long Bflag;	/* -B x: print x lines leading each match */
-int	 Eflag;		/* -E: interpret pattern as extended regexp */
-int	 Fflag;		/* -F: interpret pattern as list of fixed strings */
-int	 Gflag;		/* -G: interpret pattern as basic regexp */
 int	 Hflag;		/* -H: always print file name */
-int	 Jflag;		/* -J: grep in bzipped file */
 int	 Lflag;		/* -L: only show names of files with no matches */
-int	 Zflag;		/* -Z: grep in gzipped file */
 int	 bflag;		/* -b: show block numbers for each match */
 int	 cflag;		/* -c: only show a count of matching lines */
 int	 hflag;		/* -h: don't print filename headers */
 int	 iflag;		/* -i: ignore case */
 int	 lflag;		/* -l: only show names of files with matches */
 int	 mflag;		/* -m x: stop reading the files after x matches */
+unsigned long long mcount;	/* count for -m */
 int	 nflag;		/* -n: show line numbers in front of matching lines */
 int	 oflag;		/* -o: print only matching part */
 int	 qflag;		/* -q: quiet mode (don't output anything) */
@@ -112,15 +127,17 @@
 int	 xflag;		/* -x: pattern must match entire line */
 int	 lbflag;	/* --line-buffered */
 int	 nullflag;	/* --null */
+int	 exclflag;	/* --exclude */
+int	 inclflag;	/* --include */
 char	*label;		/* --label */
 char	*color;		/* --color */
-unsigned long long mcount;	/* count for -m */
+int	 grepbehave = GREP_BASIC;	/* -EFGP: type of the regex */
+int	 binbehave = BINFILE_BIN;	/* -aIU: handling of binary files */
+int	 filebehave = FILE_STDIO;	/* -JZ: normal, gzip or bzip2 file */
+int	 devbehave = DEV_GREP;		/* -D: handling of devices */
+int	 dirbehave = DIR_GREP;		/* -dRr: handling of directories */
+int	 linkbehave = LINK_GREP;	/* -OpS: handling of symlinks */
 
-int	 binbehave = BINFILE_BIN;
-int	 devbehave = DEV_GREP;
-int	 dirbehave = DIR_GREP;
-int	 linkbehave = LINK_GREP;
-
 enum {
 	BIN_OPT = CHAR_MAX + 1,
 	COLOR_OPT,
@@ -128,7 +145,9 @@
 	MMAP_OPT,
 	LINEBUF_OPT,
 	LABEL_OPT,
-	NULL_OPT
+	NULL_OPT,
+	R_EXCLUDE_OPT,
+	R_INCLUDE_OPT
 };
 
 /* Housekeeping */
@@ -139,6 +158,9 @@
 
 extern char	*__progname;
 
+/*
+ * Prints usage information and returns 2.
+ */
 static void
 usage(void)
 {
@@ -150,7 +172,7 @@
 	exit(2);
 }
 
-static char	*optstr = "0123456789A:B:C:D:EFGHIJLOPSRUVZabcd:e:f:hilm:noqrsuvwxy";
+static char	*optstr = "0123456789A:B:C:D:EFGHIJLOPSRUVZabcd:e:f:hilm:nopqrsuvwxy";
 
 struct option long_options[] =
 {
@@ -162,6 +184,8 @@
 	{"null",		no_argument,		NULL, NULL_OPT},
 	{"color",		optional_argument,	NULL, COLOR_OPT},
 	{"colour",		optional_argument,	NULL, COLOR_OPT},
+	{"exclude",		required_argument,	NULL, R_EXCLUDE_OPT},
+	{"include",		required_argument,	NULL, R_INCLUDE_OPT},
 	{"after-context",	required_argument,	NULL, 'A'},
 	{"text",		no_argument,		NULL, 'a'},
 	{"before-context",	required_argument,	NULL, 'B'},
@@ -184,6 +208,7 @@
 	{"max-count",		required_argument,	NULL, 'm'},
 	{"line-number",		no_argument,		NULL, 'n'},
 	{"only-matching",	no_argument,		NULL, 'o'},
+	{"perl-regexp",		no_argument,		NULL, 'P'},
 	{"quiet",		no_argument,		NULL, 'q'},
 	{"silent",		no_argument,		NULL, 'q'},
 	{"recursive",		no_argument,		NULL, 'r'},
@@ -198,15 +223,19 @@
 	{NULL,			no_argument,		NULL, 0}
 };
 
-
+/*
+ * Adds a searching pattern to the internal array.
+ */
 static void
 add_pattern(char *pat, size_t len)
 {
+
+	/* Check if we can do a shortcut */
 	if (len == 0 || matchall) {
 		matchall = 1;
 		return;
 	}
-
+	/* Increase size if necessary */
 	if (patterns == pattern_sz) {
 		pattern_sz *= 2;
 		pattern = grep_realloc(pattern, ++pattern_sz * sizeof(*pattern));
@@ -214,20 +243,20 @@
 	if (len > 0 && pat[len - 1] == '\n')
 		--len;
 	/* pat may not be NUL-terminated */
-	if (wflag && !Fflag) {
+	if (wflag && !(grepbehave == GREP_FIXED)) {
 		int bol = 0, eol = 0, extra;
 		if (pat[0] == '^')
 			bol = 1;
 		if (len > 0 && pat[len - 1] == '$')
 			eol = 1;
-		extra = Eflag ? 2 : 4;
+		extra = (grepbehave == GREP_EXTENDED) ? 2 : 4;
 		pattern[patterns] = grep_malloc(len + 15 + extra);
 		snprintf(pattern[patterns], len + 15 + extra,
 		   "%s[[:<:]]%s%.*s%s[[:>:]]%s",
 		    bol ? "^" : "",
-		    Eflag ? "(" : "\\(",
+		    (grepbehave == GREP_EXTENDED) ? "(" : "\\(",
 		    (int)len - bol - eol, pat + bol,
-		    Eflag ? ")" : "\\)",
+		    (grepbehave == GREP_EXTENDED) ? ")" : "\\)",
 		    eol ? "$" : "");
 		len += 14 + extra;
 	} else {
@@ -238,6 +267,29 @@
 	++patterns;
 }
 
+/*
+ * Adds an include/exclude pattern to the internal array.
+ */
+static void
+add_epattern(char *pat, size_t len)
+{
+
+	/* Increase size if necessary */
+	if (epatterns == epattern_sz) {
+		epattern_sz *= 2;
+		epattern = grep_realloc(epattern, ++epattern_sz * sizeof(*epattern));
+	}
+	if (len > 0 && pat[len - 1] == '\n')
+		 --len;
+	epattern[epatterns] = grep_malloc(len + 1);
+	memcpy(epattern[epatterns], pat, len);
+	epattern[epatterns][len] = '\0';
+	++epatterns;
+}
+
+/*
+ * Reads searching patterns from a file and adds them with add_pattern().
+ */
 static void
 read_patterns(const char *fn)
 {
@@ -267,27 +319,30 @@
 	catalog = catopen("grep", NL_CAT_LOCALE);
 #endif
 
+	/* Check what is the program name of the binary.  In this
+	   way we can have all the funcionalities in one binary
+	   without the need of scripting and using ugly hacks. */
 	switch (__progname[0]) {
 	case 'e':
-		Eflag++;
+		grepbehave = GREP_EXTENDED;
 		break;
 	case 'f':
-		Fflag++;
+		grepbehave = GREP_FIXED;
 		break;
 	case 'g':
-		Gflag++;
+		grepbehave = GREP_BASIC;
 		break;
 	case 'z':
-		Zflag++;
+		filebehave = FILE_GZIP;
 		switch(__progname[1]) {
 		case 'e':
-			Eflag++;
+			grepbehave = GREP_EXTENDED;
 			break;
 		case 'f':
-			Fflag++;
+			grepbehave = GREP_FIXED;
 			break;
 		case 'g':
-			Gflag++;
+			grepbehave = GREP_BASIC;
 			break;
 		}
 		break;
@@ -349,24 +404,21 @@
 				errx(2, getstr(13));
 			break;
 		case 'E':
-			Fflag = Gflag = 0;
-			Eflag++;
+			grepbehave = GREP_EXTENDED;
 			break;
 		case 'e':
 			add_pattern(optarg, strlen(optarg));
 			needpattern = 0;
 			break;
 		case 'F':
-			Eflag = Gflag = 0;
-			Fflag++;
+			grepbehave = GREP_FIXED;
 			break;
 		case 'f':
 			read_patterns(optarg);
 			needpattern = 0;
 			break;
 		case 'G':
-			Eflag = Fflag = 0;
-			Gflag++;
+			grepbehave = GREP_BASIC;
 			break;
 		case 'H':
 			Hflag++;
@@ -384,8 +436,7 @@
 			cflags |= REG_ICASE;
 			break;
 		case 'J':
-			Zflag = 0;
-			Jflag++;
+			filebehave = FILE_BZIP;
 			break;
 		case 'L':
 			lflag = 0;
@@ -411,6 +462,9 @@
 			oflag++;
 			break;
 		case 'P':
+			grepbehave = GREP_PERL;
+			break;
+		case 'p':
 			linkbehave = LINK_SKIP;
 			break;
 		case 'q':
@@ -435,7 +489,7 @@
 			/* noop, compatibility */
 			break;
 		case 'V':
-			printf(getstr(10));
+			printf(getstr(10), __progname, VERSION);
 			exit(0);
 		case 'v':
 			vflag = 1;
@@ -447,8 +501,7 @@
 			xflag = 1;
 			break;
 		case 'Z':
-			Jflag = 0;
-			Zflag++;
+			filebehave = FILE_GZIP;
 			break;
 		case BIN_OPT:
 			if (strcmp("binary", optarg) == 0)
@@ -470,7 +523,7 @@
 			} else if (strcmp("never", optarg) == 0)
 				color = NULL;
 			else
-				errx(2, getstr(14));
+				errx(2, getstr(15));
 			break;
 		case LABEL_OPT:
 			label = optarg;
@@ -481,6 +534,20 @@
 		case NULL_OPT:
 			nullflag = 1;
 			break;
+		case R_INCLUDE_OPT:
+			if (dirbehave != DIR_RECURSE)
+				usage();
+			inclflag = 1;
+			exclflag = 0;
+			add_epattern(basename(optarg), strlen(basename(optarg)));
+			break;
+		case R_EXCLUDE_OPT:
+			if (dirbehave != DIR_RECURSE)
+				usage();
+			inclflag = 0;
+			exclflag = 1;
+			add_epattern(basename(optarg), strlen(basename(optarg)));
+			break;
 		case HELP_OPT:
 		default:
 			usage();
@@ -492,29 +559,62 @@
 	argc -= optind;
 	argv += optind;
 
+	/* Fail if we don't have any pattern */
 	if (argc == 0 && needpattern)
 		usage();
 
+	/* Process patterns from command line */
 	if (argc != 0 && needpattern) {
 		add_pattern(*argv, strlen(*argv));
 		--argc;
 		++argv;
 	}
 
-	if (Fflag)
+	switch (grepbehave) {
+	case GREP_FIXED:
 		cflags |= REG_NOSPEC;
-	else if (Gflag)
+		break;
+	case GREP_BASIC:
 		cflags |= REG_BASIC;
-	else if (Eflag)
+		break;
+	case GREP_EXTENDED:
 		cflags |= REG_EXTENDED;
-	r_pattern = grep_calloc(patterns, sizeof(*r_pattern));
-	for (i = 0; i < patterns; ++i) {
-		c = regcomp(&r_pattern[i], pattern[i], cflags);
-		if (c != 0) {
-			regerror(c, &r_pattern[i], re_error,
-			    RE_ERROR_BUF);
-			errx(2, "%s", re_error);
+		break;
+	case GREP_PERL:
+#ifndef WITH_PCRE
+		errx(2, getstr(17));
+#endif
+		break;
+	default:
+		/* NOTREACHED */
+		usage();
+	}
+	if (grepbehave != GREP_PERL) {
+		/* Compile regexes with regcomp() */
+		r_pattern = grep_calloc(patterns, sizeof(*r_pattern));
+		for (i = 0; i < patterns; ++i) {
+			c = regcomp(&r_pattern[i], pattern[i], cflags);
+			if (c != 0) {
+				regerror(c, &r_pattern[i], re_error,
+				    RE_ERROR_BUF);
+				errx(2, "%s", re_error);
+			}
+		}
+	} else {
+#ifdef WITH_PCRE
+		/* Compile Perl regexes with pcre_compile() */
+		perl_pattern = grep_calloc(patterns, sizeof(perl_pattern));
+		for (i = 0; i < patterns; ++i) {
+			char	**err_msg = NULL;
+			int	erroff;
+
+			perl_pattern[i] = pcre_compile(pattern[i], 0, (const char **)err_msg, &erroff, NULL);
+			if (perl_pattern[i] != NULL)
+				errx(2, "wrong PCRE: %s", err_msg[0]);
 		}
+#else
+		;
+#endif
 	}
 
 	if (lbflag)
@@ -536,6 +636,8 @@
 	catclose(catalog);
 #endif
 
+	/* Find out the correct return value according to the
+	   results and the command line option. */
 	if (c) {
 		if (notfound && qflag)
 			exit(0);

==== //depot/projects/soc2008/gabor_textproc/src/usr.bin/grep/grep.h#2 (text+ko) ====

@@ -26,13 +26,15 @@
  * SUCH DAMAGE.
  */
 
-#include <sys/types.h>
-#include <sys/limits.h>
-
+#include <bzlib.h>
 #include <regex.h>
 #include <stdio.h>
 #include <zlib.h>
 
+#ifdef WITH_PCRE
+#include <pcre.h>
+#endif
+
 #ifdef WITHOUT_NLS
 #define getstr(n)	 errstr[n]
 #else
@@ -44,11 +46,21 @@
 
 extern char		*errstr[];
 
+#define VERSION		"2.5.1-FreeBSD"
+
+#define GREP_FIXED	0
+#define GREP_BASIC	1
+#define GREP_EXTENDED	2
+#define GREP_PERL	3
 
 #define BINFILE_BIN	0
 #define BINFILE_SKIP	1
 #define BINFILE_TEXT	2
 
+#define FILE_STDIO	0
+#define FILE_GZIP	1
+#define FILE_BZIP	2
+
 #define DIR_GREP	0
 #define DIR_SKIP	1
 #define DIR_RECURSE	2
@@ -63,9 +75,11 @@
 #define MAX_LINE_MATCHES	32
 
 struct file {
-	int		 noseek;
+	int		 binary;
 	FILE		*f;
 	struct mmfile	*mmf;
+	gzFile		*gzf;
+	BZFILE		*bzf;
 };
 
 struct str {
@@ -80,16 +94,22 @@
 extern int	 cflags, eflags;
 
 /* Command line flags */
-extern int	 Eflag, Fflag, Gflag, Hflag, Jflag, Lflag, Zflag,
+extern int	 Eflag, Fflag, Gflag, Hflag, Lflag,
 		 bflag, cflag, hflag, iflag, lflag, mflag, nflag, oflag,
-		 qflag, sflag, vflag, wflag, xflag, nullflag;
+		 qflag, sflag, vflag, wflag, xflag;
+extern int	 nullflag, exclflag, inclflag;
 extern unsigned long long Aflag, Bflag, mcount;
 extern char	*color, *label;
-extern int	 binbehave, devbehave, dirbehave, linkbehave;
+extern int	 grepbehave, binbehave, filebehave, devbehave, dirbehave, linkbehave;
+
+extern int	 first, prev, matchall, patterns, epatterns, tail, notfound;
+extern char    **pattern, **epattern;
+extern regex_t	*r_pattern, *er_pattern;
+
+#ifdef WITH_PCRE
+extern pcre	**perl_pattern;
+#endif
 
-extern int	 first, prev, matchall, patterns, tail, notfound;
-extern char    **pattern;
-extern regex_t	*r_pattern;
 
 /* For regex errors  */
 #define RE_ERROR_BUF	512
@@ -110,6 +130,11 @@
 void	 clearqueue(void);
 
 /* file.c */
-int		 bin_file(struct file * f);
+char		*binbufptr;
+
+void		 grep_close(struct file *f);
 struct file	*grep_stdin_open(void);
 struct file	*grep_open(char *path);
+int		 grep_feof(struct file *f);
+int		 grep_fgetc(struct file *f);
+char		*grep_fgetln(struct file *f, size_t *len);

==== //depot/projects/soc2008/gabor_textproc/src/usr.bin/grep/nls/C.msg#2 (text+ko) ====

@@ -11,9 +11,11 @@
 7 "\t[--null] [pattern] [file ...]\n"
 8 "parentheses not balanced"
 9 "context out of range"
-10 "FreeBSD grep 2.5.1\n"
+10 "%s (BSD grep) %s\n"
 11 "unknown --binary-files option"
 12 "Binary file %s matches\n"
-12 "value out of range"
-13 "unknown -d or --directory option"
-14 "unknown --color option"
+13 "value out of range"
+14 "unknown -d or --directory option"
+15 "unknown --color option"
+16 "cannot read bzip2 compressed file"
+17 "PCRE is not enabled in this version of grep. To enable this feature, please install libpcre and recompile grep with WITH_PCRE set."

==== //depot/projects/soc2008/gabor_textproc/src/usr.bin/grep/nls/hu_HU.ISO8859-2.msg#2 (text+ko) ====

@@ -11,9 +11,11 @@
 7 "\t[--null] [minta] [fájl ...]\n"
 8 "párosítatlan zárójelek"
 9 "a kontextus a megengedett tartományon kívül esik"
-10 "FreeBSD grep 2.5.1\n"
+10 "%s (BSD grep) %s\n"
 11 "ismeretlen --binary-files opció"
 12 "%s bináris fájl illeszkedik\n"
-12 "az érték a megengedett tartományon kívül esik"
-13 "ismeretlen -d vagy --directory opció"
-14 "ismeretlen --color opció"
+13 "az érték a megengedett tartományon kívül esik"
+14 "ismeretlen -d vagy --directory opció"
+15 "ismeretlen --color opció"
+16 "bzip2 tömörített fájl nem olvasható"
+17 "A PCRE nem aktivált a grep ezen verziójában. A funkció aktiválásához kérjük telepítse a libpcre könyvtárat és fordítsa újra a grep programot a WITH_PCRE opcióval."

==== //depot/projects/soc2008/gabor_textproc/src/usr.bin/grep/nls/pt_BR.ISO8859-1.msg#2 (text+ko) ====

@@ -11,9 +11,10 @@
 7 "\t[--null] [padrăo] [arquivo ...]\n"
 8 "paręnteses nâo balanceados"
 9 "contexto está fora da escala"
-10 "FreeBSD grep 2.5.1\n"
-11 "Opcăo năo conhecida de --binary-files"
-12 "Arquivo binário %s casa com o padrăo\n"
-12 "el valor está fora da escala"
-13 "Opcăo năo conhecida de -d ou --directory"
-14 "Opcăo năo conhecida de --color"
+10 "%s (BSD grep) %s\n"
+11 "opcăo năo conhecida de --binary-files"
+12 "arquivo binário %s casa com o padrăo\n"
+13 "el valor está fora da escala"
+14 "opcăo năo conhecida de -d ou --directory"
+15 "opcăo năo conhecida de --color"
+16 "năo se posso ler o fichero comprimido bzip2"

==== //depot/projects/soc2008/gabor_textproc/src/usr.bin/grep/util.c#2 (text+ko) ====

@@ -1,5 +1,6 @@
 /*-
  * Copyright (c) 1999 James Howard and Dag-Erling Coďdan Smřrgrav
+ * Copyright (C) 2008 Gabor Kovesdan <gabor@FreeBSD.org>
  * All rights reserved.
  *
  * Redistribution and use in source and binary forms, with or without
@@ -40,29 +41,31 @@
 #include <ctype.h>
 #include <err.h>
 #include <errno.h>
+#include <fnmatch.h>
 #include <fts.h>
-#include <regex.h>
+#include <libgen.h>
 #include <stdio.h>
 #include <stdlib.h>
 #include <string.h>
 #include <unistd.h>
-#include <zlib.h>

>>> TRUNCATED FOR MAIL (1000 lines) <<<



Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?200807241524.m6OFOLEh067746>