~ubuntu-branches/ubuntu/hoary/pcre3/hoary-security

« back to all changes in this revision

Viewing changes to pcregrep.c

  • Committer: Bazaar Package Importer
  • Author(s): Colin Watson
  • Date: 2001-08-19 20:43:28 UTC
  • Revision ID: james.westby@ubuntu.com-20010819204328-furyhi4ms3c5yjae
Tags: upstream-3.4
ImportĀ upstreamĀ versionĀ 3.4

Show diffs side-by-side

added added

removed removed

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