/* vi: set sw=4 ts=4: */
/*
 * Mini grep implementation for busybox using libc regex.
 *
 * Copyright (C) 1999,2000,2001 by Lineo, inc. and Mark Whitley
 * Copyright (C) 1999,2000,2001 by Mark Whitley <markw@codepoet.org>
 *
 * Licensed under the GPL v2 or later, see the file LICENSE in this tarball.
 */
/* BB_AUDIT SUSv3 defects - unsupported option -x "match whole line only". */
/* BB_AUDIT GNU defects - always acts as -a.  */
/* http://www.opengroup.org/onlinepubs/007904975/utilities/grep.html */
/*
 * 2004,2006 (C) Vladimir Oleynik <dzo@simtreas.ru> -
 * correction "-e pattern1 -e pattern2" logic and more optimizations.
 * precompiled regex
 */
/*
 * (C) 2006 Jac Goudsmit added -o option
 */

#include "libbb.h"
#include "xregex.h"

/* options */
#define OPTSTR_GREP \
	"lnqvscFiHhe:f:Lorm:" \
	USE_FEATURE_GREP_CONTEXT("A:B:C:") \
	USE_FEATURE_GREP_EGREP_ALIAS("E") \
	USE_DESKTOP("w") \
	"aI"
/* ignored: -a "assume all files to be text" */
/* ignored: -I "assume binary files have no matches" */

enum {
	OPTBIT_l, /* list matched file names only */
	OPTBIT_n, /* print line# */
	OPTBIT_q, /* quiet - exit(EXIT_SUCCESS) of first match */
	OPTBIT_v, /* invert the match, to select non-matching lines */
	OPTBIT_s, /* suppress errors about file open errors */
	OPTBIT_c, /* count matches per file (suppresses normal output) */
	OPTBIT_F, /* literal match */
	OPTBIT_i, /* case-insensitive */
	OPTBIT_H, /* force filename display */
	OPTBIT_h, /* inhibit filename display */
	OPTBIT_e, /* -e PATTERN */
	OPTBIT_f, /* -f FILE_WITH_PATTERNS */
	OPTBIT_L, /* list unmatched file names only */
	OPTBIT_o, /* show only matching parts of lines */
	OPTBIT_r, /* recurse dirs */
	OPTBIT_m, /* -m MAX_MATCHES */
	USE_FEATURE_GREP_CONTEXT(    OPTBIT_A ,) /* -A NUM: after-match context */
	USE_FEATURE_GREP_CONTEXT(    OPTBIT_B ,) /* -B NUM: before-match context */
	USE_FEATURE_GREP_CONTEXT(    OPTBIT_C ,) /* -C NUM: -A and -B combined */
	USE_FEATURE_GREP_EGREP_ALIAS(OPTBIT_E ,) /* extended regexp */
	USE_DESKTOP(                 OPTBIT_w ,) /* whole word match */
	OPT_l = 1 << OPTBIT_l,
	OPT_n = 1 << OPTBIT_n,
	OPT_q = 1 << OPTBIT_q,
	OPT_v = 1 << OPTBIT_v,
	OPT_s = 1 << OPTBIT_s,
	OPT_c = 1 << OPTBIT_c,
	OPT_F = 1 << OPTBIT_F,
	OPT_i = 1 << OPTBIT_i,
	OPT_H = 1 << OPTBIT_H,
	OPT_h = 1 << OPTBIT_h,
	OPT_e = 1 << OPTBIT_e,
	OPT_f = 1 << OPTBIT_f,
	OPT_L = 1 << OPTBIT_L,
	OPT_o = 1 << OPTBIT_o,
	OPT_r = 1 << OPTBIT_r,
	OPT_m = 1 << OPTBIT_m,
	OPT_A = USE_FEATURE_GREP_CONTEXT(    (1 << OPTBIT_A)) + 0,
	OPT_B = USE_FEATURE_GREP_CONTEXT(    (1 << OPTBIT_B)) + 0,
	OPT_C = USE_FEATURE_GREP_CONTEXT(    (1 << OPTBIT_C)) + 0,
	OPT_E = USE_FEATURE_GREP_EGREP_ALIAS((1 << OPTBIT_E)) + 0,
	OPT_w = USE_DESKTOP(                 (1 << OPTBIT_w)) + 0,
};

#define PRINT_FILES_WITH_MATCHES    (option_mask32 & OPT_l)
#define PRINT_LINE_NUM              (option_mask32 & OPT_n)
#define BE_QUIET                    (option_mask32 & OPT_q)
#define SUPPRESS_ERR_MSGS           (option_mask32 & OPT_s)
#define PRINT_MATCH_COUNTS          (option_mask32 & OPT_c)
#define FGREP_FLAG                  (option_mask32 & OPT_F)
#define PRINT_FILES_WITHOUT_MATCHES (option_mask32 & OPT_L)

struct globals {
	int max_matches;
	int reflags;
	smalluint invert_search;
	smalluint print_filename;
	smalluint open_errors;
#if ENABLE_FEATURE_GREP_CONTEXT
	smalluint did_print_line;
	int lines_before;
	int lines_after;
	char **before_buf;
	int last_line_printed;
#endif
	/* globals used internally */
	llist_t *pattern_head;   /* growable list of patterns to match */
	const char *cur_file;    /* the current file we are reading */
};
#define G (*(struct globals*)&bb_common_bufsiz1)
#define INIT_G() \
	do { \
		struct G_sizecheck { \
			char G_sizecheck[sizeof(G) > COMMON_BUFSIZE ? -1 : 1]; \
		}; \
	} while (0)
#define max_matches       (G.max_matches         )
#define reflags           (G.reflags             )
#define invert_search     (G.invert_search       )
#define print_filename    (G.print_filename      )
#define open_errors       (G.open_errors         )
#define did_print_line    (G.did_print_line      )
#define lines_before      (G.lines_before        )
#define lines_after       (G.lines_after         )
#define before_buf        (G.before_buf          )
#define last_line_printed (G.last_line_printed   )
#define pattern_head      (G.pattern_head        )
#define cur_file          (G.cur_file            )


typedef struct grep_list_data_t {
	char *pattern;
	regex_t preg;
#define PATTERN_MEM_A 1
#define COMPILED 2
	int flg_mem_alocated_compiled;
} grep_list_data_t;


static void print_line(const char *line, int linenum, char decoration)
{
#if ENABLE_FEATURE_GREP_CONTEXT
	/* Happens when we go to next file, immediately hit match
	 * and try to print prev context... from prev file! Don't do it */
	if (linenum < 1)
		return;
	/* possibly print the little '--' separator */
	if ((lines_before || lines_after) && did_print_line &&
			last_line_printed != linenum - 1) {
		puts("--");
	}
	/* guard against printing "--" before first line of first file */
	did_print_line = 1;
	last_line_printed = linenum;
#endif
	if (print_filename)
		printf("%s%c", cur_file, decoration);
	if (PRINT_LINE_NUM)
		printf("%i%c", linenum, decoration);
	/* Emulate weird GNU grep behavior with -ov */
	if ((option_mask32 & (OPT_v|OPT_o)) != (OPT_v|OPT_o))
		puts(line);
}

static int grep_file(FILE *file)
{
	char *line;
	smalluint found;
	int linenum = 0;
	int nmatches = 0;
	regmatch_t regmatch;
#if ENABLE_FEATURE_GREP_CONTEXT
	int print_n_lines_after = 0;
	int curpos = 0; /* track where we are in the circular 'before' buffer */
	int idx = 0; /* used for iteration through the circular buffer */
#else
	enum { print_n_lines_after = 0 };
#endif /* ENABLE_FEATURE_GREP_CONTEXT */

	while ((line = xmalloc_fgetline(file)) != NULL) {
		llist_t *pattern_ptr = pattern_head;
		grep_list_data_t *gl = gl; /* for gcc */

		linenum++;
		found = 0;
		while (pattern_ptr) {
			gl = (grep_list_data_t *)pattern_ptr->data;
			if (FGREP_FLAG) {
				found |= (strstr(line, gl->pattern) != NULL);
			} else {
				if (!(gl->flg_mem_alocated_compiled & COMPILED)) {
					gl->flg_mem_alocated_compiled |= COMPILED;
					xregcomp(&(gl->preg), gl->pattern, reflags);
				}
				regmatch.rm_so = 0;
				regmatch.rm_eo = 0;
				if (regexec(&(gl->preg), line, 1, &regmatch, 0) == 0) {
					if (!(option_mask32 & OPT_w))
						found = 1;
					else {
						char c = ' ';
						if (regmatch.rm_so)
							c = line[regmatch.rm_so - 1];
						if (!isalnum(c) && c != '_') {
							c = line[regmatch.rm_eo];
							if (!c || (!isalnum(c) && c != '_'))
								found = 1;
						}
					}
				}
			}
			/* If it's non-inverted search, we can stop
			 * at first match */
			if (found && !invert_search)
				goto do_found;
			pattern_ptr = pattern_ptr->link;
		} /* while (pattern_ptr) */

		if (found ^ invert_search) {
 do_found:
			/* keep track of matches */
			nmatches++;

			/* quiet/print (non)matching file names only? */
			if (option_mask32 & (OPT_q|OPT_l|OPT_L)) {
				free(line); /* we don't need line anymore */
				if (BE_QUIET) {
					/* manpage says about -q:
					 * "exit immediately with zero status
					 * if any match is found,
					 * even if errors were detected" */
					exit(EXIT_SUCCESS);
				}
				/* if we're just printing filenames, we stop after the first match */
				if (PRINT_FILES_WITH_MATCHES) {
					puts(cur_file);
					/* fall through to "return 1" */
				}
				/* OPT_L aka PRINT_FILES_WITHOUT_MATCHES: return early */
				return 1; /* one match */
			}

#if ENABLE_FEATURE_GREP_CONTEXT
			/* Were we printing context and saw next (unwanted) match? */
			if ((option_mask32 & OPT_m) && nmatches > max_matches)
				break;
#endif

			/* print the matched line */
			if (PRINT_MATCH_COUNTS == 0) {
#if ENABLE_FEATURE_GREP_CONTEXT
				int prevpos = (curpos == 0) ? lines_before - 1 : curpos - 1;

				/* if we were told to print 'before' lines and there is at least
				 * one line in the circular buffer, print them */
				if (lines_before && before_buf[prevpos] != NULL) {
					int first_buf_entry_line_num = linenum - lines_before;

					/* advance to the first entry in the circular buffer, and
					 * figure out the line number is of the first line in the
					 * buffer */
					idx = curpos;
					while (before_buf[idx] == NULL) {
						idx = (idx + 1) % lines_before;
						first_buf_entry_line_num++;
					}

					/* now print each line in the buffer, clearing them as we go */
					while (before_buf[idx] != NULL) {
						print_line(before_buf[idx], first_buf_entry_line_num, '-');
						free(before_buf[idx]);
						before_buf[idx] = NULL;
						idx = (idx + 1) % lines_before;
						first_buf_entry_line_num++;
					}
				}

				/* make a note that we need to print 'after' lines */
				print_n_lines_after = lines_after;
#endif
				if (option_mask32 & OPT_o) {
					if (FGREP_FLAG) {
						/* -Fo just prints the pattern
						 * (unless -v: -Fov doesnt print anything at all) */
						if (found)
							print_line(gl->pattern, linenum, ':');
					} else {
						line[regmatch.rm_eo] = '\0';
						print_line(line + regmatch.rm_so, linenum, ':');
					}
				} else {
					print_line(line, linenum, ':');
				}
			}
		}
#if ENABLE_FEATURE_GREP_CONTEXT
		else { /* no match */
			/* if we need to print some context lines after the last match, do so */
			if (print_n_lines_after) {
				print_line(line, linenum, '-');
				print_n_lines_after--;
			} else if (lines_before) {
				/* Add the line to the circular 'before' buffer */
				free(before_buf[curpos]);
				before_buf[curpos] = line;
				curpos = (curpos + 1) % lines_before;
				/* avoid free(line) - we took the line */
				line = NULL;
			}
		}

#endif /* ENABLE_FEATURE_GREP_CONTEXT */
		free(line);

		/* Did we print all context after last requested match? */
		if ((option_mask32 & OPT_m)
		 && !print_n_lines_after && nmatches == max_matches)
			break;
	}

	/* special-case file post-processing for options where we don't print line
	 * matches, just filenames and possibly match counts */

	/* grep -c: print [filename:]count, even if count is zero */
	if (PRINT_MATCH_COUNTS) {
		if (print_filename)
			printf("%s:", cur_file);
		printf("%d\n", nmatches);
	}

	/* grep -L: print just the filename */
	if (PRINT_FILES_WITHOUT_MATCHES) {
		/* nmatches is zero, no need to check it:
		 * we return 1 early if we detected a match
		 * and PRINT_FILES_WITHOUT_MATCHES is set */
		puts(cur_file);
	}

	return nmatches;
}

#if ENABLE_FEATURE_CLEAN_UP
#define new_grep_list_data(p, m) add_grep_list_data(p, m)
static char *add_grep_list_data(char *pattern, int flg_used_mem)
#else
#define new_grep_list_data(p, m) add_grep_list_data(p)
static char *add_grep_list_data(char *pattern)
#endif
{
	grep_list_data_t *gl = xzalloc(sizeof(*gl));
	gl->pattern = pattern;
#if ENABLE_FEATURE_CLEAN_UP
	gl->flg_mem_alocated_compiled = flg_used_mem;
#else
	/*gl->flg_mem_alocated_compiled = 0;*/
#endif
	return (char *)gl;
}

static void load_regexes_from_file(llist_t *fopt)
{
	char *line;
	FILE *f;

	while (fopt) {
		llist_t *cur = fopt;
		char *ffile = cur->data;

		fopt = cur->link;
		free(cur);
		f = xfopen(ffile, "r");
		while ((line = xmalloc_fgetline(f)) != NULL) {
			llist_add_to(&pattern_head,
				new_grep_list_data(line, PATTERN_MEM_A));
		}
	}
}

static int file_action_grep(const char *filename,
			struct stat *statbuf ATTRIBUTE_UNUSED,
			void* matched,
			int depth ATTRIBUTE_UNUSED)
{
	FILE *file = fopen(filename, "r");
	if (file == NULL) {
		if (!SUPPRESS_ERR_MSGS)
			bb_simple_perror_msg(filename);
		open_errors = 1;
		return 0;
	}
	cur_file = filename;
	*(int*)matched += grep_file(file);
	fclose(file);
	return 1;
}

static int grep_dir(const char *dir)
{
	int matched = 0;
	recursive_action(dir,
		/* recurse=yes */ ACTION_RECURSE |
		/* followLinks=no */
		/* depthFirst=yes */ ACTION_DEPTHFIRST,
		/* fileAction= */ file_action_grep,
		/* dirAction= */ NULL,
		/* userData= */ &matched,
		/* depth= */ 0);
	return matched;
}

int grep_main(int argc, char **argv) MAIN_EXTERNALLY_VISIBLE;
int grep_main(int argc, char **argv)
{
	FILE *file;
	int matched;
	llist_t *fopt = NULL;

	/* do normal option parsing */
#if ENABLE_FEATURE_GREP_CONTEXT
	int Copt;

	/* -H unsets -h; -C unsets -A,-B; -e,-f are lists;
	 * -m,-A,-B,-C have numeric param */
	opt_complementary = "H-h:C-AB:e::f::m+:A+:B+:C+";
	getopt32(argv,
		OPTSTR_GREP,
		&pattern_head, &fopt, &max_matches,
		&lines_after, &lines_before, &Copt);

	if (option_mask32 & OPT_C) {
		/* -C unsets prev -A and -B, but following -A or -B
		   may override it */
		if (!(option_mask32 & OPT_A)) /* not overridden */
			lines_after = Copt;
		if (!(option_mask32 & OPT_B)) /* not overridden */
			lines_before = Copt;
		//option_mask32 |= OPT_A|OPT_B; /* for parser */
	}
	/* sanity checks */
	if (option_mask32 & (OPT_c|OPT_q|OPT_l|OPT_L)) {
		option_mask32 &= ~OPT_n;
		lines_before = 0;
		lines_after = 0;
	} else if (lines_before > 0)
		before_buf = xzalloc(lines_before * sizeof(char *));
#else
	/* with auto sanity checks */
	/* -H unsets -h; -c,-q or -l unset -n; -e,-f are lists; -m N */
	opt_complementary = "H-h:c-n:q-n:l-n:e::f::m+";
	getopt32(argv, OPTSTR_GREP,
		&pattern_head, &fopt, &max_matches);
#endif
	invert_search = ((option_mask32 & OPT_v) != 0); /* 0 | 1 */

	if (pattern_head != NULL) {
		/* convert char **argv to grep_list_data_t */
		llist_t *cur;

		for (cur = pattern_head; cur; cur = cur->link)
			cur->data = new_grep_list_data(cur->data, 0);
	}
	if (option_mask32 & OPT_f)
		load_regexes_from_file(fopt);

	if (ENABLE_FEATURE_GREP_FGREP_ALIAS && applet_name[0] == 'f')
		option_mask32 |= OPT_F;

	if (!(option_mask32 & (OPT_o | OPT_w)))
		reflags = REG_NOSUB;

	if (ENABLE_FEATURE_GREP_EGREP_ALIAS
	 && (applet_name[0] == 'e' || (option_mask32 & OPT_E))
	) {
		reflags |= REG_EXTENDED;
	}

	if (option_mask32 & OPT_i)
		reflags |= REG_ICASE;

	argv += optind;
	argc -= optind;

	/* if we didn't get a pattern from -e and no command file was specified,
	 * first parameter should be the pattern. no pattern, no worky */
	if (pattern_head == NULL) {
		char *pattern;
		if (*argv == NULL)
			bb_show_usage();
		pattern = new_grep_list_data(*argv++, 0);
		llist_add_to(&pattern_head, pattern);
		argc--;
	}

	/* argv[(optind)..(argc-1)] should be names of file to grep through. If
	 * there is more than one file to grep, we will print the filenames. */
	if (argc > 1)
		print_filename = 1;
	/* -H / -h of course override */
	if (option_mask32 & OPT_H)
		print_filename = 1;
	if (option_mask32 & OPT_h)
		print_filename = 0;

	/* If no files were specified, or '-' was specified, take input from
	 * stdin. Otherwise, we grep through all the files specified. */
	matched = 0;
	do {
		cur_file = *argv++;
		file = stdin;
		if (!cur_file || LONE_DASH(cur_file)) {
			cur_file = "(standard input)";
		} else {
			if (option_mask32 & OPT_r) {
				struct stat st;
				if (stat(cur_file, &st) == 0 && S_ISDIR(st.st_mode)) {
					if (!(option_mask32 & OPT_h))
						print_filename = 1;
					matched += grep_dir(cur_file);
					goto grep_done;
				}
			}
			/* else: fopen(dir) will succeed, but reading won't */
			file = fopen(cur_file, "r");
			if (file == NULL) {
				if (!SUPPRESS_ERR_MSGS)
					bb_simple_perror_msg(cur_file);
				open_errors = 1;
				continue;
			}
		}
		matched += grep_file(file);
		fclose_if_not_stdin(file);
 grep_done: ;
	} while (--argc > 0);

	/* destroy all the elments in the pattern list */
	if (ENABLE_FEATURE_CLEAN_UP) {
		while (pattern_head) {
			llist_t *pattern_head_ptr = pattern_head;
			grep_list_data_t *gl = (grep_list_data_t *)pattern_head_ptr->data;

			pattern_head = pattern_head->link;
			if ((gl->flg_mem_alocated_compiled & PATTERN_MEM_A))
				free(gl->pattern);
			if ((gl->flg_mem_alocated_compiled & COMPILED))
				regfree(&(gl->preg));
			free(gl);
			free(pattern_head_ptr);
		}
	}
	/* 0 = success, 1 = failed, 2 = error */
	if (open_errors)
		return 2;
	return !matched; /* invert return value: 0 = success, 1 = failed */
}
