View | Details | Raw Unified | Return to bug 195763 | Differences between
and this patch

Collapse All | Expand All

(-)b/usr.bin/grep/util.c (-11 / +50 lines)
Lines 52-57 __FBSDID("$FreeBSD$"); Link Here
52
#include "fastmatch.h"
52
#include "fastmatch.h"
53
#include "grep.h"
53
#include "grep.h"
54
54
55
#ifndef MAX
56
#define MAX(a,b)			((a > b) ? (a) : (b))
57
#endif
58
55
static int	 linesqueued;
59
static int	 linesqueued;
56
static int	 procline(struct str *l, int);
60
static int	 procline(struct str *l, int);
57
61
Lines 264-269 procfile(const char *fn) Link Here
264
}
284
}
265
285
266
#define iswword(x)	(iswalnum((x)) || (x) == L'_')
286
#define iswword(x)	(iswalnum((x)) || (x) == L'_')
287
#define overlaps(a,b) ( \
288
		((a.rm_so) >= (b.rm_so) && (a.rm_so) <= (b.rm_eo-1)) || \
289
		((a.rm_eo-1) >= (b.rm_so) && (a.rm_eo) <= (b.rm_eo)) || \
290
		((a.rm_so) < (b.rm_so) && (a.rm_eo-1) >= (b.rm_so)) || \
291
		((a.rm_so) < (b.rm_eo-1) && (a.rm_eo) >= (b.rm_eo)) \
292
		)
267
293
268
/*
294
/*
269
 * Processes a line comparing it with the specified patterns.  Each pattern
295
 * Processes a line comparing it with the specified patterns.  Each pattern
Lines 277-293 procline(struct str *l, int nottext) Link Here
277
{
303
{
278
	regmatch_t matches[MAX_LINE_MATCHES];
304
	regmatch_t matches[MAX_LINE_MATCHES];
279
	regmatch_t pmatch;
305
	regmatch_t pmatch;
280
	size_t st = 0;
306
	size_t st = 0, nst = 0;
281
	unsigned int i;
307
	unsigned int i;
282
	int c = 0, m = 0, r = 0;
308
	int c = 0, m = 0, r = 0, lastmatches = 0;
283
309
284
	/* Loop to process the whole line */
310
	/* Loop to process the whole line */
285
	while (st <= l->len) {
311
	while (st <= l->len) {
286
		pmatch.rm_so = st;
312
		lastmatches = 0;
287
		pmatch.rm_eo = l->len;
288
289
		/* Loop to compare with all the patterns */
313
		/* Loop to compare with all the patterns */
290
		for (i = 0; i < patterns; i++) {
314
		for (i = 0; i < patterns; i++) {
315
			pmatch.rm_so = st;
316
			pmatch.rm_eo = l->len;
291
			if (fg_pattern[i].pattern)
317
			if (fg_pattern[i].pattern)
292
				r = fastexec(&fg_pattern[i],
318
				r = fastexec(&fg_pattern[i],
293
				    l->dat, 1, &pmatch, eflags);
319
				    l->dat, 1, &pmatch, eflags);
Lines 295-303 procline(struct str *l, int nottext) Link Here
295
				r = regexec(&r_pattern[i], l->dat, 1,
321
				r = regexec(&r_pattern[i], l->dat, 1,
296
				    &pmatch, eflags);
322
				    &pmatch, eflags);
297
			r = (r == 0) ? 0 : REG_NOMATCH;
323
			r = (r == 0) ? 0 : REG_NOMATCH;
298
			st = (cflags & REG_NOSUB)
299
				? (size_t)l->len
300
				: (size_t)pmatch.rm_eo;
301
			if (r == REG_NOMATCH)
324
			if (r == REG_NOMATCH)
302
				continue;
325
				continue;
303
			/* Check for full match */
326
			/* Check for full match */
Lines 324-333 procline(struct str *l, int nottext) Link Here
324
					r = REG_NOMATCH;
347
					r = REG_NOMATCH;
325
			}
348
			}
326
			if (r == 0) {
349
			if (r == 0) {
350
				lastmatches ++;
351
				/* Skip over zero-length matches */
352
				if (pmatch.rm_so == pmatch.rm_eo)
353
					continue;
327
				if (m == 0)
354
				if (m == 0)
328
					c++;
355
					c++;
329
				if (m < MAX_LINE_MATCHES)
356
330
					matches[m++] = pmatch;
357
				if (m < MAX_LINE_MATCHES) {
358
						/* Conflicting matches? */
359
					if (m > 0 && overlaps(pmatch, matches[m-1])) {
360
						/* Replace previous match if the new one is earlier and/or longer */
361
						if (pmatch.rm_so < matches[m-1].rm_so ||
362
							(pmatch.rm_eo - pmatch.rm_so) >= (matches[m-1].rm_eo - matches[m-1].rm_so)) {
363
							matches[m-1] = pmatch;
364
							nst = pmatch.rm_eo;
365
						}
366
					} else {
367
						/* Advance as normal if not */
368
						matches[m++] = pmatch;
369
						nst = pmatch.rm_eo;
370
					}
371
				}
372
331
				/* matches - skip further patterns */
373
				/* matches - skip further patterns */
332
				if ((color == NULL && !oflag) ||
374
				if ((color == NULL && !oflag) ||
333
				    qflag || lflag)
375
				    qflag || lflag)
Lines 335-340 procline(struct str *l, int nottext) Link Here
335
			}
377
			}
336
		}
378
		}
337
379
380
		/* If we didn't have any matches or REG_NOSUB set */
381
		if (lastmatches == 0 || (cflags & REG_NOSUB))
382
			nst = l->len;
383
		
384
		/* Advance st based on previous matches */
385
		st = nst;
386
338
		if (vflag) {
387
		if (vflag) {
339
			c = !c;
388
			c = !c;
340
			break;
389
			break;
Lines 344-351 procline(struct str *l, int nottext) Link Here
344
		if (!wflag && ((color == NULL && !oflag) || qflag || lflag || Lflag))
393
		if (!wflag && ((color == NULL && !oflag) || qflag || lflag || Lflag))
345
			break;
394
			break;
346
395
347
		if (st == (size_t)pmatch.rm_so)
396
		if (lastmatches == 0)
348
			break; 	/* No matches */
397
			break; 	/* No matches */
398
		else if (st == (size_t)pmatch.rm_so)
399
			st ++;	/* Zero-length match -- advance one more */
349
	}
400
	}
350
401
351
402
Lines 444-449 printline(struct str *line, int sep, regmatch_t *matches, int m) Link Here
444
	size_t a = 0;
495
	size_t a = 0;
445
	int i, n = 0;
496
	int i, n = 0;
446
497
498
	/* If matchall, everything matches but don't actually print for -o */
499
	if (oflag && matchall)
500
		return;
501
447
	if (!hflag) {
502
	if (!hflag) {
448
		if (!nullflag) {
503
		if (!nullflag) {
449
			fputs(line->file, stdout);
504
			fputs(line->file, stdout);

Return to bug 195763