/[pcre]/code/trunk/pgrep.c
ViewVC logotype

Contents of /code/trunk/pgrep.c

Parent Directory Parent Directory | Revision Log Revision Log


Revision 7 - (hide annotations) (download)
Sat Feb 24 21:38:09 2007 UTC (7 years, 6 months ago) by nigel
File MIME type: text/plain
File size: 4756 byte(s)
Load pcre-1.02 into code/trunk.

1 nigel 3 /*************************************************
2     * PCRE grep program *
3     *************************************************/
4    
5     #include <stdio.h>
6     #include <string.h>
7     #include <stdlib.h>
8     #include <errno.h>
9     #include "pcre.h"
10    
11    
12     #define FALSE 0
13     #define TRUE 1
14    
15     typedef int BOOL;
16    
17    
18    
19     /*************************************************
20     * Global variables *
21     *************************************************/
22    
23     static pcre *pattern;
24     static pcre_extra *hints;
25    
26     static BOOL count_only = FALSE;
27     static BOOL filenames_only = FALSE;
28     static BOOL invert = FALSE;
29     static BOOL number = FALSE;
30     static BOOL silent = FALSE;
31     static BOOL whole_lines = FALSE;
32    
33    
34    
35     #ifdef STRERROR_FROM_ERRLIST
36     /*************************************************
37     * Provide strerror() for non-ANSI libraries *
38     *************************************************/
39    
40     /* Some old-fashioned systems still around (e.g. SunOS4) don't have strerror()
41     in their libraries, but can provide the same facility by this simple
42     alternative function. */
43    
44     extern int sys_nerr;
45     extern char *sys_errlist[];
46    
47     char *
48     strerror(int n)
49     {
50     if (n < 0 || n >= sys_nerr) return "unknown error number";
51     return sys_errlist[n];
52     }
53     #endif /* STRERROR_FROM_ERRLIST */
54    
55    
56    
57     /*************************************************
58     * Grep an individual file *
59     *************************************************/
60    
61     static int
62     pgrep(FILE *in, char *name)
63     {
64     int rc = 1;
65     int linenumber = 0;
66     int count = 0;
67     int offsets[2];
68     char buffer[BUFSIZ];
69    
70     while (fgets(buffer, sizeof(buffer), in) != NULL)
71     {
72     BOOL match;
73     int length = (int)strlen(buffer);
74     if (length > 0 && buffer[length-1] == '\n') buffer[--length] = 0;
75     linenumber++;
76    
77     match = pcre_exec(pattern, hints, buffer, length, 0, offsets, 2) >= 0;
78     if (match && whole_lines && offsets[1] != length) match = FALSE;
79    
80     if (match != invert)
81     {
82     if (count_only) count++;
83    
84     else if (filenames_only)
85     {
86     fprintf(stdout, "%s\n", (name == NULL)? "<stdin>" : name);
87     return 0;
88     }
89    
90     else if (silent) return 0;
91    
92     else
93     {
94     if (name != NULL) fprintf(stdout, "%s:", name);
95     if (number) fprintf(stdout, "%d:", linenumber);
96     fprintf(stdout, "%s\n", buffer);
97     }
98    
99     rc = 0;
100     }
101     }
102    
103     if (count_only)
104     {
105     if (name != NULL) fprintf(stdout, "%s:", name);
106     fprintf(stdout, "%d\n", count);
107     }
108    
109     return rc;
110     }
111    
112    
113    
114    
115     /*************************************************
116     * Usage function *
117     *************************************************/
118    
119     static int
120     usage(int rc)
121     {
122     fprintf(stderr, "Usage: pgrep [-chilnsvx] pattern [file] ...\n");
123     return rc;
124     }
125    
126    
127    
128    
129     /*************************************************
130     * Main program *
131     *************************************************/
132    
133     int
134     main(int argc, char **argv)
135     {
136     int i;
137     int rc = 1;
138     int options = 0;
139     int errptr;
140 nigel 7 const char *error;
141 nigel 3 BOOL filenames = TRUE;
142    
143     /* Process the options */
144    
145     for (i = 1; i < argc; i++)
146     {
147     char *s;
148     if (argv[i][0] != '-') break;
149     s = argv[i] + 1;
150     while (*s != 0)
151     {
152     switch (*s++)
153     {
154     case 'c': count_only = TRUE; break;
155     case 'h': filenames = FALSE; break;
156     case 'i': options |= PCRE_CASELESS; break;
157     case 'l': filenames_only = TRUE;
158     case 'n': number = TRUE; break;
159     case 's': silent = TRUE; break;
160     case 'v': invert = TRUE; break;
161     case 'x': whole_lines = TRUE; options |= PCRE_ANCHORED; break;
162     default:
163     fprintf(stderr, "pgrep: unknown option %c\n", s[-1]);
164     return usage(2);
165     }
166     }
167     }
168    
169     /* There must be at least a regexp argument */
170    
171     if (i >= argc) return usage(0);
172    
173     /* Compile the regular expression. */
174    
175     pattern = pcre_compile(argv[i++], options, &error, &errptr);
176     if (pattern == NULL)
177     {
178     fprintf(stderr, "pgrep: error in regex at offset %d: %s\n", errptr, error);
179     return 2;
180     }
181    
182     /* Study the regular expression, as we will be running it may times */
183    
184     hints = pcre_study(pattern, 0, &error);
185     if (error != NULL)
186     {
187     fprintf(stderr, "pgrep: error while studing regex: %s\n", error);
188     return 2;
189     }
190    
191     /* If there are no further arguments, do the business on stdin and exit */
192    
193     if (i >= argc) return pgrep(stdin, NULL);
194    
195     /* Otherwise, work through the remaining arguments as files. If there is only
196     one, don't give its name on the output. */
197    
198     if (i == argc - 1) filenames = FALSE;
199     if (filenames_only) filenames = TRUE;
200    
201     for (; i < argc; i++)
202     {
203     FILE *in = fopen(argv[i], "r");
204     if (in == NULL)
205     {
206     fprintf(stderr, "%s: failed to open: %s\n", argv[i], strerror(errno));
207     rc = 2;
208     }
209     else
210     {
211     int frc = pgrep(in, filenames? argv[i] : NULL);
212     if (frc == 0 && rc == 1) rc = 0;
213     fclose(in);
214     }
215     }
216    
217     return rc;
218     }
219    
220     /* End */

webmaster@exim.org
ViewVC Help
Powered by ViewVC 1.1.12