/* vi: set sw=4 ts=4: */
/*
 * Mini diff implementation for busybox, adapted from OpenBSD diff.
 *
 * Copyright (C) 2006 by Robert Sullivan <cogito.ergo.cogito@hotmail.com>
 * Copyright (c) 2003 Todd C. Miller <Todd.Miller@courtesan.com>
 *
 * Sponsored in part by the Defense Advanced Research Projects
 * Agency (DARPA) and Air Force Research Laboratory, Air Force
 * Materiel Command, USAF, under agreement number F39502-99-1-0512.
 *
 * Licensed under GPLv2 or later, see file LICENSE in this tarball for details.
 */

#include "libbb.h"

#define FSIZE_MAX 32768

/*
 * Output flags
 */
#define D_HEADER        1	/* Print a header/footer between files */
#define D_EMPTY1        2	/* Treat first file as empty (/dev/null) */
#define D_EMPTY2        4	/* Treat second file as empty (/dev/null) */

/*
 * Status values for print_status() and diffreg() return values
 * Guide:
 * D_SAME - files are the same
 * D_DIFFER - files differ
 * D_BINARY - binary files differ
 * D_COMMON - subdirectory common to both dirs
 * D_ONLY - file only exists in one dir
 * D_MISMATCH1 - path1 a dir, path2 a file
 * D_MISMATCH2 - path1 a file, path2 a dir
 * D_ERROR - error occurred
 * D_SKIPPED1 - skipped path1 as it is a special file
 * D_SKIPPED2 - skipped path2 as it is a special file
 */

#define D_SAME		0
#define D_DIFFER	(1<<0)
#define D_BINARY	(1<<1)
#define D_COMMON	(1<<2)
#define D_ONLY		(1<<3)
#define D_MISMATCH1	(1<<4)
#define D_MISMATCH2	(1<<5)
#define D_ERROR		(1<<6)
#define D_SKIPPED1	(1<<7)
#define D_SKIPPED2	(1<<8)

/* Command line options */
#define FLAG_a	(1<<0)
#define FLAG_b	(1<<1)
#define FLAG_d  (1<<2)
#define FLAG_i	(1<<3)
#define FLAG_L	(1<<4)
#define FLAG_N	(1<<5)
#define FLAG_q	(1<<6)
#define FLAG_r	(1<<7)
#define FLAG_s	(1<<8)
#define FLAG_S	(1<<9)
#define FLAG_t	(1<<10)
#define FLAG_T	(1<<11)
#define FLAG_U	(1<<12)
#define	FLAG_w	(1<<13)

#define g_read_buf bb_common_bufsiz1

struct cand {
	int x;
	int y;
	int pred;
};

struct line {
	int serial;
	int value;
};

/*
 * The following struct is used to record change information
 * doing a "context" or "unified" diff.  (see routine "change" to
 * understand the highly mnemonic field names)
 */
struct context_vec {
	int a;          /* start line in old file */
	int b;          /* end line in old file */
	int c;          /* start line in new file */
	int d;          /* end line in new file */
};

struct globals {
	USE_FEATURE_DIFF_DIR(char **dl;)
	USE_FEATURE_DIFF_DIR(int dl_count;)
	/* This is the default number of lines of context. */
	int context;
	size_t max_context;
	int status;
	char *start;
	const char *label1;
	const char *label2;
	struct line *file[2];
	int *J;          /* will be overlaid on class */
	int *class;      /* will be overlaid on file[0] */
	int *klist;      /* will be overlaid on file[0] after class */
	int *member;     /* will be overlaid on file[1] */
	int clen;
	int len[2];
	int pref, suff;  /* length of prefix and suffix */
	int slen[2];
	bool anychange;
	long *ixnew;     /* will be overlaid on file[1] */
	long *ixold;     /* will be overlaid on klist */
	struct cand *clist;  /* merely a free storage pot for candidates */
	int clistlen;    /* the length of clist */
	struct line *sfile[2];   /* shortened by pruning common prefix/suffix */
	struct context_vec *context_vec_start;
	struct context_vec *context_vec_end;
	struct context_vec *context_vec_ptr;
	struct stat stb1, stb2;
};
#define G (*ptr_to_globals)
#define dl                 (G.dl                )
#define dl_count           (G.dl_count          )
#define context            (G.context           )
#define max_context        (G.max_context       )
#define status             (G.status            )
#define start              (G.start             )
#define label1             (G.label1            )
#define label2             (G.label2            )
#define file               (G.file              )
#define J                  (G.J                 )
#define class              (G.class             )
#define klist              (G.klist             )
#define member             (G.member            )
#define clen               (G.clen              )
#define len                (G.len               )
#define pref               (G.pref              )
#define suff               (G.suff              )
#define slen               (G.slen              )
#define anychange          (G.anychange         )
#define ixnew              (G.ixnew             )
#define ixold              (G.ixold             )
#define clist              (G.clist             )
#define clistlen           (G.clistlen          )
#define sfile              (G.sfile             )
#define context_vec_start  (G.context_vec_start )
#define context_vec_end    (G.context_vec_end   )
#define context_vec_ptr    (G.context_vec_ptr   )
#define stb1               (G.stb1              )
#define stb2               (G.stb2              )
#define INIT_G() do { \
	PTR_TO_GLOBALS = xzalloc(sizeof(G)); \
	context = 3; \
	max_context = 64; \
} while (0)


static void print_only(const char *path, size_t dirlen, const char *entry)
{
	if (dirlen > 1)
		dirlen--;
	printf("Only in %.*s: %s\n", (int) dirlen, path, entry);
}

static void print_status(int val, char *path1, char *path2, char *entry)
{
	const char *const _entry = entry ? entry : "";
	char * const _path1 = entry ? concat_path_file(path1, _entry) : path1;
	char * const _path2 = entry ? concat_path_file(path2, _entry) : path2;

	switch (val) {
	case D_ONLY:
		print_only(path1, strlen(path1), entry);
		break;
	case D_COMMON:
		printf("Common subdirectories: %s and %s\n", _path1, _path2);
		break;
	case D_BINARY:
		printf("Binary files %s and %s differ\n", _path1, _path2);
		break;
	case D_DIFFER:
		if (option_mask32 & FLAG_q)
			printf("Files %s and %s differ\n", _path1, _path2);
		break;
	case D_SAME:
		if (option_mask32 & FLAG_s)
			printf("Files %s and %s are identical\n", _path1, _path2);
		break;
	case D_MISMATCH1:
		printf("File %s is a %s while file %s is a %s\n",
			   _path1, "directory", _path2, "regular file");
		break;
	case D_MISMATCH2:
		printf("File %s is a %s while file %s is a %s\n",
			   _path1, "regular file", _path2, "directory");
		break;
	case D_SKIPPED1:
		printf("File %s is not a regular file or directory and was skipped\n",
			   _path1);
		break;
	case D_SKIPPED2:
		printf("File %s is not a regular file or directory and was skipped\n",
			   _path2);
		break;
	}
	if (entry) {
		free(_path1);
		free(_path2);
	}
}
static ALWAYS_INLINE int fiddle_sum(int sum, int t)
{
	return sum * 127 + t;
}
/*
 * Hash function taken from Robert Sedgewick, Algorithms in C, 3d ed., p 578.
 */
static int readhash(FILE *fp)
{
	int i, t, space;
	int sum;

	sum = 1;
	space = 0;
	if (!(option_mask32 & (FLAG_b | FLAG_w))) {
		for (i = 0; (t = getc(fp)) != '\n'; i++) {
			if (t == EOF) {
				if (i == 0)
					return 0;
				break;
			}
			sum = fiddle_sum(sum, t);
		}
	} else {
		for (i = 0;;) {
			switch (t = getc(fp)) {
			case '\t':
			case '\r':
			case '\v':
			case '\f':
			case ' ':
				space++;
				continue;
			default:
				if (space && !(option_mask32 & FLAG_w)) {
					i++;
					space = 0;
				}
				sum = fiddle_sum(sum, t);
				i++;
				continue;
			case EOF:
				if (i == 0)
					return 0;
				/* FALLTHROUGH */
			case '\n':
				break;
			}
			break;
		}
	}
	/*
	 * There is a remote possibility that we end up with a zero sum.
	 * Zero is used as an EOF marker, so return 1 instead.
	 */
	return (sum == 0 ? 1 : sum);
}


/*
 * Check to see if the given files differ.
 * Returns 0 if they are the same, 1 if different, and -1 on error.
 */
static int files_differ(FILE *f1, FILE *f2, int flags)
{
	size_t i, j;

	if ((flags & (D_EMPTY1 | D_EMPTY2)) || stb1.st_size != stb2.st_size
	 || (stb1.st_mode & S_IFMT) != (stb2.st_mode & S_IFMT)
	) {
		return 1;
	}
	while (1) {
		i = fread(g_read_buf,                    1, COMMON_BUFSIZE/2, f1);
		j = fread(g_read_buf + COMMON_BUFSIZE/2, 1, COMMON_BUFSIZE/2, f2);
		if (i != j)
			return 1;
		if (i == 0)
			return (ferror(f1) || ferror(f2));
		if (memcmp(g_read_buf,
		           g_read_buf + COMMON_BUFSIZE/2, i) != 0)
			return 1;
	}
}


static void prepare(int i, FILE *fp /*, off_t filesize*/)
{
	struct line *p;
	int h;
	size_t j, sz;

	rewind(fp);

	/*sz = (filesize <= FSIZE_MAX ? filesize : FSIZE_MAX) / 25;*/
	/*if (sz < 100)*/
	sz = 100;

	p = xmalloc((sz + 3) * sizeof(p[0]));
	j = 0;
	while ((h = readhash(fp))) {
		if (j == sz) {
			sz = sz * 3 / 2;
			p = xrealloc(p, (sz + 3) * sizeof(p[0]));
		}
		p[++j].value = h;
	}
	len[i] = j;
	file[i] = p;
}


static void prune(void)
{
	int i, j;

	for (pref = 0; pref < len[0] && pref < len[1] &&
		 file[0][pref + 1].value == file[1][pref + 1].value; pref++)
		continue;
	for (suff = 0; suff < len[0] - pref && suff < len[1] - pref &&
		 file[0][len[0] - suff].value == file[1][len[1] - suff].value;
		 suff++)
		continue;
	for (j = 0; j < 2; j++) {
		sfile[j] = file[j] + pref;
		slen[j] = len[j] - pref - suff;
		for (i = 0; i <= slen[j]; i++)
			sfile[j][i].serial = i;
	}
}


static void equiv(struct line *a, int n, struct line *b, int m, int *c)
{
	int i, j;

	i = j = 1;
	while (i <= n && j <= m) {
		if (a[i].value < b[j].value)
			a[i++].value = 0;
		else if (a[i].value == b[j].value)
			a[i++].value = j;
		else
			j++;
	}
	while (i <= n)
		a[i++].value = 0;
	b[m + 1].value = 0;
	j = 0;
	while (++j <= m) {
		c[j] = -b[j].serial;
		while (b[j + 1].value == b[j].value) {
			j++;
			c[j] = b[j].serial;
		}
	}
	c[j] = -1;
}


static int isqrt(int n)
{
	int y, x;

	if (n == 0)
		return 0;
	x = 1;
	do {
		y = x;
		x = n / x;
		x += y;
		x /= 2;
	} while ((x - y) > 1 || (x - y) < -1);

	return x;
}


static int newcand(int x, int y, int pred)
{
	struct cand *q;

	if (clen == clistlen) {
		clistlen = clistlen * 11 / 10;
		clist = xrealloc(clist, clistlen * sizeof(struct cand));
	}
	q = clist + clen;
	q->x = x;
	q->y = y;
	q->pred = pred;
	return clen++;
}


static int search(int *c, int k, int y)
{
	int i, j, l, t;

	if (clist[c[k]].y < y)	/* quick look for typical case */
		return k + 1;
	i = 0;
	j = k + 1;
	while (1) {
		l = i + j;
		if ((l >>= 1) <= i)
			break;
		t = clist[c[l]].y;
		if (t > y)
			j = l;
		else if (t < y)
			i = l;
		else
			return l;
	}
	return l + 1;
}


static int stone(int *a, int n, int *b, int *c)
{
	int i, k, y, j, l;
	int oldc, tc, oldl;
	unsigned int numtries;

#if ENABLE_FEATURE_DIFF_MINIMAL
	const unsigned int bound =
		(option_mask32 & FLAG_d) ? UINT_MAX : MAX(256, isqrt(n));
#else
	const unsigned int bound = MAX(256, isqrt(n));
#endif
	k = 0;
	c[0] = newcand(0, 0, 0);
	for (i = 1; i <= n; i++) {
		j = a[i];
		if (j == 0)
			continue;
		y = -b[j];
		oldl = 0;
		oldc = c[0];
		numtries = 0;
		do {
			if (y <= clist[oldc].y)
				continue;
			l = search(c, k, y);
			if (l != oldl + 1)
				oldc = c[l - 1];
			if (l <= k) {
				if (clist[c[l]].y <= y)
					continue;
				tc = c[l];
				c[l] = newcand(i, y, oldc);
				oldc = tc;
				oldl = l;
				numtries++;
			} else {
				c[l] = newcand(i, y, oldc);
				k++;
				break;
			}
		} while ((y = b[++j]) > 0 && numtries < bound);
	}
	return k;
}


static void unravel(int p)
{
	struct cand *q;
	int i;

	for (i = 0; i <= len[0]; i++)
		J[i] = i <= pref ? i : i > len[0] - suff ? i + len[1] - len[0] : 0;
	for (q = clist + p; q->y != 0; q = clist + q->pred)
		J[q->x + pref] = q->y + pref;
}


static void unsort(struct line *f, int l, int *b)
{
	int *a, i;

	a = xmalloc((l + 1) * sizeof(int));
	for (i = 1; i <= l; i++)
		a[f[i].serial] = f[i].value;
	for (i = 1; i <= l; i++)
		b[i] = a[i];
	free(a);
}


static int skipline(FILE * f)
{
	int i, c;

	for (i = 1; (c = getc(f)) != '\n' && c != EOF; i++)
		continue;
	return i;
}


/*
 * Check does double duty:
 *  1.  ferret out any fortuitous correspondences due
 *      to confounding by hashing (which result in "jackpot")
 *  2.  collect random access indexes to the two files
 */
static void check(FILE * f1, FILE * f2)
{
	int i, j, jackpot, c, d;
	long ctold, ctnew;

	rewind(f1);
	rewind(f2);
	j = 1;
	ixold[0] = ixnew[0] = 0;
	jackpot = 0;
	ctold = ctnew = 0;
	for (i = 1; i <= len[0]; i++) {
		if (J[i] == 0) {
			ixold[i] = ctold += skipline(f1);
			continue;
		}
		while (j < J[i]) {
			ixnew[j] = ctnew += skipline(f2);
			j++;
		}
		if ((option_mask32 & FLAG_b) || (option_mask32 & FLAG_w)
			|| (option_mask32 & FLAG_i)) {
			while (1) {
				c = getc(f1);
				d = getc(f2);
				/*
				 * GNU diff ignores a missing newline
				 * in one file if bflag || wflag.
				 */
				if (((option_mask32 & FLAG_b) || (option_mask32 & FLAG_w)) &&
					((c == EOF && d == '\n') || (c == '\n' && d == EOF))) {
					break;
				}
				ctold++;
				ctnew++;
				if ((option_mask32 & FLAG_b) && isspace(c) && isspace(d)) {
					do {
						if (c == '\n')
							break;
						ctold++;
					} while (isspace(c = getc(f1)));
					do {
						if (d == '\n')
							break;
						ctnew++;
					} while (isspace(d = getc(f2)));
				} else if (option_mask32 & FLAG_w) {
					while (isspace(c) && c != '\n') {
						c = getc(f1);
						ctold++;
					}
					while (isspace(d) && d != '\n') {
						d = getc(f2);
						ctnew++;
					}
				}
				if (c != d) {
					jackpot++;
					J[i] = 0;
					if (c != '\n' && c != EOF)
						ctold += skipline(f1);
					if (d != '\n' && c != EOF)
						ctnew += skipline(f2);
					break;
				}
				if (c == '\n' || c == EOF)
					break;
			}
		} else {
			while (1) {
				ctold++;
				ctnew++;
				if ((c = getc(f1)) != (d = getc(f2))) {
					J[i] = 0;
					if (c != '\n' && c != EOF)
						ctold += skipline(f1);
					if (d != '\n' && c != EOF)
						ctnew += skipline(f2);
					break;
				}
				if (c == '\n' || c == EOF)
					break;
			}
		}
		ixold[i] = ctold;
		ixnew[j] = ctnew;
		j++;
	}
	for (; j <= len[1]; j++)
		ixnew[j] = ctnew += skipline(f2);
}


/* shellsort CACM #201 */
static void sort(struct line *a, int n)
{
	struct line *ai, *aim, w;
	int j, m = 0, k;

	if (n == 0)
		return;
	for (j = 1; j <= n; j *= 2)
		m = 2 * j - 1;
	for (m /= 2; m != 0; m /= 2) {
		k = n - m;
		for (j = 1; j <= k; j++) {
			for (ai = &a[j]; ai > a; ai -= m) {
				aim = &ai[m];
				if (aim < ai)
					break;	/* wraparound */
				if (aim->value > ai[0].value ||
					(aim->value == ai[0].value && aim->serial > ai[0].serial))
					break;
				w.value = ai[0].value;
				ai[0].value = aim->value;
				aim->value = w.value;
				w.serial = ai[0].serial;
				ai[0].serial = aim->serial;
				aim->serial = w.serial;
			}
		}
	}
}


static void uni_range(int a, int b)
{
	if (a < b)
		printf("%d,%d", a, b - a + 1);
	else if (a == b)
		printf("%d", b);
	else
		printf("%d,0", b);
}


static void fetch(long *f, int a, int b, FILE * lb, int ch)
{
	int i, j, c, lastc, col, nc;

	if (a > b)
		return;
	for (i = a; i <= b; i++) {
		fseek(lb, f[i - 1], SEEK_SET);
		nc = f[i] - f[i - 1];
		if (ch != '\0') {
			putchar(ch);
			if (option_mask32 & FLAG_T)
				putchar('\t');
		}
		col = 0;
		for (j = 0, lastc = '\0'; j < nc; j++, lastc = c) {
			if ((c = getc(lb)) == EOF) {
				printf("\n\\ No newline at end of file\n");
				return;
			}
			if (c == '\t' && (option_mask32 & FLAG_t)) {
				do {
					putchar(' ');
				} while (++col & 7);
			} else {
				putchar(c);
				col++;
			}
		}
	}
}


static int asciifile(FILE * f)
{
#if ENABLE_FEATURE_DIFF_BINARY
	int i, cnt;
#endif

	if ((option_mask32 & FLAG_a) || f == NULL)
		return 1;

#if ENABLE_FEATURE_DIFF_BINARY
	rewind(f);
	cnt = fread(g_read_buf, 1, COMMON_BUFSIZE, f);
	for (i = 0; i < cnt; i++) {
		if (!isprint(g_read_buf[i])
		 && !isspace(g_read_buf[i])) {
			return 0;
		}
	}
#endif
	return 1;
}


/* dump accumulated "unified" diff changes */
static void dump_unified_vec(FILE * f1, FILE * f2)
{
	struct context_vec *cvp = context_vec_start;
	int lowa, upb, lowc, upd;
	int a, b, c, d;
	char ch;

	if (context_vec_start > context_vec_ptr)
		return;

	b = d = 0;			/* gcc */
	lowa = MAX(1, cvp->a - context);
	upb = MIN(len[0], context_vec_ptr->b + context);
	lowc = MAX(1, cvp->c - context);
	upd = MIN(len[1], context_vec_ptr->d + context);

	printf("@@ -");
	uni_range(lowa, upb);
	printf(" +");
	uni_range(lowc, upd);
	printf(" @@\n");

	/*
	 * Output changes in "unified" diff format--the old and new lines
	 * are printed together.
	 */
	for (; cvp <= context_vec_ptr; cvp++) {
		a = cvp->a;
		b = cvp->b;
		c = cvp->c;
		d = cvp->d;

		/*
		 * c: both new and old changes
		 * d: only changes in the old file
		 * a: only changes in the new file
		 */
		if (a <= b && c <= d)
			ch = 'c';
		else
			ch = (a <= b) ? 'd' : 'a';
#if 0
		switch (ch) {
		case 'c':
			fetch(ixold, lowa, a - 1, f1, ' ');
			fetch(ixold, a, b, f1, '-');
			fetch(ixnew, c, d, f2, '+');
			break;
		case 'd':
			fetch(ixold, lowa, a - 1, f1, ' ');
			fetch(ixold, a, b, f1, '-');
			break;
		case 'a':
			fetch(ixnew, lowc, c - 1, f2, ' ');
			fetch(ixnew, c, d, f2, '+');
			break;
		}
#else
		if (ch == 'c' || ch == 'd') {
			fetch(ixold, lowa, a - 1, f1, ' ');
			fetch(ixold, a, b, f1, '-');
		}
		if (ch == 'a')
			fetch(ixnew, lowc, c - 1, f2, ' ');
		if (ch == 'c' || ch == 'a')
			fetch(ixnew, c, d, f2, '+');
#endif
		lowa = b + 1;
		lowc = d + 1;
	}
	fetch(ixnew, d + 1, upd, f2, ' ');

	context_vec_ptr = context_vec_start - 1;
}


static void print_header(const char *file1, const char *file2)
{
	if (label1)
		printf("--- %s\n", label1);
	else
		printf("--- %s\t%s", file1, ctime(&stb1.st_mtime));
	if (label2)
		printf("+++ %s\n", label2);
	else
		printf("+++ %s\t%s", file2, ctime(&stb2.st_mtime));
}


/*
 * Indicate that there is a difference between lines a and b of the from file
 * to get to lines c to d of the to file.  If a is greater than b then there
 * are no lines in the from file involved and this means that there were
 * lines appended (beginning at b).  If c is greater than d then there are
 * lines missing from the to file.
 */
static void change(char *file1, FILE * f1, char *file2, FILE * f2, int a,
				   int b, int c, int d)
{
	if ((a > b && c > d) || (option_mask32 & FLAG_q)) {
		anychange = 1;
		return;
	}

	/*
	 * Allocate change records as needed.
	 */
	if (context_vec_ptr == context_vec_end - 1) {
		ptrdiff_t offset = context_vec_ptr - context_vec_start;

		max_context <<= 1;
		context_vec_start = xrealloc(context_vec_start,
				max_context * sizeof(struct context_vec));
		context_vec_end = context_vec_start + max_context;
		context_vec_ptr = context_vec_start + offset;
	}
	if (anychange == 0) {
		/*
		 * Print the context/unidiff header first time through.
		 */
		print_header(file1, file2);
	} else if (a > context_vec_ptr->b + (2 * context) + 1 &&
			   c > context_vec_ptr->d + (2 * context) + 1) {
		/*
		 * If this change is more than 'context' lines from the
		 * previous change, dump the record and reset it.
		 */
		dump_unified_vec(f1, f2);
	}
	context_vec_ptr++;
	context_vec_ptr->a = a;
	context_vec_ptr->b = b;
	context_vec_ptr->c = c;
	context_vec_ptr->d = d;
	anychange = 1;
}


static void output(char *file1, FILE * f1, char *file2, FILE * f2)
{
	/* Note that j0 and j1 can't be used as they are defined in math.h.
	 * This also allows the rather amusing variable 'j00'... */
	int m, i0, i1, j00, j01;

	rewind(f1);
	rewind(f2);
	m = len[0];
	J[0] = 0;
	J[m + 1] = len[1] + 1;
	for (i0 = 1; i0 <= m; i0 = i1 + 1) {
		while (i0 <= m && J[i0] == J[i0 - 1] + 1)
			i0++;
		j00 = J[i0 - 1] + 1;
		i1 = i0 - 1;
		while (i1 < m && J[i1 + 1] == 0)
			i1++;
		j01 = J[i1 + 1] - 1;
		J[i1] = j01;
		change(file1, f1, file2, f2, i0, i1, j00, j01);
	}
	if (m == 0) {
		change(file1, f1, file2, f2, 1, 0, 1, len[1]);
	}
	if (anychange != 0 && !(option_mask32 & FLAG_q)) {
		dump_unified_vec(f1, f2);
	}
}

/*
 * The following code uses an algorithm due to Harold Stone,
 * which finds a pair of longest identical subsequences in
 * the two files.
 *
 * The major goal is to generate the match vector J.
 * J[i] is the index of the line in file1 corresponding
 * to line i file0. J[i] = 0 if there is no
 * such line in file1.
 *
 * Lines are hashed so as to work in core. All potential
 * matches are located by sorting the lines of each file
 * on the hash (called ``value''). In particular, this
 * collects the equivalence classes in file1 together.
 * Subroutine equiv replaces the value of each line in
 * file0 by the index of the first element of its
 * matching equivalence in (the reordered) file1.
 * To save space equiv squeezes file1 into a single
 * array member in which the equivalence classes
 * are simply concatenated, except that their first
 * members are flagged by changing sign.
 *
 * Next the indices that point into member are unsorted into
 * array class according to the original order of file0.
 *
 * The cleverness lies in routine stone. This marches
 * through the lines of file0, developing a vector klist
 * of "k-candidates". At step i a k-candidate is a matched
 * pair of lines x,y (x in file0 y in file1) such that
 * there is a common subsequence of length k
 * between the first i lines of file0 and the first y
 * lines of file1, but there is no such subsequence for
 * any smaller y. x is the earliest possible mate to y
 * that occurs in such a subsequence.
 *
 * Whenever any of the members of the equivalence class of
 * lines in file1 matable to a line in file0 has serial number
 * less than the y of some k-candidate, that k-candidate
 * with the smallest such y is replaced. The new
 * k-candidate is chained (via pred) to the current
 * k-1 candidate so that the actual subsequence can
 * be recovered. When a member has serial number greater
 * that the y of all k-candidates, the klist is extended.
 * At the end, the longest subsequence is pulled out
 * and placed in the array J by unravel
 *
 * With J in hand, the matches there recorded are
 * checked against reality to assure that no spurious
 * matches have crept in due to hashing. If they have,
 * they are broken, and "jackpot" is recorded--a harmless
 * matter except that a true match for a spuriously
 * mated line may now be unnecessarily reported as a change.
 *
 * Much of the complexity of the program comes simply
 * from trying to minimize core utilization and
 * maximize the range of doable problems by dynamically
 * allocating what is needed and reusing what is not.
 * The core requirements for problems larger than somewhat
 * are (in words) 2*length(file0) + length(file1) +
 * 3*(number of k-candidates installed),  typically about
 * 6n words for files of length n.
 */
static unsigned diffreg(char *ofile1, char *ofile2, int flags)
{
	char *file1 = ofile1;
	char *file2 = ofile2;
	FILE *f1 = stdin, *f2 = stdin;
	unsigned rval;
	int i;

	anychange = 0;
	context_vec_ptr = context_vec_start - 1;

	if (S_ISDIR(stb1.st_mode) != S_ISDIR(stb2.st_mode))
		return (S_ISDIR(stb1.st_mode) ? D_MISMATCH1 : D_MISMATCH2);

	rval = D_SAME;

	if (LONE_DASH(file1) && LONE_DASH(file2))
		goto closem;

	if (flags & D_EMPTY1)
		f1 = xfopen(bb_dev_null, "r");
	else if (NOT_LONE_DASH(file1))
		f1 = xfopen(file1, "r");
	if (flags & D_EMPTY2)
		f2 = xfopen(bb_dev_null, "r");
	else if (NOT_LONE_DASH(file2))
		f2 = xfopen(file2, "r");

/* We can't diff non-seekable stream - we use rewind(), fseek().
 * This can be fixed (volunteers?).
 * Meanwhile we should check it here by stat'ing input fds,
 * but I am lazy and check that in main() instead.
 * Check in main won't catch "diffing fifos buried in subdirectories"
 * failure scenario - not very likely in real life... */

	i = files_differ(f1, f2, flags);
	if (i == 0)
		goto closem;
	else if (i != 1) {	/* 1 == ok */
		/* error */
		status |= 2;
		goto closem;
	}

	if (!asciifile(f1) || !asciifile(f2)) {
		rval = D_BINARY;
		status |= 1;
		goto closem;
	}

	prepare(0, f1 /*, stb1.st_size*/);
	prepare(1, f2 /*, stb2.st_size*/);
	prune();
	sort(sfile[0], slen[0]);
	sort(sfile[1], slen[1]);

	member = (int *) file[1];
	equiv(sfile[0], slen[0], sfile[1], slen[1], member);
	member = xrealloc(member, (slen[1] + 2) * sizeof(int));

	class = (int *) file[0];
	unsort(sfile[0], slen[0], class);
	class = xrealloc(class, (slen[0] + 2) * sizeof(int));

	klist = xmalloc((slen[0] + 2) * sizeof(int));
	clen = 0;
	clistlen = 100;
	clist = xmalloc(clistlen * sizeof(struct cand));
	i = stone(class, slen[0], member, klist);
	free(member);
	free(class);

	J = xrealloc(J, (len[0] + 2) * sizeof(int));
	unravel(klist[i]);
	free(clist);
	free(klist);

	ixold = xrealloc(ixold, (len[0] + 2) * sizeof(long));
	ixnew = xrealloc(ixnew, (len[1] + 2) * sizeof(long));
	check(f1, f2);
	output(file1, f1, file2, f2);

 closem:
	if (anychange) {
		status |= 1;
		if (rval == D_SAME)
			rval = D_DIFFER;
	}
	fclose_if_not_stdin(f1);
	fclose_if_not_stdin(f2);
	if (file1 != ofile1)
		free(file1);
	if (file2 != ofile2)
		free(file2);
	return rval;
}


#if ENABLE_FEATURE_DIFF_DIR
static void do_diff(char *dir1, char *path1, char *dir2, char *path2)
{
	int flags = D_HEADER;
	int val;
	char *fullpath1 = NULL; /* if -N */
	char *fullpath2 = NULL;

	if (path1)
		fullpath1 = concat_path_file(dir1, path1);
	if (path2)
		fullpath2 = concat_path_file(dir2, path2);

	if (!fullpath1 || stat(fullpath1, &stb1) != 0) {
		flags |= D_EMPTY1;
		memset(&stb1, 0, sizeof(stb1));
		if (path2) {
			free(fullpath1);
			fullpath1 = concat_path_file(dir1, path2);
		}
	}
	if (!fullpath2 || stat(fullpath2, &stb2) != 0) {
		flags |= D_EMPTY2;
		memset(&stb2, 0, sizeof(stb2));
		stb2.st_mode = stb1.st_mode;
		if (path1) {
			free(fullpath2);
			fullpath2 = concat_path_file(dir2, path1);
		}
	}

	if (stb1.st_mode == 0)
		stb1.st_mode = stb2.st_mode;

	if (S_ISDIR(stb1.st_mode) && S_ISDIR(stb2.st_mode)) {
		printf("Common subdirectories: %s and %s\n", fullpath1, fullpath2);
		goto ret;
	}

	if (!S_ISREG(stb1.st_mode) && !S_ISDIR(stb1.st_mode))
		val = D_SKIPPED1;
	else if (!S_ISREG(stb2.st_mode) && !S_ISDIR(stb2.st_mode))
		val = D_SKIPPED2;
	else
		val = diffreg(fullpath1, fullpath2, flags);

	print_status(val, fullpath1, fullpath2, NULL);
 ret:
	free(fullpath1);
	free(fullpath2);
}
#endif


#if ENABLE_FEATURE_DIFF_DIR
static int dir_strcmp(const void *p1, const void *p2)
{
	return strcmp(*(char *const *) p1, *(char *const *) p2);
}


/* This function adds a filename to dl, the directory listing. */
static int add_to_dirlist(const char *filename,
		struct stat ATTRIBUTE_UNUSED * sb, void *userdata,
		int depth ATTRIBUTE_UNUSED)
{
	/* +2: with space for eventual trailing NULL */
	dl = xrealloc(dl, (dl_count+2) * sizeof(dl[0]));
	dl[dl_count] = xstrdup(filename + (int)(ptrdiff_t)userdata);
	dl_count++;
	return TRUE;
}


/* This returns a sorted directory listing. */
static char **get_dir(char *path)
{
	dl_count = 0;
	dl = xzalloc(sizeof(dl[0]));

	/* If -r has been set, then the recursive_action function will be
	 * used. Unfortunately, this outputs the root directory along with
	 * the recursed paths, so use void *userdata to specify the string
	 * length of the root directory - '(void*)(strlen(path)+)'.
	 * add_to_dirlist then removes root dir prefix. */

	if (option_mask32 & FLAG_r) {
		recursive_action(path, ACTION_RECURSE|ACTION_FOLLOWLINKS,
					add_to_dirlist, NULL,
					(void*)(strlen(path)+1), 0);
	} else {
		DIR *dp;
		struct dirent *ep;

		dp = warn_opendir(path);
		while ((ep = readdir(dp))) {
			if (!strcmp(ep->d_name, "..") || LONE_CHAR(ep->d_name, '.'))
				continue;
			add_to_dirlist(ep->d_name, NULL, (void*)(int)0, 0);
		}
		closedir(dp);
	}

	/* Sort dl alphabetically. */
	qsort(dl, dl_count, sizeof(char *), dir_strcmp);

	dl[dl_count] = NULL;
	return dl;
}


static void diffdir(char *p1, char *p2)
{
	char **dirlist1, **dirlist2;
	char *dp1, *dp2;
	int pos;

	/* Check for trailing slashes. */
	dp1 = last_char_is(p1, '/');
	if (dp1 != NULL)
		*dp1 = '\0';
	dp2 = last_char_is(p2, '/');
	if (dp2 != NULL)
		*dp2 = '\0';

	/* Get directory listings for p1 and p2. */

	dirlist1 = get_dir(p1);
	dirlist2 = get_dir(p2);

	/* If -S was set, find the starting point. */
	if (start) {
		while (*dirlist1 != NULL && strcmp(*dirlist1, start) < 0)
			dirlist1++;
		while (*dirlist2 != NULL && strcmp(*dirlist2, start) < 0)
			dirlist2++;
		if ((*dirlist1 == NULL) || (*dirlist2 == NULL))
			bb_error_msg(bb_msg_invalid_arg, "NULL", "-S");
	}

	/* Now that both dirlist1 and dirlist2 contain sorted directory
	 * listings, we can start to go through dirlist1. If both listings
	 * contain the same file, then do a normal diff. Otherwise, behaviour
	 * is determined by whether the -N flag is set. */
	while (*dirlist1 != NULL || *dirlist2 != NULL) {
		dp1 = *dirlist1;
		dp2 = *dirlist2;
		pos = dp1 == NULL ? 1 : dp2 == NULL ? -1 : strcmp(dp1, dp2);
		if (pos == 0) {
			do_diff(p1, dp1, p2, dp2);
			dirlist1++;
			dirlist2++;
		} else if (pos < 0) {
			if (option_mask32 & FLAG_N)
				do_diff(p1, dp1, p2, NULL);
			else
				print_only(p1, strlen(p1) + 1, dp1);
			dirlist1++;
		} else {
			if (option_mask32 & FLAG_N)
				do_diff(p1, NULL, p2, dp2);
			else
				print_only(p2, strlen(p2) + 1, dp2);
			dirlist2++;
		}
	}
}
#endif


int diff_main(int argc, char **argv) MAIN_EXTERNALLY_VISIBLE;
int diff_main(int argc, char **argv)
{
	bool gotstdin = 0;
	char *U_opt;
	char *f1, *f2;
	llist_t *L_arg = NULL;

	INIT_G();

	/* exactly 2 params; collect multiple -L <label> */
	opt_complementary = "=2:L::";
	getopt32(argv, "abdiL:NqrsS:tTU:wu"
			"p" /* ignored (for compatibility) */,
			&L_arg, &start, &U_opt);
	/*argc -= optind;*/
	argv += optind;
	while (L_arg) {
		if (label1 && label2)
			bb_show_usage();
		if (!label1)
			label1 = L_arg->data;
		else { /* then label2 is NULL */
			label2 = label1;
			label1 = L_arg->data;
		}
		/* we leak L_arg here... */
		L_arg = L_arg->link;
	}
	if (option_mask32 & FLAG_U)
		context = xatoi_u(U_opt);

	/*
	 * Do sanity checks, fill in stb1 and stb2 and call the appropriate
	 * driver routine.  Both drivers use the contents of stb1 and stb2.
	 */

	f1 = argv[0];
	f2 = argv[1];
	if (LONE_DASH(f1)) {
		fstat(STDIN_FILENO, &stb1);
		gotstdin = 1;
	} else
		xstat(f1, &stb1);
	if (LONE_DASH(f2)) {
		fstat(STDIN_FILENO, &stb2);
		gotstdin = 1;
	} else
		xstat(f2, &stb2);
	if (gotstdin && (S_ISDIR(stb1.st_mode) || S_ISDIR(stb2.st_mode)))
		bb_error_msg_and_die("can't compare - to a directory");
	if (S_ISDIR(stb1.st_mode) && S_ISDIR(stb2.st_mode)) {
#if ENABLE_FEATURE_DIFF_DIR
		diffdir(f1, f2);
#else
		bb_error_msg_and_die("directory comparison not supported");
#endif
	} else {
		if (S_ISDIR(stb1.st_mode)) {
			f1 = concat_path_file(f1, f2);
			xstat(f1, &stb1);
		}
		if (S_ISDIR(stb2.st_mode)) {
			f2 = concat_path_file(f2, f1);
			xstat(f2, &stb2);
		}
/* XXX: FIXME: */
/* We can't diff e.g. stdin supplied by a pipe - we use rewind(), fseek().
 * This can be fixed (volunteers?) */
		if (!S_ISREG(stb1.st_mode) || !S_ISREG(stb2.st_mode))
			bb_error_msg_and_die("can't diff non-seekable stream");
		print_status(diffreg(f1, f2, 0), f1, f2, NULL);
	}
	return status;
}
